diff options
author | Alexandre Oliva <aoliva@redhat.com> | 2016-08-19 15:57:11 -0300 |
---|---|---|
committer | Alexandre Oliva <aoliva@redhat.com> | 2016-09-02 21:15:12 -0300 |
commit | 0ff28ef21a21b2577bd1cc3a9655bfc96f1edc47 (patch) | |
tree | fbbf9a01dade4b8ad9c402786f9b2bfa85686460 | |
parent | 0e338ebb5a8ded9d39895ed6e478a137ba630de7 (diff) | |
download | gcc-0ff28ef21a21b2577bd1cc3a9655bfc96f1edc47.tar.gz |
[PR63238] output alignment debug information
Output DWARFv5+ DW_AT_alignment for non-default alignment of
variables, fields and types.
for include/ChangeLog
PR debug/63238
* dwarf2.def (DW_AT_alignment): New.
for gcc/ChangeLog
PR debug/63238
* dwarf2out.c (clone_as_declaration): Drop DW_AT_alignment.
(add_alignment_attribute): New.
(base_type_die): Add alignment attribute.
(subrange_type_die): Likewise.
(modified_type_die): Likewise.
(gen_array_type_die): Likewise.
(gen_descr_array_type_die: Likewise.
(gen_enumeration_type_die): Likewise.
(gen_subprogram_die): Likewise.
(gen_variable_die): Likewise.
(gen_field_die): Likewise.
(gen_ptr_to_mbr_type_die): Likewise.
(gen_struct_or_union_type_die): Likewise.
(gen_subroutine_type_die): Likewise.
(gen_typedef_die): Likewise.
(base_type_cmp): Compare alignment attribute.
for gcc/testsuite/ChangeLog
PR debug/63238
* gcc.dg/debug/dwarf2/align-1.c: New.
* gcc.dg/debug/dwarf2/align-2.c: New.
* gcc.dg/debug/dwarf2/align-3.c: New.
* gcc.dg/debug/dwarf2/align-4.c: New.
* gcc.dg/debug/dwarf2/align-5.c: New.
* gcc.dg/debug/dwarf2/align-6.c: New.
* gcc.dg/debug/dwarf2/align-as-1.c: New.
* g++.dg/debug/dwarf2/align-1.C: New.
* g++.dg/debug/dwarf2/align-2.C: New.
* g++.dg/debug/dwarf2/align-3.C: New.
* g++.dg/debug/dwarf2/align-4.C: New.
* g++.dg/debug/dwarf2/align-5.C: New.
* g++.dg/debug/dwarf2/align-6.C: New.
-rw-r--r-- | gcc/dwarf2out.c | 76 | ||||
-rw-r--r-- | gcc/testsuite/g++.dg/debug/dwarf2/align-1.C | 5 | ||||
-rw-r--r-- | gcc/testsuite/g++.dg/debug/dwarf2/align-2.C | 6 | ||||
-rw-r--r-- | gcc/testsuite/g++.dg/debug/dwarf2/align-3.C | 7 | ||||
-rw-r--r-- | gcc/testsuite/g++.dg/debug/dwarf2/align-4.C | 7 | ||||
-rw-r--r-- | gcc/testsuite/g++.dg/debug/dwarf2/align-5.C | 7 | ||||
-rw-r--r-- | gcc/testsuite/g++.dg/debug/dwarf2/align-6.C | 9 | ||||
-rw-r--r-- | gcc/testsuite/gcc.dg/debug/dwarf2/align-1.c | 5 | ||||
-rw-r--r-- | gcc/testsuite/gcc.dg/debug/dwarf2/align-2.c | 6 | ||||
-rw-r--r-- | gcc/testsuite/gcc.dg/debug/dwarf2/align-3.c | 7 | ||||
-rw-r--r-- | gcc/testsuite/gcc.dg/debug/dwarf2/align-4.c | 7 | ||||
-rw-r--r-- | gcc/testsuite/gcc.dg/debug/dwarf2/align-5.c | 7 | ||||
-rw-r--r-- | gcc/testsuite/gcc.dg/debug/dwarf2/align-6.c | 9 | ||||
-rw-r--r-- | gcc/testsuite/gcc.dg/debug/dwarf2/align-as-1.c | 5 | ||||
-rw-r--r-- | include/dwarf2.def | 1 |
15 files changed, 158 insertions, 6 deletions
diff --git a/gcc/dwarf2out.c b/gcc/dwarf2out.c index 4576377f9af..05ef2e4c02a 100644 --- a/gcc/dwarf2out.c +++ b/gcc/dwarf2out.c @@ -3346,6 +3346,7 @@ static void add_bound_info (dw_die_ref, enum dwarf_attribute, tree, const struct loc_descr_context *); static void add_subscript_info (dw_die_ref, tree, bool); static void add_byte_size_attribute (dw_die_ref, tree); +static void add_alignment_attribute (dw_die_ref, tree); static inline void add_bit_offset_attribute (dw_die_ref, tree, struct vlr_context *); static void add_bit_size_attribute (dw_die_ref, tree); @@ -7429,6 +7430,7 @@ clone_as_declaration (dw_die_ref die) add_dwarf_attr (clone, a); break; case DW_AT_byte_size: + case DW_AT_alignment: default: break; } @@ -10952,6 +10954,8 @@ base_type_die (tree type, bool reverse) add_AT_unsigned (base_type_result, DW_AT_endianity, BYTES_BIG_ENDIAN ? DW_END_little : DW_END_big); + add_alignment_attribute (base_type_result, type); + if (fpt_used) { switch (fpt_info.scale_factor_kind) @@ -11115,6 +11119,8 @@ subrange_type_die (tree type, tree low, tree high, tree bias, add_AT_unsigned (subrange_die, DW_AT_byte_size, size_in_bytes); } + add_alignment_attribute (subrange_die, type); + if (low) add_bound_info (subrange_die, DW_AT_lower_bound, low, NULL); if (high) @@ -11432,6 +11438,7 @@ modified_type_die (tree type, int cv_quals, bool reverse, add_AT_unsigned (mod_type_die, DW_AT_byte_size, simple_type_size_in_bits (type) / BITS_PER_UNIT); + add_alignment_attribute (mod_type_die, type); item_type = TREE_TYPE (type); addr_space_t as = TYPE_ADDR_SPACE (item_type); @@ -18604,6 +18611,37 @@ add_byte_size_attribute (dw_die_ref die, tree tree_node) add_AT_unsigned (die, DW_AT_byte_size, size); } +/* Add a DW_AT_alignment attribute to DIE with TREE_NODE's non-default + alignment. */ + +static void +add_alignment_attribute (dw_die_ref die, tree tree_node) +{ + if (dwarf_version < 5 && dwarf_strict) + return; + + unsigned align; + + if (DECL_P (tree_node)) + { + if (!DECL_USER_ALIGN (tree_node)) + return; + + align = DECL_ALIGN_UNIT (tree_node); + } + else if (TYPE_P (tree_node)) + { + if (!TYPE_USER_ALIGN (tree_node)) + return; + + align = TYPE_ALIGN_UNIT (tree_node); + } + else + gcc_unreachable (); + + add_AT_unsigned (die, DW_AT_alignment, align); +} + /* For a FIELD_DECL node which represents a bit-field, output an attribute which specifies the distance in bits from the highest order bit of the "containing object" for the bit-field to the highest order bit of the @@ -19421,6 +19459,8 @@ gen_array_type_die (tree type, dw_die_ref context_die) if (get_AT (array_die, DW_AT_name)) add_pubtype (type, array_die); + + add_alignment_attribute (array_die, type); } /* After all arguments are created, adjust any DW_TAG_string_type @@ -19548,6 +19588,8 @@ gen_descr_array_type_die (tree type, struct array_descr_info *info, if (get_AT (array_die, DW_AT_name)) add_pubtype (type, array_die); + + add_alignment_attribute (array_die, type); } #if 0 @@ -19652,6 +19694,7 @@ gen_enumeration_type_die (tree type, dw_die_ref context_die) TREE_ASM_WRITTEN (type) = 1; add_byte_size_attribute (type_die, type); + add_alignment_attribute (type_die, type); if (dwarf_version >= 3 || !dwarf_strict) { tree underlying = lang_hooks.types.enum_underlying_base_type (type); @@ -19710,6 +19753,8 @@ gen_enumeration_type_die (tree type, dw_die_ref context_die) else add_AT_flag (type_die, DW_AT_declaration, 1); + add_alignment_attribute (type_die, type); + add_pubtype (type, type_die); return type_die; @@ -20612,6 +20657,8 @@ gen_subprogram_die (tree decl, dw_die_ref context_die) if (TREE_THIS_VOLATILE (decl) && (dwarf_version >= 5 || !dwarf_strict)) add_AT_flag (subr_die, DW_AT_noreturn, 1); + add_alignment_attribute (subr_die, decl); + add_accessibility_attribute (subr_die, decl); } @@ -21329,6 +21376,7 @@ gen_variable_die (tree decl, tree origin, dw_die_ref context_die) add_type_attribute (var_die, TREE_TYPE (decl_or_origin), decl_quals (decl_or_origin), false, context_die); + add_alignment_attribute (var_die, decl); add_AT_flag (var_die, DW_AT_external, 1); if (loc) { @@ -21456,6 +21504,8 @@ gen_variable_die (tree decl, tree origin, dw_die_ref context_die) if (DECL_ARTIFICIAL (decl)) add_AT_flag (var_die, DW_AT_artificial, 1); + add_alignment_attribute (var_die, decl); + add_accessibility_attribute (var_die, decl); } @@ -21805,6 +21855,8 @@ gen_field_die (tree decl, struct vlr_context *ctx, dw_die_ref context_die) add_bit_offset_attribute (decl_die, decl, ctx); } + add_alignment_attribute (decl_die, decl); + /* If we have a variant part offset, then we are supposed to process a member of a QUAL_UNION_TYPE, which is how we represent variant parts in trees. */ @@ -21879,6 +21931,7 @@ gen_ptr_to_mbr_type_die (tree type, dw_die_ref context_die, lookup_type_die (class_type)); add_type_attribute (ptr_die, member_type, TYPE_UNQUALIFIED, false, context_die); + add_alignment_attribute (ptr_die, type); if (TREE_CODE (type) == OFFSET_TYPE) { @@ -22731,6 +22784,7 @@ gen_struct_or_union_type_die (tree type, dw_die_ref context_die, this type is expressed in terms of this type itself. */ TREE_ASM_WRITTEN (type) = 1; add_byte_size_attribute (type_die, type); + add_alignment_attribute (type_die, type); if (TYPE_STUB_DECL (type) != NULL_TREE) { add_src_coords_attributes (type_die, TYPE_STUB_DECL (type)); @@ -22788,6 +22842,7 @@ gen_subroutine_type_die (tree type, dw_die_ref context_die) add_prototyped_attribute (subr_die, type); add_type_attribute (subr_die, return_type, TYPE_UNQUALIFIED, false, context_die); + add_alignment_attribute (subr_die, type); gen_formal_types_die (type, subr_die); if (get_AT (subr_die, DW_AT_name)) @@ -22835,7 +22890,10 @@ gen_typedef_die (tree decl, dw_die_ref context_die) add_abstract_origin_attribute (type_die, origin); else { - tree type; + tree type = TREE_TYPE (decl); + + if (type == error_mark_node) + return; add_name_and_src_coords_attributes (type_die, decl); if (DECL_ORIGINAL_TYPE (decl)) @@ -22850,11 +22908,6 @@ gen_typedef_die (tree decl, dw_die_ref context_die) } else { - type = TREE_TYPE (decl); - - if (type == error_mark_node) - return; - if (is_naming_typedef_decl (TYPE_NAME (type))) { /* Here, we are in the case of decl being a typedef naming @@ -22893,6 +22946,10 @@ gen_typedef_die (tree decl, dw_die_ref context_die) created. */ equate_type_number_to_die (type, type_die); + type = TREE_TYPE (decl); + + add_alignment_attribute (type_die, type); + add_accessibility_attribute (type_die, decl); } @@ -26468,6 +26525,7 @@ base_type_cmp (const void *x, const void *y) dw_die_ref dy = *(const dw_die_ref *) y; unsigned int byte_size1, byte_size2; unsigned int encoding1, encoding2; + unsigned int align1, align2; if (dx->die_mark > dy->die_mark) return -1; if (dx->die_mark < dy->die_mark) @@ -26484,6 +26542,12 @@ base_type_cmp (const void *x, const void *y) return 1; if (encoding1 > encoding2) return -1; + align1 = get_AT_unsigned (dx, DW_AT_alignment); + align2 = get_AT_unsigned (dy, DW_AT_alignment); + if (align1 < align2) + return 1; + if (align1 > align2) + return -1; return 0; } diff --git a/gcc/testsuite/g++.dg/debug/dwarf2/align-1.C b/gcc/testsuite/g++.dg/debug/dwarf2/align-1.C new file mode 100644 index 00000000000..58b773179cb --- /dev/null +++ b/gcc/testsuite/g++.dg/debug/dwarf2/align-1.C @@ -0,0 +1,5 @@ +// { dg-do compile } +// { dg-options "-O -g -dA" } +// { dg-final { scan-assembler-times " DW_AT_alignment" 1 { xfail { powerpc-ibm-aix* } } } } + +int __attribute__((__aligned__(64))) i; diff --git a/gcc/testsuite/g++.dg/debug/dwarf2/align-2.C b/gcc/testsuite/g++.dg/debug/dwarf2/align-2.C new file mode 100644 index 00000000000..31eed4a5141 --- /dev/null +++ b/gcc/testsuite/g++.dg/debug/dwarf2/align-2.C @@ -0,0 +1,6 @@ +// { dg-do compile } +// { dg-options "-O -g -dA" } +// { dg-final { scan-assembler-times " DW_AT_alignment" 1 { xfail { powerpc-ibm-aix* } } } } + +typedef int __attribute__((__aligned__(64))) i_t; +i_t i; diff --git a/gcc/testsuite/g++.dg/debug/dwarf2/align-3.C b/gcc/testsuite/g++.dg/debug/dwarf2/align-3.C new file mode 100644 index 00000000000..328ea0d1ae3 --- /dev/null +++ b/gcc/testsuite/g++.dg/debug/dwarf2/align-3.C @@ -0,0 +1,7 @@ +// { dg-do compile } +// { dg-options "-O -g -dA" } +// { dg-final { scan-assembler-times " DW_AT_alignment" 1 { xfail { powerpc-ibm-aix* } } } } + +typedef int int_t; +typedef int_t __attribute__((__aligned__(64))) i_t; +i_t i; diff --git a/gcc/testsuite/g++.dg/debug/dwarf2/align-4.C b/gcc/testsuite/g++.dg/debug/dwarf2/align-4.C new file mode 100644 index 00000000000..31e9e81b62e --- /dev/null +++ b/gcc/testsuite/g++.dg/debug/dwarf2/align-4.C @@ -0,0 +1,7 @@ +// { dg-do compile } +// { dg-options "-O -g -dA" } +// { dg-final { scan-assembler-times " DW_AT_alignment" 2 { xfail { powerpc-ibm-aix* } } } } + +struct tt { + int __attribute__((__aligned__(64))) i; +} t; diff --git a/gcc/testsuite/g++.dg/debug/dwarf2/align-5.C b/gcc/testsuite/g++.dg/debug/dwarf2/align-5.C new file mode 100644 index 00000000000..21166463902 --- /dev/null +++ b/gcc/testsuite/g++.dg/debug/dwarf2/align-5.C @@ -0,0 +1,7 @@ +// { dg-do compile } +// { dg-options "-O -g -dA" } +// { dg-final { scan-assembler-times " DW_AT_alignment" 1 { xfail { powerpc-ibm-aix* } } } } + +struct tt { + int i; +} __attribute__((__aligned__(64))) t; diff --git a/gcc/testsuite/g++.dg/debug/dwarf2/align-6.C b/gcc/testsuite/g++.dg/debug/dwarf2/align-6.C new file mode 100644 index 00000000000..e8fc43f6e90 --- /dev/null +++ b/gcc/testsuite/g++.dg/debug/dwarf2/align-6.C @@ -0,0 +1,9 @@ +// { dg-do compile } +// { dg-options "-O -g -dA" } +// { dg-final { scan-assembler-times " DW_AT_alignment" 1 { xfail { powerpc-ibm-aix* } } } } + +struct tt { + int i; +}; + +struct tt __attribute__((__aligned__(64))) t; diff --git a/gcc/testsuite/gcc.dg/debug/dwarf2/align-1.c b/gcc/testsuite/gcc.dg/debug/dwarf2/align-1.c new file mode 100644 index 00000000000..58b773179cb --- /dev/null +++ b/gcc/testsuite/gcc.dg/debug/dwarf2/align-1.c @@ -0,0 +1,5 @@ +// { dg-do compile } +// { dg-options "-O -g -dA" } +// { dg-final { scan-assembler-times " DW_AT_alignment" 1 { xfail { powerpc-ibm-aix* } } } } + +int __attribute__((__aligned__(64))) i; diff --git a/gcc/testsuite/gcc.dg/debug/dwarf2/align-2.c b/gcc/testsuite/gcc.dg/debug/dwarf2/align-2.c new file mode 100644 index 00000000000..31eed4a5141 --- /dev/null +++ b/gcc/testsuite/gcc.dg/debug/dwarf2/align-2.c @@ -0,0 +1,6 @@ +// { dg-do compile } +// { dg-options "-O -g -dA" } +// { dg-final { scan-assembler-times " DW_AT_alignment" 1 { xfail { powerpc-ibm-aix* } } } } + +typedef int __attribute__((__aligned__(64))) i_t; +i_t i; diff --git a/gcc/testsuite/gcc.dg/debug/dwarf2/align-3.c b/gcc/testsuite/gcc.dg/debug/dwarf2/align-3.c new file mode 100644 index 00000000000..328ea0d1ae3 --- /dev/null +++ b/gcc/testsuite/gcc.dg/debug/dwarf2/align-3.c @@ -0,0 +1,7 @@ +// { dg-do compile } +// { dg-options "-O -g -dA" } +// { dg-final { scan-assembler-times " DW_AT_alignment" 1 { xfail { powerpc-ibm-aix* } } } } + +typedef int int_t; +typedef int_t __attribute__((__aligned__(64))) i_t; +i_t i; diff --git a/gcc/testsuite/gcc.dg/debug/dwarf2/align-4.c b/gcc/testsuite/gcc.dg/debug/dwarf2/align-4.c new file mode 100644 index 00000000000..31e9e81b62e --- /dev/null +++ b/gcc/testsuite/gcc.dg/debug/dwarf2/align-4.c @@ -0,0 +1,7 @@ +// { dg-do compile } +// { dg-options "-O -g -dA" } +// { dg-final { scan-assembler-times " DW_AT_alignment" 2 { xfail { powerpc-ibm-aix* } } } } + +struct tt { + int __attribute__((__aligned__(64))) i; +} t; diff --git a/gcc/testsuite/gcc.dg/debug/dwarf2/align-5.c b/gcc/testsuite/gcc.dg/debug/dwarf2/align-5.c new file mode 100644 index 00000000000..21166463902 --- /dev/null +++ b/gcc/testsuite/gcc.dg/debug/dwarf2/align-5.c @@ -0,0 +1,7 @@ +// { dg-do compile } +// { dg-options "-O -g -dA" } +// { dg-final { scan-assembler-times " DW_AT_alignment" 1 { xfail { powerpc-ibm-aix* } } } } + +struct tt { + int i; +} __attribute__((__aligned__(64))) t; diff --git a/gcc/testsuite/gcc.dg/debug/dwarf2/align-6.c b/gcc/testsuite/gcc.dg/debug/dwarf2/align-6.c new file mode 100644 index 00000000000..e8fc43f6e90 --- /dev/null +++ b/gcc/testsuite/gcc.dg/debug/dwarf2/align-6.c @@ -0,0 +1,9 @@ +// { dg-do compile } +// { dg-options "-O -g -dA" } +// { dg-final { scan-assembler-times " DW_AT_alignment" 1 { xfail { powerpc-ibm-aix* } } } } + +struct tt { + int i; +}; + +struct tt __attribute__((__aligned__(64))) t; diff --git a/gcc/testsuite/gcc.dg/debug/dwarf2/align-as-1.c b/gcc/testsuite/gcc.dg/debug/dwarf2/align-as-1.c new file mode 100644 index 00000000000..6923257e111 --- /dev/null +++ b/gcc/testsuite/gcc.dg/debug/dwarf2/align-as-1.c @@ -0,0 +1,5 @@ +// { dg-do compile } +// { dg-options "-O -g -dA" } +// { dg-final { scan-assembler-times " DW_AT_alignment" 1 { xfail { powerpc-ibm-aix* } } } } + +int _Alignas(64) i; diff --git a/include/dwarf2.def b/include/dwarf2.def index 0bd729be352..78a3c3770cf 100644 --- a/include/dwarf2.def +++ b/include/dwarf2.def @@ -314,6 +314,7 @@ DW_AT (DW_AT_string_length_byte_size, 0x70) DW_AT (DW_AT_reference, 0x77) DW_AT (DW_AT_rvalue_reference, 0x78) DW_AT (DW_AT_noreturn, 0x87) +DW_AT (DW_AT_alignment, 0x88) DW_AT (DW_AT_deleted, 0x8a) DW_AT (DW_AT_defaulted, 0x8b) |