[IndVars] Sharpen context in eliminateIVComparison

When eliminating comparisons, we can use common dominator of
all its users as context. This gives better results when ICMP is not
computed right before the branch that uses it.

Differential Revision: https://reviews.llvm.org/D98924
Reviewed By: lebedev.ri
This commit is contained in:
Max Kazantsev 2021-03-22 11:07:32 +07:00
parent fc36a511c6
commit 8fab9f824f
2 changed files with 7 additions and 6 deletions

View File

@ -281,8 +281,11 @@ void SimplifyIndvar::eliminateIVComparison(ICmpInst *ICmp, Value *IVOperand) {
// If the condition is always true or always false in the given context,
// replace it with a constant value.
// TODO: We can sharpen the context to common dominator of all ICmp's users.
if (auto Ev = SE->evaluatePredicateAt(Pred, S, X, ICmp)) {
SmallVector<Instruction *, 4> Users;
for (auto *U : ICmp->users())
Users.push_back(cast<Instruction>(U));
const Instruction *CtxI = findCommonDominator(Users, *DT);
if (auto Ev = SE->evaluatePredicateAt(Pred, S, X, CtxI)) {
ICmp->replaceAllUsesWith(ConstantInt::getBool(ICmp->getContext(), *Ev));
DeadInsts.emplace_back(ICmp);
LLVM_DEBUG(dbgs() << "INDVARS: Eliminated comparison: " << *ICmp << '\n');

View File

@ -1101,13 +1101,11 @@ define i32 @func_28(i32 %start) {
; CHECK: loop:
; CHECK-NEXT: [[IV:%.*]] = phi i32 [ [[START:%.*]], [[ENTRY:%.*]] ], [ [[IV_NEXT:%.*]], [[BACKEDGE:%.*]] ]
; CHECK-NEXT: [[C1:%.*]] = icmp ne i32 [[IV]], 0
; CHECK-NEXT: [[C2:%.*]] = icmp ne i32 [[IV]], 0
; CHECK-NEXT: [[C3:%.*]] = icmp ne i32 [[IV]], 0
; CHECK-NEXT: br i1 [[C1]], label [[CHECKED_1:%.*]], label [[FAIL:%.*]]
; CHECK: checked.1:
; CHECK-NEXT: br i1 [[C2]], label [[CHECKED_2:%.*]], label [[FAIL]]
; CHECK-NEXT: br i1 true, label [[CHECKED_2:%.*]], label [[FAIL]]
; CHECK: checked.2:
; CHECK-NEXT: br i1 [[C3]], label [[BACKEDGE]], label [[FAIL]]
; CHECK-NEXT: br i1 true, label [[BACKEDGE]], label [[FAIL]]
; CHECK: backedge:
; CHECK-NEXT: [[IV_NEXT]] = add i32 [[IV]], 758394
; CHECK-NEXT: [[LOOP_COND:%.*]] = call i1 @cond_func()