* dwarf2read.c (attr_form_is_constant): New function.
(dwarf2_add_field): Use it and attr_form_is_section_offset to recognize DW_AT_data_member_location attributes. Use dwarf2_get_attr_constant_value when the attribute is a constant. * dwarf2read.c (attr_form_is_section_offset): New function. (dwarf_add_member_fn, read_common_block, read_partial_die) (dwarf2_symbol_mark_computed): Use it, instead of writing it out.
This commit is contained in:
parent
dfdfb3ca98
commit
3690dd376b
2 changed files with 69 additions and 6 deletions
|
@ -1,3 +1,14 @@
|
|||
2007-12-13 Jim Blandy <jimb@codesourcery.com>
|
||||
|
||||
* dwarf2read.c (attr_form_is_constant): New function.
|
||||
(dwarf2_add_field): Use it and attr_form_is_section_offset to
|
||||
recognize DW_AT_data_member_location attributes. Use
|
||||
dwarf2_get_attr_constant_value when the attribute is a constant.
|
||||
|
||||
* dwarf2read.c (attr_form_is_section_offset): New function.
|
||||
(dwarf_add_member_fn, read_common_block, read_partial_die)
|
||||
(dwarf2_symbol_mark_computed): Use it, instead of writing it out.
|
||||
|
||||
2007-12-12 Jim Blandy <jimb@codesourcery.com>
|
||||
|
||||
Remove unused support for target-based exception catching.
|
||||
|
|
|
@ -1027,6 +1027,10 @@ static void dwarf_decode_macros (struct line_header *, unsigned int,
|
|||
|
||||
static int attr_form_is_block (struct attribute *);
|
||||
|
||||
static int attr_form_is_section_offset (struct attribute *);
|
||||
|
||||
static int attr_form_is_constant (struct attribute *);
|
||||
|
||||
static void dwarf2_symbol_mark_computed (struct attribute *attr,
|
||||
struct symbol *sym,
|
||||
struct dwarf2_cu *cu);
|
||||
|
@ -3474,8 +3478,16 @@ dwarf2_add_field (struct field_info *fip, struct die_info *die,
|
|||
attr = dwarf2_attr (die, DW_AT_data_member_location, cu);
|
||||
if (attr)
|
||||
{
|
||||
FIELD_BITPOS (*fp) =
|
||||
decode_locdesc (DW_BLOCK (attr), cu) * bits_per_byte;
|
||||
if (attr_form_is_section_offset (attr))
|
||||
{
|
||||
dwarf2_complex_location_expr_complaint ();
|
||||
FIELD_BITPOS (*fp) = 0;
|
||||
}
|
||||
else if (attr_form_is_constant (attr))
|
||||
FIELD_BITPOS (*fp) = dwarf2_get_attr_constant_value (attr, 0);
|
||||
else
|
||||
FIELD_BITPOS (*fp) =
|
||||
decode_locdesc (DW_BLOCK (attr), cu) * bits_per_byte;
|
||||
}
|
||||
else
|
||||
FIELD_BITPOS (*fp) = 0;
|
||||
|
@ -3794,7 +3806,7 @@ dwarf2_add_member_fn (struct field_info *fip, struct die_info *die,
|
|||
{
|
||||
fnp->voffset = decode_locdesc (DW_BLOCK (attr), cu) + 2;
|
||||
}
|
||||
else if (attr->form == DW_FORM_data4 || attr->form == DW_FORM_data8)
|
||||
else if (attr_form_is_section_offset (attr))
|
||||
{
|
||||
dwarf2_complex_location_expr_complaint ();
|
||||
}
|
||||
|
@ -4510,7 +4522,7 @@ read_common_block (struct die_info *die, struct dwarf2_cu *cu)
|
|||
{
|
||||
base = decode_locdesc (DW_BLOCK (attr), cu);
|
||||
}
|
||||
else if (attr->form == DW_FORM_data4 || attr->form == DW_FORM_data8)
|
||||
else if (attr_form_is_section_offset (attr))
|
||||
{
|
||||
dwarf2_complex_location_expr_complaint ();
|
||||
}
|
||||
|
@ -5673,7 +5685,7 @@ read_partial_die (struct partial_die_info *part_die,
|
|||
{
|
||||
part_die->locdesc = DW_BLOCK (&attr);
|
||||
}
|
||||
else if (attr.form == DW_FORM_data4 || attr.form == DW_FORM_data8)
|
||||
else if (attr_form_is_section_offset (&attr))
|
||||
{
|
||||
dwarf2_complex_location_expr_complaint ();
|
||||
}
|
||||
|
@ -9722,6 +9734,46 @@ attr_form_is_block (struct attribute *attr)
|
|||
|| attr->form == DW_FORM_block);
|
||||
}
|
||||
|
||||
/* Return non-zero if ATTR's value is a section offset (classes
|
||||
lineptr, loclistptr, macptr or rangelistptr). In this case,
|
||||
you may use DW_UNSND (attr) to retrieve the offset. */
|
||||
static int
|
||||
attr_form_is_section_offset (struct attribute *attr)
|
||||
{
|
||||
return (attr->form == DW_FORM_data4
|
||||
|| attr->form == DW_FORM_data8);
|
||||
}
|
||||
|
||||
|
||||
/* Return non-zero if ATTR's value falls in the 'constant' class, or
|
||||
zero otherwise. When this function returns true, you can apply
|
||||
dwarf2_get_attr_constant_value to it.
|
||||
|
||||
However, note that for some attributes you must check
|
||||
attr_form_is_section_offset before using this test. DW_FORM_data4
|
||||
and DW_FORM_data8 are members of both the constant class, and of
|
||||
the classes that contain offsets into other debug sections
|
||||
(lineptr, loclistptr, macptr or rangelistptr). The DWARF spec says
|
||||
that, if an attribute's can be either a constant or one of the
|
||||
section offset classes, DW_FORM_data4 and DW_FORM_data8 should be
|
||||
taken as section offsets, not constants. */
|
||||
static int
|
||||
attr_form_is_constant (struct attribute *attr)
|
||||
{
|
||||
switch (attr->form)
|
||||
{
|
||||
case DW_FORM_sdata:
|
||||
case DW_FORM_udata:
|
||||
case DW_FORM_data1:
|
||||
case DW_FORM_data2:
|
||||
case DW_FORM_data4:
|
||||
case DW_FORM_data8:
|
||||
return 1;
|
||||
default:
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
dwarf2_symbol_mark_computed (struct attribute *attr, struct symbol *sym,
|
||||
struct dwarf2_cu *cu)
|
||||
|
@ -9733,7 +9785,7 @@ dwarf2_symbol_mark_computed (struct attribute *attr, struct symbol *sym,
|
|||
if (objfile->separate_debug_objfile_backlink)
|
||||
objfile = objfile->separate_debug_objfile_backlink;
|
||||
|
||||
if ((attr->form == DW_FORM_data4 || attr->form == DW_FORM_data8)
|
||||
if (attr_form_is_section_offset (attr)
|
||||
/* ".debug_loc" may not exist at all, or the offset may be outside
|
||||
the section. If so, fall through to the complaint in the
|
||||
other branch. */
|
||||
|
|
Loading…
Add table
Reference in a new issue