mirror of
https://github.com/c64scene-ar/llvm-6502.git
synced 2024-08-18 12:29:21 +00:00
Reimplement the loopsimplify code which deletes edges from unreachable
blocks that target loop blocks. Before, the code was run once per loop, and depended on the number of predecessors each block in the loop had. Unfortunately, scanning preds can be really slow when huge numbers of phis exist or when phis with huge numbers of inputs exist. Now, the code is run once per function and scans successors instead of preds, which is far faster. In addition, the new code is simpler and is goto free, woo. This change speeds up a nasty testcase Duraid provided me from taking hours to taking ~72s with a debug build. The functionality this implements is already tested in the testsuite as Transforms/CodeExtractor/2004-03-13-LoopExtractorCrash.ll. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@29644 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
parent
8731c0d234
commit
fa78946482
@ -105,6 +105,58 @@ bool LoopSimplify::runOnFunction(Function &F) {
|
||||
LI = &getAnalysis<LoopInfo>();
|
||||
AA = getAnalysisToUpdate<AliasAnalysis>();
|
||||
|
||||
// Check to see that no blocks (other than the header) in loops have
|
||||
// predecessors that are not in loops. This is not valid for natural loops,
|
||||
// but can occur if the blocks are unreachable. Since they are unreachable we
|
||||
// can just shamelessly destroy their terminators to make them not branch into
|
||||
// the loop!
|
||||
for (Function::iterator BB = F.begin(), E = F.end(); BB != E; ++BB) {
|
||||
// This case can only occur for unreachable blocks. Blocks that are
|
||||
// unreachable can't be in loops, so filter those blocks out.
|
||||
if (LI->getLoopFor(BB)) continue;
|
||||
|
||||
bool BlockUnreachable = false;
|
||||
TerminatorInst *TI = BB->getTerminator();
|
||||
|
||||
// Check to see if any successors of this block are non-loop-header loops
|
||||
// that are not the header.
|
||||
for (unsigned i = 0, e = TI->getNumSuccessors(); i != e; ++i) {
|
||||
// If this successor is not in a loop, BB is clearly ok.
|
||||
Loop *L = LI->getLoopFor(TI->getSuccessor(i));
|
||||
if (!L) continue;
|
||||
|
||||
// If the succ is the loop header, and if L is a top-level loop, then this
|
||||
// is an entrance into a loop through the header, which is also ok.
|
||||
if (L->getHeader() == TI->getSuccessor(i) && L->getParentLoop() == 0)
|
||||
continue;
|
||||
|
||||
// Otherwise, this is an entrance into a loop from some place invalid.
|
||||
// Either the loop structure is invalid and this is not a natural loop (in
|
||||
// which case the compiler is buggy somewhere else) or BB is unreachable.
|
||||
BlockUnreachable = true;
|
||||
break;
|
||||
}
|
||||
|
||||
// If this block is ok, check the next one.
|
||||
if (!BlockUnreachable) continue;
|
||||
|
||||
// Otherwise, this block is dead. To clean up the CFG and to allow later
|
||||
// loop transformations to ignore this case, we delete the edges into the
|
||||
// loop by replacing the terminator.
|
||||
|
||||
// Remove PHI entries from the successors.
|
||||
for (unsigned i = 0, e = TI->getNumSuccessors(); i != e; ++i)
|
||||
TI->getSuccessor(i)->removePredecessor(BB);
|
||||
|
||||
// Add a new unreachable instruction.
|
||||
new UnreachableInst(TI);
|
||||
|
||||
// Delete the dead terminator.
|
||||
if (AA) AA->deleteValue(&BB->back());
|
||||
BB->getInstList().pop_back();
|
||||
Changed |= true;
|
||||
}
|
||||
|
||||
for (LoopInfo::iterator I = LI->begin(), E = LI->end(); I != E; ++I)
|
||||
Changed |= ProcessLoop(*I);
|
||||
|
||||
@ -121,38 +173,10 @@ bool LoopSimplify::ProcessLoop(Loop *L) {
|
||||
for (Loop::iterator I = L->begin(), E = L->end(); I != E; ++I)
|
||||
Changed |= ProcessLoop(*I);
|
||||
|
||||
// Check to see that no blocks (other than the header) in the loop have
|
||||
// predecessors that are not in the loop. This is not valid for natural
|
||||
// loops, but can occur if the blocks are unreachable. Since they are
|
||||
// unreachable we can just shamelessly destroy their terminators to make them
|
||||
// not branch into the loop!
|
||||
assert(L->getBlocks()[0] == L->getHeader() &&
|
||||
"Header isn't first block in loop?");
|
||||
for (unsigned i = 1, e = L->getBlocks().size(); i != e; ++i) {
|
||||
BasicBlock *LoopBB = L->getBlocks()[i];
|
||||
Retry:
|
||||
for (pred_iterator PI = pred_begin(LoopBB), E = pred_end(LoopBB);
|
||||
PI != E; ++PI)
|
||||
if (!L->contains(*PI)) {
|
||||
// This predecessor is not in the loop. Kill its terminator!
|
||||
BasicBlock *DeadBlock = *PI;
|
||||
for (succ_iterator SI = succ_begin(DeadBlock), E = succ_end(DeadBlock);
|
||||
SI != E; ++SI)
|
||||
(*SI)->removePredecessor(DeadBlock); // Remove PHI node entries
|
||||
|
||||
// Delete the dead terminator.
|
||||
if (AA) AA->deleteValue(&DeadBlock->back());
|
||||
DeadBlock->getInstList().pop_back();
|
||||
|
||||
Value *RetVal = 0;
|
||||
if (LoopBB->getParent()->getReturnType() != Type::VoidTy)
|
||||
RetVal = Constant::getNullValue(LoopBB->getParent()->getReturnType());
|
||||
new ReturnInst(RetVal, DeadBlock);
|
||||
goto Retry; // We just invalidated the pred_iterator. Retry.
|
||||
}
|
||||
}
|
||||
|
||||
// Does the loop already have a preheader? If so, don't modify the loop...
|
||||
// Does the loop already have a preheader? If so, don't insert one.
|
||||
if (L->getLoopPreheader() == 0) {
|
||||
InsertPreheaderForLoop(L);
|
||||
NumInserted++;
|
||||
|
Loading…
Reference in New Issue
Block a user