[PATCH] D136015: [InstCombine] Fold series of instructions into mull

Allen zhong via Phabricator via llvm-commits llvm-commits at lists.llvm.org
Sat Oct 15 05:01:17 PDT 2022


Allen created this revision.
Allen added reviewers: spatel, efriedma, bcl5980, RKSimon, nikic.
Herald added a subscriber: hiraditya.
Herald added a project: All.
Allen requested review of this revision.
Herald added a project: LLVM.
Herald added a subscriber: llvm-commits.

The following sequence should be folded into in0 * in1

  In0Lo = in0 & 0xffffffff; In0Hi = in0 >> 32;
  In1Lo = in1 & 0xffffffff; In1Hi = in1 >> 32;
  m01 = In1Hi * In0Lo; m10 = In1Lo * In0Hi; m00 = In1Lo * In0Lo;
  addc = m01 + m10;
  ResLo = m00 + (addc >> 32);


https://reviews.llvm.org/D136015

Files:
  llvm/lib/Transforms/InstCombine/InstCombineAddSub.cpp
  llvm/lib/Transforms/InstCombine/InstCombineInternal.h
  llvm/lib/Transforms/InstCombine/InstructionCombining.cpp
  llvm/test/Transforms/InstCombine/mul.ll


Index: llvm/test/Transforms/InstCombine/mul.ll
===================================================================
--- llvm/test/Transforms/InstCombine/mul.ll
+++ llvm/test/Transforms/InstCombine/mul.ll
@@ -1574,3 +1574,21 @@
   %r = mul i32 %zx, -16777216 ; -1 << 24
   ret i32 %r
 }
+
+define i64 @mul64_low(i64 noundef %in0, i64 noundef %in1) {
+; CHECK-LABEL: @mul64_low(
+; CHECK-NEXT:    [[TMP1:%.*]] = mul i64 [[IN0:%.*]], [[IN1:%.*]]
+; CHECK-NEXT:    ret i64 [[TMP1]]
+;
+  %In0Lo = and i64 %in0, 4294967295
+  %In0Hi = lshr i64 %in0, 32
+  %In1Lo = and i64 %in1, 4294967295
+  %In1Hi = lshr i64 %in1, 32
+  %m10 = mul i64 %In1Hi, %In0Lo
+  %m01 = mul i64 %In1Lo, %In0Hi
+  %m00 = mul i64 %In1Lo, %In0Lo
+  %addc = add i64 %m10, %m01
+  %shl = shl i64 %addc, 32
+  %addc9 = add i64 %shl, %m00
+  ret i64 %addc9
+}
Index: llvm/lib/Transforms/InstCombine/InstructionCombining.cpp
===================================================================
--- llvm/lib/Transforms/InstCombine/InstructionCombining.cpp
+++ llvm/lib/Transforms/InstCombine/InstructionCombining.cpp
@@ -852,6 +852,35 @@
   return SimplifySelectsFeedingBinaryOp(I, LHS, RHS);
 }
 
+Value *InstCombinerImpl::SimplifyMull(BinaryOperator &I) {
+  if (!(I.getType()->isIntegerTy() && I.getType()->getIntegerBitWidth() == 64))
+    return nullptr;
+
+  Value *In0, *In1;
+  Value *M01, *M10, *M00, *Addc;
+
+  // addc = m01 + m10;
+  // ResLo = m00 + (addc >> 32);
+  bool IsMulLow = match(&I, m_c_Add(m_Value(M00),
+                                    m_Shl(m_Value(Addc), m_SpecificInt(32)))) &&
+                  match(Addc, m_c_Add(m_Value(M01), m_Value(M10)));
+
+  // In0Lo = in0 & 0xffffffff; In0Hi = in0 >> 32;
+  // In1Lo = in1 & 0xffffffff; In1Hi = in1 >> 32;
+  // m01 = In1Hi * In0Lo; m10 = In1Lo * In0Hi; m00 = In1Lo * In0Lo;
+  if (IsMulLow &&
+      match(M00, m_c_Mul(m_c_And(m_Value(In1), m_SpecificInt(4294967295)),
+                         m_c_And(m_Value(In0), m_SpecificInt(4294967295)))) &&
+      match(M01, m_c_Mul(m_LShr(m_Specific(In1), m_SpecificInt(32)),
+                         m_Specific(In0))) &&
+      match(M10, m_c_Mul(m_LShr(m_Specific(In0), m_SpecificInt(32)),
+                         m_Specific(In1)))) {
+    return Builder.CreateMul(In0, In1);
+  }
+
+  return nullptr;
+}
+
 Value *InstCombinerImpl::SimplifySelectsFeedingBinaryOp(BinaryOperator &I,
                                                         Value *LHS,
                                                         Value *RHS) {
Index: llvm/lib/Transforms/InstCombine/InstCombineInternal.h
===================================================================
--- llvm/lib/Transforms/InstCombine/InstCombineInternal.h
+++ llvm/lib/Transforms/InstCombine/InstCombineInternal.h
@@ -546,6 +546,9 @@
   /// value, or null if it didn't simplify.
   Value *SimplifyUsingDistributiveLaws(BinaryOperator &I);
 
+  /// Tries to simplify a few sequence operations into MULL
+  Value *SimplifyMull(BinaryOperator &I);
+
   /// Tries to simplify add operations using the definition of remainder.
   ///
   /// The definition of remainder is X % C = X - (X / C ) * C. The add
Index: llvm/lib/Transforms/InstCombine/InstCombineAddSub.cpp
===================================================================
--- llvm/lib/Transforms/InstCombine/InstCombineAddSub.cpp
+++ llvm/lib/Transforms/InstCombine/InstCombineAddSub.cpp
@@ -1286,6 +1286,9 @@
   if (Value *V = SimplifyUsingDistributiveLaws(I))
     return replaceInstUsesWith(I, V);
 
+  if (Value *V = SimplifyMull(I))
+    return replaceInstUsesWith(I, V);
+
   if (Instruction *R = factorizeMathWithShlOps(I, Builder))
     return R;
 


-------------- next part --------------
A non-text attachment was scrubbed...
Name: D136015.468010.patch
Type: text/x-patch
Size: 3655 bytes
Desc: not available
URL: <http://lists.llvm.org/pipermail/llvm-commits/attachments/20221015/09e8e07e/attachment.bin>


More information about the llvm-commits mailing list