|
4 | 4 | ; RUN: opt -S -passes='early-cse<memssa>' --enable-knowledge-retention < %s | FileCheck %s --check-prefixes=CHECK,USE_ASSUME
|
5 | 5 |
|
6 | 6 | declare void @clobber_and_use(i32)
|
| 7 | +declare void @clobber_and_combine(i32, i32) |
7 | 8 |
|
8 | 9 | define void @f_0(ptr %ptr) {
|
9 | 10 | ; NO_ASSUME-LABEL: @f_0(
|
@@ -164,6 +165,32 @@ define void @test_dse1(ptr %p) {
|
164 | 165 | ret void
|
165 | 166 | }
|
166 | 167 |
|
| 168 | +; Extending @test_dse1, the call can't change the contents of p.invariant. |
| 169 | +; Moreover, the contents of p.invariant cannot change from the store to p. |
| 170 | +define void @test_dse2(ptr noalias %p, ptr noalias %p.invariant) { |
| 171 | +; NO_ASSUME-LABEL: @test_dse2( |
| 172 | +; NO_ASSUME-NEXT: [[V:%.*]] = load i32, ptr [[P:%.*]], align 4 |
| 173 | +; NO_ASSUME-NEXT: [[V_INVARIANT:%.*]] = load i32, ptr [[P_INVARIANT:%.*]], align 4, !invariant.load !0 |
| 174 | +; NO_ASSUME-NEXT: [[V_COMB:%.*]] = call i32 @clobber_and_combine(i32 [[V]], i32 [[V_INVARIANT]]) |
| 175 | +; NO_ASSUME-NEXT: store i32 [[V_COMB]], ptr [[P]], align 4 |
| 176 | +; NO_ASSUME-NEXT: ret void |
| 177 | +; |
| 178 | +; USE_ASSUME-LABEL: @test_dse2( |
| 179 | +; USE_ASSUME-NEXT: [[V:%.*]] = load i32, ptr [[P:%.*]], align 4 |
| 180 | +; USE_ASSUME-NEXT: [[V_INVARIANT:%.*]] = load i32, ptr [[P_INVARIANT:%.*]], align 4, !invariant.load !0 |
| 181 | +; USE_ASSUME-NEXT: [[V_COMB:%.*]] = call i32 @clobber_and_combine(i32 [[V]], i32 [[V_INVARIANT]]) |
| 182 | +; USE_ASSUME-NEXT: store i32 [[V_COMB]], ptr [[P]], align 4 |
| 183 | +; USE_ASSUME-NEXT: call void @llvm.assume(i1 true) [ "dereferenceable"(ptr [[P_INVARIANT]], i64 4), "nonnull"(ptr [[P_INVARIANT]]), "align"(ptr [[P_INVARIANT]], i64 4) ] |
| 184 | +; USE_ASSUME-NEXT: ret void |
| 185 | +; |
| 186 | + %v = load i32, ptr %p |
| 187 | + %v.invariant = load i32, ptr %p.invariant, !invariant.load !{} |
| 188 | + %v.comb = call i32 @clobber_and_combine(i32 %v, i32 %v.invariant) |
| 189 | + store i32 %v.comb, ptr %p |
| 190 | + store i32 %v.invariant, ptr %p.invariant |
| 191 | + ret void |
| 192 | +} |
| 193 | + |
167 | 194 | ; By assumption, v1 must equal v2 (TODO)
|
168 | 195 | define void @test_false_negative_dse2(ptr %p, i32 %v2) {
|
169 | 196 | ; CHECK-LABEL: @test_false_negative_dse2(
|
|
0 commit comments