-
Notifications
You must be signed in to change notification settings - Fork 14.3k
[SCEV] Avoid unnecessary call to getExitingBlock() in computeExitLimit() #96188
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
[SCEV] Avoid unnecessary call to getExitingBlock() in computeExitLimit() #96188
Conversation
In `computeExitLimit()`, we use `getExitingBlock()` to check if loop has exactly one exiting block. Since `computeExitLimit()` is only used in `computeBackedgeTakenCount()`, and `getExitingBlocks()` is called to get all exiting blocks in `computeBackedgeTakenCount()`, we can simply check if loop has exactly one exiting block by checking if the number of exiting blocks equals 1 in `computeBackedgeTakenCount()` and pass it as an argument to `computeExitLimit()`. This change helps to improve the compile time for files containing large loops.
@llvm/pr-subscribers-llvm-analysis Author: Enna1 (Enna1) ChangesIn This change helps to improve the compile time for files containing large loops. Full diff: https://github.com/llvm/llvm-project/pull/96188.diff 2 Files Affected:
diff --git a/llvm/include/llvm/Analysis/ScalarEvolution.h b/llvm/include/llvm/Analysis/ScalarEvolution.h
index b273d118c4c76..67260ac4d8a9c 100644
--- a/llvm/include/llvm/Analysis/ScalarEvolution.h
+++ b/llvm/include/llvm/Analysis/ScalarEvolution.h
@@ -1766,6 +1766,7 @@ class ScalarEvolution {
/// this call will try to use a minimal set of SCEV predicates in order to
/// return an exact answer.
ExitLimit computeExitLimit(const Loop *L, BasicBlock *ExitingBlock,
+ bool ControlsOnlyExit,
bool AllowPredicates = false);
// Helper functions for computeExitLimitFromCond to avoid exponential time
diff --git a/llvm/lib/Analysis/ScalarEvolution.cpp b/llvm/lib/Analysis/ScalarEvolution.cpp
index 7d3e3f4fcd45d..2d88e35e67823 100644
--- a/llvm/lib/Analysis/ScalarEvolution.cpp
+++ b/llvm/lib/Analysis/ScalarEvolution.cpp
@@ -8775,6 +8775,7 @@ ScalarEvolution::computeBackedgeTakenCount(const Loop *L,
const SCEV *MustExitMaxBECount = nullptr;
const SCEV *MayExitMaxBECount = nullptr;
bool MustExitMaxOrZero = false;
+ bool IsOnlyExit = ExitingBlocks.size() == 1;
// Compute the ExitLimit for each loop exit. Use this to populate ExitCounts
// and compute maxBECount.
@@ -8792,7 +8793,7 @@ ScalarEvolution::computeBackedgeTakenCount(const Loop *L,
continue;
}
- ExitLimit EL = computeExitLimit(L, ExitBB, AllowPredicates);
+ ExitLimit EL = computeExitLimit(L, ExitBB, IsOnlyExit, AllowPredicates);
assert((AllowPredicates || EL.Predicates.empty()) &&
"Predicated exit limit when predicates are not allowed!");
@@ -8867,7 +8868,7 @@ ScalarEvolution::computeBackedgeTakenCount(const Loop *L,
ScalarEvolution::ExitLimit
ScalarEvolution::computeExitLimit(const Loop *L, BasicBlock *ExitingBlock,
- bool AllowPredicates) {
+ bool ControlsOnlyExit, bool AllowPredicates) {
assert(L->contains(ExitingBlock) && "Exit count for non-loop block?");
// If our exiting block does not dominate the latch, then its connection with
// loop's exit limit may be far from trivial.
@@ -8875,7 +8876,6 @@ ScalarEvolution::computeExitLimit(const Loop *L, BasicBlock *ExitingBlock,
if (!Latch || !DT.dominates(ExitingBlock, Latch))
return getCouldNotCompute();
- bool IsOnlyExit = (L->getExitingBlock() != nullptr);
Instruction *Term = ExitingBlock->getTerminator();
if (BranchInst *BI = dyn_cast<BranchInst>(Term)) {
assert(BI->isConditional() && "If unconditional, it can't be in loop!");
@@ -8884,8 +8884,7 @@ ScalarEvolution::computeExitLimit(const Loop *L, BasicBlock *ExitingBlock,
"It should have one successor in loop and one exit block!");
// Proceed to the next level to examine the exit condition expression.
return computeExitLimitFromCond(L, BI->getCondition(), ExitIfTrue,
- /*ControlsOnlyExit=*/IsOnlyExit,
- AllowPredicates);
+ ControlsOnlyExit, AllowPredicates);
}
if (SwitchInst *SI = dyn_cast<SwitchInst>(Term)) {
@@ -8898,9 +8897,7 @@ ScalarEvolution::computeExitLimit(const Loop *L, BasicBlock *ExitingBlock,
Exit = SBB;
}
assert(Exit && "Exiting block must have at least one exit");
- return computeExitLimitFromSingleExitSwitch(
- L, SI, Exit,
- /*ControlsOnlyExit=*/IsOnlyExit);
+ return computeExitLimitFromSingleExitSwitch(L, SI, Exit, ControlsOnlyExit);
}
return getCouldNotCompute();
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
LGTM
@@ -1766,6 +1766,7 @@ class ScalarEvolution { | |||
/// this call will try to use a minimal set of SCEV predicates in order to | |||
/// return an exact answer. | |||
ExitLimit computeExitLimit(const Loop *L, BasicBlock *ExitingBlock, | |||
bool ControlsOnlyExit, |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
bool ControlsOnlyExit, | |
bool IsOnlyExit, |
here and elsewhere. The APIs that use ControlsOnlyExit pass a (controlling) exit condition, using this here doesn't make a lot of sense.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thanks! done.
…t() (llvm#96188) In `computeExitLimit()`, we use `getExitingBlock()` to check if loop has exactly one exiting block. Since `computeExitLimit()` is only used in `computeBackedgeTakenCount()`, and `getExitingBlocks()` is called to get all exiting blocks in `computeBackedgeTakenCount()`, we can simply check if loop has exactly one exiting block by checking if the number of exiting blocks equals 1 in `computeBackedgeTakenCount()` and pass it as an argument to `computeExitLimit()`. This change helps to improve the compile time for files containing large loops.
In
computeExitLimit()
, we usegetExitingBlock()
to check if loop has exactly one exiting block.Since
computeExitLimit()
is only used incomputeBackedgeTakenCount()
, andgetExitingBlocks()
is called to get all exiting blocks incomputeBackedgeTakenCount()
, we can simply check if loop has exactly one exiting block by checking if the number of exiting blocks equals 1 incomputeBackedgeTakenCount()
and pass it as an argument tocomputeExitLimit()
.This change helps to improve the compile time for files containing large loops.