54 #define DEBUG_TYPE "loopsink"
56 STATISTIC(NumLoopSunk,
"Number of instructions sunk into loop");
57 STATISTIC(NumLoopSunkCloned,
"Number of cloned instructions sunk into loop");
61 cl::desc(
"Do not sink instructions that require cloning unless they "
62 "execute less than this percent of the time."));
66 cl::desc(
"Do not sink instructions that have too many uses."));
123 if (UseBBs.
size() == 0)
124 return BBsToSinkInto;
138 BBsDominatedByColdestBB.
clear();
141 BBsDominatedByColdestBB.
insert(SinkedBB);
142 if (BBsDominatedByColdestBB.
size() == 0)
146 for (
BasicBlock *DominatedBB : BBsDominatedByColdestBB) {
147 BBsToSinkInto.erase(DominatedBB);
149 BBsToSinkInto.insert(ColdestBB);
157 BBsToSinkInto.
clear();
158 return BBsToSinkInto;
172 for (
auto &U : I.
uses()) {
175 if (dyn_cast<PHINode>(UI))
192 if (BBsToSinkInto.
empty())
199 SortedBBsToSinkInto.
insert(SortedBBsToSinkInto.
begin(), BBsToSinkInto.
begin(),
200 BBsToSinkInto.
end());
201 std::sort(SortedBBsToSinkInto.
begin(), SortedBBsToSinkInto.
end(),
203 return *LoopBlockNumber.
find(A) < *LoopBlockNumber.
find(
B);
219 auto *I = cast<Instruction>(U.
getUser());
225 DEBUG(
dbgs() <<
"Sinking a clone of " << I <<
" To: " <<
N->getName()
231 I.
moveBefore(&*MoveBB->getFirstInsertionPt());
260 bool Changed =
false;
274 LoopBlockNumber[
B] = ++
i;
276 std::stable_sort(ColdLoopBBs.
begin(), ColdLoopBBs.
end(),
284 for (
auto II = Preheader->
rbegin(),
E = Preheader->
rend(); II !=
E;) {
288 "Insts in a loop's preheader should have loop invariant operands!");
301 struct LegacyLoopSinkPass :
public LoopPass {
311 auto *SE = getAnalysisIfAvailable<ScalarEvolutionWrapperPass>();
313 *L, getAnalysis<AAResultsWrapperPass>().getAAResults(),
314 getAnalysis<LoopInfoWrapperPass>().getLoopInfo(),
315 getAnalysis<DominatorTreeWrapperPass>().getDomTree(),
316 getAnalysis<BlockFrequencyInfoWrapperPass>().getBFI(),
317 SE ? &SE->getSE() :
nullptr);
Pass interface - Implemented by all 'passes'.
void push_back(const T &Elt)
use_iterator_impl< Use > use_iterator
iterator_range< use_iterator > uses()
static PassRegistry * getPassRegistry()
getPassRegistry - Access the global registry object, which is automatically initialized at applicatio...
STATISTIC(NumFunctions,"Total number of functions")
This header provides classes for managing a pipeline of passes over loops in LLVM IR...
static cl::opt< unsigned > SinkFrequencyPercentThreshold("sink-freq-percent-threshold", cl::Hidden, cl::init(90), cl::desc("Do not sink instructions that require cloning unless they ""execute less than this percent of the time."))
The main scalar evolution driver.
bool all_of(R &&range, UnaryPredicate P)
Provide wrappers to std::all_of which take ranges instead of having to pass begin/end explicitly...
const Function * getParent() const
Return the enclosing method, or null if none.
bool hasLoopInvariantOperands(const Instruction *I) const
Return true if all the operands of the specified instruction are loop invariant.
reverse_iterator rbegin()
LoopT * getLoopFor(const BlockT *BB) const
Return the inner most loop that BB lives in.
unsigned replaceDominatedUsesWith(Value *From, Value *To, DominatorTree &DT, const BasicBlockEdge &Edge)
Replace each use of 'From' with 'To' if that use is dominated by the given edge.
StringRef getName() const
Return a constant reference to the value's name.
A templated base class for SmallPtrSet which provides the typesafe interface that is common across al...
AnalysisUsage & addRequired()
#define INITIALIZE_PASS_DEPENDENCY(depName)
This is the interface for a SCEV-based alias analysis.
A Use represents the edge between a Value definition and its users.
This class consists of common code factored out of the SmallVector class to reduce code duplication b...
Legacy analysis pass which computes BlockFrequencyInfo.
void setName(const Twine &Name)
Change the name of the value.
Instruction * clone() const
Create a copy of 'this' instruction that is identical in all ways except the following: ...
Function Alias Analysis false
static GCRegistry::Add< OcamlGC > B("ocaml","ocaml 3.10-compatible GC")
Optional< uint64_t > getEntryCount() const
Get the entry count for this function.
Concrete subclass of DominatorTreeBase that is used to compute a normal dominator tree...
void forgetLoopDispositions(const Loop *L)
Called when the client has changed the disposition of values in this loop.
static GCRegistry::Add< CoreCLRGC > E("coreclr","CoreCLR-compatible GC")
iterator_range< block_iterator > blocks() const
BlockFrequencyInfo pass uses BlockFrequencyInfoImpl implementation to estimate IR basic block frequen...
initializer< Ty > init(const Ty &Val)
BlockT * getLoopPreheader() const
If there is a preheader for this loop, return it.
void insertBefore(Instruction *InsertPos)
Insert an unlinked instruction into a basic block immediately before the specified instruction...
LLVM Basic Block Representation.
LLVM_ATTRIBUTE_ALWAYS_INLINE iterator begin()
std::pair< iterator, bool > insert(PtrType Ptr)
Inserts Ptr if and only if there is no element in the container equal to Ptr.
Represent the analysis usage information of a pass.
bool contains(const LoopT *L) const
Return true if the specified loop is contained within in this loop.
INITIALIZE_PASS_END(RegBankSelect, DEBUG_TYPE,"Assign register bank of generic virtual registers", false, false) RegBankSelect
User * getUser() const
Returns the User that contains this Use.
static bool sinkLoopInvariantInstructions(Loop &L, AAResults &AA, LoopInfo &LI, DominatorTree &DT, BlockFrequencyInfo &BFI, ScalarEvolution *SE)
Sinks instructions from loop's preheader to the loop body if the sum frequency of inserted copy is sm...
Pass * createLoopSinkPass()
LLVM_NODISCARD bool empty() const
bool dominates(const Instruction *Def, const Use &U) const
Return true if Def dominates a use in User.
SmallPtrSet - This class implements a set which is optimized for holding SmallSize or less elements...
This is a 'vector' (really, a variable-sized array), optimized for the case when the array is small...
static SmallPtrSet< BasicBlock *, 2 > findBBsToSinkInto(const Loop &L, const SmallPtrSetImpl< BasicBlock * > &UseBBs, const SmallVectorImpl< BasicBlock * > &ColdLoopBBs, DominatorTree &DT, BlockFrequencyInfo &BFI)
Return a set of basic blocks to insert sinked instructions.
void setPreservesCFG()
This function should be called by the pass, iff they do not:
void add(Value *Ptr, uint64_t Size, const AAMDNodes &AAInfo)
These methods are used to add different types of instructions to the alias sets.
raw_ostream & dbgs()
dbgs() - This returns a reference to a raw_ostream for debugging messages.
iterator insert(iterator I, T &&Elt)
LLVM_ATTRIBUTE_ALWAYS_INLINE iterator end()
Represents a single loop in the control flow graph.
void getLoopAnalysisUsage(AnalysisUsage &AU)
Helper to consistently add the set of standard passes to a loop pass's AnalysisUsage.
iterator find(const KeyT &Val)
static cl::opt< unsigned > MaxNumberOfUseBBsForSinking("max-uses-for-sinking", cl::Hidden, cl::init(30), cl::desc("Do not sink instructions that have too many uses."))
INITIALIZE_PASS_BEGIN(LegacyLoopSinkPass,"loop-sink","Loop Sink", false, false) Pass *llvm
assert(ImpDefSCC.getReg()==AMDGPU::SCC &&ImpDefSCC.isDef())
void initializeLegacyLoopSinkPassPass(PassRegistry &)
void moveBefore(Instruction *MovePos)
Unlink this instruction from its current basic block and insert it into the basic block that MovePos ...
This is the interface for LLVM's primary stateless and local alias analysis.
bool canSinkOrHoistInst(Instruction &I, AAResults *AA, DominatorTree *DT, Loop *CurLoop, AliasSetTracker *CurAST, LoopSafetyInfo *SafetyInfo, OptimizationRemarkEmitter *ORE=nullptr)
Returns true if the hoister and sinker can handle this instruction.
machine sink
When an instruction is found to only be used outside of the loop, this function moves it to the exit ...
static GCRegistry::Add< ErlangGC > A("erlang","erlang-compatible garbage collector")
static BlockFrequency adjustedSumFreq(SmallPtrSetImpl< BasicBlock * > &BBs, BlockFrequencyInfo &BFI)
Return adjusted total frequency of BBs.
const BasicBlock * getParent() const
static bool sinkInstruction(Loop &L, Instruction &I, const SmallVectorImpl< BasicBlock * > &ColdLoopBBs, const SmallDenseMap< BasicBlock *, int, 16 > &LoopBlockNumber, LoopInfo &LI, DominatorTree &DT, BlockFrequencyInfo &BFI)
BlockFrequency getBlockFreq(const BasicBlock *BB) const
getblockFreq - Return block frequency.