X-Git-Url: http://demsky.eecs.uci.edu/git/?a=blobdiff_plain;f=lib%2FAnalysis%2FPostDominators.cpp;h=b8d833e23d7501a55c7c5262f7e63e842f5c3c48;hb=2a3876d885e7dd9eab77937187df4b65b2ad887f;hp=1188cff0303644ebcb953eca24921a72c54e87c9;hpb=62e279bbdb235e247fa43223ba920f97ae27e4ac;p=oota-llvm.git diff --git a/lib/Analysis/PostDominators.cpp b/lib/Analysis/PostDominators.cpp index 1188cff0303..b8d833e23d7 100644 --- a/lib/Analysis/PostDominators.cpp +++ b/lib/Analysis/PostDominators.cpp @@ -16,6 +16,7 @@ #include "llvm/Support/CFG.h" #include "llvm/ADT/DepthFirstIterator.h" #include "llvm/ADT/SetOperations.h" +#include "PostDominatorCalculation.h" using namespace llvm; //===----------------------------------------------------------------------===// @@ -27,28 +28,25 @@ char PostDominanceFrontier::ID = 0; static RegisterPass F("postdomtree", "Post-Dominator Tree Construction", true); -unsigned PostDominatorTree::DFSPass(BasicBlock *V, InfoRec &VInfo, - unsigned N) { - std::vector > workStack; - std::set visited; - workStack.push_back(std::make_pair(V, &VInfo)); +unsigned PostDominatorTree::DFSPass(BasicBlock *V, unsigned N) { + std::vector workStack; + SmallPtrSet Visited; + workStack.push_back(V); do { - BasicBlock *currentBB = workStack.back().first; - InfoRec *currentVInfo = workStack.back().second; + BasicBlock *currentBB = workStack.back(); + InfoRec &CurVInfo = Info[currentBB]; // Visit each block only once. - if (visited.count(currentBB) == 0) { - - visited.insert(currentBB); - currentVInfo->Semi = ++N; - currentVInfo->Label = currentBB; + if (Visited.insert(currentBB)) { + CurVInfo.Semi = ++N; + CurVInfo.Label = currentBB; Vertex.push_back(currentBB); // Vertex[n] = current; // Info[currentBB].Ancestor = 0; // Ancestor[n] = 0 // Child[currentBB] = 0; - currentVInfo->Size = 1; // Size[currentBB] = 1 + CurVInfo.Size = 1; // Size[currentBB] = 1 } // Visit children @@ -58,8 +56,8 @@ unsigned PostDominatorTree::DFSPass(BasicBlock *V, InfoRec &VInfo, InfoRec &SuccVInfo = Info[*PI]; if (SuccVInfo.Semi == 0) { SuccVInfo.Parent = currentBB; - if (visited.count (*PI) == 0) { - workStack.push_back(std::make_pair(*PI, &SuccVInfo)); + if (!Visited.count(*PI)) { + workStack.push_back(*PI); visitChild = true; } } @@ -75,150 +73,6 @@ unsigned PostDominatorTree::DFSPass(BasicBlock *V, InfoRec &VInfo, return N; } -void PostDominatorTree::Compress(BasicBlock *V, InfoRec &VInfo) { - BasicBlock *VAncestor = VInfo.Ancestor; - InfoRec &VAInfo = Info[VAncestor]; - if (VAInfo.Ancestor == 0) - return; - - Compress(VAncestor, VAInfo); - - BasicBlock *VAncestorLabel = VAInfo.Label; - BasicBlock *VLabel = VInfo.Label; - if (Info[VAncestorLabel].Semi < Info[VLabel].Semi) - VInfo.Label = VAncestorLabel; - - VInfo.Ancestor = VAInfo.Ancestor; -} - -BasicBlock *PostDominatorTree::Eval(BasicBlock *V) { - InfoRec &VInfo = Info[V]; - - // Higher-complexity but faster implementation - if (VInfo.Ancestor == 0) - return V; - Compress(V, VInfo); - return VInfo.Label; -} - -void PostDominatorTree::Link(BasicBlock *V, BasicBlock *W, - InfoRec &WInfo) { - // Higher-complexity but faster implementation - WInfo.Ancestor = V; -} - -void PostDominatorTree::calculate(Function &F) { - // Step #0: Scan the function looking for the root nodes of the post-dominance - // relationships. These blocks, which have no successors, end with return and - // unwind instructions. - for (Function::iterator I = F.begin(), E = F.end(); I != E; ++I) - if (succ_begin(I) == succ_end(I)) { - Instruction *Insn = I->getTerminator(); - // Unreachable block is not a root node. - if (!isa(Insn)) - Roots.push_back(I); - } - - Vertex.push_back(0); - - // Step #1: Number blocks in depth-first order and initialize variables used - // in later stages of the algorithm. - unsigned N = 0; - for (unsigned i = 0, e = Roots.size(); i != e; ++i) - N = DFSPass(Roots[i], Info[Roots[i]], N); - - for (unsigned i = N; i >= 2; --i) { - BasicBlock *W = Vertex[i]; - InfoRec &WInfo = Info[W]; - - // Step #2: Calculate the semidominators of all vertices - for (succ_iterator SI = succ_begin(W), SE = succ_end(W); SI != SE; ++SI) - if (Info.count(*SI)) { // Only if this predecessor is reachable! - unsigned SemiU = Info[Eval(*SI)].Semi; - if (SemiU < WInfo.Semi) - WInfo.Semi = SemiU; - } - - Info[Vertex[WInfo.Semi]].Bucket.push_back(W); - - BasicBlock *WParent = WInfo.Parent; - Link(WParent, W, WInfo); - - // Step #3: Implicitly define the immediate dominator of vertices - std::vector &WParentBucket = Info[WParent].Bucket; - while (!WParentBucket.empty()) { - BasicBlock *V = WParentBucket.back(); - WParentBucket.pop_back(); - BasicBlock *U = Eval(V); - IDoms[V] = Info[U].Semi < Info[V].Semi ? U : WParent; - } - } - - // Step #4: Explicitly define the immediate dominator of each vertex - for (unsigned i = 2; i <= N; ++i) { - BasicBlock *W = Vertex[i]; - BasicBlock *&WIDom = IDoms[W]; - if (WIDom != Vertex[Info[W].Semi]) - WIDom = IDoms[WIDom]; - } - - if (Roots.empty()) return; - - // Add a node for the root. This node might be the actual root, if there is - // one exit block, or it may be the virtual exit (denoted by (BasicBlock *)0) - // which postdominates all real exits if there are multiple exit blocks. - BasicBlock *Root = Roots.size() == 1 ? Roots[0] : 0; - DomTreeNodes[Root] = RootNode = new DomTreeNode(Root, 0); - - // Loop over all of the reachable blocks in the function... - for (Function::iterator I = F.begin(), E = F.end(); I != E; ++I) - if (BasicBlock *ImmPostDom = getIDom(I)) { // Reachable block. - DomTreeNode *&BBNode = DomTreeNodes[I]; - if (!BBNode) { // Haven't calculated this node yet? - // Get or calculate the node for the immediate dominator - DomTreeNode *IPDomNode = getNodeForBlock(ImmPostDom); - - // Add a new tree node for this BasicBlock, and link it as a child of - // IDomNode - DomTreeNode *C = new DomTreeNode(I, IPDomNode); - DomTreeNodes[I] = C; - BBNode = IPDomNode->addChild(C); - } - } - - // Free temporary memory used to construct idom's - IDoms.clear(); - Info.clear(); - std::vector().swap(Vertex); - - int dfsnum = 0; - // Iterate over all nodes in depth first order... - for (unsigned i = 0, e = Roots.size(); i != e; ++i) - for (idf_iterator I = idf_begin(Roots[i]), - E = idf_end(Roots[i]); I != E; ++I) { - if (!getNodeForBlock(*I)->getIDom()) - getNodeForBlock(*I)->assignDFSNumber(dfsnum); - } - DFSInfoValid = true; -} - - -DomTreeNode *PostDominatorTree::getNodeForBlock(BasicBlock *BB) { - DomTreeNode *&BBNode = DomTreeNodes[BB]; - if (BBNode) return BBNode; - - // Haven't calculated this node yet? Get or calculate the node for the - // immediate postdominator. - BasicBlock *IPDom = getIDom(BB); - DomTreeNode *IPDomNode = getNodeForBlock(IPDom); - - // Add a new tree node for this BasicBlock, and link it as a child of - // IDomNode - DomTreeNode *C = new DomTreeNode(BB, IPDomNode); - DomTreeNodes[BB] = C; - return BBNode = IPDomNode->addChild(C); -} - //===----------------------------------------------------------------------===// // PostDominanceFrontier Implementation //===----------------------------------------------------------------------===//