any of the current compilation units are processed. */
unsigned int queued : 1;
- /* This flag will be set if we need to load absolutely all DIEs
- for this compilation unit, instead of just the ones we think
- are interesting. It gets set if we look for a DIE in the
+ /* This flag will be set when reading partial DIEs if we need to load
+ absolutely all DIEs for this compilation unit, instead of just the ones
+ we think are interesting. It gets set if we look for a DIE in the
hash table and don't find it. */
unsigned int load_all_dies : 1;
static void load_full_type_unit (struct dwarf2_per_cu_data *per_cu);
-static void read_signatured_type (struct signatured_type *type_sig);
+static void read_signatured_type (struct signatured_type *);
/* memory allocation interface */
static void create_all_comp_units (struct objfile *);
-static int create_debug_types_hash_table (struct objfile *objfile);
+static int create_all_type_units (struct objfile *);
static void load_full_comp_unit (struct dwarf2_per_cu_data *);
for (i = 0; i < elements; i += 3)
{
- struct signatured_type *type_sig;
- ULONGEST offset, type_offset, signature;
+ struct signatured_type *sig_type;
+ ULONGEST offset, type_offset_in_tu, signature;
void **slot;
if (!extract_cu_value (bytes, &offset)
- || !extract_cu_value (bytes + 8, &type_offset))
+ || !extract_cu_value (bytes + 8, &type_offset_in_tu))
return 0;
signature = extract_unsigned_integer (bytes + 16, 8, BFD_ENDIAN_LITTLE);
bytes += 3 * 8;
- type_sig = OBSTACK_ZALLOC (&objfile->objfile_obstack,
+ sig_type = OBSTACK_ZALLOC (&objfile->objfile_obstack,
struct signatured_type);
- type_sig->signature = signature;
- type_sig->type_offset.cu_off = type_offset;
- type_sig->per_cu.debug_types_section = section;
- type_sig->per_cu.offset.sect_off = offset;
- type_sig->per_cu.objfile = objfile;
- type_sig->per_cu.v.quick
+ sig_type->signature = signature;
+ sig_type->type_offset.cu_off = type_offset_in_tu;
+ sig_type->per_cu.debug_types_section = section;
+ sig_type->per_cu.offset.sect_off = offset;
+ sig_type->per_cu.objfile = objfile;
+ sig_type->per_cu.v.quick
= OBSTACK_ZALLOC (&objfile->objfile_obstack,
struct dwarf2_per_cu_quick_data);
- slot = htab_find_slot (sig_types_hash, type_sig, INSERT);
- *slot = type_sig;
+ slot = htab_find_slot (sig_types_hash, sig_type, INSERT);
+ *slot = sig_type;
- dwarf2_per_objfile->all_type_units[i / 3] = &type_sig->per_cu;
+ dwarf2_per_objfile->all_type_units[i / 3] = &sig_type->per_cu;
}
dwarf2_per_objfile->signatured_types = sig_types_hash;
dwarf2_per_objfile->using_index = 1;
create_all_comp_units (objfile);
- create_debug_types_hash_table (objfile);
+ create_all_type_units (objfile);
dwarf2_per_objfile->quick_file_names_table =
create_quick_file_names_table (dwarf2_per_objfile->n_comp_units);
}
static hashval_t
-hash_type_signature (const void *item)
+hash_signatured_type (const void *item)
{
- const struct signatured_type *type_sig = item;
+ const struct signatured_type *sig_type = item;
/* This drops the top 32 bits of the signature, but is ok for a hash. */
- return type_sig->signature;
+ return sig_type->signature;
}
static int
-eq_type_signature (const void *item_lhs, const void *item_rhs)
+eq_signatured_type (const void *item_lhs, const void *item_rhs)
{
const struct signatured_type *lhs = item_lhs;
const struct signatured_type *rhs = item_rhs;
allocate_signatured_type_table (struct objfile *objfile)
{
return htab_create_alloc_ex (41,
- hash_type_signature,
- eq_type_signature,
+ hash_signatured_type,
+ eq_signatured_type,
NULL,
&objfile->objfile_obstack,
hashtab_obstack_allocate,
}
/* Create the hash table of all entries in the .debug_types section(s).
- The result is zero if there is an error (e.g. missing .debug_types section),
- otherwise non-zero. */
+ The result is zero if there are no .debug_types sections,
+ otherwise non-zero. */
static int
-create_debug_types_hash_table (struct objfile *objfile)
+create_all_type_units (struct objfile *objfile)
{
htab_t types_htab = NULL;
struct dwarf2_per_cu_data **iter;
sect_offset offset;
cu_offset type_offset;
ULONGEST signature;
- struct signatured_type *type_sig;
+ struct signatured_type *sig_type;
void **slot;
gdb_byte *ptr = info_ptr;
struct comp_unit_head header;
continue;
}
- type_sig = obstack_alloc (&objfile->objfile_obstack, sizeof (*type_sig));
- memset (type_sig, 0, sizeof (*type_sig));
- type_sig->signature = signature;
- type_sig->type_offset = type_offset;
- type_sig->per_cu.objfile = objfile;
- type_sig->per_cu.debug_types_section = section;
- type_sig->per_cu.offset = offset;
+ sig_type = obstack_alloc (&objfile->objfile_obstack, sizeof (*sig_type));
+ memset (sig_type, 0, sizeof (*sig_type));
+ sig_type->signature = signature;
+ sig_type->type_offset = type_offset;
+ sig_type->per_cu.objfile = objfile;
+ sig_type->per_cu.debug_types_section = section;
+ sig_type->per_cu.offset = offset;
- slot = htab_find_slot (types_htab, type_sig, INSERT);
+ slot = htab_find_slot (types_htab, sig_type, INSERT);
gdb_assert (slot != NULL);
if (*slot != NULL)
{
phex (signature, sizeof (signature)));
gdb_assert (signature == dup_sig->signature);
}
- *slot = type_sig;
+ *slot = sig_type;
if (dwarf2_die_debug)
fprintf_unfiltered (gdb_stdlog, " offset 0x%x, signature 0x%s\n",
}
/* Lookup a signature based type.
- Returns NULL if SIG is not present in the table. */
+ Returns NULL if signature SIG is not present in the table. */
static struct signatured_type *
-lookup_signatured_type (struct objfile *objfile, ULONGEST sig)
+lookup_signatured_type (ULONGEST sig)
{
struct signatured_type find_entry, *entry;
static void
build_type_psymtabs (struct objfile *objfile)
{
- if (! create_debug_types_hash_table (objfile))
+ if (! create_all_type_units (objfile))
return;
htab_traverse_noresize (dwarf2_per_objfile->signatured_types,
if (cu->per_cu->debug_types_section
&& die_is_declaration (die, cu))
{
- struct signatured_type *type_sig;
+ struct signatured_type *sig_type;
- type_sig
+ sig_type
= lookup_signatured_type_at_offset (dwarf2_per_objfile->objfile,
cu->per_cu->debug_types_section,
cu->per_cu->offset);
- if (type_sig->per_cu.offset.sect_off + type_sig->type_offset.cu_off
+ if (sig_type->per_cu.offset.sect_off + sig_type->type_offset.cu_off
!= die->offset.sect_off)
return;
}
struct abbrev_info *abbrev;
unsigned int bytes_read;
unsigned int load_all = 0;
-
int nesting_level = 1;
parent_die = NULL;
last_die = NULL;
- if (cu->per_cu && cu->per_cu->load_all_dies)
+ gdb_assert (cu->per_cu != NULL);
+ if (cu->per_cu->load_all_dies)
load_all = 1;
cu->partial_dies
}
}
- /* We only recurse into subprograms looking for template arguments.
+ /* We only recurse into c++ subprograms looking for template arguments.
Skip their other children. */
if (!load_all
&& cu->language == language_cplus
struct dwarf2_per_cu_data *per_cu = NULL;
struct partial_die_info *pd = NULL;
- if (cu->per_cu->debug_types_section)
- {
- pd = find_partial_die_in_comp_unit (offset, cu);
- if (pd != NULL)
- return pd;
- goto not_found;
- }
-
if (offset_in_cu_p (&cu->header, offset))
{
pd = find_partial_die_in_comp_unit (offset, cu);
if (pd != NULL)
return pd;
+ /* We missed recording what we needed.
+ Load all dies and try again. */
+ per_cu = cu->per_cu;
}
+ else
+ {
+ /* TUs don't reference other CUs/TUs (except via type signatures). */
+ if (cu->per_cu->debug_types_section)
+ {
+ error (_("Dwarf Error: Type Unit at offset 0x%lx contains"
+ " external reference to offset 0x%lx [in module %s].\n"),
+ (long) cu->header.offset.sect_off, (long) offset.sect_off,
+ bfd_get_filename (objfile->obfd));
+ }
+ per_cu = dwarf2_find_containing_comp_unit (offset, objfile);
- per_cu = dwarf2_find_containing_comp_unit (offset, objfile);
-
- if (per_cu->cu == NULL || per_cu->cu->partial_dies == NULL)
- load_partial_comp_unit (per_cu);
+ if (per_cu->cu == NULL || per_cu->cu->partial_dies == NULL)
+ load_partial_comp_unit (per_cu);
- per_cu->cu->last_used = 0;
- pd = find_partial_die_in_comp_unit (offset, per_cu->cu);
+ per_cu->cu->last_used = 0;
+ pd = find_partial_die_in_comp_unit (offset, per_cu->cu);
+ }
if (pd == NULL && per_cu->load_all_dies == 0)
{
struct abbrev_info *abbrev;
unsigned int bytes_read;
char *info_ptr;
+ struct dwarf2_section_info *sec;
per_cu->load_all_dies = 1;
- /* Re-read the DIEs. */
+ if (per_cu->debug_types_section)
+ sec = per_cu->debug_types_section;
+ else
+ sec = &dwarf2_per_objfile->info;
+
+ /* Re-read the DIEs, this time reading all of them.
+ NOTE: We don't discard the previous set of DIEs.
+ This doesn't happen very often so it's (hopefully) not a problem. */
back_to = make_cleanup (null_cleanup, 0);
if (per_cu->cu->dwarf2_abbrevs == NULL)
{
dwarf2_read_abbrevs (per_cu->cu);
make_cleanup (dwarf2_free_abbrev_table, per_cu->cu);
}
- info_ptr = (dwarf2_per_objfile->info.buffer
+ info_ptr = (sec->buffer
+ per_cu->cu->header.offset.sect_off
+ per_cu->cu->header.first_die_offset.cu_off);
abbrev = peek_die_abbrev (info_ptr, &bytes_read, per_cu->cu);
info_ptr = read_partial_die (&comp_unit_die, abbrev, bytes_read,
- objfile->obfd,
- dwarf2_per_objfile->info.buffer, info_ptr,
+ objfile->obfd, sec->buffer, info_ptr,
per_cu->cu);
if (comp_unit_die.has_children)
- load_partial_dies (objfile->obfd,
- dwarf2_per_objfile->info.buffer, info_ptr,
- 0, per_cu->cu);
+ load_partial_dies (objfile->obfd, sec->buffer, info_ptr, 0,
+ per_cu->cu);
do_cleanups (back_to);
pd = find_partial_die_in_comp_unit (offset, per_cu->cu);
}
- not_found:
-
if (pd == NULL)
internal_error (__FILE__, __LINE__,
_("could not find partial DIE 0x%x "
for later lookup.
NOTE: This is NULL if the type wasn't found. */
DW_SIGNATURED_TYPE (attr) =
- lookup_signatured_type (cu->objfile, read_8_bytes (abfd, info_ptr));
+ lookup_signatured_type (read_8_bytes (abfd, info_ptr));
info_ptr += 8;
break;
case DW_FORM_ref_udata:
gdb_byte *info_ptr = section->buffer + offset.sect_off;
unsigned int length, initial_length_size;
unsigned int sig_offset;
- struct signatured_type find_entry, *type_sig;
+ struct signatured_type find_entry, *sig_type;
length = read_initial_length (objfile->obfd, info_ptr, &initial_length_size);
sig_offset = (initial_length_size
+ (initial_length_size == 4 ? 4 : 8) /*debug_abbrev_offset*/
+ 1 /*address_size*/);
find_entry.signature = bfd_get_64 (objfile->obfd, info_ptr + sig_offset);
- type_sig = htab_find (dwarf2_per_objfile->signatured_types, &find_entry);
+ sig_type = htab_find (dwarf2_per_objfile->signatured_types, &find_entry);
/* This is only used to lookup previously recorded types.
If we didn't find it, it's our bug. */
- gdb_assert (type_sig != NULL);
- gdb_assert (offset.sect_off == type_sig->per_cu.offset.sect_off);
+ gdb_assert (sig_type != NULL);
+ gdb_assert (offset.sect_off == sig_type->per_cu.offset.sect_off);
- return type_sig;
+ return sig_type;
}
/* Load the DIEs associated with type unit PER_CU into memory. */
struct objfile *objfile = per_cu->objfile;
struct dwarf2_section_info *sect = per_cu->debug_types_section;
sect_offset offset = per_cu->offset;
- struct signatured_type *type_sig;
+ struct signatured_type *sig_type;
dwarf2_read_section (objfile, sect);
the signature to assert we found the right one.
Ok, but it's a lot of work. We should simplify things so any needed
assert doesn't require all this clumsiness. */
- type_sig = lookup_signatured_type_at_offset (objfile, sect, offset);
+ sig_type = lookup_signatured_type_at_offset (objfile, sect, offset);
- gdb_assert (type_sig->per_cu.cu == NULL);
+ gdb_assert (sig_type->per_cu.cu == NULL);
- read_signatured_type (type_sig);
+ read_signatured_type (sig_type);
- gdb_assert (type_sig->per_cu.cu != NULL);
+ gdb_assert (sig_type->per_cu.cu != NULL);
}
/* Read in a signatured type and build its CU and DIEs. */
static void
-read_signatured_type (struct signatured_type *type_sig)
+read_signatured_type (struct signatured_type *sig_type)
{
- struct objfile *objfile = type_sig->per_cu.objfile;
+ struct objfile *objfile = sig_type->per_cu.objfile;
gdb_byte *types_ptr;
struct die_reader_specs reader_specs;
struct dwarf2_cu *cu;
ULONGEST signature;
struct cleanup *back_to, *free_cu_cleanup;
- struct dwarf2_section_info *section = type_sig->per_cu.debug_types_section;
+ struct dwarf2_section_info *section = sig_type->per_cu.debug_types_section;
dwarf2_read_section (objfile, section);
- types_ptr = section->buffer + type_sig->per_cu.offset.sect_off;
+ types_ptr = section->buffer + sig_type->per_cu.offset.sect_off;
- gdb_assert (type_sig->per_cu.cu == NULL);
+ gdb_assert (sig_type->per_cu.cu == NULL);
cu = xmalloc (sizeof (*cu));
- init_one_comp_unit (cu, &type_sig->per_cu);
+ init_one_comp_unit (cu, &sig_type->per_cu);
/* If an error occurs while loading, release our storage. */
free_cu_cleanup = make_cleanup (free_heap_comp_unit, cu);
types_ptr = read_and_check_type_unit_head (&cu->header, section, types_ptr,
&signature, NULL);
- gdb_assert (signature == type_sig->signature);
+ gdb_assert (signature == sig_type->signature);
cu->die_hash
= htab_create_alloc_ex (cu->header.length / 12,
discard_cleanups (free_cu_cleanup);
/* Link this TU into read_in_chain. */
- type_sig->per_cu.cu->read_in_chain = dwarf2_per_objfile->read_in_chain;
- dwarf2_per_objfile->read_in_chain = &type_sig->per_cu;
+ sig_type->per_cu.cu->read_in_chain = dwarf2_per_objfile->read_in_chain;
+ dwarf2_per_objfile->read_in_chain = &sig_type->per_cu;
}
/* Decode simple location descriptions.