dwarf2out: Emit DW_AT_location for global register vars during early dwarf [PR101905]
authorJakub Jelinek <jakub@redhat.com>
Mon, 23 Aug 2021 09:50:14 +0000 (11:50 +0200)
committerJakub Jelinek <jakub@redhat.com>
Mon, 23 Aug 2021 09:50:14 +0000 (11:50 +0200)
The following patch emits DW_AT_location for global register variables
already during early dwarf, since usually late_global_decl hook isn't even
called for those, as nothing needs to be emitted for them.

2021-08-23  Jakub Jelinek  <jakub@redhat.com>

PR debug/101905
* dwarf2out.c (gen_variable_die): Add DW_AT_location for global
register variables already during early_dwarf if possible.

* gcc.dg/guality/pr101905.c: New test.

gcc/dwarf2out.c
gcc/testsuite/gcc.dg/guality/pr101905.c [new file with mode: 0644]

index ba0a6d6..07a479f 100644 (file)
@@ -24476,7 +24476,26 @@ gen_variable_die (tree decl, tree origin, dw_die_ref context_die)
              && DECL_RTL_SET_P (decl_or_origin))))
     {
       if (early_dwarf)
-       add_pubname (decl_or_origin, var_die);
+       {
+         add_pubname (decl_or_origin, var_die);
+         /* For global register variables, emit DW_AT_location if possible
+            already during early_dwarf, as late_global_decl won't be usually
+            called.  */
+         if (DECL_HARD_REGISTER (decl_or_origin)
+             && TREE_STATIC (decl_or_origin)
+             && !decl_by_reference_p (decl_or_origin)
+             && !get_AT (var_die, DW_AT_location)
+             && !get_AT (var_die, DW_AT_const_value)
+             && DECL_RTL_SET_P (decl_or_origin)
+             && REG_P (DECL_RTL (decl_or_origin)))
+           {
+             dw_loc_descr_ref descr
+               = reg_loc_descriptor (DECL_RTL (decl_or_origin),
+                                     VAR_INIT_STATUS_INITIALIZED);
+             if (descr)
+               add_AT_loc (var_die, DW_AT_location, descr);
+           }
+       }
       else
        add_location_or_const_value_attribute (var_die, decl_or_origin,
                                               decl == NULL);
diff --git a/gcc/testsuite/gcc.dg/guality/pr101905.c b/gcc/testsuite/gcc.dg/guality/pr101905.c
new file mode 100644 (file)
index 0000000..71b7516
--- /dev/null
@@ -0,0 +1,15 @@
+/* { dg-do run { target { { i?86-*-* x86_64-*-* } && lp64 } } } */
+/* { dg-options "-g -ffixed-r15" } */
+/* { dg-skip-if "" { *-*-* }  { "*" } { "-O0" } } */
+
+register unsigned long long regVar asm ("r15");
+
+int
+main()
+{
+  regVar = 0xdeadbeefcafebabeULL;
+  asm ("nop" : "+r" (regVar));
+  asm volatile ("nop");                /* { dg-final { gdb-test . "regVar" "0xdeadbeefcafebabeULL" } } */
+  asm volatile ("nop" : : "r" (regVar));
+  return 0;
+}