diff options
Diffstat (limited to 'llvm/lib/Analysis/LoopInfo.cpp')
| -rw-r--r-- | llvm/lib/Analysis/LoopInfo.cpp | 32 |
1 files changed, 26 insertions, 6 deletions
diff --git a/llvm/lib/Analysis/LoopInfo.cpp b/llvm/lib/Analysis/LoopInfo.cpp index b5af210f1b92..a85869b16333 100644 --- a/llvm/lib/Analysis/LoopInfo.cpp +++ b/llvm/lib/Analysis/LoopInfo.cpp @@ -34,6 +34,7 @@ #include "llvm/IR/LLVMContext.h" #include "llvm/IR/Metadata.h" #include "llvm/IR/PassManager.h" +#include "llvm/IR/PrintPasses.h" #include "llvm/InitializePasses.h" #include "llvm/Support/CommandLine.h" #include "llvm/Support/Debug.h" @@ -431,6 +432,10 @@ static bool isBlockInLCSSAForm(const Loop &L, const BasicBlock &BB, for (const Use &U : I.uses()) { const Instruction *UI = cast<Instruction>(U.getUser()); const BasicBlock *UserBB = UI->getParent(); + + // For practical purposes, we consider that the use in a PHI + // occurs in the respective predecessor block. For more info, + // see the `phi` doc in LangRef and the LCSSA doc. if (const PHINode *P = dyn_cast<PHINode>(UI)) UserBB = P->getIncomingBlock(U); @@ -535,6 +540,22 @@ void Loop::setLoopAlreadyUnrolled() { setLoopID(NewLoopID); } +void Loop::setLoopMustProgress() { + LLVMContext &Context = getHeader()->getContext(); + + MDNode *MustProgress = findOptionMDForLoop(this, "llvm.loop.mustprogress"); + + if (MustProgress) + return; + + MDNode *MustProgressMD = + MDNode::get(Context, MDString::get(Context, "llvm.loop.mustprogress")); + MDNode *LoopID = getLoopID(); + MDNode *NewLoopID = + makePostTransformationMetadata(Context, LoopID, {}, {MustProgressMD}); + setLoopID(NewLoopID); +} + bool Loop::isAnnotatedParallel() const { MDNode *DesiredLoopIdMetadata = getLoopID(); @@ -546,7 +567,7 @@ bool Loop::isAnnotatedParallel() const { SmallPtrSet<MDNode *, 4> ParallelAccessGroups; // For scalable 'contains' check. if (ParallelAccesses) { - for (const MDOperand &MD : drop_begin(ParallelAccesses->operands(), 1)) { + for (const MDOperand &MD : drop_begin(ParallelAccesses->operands())) { MDNode *AccGroup = cast<MDNode>(MD.get()); assert(isValidAsAccessGroup(AccGroup) && "List item must be an access group"); @@ -764,7 +785,7 @@ void UnloopUpdater::removeBlocksFromAncestors() { /// Update the parent loop for all subloops directly nested within unloop. void UnloopUpdater::updateSubloopParents() { - while (!Unloop.empty()) { + while (!Unloop.isInnermost()) { Loop *Subloop = *std::prev(Unloop.end()); Unloop.removeChildLoop(std::prev(Unloop.end())); @@ -862,7 +883,7 @@ void LoopInfo::erase(Loop *Unloop) { auto InvalidateOnExit = make_scope_exit([&]() { destroy(Unloop); }); // First handle the special case of no parent loop to simplify the algorithm. - if (!Unloop->getParentLoop()) { + if (Unloop->isOutermost()) { // Since BBLoop had no parent, Unloop blocks are no longer in a loop. for (Loop::block_iterator I = Unloop->block_begin(), E = Unloop->block_end(); @@ -887,7 +908,7 @@ void LoopInfo::erase(Loop *Unloop) { } // Move all of the subloops to the top-level. - while (!Unloop->empty()) + while (!Unloop->isInnermost()) addTopLevelLoop(Unloop->removeChildLoop(std::prev(Unloop->end()))); return; @@ -1017,8 +1038,7 @@ MDNode *llvm::makePostTransformationMetadata(LLVMContext &Context, SmallVector<Metadata *, 4> MDs; // Reserve first location for self reference to the LoopID metadata node. - TempMDTuple TempNode = MDNode::getTemporary(Context, None); - MDs.push_back(TempNode.get()); + MDs.push_back(nullptr); // Remove metadata for the transformation that has been applied or that became // outdated. |
