diff options
| author | Erik Eckstein <eeckstein@apple.com> | 2015-08-13 15:36:11 +0000 |
|---|---|---|
| committer | Erik Eckstein <eeckstein@apple.com> | 2015-08-13 15:36:11 +0000 |
| commit | 11fc8175d9abba0dbba643c0ea81400afba017dc (patch) | |
| tree | 0c093b773f2a14e766c40fed0ab145d72a4b6f89 /llvm/test/Transforms/DeadStoreElimination | |
| parent | ef1ac01c2ebac3dec3d4288b323576cc0d4139ae (diff) | |
| download | bcm5719-llvm-11fc8175d9abba0dbba643c0ea81400afba017dc.tar.gz bcm5719-llvm-11fc8175d9abba0dbba643c0ea81400afba017dc.zip | |
[DeadStoreElimination] remove a redundant store even if the load is in a different block.
DeadStoreElimination does eliminate a store if it stores a value which was loaded from the same memory location.
So far this worked only if the store is in the same block as the load.
Now we can also handle stores which are in a different block than the load.
Example:
define i32 @test(i1, i32*) {
entry:
%l2 = load i32, i32* %1, align 4
br i1 %0, label %bb1, label %bb2
bb1:
br label %bb3
bb2:
; This store is redundant
store i32 %l2, i32* %1, align 4
br label %bb3
bb3:
ret i32 0
}
Differential Revision: http://reviews.llvm.org/D11854
llvm-svn: 244901
Diffstat (limited to 'llvm/test/Transforms/DeadStoreElimination')
| -rw-r--r-- | llvm/test/Transforms/DeadStoreElimination/simple.ll | 147 |
1 files changed, 147 insertions, 0 deletions
diff --git a/llvm/test/Transforms/DeadStoreElimination/simple.ll b/llvm/test/Transforms/DeadStoreElimination/simple.ll index 2ffe0539098..4f6221db245 100644 --- a/llvm/test/Transforms/DeadStoreElimination/simple.ll +++ b/llvm/test/Transforms/DeadStoreElimination/simple.ll @@ -350,3 +350,150 @@ define i8* @test25(i8* %p) nounwind { store i8 %tmp, i8* %p.4, align 1 ret i8* %q } + +; Remove redundant store if loaded value is in another block. +; CHECK-LABEL: @test26( +; CHECK-NOT: store +; CHECK: ret +define i32 @test26(i1 %c, i32* %p) { +entry: + %v = load i32, i32* %p, align 4 + br i1 %c, label %bb1, label %bb2 +bb1: + br label %bb3 +bb2: + store i32 %v, i32* %p, align 4 + br label %bb3 +bb3: + ret i32 0 +} + +; Remove redundant store if loaded value is in another block. +; CHECK-LABEL: @test27( +; CHECK-NOT: store +; CHECK: ret +define i32 @test27(i1 %c, i32* %p) { +entry: + %v = load i32, i32* %p, align 4 + br i1 %c, label %bb1, label %bb2 +bb1: + br label %bb3 +bb2: + br label %bb3 +bb3: + store i32 %v, i32* %p, align 4 + ret i32 0 +} + +; Don't remove redundant store because of may-aliased store. +; CHECK-LABEL: @test28( +; CHECK: bb3: +; CHECK-NEXT: store i32 %v +define i32 @test28(i1 %c, i32* %p, i32* %p2, i32 %i) { +entry: + %v = load i32, i32* %p, align 4 + + ; Might overwrite value at %p + store i32 %i, i32* %p2, align 4 + br i1 %c, label %bb1, label %bb2 +bb1: + br label %bb3 +bb2: + br label %bb3 +bb3: + store i32 %v, i32* %p, align 4 + ret i32 0 +} + +; Don't remove redundant store because of may-aliased store. +; CHECK-LABEL: @test29( +; CHECK: bb3: +; CHECK-NEXT: store i32 %v +define i32 @test29(i1 %c, i32* %p, i32* %p2, i32 %i) { +entry: + %v = load i32, i32* %p, align 4 + br i1 %c, label %bb1, label %bb2 +bb1: + br label %bb3 +bb2: + ; Might overwrite value at %p + store i32 %i, i32* %p2, align 4 + br label %bb3 +bb3: + store i32 %v, i32* %p, align 4 + ret i32 0 +} + +declare void @unknown_func() + +; Don't remove redundant store because of unknown call. +; CHECK-LABEL: @test30( +; CHECK: bb3: +; CHECK-NEXT: store i32 %v +define i32 @test30(i1 %c, i32* %p, i32 %i) { +entry: + %v = load i32, i32* %p, align 4 + br i1 %c, label %bb1, label %bb2 +bb1: + br label %bb3 +bb2: + ; Might overwrite value at %p + call void @unknown_func() + br label %bb3 +bb3: + store i32 %v, i32* %p, align 4 + ret i32 0 +} + +; Remove redundant store if loaded value is in another block inside a loop. +; CHECK-LABEL: @test31( +; CHECK-NOT: store +; CHECK: ret +define i32 @test31(i1 %c, i32* %p, i32 %i) { +entry: + %v = load i32, i32* %p, align 4 + br label %bb1 +bb1: + store i32 %v, i32* %p, align 4 + br i1 undef, label %bb1, label %bb2 +bb2: + ret i32 0 +} + +; Don't remove redundant store in a loop with a may-alias store. +; CHECK-LABEL: @test32( +; CHECK: bb1: +; CHECK-NEXT: store i32 %v +; CHECK-NEXT: call void @unknown_func +define i32 @test32(i1 %c, i32* %p, i32 %i) { +entry: + %v = load i32, i32* %p, align 4 + br label %bb1 +bb1: + store i32 %v, i32* %p, align 4 + ; Might read and overwrite value at %p + call void @unknown_func() + br i1 undef, label %bb1, label %bb2 +bb2: + ret i32 0 +} + +; Remove redundant store, which is in the lame loop as the load. +; CHECK-LABEL: @test33( +; CHECK-NOT: store +; CHECK: ret +define i32 @test33(i1 %c, i32* %p, i32 %i) { +entry: + br label %bb1 +bb1: + %v = load i32, i32* %p, align 4 + br label %bb2 +bb2: + store i32 %v, i32* %p, align 4 + ; Might read and overwrite value at %p, but doesn't matter. + call void @unknown_func() + br i1 undef, label %bb1, label %bb3 +bb3: + ret i32 0 +} + |

