mirror of
https://github.com/RPCS3/llvm-mirror.git
synced 2024-11-22 02:33:06 +01:00
[CFG] Move reachable from entry checks into basic block variant
These checks are not specific to the instruction based variant of isPotentiallyReachable(), they are equally valid for the basic block based variant. Move them there, to make sure that switching between the instruction and basic block variants cannot introduce regressions.
This commit is contained in:
parent
a6e815c9bd
commit
fffdcaf76a
@ -77,9 +77,10 @@ bool isPotentiallyReachable(
|
||||
/// Determine whether there is a path from From to To within a single function.
|
||||
/// Returns false only if we can prove that once 'From' has been reached then
|
||||
/// 'To' can not be executed. Conservatively returns true.
|
||||
bool isPotentiallyReachable(const BasicBlock *From, const BasicBlock *To,
|
||||
const DominatorTree *DT = nullptr,
|
||||
const LoopInfo *LI = nullptr);
|
||||
bool isPotentiallyReachable(
|
||||
const BasicBlock *From, const BasicBlock *To,
|
||||
const SmallPtrSetImpl<BasicBlock *> *ExclusionSet = nullptr,
|
||||
const DominatorTree *DT = nullptr, const LoopInfo *LI = nullptr);
|
||||
|
||||
/// Determine whether there is at least one path from a block in
|
||||
/// 'Worklist' to 'StopBB', returning true if uncertain.
|
||||
|
@ -208,16 +208,29 @@ bool llvm::isPotentiallyReachableFromMany(
|
||||
return false;
|
||||
}
|
||||
|
||||
bool llvm::isPotentiallyReachable(const BasicBlock *A, const BasicBlock *B,
|
||||
const DominatorTree *DT, const LoopInfo *LI) {
|
||||
bool llvm::isPotentiallyReachable(
|
||||
const BasicBlock *A, const BasicBlock *B,
|
||||
const SmallPtrSetImpl<BasicBlock *> *ExclusionSet, const DominatorTree *DT,
|
||||
const LoopInfo *LI) {
|
||||
assert(A->getParent() == B->getParent() &&
|
||||
"This analysis is function-local!");
|
||||
|
||||
if (DT) {
|
||||
if (DT->isReachableFromEntry(A) && !DT->isReachableFromEntry(B))
|
||||
return false;
|
||||
if (!ExclusionSet || ExclusionSet->empty()) {
|
||||
if (A->isEntryBlock() && DT->isReachableFromEntry(B))
|
||||
return true;
|
||||
if (B->isEntryBlock() && DT->isReachableFromEntry(A))
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
SmallVector<BasicBlock*, 32> Worklist;
|
||||
Worklist.push_back(const_cast<BasicBlock*>(A));
|
||||
|
||||
return isPotentiallyReachableFromMany(Worklist, const_cast<BasicBlock *>(B),
|
||||
nullptr, DT, LI);
|
||||
ExclusionSet, DT, LI);
|
||||
}
|
||||
|
||||
bool llvm::isPotentiallyReachable(
|
||||
@ -227,8 +240,6 @@ bool llvm::isPotentiallyReachable(
|
||||
assert(A->getParent()->getParent() == B->getParent()->getParent() &&
|
||||
"This analysis is function-local!");
|
||||
|
||||
SmallVector<BasicBlock*, 32> Worklist;
|
||||
|
||||
if (A->getParent() == B->getParent()) {
|
||||
// The same block case is special because it's the only time we're looking
|
||||
// within a single block to see which instruction comes first. Once we
|
||||
@ -252,30 +263,18 @@ bool llvm::isPotentiallyReachable(
|
||||
return false;
|
||||
|
||||
// Otherwise, continue doing the normal per-BB CFG walk.
|
||||
SmallVector<BasicBlock*, 32> Worklist;
|
||||
Worklist.append(succ_begin(BB), succ_end(BB));
|
||||
|
||||
if (Worklist.empty()) {
|
||||
// We've proven that there's no path!
|
||||
return false;
|
||||
}
|
||||
} else {
|
||||
Worklist.push_back(const_cast<BasicBlock*>(A->getParent()));
|
||||
|
||||
return isPotentiallyReachableFromMany(
|
||||
Worklist, const_cast<BasicBlock *>(B->getParent()), ExclusionSet,
|
||||
DT, LI);
|
||||
}
|
||||
|
||||
if (DT) {
|
||||
if (DT->isReachableFromEntry(A->getParent()) &&
|
||||
!DT->isReachableFromEntry(B->getParent()))
|
||||
return false;
|
||||
if (!ExclusionSet || ExclusionSet->empty()) {
|
||||
if (A->getParent()->isEntryBlock() &&
|
||||
DT->isReachableFromEntry(B->getParent()))
|
||||
return true;
|
||||
if (B->getParent()->isEntryBlock() &&
|
||||
DT->isReachableFromEntry(A->getParent()))
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
return isPotentiallyReachableFromMany(
|
||||
Worklist, const_cast<BasicBlock *>(B->getParent()), ExclusionSet, DT, LI);
|
||||
return isPotentiallyReachable(
|
||||
A->getParent(), B->getParent(), ExclusionSet, DT, LI);
|
||||
}
|
||||
|
@ -1098,7 +1098,7 @@ Instruction *InstCombinerImpl::foldOpIntoPhi(Instruction &I, PHINode *PN) {
|
||||
// If the incoming non-constant value is in I's block, we will remove one
|
||||
// instruction, but insert another equivalent one, leading to infinite
|
||||
// instcombine.
|
||||
if (isPotentiallyReachable(I.getParent(), NonConstBB, &DT, LI))
|
||||
if (isPotentiallyReachable(I.getParent(), NonConstBB, nullptr, &DT, LI))
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user