friend class OpenMPIRBuilder;
private:
- BasicBlock *Preheader = nullptr;
BasicBlock *Header = nullptr;
BasicBlock *Cond = nullptr;
- BasicBlock *Body = nullptr;
BasicBlock *Latch = nullptr;
BasicBlock *Exit = nullptr;
- BasicBlock *After = nullptr;
/// Add the control blocks of this loop to \p BBs.
///
/// Code that must be execute before any loop iteration can be emitted here,
/// such as computing the loop trip count and begin lifetime markers. Code in
/// the preheader is not considered part of the canonical loop.
- BasicBlock *getPreheader() const {
- assert(isValid() && "Requires a valid canonical loop");
- return Preheader;
- }
+ BasicBlock *getPreheader() const;
/// The header is the entry for each iteration. In the canonical control flow,
/// it only contains the PHINode for the induction variable.
/// eventually branch to the \p Latch block.
BasicBlock *getBody() const {
assert(isValid() && "Requires a valid canonical loop");
- return Body;
+ return cast<BranchInst>(Cond->getTerminator())->getSuccessor(0);
}
/// Reaching the latch indicates the end of the loop body code. In the
/// statements/cancellations).
BasicBlock *getAfter() const {
assert(isValid() && "Requires a valid canonical loop");
- return After;
+ return Exit->getSingleSuccessor();
}
/// Returns the llvm::Value containing the number of loop iterations. It must
/// Return the insertion point for user code before the loop.
OpenMPIRBuilder::InsertPointTy getPreheaderIP() const {
assert(isValid() && "Requires a valid canonical loop");
+ BasicBlock *Preheader = getPreheader();
return {Preheader, std::prev(Preheader->end())};
};
/// Return the insertion point for user code in the body.
OpenMPIRBuilder::InsertPointTy getBodyIP() const {
assert(isValid() && "Requires a valid canonical loop");
+ BasicBlock *Body = getBody();
return {Body, Body->begin()};
};
/// Return the insertion point for user code after the loop.
OpenMPIRBuilder::InsertPointTy getAfterIP() const {
assert(isValid() && "Requires a valid canonical loop");
+ BasicBlock *After = getAfter();
return {After, After->begin()};
};
LoopInfos.emplace_front();
CanonicalLoopInfo *CL = &LoopInfos.front();
- CL->Preheader = Preheader;
CL->Header = Header;
CL->Cond = Cond;
- CL->Body = Body;
CL->Latch = Latch;
CL->Exit = Exit;
- CL->After = After;
#ifndef NDEBUG
CL->assertOK();
// Split the loop at the insertion point: Branch to the preheader and move
// every following instruction to after the loop (the After BB). Also, the
// new successor is the loop's after block.
- Builder.CreateBr(CL->Preheader);
+ Builder.CreateBr(CL->getPreheader());
After->getInstList().splice(After->begin(), BB->getInstList(),
Builder.GetInsertPoint(), BB->end());
After->replaceSuccessorsPhiUsesWith(BB, After);
BasicBlock *OrigAfter = Outermost->getAfter();
Function *F = OrigPreheader->getParent();
+ // Loop control blocks that may become orphaned later.
+ SmallVector<BasicBlock *, 12> OldControlBBs;
+ OldControlBBs.reserve(6 * Loops.size());
+ for (CanonicalLoopInfo *Loop : Loops)
+ Loop->collectControlBlocks(OldControlBBs);
+
// Setup the IRBuilder for inserting the trip count computation.
Builder.SetCurrentDebugLocation(DL);
if (ComputeIP.isSet())
Loops[i]->getIndVar()->replaceAllUsesWith(NewIndVars[i]);
// Remove unused parts of the input loops.
- SmallVector<BasicBlock *, 12> OldControlBBs;
- OldControlBBs.reserve(6 * Loops.size());
- for (CanonicalLoopInfo *Loop : Loops)
- Loop->collectControlBlocks(OldControlBBs);
removeUnusedBlocksFromParent(OldControlBBs);
for (CanonicalLoopInfo *L : Loops)
BasicBlock *InnerEnter = InnermostLoop->getBody();
BasicBlock *InnerLatch = InnermostLoop->getLatch();
+ // Loop control blocks that may become orphaned later.
+ SmallVector<BasicBlock *, 12> OldControlBBs;
+ OldControlBBs.reserve(6 * Loops.size());
+ for (CanonicalLoopInfo *Loop : Loops)
+ Loop->collectControlBlocks(OldControlBBs);
+
// Collect original trip counts and induction variable to be accessible by
// index. Also, the structure of the original loops is not preserved during
// the construction of the tiled loops, so do it before we scavenge the BBs of
}
// Remove unused parts of the original loops.
- SmallVector<BasicBlock *, 12> OldControlBBs;
- OldControlBBs.reserve(6 * Loops.size());
- for (CanonicalLoopInfo *Loop : Loops)
- Loop->collectControlBlocks(OldControlBBs);
removeUnusedBlocksFromParent(OldControlBBs);
for (CanonicalLoopInfo *L : Loops)
// flow. For consistency, this also means we do not add the Body block, which
// is just the entry to the body code.
BBs.reserve(BBs.size() + 6);
- BBs.append({Preheader, Header, Cond, Latch, Exit, After});
+ BBs.append({getPreheader(), Header, Cond, Latch, Exit, getAfter()});
+}
+
+BasicBlock *CanonicalLoopInfo::getPreheader() const {
+ assert(isValid() && "Requires a valid canonical loop");
+ for (BasicBlock *Pred : predecessors(Header)) {
+ if (Pred != Latch)
+ return Pred;
+ }
+ llvm_unreachable("Missing preheader");
}
void CanonicalLoopInfo::assertOK() const {
if (!isValid())
return;
+ BasicBlock *Preheader = getPreheader();
+ BasicBlock *Body = getBody();
+ BasicBlock *After = getAfter();
+
// Verify standard control-flow we use for OpenMP loops.
assert(Preheader);
assert(isa<BranchInst>(Preheader->getTerminator()) &&
}
void CanonicalLoopInfo::invalidate() {
- Preheader = nullptr;
Header = nullptr;
Cond = nullptr;
- Body = nullptr;
Latch = nullptr;
Exit = nullptr;
- After = nullptr;
}