/* DWARF 2 debugging format support for GDB.
- Copyright (C) 1994-2019 Free Software Foundation, Inc.
+ Copyright (C) 1994-2020 Free Software Foundation, Inc.
Adapted by Gary Funck (gary@intrepid.com), Intrepid Technology,
Inc. with support from Florida State University (under contract
const gdb_byte *data;
};
-#ifndef ATTR_ALLOC_CHUNK
-#define ATTR_ALLOC_CHUNK 4
-#endif
-
-/* Allocate fields for structs, unions and enums in this size. */
-#ifndef DW_FIELD_ALLOC_CHUNK
-#define DW_FIELD_ALLOC_CHUNK 4
-#endif
-
/* FIXME: We might want to set this from BFD via bfd_arch_bits_per_byte,
but this would require a corresponding change in unpack_field_as_long
and friends. */
static struct type *dwarf2_per_cu_addr_type (struct dwarf2_per_cu_data *per_cu);
static struct type *dwarf2_per_cu_addr_sized_int_type
(struct dwarf2_per_cu_data *per_cu, bool unsigned_p);
+static struct type *dwarf2_per_cu_int_type
+ (struct dwarf2_per_cu_data *per_cu, int size_in_bytes,
+ bool unsigned_p);
/* Class, the destructor of which frees all allocated queue entries. This
will only have work to do if an error was thrown while processing the
iter = index->address_table.data ();
end = iter + index->address_table.size ();
- baseaddr = ANOFFSET (objfile->section_offsets, SECT_OFF_TEXT (objfile));
+ baseaddr = objfile->section_offsets[SECT_OFF_TEXT (objfile)];
while (iter < end)
{
struct objfile *objfile = dwarf2_per_objfile->objfile;
bfd *abfd = objfile->obfd;
struct gdbarch *gdbarch = get_objfile_arch (objfile);
- const CORE_ADDR baseaddr = ANOFFSET (objfile->section_offsets,
- SECT_OFF_TEXT (objfile));
+ const CORE_ADDR baseaddr = objfile->section_offsets[SECT_OFF_TEXT (objfile)];
auto_obstack temp_obstack;
addrmap *mutable_map = addrmap_create_mutable (&temp_obstack);
if (!objfile->partial_symtabs->psymtabs_addrmap)
return NULL;
- CORE_ADDR baseaddr = ANOFFSET (objfile->section_offsets,
- SECT_OFF_TEXT (objfile));
+ CORE_ADDR baseaddr = objfile->section_offsets[SECT_OFF_TEXT (objfile)];
data = (struct dwarf2_per_cu_data *) addrmap_find
(objfile->partial_symtabs->psymtabs_addrmap, pc - baseaddr);
if (!data)
information (but NAME might contain it). */
if (sym != NULL
- && strcmp_iw (SYMBOL_SEARCH_NAME (sym), name) == 0)
+ && strcmp_iw (sym->search_name (), name) == 0)
return stab;
if (with_opaque != NULL
- && strcmp_iw (SYMBOL_SEARCH_NAME (with_opaque), name) == 0)
+ && strcmp_iw (with_opaque->search_name (), name) == 0)
stab_best = stab;
/* Keep looking through other CUs. */
/* This must be done before calling dwarf2_build_include_psymtabs. */
pst->dirname = dwarf2_string_attr (comp_unit_die, DW_AT_comp_dir, cu);
- baseaddr = ANOFFSET (objfile->section_offsets, SECT_OFF_TEXT (objfile));
+ baseaddr = objfile->section_offsets[SECT_OFF_TEXT (objfile)];
dwarf2_find_base_address (comp_unit_die, cu);
/* Return the fully scoped name associated with PDI, from compilation unit
CU. The result will be allocated with malloc. */
-static char *
+static gdb::unique_xmalloc_ptr<char>
partial_die_full_name (struct partial_die_info *pdi,
struct dwarf2_cu *cu)
{
attr.u.unsnd = to_underlying (pdi->sect_off);
die = follow_die_ref (NULL, &attr, &ref_cu);
- return xstrdup (dwarf2_full_name (NULL, die, ref_cu));
+ return make_unique_xstrdup (dwarf2_full_name (NULL, die, ref_cu));
}
}
if (parent_scope == NULL)
return NULL;
else
- return typename_concat (NULL, parent_scope, pdi->name, 0, cu);
+ return gdb::unique_xmalloc_ptr<char> (typename_concat (NULL, parent_scope,
+ pdi->name, 0, cu));
}
static void
CORE_ADDR addr = 0;
const char *actual_name = NULL;
CORE_ADDR baseaddr;
- char *built_actual_name;
- baseaddr = ANOFFSET (objfile->section_offsets, SECT_OFF_TEXT (objfile));
+ baseaddr = objfile->section_offsets[SECT_OFF_TEXT (objfile)];
- built_actual_name = partial_die_full_name (pdi, cu);
+ gdb::unique_xmalloc_ptr<char> built_actual_name
+ = partial_die_full_name (pdi, cu);
if (built_actual_name != NULL)
- actual_name = built_actual_name;
+ actual_name = built_actual_name.get ();
if (actual_name == NULL)
actual_name = pdi->name;
/* Static Variable. Skip symbols whose value we cannot know (those
without location descriptors or constant values). */
if (!has_loc && !pdi->has_const_value)
- {
- xfree (built_actual_name);
- return;
- }
+ return;
add_psymbol_to_list (actual_name,
built_actual_name != NULL,
union or class entry that does not have a byte size attribute
and that has a DW_AT_declaration attribute." */
if (!pdi->has_byte_size && pdi->is_declaration)
- {
- xfree (built_actual_name);
- return;
- }
+ return;
/* NOTE: carlton/2003-10-07: See comment in new_symbol about
static vs. global. */
default:
break;
}
-
- xfree (built_actual_name);
}
/* Read a partial die corresponding to a namespace; also, add a symbol
CORE_ADDR this_highpc;
CORE_ADDR this_lowpc;
- baseaddr = ANOFFSET (objfile->section_offsets,
- SECT_OFF_TEXT (objfile));
+ baseaddr = objfile->section_offsets[SECT_OFF_TEXT (objfile)];
this_lowpc
= (gdbarch_adjust_dwarf2_addr (gdbarch,
pdi->lowpc + baseaddr)
static void
fixup_go_packaging (struct dwarf2_cu *cu)
{
- char *package_name = NULL;
+ gdb::unique_xmalloc_ptr<char> package_name;
struct pending *list;
int i;
{
struct symbol *sym = list->symbol[i];
- if (SYMBOL_LANGUAGE (sym) == language_go
+ if (sym->language () == language_go
&& SYMBOL_CLASS (sym) == LOC_BLOCK)
{
- char *this_package_name = go_symbol_package_name (sym);
+ gdb::unique_xmalloc_ptr<char> this_package_name
+ (go_symbol_package_name (sym));
if (this_package_name == NULL)
continue;
if (package_name == NULL)
- package_name = this_package_name;
+ package_name = std::move (this_package_name);
else
{
struct objfile *objfile
= cu->per_cu->dwarf2_per_objfile->objfile;
- if (strcmp (package_name, this_package_name) != 0)
+ if (strcmp (package_name.get (), this_package_name.get ()) != 0)
complaint (_("Symtab %s has objects from two different Go packages: %s and %s"),
(symbol_symtab (sym) != NULL
? symtab_to_filename_for_display
(symbol_symtab (sym))
: objfile_name (objfile)),
- this_package_name, package_name);
- xfree (this_package_name);
+ this_package_name.get (), package_name.get ());
}
}
}
{
struct objfile *objfile = cu->per_cu->dwarf2_per_objfile->objfile;
const char *saved_package_name
- = obstack_strdup (&objfile->per_bfd->storage_obstack, package_name);
+ = obstack_strdup (&objfile->per_bfd->storage_obstack, package_name.get ());
struct type *type = init_type (objfile, TYPE_CODE_MODULE, 0,
saved_package_name);
struct symbol *sym;
sym = allocate_symbol (objfile);
- SYMBOL_SET_LANGUAGE (sym, language_go, &objfile->objfile_obstack);
- SYMBOL_SET_NAMES (sym, saved_package_name, false, objfile);
+ sym->set_language (language_go, &objfile->objfile_obstack);
+ sym->compute_and_set_names (saved_package_name, false, objfile->per_bfd);
/* This is not VAR_DOMAIN because we want a way to ensure a lookup of,
e.g., "main" finds the "main" module and not C's main(). */
SYMBOL_DOMAIN (sym) = STRUCT_DOMAIN;
SYMBOL_TYPE (sym) = type;
add_symbol_to_list (sym, cu->get_builder ()->get_global_symbols ());
-
- xfree (package_name);
}
}
struct block *static_block;
CORE_ADDR addr;
- baseaddr = ANOFFSET (objfile->section_offsets, SECT_OFF_TEXT (objfile));
+ baseaddr = objfile->section_offsets[SECT_OFF_TEXT (objfile)];
/* Clear the list here in case something was left over. */
cu->method_list.clear ();
/* For Fortran GDB prefers DW_AT_*linkage_name for the physname if present
but otherwise compute it by typename_concat inside GDB.
FIXME: Actually this is not really true, or at least not always true.
- It's all very confusing. SYMBOL_SET_NAMES doesn't try to demangle
+ It's all very confusing. compute_and_set_names doesn't try to demangle
Fortran names because there is no mangling standard. So new_symbol
will set the demangled name to the result of dwarf2_full_name, and it is
the demangled name that GDB uses if it exists. */
prefix = determine_prefix (die, cu);
if (*prefix != '\0')
{
- char *prefixed_name = typename_concat (NULL, prefix, name,
- physname, cu);
+ gdb::unique_xmalloc_ptr<char> prefixed_name
+ (typename_concat (NULL, prefix, name, physname, cu));
- buf.puts (prefixed_name);
- xfree (prefixed_name);
+ buf.puts (prefixed_name.get ());
}
else
buf.puts (name);
CORE_ADDR baseaddr;
prepare_one_comp_unit (cu, die, cu->language);
- baseaddr = ANOFFSET (objfile->section_offsets, SECT_OFF_TEXT (objfile));
+ baseaddr = objfile->section_offsets[SECT_OFF_TEXT (objfile)];
get_scope_pc_bounds (die, &lowpc, &highpc, cu);
if (comp_dir != NULL)
{
- char *path_to_try = concat (comp_dir, SLASH_STRING,
- file_name, (char *) NULL);
+ gdb::unique_xmalloc_ptr<char> path_to_try
+ (concat (comp_dir, SLASH_STRING, file_name, (char *) NULL));
/* NOTE: If comp_dir is a relative path, this will also try the
search path, which seems useful. */
gdb_bfd_ref_ptr abfd (try_open_dwop_file (dwarf2_per_objfile,
- path_to_try,
+ path_to_try.get (),
0 /*is_dwp*/,
1 /*search_cwd*/));
- xfree (path_to_try);
if (abfd != NULL)
return abfd;
}
origin_child_die = sibling_die (origin_child_die);
}
origin_cu->list_in_scope = origin_previous_list_in_scope;
+
+ if (cu != origin_cu)
+ compute_delayed_physnames (origin_cu);
}
static void
}
}
- baseaddr = ANOFFSET (objfile->section_offsets, SECT_OFF_TEXT (objfile));
+ baseaddr = objfile->section_offsets[SECT_OFF_TEXT (objfile)];
name = dwarf2_name (die, cu);
(struct symbol *) templ_func);
if (dwarf2_flag_true_p (die, DW_AT_main_subprogram, cu))
- set_objfile_main_name (objfile, SYMBOL_LINKAGE_NAME (newobj->name),
+ set_objfile_main_name (objfile, newobj->name->linkage_name (),
cu->language);
/* If there is a location expression for DW_AT_frame_base, record
struct die_info *child_die;
CORE_ADDR baseaddr;
- baseaddr = ANOFFSET (objfile->section_offsets, SECT_OFF_TEXT (objfile));
+ baseaddr = objfile->section_offsets[SECT_OFF_TEXT (objfile)];
/* Ignore blocks with missing or invalid low and high pc attributes. */
/* ??? Perhaps consider discontiguous blocks defined by DW_AT_ranges
int nparams;
struct die_info *child_die;
- baseaddr = ANOFFSET (objfile->section_offsets, SECT_OFF_TEXT (objfile));
+ baseaddr = objfile->section_offsets[SECT_OFF_TEXT (objfile)];
attr = dwarf2_attr (die, DW_AT_call_return_pc, cu);
if (attr == NULL)
}
buffer = dwarf2_per_objfile->rnglists.buffer + offset;
- baseaddr = ANOFFSET (objfile->section_offsets, SECT_OFF_TEXT (objfile));
+ baseaddr = objfile->section_offsets[SECT_OFF_TEXT (objfile)];
while (1)
{
}
buffer = dwarf2_per_objfile->ranges.buffer + offset;
- baseaddr = ANOFFSET (objfile->section_offsets, SECT_OFF_TEXT (objfile));
+ baseaddr = objfile->section_offsets[SECT_OFF_TEXT (objfile)];
while (1)
{
{
struct objfile *objfile = cu->per_cu->dwarf2_per_objfile->objfile;
struct gdbarch *gdbarch = get_objfile_arch (objfile);
- const CORE_ADDR baseaddr = ANOFFSET (objfile->section_offsets,
- SECT_OFF_TEXT (objfile));
+ const CORE_ADDR baseaddr = objfile->section_offsets[SECT_OFF_TEXT (objfile)];
int low_set = 0;
CORE_ADDR low = 0;
CORE_ADDR high = 0;
attr = dwarf2_attr (die, DW_AT_bit_offset, cu);
if (attr != nullptr)
{
- if (gdbarch_bits_big_endian (gdbarch))
+ if (gdbarch_byte_order (gdbarch) == BFD_ENDIAN_BIG)
{
/* For big endian bits, the DW_AT_bit_offset gives the
additional bit offset from the MSB of the containing
/* Normally a DW_TAG_variant_part won't have a size, but our
representation requires one, so set it to the maximum of the
- child sizes. */
+ child sizes, being sure to account for the offset at which
+ each child is seen. */
if (TYPE_LENGTH (fp->type) == 0)
{
unsigned max = 0;
for (int i = 0; i < TYPE_NFIELDS (fp->type); ++i)
- if (TYPE_LENGTH (TYPE_FIELD_TYPE (fp->type, i)) > max)
- max = TYPE_LENGTH (TYPE_FIELD_TYPE (fp->type, i));
+ {
+ unsigned len = ((TYPE_FIELD_BITPOS (fp->type, i) + 7) / 8
+ + TYPE_LENGTH (TYPE_FIELD_TYPE (fp->type, i)));
+ if (len > max)
+ max = len;
+ }
TYPE_LENGTH (fp->type) = max;
}
}
&& (type_name[len] == '\0' || type_name[len] == '<'));
}
+/* Check if the given VALUE is a recognized enum
+ dwarf_defaulted_attribute constant according to DWARF5 spec,
+ Table 7.24. */
+
+static bool
+is_valid_DW_AT_defaulted (ULONGEST value)
+{
+ switch (value)
+ {
+ case DW_DEFAULTED_no:
+ case DW_DEFAULTED_in_class:
+ case DW_DEFAULTED_out_of_class:
+ return true;
+ }
+
+ complaint (_("unrecognized DW_AT_defaulted value (%s)"), pulongest (value));
+ return false;
+}
+
/* Add a member function to the proper fieldlist. */
static void
if (attr && DW_UNSND (attr) != 0)
fnp->is_artificial = 1;
+ /* Check for defaulted methods. */
+ attr = dwarf2_attr (die, DW_AT_defaulted, cu);
+ if (attr != nullptr && is_valid_DW_AT_defaulted (DW_UNSND (attr)))
+ fnp->defaulted = (enum dwarf_defaulted_attribute) DW_UNSND (attr);
+
+ /* Check for deleted methods. */
+ attr = dwarf2_attr (die, DW_AT_deleted, cu);
+ if (attr != nullptr && DW_UNSND (attr) != 0)
+ fnp->is_deleted = 1;
+
fnp->is_constructor = dwarf2_is_constructor (die, cu);
/* Get index in virtual function table if it is a virtual member
objfile_name (cu->per_cu->dwarf2_per_objfile->objfile));
}
+/* Check if the given VALUE is a valid enum dwarf_calling_convention
+ constant for a type, according to DWARF5 spec, Table 5.5. */
+
+static bool
+is_valid_DW_AT_calling_convention_for_type (ULONGEST value)
+{
+ switch (value)
+ {
+ case DW_CC_normal:
+ case DW_CC_pass_by_reference:
+ case DW_CC_pass_by_value:
+ return true;
+
+ default:
+ complaint (_("unrecognized DW_AT_calling_convention value "
+ "(%s) for a type"), pulongest (value));
+ return false;
+ }
+}
+
+/* Check if the given VALUE is a valid enum dwarf_calling_convention
+ constant for a subroutine, according to DWARF5 spec, Table 3.3, and
+ also according to GNU-specific values (see include/dwarf2.h). */
+
+static bool
+is_valid_DW_AT_calling_convention_for_subroutine (ULONGEST value)
+{
+ switch (value)
+ {
+ case DW_CC_normal:
+ case DW_CC_program:
+ case DW_CC_nocall:
+ return true;
+
+ case DW_CC_GNU_renesas_sh:
+ case DW_CC_GNU_borland_fastcall_i386:
+ case DW_CC_GDB_IBM_OpenCL:
+ return true;
+
+ default:
+ complaint (_("unrecognized DW_AT_calling_convention value "
+ "(%s) for a subroutine"), pulongest (value));
+ return false;
+ }
+}
+
/* Called when we find the DIE that starts a structure or union scope
(definition) to create a type for the structure or union. Fill in
the type's name and general properties; the members will not be
if (cu->language == language_cplus && die->tag == DW_TAG_class_type)
TYPE_DECLARED_CLASS (type) = 1;
+ /* Store the calling convention in the type if it's available in
+ the die. Otherwise the calling convention remains set to
+ the default value DW_CC_normal. */
+ attr = dwarf2_attr (die, DW_AT_calling_convention, cu);
+ if (attr != nullptr
+ && is_valid_DW_AT_calling_convention_for_type (DW_UNSND (attr)))
+ {
+ ALLOCATE_CPLUS_STRUCT_TYPE (type);
+ TYPE_CPLUS_CALLING_CONVENTION (type)
+ = (enum dwarf_calling_convention) (DW_UNSND (attr));
+ }
+
attr = dwarf2_attr (die, DW_AT_byte_size, cu);
if (attr != nullptr)
{
read the discriminant member, so we can record it later in the
discriminant_info. */
bool is_variant_part = TYPE_FLAG_DISCRIMINATED_UNION (type);
- sect_offset discr_offset;
+ sect_offset discr_offset {};
bool has_template_parameters = false;
if (is_variant_part)
{
struct die_info *child_die;
struct symbol *sym;
- struct field *fields = NULL;
- int num_fields = 0;
+ std::vector<struct field> fields;
const char *name;
child_die = die->child;
{
sym = new_symbol (child_die, this_type, cu);
- if ((num_fields % DW_FIELD_ALLOC_CHUNK) == 0)
- {
- fields = (struct field *)
- xrealloc (fields,
- (num_fields + DW_FIELD_ALLOC_CHUNK)
- * sizeof (struct field));
- }
+ fields.emplace_back ();
+ struct field &field = fields.back ();
- FIELD_NAME (fields[num_fields]) = SYMBOL_LINKAGE_NAME (sym);
- FIELD_TYPE (fields[num_fields]) = NULL;
- SET_FIELD_ENUMVAL (fields[num_fields], SYMBOL_VALUE (sym));
- FIELD_BITSIZE (fields[num_fields]) = 0;
-
- num_fields++;
+ FIELD_NAME (field) = sym->linkage_name ();
+ FIELD_TYPE (field) = NULL;
+ SET_FIELD_ENUMVAL (field, SYMBOL_VALUE (sym));
+ FIELD_BITSIZE (field) = 0;
}
}
child_die = sibling_die (child_die);
}
- if (num_fields)
+ if (!fields.empty ())
{
- TYPE_NFIELDS (this_type) = num_fields;
+ TYPE_NFIELDS (this_type) = fields.size ();
TYPE_FIELDS (this_type) = (struct field *)
- TYPE_ALLOC (this_type, sizeof (struct field) * num_fields);
- memcpy (TYPE_FIELDS (this_type), fields,
- sizeof (struct field) * num_fields);
- xfree (fields);
+ TYPE_ALLOC (this_type, sizeof (struct field) * fields.size ());
+ memcpy (TYPE_FIELDS (this_type), fields.data (),
+ sizeof (struct field) * fields.size ());
}
}
struct gdbarch *gdbarch = get_objfile_arch (objfile);
struct type *type, *range_type, *index_type, *char_type;
struct attribute *attr;
- unsigned int length;
+ struct dynamic_prop prop;
+ bool length_is_constant = true;
+ LONGEST length;
+
+ /* There are a couple of places where bit sizes might be made use of
+ when parsing a DW_TAG_string_type, however, no producer that we know
+ of make use of these. Handling bit sizes that are a multiple of the
+ byte size is easy enough, but what about other bit sizes? Lets deal
+ with that problem when we have to. Warn about these attributes being
+ unsupported, then parse the type and ignore them like we always
+ have. */
+ if (dwarf2_attr (die, DW_AT_bit_size, cu) != nullptr
+ || dwarf2_attr (die, DW_AT_string_length_bit_size, cu) != nullptr)
+ {
+ static bool warning_printed = false;
+ if (!warning_printed)
+ {
+ warning (_("DW_AT_bit_size and DW_AT_string_length_bit_size not "
+ "currently supported on DW_TAG_string_type."));
+ warning_printed = true;
+ }
+ }
attr = dwarf2_attr (die, DW_AT_string_length, cu);
- if (attr != nullptr)
+ if (attr != nullptr && !attr_form_is_constant (attr))
+ {
+ /* The string length describes the location at which the length of
+ the string can be found. The size of the length field can be
+ specified with one of the attributes below. */
+ struct type *prop_type;
+ struct attribute *len
+ = dwarf2_attr (die, DW_AT_string_length_byte_size, cu);
+ if (len == nullptr)
+ len = dwarf2_attr (die, DW_AT_byte_size, cu);
+ if (len != nullptr && attr_form_is_constant (len))
+ {
+ /* Pass 0 as the default as we know this attribute is constant
+ and the default value will not be returned. */
+ LONGEST sz = dwarf2_get_attr_constant_value (len, 0);
+ prop_type = dwarf2_per_cu_int_type (cu->per_cu, sz, true);
+ }
+ else
+ {
+ /* If the size is not specified then we assume it is the size of
+ an address on this target. */
+ prop_type = dwarf2_per_cu_addr_sized_int_type (cu->per_cu, true);
+ }
+
+ /* Convert the attribute into a dynamic property. */
+ if (!attr_to_dynamic_prop (attr, die, cu, &prop, prop_type))
+ length = 1;
+ else
+ length_is_constant = false;
+ }
+ else if (attr != nullptr)
+ {
+ /* This DW_AT_string_length just contains the length with no
+ indirection. There's no need to create a dynamic property in this
+ case. Pass 0 for the default value as we know it will not be
+ returned in this case. */
+ length = dwarf2_get_attr_constant_value (attr, 0);
+ }
+ else if ((attr = dwarf2_attr (die, DW_AT_byte_size, cu)) != nullptr)
{
- length = DW_UNSND (attr);
+ /* We don't currently support non-constant byte sizes for strings. */
+ length = dwarf2_get_attr_constant_value (attr, 1);
}
else
{
- /* Check for the DW_AT_byte_size attribute. */
- attr = dwarf2_attr (die, DW_AT_byte_size, cu);
- if (attr != nullptr)
- {
- length = DW_UNSND (attr);
- }
- else
- {
- length = 1;
- }
+ /* Use 1 as a fallback length if we have nothing else. */
+ length = 1;
}
index_type = objfile_type (objfile)->builtin_int;
- range_type = create_static_range_type (NULL, index_type, 1, length);
+ if (length_is_constant)
+ range_type = create_static_range_type (NULL, index_type, 1, length);
+ else
+ {
+ struct dynamic_prop low_bound;
+
+ low_bound.kind = PROP_CONST;
+ low_bound.data.const_val = 1;
+ range_type = create_range_type (NULL, index_type, &low_bound, &prop, 0);
+ }
char_type = language_string_char_type (cu->language_defn, gdbarch);
type = create_string_type (NULL, char_type, range_type);
the subroutine die. Otherwise set the calling convention to
the default value DW_CC_normal. */
attr = dwarf2_attr (die, DW_AT_calling_convention, cu);
- if (attr != nullptr)
- TYPE_CALLING_CONVENTION (ftype) = DW_UNSND (attr);
+ if (attr != nullptr
+ && is_valid_DW_AT_calling_convention_for_subroutine (DW_UNSND (attr)))
+ TYPE_CALLING_CONVENTION (ftype)
+ = (enum dwarf_calling_convention) (DW_UNSND (attr));
else if (cu->producer && strstr (cu->producer, "IBM XL C for OpenCL"))
TYPE_CALLING_CONVENTION (ftype) = DW_CC_GDB_IBM_OpenCL;
else
static struct type *
dwarf2_init_float_type (struct objfile *objfile, int bits, const char *name,
- const char *name_hint)
+ const char *name_hint, enum bfd_endian byte_order)
{
struct gdbarch *gdbarch = get_objfile_arch (objfile);
const struct floatformat **format;
format = gdbarch_floatformat_for_type (gdbarch, name_hint, bits);
if (format)
- type = init_float_type (objfile, bits, name, format);
+ type = init_float_type (objfile, bits, name, format, byte_order);
else
type = init_type (objfile, TYPE_CODE_ERROR, bits, name);
static struct type *
dwarf2_init_complex_target_type (struct dwarf2_cu *cu,
struct objfile *objfile,
- int bits, const char *name_hint)
+ int bits, const char *name_hint,
+ enum bfd_endian byte_order)
{
gdbarch *gdbarch = get_objfile_arch (objfile);
struct type *tt = nullptr;
tt = nullptr;
const char *name = (tt == nullptr) ? nullptr : TYPE_NAME (tt);
- return dwarf2_init_float_type (objfile, bits, name, name_hint);
+ return dwarf2_init_float_type (objfile, bits, name, name_hint, byte_order);
}
/* Find a representation of a given base type and install
struct attribute *attr;
int encoding = 0, bits = 0;
const char *name;
+ gdbarch *arch;
attr = dwarf2_attr (die, DW_AT_encoding, cu);
if (attr != nullptr)
- {
- encoding = DW_UNSND (attr);
- }
+ encoding = DW_UNSND (attr);
attr = dwarf2_attr (die, DW_AT_byte_size, cu);
if (attr != nullptr)
- {
- bits = DW_UNSND (attr) * TARGET_CHAR_BIT;
- }
+ bits = DW_UNSND (attr) * TARGET_CHAR_BIT;
name = dwarf2_name (die, cu);
if (!name)
+ complaint (_("DW_AT_name missing from DW_TAG_base_type"));
+
+ arch = get_objfile_arch (objfile);
+ enum bfd_endian byte_order = gdbarch_byte_order (arch);
+
+ attr = dwarf2_attr (die, DW_AT_endianity, cu);
+ if (attr)
{
- complaint (_("DW_AT_name missing from DW_TAG_base_type"));
+ int endianity = DW_UNSND (attr);
+
+ switch (endianity)
+ {
+ case DW_END_big:
+ byte_order = BFD_ENDIAN_BIG;
+ break;
+ case DW_END_little:
+ byte_order = BFD_ENDIAN_LITTLE;
+ break;
+ default:
+ complaint (_("DW_AT_endianity has unrecognized value %d"), endianity);
+ break;
+ }
}
switch (encoding)
type = init_boolean_type (objfile, bits, 1, name);
break;
case DW_ATE_complex_float:
- type = dwarf2_init_complex_target_type (cu, objfile, bits / 2, name);
+ type = dwarf2_init_complex_target_type (cu, objfile, bits / 2, name,
+ byte_order);
type = init_complex_type (objfile, name, type);
break;
case DW_ATE_decimal_float:
type = init_decfloat_type (objfile, bits, name);
break;
case DW_ATE_float:
- type = dwarf2_init_float_type (objfile, bits, name, name);
+ type = dwarf2_init_float_type (objfile, bits, name, name, byte_order);
break;
case DW_ATE_signed:
type = dwarf2_init_integer_type (cu, objfile, bits, 0, name);
break;
case DW_ATE_UTF:
{
- gdbarch *arch = get_objfile_arch (objfile);
-
if (bits == 16)
type = builtin_type (arch)->builtin_char16;
else if (bits == 32)
maybe_set_alignment (cu, die, type);
+ TYPE_ENDIANITY_NOT_DEFAULT (type) = gdbarch_byte_order (arch) != byte_order;
+
return set_die_type (die, type, cu);
}
baton->locexpr.per_cu = cu->per_cu;
baton->locexpr.size = DW_BLOCK (attr)->size;
baton->locexpr.data = DW_BLOCK (attr)->data;
- baton->locexpr.is_reference = false;
+ switch (attr->name)
+ {
+ case DW_AT_string_length:
+ baton->locexpr.is_reference = true;
+ break;
+ default:
+ baton->locexpr.is_reference = false;
+ break;
+ }
prop->data.baton = baton;
prop->kind = PROP_LOCEXPR;
gdb_assert (prop->data.baton != NULL);
return 1;
}
-/* Find an integer type the same size as the address size given in the
- compilation unit header for PER_CU. UNSIGNED_P controls if the integer
- is unsigned or not. */
+/* Find an integer type SIZE_IN_BYTES bytes in size and return it.
+ UNSIGNED_P controls if the integer is unsigned or not. */
static struct type *
-dwarf2_per_cu_addr_sized_int_type (struct dwarf2_per_cu_data *per_cu,
- bool unsigned_p)
+dwarf2_per_cu_int_type (struct dwarf2_per_cu_data *per_cu,
+ int size_in_bytes, bool unsigned_p)
{
struct objfile *objfile = per_cu->dwarf2_per_objfile->objfile;
- int addr_size = dwarf2_per_cu_addr_size (per_cu);
struct type *int_type;
/* Helper macro to examine the various builtin types. */
-#define TRY_TYPE(F) \
- int_type = (unsigned_p \
- ? objfile_type (objfile)->builtin_unsigned_ ## F \
- : objfile_type (objfile)->builtin_ ## F); \
- if (int_type != NULL && TYPE_LENGTH (int_type) == addr_size) \
+#define TRY_TYPE(F) \
+ int_type = (unsigned_p \
+ ? objfile_type (objfile)->builtin_unsigned_ ## F \
+ : objfile_type (objfile)->builtin_ ## F); \
+ if (int_type != NULL && TYPE_LENGTH (int_type) == size_in_bytes) \
return int_type
TRY_TYPE (char);
gdb_assert_not_reached ("unable to find suitable integer type");
}
+/* Find an integer type the same size as the address size given in the
+ compilation unit header for PER_CU. UNSIGNED_P controls if the integer
+ is unsigned or not. */
+
+static struct type *
+dwarf2_per_cu_addr_sized_int_type (struct dwarf2_per_cu_data *per_cu,
+ bool unsigned_p)
+{
+ int addr_size = dwarf2_per_cu_addr_size (per_cu);
+ return dwarf2_per_cu_int_type (per_cu, addr_size, unsigned_p);
+}
+
/* Read the DW_AT_type attribute for a sub-range. If this attribute is not
present (which is valid) then compute the default type based on the
compilation units address size. */
&& !TYPE_UNSIGNED (base_type) && (high.data.const_val & negative_mask))
high.data.const_val |= negative_mask;
- range_type = create_range_type (NULL, orig_base_type, &low, &high, bias);
+ /* Check for bit and byte strides. */
+ struct dynamic_prop byte_stride_prop;
+ attribute *attr_byte_stride = dwarf2_attr (die, DW_AT_byte_stride, cu);
+ if (attr_byte_stride != nullptr)
+ {
+ struct type *prop_type
+ = dwarf2_per_cu_addr_sized_int_type (cu->per_cu, false);
+ attr_to_dynamic_prop (attr_byte_stride, die, cu, &byte_stride_prop,
+ prop_type);
+ }
+
+ struct dynamic_prop bit_stride_prop;
+ attribute *attr_bit_stride = dwarf2_attr (die, DW_AT_bit_stride, cu);
+ if (attr_bit_stride != nullptr)
+ {
+ /* It only makes sense to have either a bit or byte stride. */
+ if (attr_byte_stride != nullptr)
+ {
+ complaint (_("Found DW_AT_bit_stride and DW_AT_byte_stride "
+ "- DIE at %s [in module %s]"),
+ sect_offset_str (die->sect_off),
+ objfile_name (cu->per_cu->dwarf2_per_objfile->objfile));
+ attr_bit_stride = nullptr;
+ }
+ else
+ {
+ struct type *prop_type
+ = dwarf2_per_cu_addr_sized_int_type (cu->per_cu, false);
+ attr_to_dynamic_prop (attr_bit_stride, die, cu, &bit_stride_prop,
+ prop_type);
+ }
+ }
+
+ if (attr_byte_stride != nullptr
+ || attr_bit_stride != nullptr)
+ {
+ bool byte_stride_p = (attr_byte_stride != nullptr);
+ struct dynamic_prop *stride
+ = byte_stride_p ? &byte_stride_prop : &bit_stride_prop;
+
+ range_type
+ = create_range_type_with_stride (NULL, orig_base_type, &low,
+ &high, bias, stride, byte_stride_p);
+ }
+ else
+ range_type = create_range_type (NULL, orig_base_type, &low, &high, bias);
if (high_bound_is_count)
TYPE_RANGE_DATA (range_type)->flag_upper_bound_is_count = 1;
struct abbrev_info *cur_abbrev;
unsigned int abbrev_number, bytes_read, abbrev_name;
unsigned int abbrev_form;
- struct attr_abbrev *cur_attrs;
- unsigned int allocated_attrs;
+ std::vector<struct attr_abbrev> cur_attrs;
abbrev_table_up abbrev_table (new struct abbrev_table (sect_off));
abbrev_number = read_unsigned_leb128 (abfd, abbrev_ptr, &bytes_read);
abbrev_ptr += bytes_read;
- allocated_attrs = ATTR_ALLOC_CHUNK;
- cur_attrs = XNEWVEC (struct attr_abbrev, allocated_attrs);
-
/* Loop until we reach an abbrev number of 0. */
while (abbrev_number)
{
+ cur_attrs.clear ();
cur_abbrev = abbrev_table->alloc_abbrev ();
/* read in abbrev header */
if (abbrev_name == 0)
break;
- if (cur_abbrev->num_attrs == allocated_attrs)
- {
- allocated_attrs += ATTR_ALLOC_CHUNK;
- cur_attrs
- = XRESIZEVEC (struct attr_abbrev, cur_attrs, allocated_attrs);
- }
-
- cur_attrs[cur_abbrev->num_attrs].name
- = (enum dwarf_attribute) abbrev_name;
- cur_attrs[cur_abbrev->num_attrs].form
- = (enum dwarf_form) abbrev_form;
- cur_attrs[cur_abbrev->num_attrs].implicit_const = implicit_const;
+ cur_attrs.emplace_back ();
+ struct attr_abbrev &cur_attr = cur_attrs.back ();
+ cur_attr.name = (enum dwarf_attribute) abbrev_name;
+ cur_attr.form = (enum dwarf_form) abbrev_form;
+ cur_attr.implicit_const = implicit_const;
++cur_abbrev->num_attrs;
}
cur_abbrev->attrs =
XOBNEWVEC (&abbrev_table->abbrev_obstack, struct attr_abbrev,
cur_abbrev->num_attrs);
- memcpy (cur_abbrev->attrs, cur_attrs,
+ memcpy (cur_abbrev->attrs, cur_attrs.data (),
cur_abbrev->num_attrs * sizeof (struct attr_abbrev));
abbrev_table->add_abbrev (abbrev_number, cur_abbrev);
break;
}
- xfree (cur_attrs);
return abbrev_table;
}
if (child_pdi->tag == DW_TAG_subprogram
&& child_pdi->linkage_name != NULL)
{
- char *actual_class_name
- = language_class_name_from_physname (cu->language_defn,
- child_pdi->linkage_name);
+ gdb::unique_xmalloc_ptr<char> actual_class_name
+ (language_class_name_from_physname (cu->language_defn,
+ child_pdi->linkage_name));
if (actual_class_name != NULL)
{
struct objfile *objfile = cu->per_cu->dwarf2_per_objfile->objfile;
struct_pdi->name
= obstack_strdup (&objfile->per_bfd->storage_obstack,
- actual_class_name);
- xfree (actual_class_name);
+ actual_class_name.get ());
}
break;
}
|| tag == DW_TAG_union_type)
&& linkage_name != NULL)
{
- char *demangled;
-
- demangled = gdb_demangle (linkage_name, DMGL_TYPES);
- if (demangled)
+ gdb::unique_xmalloc_ptr<char> demangled
+ (gdb_demangle (linkage_name, DMGL_TYPES));
+ if (demangled != nullptr)
{
const char *base;
/* Strip any leading namespaces/classes, keep only the base name.
DW_AT_name for named DIEs does not contain the prefixes. */
- base = strrchr (demangled, ':');
- if (base && base > demangled && base[-1] == ':')
+ base = strrchr (demangled.get (), ':');
+ if (base && base > demangled.get () && base[-1] == ':')
base++;
else
- base = demangled;
+ base = demangled.get ();
struct objfile *objfile = cu->per_cu->dwarf2_per_objfile->objfile;
name = obstack_strdup (&objfile->per_bfd->storage_obstack, base);
- xfree (demangled);
}
}
the line number program). */
bool record_lines_p = !decode_for_pst_p;
- baseaddr = ANOFFSET (objfile->section_offsets, SECT_OFF_TEXT (objfile));
+ baseaddr = objfile->section_offsets[SECT_OFF_TEXT (objfile)];
line_ptr = lh->statement_program_start;
line_end = lh->statement_program_end;
dwarf2_start_subfile (struct dwarf2_cu *cu, const char *filename,
const char *dirname)
{
- char *copy = NULL;
+ gdb::unique_xmalloc_ptr<char> copy;
/* In order not to lose the line information directory,
we concatenate it to the filename when it makes sense.
if (!IS_ABSOLUTE_PATH (filename) && dirname != NULL)
{
- copy = concat (dirname, SLASH_STRING, filename, (char *)NULL);
- filename = copy;
+ copy.reset (concat (dirname, SLASH_STRING, filename, (char *) NULL));
+ filename = copy.get ();
}
cu->get_builder ()->start_subfile (filename);
-
- if (copy != NULL)
- xfree (copy);
}
/* Start a symtab for DWARF. NAME, COMP_DIR, LOW_PC are passed to the
&dummy));
SYMBOL_ACLASS_INDEX (sym) = LOC_STATIC;
fixup_symbol_section (sym, objfile);
- SET_SYMBOL_VALUE_ADDRESS (sym,
- SYMBOL_VALUE_ADDRESS (sym)
- + ANOFFSET (objfile->section_offsets,
- SYMBOL_SECTION (sym)));
+ SET_SYMBOL_VALUE_ADDRESS
+ (sym,
+ SYMBOL_VALUE_ADDRESS (sym)
+ + objfile->section_offsets[SYMBOL_SECTION (sym)]);
return;
}
int inlined_func = (die->tag == DW_TAG_inlined_subroutine);
- baseaddr = ANOFFSET (objfile->section_offsets, SECT_OFF_TEXT (objfile));
+ baseaddr = objfile->section_offsets[SECT_OFF_TEXT (objfile)];
name = dwarf2_name (die, cu);
if (name)
OBJSTAT (objfile, n_syms++);
/* Cache this symbol's name and the name's demangled form (if any). */
- SYMBOL_SET_LANGUAGE (sym, cu->language, &objfile->objfile_obstack);
+ sym->set_language (cu->language, &objfile->objfile_obstack);
linkagename = dwarf2_physname (name, die, cu);
- SYMBOL_SET_NAMES (sym, linkagename, false, objfile);
+ sym->compute_and_set_names (linkagename, false, objfile->per_bfd);
/* Fortran does not have mangling standard and the mangling does differ
between gfortran, iFort etc. */
apply. */
bound_minimal_symbol found
= (lookup_minimal_symbol_linkage
- (SYMBOL_LINKAGE_NAME (sym), objfile));
+ (sym->linkage_name (), objfile));
if (found.minsym != nullptr)
sym->maybe_copied = 1;
}
with this objfile, so we don't need to
duplicate it for the type. */
if (TYPE_NAME (SYMBOL_TYPE (sym)) == 0)
- TYPE_NAME (SYMBOL_TYPE (sym)) = SYMBOL_SEARCH_NAME (sym);
+ TYPE_NAME (SYMBOL_TYPE (sym)) = sym->search_name ();
}
}
}
struct dwarf2_locexpr_baton *baton;
dwarf2_const_value_attr (attr, SYMBOL_TYPE (sym),
- SYMBOL_PRINT_NAME (sym),
+ sym->print_name (),
&objfile->objfile_obstack, cu,
&value, &bytes, &baton);
This is the full-die version of guess_partial_die_structure_name.
In this case we know DIE has no useful parent. */
-static char *
+static const char *
guess_full_die_structure_name (struct die_info *die, struct dwarf2_cu *cu)
{
struct die_info *spec_die;
if (linkage_name != NULL)
{
- char *actual_name
- = language_class_name_from_physname (cu->language_defn,
- linkage_name);
- char *name = NULL;
+ gdb::unique_xmalloc_ptr<char> actual_name
+ (language_class_name_from_physname (cu->language_defn,
+ linkage_name));
+ const char *name = NULL;
if (actual_name != NULL)
{
const char *die_name = dwarf2_name (die, cu);
if (die_name != NULL
- && strcmp (die_name, actual_name) != 0)
+ && strcmp (die_name, actual_name.get ()) != 0)
{
/* Strip off the class name from the full name.
We want the prefix. */
int die_name_len = strlen (die_name);
- int actual_name_len = strlen (actual_name);
+ int actual_name_len = strlen (actual_name.get ());
+ const char *ptr = actual_name.get ();
/* Test for '::' as a sanity check. */
if (actual_name_len > die_name_len + 2
- && actual_name[actual_name_len
- - die_name_len - 1] == ':')
+ && ptr[actual_name_len - die_name_len - 1] == ':')
name = obstack_strndup (
&objfile->per_bfd->storage_obstack,
- actual_name, actual_name_len - die_name_len - 2);
+ ptr, actual_name_len - die_name_len - 2);
}
}
- xfree (actual_name);
return name;
}
}
|| die->tag == DW_TAG_structure_type
|| die->tag == DW_TAG_union_type))
{
- char *name = guess_full_die_structure_name (die, cu);
+ const char *name = guess_full_die_structure_name (die, cu);
if (name != NULL)
return name;
}
http://gcc.gnu.org/bugzilla/show_bug.cgi?id=47510. */
if (!attr || DW_STRING (attr) == NULL)
{
- char *demangled = NULL;
-
attr = dw2_linkage_name_attr (die, cu);
if (attr == NULL || DW_STRING (attr) == NULL)
return NULL;
/* Avoid demangling DW_STRING (attr) the second time on a second
call for the same DIE. */
if (!DW_STRING_IS_CANONICAL (attr))
- demangled = gdb_demangle (DW_STRING (attr), DMGL_TYPES);
-
- if (demangled)
{
+ gdb::unique_xmalloc_ptr<char> demangled
+ (gdb_demangle (DW_STRING (attr), DMGL_TYPES));
+
const char *base;
/* FIXME: we already did this for the partial symbol... */
DW_STRING (attr)
= obstack_strdup (&objfile->per_bfd->storage_obstack,
- demangled);
+ demangled.get ());
DW_STRING_IS_CANONICAL (attr) = 1;
- xfree (demangled);
/* Strip any leading namespaces/classes, keep only the base name.
DW_AT_name for named DIEs does not contain the prefixes. */
!= dwarf2_per_objfile->abstract_to_concrete.end ()))
{
CORE_ADDR pc = (*get_frame_pc) (baton);
- CORE_ADDR baseaddr
- = ANOFFSET (objfile->section_offsets, SECT_OFF_TEXT (objfile));
+ CORE_ADDR baseaddr = objfile->section_offsets[SECT_OFF_TEXT (objfile)];
struct gdbarch *gdbarch = get_objfile_arch (objfile);
for (const auto &cand_off
{
/* It's an object-like macro. */
int name_len = p - body;
- char *name = savestring (body, name_len);
+ std::string name (body, name_len);
const char *replacement;
if (*p == ' ')
replacement = body + name_len;
}
- macro_define_object (file, line, name, replacement);
-
- xfree (name);
+ macro_define_object (file, line, name.c_str (), replacement);
}
else if (*p == '(')
{
/* It's a function-like macro. */
- char *name = savestring (body, p - body);
+ std::string name (body, p - body);
int argc = 0;
int argv_size = 1;
char **argv = XNEWVEC (char *, argv_size);
if (*p == ' ')
/* Perfectly formed definition, no complaints. */
- macro_define_function (file, line, name,
+ macro_define_function (file, line, name.c_str (),
argc, (const char **) argv,
p + 1);
else if (*p == '\0')
{
/* Complain, but do define it. */
dwarf2_macro_malformed_definition_complaint (body);
- macro_define_function (file, line, name,
+ macro_define_function (file, line, name.c_str (),
argc, (const char **) argv,
p);
}
/* Just complain. */
dwarf2_macro_malformed_definition_complaint (body);
- xfree (name);
{
int i;
else
{
dwarf2_invalid_attrib_class_complaint ("location description",
- SYMBOL_NATURAL_NAME (sym));
+ sym->natural_name ());
baton->size = 0;
}
{
struct objfile *objfile = per_cu->dwarf2_per_objfile->objfile;
- return ANOFFSET (objfile->section_offsets, SECT_OFF_TEXT (objfile));
+ return objfile->section_offsets[SECT_OFF_TEXT (objfile)];
}
/* Return a type that is a generic pointer type, the size of which matches