Please use GitHub pull requests for new patches. Phabricator shutdown timeline
Changeset View
Changeset View
Standalone View
Standalone View
llvm/lib/Transforms/Utils/SimplifyCFG.cpp
- This file is larger than 256 KB, so syntax highlighting is disabled by default.
Show First 20 Lines • Show All 6,607 Lines • ▼ Show 20 Lines | for (unsigned i = 0, e = PHI.getNumIncomingValues(); i != e; ++i) | ||||
Builder.CreateAssumption(Cond); | Builder.CreateAssumption(Cond); | ||||
Builder.CreateBr(BI->getSuccessor(0) == BB ? BI->getSuccessor(1) | Builder.CreateBr(BI->getSuccessor(0) == BB ? BI->getSuccessor(1) | ||||
: BI->getSuccessor(0)); | : BI->getSuccessor(0)); | ||||
} | } | ||||
BI->eraseFromParent(); | BI->eraseFromParent(); | ||||
if (DTU) | if (DTU) | ||||
DTU->applyUpdates({{DominatorTree::Delete, Predecessor, BB}}); | DTU->applyUpdates({{DominatorTree::Delete, Predecessor, BB}}); | ||||
return true; | return true; | ||||
} else if (SwitchInst *SI = dyn_cast<SwitchInst>(T)) { | |||||
// Create the new block in which will redirect the edges that | |||||
mkazantsev: "Create an unreachable block and redirect all edges going to BB into this block". | |||||
// lead to undefine behavior | |||||
Better Redirect all branches leading to UB into a newly created unreachable block. mkazantsev: Better
```
Redirect all branches leading to UB into a newly created unreachable block.
``` | |||||
BasicBlock *Unreachable = BasicBlock::Create( | |||||
Predecessor->getContext(), "unreachable", SI->getFunction()); | |||||
Builder.SetInsertPoint(Unreachable); | |||||
// The new block contains only one instruction: Unreachable | |||||
Builder.CreateUnreachable(); | |||||
for (auto &Case : SI->cases()) | |||||
if (Case.getCaseSuccessor() == BB) | |||||
Case.setSuccessor(Unreachable); | |||||
mkazantsevUnsubmitted Not Done ReplyInline ActionsInteresting follow-up can be done here. Imagine that after this is done, only one edge that doesn't go to unreachable remains. In this case, we can remove this switch and insert assume(switched_value == remained_case_value). Totally fine if it's a separate patch. mkazantsev: Interesting follow-up can be done here. Imagine that after this is done, only one edge that… | |||||
if (DTU) | |||||
DTU->applyUpdates( | |||||
{ { DominatorTree::Delete, Predecessor, BB }, | |||||
{ DominatorTree::Insert, Predecessor, Unreachable } }); | |||||
return true; | |||||
} | } | ||||
// TODO: SwitchInst. | |||||
} | } | ||||
return false; | return false; | ||||
} | } | ||||
Not Done ReplyInline ActionsIs the code clang-formatted? lebedev.ri: Is the code clang-formatted?
Let's for consistency always do `Insert` first. | |||||
bool SimplifyCFGOpt::simplifyOnceImpl(BasicBlock *BB) { | bool SimplifyCFGOpt::simplifyOnceImpl(BasicBlock *BB) { | ||||
bool Changed = false; | bool Changed = false; | ||||
assert(BB && BB->getParent() && "Block not embedded in function!"); | assert(BB && BB->getParent() && "Block not embedded in function!"); | ||||
assert(BB->getTerminator() && "Degenerate basic block encountered!"); | assert(BB->getTerminator() && "Degenerate basic block encountered!"); | ||||
// Remove basic blocks that have no predecessors (except the entry block)... | // Remove basic blocks that have no predecessors (except the entry block)... | ||||
// or that just have themself as a predecessor. These are unreachable. | // or that just have themself as a predecessor. These are unreachable. | ||||
▲ Show 20 Lines • Show All 100 Lines • Show Last 20 Lines |
"Create an unreachable block and redirect all edges going to BB into this block".