[llvm-commits] [llvm] r53615 - /llvm/trunk/lib/Transforms/Scalar/GVN.cpp
Chris Lattner
clattner at apple.com
Tue Jul 15 09:59:49 PDT 2008
On Jul 15, 2008, at 9:28 AM, Owen Anderson wrote:
> +// mergeBlockIntoPredecessor - If this block is the only successor
> +// of its predecessor, and the edge is non-critical,
> +// fold it into that predecessor.
> +bool GVN::mergeBlockIntoPredecessor(BasicBlock* BB) {
Hey Owen,
Can you move this to transform utils?
-Chris
>
> + // Can't merge the entry block.
> + if (pred_begin(BB) == pred_end(BB)) return false;
> + // Can't merge if there are multiple preds.
> + if (++pred_begin(BB) != pred_end(BB)) return false;
> +
> + BasicBlock* PredBB = *pred_begin(BB);
> +
> + // Can't merge if the edge is critical.
> + if (PredBB->getTerminator()->getNumSuccessors() != 1) return false;
> +
> + // Begin by getting rid of unneeded PHIs.
> + while (PHINode *PN = dyn_cast<PHINode>(&BB->front())) {
> + PN->replaceAllUsesWith(PN->getIncomingValue(0));
> + BB->getInstList().pop_front(); // Delete the phi node...
> + }
> +
> + // Delete the unconditional branch from the predecessor...
> + PredBB->getInstList().pop_back();
> +
> + // Move all definitions in the successor to the predecessor...
> + PredBB->getInstList().splice(PredBB->end(), BB->getInstList());
> +
> + // Make all PHI nodes that referred to BB now refer to Pred as
> their
> + // source...
> + BB->replaceAllUsesWith(PredBB);
> +
> + // Finally, erase the old block and update dominator info.
> + DominatorTree& DT = getAnalysis<DominatorTree>();
> + DomTreeNode* DTN = DT[BB];
> + DomTreeNode* PredDTN = DT[PredBB];
> +
> + if (DTN) {
> + SmallPtrSet<DomTreeNode*, 8> Children(DTN->begin(), DTN->end());
> + for (SmallPtrSet<DomTreeNode*, 8>::iterator DI =
> Children.begin(),
> + DE = Children.end(); DI != DE; ++DI)
> + DT.changeImmediateDominator(*DI, PredDTN);
> +
> + DT.eraseNode(BB);
> + }
> +
> + BB->eraseFromParent();
> +
> + NumGVNBlocks++;
> + return true;
> +}
> +
> +// iterateOnFunction - Executes one iteration of GVN
> bool GVN::iterateOnFunction(Function &F) {
> // Clean out global sets from any previous functions
> VN.clear();
> phiMap.clear();
>
> + // Merge unconditional branches, allowing PRE to catch more
> + // optimization opportunities.
> + bool mergedBlocks = false;
> + for (Function::iterator FI = F.begin(), FE = F.end(); FI != FE; ) {
> + BasicBlock* BB = FI;
> + ++FI;
> + mergedBlocks |= mergeBlockIntoPredecessor(BB);
> + }
> +
> for (DenseMap<BasicBlock*, ValueNumberScope*>::iterator
> I = localAvail.begin(), E = localAvail.end(); I != E; ++I)
> delete I->second;
> @@ -1346,5 +1407,5 @@
> if (EnablePRE)
> changed |= performPRE(F);
>
> - return changed;
> + return changed || mergedBlocks;
> }
>
>
> _______________________________________________
> llvm-commits mailing list
> llvm-commits at cs.uiuc.edu
> http://lists.cs.uiuc.edu/mailman/listinfo/llvm-commits
More information about the llvm-commits
mailing list