1 # RUN: llc %s -o - -run-pass=simple-register-coalescing | FileCheck %s
2 # PR40010: DBG_VALUEs do not contribute to the liveness of virtual registers,
3 # and the register coalescer would merge new live values on top of DBG_VALUEs,
4 # leading to them presenting new (wrong) values to the debugger. Test that
5 # when out of liveness, coalescing will mark DBG_VALUEs in non-live locations
8 ; ModuleID = './test.ll'
9 source_filename = "./test.ll"
10 target datalayout = "e-m:e-i64:64-f80:128-n8:16:32:64-S128"
12 ; Function Attrs: nounwind readnone speculatable
13 declare void @llvm.dbg.value(metadata, metadata, metadata) #0
15 ; Original IR source here:
16 define i32 @test(i32* %pin) {
20 start.test1: ; preds = %start, %entry
21 %foo = phi i32 [ 0, %entry ], [ %bar, %start.test1 ]
22 %baz = load i32, i32* %pin, align 1
23 %qux = xor i32 %baz, 1234
24 %bar = add i32 %qux, %foo
25 call void @llvm.dbg.value(metadata i32 %foo, metadata !3, metadata !DIExpression()), !dbg !5
26 %cmp = icmp ugt i32 %bar, 1000000
27 br i1 %cmp, label %leave, label %start.test1
29 leave: ; preds = %start
33 ; Stubs to appease the MIR parser
34 define i32 @test2(i32* %pin) {
43 define i32 @test3(i32* %pin) {
52 define i32 @test4(i32* %pin) {
61 ; Function Attrs: nounwind
62 declare void @llvm.stackprotector(i8*, i8**) #1
64 attributes #0 = { nounwind readnone speculatable }
65 attributes #1 = { nounwind }
67 !llvm.module.flags = !{!0}
70 !0 = !{i32 2, !"Debug Info Version", i32 3}
71 !1 = distinct !DICompileUnit(language: DW_LANG_C_plus_plus, file: !2, producer: "beards", isOptimized: true, runtimeVersion: 4, emissionKind: FullDebug)
72 !2 = !DIFile(filename: "bees.cpp", directory: "")
73 !3 = !DILocalVariable(name: "bees", scope: !4)
74 !4 = distinct !DISubprogram(name: "nope", scope: !1, file: !2, line: 1, spFlags: DISPFlagDefinition, unit: !1)
75 !5 = !DILocation(line: 0, scope: !4)
80 tracksRegLiveness: true
83 successors: %bb.1(0x80000000)
86 %2:gr64 = COPY killed $rdi
87 %3:gr32 = MOV32r0 implicit-def dead $eflags
88 %4:gr32 = MOV32ri 1234
89 %7:gr32 = COPY killed %3
92 successors: %bb.2(0x04000000), %bb.1(0x7c000000)
94 ; CHECK-LABEL: name: test
96 ; We currently expect %1 and %0 to merge into %7
98 ; CHECK: %[[REG1:[0-9]+]]:gr32 = MOV32rm
99 ; CHECK-NEXT: %[[REG2:[0-9]+]]:gr32 = XOR32rr %[[REG1]]
100 ; CHECK-NEXT: %[[REG3:[0-9]+]]:gr32 = ADD32rr %[[REG3]], %[[REG2]]
101 ; CHECK-NEXT: DBG_VALUE $noreg
103 %0:gr32 = COPY killed %7
104 %8:gr32 = MOV32rm %2, 1, $noreg, 0, $noreg :: (load 4 from %ir.pin, align 1)
105 %5:gr32 = COPY killed %8
106 %5:gr32 = XOR32rr %5, %4, implicit-def dead $eflags
107 %1:gr32 = COPY killed %0
108 %1:gr32 = ADD32rr %1, killed %5, implicit-def dead $eflags
109 DBG_VALUE %0, $noreg, !3, !DIExpression(), debug-location !5
110 CMP32ri %1, 1000001, implicit-def $eflags
112 JCC_1 %bb.1, 2, implicit killed $eflags
116 $eax = COPY killed %1
122 tracksRegLiveness: true
125 successors: %bb.1(0x80000000)
128 %2:gr64 = COPY killed $rdi
129 %3:gr32 = MOV32r0 implicit-def dead $eflags
130 %4:gr32 = MOV32ri 1234
131 %7:gr32 = COPY killed %3
134 successors: %bb.2(0x04000000), %bb.1(0x7c000000)
136 ; CHECK-LABEL: name: test2
138 ; %0 should be merged into %7, but as %0 is live at this location the
139 ; DBG_VALUE should be preserved and point at the operand of ADD32rr.
141 ; CHECK: %[[REG11:[0-9]+]]:gr32 = MOV32rm
142 ; CHECK-NEXT: %[[REG12:[0-9]+]]:gr32 = XOR32rr %[[REG11]]
143 ; CHECK-NEXT: DBG_VALUE %[[REG13:[0-9]+]]
144 ; CHECK-NEXT: %[[REG13]]:gr32 = ADD32rr %[[REG13]], %[[REG12]]
146 %0:gr32 = COPY killed %7
147 %8:gr32 = MOV32rm %2, 1, $noreg, 0, $noreg :: (load 4 from %ir.pin, align 1)
148 %5:gr32 = COPY killed %8
149 %5:gr32 = XOR32rr %5, %4, implicit-def dead $eflags
150 DBG_VALUE %0, $noreg, !3, !DIExpression(), debug-location !5
151 %1:gr32 = COPY killed %0
152 %1:gr32 = ADD32rr %1, killed %5, implicit-def dead $eflags
153 CMP32ri %1, 1000001, implicit-def $eflags
155 JCC_1 %bb.1, 2, implicit killed $eflags
159 $eax = COPY killed %1
165 tracksRegLiveness: true
168 successors: %bb.1(0x80000000)
171 %2:gr64 = COPY killed $rdi
172 %3:gr32 = MOV32r0 implicit-def dead $eflags
173 %4:gr32 = MOV32ri 1234
174 %7:gr32 = COPY killed %3
177 successors: %bb.2(0x04000000), %bb.1(0x7c000000)
179 ; CHECK-LABEL: name: test3
181 ; This is a use-before-def, merging new registers into %0 could unsoundly
182 ; make it live again, on merge mark it undef.
184 ; CHECK: DBG_VALUE $noreg
186 DBG_VALUE %0, $noreg, !3, !DIExpression(), debug-location !5
187 %0:gr32 = COPY killed %7
188 %8:gr32 = MOV32rm %2, 1, $noreg, 0, $noreg :: (load 4 from %ir.pin, align 1)
189 %5:gr32 = COPY killed %8
190 %5:gr32 = XOR32rr %5, %4, implicit-def dead $eflags
191 %1:gr32 = COPY killed %0
192 %1:gr32 = ADD32rr %1, killed %5, implicit-def dead $eflags
193 CMP32ri %1, 1000001, implicit-def $eflags
195 JCC_1 %bb.1, 2, implicit killed $eflags
199 $eax = COPY killed %1
205 tracksRegLiveness: true
208 successors: %bb.1(0x80000000)
211 %2:gr64 = COPY killed $rdi
212 %3:gr32 = MOV32r0 implicit-def dead $eflags
213 %4:gr32 = MOV32ri 1234
214 %7:gr32 = COPY killed %3
217 successors: %bb.2(0x04000000), %bb.1(0x7c000000)
219 ; CHECK-LABEL: name: test4
221 ; Using a dead register, even if we coalesce it to the right value, should
222 ; be marked undef. The coalescer can't prove it's correct without
223 ; considering control flow in the general case.
225 ; CHECK: DBG_VALUE $noreg
227 %0:gr32 = COPY killed %7
228 DBG_VALUE %7, $noreg, !3, !DIExpression(), debug-location !5
229 %8:gr32 = MOV32rm %2, 1, $noreg, 0, $noreg :: (load 4 from %ir.pin, align 1)
230 %5:gr32 = COPY killed %8
231 %5:gr32 = XOR32rr %5, %4, implicit-def dead $eflags
232 %1:gr32 = COPY killed %0
233 %1:gr32 = ADD32rr %1, killed %5, implicit-def dead $eflags
234 CMP32ri %1, 1000001, implicit-def $eflags
236 JCC_1 %bb.1, 2, implicit killed $eflags
240 $eax = COPY killed %1