https://gcc.gnu.org/bugzilla/show_bug.cgi?id=105194

            Bug ID: 105194
           Summary: -ftree-dce leads to intermittent visibility of
                    variable due to partial DWARF location ranges
           Product: gcc
           Version: 12.0
            Status: UNCONFIRMED
          Severity: normal
          Priority: P3
         Component: debug
          Assignee: unassigned at gcc dot gnu.org
          Reporter: dc.delia at protonmail dot com
  Target Milestone: ---

When debugging this code, the value of variable l_33 is available when stepping
on line 8 and 10 but appears as optimized out on line 9. We tested and found
the issue at -Og/-O1/-O2/-O3.

Apparently, with -ftree-dce we get DWARF location info for l_33 that does not
include the address of the instruction mapped to line 9. By disabling it,
instead of a location attribute we see in DWARF a const value 1 for l_33 set
(as in the reassignment at line 9 the program compares a boolean expression
against 0), which makes the variable value always available.

We found this issue on x64 using gdb 11.2 with gcc commit 500d3f0a302. As for
past gcc versions, the issue is found in gcc 9/10/11 (we tested 9.3, 10.3,
11.1) but not in 6/7/8 (6.4, 7.5, 8.4). Attaching an analysis for -Og below:

$ cat a.c
short a;
int b;
char c(int d) { return 0; }
char e(int d) { return d; }
void f(int d) {
  int l_33 = 1;
  for (;;) {
    b = e(l_33);
    l_33 = a = (d || c(l_33 = 0)) >= 0;
    if (b)
      break;
  }
}
int main() { f(4); }


GDB trace:
$ gcc -Og -g a.c -o opt
$ gdb -q
Reading symbols from opt...
(gdb) b f
Breakpoint 1 at 0x40048f: file a.c, line 8.
(gdb) r       
Starting program: /tmp/opt 

Breakpoint 1, f (d=4) at a.c:8
8           b = e(l_33);
(gdb) info loc
l_33 = 1
(gdb) n
9           l_33 = a = (d || c(l_33 = 0)) >= 0;
(gdb) info loc
l_33 = <optimized out>
(gdb) n
10          if (b)
(gdb) info loc
l_33 = 1


Code at -Og:
000000000040048f <f>:
  40048f:       bf 01 00 00 00          mov    $0x1,%edi
  400494:       e8 f3 ff ff ff          callq  40048c <e>
  400499:       0f be c0                movsbl %al,%eax
  40049c:       89 05 8a 0b 20 00       mov    %eax,0x200b8a(%rip)        #
60102c <b>
  4004a2:       66 c7 05 85 0b 20 00    movw   $0x1,0x200b85(%rip)        #
601030 <a>
  4004a9:       01 00 
  4004ab:       85 c0                   test   %eax,%eax
  4004ad:       74 e0                   je     40048f <f>
  4004af:       c3                      retq


DWARF info at -Og:
0x000000c6:     DW_TAG_variable
                  DW_AT_name    ("l_33")
                  DW_AT_decl_file       ("/tmp/a.c")
                  DW_AT_decl_line       (6)
                  DW_AT_decl_column     (0x07)
                  DW_AT_type    (0x0000005b "int")
                  DW_AT_location        (0x0000001b: 
                     [0x000000000040048f, 0x00000000004004a2): DW_OP_lit1,
DW_OP_stack_value
                     [0x00000000004004ab, 0x00000000004004b0): DW_OP_lit1,
DW_OP_stack_value)
                  DW_AT_GNU_locviews    (0x00000017)


The transformation behind the issue may be -ftree-dce. If we add -fno-tree-dce
to the compilation command line, the value of variable l_33 is correctly shown
at line 9. In particular, the DWARF location info is not generated but a const
value attribute is emmitted.

Code at -Og with -fno-tree-dce:
000000000040048f <f>:
  40048f:       55                      push   %rbp
  400490:       53                      push   %rbx
  400491:       89 fd                   mov    %edi,%ebp
  400493:       bf 01 00 00 00          mov    $0x1,%edi
  400498:       e8 ef ff ff ff          callq  40048c <e>
  40049d:       0f be d8                movsbl %al,%ebx
  4004a0:       89 1d 86 0b 20 00       mov    %ebx,0x200b86(%rip)        #
60102c <b>
  4004a6:       85 ed                   test   %ebp,%ebp
  4004a8:       66 c7 05 7f 0b 20 00    movw   $0x1,0x200b7f(%rip)        #
601030 <a>
  4004af:       01 00 
  4004b1:       85 db                   test   %ebx,%ebx
  4004b3:       74 de                   je     400493 <f+0x4>
  4004b5:       5b                      pop    %rbx
  4004b6:       5d                      pop    %rbp
  4004b7:       c3                      retq


DWARF info at -Og with -fno-tree-dce:
0x000000c6:     DW_TAG_variable
                  DW_AT_name    ("l_33")
                  DW_AT_decl_file       ("/tmp/a.c")
                  DW_AT_decl_line       (6)
                  DW_AT_decl_column     (0x07)
                  DW_AT_type    (0x0000005b "int")
                  DW_AT_const_value     (0x01)
  • [Bug debug/105194] New: -ftree... dc.delia at protonmail dot com via Gcc-bugs

Reply via email to