summaryrefslogtreecommitdiffstats
path: root/include/llvm/Analysis/LoopInfo.h
diff options
context:
space:
mode:
Diffstat (limited to 'include/llvm/Analysis/LoopInfo.h')
-rw-r--r--include/llvm/Analysis/LoopInfo.h59
1 files changed, 40 insertions, 19 deletions
diff --git a/include/llvm/Analysis/LoopInfo.h b/include/llvm/Analysis/LoopInfo.h
index 2babc25..9455fd8 100644
--- a/include/llvm/Analysis/LoopInfo.h
+++ b/include/llvm/Analysis/LoopInfo.h
@@ -256,6 +256,27 @@ public:
///
BlockT *getLoopPreheader() const {
// Keep track of nodes outside the loop branching to the header...
+ BlockT *Out = getLoopPredecessor();
+ if (!Out) return 0;
+
+ // Make sure there is only one exit out of the preheader.
+ typedef GraphTraits<BlockT*> BlockTraits;
+ typename BlockTraits::ChildIteratorType SI = BlockTraits::child_begin(Out);
+ ++SI;
+ if (SI != BlockTraits::child_end(Out))
+ return 0; // Multiple exits from the block, must not be a preheader.
+
+ // The predecessor has exactly one successor, so it is a preheader.
+ return Out;
+ }
+
+ /// getLoopPredecessor - If the given loop's header has exactly one unique
+ /// predecessor outside the loop, return it. Otherwise return null.
+ /// This is less strict that the loop "preheader" concept, which requires
+ /// the predecessor to have exactly one successor.
+ ///
+ BlockT *getLoopPredecessor() const {
+ // Keep track of nodes outside the loop branching to the header...
BlockT *Out = 0;
// Loop over the predecessors of the header node...
@@ -264,22 +285,17 @@ public:
typedef GraphTraits<Inverse<BlockT*> > InvBlockTraits;
for (typename InvBlockTraits::ChildIteratorType PI =
InvBlockTraits::child_begin(Header),
- PE = InvBlockTraits::child_end(Header); PI != PE; ++PI)
- if (!contains(*PI)) { // If the block is not in the loop...
- if (Out && Out != *PI)
+ PE = InvBlockTraits::child_end(Header); PI != PE; ++PI) {
+ typename InvBlockTraits::NodeType *N = *PI;
+ if (!contains(N)) { // If the block is not in the loop...
+ if (Out && Out != N)
return 0; // Multiple predecessors outside the loop
- Out = *PI;
+ Out = N;
}
+ }
// Make sure there is only one exit out of the preheader.
assert(Out && "Header of loop has no predecessors from outside loop?");
- typename BlockTraits::ChildIteratorType SI = BlockTraits::child_begin(Out);
- ++SI;
- if (SI != BlockTraits::child_end(Out))
- return 0; // Multiple exits from the block, must not be a preheader.
-
- // If there is exactly one preheader, return it. If there was zero, then
- // Out is still null.
return Out;
}
@@ -293,11 +309,13 @@ public:
typename InvBlockTraits::ChildIteratorType PE =
InvBlockTraits::child_end(Header);
BlockT *Latch = 0;
- for (; PI != PE; ++PI)
- if (contains(*PI)) {
+ for (; PI != PE; ++PI) {
+ typename InvBlockTraits::NodeType *N = *PI;
+ if (contains(N)) {
if (Latch) return 0;
- Latch = *PI;
+ Latch = N;
}
+ }
return Latch;
}
@@ -409,10 +427,11 @@ public:
for (typename InvBlockTraits::ChildIteratorType PI =
InvBlockTraits::child_begin(BB), PE = InvBlockTraits::child_end(BB);
PI != PE; ++PI) {
- if (std::binary_search(LoopBBs.begin(), LoopBBs.end(), *PI))
+ typename InvBlockTraits::NodeType *N = *PI;
+ if (std::binary_search(LoopBBs.begin(), LoopBBs.end(), N))
HasInsideLoopPreds = true;
else
- OutsideLoopPreds.push_back(*PI);
+ OutsideLoopPreds.push_back(N);
}
if (BB == getHeader()) {
@@ -743,9 +762,11 @@ public:
typedef GraphTraits<Inverse<BlockT*> > InvBlockTraits;
for (typename InvBlockTraits::ChildIteratorType I =
InvBlockTraits::child_begin(BB), E = InvBlockTraits::child_end(BB);
- I != E; ++I)
- if (DT.dominates(BB, *I)) // If BB dominates its predecessor...
- TodoStack.push_back(*I);
+ I != E; ++I) {
+ typename InvBlockTraits::NodeType *N = *I;
+ if (DT.dominates(BB, N)) // If BB dominates its predecessor...
+ TodoStack.push_back(N);
+ }
if (TodoStack.empty()) return 0; // No backedges to this block...
OpenPOWER on IntegriCloud