26bool maybeReachableFromEachOther(
const SmallVectorImpl<IntrinsicInst *> &Insts,
27 const DominatorTree *DT,
const LoopInfo *LI,
28 size_t MaxLifetimes) {
30 if (Insts.size() > MaxLifetimes)
32 for (
size_t I = 0;
I < Insts.size(); ++
I) {
33 for (
size_t J = 0; J < Insts.size(); ++J) {
54 for (
auto *
End : Ends) {
58 unsigned NumCoveredExits = 0;
59 for (
auto *RI : RetVec) {
67 if (EndBlocks.
count(RI->getParent()) > 0 ||
74 if (NumCoveredExits == ReachableRetVec.
size()) {
75 for (
auto *
End : Ends)
78 for (
auto *RI : ReachableRetVec)
90 size_t MaxLifetimes) {
94 return LifetimeStart.
size() == 1 &&
95 (LifetimeEnd.
size() == 1 ||
96 (LifetimeEnd.
size() > 0 &&
97 !maybeReachableFromEachOther(LifetimeEnd, DT, LI, MaxLifetimes)));
101 if (isa<ReturnInst>(Inst)) {
106 if (isa<ResumeInst, CleanupReturnInst>(Inst)) {
113 if (
CallInst *CI = dyn_cast<CallInst>(&Inst)) {
114 if (CI->canReturnTwice()) {
118 if (
AllocaInst *AI = dyn_cast<AllocaInst>(&Inst)) {
124 auto *II = dyn_cast<IntrinsicInst>(&Inst);
125 if (II && (II->getIntrinsicID() == Intrinsic::lifetime_start ||
126 II->getIntrinsicID() == Intrinsic::lifetime_end)) {
134 if (II->getIntrinsicID() == Intrinsic::lifetime_start)
140 if (
auto *DVI = dyn_cast<DbgVariableIntrinsic>(&Inst)) {
141 for (
Value *V : DVI->location_ops()) {
142 if (
auto *AI = dyn_cast_or_null<AllocaInst>(V)) {
147 if (DVIVec.empty() || DVIVec.back() != DVI)
148 DVIVec.push_back(DVI);
172 !(SSI && SSI->
isSafe(AI));
181 const Align NewAlignment = std::max(
Info.AI->getAlign(), Alignment);
182 Info.AI->setAlignment(NewAlignment);
183 auto &Ctx =
Info.AI->getFunction()->getContext();
187 if (
Size == AlignedSize)
191 Type *AllocatedType =
192 Info.AI->isArrayAllocation()
194 Info.AI->getAllocatedType(),
195 cast<ConstantInt>(
Info.AI->getArraySize())->getZExtValue())
196 :
Info.AI->getAllocatedType();
199 auto *NewAI =
new AllocaInst(TypeWithPadding,
Info.AI->getAddressSpace(),
200 nullptr,
"",
Info.AI);
201 NewAI->takeName(
Info.AI);
202 NewAI->setAlignment(
Info.AI->getAlign());
203 NewAI->setUsedWithInAlloca(
Info.AI->isUsedWithInAlloca());
204 NewAI->setSwiftError(
Info.AI->isSwiftError());
205 NewAI->copyMetadata(*
Info.AI);
207 Value *NewPtr = NewAI;
210 if (
Info.AI->getType() != NewAI->getType())
213 Info.AI->replaceAllUsesWith(NewPtr);
214 Info.AI->eraseFromParent();
MachineBasicBlock MachineBasicBlock::iterator DebugLoc DL
Analysis containing CSE Info
an instruction to allocate memory on the stack
bool isSwiftError() const
Return true if this alloca is used as a swifterror argument to a call.
bool isStaticAlloca() const
Return true if this alloca is in the entry block of the function and is a constant size.
Type * getAllocatedType() const
Return the type that is being allocated by the instruction.
bool isUsedWithInAlloca() const
Return true if this alloca is used as an inalloca argument to a call.
std::optional< TypeSize > getAllocationSize(const DataLayout &DL) const
Get allocation size in bytes.
static ArrayType * get(Type *ElementType, uint64_t NumElements)
This static method is the primary way to construct an ArrayType.
const CallInst * getTerminatingMustTailCall() const
Returns the call instruction marked 'musttail' prior to the terminating return instruction of this ba...
This class represents a no-op cast from one type to another.
This class represents a function call, abstracting a target machine's calling convention.
Concrete subclass of DominatorTreeBase that is used to compute a normal dominator tree.
const Module * getModule() const
Return the module owning the function this instruction belongs to or nullptr it the function does not...
const BasicBlock * getParent() const
const DataLayout & getDataLayout() const
Get the data layout for the module's target platform.
PostDominatorTree Class - Concrete subclass of DominatorTree that is used to compute the post-dominat...
bool dominates(const Instruction *I1, const Instruction *I2) const
Return true if I1 dominates I2.
size_type count(ConstPtrType Ptr) const
count - Return 1 if the specified pointer is in the set, 0 otherwise.
std::pair< iterator, bool > insert(PtrType Ptr)
Inserts Ptr if and only if there is no element in the container equal to Ptr.
SmallPtrSet - This class implements a set which is optimized for holding SmallSize or less elements.
This class consists of common code factored out of the SmallVector class to reduce code duplication b...
void push_back(const T &Elt)
This is a 'vector' (really, a variable-sized array), optimized for the case when the array is small.
bool isSafe(const AllocaInst &AI) const
static StructType * get(LLVMContext &Context, ArrayRef< Type * > Elements, bool isPacked=false)
This static method is the primary way to create a literal StructType.
The instances of the Type class are immutable: once they are created, they are never changed.
bool isSized(SmallPtrSetImpl< Type * > *Visited=nullptr) const
Return true if it makes sense to take the size of this type.
static IntegerType * getInt8Ty(LLVMContext &C)
LLVM Value Representation.
An efficient, type-erasing, non-owning reference to a callable.
bool isInterestingAlloca(const AllocaInst &AI)
void visit(Instruction &Inst)
bool isStandardLifetime(const SmallVectorImpl< IntrinsicInst * > &LifetimeStart, const SmallVectorImpl< IntrinsicInst * > &LifetimeEnd, const DominatorTree *DT, const LoopInfo *LI, size_t MaxLifetimes)
bool forAllReachableExits(const DominatorTree &DT, const PostDominatorTree &PDT, const LoopInfo &LI, const Instruction *Start, const SmallVectorImpl< IntrinsicInst * > &Ends, const SmallVectorImpl< Instruction * > &RetVec, llvm::function_ref< void(Instruction *)> Callback)
uint64_t getAllocaSizeInBytes(const AllocaInst &AI)
Instruction * getUntagLocationIfFunctionExit(Instruction &Inst)
void alignAndPadAlloca(memtag::AllocaInfo &Info, llvm::Align Align)
This is an optimization pass for GlobalISel generic memory operations.
AllocaInst * findAllocaForValue(Value *V, bool OffsetZero=false)
Returns unique alloca where the value comes from, or nullptr.
bool isAllocaPromotable(const AllocaInst *AI)
Return true if this alloca is legal for promotion.
uint64_t alignTo(uint64_t Size, Align A)
Returns a multiple of A needed to store Size bytes.
bool isPotentiallyReachable(const Instruction *From, const Instruction *To, const SmallPtrSetImpl< BasicBlock * > *ExclusionSet=nullptr, const DominatorTree *DT=nullptr, const LoopInfo *LI=nullptr)
Determine whether instruction 'To' is reachable from 'From', without passing through any blocks in Ex...
This struct is a compact representation of a valid (non-zero power of two) alignment.
SmallVector< DbgVariableIntrinsic *, 2 > DbgVariableIntrinsics
MapVector< AllocaInst *, AllocaInfo > AllocasToInstrument
SmallVector< Instruction *, 4 > UnrecognizedLifetimes
SmallVector< Instruction *, 8 > RetVec