diff options
author | Nick Lewycky <nicholas@mxc.ca> | 2009-11-28 21:27:49 +0000 |
---|---|---|
committer | Nick Lewycky <nicholas@mxc.ca> | 2009-11-28 21:27:49 +0000 |
commit | d801c10de6cd1760f0994452c0e78156782d9fca (patch) | |
tree | 61376d8c37a73473ed3f5ee5124316ffe845870a /lib/Analysis/MemoryDependenceAnalysis.cpp | |
parent | 0c264b16b0e8a373888d1a5cfeb90af4fda3cd14 (diff) |
Teach memdep to look for memory use intrinsics during dependency queries. Fixes
PR5574.
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@90045 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'lib/Analysis/MemoryDependenceAnalysis.cpp')
-rw-r--r-- | lib/Analysis/MemoryDependenceAnalysis.cpp | 39 |
1 files changed, 30 insertions, 9 deletions
diff --git a/lib/Analysis/MemoryDependenceAnalysis.cpp b/lib/Analysis/MemoryDependenceAnalysis.cpp index 4cbb62790d..eec6d6bb11 100644 --- a/lib/Analysis/MemoryDependenceAnalysis.cpp +++ b/lib/Analysis/MemoryDependenceAnalysis.cpp @@ -201,7 +201,7 @@ getPointerDependencyFrom(Value *MemPtr, uint64_t MemSize, bool isLoad, // If we reach a lifetime begin or end marker, then the query ends here // because the value is undefined. } else if (II->getIntrinsicID() == Intrinsic::lifetime_start || - II->getIntrinsicID() == Intrinsic::lifetime_end) { + II->getIntrinsicID() == Intrinsic::lifetime_end) { uint64_t invariantSize = ~0ULL; if (ConstantInt *CI = dyn_cast<ConstantInt>(II->getOperand(1))) invariantSize = CI->getZExtValue(); @@ -369,20 +369,41 @@ MemDepResult MemoryDependenceAnalysis::getDependency(Instruction *QueryInst) { // calls to free() erase the entire structure, not just a field. MemSize = ~0UL; } else if (isa<CallInst>(QueryInst) || isa<InvokeInst>(QueryInst)) { - CallSite QueryCS = CallSite::get(QueryInst); - bool isReadOnly = AA->onlyReadsMemory(QueryCS); - LocalCache = getCallSiteDependencyFrom(QueryCS, isReadOnly, ScanPos, - QueryParent); + int IntrinsicID = 0; // Intrinsic IDs start at 1. + if (IntrinsicInst *II = dyn_cast<IntrinsicInst>(QueryInst)) + IntrinsicID = II->getIntrinsicID(); + + switch (IntrinsicID) { + case Intrinsic::lifetime_start: + case Intrinsic::lifetime_end: + case Intrinsic::invariant_start: + MemPtr = QueryInst->getOperand(2); + MemSize = cast<ConstantInt>(QueryInst->getOperand(1))->getZExtValue(); + break; + case Intrinsic::invariant_end: + MemPtr = QueryInst->getOperand(3); + MemSize = cast<ConstantInt>(QueryInst->getOperand(2))->getZExtValue(); + break; + default: + CallSite QueryCS = CallSite::get(QueryInst); + bool isReadOnly = AA->onlyReadsMemory(QueryCS); + LocalCache = getCallSiteDependencyFrom(QueryCS, isReadOnly, ScanPos, + QueryParent); + } } else { // Non-memory instruction. LocalCache = MemDepResult::getClobber(--BasicBlock::iterator(ScanPos)); } // If we need to do a pointer scan, make it happen. - if (MemPtr) - LocalCache = getPointerDependencyFrom(MemPtr, MemSize, - isa<LoadInst>(QueryInst), - ScanPos, QueryParent); + if (MemPtr) { + bool isLoad = !QueryInst->mayWriteToMemory(); + if (IntrinsicInst *II = dyn_cast<MemoryUseIntrinsic>(QueryInst)) { + isLoad |= II->getIntrinsicID() == Intrinsic::lifetime_end; + } + LocalCache = getPointerDependencyFrom(MemPtr, MemSize, isLoad, ScanPos, + QueryParent); + } // Remember the result! if (Instruction *I = LocalCache.getInst()) |