Open Quuxplusone opened 7 years ago
Bugzilla Link | PR35318 |
Status | NEW |
Importance | P enhancement |
Reported by | Adrian Prantl (aprantl@apple.com) |
Reported on | 2017-11-15 10:11:04 -0800 |
Last modified on | 2019-09-12 05:02:16 -0700 |
Version | trunk |
Hardware | PC All |
CC | aprantl@apple.com, david.stenberg@ericsson.com, dblaikie@gmail.com, jeremy.morse.llvm@gmail.com, llvm-bugs@lists.llvm.org, rnk@google.com |
Fixed by commit(s) | |
Attachments | |
Blocks | |
Blocked by | |
See also |
I have to be more specific. The location is not *wrong* it just begins too late
to be useful.
0x0000000100000f84 is the beginning of the epilogue:
(lldb) b 0x0000000100000f84
Breakpoint 3: where = test`main + 68 at t.c:6, address = 0x0000000100000f84
(lldb) c
Process 30997 resuming
Process 30997 stopped
* thread #1, queue = 'com.apple.main-thread', stop reason = breakpoint 3.1
frame #0: 0x0000000100000f84 test`main(argc=1, argv=0x00007ffeefbff848) at t.c:6
3 int i = argc;
4 ++i;
5 ++i;
-> 6 return i;
7 }
Target 0: (test) stopped.
(lldb) fr var
(int) argc = 1
(char **) argv = 0x00007ffeefbff848
(int) i = 3
(lldb) dis
0x100000f82 <+66>: movl %ecx, %eax
-> 0x100000f84 <+68>: addq $0x20, %rsp
0x100000f88 <+72>: popq %rbp
0x100000f89 <+73>: retq
This is still reproducible on trunk.
The dbg.addr seems to be placed incorrectly after instruction selection.
Before:
*** IR Dump After Module Verifier ***
; Function Attrs: noinline nounwind optnone uwtable
define dso_local i32 @main(i32 %argc, i8** %argv) #0 !dbg !7 {
entry:
%retval = alloca i32, align 4
%argc.addr = alloca i32, align 4
%argv.addr = alloca i8**, align 8
%i = alloca i32, align 4
store i32 0, i32* %retval, align 4
store i32 %argc, i32* %argc.addr, align 4
call void @llvm.dbg.addr(metadata i32* %argc.addr, metadata !14, metadata !DIExpression()), !dbg !15
store i8** %argv, i8*** %argv.addr, align 8
call void @llvm.dbg.addr(metadata i8*** %argv.addr, metadata !16, metadata !DIExpression()), !dbg !17
%0 = load i8**, i8*** %argv.addr, align 8, !dbg !18
%arrayidx = getelementptr inbounds i8*, i8** %0, i64 0, !dbg !18
%1 = load i8*, i8** %arrayidx, align 8, !dbg !18
%call = call i32 (i8*, ...) @printf(i8* %1), !dbg !19
-> call void @llvm.dbg.addr(metadata i32* %i, metadata !20, metadata
!DIExpression()), !dbg !21
%2 = load i32, i32* %argc.addr, align 4, !dbg !22
store i32 %2, i32* %i, align 4, !dbg !21
%3 = load i32, i32* %i, align 4, !dbg !23
%inc = add nsw i32 %3, 1, !dbg !23
store i32 %inc, i32* %i, align 4, !dbg !23
%4 = load i32, i32* %i, align 4, !dbg !24
%inc1 = add nsw i32 %4, 1, !dbg !24
store i32 %inc1, i32* %i, align 4, !dbg !24
%5 = load i32, i32* %i, align 4, !dbg !25
ret i32 %5, !dbg !26
}
# *** IR Dump Before X86 DAG->DAG Instruction Selection ***:
# Machine code for function main: IsSSA, TracksLiveness
After:
# *** IR Dump After X86 DAG->DAG Instruction Selection ***:
# Machine code for function main: IsSSA, TracksLiveness
Frame Objects:
fi#0: size=4, align=4, at location [SP+8]
fi#1: size=4, align=4, at location [SP+8]
fi#2: size=8, align=8, at location [SP+8]
fi#3: size=4, align=4, at location [SP+8]
Function Live Ins: $edi in %0, $rsi in %2
bb.0.entry:
liveins: $edi, $rsi
%2:gr64 = COPY $rsi
%0:gr32 = COPY $edi
%1:gr32 = COPY killed %0:gr32
%3:gr64 = COPY killed %2:gr64
MOV32mi %stack.0.retval, 1, $noreg, 0, $noreg, 0 :: (store 4 into %ir.retval)
MOV32mr %stack.1.argc.addr, 1, $noreg, 0, $noreg, %1:gr32 :: (store 4 into %ir.argc.addr)
DBG_VALUE %stack.1.argc.addr, 0, !"argc", !DIExpression(), debug-location !15; pr35318.c:1:14 line no:1
MOV64mr %stack.2.argv.addr, 1, $noreg, 0, $noreg, %3:gr64 :: (store 8 into %ir.argv.addr)
DBG_VALUE %stack.2.argv.addr, 0, !"argv", !DIExpression(), debug-location !17; pr35318.c:1:27 line no:1
%20:gr64 = MOV64rm %stack.2.argv.addr, 1, $noreg, 0, $noreg, debug-location !18 :: (load 8 from %ir.argv.addr); pr35318.c:2:10
%19:gr64 = MOV64rm %20:gr64, 1, $noreg, 0, $noreg, debug-location !18 :: (load 8 from %ir.arrayidx); pr35318.c:2:10
ADJCALLSTACKDOWN64 0, 0, 0, implicit-def $rsp, implicit-def $eflags, implicit-def $ssp, implicit $rsp, implicit $ssp, debug-location !19; pr35318.c:2:3
$rdi = COPY %19:gr64, debug-location !19; pr35318.c:2:3
$al = MOV8ri 0, debug-location !19; pr35318.c:2:3
CALL64pcrel32 @printf, <regmask $bh $bl $bp $bph $bpl $bx $ebp $ebx $hbp $hbx $rbp $rbx $r12 $r13 $r14 $r15 $r12b $r13b $r14b $r15b $r12bh $r13bh $r14bh $r15bh $r12d $r13d $r14d $r15d $r12w $r13w $r14w $r15w $r12wh and 3 more...>, implicit $rsp, implicit $ssp, implicit $al, implicit $rdi, implicit-def $eax, debug-location !19; pr35318.c:2:3
ADJCALLSTACKUP64 0, 0, implicit-def $rsp, implicit-def $eflags, implicit-def $ssp, implicit $rsp, implicit $ssp, debug-location !19; pr35318.c:2:3
%17:gr32 = COPY $eax, debug-location !19; pr35318.c:2:3
%15:gr32 = MOV32rm %stack.1.argc.addr, 1, $noreg, 0, $noreg, debug-location !22 :: (load 4 from %ir.argc.addr); pr35318.c:3:11
MOV32mr %stack.3.i, 1, $noreg, 0, $noreg, killed %15:gr32, debug-location !21 :: (store 4 into %ir.i); pr35318.c:3:7
%13:gr32 = MOV32rm %stack.3.i, 1, $noreg, 0, $noreg, debug-location !23 :: (load 4 from %ir.i); pr35318.c:4:3
%12:gr32 = ADD32ri8 killed %13:gr32(tied-def 0), 1, implicit-def $eflags, debug-location !23; pr35318.c:4:3
MOV32mr %stack.3.i, 1, $noreg, 0, $noreg, killed %12:gr32, debug-location !23 :: (store 4 into %ir.i); pr35318.c:4:3
%9:gr32 = MOV32rm %stack.3.i, 1, $noreg, 0, $noreg, debug-location !24 :: (load 4 from %ir.i); pr35318.c:5:3
%8:gr32 = ADD32ri8 killed %9:gr32(tied-def 0), 1, implicit-def $eflags, debug-location !24; pr35318.c:5:3
MOV32mr %stack.3.i, 1, $noreg, 0, $noreg, killed %8:gr32, debug-location !24 :: (store 4 into %ir.i); pr35318.c:5:3
%5:gr32 = MOV32rm %stack.3.i, 1, $noreg, 0, $noreg, debug-location !25 :: (load 4 from %ir.i); pr35318.c:6:10
$eax = COPY %5:gr32, debug-location !26; pr35318.c:6:3
-> DBG_VALUE %stack.3.i, 0, !"i", !DIExpression(), debug-location !21;
pr35318.c:3:7 line no:3
RETQ implicit $eax, debug-location !26; pr35318.c:6:3
I don't know much about this code, but a quick troubleshooting session shows
that the DbgValue for i is treated as trailing, which is why it is emitted
before the terminator:
// Add trailing DbgValue's before the terminator. FIXME: May want to add
// some of them before one or more conditional branches?
SmallVector<MachineInstr*, 8> DbgMIs;
for (; DI != DE; ++DI) {
if ((*DI)->isInvalidated())
continue;
assert((*DI)->getOrder() >= LastOrder &&
"emitting DBG_VALUE out of order");
if (MachineInstr *DbgMI = Emitter.EmitDbgValue(*DI, VRBaseMap))
DbgMIs.push_back(DbgMI);
}