summaryrefslogtreecommitdiffstats
path: root/llvm/unittests/Analysis
diff options
context:
space:
mode:
authorGeorge Burgess IV <george.burgess.iv@gmail.com>2018-08-10 05:14:43 +0000
committerGeorge Burgess IV <george.burgess.iv@gmail.com>2018-08-10 05:14:43 +0000
commitff08c80efcd5f69b9ac9881699b45fb8aa10f15e (patch)
tree8994606ea6ce9320ea9aab94e2039ba82ef933f1 /llvm/unittests/Analysis
parent909889b2cbd55fbc4a5bb7f155bd286a82da1fef (diff)
downloadbcm5719-llvm-ff08c80efcd5f69b9ac9881699b45fb8aa10f15e.tar.gz
bcm5719-llvm-ff08c80efcd5f69b9ac9881699b45fb8aa10f15e.zip
[MemorySSA] "Fix" lifetime intrinsic handling
MemorySSA currently creates MemoryAccesses for lifetime intrinsics, and sometimes treats them as clobbers. This may/may not be the best way forward, but while we're doing it, we should consider MayAlias/PartialAlias to be clobbers. The ideal fix here is probably to remove all of this reasoning about lifetimes from MemorySSA + put it into the passes that need to care. But that's a wayyy broader fix that needs some consensus, and we have miscompiles + a release branch today, and this should solve the miscompiles just as well. differential revision is D43269. Landing without an explicit LGTM (and without using the special please-autoclose-this syntax) so we can still use that revision as a place to decide what the right fix here is. llvm-svn: 339411
Diffstat (limited to 'llvm/unittests/Analysis')
-rw-r--r--llvm/unittests/Analysis/MemorySSA.cpp66
1 files changed, 66 insertions, 0 deletions
diff --git a/llvm/unittests/Analysis/MemorySSA.cpp b/llvm/unittests/Analysis/MemorySSA.cpp
index 1a1675faca1..0eb543b5477 100644
--- a/llvm/unittests/Analysis/MemorySSA.cpp
+++ b/llvm/unittests/Analysis/MemorySSA.cpp
@@ -1199,3 +1199,69 @@ TEST_F(MemorySSATest, TestStoreMayAlias) {
++I;
}
}
+
+TEST_F(MemorySSATest, LifetimeMarkersAreClobbers) {
+ // Example code:
+ // define void @a(i8* %foo) {
+ // %bar = getelementptr i8, i8* %foo, i64 1
+ // store i8 0, i8* %foo
+ // store i8 0, i8* %bar
+ // call void @llvm.lifetime.end.p0i8(i64 8, i32* %p)
+ // call void @llvm.lifetime.start.p0i8(i64 8, i32* %p)
+ // store i8 0, i8* %foo
+ // store i8 0, i8* %bar
+ // ret void
+ // }
+ //
+ // Patterns like this are possible after inlining; the stores to %foo and %bar
+ // should both be clobbered by the lifetime.start call if they're dominated by
+ // it.
+
+ IRBuilder<> B(C);
+ F = Function::Create(
+ FunctionType::get(B.getVoidTy(), {B.getInt8PtrTy()}, false),
+ GlobalValue::ExternalLinkage, "F", &M);
+
+ // Make blocks
+ BasicBlock *Entry = BasicBlock::Create(C, "entry", F);
+
+ B.SetInsertPoint(Entry);
+ Value *Foo = &*F->arg_begin();
+
+ Value *Bar = B.CreateGEP(Foo, B.getInt64(1), "bar");
+
+ B.CreateStore(B.getInt8(0), Foo);
+ B.CreateStore(B.getInt8(0), Bar);
+
+ auto GetLifetimeIntrinsic = [&](Intrinsic::ID ID) {
+ return Intrinsic::getDeclaration(&M, ID, {Foo->getType()});
+ };
+
+ B.CreateCall(GetLifetimeIntrinsic(Intrinsic::lifetime_end),
+ {B.getInt64(2), Foo});
+ Instruction *LifetimeStart = B.CreateCall(
+ GetLifetimeIntrinsic(Intrinsic::lifetime_start), {B.getInt64(2), Foo});
+
+ Instruction *FooStore = B.CreateStore(B.getInt8(0), Foo);
+ Instruction *BarStore = B.CreateStore(B.getInt8(0), Bar);
+
+ setupAnalyses();
+ MemorySSA &MSSA = *Analyses->MSSA;
+
+ MemoryAccess *LifetimeStartAccess = MSSA.getMemoryAccess(LifetimeStart);
+ ASSERT_NE(LifetimeStartAccess, nullptr);
+
+ MemoryAccess *FooAccess = MSSA.getMemoryAccess(FooStore);
+ ASSERT_NE(FooAccess, nullptr);
+
+ MemoryAccess *BarAccess = MSSA.getMemoryAccess(BarStore);
+ ASSERT_NE(BarAccess, nullptr);
+
+ MemoryAccess *FooClobber =
+ MSSA.getWalker()->getClobberingMemoryAccess(FooAccess);
+ EXPECT_EQ(FooClobber, LifetimeStartAccess);
+
+ MemoryAccess *BarClobber =
+ MSSA.getWalker()->getClobberingMemoryAccess(BarAccess);
+ EXPECT_EQ(BarClobber, LifetimeStartAccess);
+}
OpenPOWER on IntegriCloud