34#define DEBUG_TYPE "coro-annotation-elide"
38 if (!isa<AllocaInst>(&
I))
52 auto *Frame =
new AllocaInst(FrameTy,
DL.getAllocaAddrSpace(),
"", InsertPt);
53 Frame->setAlignment(FrameAlign);
74 if (
auto *CI = dyn_cast<CallInst>(CB)) {
76 NewArgs,
"", NewCBInsertPt);
77 NewCI->setTailCallKind(CI->getTailCallKind());
79 }
else if (
auto *
II = dyn_cast<InvokeInst>(CB)) {
81 II->getNormalDest(),
II->getUnwindDest(),
82 NewArgs, {},
"", NewCBInsertPt);
111 bool Changed =
false;
120 Function *NewCallee = Callee->getParent()->getFunction(
121 (Callee->getName() +
".noalloc").str());
126 for (
auto *U : Callee->users()) {
127 if (
auto *CB = dyn_cast<CallBase>(U)) {
128 if (CB->getCalledFunction() == Callee)
132 auto FramePtrArgPosition = NewCallee->
arg_size() - 1;
140 for (
auto *CB :
Users) {
141 auto *Caller = CB->getFunction();
145 bool IsCallerPresplitCoroutine = Caller->isPresplitCoroutine();
146 bool HasAttr = CB->hasFnAttr(llvm::Attribute::CoroElideSafe);
147 if (IsCallerPresplitCoroutine && HasAttr) {
148 auto *CallerN = CG.
lookup(*Caller);
149 auto *CallerC = CallerN ? CG.
lookupSCC(*CallerN) :
nullptr;
152 auto ShouldUpdateCallGraph = !!CallerC;
153 processCall(CB, Caller, NewCallee, FrameSize, FrameAlign);
157 <<
"'" <<
ore::NV(
"callee", Callee->getName())
158 <<
"' elided in '" <<
ore::NV(
"caller", Caller->getName())
164 if (ShouldUpdateCallGraph)
172 <<
"'" <<
ore::NV(
"callee", Callee->getName())
173 <<
"' not elided in '" <<
ore::NV(
"caller", Caller->getName())
174 <<
"' (caller_presplit="
175 <<
ore::NV(
"caller_presplit", IsCallerPresplitCoroutine)
176 <<
", elide_safe_attr=" <<
ore::NV(
"elide_safe_attr", HasAttr)
MachineBasicBlock MachineBasicBlock::iterator DebugLoc DL
This header provides classes for managing passes over SCCs of the call graph.
This file provides interfaces used to manipulate a call graph, regardless if it is a "old style" Call...
static void processCall(CallBase *CB, Function *Caller, Function *NewCallee, uint64_t FrameSize, Align FrameAlign)
static Instruction * getFirstNonAllocaInTheEntryBlock(Function *F)
static Value * allocateFrameInCaller(Function *Caller, uint64_t FrameSize, Align FrameAlign)
Module.h This file contains the declarations for the Module class.
This header defines various interfaces for pass management in LLVM.
iv Induction Variable Users
Implements a lazy call graph analysis and related passes for the new pass manager.
Legalize the Machine IR a function s Machine IR
uint64_t IntrinsicInst * II
FunctionAnalysisManager FAM
static const unsigned FramePtr
an instruction to allocate memory on the stack
A container for analyses that lazily runs them and caches their results.
void invalidate(IRUnitT &IR, const PreservedAnalyses &PA)
Invalidate cached analyses for an IR unit.
PassT::Result & getResult(IRUnitT &IR, ExtraArgTs... ExtraArgs)
Get the result of an analysis pass for a given IR unit.
InstListType::iterator iterator
Instruction iterators...
Base class for all callable instructions (InvokeInst and CallInst) Holds everything related to callin...
void setCallingConv(CallingConv::ID CC)
bundle_op_iterator bundle_op_info_begin()
Return the start of the list of BundleOpInfo instances associated with this OperandBundleUser.
CallingConv::ID getCallingConv() const
bundle_op_iterator bundle_op_info_end()
Return the end of the list of BundleOpInfo instances associated with this OperandBundleUser.
User::op_iterator arg_begin()
Return the iterator pointing to the beginning of the argument list.
void setAttributes(AttributeList A)
Set the attributes for this call.
User::op_iterator arg_end()
Return the iterator pointing to the end of the argument list.
void removeFnAttr(Attribute::AttrKind Kind)
Removes the attribute from the function.
AttributeList getAttributes() const
Return the attributes for this call.
void setCalledFunction(Function *Fn)
Sets the function called, including updating the function type.
Wrapper to unify "old style" CallGraph and "new style" LazyCallGraph.
void initialize(LazyCallGraph &LCG, LazyCallGraph::SCC &SCC, CGSCCAnalysisManager &AM, CGSCCUpdateResult &UR)
Initializers for usage outside of a CGSCC pass, inside a CGSCC pass in the old and new pass manager (...
static CallInst * Create(FunctionType *Ty, Value *F, const Twine &NameStr="", InsertPosition InsertBefore=nullptr)
A parsed version of the target data layout string in and methods for querying it.
A proxy from a FunctionAnalysisManager to an SCC.
FunctionType * getFunctionType() const
Returns the FunctionType for me.
uint64_t getParamDereferenceableBytes(unsigned ArgNo) const
Extract the number of dereferenceable bytes for a parameter.
MaybeAlign getParamAlign(unsigned ArgNo) const
This class captures the data input to the InlineFunction call, and records the auxiliary results prod...
InlineResult is basically true or false.
const DebugLoc & getDebugLoc() const
Return the debug location for this node as a DebugLoc.
InstListType::iterator eraseFromParent()
This method unlinks 'this' from the containing basic block and deletes it.
void setDebugLoc(DebugLoc Loc)
Set the debug location information for this instruction.
static InvokeInst * Create(FunctionType *Ty, Value *Func, BasicBlock *IfNormal, BasicBlock *IfException, ArrayRef< Value * > Args, const Twine &NameStr, InsertPosition InsertBefore=nullptr)
This is an important class for using LLVM in a threaded context.
A node in the call graph.
An SCC of the call graph.
A lazily constructed view of the call graph of a module.
SCC * lookupSCC(Node &N) const
Lookup a function's SCC in the graph.
Node * lookup(const Function &F) const
Lookup a function in the graph which has already been scanned and added.
A set of analyses that are preserved following a run of a transformation pass.
static PreservedAnalyses none()
Convenience factory function for the empty preserved set.
static PreservedAnalyses all()
Construct a special preserved set that preserves all passes.
void append(ItTy in_start, ItTy in_end)
Add the specified range to the end of the SmallVector.
void push_back(const T &Elt)
This is a 'vector' (really, a variable-sized array), optimized for the case when the array is small.
static IntegerType * getInt8Ty(LLVMContext &C)
LLVM Value Representation.
void replaceAllUsesWith(Value *V)
Change all uses of this to point to a new Value.
self_iterator getIterator()
Pass manager infrastructure for declaring and invalidating analyses.
#define llvm_unreachable(msg)
Marks that the current location is not supposed to be reachable.
@ C
The default llvm calling convention, compatible with C.
DiagnosticInfoOptimizationBase::Argument NV
This is an optimization pass for GlobalISel generic memory operations.
LazyCallGraph::SCC & updateCGAndAnalysisManagerForCGSCCPass(LazyCallGraph &G, LazyCallGraph::SCC &C, LazyCallGraph::Node &N, CGSCCAnalysisManager &AM, CGSCCUpdateResult &UR, FunctionAnalysisManager &FAM)
Helper to update the call graph after running a CGSCC pass.
InlineResult InlineFunction(CallBase &CB, InlineFunctionInfo &IFI, bool MergeAttributes=false, AAResults *CalleeAAR=nullptr, bool InsertLifetime=true, Function *ForwardVarArgsTo=nullptr)
This function inlines the called function into the basic block of the caller.
This struct is a compact representation of a valid (non-zero power of two) alignment.
Support structure for SCC passes to communicate updates the call graph back to the CGSCC pass manager...
PreservedAnalyses run(LazyCallGraph::SCC &C, CGSCCAnalysisManager &AM, LazyCallGraph &CG, CGSCCUpdateResult &UR)
Align valueOrOne() const
For convenience, returns a valid alignment or 1 if undefined.