The following is just a prototype to try out a new qualifier type tag proposed for DWARFv5. There is not even a draft yet of DWARFv5, so this is just based on a proposal that might or might not be adopted and/or changed http://dwarfstd.org/ShowIssue.php?issue=131112.1
I have a corresponding patch for GDB so that the new testcase added PASSes. But without that patch the guality.exp tests will notice GDB doesn't recognize the new type (or DWARFv5 in general of course) and just mark the test as UNSUPPORTED. Since there is not even a draft of DWARFv5 I don't recommend adopting this patch. All details may change in the future. I am mainly doing it to give better feedback on the DWARFv5 proposals (in this case the feedback would be that it is unfortunate we cannot easily do this as a vendor extension with DW_TAG_GNU_atomic_type since that would break backward compatibility). Feedback on the patch is of course still very welcome. Is there a recommended way for doing/keeping these kind of speculative patches? I'll keep a local git branch with my experiments that I'll rebase against master for larger updates. And would like to send out new patches to the list for review even if we won't adopt them for now. But if there is a better way/best practice for this kind of experimental changes based on just ideas for a next version of a not yet public standard please let me know. gcc/ChangeLog * dwarf2out.h (enum dw_mod_flag): Add dw_mod_atomic. * dwarf2out.c (dw_mod_decl_flags): Handle TYPE_ATOMIC. (dw_mod_type_flags): Likewise. (dw_mods_to_quals): Likewise. (dw_mod_qualified_type): Likewise. (modified_type_die): Likewise. opts.c (common_handle_option): Accept -gdwarf-5. gcc/testsuite/ChangeLog * lib/gcc-gdb-test.exp (gdb-test): Catch '<unknown type in ' to recognize older gdb versions. * gcc.dg/guality/atomic.c: New test. include/ChangeLog * dwarf2.def: Add DWARFv5 DW_TAG_atomic_type. --- gcc/ChangeLog | 10 ++++++++++ gcc/dwarf2out.c | 28 ++++++++++++++++++++++++---- gcc/dwarf2out.h | 3 ++- gcc/opts.c | 2 +- gcc/testsuite/ChangeLog | 6 ++++++ gcc/testsuite/gcc.dg/guality/atomic.c | 13 +++++++++++++ gcc/testsuite/lib/gcc-gdb-test.exp | 2 +- include/ChangeLog | 4 ++++ include/dwarf2.def | 2 ++ 9 files changed, 63 insertions(+), 7 deletions(-) create mode 100644 gcc/testsuite/gcc.dg/guality/atomic.c diff --git a/gcc/ChangeLog b/gcc/ChangeLog index 06a8767..4d81763 100644 --- a/gcc/ChangeLog +++ b/gcc/ChangeLog @@ -1,3 +1,13 @@ +2014-06-22 Mark Wielaard <m...@redhat.com> + + * dwarf2out.h (enum dw_mod_flag): Add dw_mod_atomic. + * dwarf2out.c (dw_mod_decl_flags): Handle TYPE_ATOMIC. + (dw_mod_type_flags): Likewise. + (dw_mods_to_quals): Likewise. + (dw_mod_qualified_type): Likewise. + (modified_type_die): Likewise. + opts.c (common_handle_option): Accept -gdwarf-5. + 2014-06-20 Mark Wielaard <m...@redhat.com> PR debug/59051 diff --git a/gcc/dwarf2out.c b/gcc/dwarf2out.c index b99d1b9..2b8a4bd 100644 --- a/gcc/dwarf2out.c +++ b/gcc/dwarf2out.c @@ -10507,7 +10507,8 @@ dw_mod_decl_flags (const_tree decl) | (TREE_THIS_VOLATILE (decl) ? dw_mod_volatile : dw_mod_none) | ((POINTER_TYPE_P (TREE_TYPE (decl)) && TYPE_RESTRICT (TREE_TYPE (decl))) - ? dw_mod_restrict : dw_mod_none)); + ? dw_mod_restrict : dw_mod_none) + | (TYPE_ATOMIC (TREE_TYPE (decl)) ? dw_mod_atomic : dw_mod_none)); } static int @@ -10516,7 +10517,8 @@ dw_mod_type_flags (const_tree type) return ((TYPE_READONLY (type) ? dw_mod_const : dw_mod_none) | (TYPE_VOLATILE (type) ? dw_mod_volatile : dw_mod_none) | ((POINTER_TYPE_P (type) && TYPE_RESTRICT (type)) - ? dw_mod_restrict : dw_mod_none)); + ? dw_mod_restrict : dw_mod_none) + | (TYPE_ATOMIC (type) ? dw_mod_atomic : dw_mod_none)); } static int @@ -10524,7 +10526,8 @@ dw_mods_to_quals (int mods) { return (((mods & dw_mod_const) ? TYPE_QUAL_CONST : 0) | ((mods & dw_mod_volatile) ? TYPE_QUAL_VOLATILE : 0) - | ((mods & dw_mod_restrict) ? TYPE_QUAL_RESTRICT : 0)); + | ((mods & dw_mod_restrict) ? TYPE_QUAL_RESTRICT : 0) + | ((mods & dw_mod_atomic) ? TYPE_QUAL_ATOMIC : 0)); } /* Returns true if there is a qualified type with at least one @@ -10549,6 +10552,9 @@ dw_mod_qualified_type (tree type, int mods) if (mods & dw_mod_restrict) return dw_mod_qualified_type (type, mods & ~dw_mod_restrict); + if (mods & dw_mod_atomic) + return dw_mod_qualified_type (type, mods & ~dw_mod_atomic); + gcc_unreachable (); } @@ -10575,6 +10581,10 @@ modified_type_die (tree type, int mods, dw_die_ref context_die) if (dwarf_version < 3) mods &= ~dw_mod_restrict; + /* Likewise for DW_TAG_atomic_type for DWARFv5. */ + if (dwarf_version < 5) + mods &= ~dw_mod_atomic; + /* See if we already have the appropriately qualified variant of this type. */ qualified_type = get_qualified_type (type, dw_mods_to_quals (mods)); @@ -10618,9 +10628,11 @@ modified_type_die (tree type, int mods, dw_die_ref context_die) else if ((mods & dw_mod_const) < TYPE_READONLY (dtype) || (mods & dw_mod_volatile) < TYPE_VOLATILE (dtype) || (mods & dw_mod_restrict) < TYPE_RESTRICT (dtype) + || (mods & dw_mod_atomic) < TYPE_ATOMIC (dtype) || ((mods & dw_mod_const) <= TYPE_READONLY (dtype) && (mods & dw_mod_volatile) <= TYPE_VOLATILE (dtype) && (mods & dw_mod_restrict) <= TYPE_RESTRICT (dtype) + && (mods & dw_mod_atomic) <= TYPE_ATOMIC (dtype) && DECL_ORIGINAL_TYPE (name) != type)) /* cv-unqualified version of named type. Just use the unnamed type to which it refers. */ @@ -10649,11 +10661,19 @@ modified_type_die (tree type, int mods, dw_die_ref context_die) mod_type_die = new_die (DW_TAG_volatile_type, mod_scope, type); sub_die = modified_type_die (type, mods & ~dw_mod_volatile, context_die); } - else if (mods & dw_mod_restrict) + else if ((mods & dw_mod_restrict) + && (((mods & ~dw_mod_restrict) == dw_mod_none) + || get_qualified_type (type, dw_mods_to_quals (mods)) == NULL_TREE + || dw_mod_qualified_type (type, mods & ~dw_mod_restrict))) { mod_type_die = new_die (DW_TAG_restrict_type, mod_scope, type); sub_die = modified_type_die (type, mods & ~dw_mod_restrict, context_die); } + else if (mods & dw_mod_atomic) + { + mod_type_die = new_die (DW_TAG_atomic_type, mod_scope, type); + sub_die = modified_type_die (type, mods & ~dw_mod_atomic, context_die); + } else if (code == POINTER_TYPE) { mod_type_die = new_die (DW_TAG_pointer_type, mod_scope, type); diff --git a/gcc/dwarf2out.h b/gcc/dwarf2out.h index 7c109ea..8d5a5c9 100644 --- a/gcc/dwarf2out.h +++ b/gcc/dwarf2out.h @@ -52,7 +52,8 @@ enum dw_mod_flag { dw_mod_none = 0, dw_mod_restrict = 1, dw_mod_const = 1 << 1, - dw_mod_volatile = 1 << 2 + dw_mod_volatile = 1 << 2, + dw_mod_atomic = 1 << 3 }; typedef union GTY(()) { diff --git a/gcc/opts.c b/gcc/opts.c index 324d545..719f741 100644 --- a/gcc/opts.c +++ b/gcc/opts.c @@ -1839,7 +1839,7 @@ common_handle_option (struct gcc_options *opts, /* FALLTHRU */ case OPT_gdwarf_: - if (value < 2 || value > 4) + if (value < 2 || value > 5) error_at (loc, "dwarf version %d is not supported", value); else opts->x_dwarf_version = value; diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog index 9c5418c..d370648 100644 --- a/gcc/testsuite/ChangeLog +++ b/gcc/testsuite/ChangeLog @@ -1,3 +1,9 @@ +2014-06-22 Mark Wielaard <m...@redhat.com> + + * lib/gcc-gdb-test.exp (gdb-test): Catch '<unknown type in ' to + recognize older gdb versions. + * gcc.dg/guality/atomic.c: New test. + 2014-06-20 Mark Wielaard <m...@redhat.com> * gcc.dg/guality/restrict.c: New test. diff --git a/gcc/testsuite/gcc.dg/guality/atomic.c b/gcc/testsuite/gcc.dg/guality/atomic.c new file mode 100644 index 0000000..c76cfa4 --- /dev/null +++ b/gcc/testsuite/gcc.dg/guality/atomic.c @@ -0,0 +1,13 @@ +/* debuginfo tests for the _Atomic type qualifier. */ +/* { dg-do run } */ +/* { dg-options "-std=c11 -gdwarf-5" } */ + +volatile _Atomic int * const _Atomic hwaddr = (void *) 0x1234; + +int +main (int argc, char **argv) +{ + return hwaddr == (void *) argv[0]; +} + +/* { dg-final { gdb-test 10 "type:hwaddr" "volatile _Atomic int * const _Atomic" } } */ diff --git a/gcc/testsuite/lib/gcc-gdb-test.exp b/gcc/testsuite/lib/gcc-gdb-test.exp index 0a8a6df..c729793 100644 --- a/gcc/testsuite/lib/gcc-gdb-test.exp +++ b/gcc/testsuite/lib/gcc-gdb-test.exp @@ -83,7 +83,7 @@ proc gdb-test { args } { remote_expect target [timeout_value] { # Too old GDB - -re "Unhandled dwarf expression|Error in sourced command file" { + -re "Unhandled dwarf expression|Error in sourced command file|<unknown type in " { unsupported "$testname" remote_close target file delete $cmd_file diff --git a/include/ChangeLog b/include/ChangeLog index 1cda0dc..5d42014 100644 --- a/include/ChangeLog +++ b/include/ChangeLog @@ -1,3 +1,7 @@ +2014-06-22 Mark Wielaard <m...@redhat.com> + + * dwarf2.def: Add DWARFv5 DW_TAG_atomic_type. + 2014-06-10 Thomas Schwinge <tho...@codesourcery.com> PR lto/61334 diff --git a/include/dwarf2.def b/include/dwarf2.def index 71a37b3..6941922 100644 --- a/include/dwarf2.def +++ b/include/dwarf2.def @@ -133,6 +133,8 @@ DW_TAG (DW_TAG_shared_type, 0x40) DW_TAG (DW_TAG_type_unit, 0x41) DW_TAG (DW_TAG_rvalue_reference_type, 0x42) DW_TAG (DW_TAG_template_alias, 0x43) +/* DWARF 5. */ +DW_TAG (DW_TAG_atomic_type, 0x47) DW_TAG_DUP (DW_TAG_lo_user, 0x4080) DW_TAG_DUP (DW_TAG_hi_user, 0xffff) -- 1.7.1