diff options
author | Jakub Jelinek <jakub@redhat.com> | 2011-07-28 18:21:08 +0200 |
---|---|---|
committer | Jakub Jelinek <jakub@gcc.gnu.org> | 2011-07-28 18:21:08 +0200 |
commit | 64153cceb266ecd5794c158db93e92025b457d5d (patch) | |
tree | 7379b4d011cad1ddaa2ade0d8f107bdba79e0fc2 /gcc/dwarf2out.c | |
parent | 844bf05b0d607c110483c0a01462c21a63b28c87 (diff) | |
download | gcc-64153cceb266ecd5794c158db93e92025b457d5d.zip gcc-64153cceb266ecd5794c158db93e92025b457d5d.tar.gz gcc-64153cceb266ecd5794c158db93e92025b457d5d.tar.bz2 |
re PR debug/49871 (-gdwarf-3 creates invalid DWARF3 with DW_AT_data_member_location attribute)
PR debug/49871
* dwarf2out.c (size_of_die, value_format, output_die): Use
DW_FORM_udata instead of DW_FORM_data[48] for
dw_val_class_unsigned_const DW_AT_data_member_location for DWARF 3.
* gcc.dg/debug/dwarf2/pr49871.c: New test.
From-SVN: r176876
Diffstat (limited to 'gcc/dwarf2out.c')
-rw-r--r-- | gcc/dwarf2out.c | 29 |
1 files changed, 26 insertions, 3 deletions
diff --git a/gcc/dwarf2out.c b/gcc/dwarf2out.c index 7109c9d..806c0d75c 100644 --- a/gcc/dwarf2out.c +++ b/gcc/dwarf2out.c @@ -7652,7 +7652,15 @@ size_of_die (dw_die_ref die) size += size_of_sleb128 (AT_int (a)); break; case dw_val_class_unsigned_const: - size += constant_size (AT_unsigned (a)); + { + int csize = constant_size (AT_unsigned (a)); + if (dwarf_version == 3 + && a->dw_attr == DW_AT_data_member_location + && csize >= 4) + size += size_of_uleb128 (AT_unsigned (a)); + else + size += csize; + } break; case dw_val_class_const_double: size += 2 * HOST_BITS_PER_WIDE_INT / HOST_BITS_PER_CHAR; @@ -7953,8 +7961,16 @@ value_format (dw_attr_ref a) case 2: return DW_FORM_data2; case 4: + /* In DWARF3 DW_AT_data_member_location with + DW_FORM_data4 or DW_FORM_data8 is a loclistptr, not + constant, so we need to use DW_FORM_udata if we need + a large constant. */ + if (dwarf_version == 3 && a->dw_attr == DW_AT_data_member_location) + return DW_FORM_udata; return DW_FORM_data4; case 8: + if (dwarf_version == 3 && a->dw_attr == DW_AT_data_member_location) + return DW_FORM_udata; return DW_FORM_data8; default: gcc_unreachable (); @@ -8261,8 +8277,15 @@ output_die (dw_die_ref die) break; case dw_val_class_unsigned_const: - dw2_asm_output_data (constant_size (AT_unsigned (a)), - AT_unsigned (a), "%s", name); + { + int csize = constant_size (AT_unsigned (a)); + if (dwarf_version == 3 + && a->dw_attr == DW_AT_data_member_location + && csize >= 4) + dw2_asm_output_data_uleb128 (AT_unsigned (a), "%s", name); + else + dw2_asm_output_data (csize, AT_unsigned (a), "%s", name); + } break; case dw_val_class_const_double: |