123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958 |
- /* varobj support for C and C++.
- Copyright (C) 1999-2022 Free Software Foundation, Inc.
- This program is free software; you can redistribute it and/or modify
- it under the terms of the GNU General Public License as published by
- the Free Software Foundation; either version 3 of the License, or
- (at your option) any later version.
- This program is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- GNU General Public License for more details.
- You should have received a copy of the GNU General Public License
- along with this program. If not, see <http://www.gnu.org/licenses/>. */
- #include "defs.h"
- #include "value.h"
- #include "varobj.h"
- #include "gdbthread.h"
- #include "valprint.h"
- static void cplus_class_num_children (struct type *type, int children[3]);
- /* The names of varobjs representing anonymous structs or unions. */
- #define ANONYMOUS_STRUCT_NAME _("<anonymous struct>")
- #define ANONYMOUS_UNION_NAME _("<anonymous union>")
- /* Does CHILD represent a child with no name? This happens when
- the child is an anonymous struct or union and it has no field name
- in its parent variable.
- This has already been determined by *_describe_child. The easiest
- thing to do is to compare the child's name with ANONYMOUS_*_NAME. */
- bool
- varobj_is_anonymous_child (const struct varobj *child)
- {
- return (child->name == ANONYMOUS_STRUCT_NAME
- || child->name == ANONYMOUS_UNION_NAME);
- }
- /* Given the value and the type of a variable object,
- adjust the value and type to those necessary
- for getting children of the variable object.
- This includes dereferencing top-level references
- to all types and dereferencing pointers to
- structures.
- If LOOKUP_ACTUAL_TYPE is set the enclosing type of the
- value will be fetched and if it differs from static type
- the value will be casted to it.
- Both TYPE and *TYPE should be non-null. VALUE
- can be null if we want to only translate type.
- *VALUE can be null as well -- if the parent
- value is not known.
- If WAS_PTR is not NULL, set *WAS_PTR to 0 or 1
- depending on whether pointer was dereferenced
- in this function. */
- static void
- adjust_value_for_child_access (struct value **value,
- struct type **type,
- int *was_ptr,
- int lookup_actual_type)
- {
- gdb_assert (type && *type);
- if (was_ptr)
- *was_ptr = 0;
- *type = check_typedef (*type);
-
- /* The type of value stored in varobj, that is passed
- to us, is already supposed to be
- reference-stripped. */
- gdb_assert (!TYPE_IS_REFERENCE (*type));
- /* Pointers to structures are treated just like
- structures when accessing children. Don't
- dereference pointers to other types. */
- if ((*type)->code () == TYPE_CODE_PTR)
- {
- struct type *target_type = get_target_type (*type);
- if (target_type->code () == TYPE_CODE_STRUCT
- || target_type->code () == TYPE_CODE_UNION)
- {
- if (value && *value)
- {
- try
- {
- *value = value_ind (*value);
- }
- catch (const gdb_exception_error &except)
- {
- *value = NULL;
- }
- }
- *type = target_type;
- if (was_ptr)
- *was_ptr = 1;
- }
- }
- /* The 'get_target_type' function calls check_typedef on
- result, so we can immediately check type code. No
- need to call check_typedef here. */
- /* Access a real type of the value (if necessary and possible). */
- if (value && *value && lookup_actual_type)
- {
- struct type *enclosing_type;
- int real_type_found = 0;
- enclosing_type = value_actual_type (*value, 1, &real_type_found);
- if (real_type_found)
- {
- *type = enclosing_type;
- *value = value_cast (enclosing_type, *value);
- }
- }
- }
- /* Is VAR a path expression parent, i.e., can it be used to construct
- a valid path expression? */
- static bool
- c_is_path_expr_parent (const struct varobj *var)
- {
- struct type *type;
- /* "Fake" children are not path_expr parents. */
- if (CPLUS_FAKE_CHILD (var))
- return false;
- type = varobj_get_gdb_type (var);
- /* Anonymous unions and structs are also not path_expr parents. */
- if ((type->code () == TYPE_CODE_STRUCT
- || type->code () == TYPE_CODE_UNION)
- && type->name () == NULL)
- {
- const struct varobj *parent = var->parent;
- while (parent != NULL && CPLUS_FAKE_CHILD (parent))
- parent = parent->parent;
- if (parent != NULL)
- {
- struct type *parent_type;
- int was_ptr;
- parent_type = varobj_get_value_type (parent);
- adjust_value_for_child_access (NULL, &parent_type, &was_ptr, 0);
- if (parent_type->code () == TYPE_CODE_STRUCT
- || parent_type->code () == TYPE_CODE_UNION)
- {
- const char *field_name;
- gdb_assert (var->index < parent_type->num_fields ());
- field_name = parent_type->field (var->index).name ();
- return !(field_name == NULL || *field_name == '\0');
- }
- }
- return false;
- }
- return true;
- }
- /* C */
- static int
- c_number_of_children (const struct varobj *var)
- {
- struct type *type = varobj_get_value_type (var);
- int children = 0;
- struct type *target;
- adjust_value_for_child_access (NULL, &type, NULL, 0);
- target = get_target_type (type);
- switch (type->code ())
- {
- case TYPE_CODE_ARRAY:
- if (TYPE_LENGTH (type) > 0 && TYPE_LENGTH (target) > 0
- && (type->bounds ()->high.kind () != PROP_UNDEFINED))
- children = TYPE_LENGTH (type) / TYPE_LENGTH (target);
- else
- /* If we don't know how many elements there are, don't display
- any. */
- children = 0;
- break;
- case TYPE_CODE_STRUCT:
- case TYPE_CODE_UNION:
- children = type->num_fields ();
- break;
- case TYPE_CODE_PTR:
- /* The type here is a pointer to non-struct. Typically, pointers
- have one child, except for function ptrs, which have no children,
- and except for void*, as we don't know what to show.
- We can show char* so we allow it to be dereferenced. If you decide
- to test for it, please mind that a little magic is necessary to
- properly identify it: char* has TYPE_CODE == TYPE_CODE_INT and
- TYPE_NAME == "char". */
- if (target->code () == TYPE_CODE_FUNC
- || target->code () == TYPE_CODE_VOID)
- children = 0;
- else
- children = 1;
- break;
- default:
- /* Other types have no children. */
- break;
- }
- return children;
- }
- static std::string
- c_name_of_variable (const struct varobj *parent)
- {
- return parent->name;
- }
- /* Return the value of element TYPE_INDEX of a structure
- value VALUE. VALUE's type should be a structure,
- or union, or a typedef to struct/union.
- Returns NULL if getting the value fails. Never throws. */
- static struct value *
- value_struct_element_index (struct value *value, int type_index)
- {
- struct value *result = NULL;
- struct type *type = value_type (value);
- type = check_typedef (type);
- gdb_assert (type->code () == TYPE_CODE_STRUCT
- || type->code () == TYPE_CODE_UNION);
- try
- {
- if (field_is_static (&type->field (type_index)))
- result = value_static_field (type, type_index);
- else
- result = value_primitive_field (value, 0, type_index, type);
- }
- catch (const gdb_exception_error &e)
- {
- return NULL;
- }
- return result;
- }
- /* Obtain the information about child INDEX of the variable
- object PARENT.
- If CNAME is not null, sets *CNAME to the name of the child relative
- to the parent.
- If CVALUE is not null, sets *CVALUE to the value of the child.
- If CTYPE is not null, sets *CTYPE to the type of the child.
- If any of CNAME, CVALUE, or CTYPE is not null, but the corresponding
- information cannot be determined, set *CNAME, *CVALUE, or *CTYPE
- to empty. */
- static void
- c_describe_child (const struct varobj *parent, int index,
- std::string *cname, struct value **cvalue,
- struct type **ctype, std::string *cfull_expression)
- {
- struct value *value = parent->value.get ();
- struct type *type = varobj_get_value_type (parent);
- std::string parent_expression;
- int was_ptr;
- if (cname)
- *cname = std::string ();
- if (cvalue)
- *cvalue = NULL;
- if (ctype)
- *ctype = NULL;
- if (cfull_expression)
- {
- *cfull_expression = std::string ();
- parent_expression
- = varobj_get_path_expr (varobj_get_path_expr_parent (parent));
- }
- adjust_value_for_child_access (&value, &type, &was_ptr, 0);
- switch (type->code ())
- {
- case TYPE_CODE_ARRAY:
- if (cname)
- *cname = int_string (index + type->bounds ()->low.const_val (),
- 10, 1, 0, 0);
- if (cvalue && value)
- {
- int real_index
- = index + type->bounds ()->low.const_val ();
- try
- {
- *cvalue = value_subscript (value, real_index);
- }
- catch (const gdb_exception_error &except)
- {
- }
- }
- if (ctype)
- *ctype = get_target_type (type);
- if (cfull_expression)
- *cfull_expression = string_printf
- ("(%s)[%s]", parent_expression.c_str (),
- int_string (index + type->bounds ()->low.const_val (),
- 10, 1, 0, 0));
- break;
- case TYPE_CODE_STRUCT:
- case TYPE_CODE_UNION:
- {
- const char *field_name;
- /* If the type is anonymous and the field has no name,
- set an appropriate name. */
- field_name = type->field (index).name ();
- if (field_name == NULL || *field_name == '\0')
- {
- if (cname)
- {
- if (type->field (index).type ()->code ()
- == TYPE_CODE_STRUCT)
- *cname = ANONYMOUS_STRUCT_NAME;
- else
- *cname = ANONYMOUS_UNION_NAME;
- }
- if (cfull_expression)
- *cfull_expression = "";
- }
- else
- {
- if (cname)
- *cname = field_name;
- if (cfull_expression)
- {
- const char *join = was_ptr ? "->" : ".";
- *cfull_expression = string_printf ("(%s)%s%s",
- parent_expression.c_str (),
- join, field_name);
- }
- }
- if (cvalue && value)
- {
- /* For C, varobj index is the same as type index. */
- *cvalue = value_struct_element_index (value, index);
- }
- if (ctype)
- *ctype = type->field (index).type ();
- }
- break;
- case TYPE_CODE_PTR:
- if (cname)
- *cname = string_printf ("*%s", parent->name.c_str ());
- if (cvalue && value)
- {
- try
- {
- *cvalue = value_ind (value);
- }
- catch (const gdb_exception_error &except)
- {
- *cvalue = NULL;
- }
- }
- /* Don't use get_target_type because it calls
- check_typedef and here, we want to show the true
- declared type of the variable. */
- if (ctype)
- *ctype = TYPE_TARGET_TYPE (type);
- if (cfull_expression)
- *cfull_expression = string_printf ("*(%s)", parent_expression.c_str ());
- break;
- default:
- /* This should not happen. */
- if (cname)
- *cname = "???";
- if (cfull_expression)
- *cfull_expression = "???";
- /* Don't set value and type, we don't know then. */
- }
- }
- static std::string
- c_name_of_child (const struct varobj *parent, int index)
- {
- std::string name;
- c_describe_child (parent, index, &name, NULL, NULL, NULL);
- return name;
- }
- static std::string
- c_path_expr_of_child (const struct varobj *child)
- {
- std::string path_expr;
- c_describe_child (child->parent, child->index, NULL, NULL, NULL,
- &path_expr);
- return path_expr;
- }
- static struct value *
- c_value_of_child (const struct varobj *parent, int index)
- {
- struct value *value = NULL;
- c_describe_child (parent, index, NULL, &value, NULL, NULL);
- return value;
- }
- static struct type *
- c_type_of_child (const struct varobj *parent, int index)
- {
- struct type *type = NULL;
- c_describe_child (parent, index, NULL, NULL, &type, NULL);
- return type;
- }
- /* This returns the type of the variable. It also skips past typedefs
- to return the real type of the variable. */
- static struct type *
- get_type (const struct varobj *var)
- {
- struct type *type;
- type = var->type;
- if (type != NULL)
- type = check_typedef (type);
- return type;
- }
- static std::string
- c_value_of_variable (const struct varobj *var,
- enum varobj_display_formats format)
- {
- /* BOGUS: if val_print sees a struct/class, or a reference to one,
- it will print out its children instead of "{...}". So we need to
- catch that case explicitly. */
- struct type *type = get_type (var);
- /* Strip top-level references. */
- while (TYPE_IS_REFERENCE (type))
- type = check_typedef (TYPE_TARGET_TYPE (type));
- switch (type->code ())
- {
- case TYPE_CODE_STRUCT:
- case TYPE_CODE_UNION:
- return "{...}";
- /* break; */
- case TYPE_CODE_ARRAY:
- return string_printf ("[%d]", var->num_children);
- /* break; */
- default:
- {
- if (var->value == NULL)
- {
- /* This can happen if we attempt to get the value of a struct
- member when the parent is an invalid pointer. This is an
- error condition, so we should tell the caller. */
- return std::string ();
- }
- else
- {
- if (var->not_fetched && value_lazy (var->value.get ()))
- /* Frozen variable and no value yet. We don't
- implicitly fetch the value. MI response will
- use empty string for the value, which is OK. */
- return std::string ();
- gdb_assert (varobj_value_is_changeable_p (var));
- gdb_assert (!value_lazy (var->value.get ()));
-
- /* If the specified format is the current one,
- we can reuse print_value. */
- if (format == var->format)
- return var->print_value;
- else
- return varobj_value_get_print_value (var->value.get (), format,
- var);
- }
- }
- }
- }
- /* varobj operations for c. */
- const struct lang_varobj_ops c_varobj_ops =
- {
- c_number_of_children,
- c_name_of_variable,
- c_name_of_child,
- c_path_expr_of_child,
- c_value_of_child,
- c_type_of_child,
- c_value_of_variable,
- varobj_default_value_is_changeable_p,
- NULL, /* value_has_mutated */
- c_is_path_expr_parent /* is_path_expr_parent */
- };
- /* A little convenience enum for dealing with C++. */
- enum vsections
- {
- v_public = 0, v_private, v_protected
- };
- /* C++ */
- static int
- cplus_number_of_children (const struct varobj *var)
- {
- struct value *value = NULL;
- struct type *type;
- int children, dont_know;
- int lookup_actual_type = 0;
- struct value_print_options opts;
- dont_know = 1;
- children = 0;
- get_user_print_options (&opts);
- if (!CPLUS_FAKE_CHILD (var))
- {
- type = varobj_get_value_type (var);
- /* It is necessary to access a real type (via RTTI). */
- if (opts.objectprint)
- {
- value = var->value.get ();
- lookup_actual_type = var->type->is_pointer_or_reference ();
- }
- adjust_value_for_child_access (&value, &type, NULL, lookup_actual_type);
- if (((type->code ()) == TYPE_CODE_STRUCT)
- || ((type->code ()) == TYPE_CODE_UNION))
- {
- int kids[3];
- cplus_class_num_children (type, kids);
- if (kids[v_public] != 0)
- children++;
- if (kids[v_private] != 0)
- children++;
- if (kids[v_protected] != 0)
- children++;
- /* Add any baseclasses. */
- children += TYPE_N_BASECLASSES (type);
- dont_know = 0;
- /* FIXME: save children in var. */
- }
- }
- else
- {
- int kids[3];
- type = varobj_get_value_type (var->parent);
- /* It is necessary to access a real type (via RTTI). */
- if (opts.objectprint)
- {
- const struct varobj *parent = var->parent;
- value = parent->value.get ();
- lookup_actual_type = parent->type->is_pointer_or_reference ();
- }
- adjust_value_for_child_access (&value, &type, NULL, lookup_actual_type);
- cplus_class_num_children (type, kids);
- if (var->name == "public")
- children = kids[v_public];
- else if (var->name == "private")
- children = kids[v_private];
- else
- children = kids[v_protected];
- dont_know = 0;
- }
- if (dont_know)
- children = c_number_of_children (var);
- return children;
- }
- /* Compute # of public, private, and protected variables in this class.
- That means we need to descend into all baseclasses and find out
- how many are there, too. */
- static void
- cplus_class_num_children (struct type *type, int children[3])
- {
- int i, vptr_fieldno;
- struct type *basetype = NULL;
- children[v_public] = 0;
- children[v_private] = 0;
- children[v_protected] = 0;
- vptr_fieldno = get_vptr_fieldno (type, &basetype);
- for (i = TYPE_N_BASECLASSES (type); i < type->num_fields (); i++)
- {
- /* If we have a virtual table pointer, omit it. Even if virtual
- table pointers are not specifically marked in the debug info,
- they should be artificial. */
- if ((type == basetype && i == vptr_fieldno)
- || TYPE_FIELD_ARTIFICIAL (type, i))
- continue;
- if (TYPE_FIELD_PROTECTED (type, i))
- children[v_protected]++;
- else if (TYPE_FIELD_PRIVATE (type, i))
- children[v_private]++;
- else
- children[v_public]++;
- }
- }
- static std::string
- cplus_name_of_variable (const struct varobj *parent)
- {
- return c_name_of_variable (parent);
- }
- enum accessibility { private_field, protected_field, public_field };
- /* Check if field INDEX of TYPE has the specified accessibility.
- Return 0 if so and 1 otherwise. */
- static int
- match_accessibility (struct type *type, int index, enum accessibility acc)
- {
- if (acc == private_field && TYPE_FIELD_PRIVATE (type, index))
- return 1;
- else if (acc == protected_field && TYPE_FIELD_PROTECTED (type, index))
- return 1;
- else if (acc == public_field && !TYPE_FIELD_PRIVATE (type, index)
- && !TYPE_FIELD_PROTECTED (type, index))
- return 1;
- else
- return 0;
- }
- static void
- cplus_describe_child (const struct varobj *parent, int index,
- std::string *cname, struct value **cvalue, struct type **ctype,
- std::string *cfull_expression)
- {
- struct value *value;
- struct type *type;
- int was_ptr;
- int lookup_actual_type = 0;
- const char *parent_expression = NULL;
- const struct varobj *var;
- struct value_print_options opts;
- if (cname)
- *cname = std::string ();
- if (cvalue)
- *cvalue = NULL;
- if (ctype)
- *ctype = NULL;
- if (cfull_expression)
- *cfull_expression = std::string ();
- get_user_print_options (&opts);
- var = (CPLUS_FAKE_CHILD (parent)) ? parent->parent : parent;
- if (opts.objectprint)
- lookup_actual_type = var->type->is_pointer_or_reference ();
- value = var->value.get ();
- type = varobj_get_value_type (var);
- if (cfull_expression)
- parent_expression
- = varobj_get_path_expr (varobj_get_path_expr_parent (var));
- adjust_value_for_child_access (&value, &type, &was_ptr, lookup_actual_type);
- if (type->code () == TYPE_CODE_STRUCT
- || type->code () == TYPE_CODE_UNION)
- {
- const char *join = was_ptr ? "->" : ".";
- if (CPLUS_FAKE_CHILD (parent))
- {
- /* The fields of the class type are ordered as they
- appear in the class. We are given an index for a
- particular access control type ("public","protected",
- or "private"). We must skip over fields that don't
- have the access control we are looking for to properly
- find the indexed field. */
- int type_index = TYPE_N_BASECLASSES (type);
- enum accessibility acc = public_field;
- int vptr_fieldno;
- struct type *basetype = NULL;
- const char *field_name;
- vptr_fieldno = get_vptr_fieldno (type, &basetype);
- if (parent->name == "private")
- acc = private_field;
- else if (parent->name == "protected")
- acc = protected_field;
- while (index >= 0)
- {
- if ((type == basetype && type_index == vptr_fieldno)
- || TYPE_FIELD_ARTIFICIAL (type, type_index))
- ; /* ignore vptr */
- else if (match_accessibility (type, type_index, acc))
- --index;
- ++type_index;
- }
- --type_index;
- /* If the type is anonymous and the field has no name,
- set an appropriate name. */
- field_name = type->field (type_index).name ();
- if (field_name == NULL || *field_name == '\0')
- {
- if (cname)
- {
- if (type->field (type_index).type ()->code ()
- == TYPE_CODE_STRUCT)
- *cname = ANONYMOUS_STRUCT_NAME;
- else if (type->field (type_index).type ()->code ()
- == TYPE_CODE_UNION)
- *cname = ANONYMOUS_UNION_NAME;
- }
- if (cfull_expression)
- *cfull_expression = std::string ();
- }
- else
- {
- if (cname)
- *cname = type->field (type_index).name ();
- if (cfull_expression)
- *cfull_expression
- = string_printf ("((%s)%s%s)", parent_expression, join,
- field_name);
- }
- if (cvalue && value)
- *cvalue = value_struct_element_index (value, type_index);
- if (ctype)
- *ctype = type->field (type_index).type ();
- }
- else if (index < TYPE_N_BASECLASSES (type))
- {
- /* This is a baseclass. */
- if (cname)
- *cname = type->field (index).name ();
- if (cvalue && value)
- *cvalue = value_cast (type->field (index).type (), value);
- if (ctype)
- {
- *ctype = type->field (index).type ();
- }
- if (cfull_expression)
- {
- const char *ptr = was_ptr ? "*" : "";
- /* Cast the parent to the base' type. Note that in gdb,
- expression like
- (Base1)d
- will create an lvalue, for all appearences, so we don't
- need to use more fancy:
- *(Base1*)(&d)
- construct.
- When we are in the scope of the base class or of one
- of its children, the type field name will be interpreted
- as a constructor, if it exists. Therefore, we must
- indicate that the name is a class name by using the
- 'class' keyword. See PR mi/11912 */
- *cfull_expression = string_printf ("(%s(class %s%s) %s)",
- ptr,
- type->field (index).name (),
- ptr,
- parent_expression);
- }
- }
- else
- {
- const char *access = NULL;
- int children[3];
- cplus_class_num_children (type, children);
- /* Everything beyond the baseclasses can
- only be "public", "private", or "protected"
- The special "fake" children are always output by varobj in
- this order. So if INDEX == 2, it MUST be "protected". */
- index -= TYPE_N_BASECLASSES (type);
- switch (index)
- {
- case 0:
- if (children[v_public] > 0)
- access = "public";
- else if (children[v_private] > 0)
- access = "private";
- else
- access = "protected";
- break;
- case 1:
- if (children[v_public] > 0)
- {
- if (children[v_private] > 0)
- access = "private";
- else
- access = "protected";
- }
- else if (children[v_private] > 0)
- access = "protected";
- break;
- case 2:
- /* Must be protected. */
- access = "protected";
- break;
- default:
- /* error! */
- break;
- }
- gdb_assert (access);
- if (cname)
- *cname = access;
- /* Value and type and full expression are null here. */
- }
- }
- else
- {
- c_describe_child (parent, index, cname, cvalue, ctype, cfull_expression);
- }
- }
- static std::string
- cplus_name_of_child (const struct varobj *parent, int index)
- {
- std::string name;
- cplus_describe_child (parent, index, &name, NULL, NULL, NULL);
- return name;
- }
- static std::string
- cplus_path_expr_of_child (const struct varobj *child)
- {
- std::string path_expr;
- cplus_describe_child (child->parent, child->index, NULL, NULL, NULL,
- &path_expr);
- return path_expr;
- }
- static struct value *
- cplus_value_of_child (const struct varobj *parent, int index)
- {
- struct value *value = NULL;
- cplus_describe_child (parent, index, NULL, &value, NULL, NULL);
- return value;
- }
- static struct type *
- cplus_type_of_child (const struct varobj *parent, int index)
- {
- struct type *type = NULL;
- cplus_describe_child (parent, index, NULL, NULL, &type, NULL);
- return type;
- }
- static std::string
- cplus_value_of_variable (const struct varobj *var,
- enum varobj_display_formats format)
- {
- /* If we have one of our special types, don't print out
- any value. */
- if (CPLUS_FAKE_CHILD (var))
- return std::string ();
- return c_value_of_variable (var, format);
- }
- /* varobj operations for c++. */
- const struct lang_varobj_ops cplus_varobj_ops =
- {
- cplus_number_of_children,
- cplus_name_of_variable,
- cplus_name_of_child,
- cplus_path_expr_of_child,
- cplus_value_of_child,
- cplus_type_of_child,
- cplus_value_of_variable,
- varobj_default_value_is_changeable_p,
- NULL, /* value_has_mutated */
- c_is_path_expr_parent /* is_path_expr_parent */
- };
|