diff options
Diffstat (limited to 'lib/Analysis/MemoryLocation.cpp')
-rw-r--r-- | lib/Analysis/MemoryLocation.cpp | 96 |
1 files changed, 67 insertions, 29 deletions
diff --git a/lib/Analysis/MemoryLocation.cpp b/lib/Analysis/MemoryLocation.cpp index 55924db284ec..27e8d72b8e89 100644 --- a/lib/Analysis/MemoryLocation.cpp +++ b/lib/Analysis/MemoryLocation.cpp @@ -18,13 +18,28 @@ #include "llvm/IR/Type.h" using namespace llvm; +void LocationSize::print(raw_ostream &OS) const { + OS << "LocationSize::"; + if (*this == unknown()) + OS << "unknown"; + else if (*this == mapEmpty()) + OS << "mapEmpty"; + else if (*this == mapTombstone()) + OS << "mapTombstone"; + else if (isPrecise()) + OS << "precise(" << getValue() << ')'; + else + OS << "upperBound(" << getValue() << ')'; +} + MemoryLocation MemoryLocation::get(const LoadInst *LI) { AAMDNodes AATags; LI->getAAMetadata(AATags); const auto &DL = LI->getModule()->getDataLayout(); - return MemoryLocation(LI->getPointerOperand(), - DL.getTypeStoreSize(LI->getType()), AATags); + return MemoryLocation( + LI->getPointerOperand(), + LocationSize::precise(DL.getTypeStoreSize(LI->getType())), AATags); } MemoryLocation MemoryLocation::get(const StoreInst *SI) { @@ -33,7 +48,8 @@ MemoryLocation MemoryLocation::get(const StoreInst *SI) { const auto &DL = SI->getModule()->getDataLayout(); return MemoryLocation(SI->getPointerOperand(), - DL.getTypeStoreSize(SI->getValueOperand()->getType()), + LocationSize::precise(DL.getTypeStoreSize( + SI->getValueOperand()->getType())), AATags); } @@ -41,7 +57,8 @@ MemoryLocation MemoryLocation::get(const VAArgInst *VI) { AAMDNodes AATags; VI->getAAMetadata(AATags); - return MemoryLocation(VI->getPointerOperand(), UnknownSize, AATags); + return MemoryLocation(VI->getPointerOperand(), LocationSize::unknown(), + AATags); } MemoryLocation MemoryLocation::get(const AtomicCmpXchgInst *CXI) { @@ -49,9 +66,10 @@ MemoryLocation MemoryLocation::get(const AtomicCmpXchgInst *CXI) { CXI->getAAMetadata(AATags); const auto &DL = CXI->getModule()->getDataLayout(); - return MemoryLocation( - CXI->getPointerOperand(), - DL.getTypeStoreSize(CXI->getCompareOperand()->getType()), AATags); + return MemoryLocation(CXI->getPointerOperand(), + LocationSize::precise(DL.getTypeStoreSize( + CXI->getCompareOperand()->getType())), + AATags); } MemoryLocation MemoryLocation::get(const AtomicRMWInst *RMWI) { @@ -60,7 +78,8 @@ MemoryLocation MemoryLocation::get(const AtomicRMWInst *RMWI) { const auto &DL = RMWI->getModule()->getDataLayout(); return MemoryLocation(RMWI->getPointerOperand(), - DL.getTypeStoreSize(RMWI->getValOperand()->getType()), + LocationSize::precise(DL.getTypeStoreSize( + RMWI->getValOperand()->getType())), AATags); } @@ -73,9 +92,9 @@ MemoryLocation MemoryLocation::getForSource(const AtomicMemTransferInst *MTI) { } MemoryLocation MemoryLocation::getForSource(const AnyMemTransferInst *MTI) { - uint64_t Size = UnknownSize; + auto Size = LocationSize::unknown(); if (ConstantInt *C = dyn_cast<ConstantInt>(MTI->getLength())) - Size = C->getValue().getZExtValue(); + Size = LocationSize::precise(C->getValue().getZExtValue()); // memcpy/memmove can have AA tags. For memcpy, they apply // to both the source and the destination. @@ -94,9 +113,9 @@ MemoryLocation MemoryLocation::getForDest(const AtomicMemIntrinsic *MI) { } MemoryLocation MemoryLocation::getForDest(const AnyMemIntrinsic *MI) { - uint64_t Size = UnknownSize; + auto Size = LocationSize::unknown(); if (ConstantInt *C = dyn_cast<ConstantInt>(MI->getLength())) - Size = C->getValue().getZExtValue(); + Size = LocationSize::precise(C->getValue().getZExtValue()); // memcpy/memmove can have AA tags. For memcpy, they apply // to both the source and the destination. @@ -106,15 +125,15 @@ MemoryLocation MemoryLocation::getForDest(const AnyMemIntrinsic *MI) { return MemoryLocation(MI->getRawDest(), Size, AATags); } -MemoryLocation MemoryLocation::getForArgument(ImmutableCallSite CS, +MemoryLocation MemoryLocation::getForArgument(const CallBase *Call, unsigned ArgIdx, - const TargetLibraryInfo &TLI) { + const TargetLibraryInfo *TLI) { AAMDNodes AATags; - CS->getAAMetadata(AATags); - const Value *Arg = CS.getArgument(ArgIdx); + Call->getAAMetadata(AATags); + const Value *Arg = Call->getArgOperand(ArgIdx); // We may be able to produce an exact size for known intrinsics. - if (const IntrinsicInst *II = dyn_cast<IntrinsicInst>(CS.getInstruction())) { + if (const IntrinsicInst *II = dyn_cast<IntrinsicInst>(Call)) { const DataLayout &DL = II->getModule()->getDataLayout(); switch (II->getIntrinsicID()) { @@ -126,7 +145,8 @@ MemoryLocation MemoryLocation::getForArgument(ImmutableCallSite CS, assert((ArgIdx == 0 || ArgIdx == 1) && "Invalid argument index for memory intrinsic"); if (ConstantInt *LenCI = dyn_cast<ConstantInt>(II->getArgOperand(2))) - return MemoryLocation(Arg, LenCI->getZExtValue(), AATags); + return MemoryLocation(Arg, LocationSize::precise(LenCI->getZExtValue()), + AATags); break; case Intrinsic::lifetime_start: @@ -134,23 +154,37 @@ MemoryLocation MemoryLocation::getForArgument(ImmutableCallSite CS, case Intrinsic::invariant_start: assert(ArgIdx == 1 && "Invalid argument index"); return MemoryLocation( - Arg, cast<ConstantInt>(II->getArgOperand(0))->getZExtValue(), AATags); + Arg, + LocationSize::precise( + cast<ConstantInt>(II->getArgOperand(0))->getZExtValue()), + AATags); case Intrinsic::invariant_end: + // The first argument to an invariant.end is a "descriptor" type (e.g. a + // pointer to a empty struct) which is never actually dereferenced. + if (ArgIdx == 0) + return MemoryLocation(Arg, LocationSize::precise(0), AATags); assert(ArgIdx == 2 && "Invalid argument index"); return MemoryLocation( - Arg, cast<ConstantInt>(II->getArgOperand(1))->getZExtValue(), AATags); + Arg, + LocationSize::precise( + cast<ConstantInt>(II->getArgOperand(1))->getZExtValue()), + AATags); case Intrinsic::arm_neon_vld1: assert(ArgIdx == 0 && "Invalid argument index"); // LLVM's vld1 and vst1 intrinsics currently only support a single // vector register. - return MemoryLocation(Arg, DL.getTypeStoreSize(II->getType()), AATags); + return MemoryLocation( + Arg, LocationSize::precise(DL.getTypeStoreSize(II->getType())), + AATags); case Intrinsic::arm_neon_vst1: assert(ArgIdx == 0 && "Invalid argument index"); - return MemoryLocation( - Arg, DL.getTypeStoreSize(II->getArgOperand(1)->getType()), AATags); + return MemoryLocation(Arg, + LocationSize::precise(DL.getTypeStoreSize( + II->getArgOperand(1)->getType())), + AATags); } } @@ -159,16 +193,20 @@ MemoryLocation MemoryLocation::getForArgument(ImmutableCallSite CS, // LoopIdiomRecognizer likes to turn loops into calls to memset_pattern16 // whenever possible. LibFunc F; - if (CS.getCalledFunction() && TLI.getLibFunc(*CS.getCalledFunction(), F) && - F == LibFunc_memset_pattern16 && TLI.has(F)) { + if (TLI && Call->getCalledFunction() && + TLI->getLibFunc(*Call->getCalledFunction(), F) && + F == LibFunc_memset_pattern16 && TLI->has(F)) { assert((ArgIdx == 0 || ArgIdx == 1) && "Invalid argument index for memset_pattern16"); if (ArgIdx == 1) - return MemoryLocation(Arg, 16, AATags); - if (const ConstantInt *LenCI = dyn_cast<ConstantInt>(CS.getArgument(2))) - return MemoryLocation(Arg, LenCI->getZExtValue(), AATags); + return MemoryLocation(Arg, LocationSize::precise(16), AATags); + if (const ConstantInt *LenCI = + dyn_cast<ConstantInt>(Call->getArgOperand(2))) + return MemoryLocation(Arg, LocationSize::precise(LenCI->getZExtValue()), + AATags); } // FIXME: Handle memset_pattern4 and memset_pattern8 also. - return MemoryLocation(CS.getArgument(ArgIdx), UnknownSize, AATags); + return MemoryLocation(Call->getArgOperand(ArgIdx), LocationSize::unknown(), + AATags); } |