[PATCH] D132777: [InstCombine] Propagate the nuw for combine of add+mul
Allen zhong via Phabricator via llvm-commits
llvm-commits at lists.llvm.org
Sun Aug 28 03:37:35 PDT 2022
Allen updated this revision to Diff 456181.
Allen added a comment.
1. add new test case with only mull or add has nuw
2. add checking dyn_cast<BinaryOperator>(NewMul)
CHANGES SINCE LAST ACTION
https://reviews.llvm.org/D132777/new/
https://reviews.llvm.org/D132777
Files:
llvm/lib/Transforms/InstCombine/InstCombineMulDivRem.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
@@ -624,6 +624,53 @@
ret i32 %mul
}
+; Keep nuw flag in this change, https://alive2.llvm.org/ce/z/-Wowpk
+define i32 @add_mul_nuw(i32 %a) {
+; CHECK-LABEL: @add_mul_nuw(
+; CHECK-NEXT: [[TMP1:%.*]] = mul nuw i32 [[A:%.*]], 3
+; CHECK-NEXT: [[MUL:%.*]] = add nuw i32 [[TMP1]], 9
+; CHECK-NEXT: ret i32 [[MUL]]
+;
+ %add = add nuw i32 %a, 3
+ %mul = mul nuw i32 %add, 3
+ ret i32 %mul
+}
+
+; Don't propagate nsw flag in this change
+define i32 @add_mul_nsw(i32 %a) {
+; CHECK-LABEL: @add_mul_nsw(
+; CHECK-NEXT: [[TMP1:%.*]] = mul i32 [[A:%.*]], 3
+; CHECK-NEXT: [[MUL:%.*]] = add i32 [[TMP1]], 9
+; CHECK-NEXT: ret i32 [[MUL]]
+;
+ %add = add nsw i32 %a, 3
+ %mul = mul nsw i32 %add, 3
+ ret i32 %mul
+}
+
+; Only the add or only the mul has nuw, https://alive2.llvm.org/ce/z/vPwbEa
+define i32 @only_add_nuw(i32 %a) {
+; CHECK-LABEL: @only_add_nuw(
+; CHECK-NEXT: [[TMP1:%.*]] = mul i32 [[A:%.*]], 3
+; CHECK-NEXT: [[MUL:%.*]] = add i32 [[TMP1]], 9
+; CHECK-NEXT: ret i32 [[MUL]]
+;
+ %add = add nuw i32 %a, 3
+ %mul = mul i32 %add, 3
+ ret i32 %mul
+}
+
+define i32 @only_mul_nuw(i32 %a) {
+; CHECK-LABEL: @only_mul_nuw(
+; CHECK-NEXT: [[TMP1:%.*]] = mul i32 [[A:%.*]], 3
+; CHECK-NEXT: [[MUL:%.*]] = add i32 [[TMP1]], 9
+; CHECK-NEXT: ret i32 [[MUL]]
+;
+ %add = add i32 %a, 3
+ %mul = mul nuw i32 %add, 3
+ ret i32 %mul
+}
+
define <2 x i1> @test21(<2 x i1> %A, <2 x i1> %B) {
; CHECK-LABEL: @test21(
; CHECK-NEXT: [[C:%.*]] = and <2 x i1> [[A:%.*]], [[B:%.*]]
Index: llvm/lib/Transforms/InstCombine/InstCombineMulDivRem.cpp
===================================================================
--- llvm/lib/Transforms/InstCombine/InstCombineMulDivRem.cpp
+++ llvm/lib/Transforms/InstCombine/InstCombineMulDivRem.cpp
@@ -221,16 +221,23 @@
return replaceInstUsesWith(I, FoldedMul);
// Simplify mul instructions with a constant RHS.
- if (isa<Constant>(Op1)) {
- // Canonicalize (X+C1)*CI -> X*CI+C1*CI.
+ Constant *MulC;
+ if (match(Op1, m_ImmConstant(MulC))) {
+ // Canonicalize (X+C1)*MulC -> X*MulC+C1*MulC.
Value *X;
Constant *C1;
- if (match(Op0, m_OneUse(m_Add(m_Value(X), m_Constant(C1))))) {
- Value *Mul = Builder.CreateMul(C1, Op1);
- // Only go forward with the transform if C1*CI simplifies to a tidier
- // constant.
- if (!match(Mul, m_Mul(m_Value(), m_Value())))
- return BinaryOperator::CreateAdd(Builder.CreateMul(X, Op1), Mul);
+ if (match(Op0, m_OneUse(m_Add(m_Value(X), m_ImmConstant(C1))))) {
+ // C1*MulC simplifies to a tidier constant.
+ Value *NewC = Builder.CreateMul(C1, MulC);
+ auto *BOp0 = cast<BinaryOperator>(Op0);
+ Value *NewMul = Builder.CreateMul(X, MulC);
+ auto *BO = BinaryOperator::CreateAdd(NewMul, NewC);
+ if (I.hasNoUnsignedWrap() && BOp0->hasNoUnsignedWrap() &&
+ dyn_cast<BinaryOperator>(NewMul)) {
+ cast<BinaryOperator>(NewMul)->setHasNoUnsignedWrap();
+ BO->setHasNoUnsignedWrap();
+ }
+ return BO;
}
}
-------------- next part --------------
A non-text attachment was scrubbed...
Name: D132777.456181.patch
Type: text/x-patch
Size: 3251 bytes
Desc: not available
URL: <http://lists.llvm.org/pipermail/llvm-commits/attachments/20220828/4cf29e29/attachment.bin>
More information about the llvm-commits
mailing list