[llvm] [InstCombine] Fold `icmp pred X + K, Y -> icmp pred2 X, Y` if both X and Y is divisible by K (PR #147130)
Nikita Popov via llvm-commits
llvm-commits at lists.llvm.org
Sat Jul 5 00:32:35 PDT 2025
================
@@ -5278,66 +5287,62 @@ Instruction *InstCombinerImpl::foldICmpBinOp(ICmpInst &I,
return new ICmpInst(Pred, Y, Z);
}
- // icmp slt (A + -1), Op1 -> icmp sle A, Op1
- if (A && NoOp0WrapProblem && Pred == CmpInst::ICMP_SLT &&
- match(B, m_AllOnes()))
- return new ICmpInst(CmpInst::ICMP_SLE, A, Op1);
-
- // icmp sge (A + -1), Op1 -> icmp sgt A, Op1
- if (A && NoOp0WrapProblem && Pred == CmpInst::ICMP_SGE &&
- match(B, m_AllOnes()))
- return new ICmpInst(CmpInst::ICMP_SGT, A, Op1);
-
- // icmp sle (A + 1), Op1 -> icmp slt A, Op1
- if (A && NoOp0WrapProblem && Pred == CmpInst::ICMP_SLE && match(B, m_One()))
- return new ICmpInst(CmpInst::ICMP_SLT, A, Op1);
-
- // icmp sgt (A + 1), Op1 -> icmp sge A, Op1
- if (A && NoOp0WrapProblem && Pred == CmpInst::ICMP_SGT && match(B, m_One()))
- return new ICmpInst(CmpInst::ICMP_SGE, A, Op1);
+ if (ICmpInst::isRelational(Pred)) {
+ // Return if both X and Y is divisible by Z/-Z.
+ // TODO: Generalize to check if (X - Y) is divisible by Z/-Z.
+ auto ShareCommonDivisor = [&Q](Value *X, Value *Y, Value *Z,
+ bool IsNegative) -> bool {
+ const APInt *OffsetC;
+ if (!match(Z, m_APInt(OffsetC)))
+ return false;
- // icmp sgt Op0, (C + -1) -> icmp sge Op0, C
- if (C && NoOp1WrapProblem && Pred == CmpInst::ICMP_SGT &&
- match(D, m_AllOnes()))
- return new ICmpInst(CmpInst::ICMP_SGE, Op0, C);
+ // Fast path for Z == 1/-1.
+ if (IsNegative ? OffsetC->isAllOnes() : OffsetC->isOne())
+ return true;
----------------
nikic wrote:
Okay, I see you have a fast-path here, but I think isMultipleOf() should also handle it directly, for future users.
https://github.com/llvm/llvm-project/pull/147130
More information about the llvm-commits
mailing list