[llvm] [CGP] Reconstruct borrow chain from icmp pattern for subtract-with-carry (PR #189018)
Paweł Bylica via llvm-commits
llvm-commits at lists.llvm.org
Tue Apr 7 14:48:40 PDT 2026
================
@@ -1797,6 +1798,66 @@ bool CodeGenPrepare::combineToUSubWithOverflow(CmpInst *Cmp,
return true;
}
+/// FIXME: The name is similar to combineToUSubWithOverflow. Consider renaming
+/// one or both to better distinguish them.
+///
+/// Reconstruct a subtract-with-borrow chain from its canonicalized icmp form.
+///
+/// InstCombine simplifies chained usub.with.overflow intrinsics (used for
+/// multi-precision subtraction) into icmp patterns:
+/// carry_out = or(icmp ult A, B, and(icmp eq A, B, carry_in))
+///
+/// This is algebraically correct but prevents the backend from generating
+/// efficient subtract-with-borrow instructions (e.g. x86 sbb, aarch64 sbcs).
+///
+/// This function matches the pattern and reconstructs the chained
+/// usub.with.overflow form that the DAG combiner can lower to USUBO_CARRY.
+bool CodeGenPrepare::combineToUSubWithCarry(BinaryOperator *OrI) {
+ if (!OrI->getType()->isIntOrIntVectorTy(1))
+ return false;
+
+ assert(OrI->getOpcode() == Instruction::Or && "Expected or instruction");
+
+ // Match: or(icmp ult A, B, and(icmp eq A, B, carry_in))
+ // with all commuted variants of and and icmp eq operand order.
+ Value *A, *B, *CarryIn;
+ if (!match(
+ OrI,
+ m_c_BinOp(m_SpecificICmp(ICmpInst::ICMP_ULT, m_Value(A), m_Value(B)),
----------------
chfast wrote:
Fixed.
https://github.com/llvm/llvm-project/pull/189018
More information about the llvm-commits
mailing list