aboutsummaryrefslogtreecommitdiff
path: root/gdb/valops.c
diff options
context:
space:
mode:
authorJim Blandy <jimb@codesourcery.com>2001-04-27 00:19:09 +0000
committerJim Blandy <jimb@codesourcery.com>2001-04-27 00:19:09 +0000
commit015a42b4cf96cadcb996b6474ab61eca781fdde6 (patch)
tree9c6498c34c193f62714d7cded22a5537ec3be632 /gdb/valops.c
parent20b8570d73f0a4e0e83a44d6aaa639a93a17f3b8 (diff)
downloadgdb-015a42b4cf96cadcb996b6474ab61eca781fdde6.zip
gdb-015a42b4cf96cadcb996b6474ab61eca781fdde6.tar.gz
gdb-015a42b4cf96cadcb996b6474ab61eca781fdde6.tar.bz2
(Changes from Daniel Berlin, with revisions by Jim Blandy.)
Abstract out operations specific to particular C++ ABI's, and invoke them through a function table. This removes the C++ ABI dependencies scattered throughout the code, and allows us to cleanly add support for new C++ ABI's. * cp-abi.h, cp-abi.h, gnu-v2-abi.c, hpacc-abi.c: New files. * c-typeprint.c, c-valprint.c, dbxread.c, eval.c, gdbtypes.c, jv-typeprint.c, linespec.c, symtab.c, typeprint.c, valops.c: #include "cp-abi.h". These files all use functions now declared there. * symtab.h (OPNAME_PREFIX_P, VTBL_PREFIX_P, DESTRUCTOR_PREFIX_P): Deleted. These services are now provided by functions declared in cp-abi.h. * value.h (value_rtti_type, value_virtual_fn_field): Same. * values.c (value_virtual_fn_field): Same, for this definition. * valops.c (value_rtti_type): Same. * c-typeprint.c (c_type_print_base): Use the functions from "cp-abi.h", instead of the old macros, or hard-coded ABI-specific tests. * dbxread.c (record_minimal_symbol): Same. * gdbtypes.c (get_destructor_fn_field, virtual_base_index, virtual_base_index_skip_primaries): Same. * jv-typeprint.c (java_type_print_base): Same. * linespec.c (find_methods, decode_line_1): Same. * symtab.c (gdb_mangle_name): Same. * Makefile.in (SFILES): Add the new .c files mentioned above. (cp_abi_h): New variable. (COMMON_OBS): Add gnu-v2-abi.o, hpacc-abi.o, and cp-abi.o. (cp-abi.o, gnu-v2-abi.o, hpacc-abi.o): New targets. (c-typeprint.o, c-valprint.o, dbxread.o, eval.o, gdbtypes.o, jv-typeprint.o, symtab.o, linespec.o, typeprint.o, valops.o): Add dependency on $(cp_abi_h).
Diffstat (limited to 'gdb/valops.c')
-rw-r--r--gdb/valops.c221
1 files changed, 1 insertions, 220 deletions
diff --git a/gdb/valops.c b/gdb/valops.c
index 0ab0ae6..0e7e7e1 100644
--- a/gdb/valops.c
+++ b/gdb/valops.c
@@ -31,6 +31,7 @@
#include "language.h"
#include "gdbcmd.h"
#include "regcache.h"
+#include "cp-abi.h"
#include <errno.h>
#include "gdb_string.h"
@@ -3111,226 +3112,6 @@ value_struct_elt_for_reference (struct type *domain, int offset,
}
-/* Find the real run-time type of a value using RTTI.
- * V is a pointer to the value.
- * A pointer to the struct type entry of the run-time type
- * is returneed.
- * FULL is a flag that is set only if the value V includes
- * the entire contents of an object of the RTTI type.
- * TOP is the offset to the top of the enclosing object of
- * the real run-time type. This offset may be for the embedded
- * object, or for the enclosing object of V.
- * USING_ENC is the flag that distinguishes the two cases.
- * If it is 1, then the offset is for the enclosing object,
- * otherwise for the embedded object.
- *
- */
-
-struct type *
-value_rtti_type (value_ptr v, int *full, int *top, int *using_enc)
-{
- struct type *known_type;
- struct type *rtti_type;
- CORE_ADDR coreptr;
- value_ptr vp;
- int using_enclosing = 0;
- long top_offset = 0;
- char rtti_type_name[256];
-
- if (full)
- *full = 0;
- if (top)
- *top = -1;
- if (using_enc)
- *using_enc = 0;
-
- /* Get declared type */
- known_type = VALUE_TYPE (v);
- CHECK_TYPEDEF (known_type);
- /* RTTI works only or class objects */
- if (TYPE_CODE (known_type) != TYPE_CODE_CLASS)
- return NULL;
- if (TYPE_HAS_VTABLE(known_type))
- {
- /* If neither the declared type nor the enclosing type of the
- * value structure has a HP ANSI C++ style virtual table,
- * we can't do anything. */
- if (!TYPE_HAS_VTABLE (known_type))
- {
- known_type = VALUE_ENCLOSING_TYPE (v);
- CHECK_TYPEDEF (known_type);
- if ((TYPE_CODE (known_type) != TYPE_CODE_CLASS) ||
- !TYPE_HAS_VTABLE (known_type))
- return NULL; /* No RTTI, or not HP-compiled types */
- CHECK_TYPEDEF (known_type);
- using_enclosing = 1;
- }
-
- if (using_enclosing && using_enc)
- *using_enc = 1;
-
- /* First get the virtual table address */
- coreptr = *(CORE_ADDR *) ((VALUE_CONTENTS_ALL (v))
- + VALUE_OFFSET (v)
- + (using_enclosing ? 0 : VALUE_EMBEDDED_OFFSET (v)));
- if (coreptr == 0)
- return NULL; /* return silently -- maybe called on gdb-generated value */
-
- /* Fetch the top offset of the object */
- /* FIXME possible 32x64 problem with pointer size & arithmetic */
- vp = value_at (builtin_type_int,
- coreptr + 4 * HP_ACC_TOP_OFFSET_OFFSET,
- VALUE_BFD_SECTION (v));
- top_offset = value_as_long (vp);
- if (top)
- *top = top_offset;
-
- /* Fetch the typeinfo pointer */
- /* FIXME possible 32x64 problem with pointer size & arithmetic */
- vp = value_at (builtin_type_int, coreptr + 4 * HP_ACC_TYPEINFO_OFFSET, VALUE_BFD_SECTION (v));
- /* Indirect through the typeinfo pointer and retrieve the pointer
- * to the string name */
- coreptr = *(CORE_ADDR *) (VALUE_CONTENTS (vp));
- if (!coreptr)
- error ("Retrieved null typeinfo pointer in trying to determine run-time type");
- vp = value_at (builtin_type_int, coreptr + 4, VALUE_BFD_SECTION (v)); /* 4 -> offset of name field */
- /* FIXME possible 32x64 problem */
-
- coreptr = *(CORE_ADDR *) (VALUE_CONTENTS (vp));
-
- read_memory_string (coreptr, rtti_type_name, 256);
-
- if (strlen (rtti_type_name) == 0)
- error ("Retrieved null type name from typeinfo");
-
- /* search for type */
- rtti_type = lookup_typename (rtti_type_name, (struct block *) 0, 1);
-
- if (!rtti_type)
- error ("Could not find run-time type: invalid type name %s in typeinfo??", rtti_type_name);
- CHECK_TYPEDEF (rtti_type);
-#if 0
- printf ("RTTI type name %s, tag %s, full? %d\n", TYPE_NAME (rtti_type), TYPE_TAG_NAME (rtti_type), full ? *full : -1);
-#endif
- /* Check whether we have the entire object */
- if (full /* Non-null pointer passed */
- &&
- /* Either we checked on the whole object in hand and found the
- top offset to be zero */
- (((top_offset == 0) &&
- using_enclosing &&
- TYPE_LENGTH (known_type) == TYPE_LENGTH (rtti_type))
- ||
- /* Or we checked on the embedded object and top offset was the
- same as the embedded offset */
- ((top_offset == VALUE_EMBEDDED_OFFSET (v)) &&
- !using_enclosing &&
- TYPE_LENGTH (VALUE_ENCLOSING_TYPE (v)) == TYPE_LENGTH (rtti_type))))
-
- *full = 1;
- }
- else
- /*
- Right now this is G++ RTTI. Plan on this changing in the
- future as i get around to setting the vtables properly for G++
- compiled stuff. Also, i'll be using the type info functions,
- which are always right. Deal with it until then.
- */
- {
- CORE_ADDR vtbl;
- struct minimal_symbol *minsym;
- struct symbol *sym;
- char *demangled_name;
- struct type *btype;
- /* If the type has no vptr fieldno, try to get it filled in */
- if (TYPE_VPTR_FIELDNO(known_type) < 0)
- fill_in_vptr_fieldno(known_type);
-
- /* If we still can't find one, give up */
- if (TYPE_VPTR_FIELDNO(known_type) < 0)
- return NULL;
-
- /* Make sure our basetype and known type match, otherwise, cast
- so we can get at the vtable properly.
- */
- btype = TYPE_VPTR_BASETYPE (known_type);
- CHECK_TYPEDEF (btype);
- if (btype != known_type )
- {
- v = value_cast (btype, v);
- if (using_enc)
- *using_enc=1;
- }
- /*
- We can't use value_ind here, because it would want to use RTTI, and
- we'd waste a bunch of time figuring out we already know the type.
- Besides, we don't care about the type, just the actual pointer
- */
- if (VALUE_ADDRESS (value_field (v, TYPE_VPTR_FIELDNO (known_type))) == 0)
- return NULL;
-
- /*
- If we are enclosed by something that isn't us, adjust the
- address properly and set using_enclosing.
- */
- if (VALUE_ENCLOSING_TYPE(v) != VALUE_TYPE(v))
- {
- value_ptr tempval;
- tempval=value_field(v,TYPE_VPTR_FIELDNO(known_type));
- VALUE_ADDRESS(tempval)+=(TYPE_BASECLASS_BITPOS(known_type,TYPE_VPTR_FIELDNO(known_type))/8);
- vtbl=value_as_pointer(tempval);
- using_enclosing=1;
- }
- else
- {
- vtbl=value_as_pointer(value_field(v,TYPE_VPTR_FIELDNO(known_type)));
- using_enclosing=0;
- }
-
- /* Try to find a symbol that is the vtable */
- minsym=lookup_minimal_symbol_by_pc(vtbl);
- if (minsym==NULL || (demangled_name=SYMBOL_NAME(minsym))==NULL || !VTBL_PREFIX_P(demangled_name))
- return NULL;
-
- /* If we just skip the prefix, we get screwed by namespaces */
- demangled_name=cplus_demangle(demangled_name,DMGL_PARAMS|DMGL_ANSI);
- *(strchr(demangled_name,' '))=0;
-
- /* Lookup the type for the name */
- rtti_type=lookup_typename(demangled_name, (struct block *)0,1);
-
- if (rtti_type==NULL)
- return NULL;
-
- if (TYPE_N_BASECLASSES(rtti_type) > 1 && full && (*full) != 1)
- {
- if (top)
- *top=TYPE_BASECLASS_BITPOS(rtti_type,TYPE_VPTR_FIELDNO(rtti_type))/8;
- if (top && ((*top) >0))
- {
- if (TYPE_LENGTH(rtti_type) > TYPE_LENGTH(known_type))
- {
- if (full)
- *full=0;
- }
- else
- {
- if (full)
- *full=1;
- }
- }
- }
- else
- {
- if (full)
- *full=1;
- }
- if (using_enc)
- *using_enc=using_enclosing;
- }
- return rtti_type;
-}
-
/* Given a pointer value V, find the real (RTTI) type
of the object it points to.
Other parameters FULL, TOP, USING_ENC as with value_rtti_type()