[llvm] [InstCombine] Fix #163110: Fold icmp (shl X, L), (add (shl Y, L), 1<<L) to icmp X, (Y + 1) (PR #165975)

Yingwei Zheng via llvm-commits llvm-commits at lists.llvm.org
Sun Jan 25 07:17:01 PST 2026


================
@@ -701,62 +725,73 @@ static Value *foldShiftedShift(BinaryOperator *InnerShift, unsigned OuterShAmt,
 
 /// When canEvaluateShifted() returns true for an expression, this function
 /// inserts the new computation that produces the shifted value.
-static Value *getShiftedValue(Value *V, unsigned NumBits, bool isLeftShift,
-                              InstCombinerImpl &IC, const DataLayout &DL) {
+Value *InstCombinerImpl::getShiftedValue(Value *V, unsigned NumBits,
+                                         unsigned ShiftOp) {
   // We can always evaluate constants shifted.
   if (Constant *C = dyn_cast<Constant>(V)) {
-    if (isLeftShift)
-      return IC.Builder.CreateShl(C, NumBits);
+    if (ShiftOp == Instruction::Shl)
+      return Builder.CreateShl(C, NumBits);
     else
-      return IC.Builder.CreateLShr(C, NumBits);
+      return Builder.CreateBinOp((Instruction::BinaryOps)ShiftOp, C,
+                                 ConstantInt::get(C->getType(), NumBits));
   }
 
   Instruction *I = cast<Instruction>(V);
-  IC.addToWorklist(I);
+  addToWorklist(I);
 
   switch (I->getOpcode()) {
   default: llvm_unreachable("Inconsistency with CanEvaluateShifted");
   case Instruction::And:
   case Instruction::Or:
   case Instruction::Xor:
     // Bitwise operators can all arbitrarily be arbitrarily evaluated shifted.
-    I->setOperand(
-        0, getShiftedValue(I->getOperand(0), NumBits, isLeftShift, IC, DL));
-    I->setOperand(
-        1, getShiftedValue(I->getOperand(1), NumBits, isLeftShift, IC, DL));
+    I->setOperand(0, getShiftedValue(I->getOperand(0), NumBits, ShiftOp));
+    I->setOperand(1, getShiftedValue(I->getOperand(1), NumBits, ShiftOp));
     return I;
 
   case Instruction::Shl:
-  case Instruction::LShr:
-    return foldShiftedShift(cast<BinaryOperator>(I), NumBits, isLeftShift,
-                            IC.Builder);
+  case Instruction::LShr: {
+    auto *OBO = dyn_cast<OverflowingBinaryOperator>(I);
+
+    if (OBO && match(I->getOperand(1), m_SpecificInt(NumBits))) {
----------------
dtcxzyw wrote:

Handle ashr inside the function `foldShiftedShift`.

https://github.com/llvm/llvm-project/pull/165975


More information about the llvm-commits mailing list