mirror of
https://github.com/c64scene-ar/llvm-6502.git
synced 2025-03-03 14:31:10 +00:00
Merge blocks like this:
void "test3"(bool %T) { br bool %T, label %BB1, label %BB1 BB1: ret void } git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@2472 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
parent
4c1061f58c
commit
cdac78b8a4
@ -231,43 +231,56 @@ bool SimplifyCFG(Function::iterator &BBIt) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Merge basic blocks into their predecessor if there is only one pred,
|
// Merge basic blocks into their predecessor if there is only one distinct
|
||||||
// and if there is only one successor of the predecessor.
|
// pred, and if there is only one distinct successor of the predecessor, and
|
||||||
pred_iterator PI(pred_begin(BB));
|
// if there are no PHI nodes.
|
||||||
if (PI != pred_end(BB) && *PI != BB && // Not empty? Not same BB?
|
//
|
||||||
++PI == pred_end(BB) && !BB->hasConstantReferences()) {
|
if (!isa<PHINode>(BB->front()) && !BB->hasConstantReferences()) {
|
||||||
BasicBlock *Pred = *pred_begin(BB);
|
pred_iterator PI(pred_begin(BB)), PE(pred_end(BB));
|
||||||
TerminatorInst *Term = Pred->getTerminator();
|
BasicBlock *OnlyPred = *PI++;
|
||||||
assert(Term != 0 && "malformed basic block without terminator!");
|
for (; PI != PE; ++PI) // Search all predecessors, see if they are all same
|
||||||
|
if (*PI != OnlyPred) {
|
||||||
// Does the predecessor block only have a single successor?
|
OnlyPred = 0; // There are multiple different predecessors...
|
||||||
succ_iterator SI(succ_begin(Pred));
|
break;
|
||||||
if (++SI == succ_end(Pred)) {
|
}
|
||||||
|
|
||||||
|
BasicBlock *OnlySucc = 0;
|
||||||
|
if (OnlyPred && OnlyPred != BB) { // Don't break self loops
|
||||||
|
// Check to see if there is only one distinct successor...
|
||||||
|
succ_iterator SI(succ_begin(OnlyPred)), SE(succ_end(OnlyPred));
|
||||||
|
OnlySucc = BB;
|
||||||
|
for (; SI != SE; ++SI)
|
||||||
|
if (*SI != OnlySucc) {
|
||||||
|
OnlySucc = 0; // There are multiple distinct successors!
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (OnlySucc) {
|
||||||
//cerr << "Merging: " << BB << "into: " << Pred;
|
//cerr << "Merging: " << BB << "into: " << Pred;
|
||||||
|
TerminatorInst *Term = OnlyPred->getTerminator();
|
||||||
// Delete the unconditianal branch from the predecessor...
|
|
||||||
BasicBlock::iterator DI = Pred->end();
|
// Delete the unconditional branch from the predecessor...
|
||||||
assert(Pred->getTerminator() &&
|
BasicBlock::iterator DI = OnlyPred->end();
|
||||||
"Degenerate basic block encountered!"); // Empty bb???
|
delete OnlyPred->getInstList().remove(--DI); // Destroy branch
|
||||||
delete Pred->getInstList().remove(--DI); // Destroy uncond branch
|
|
||||||
|
|
||||||
// Move all definitions in the succecessor to the predecessor...
|
// Move all definitions in the succecessor to the predecessor...
|
||||||
while (!BB->empty()) {
|
std::vector<Instruction*> Insts(BB->begin(), BB->end());
|
||||||
DI = BB->begin();
|
BB->getInstList().remove(BB->begin(), BB->end());
|
||||||
Instruction *Def = BB->getInstList().remove(DI); // Remove from front
|
OnlyPred->getInstList().insert(OnlyPred->end(),
|
||||||
Pred->getInstList().push_back(Def); // Add to end...
|
Insts.begin(), Insts.end());
|
||||||
}
|
|
||||||
|
|
||||||
// Remove basic block from the function... and advance iterator to the
|
// Remove basic block from the function... and advance iterator to the
|
||||||
// next valid block...
|
// next valid block...
|
||||||
BB = M->getBasicBlocks().remove(BBIt);
|
M->getBasicBlocks().remove(BBIt);
|
||||||
|
|
||||||
// Make all PHI nodes that refered to BB now refer to Pred as their
|
// Make all PHI nodes that refered to BB now refer to Pred as their
|
||||||
// source...
|
// source...
|
||||||
BB->replaceAllUsesWith(Pred);
|
BB->replaceAllUsesWith(OnlyPred);
|
||||||
|
|
||||||
// Inherit predecessors name if it exists...
|
// Inherit predecessors name if it exists...
|
||||||
if (BB->hasName() && !Pred->hasName()) Pred->setName(BB->getName());
|
if (BB->hasName() && !OnlyPred->hasName())
|
||||||
|
OnlyPred->setName(BB->getName());
|
||||||
|
|
||||||
delete BB; // You ARE the weakest link... goodbye
|
delete BB; // You ARE the weakest link... goodbye
|
||||||
return true;
|
return true;
|
||||||
|
Loading…
x
Reference in New Issue
Block a user