From: Sanjay Patel Date: Thu, 9 Aug 2018 18:42:12 +0000 (+0000) Subject: [InstCombine] allow fsub+fmul FMF folds for vectors X-Git-Url: http://review.tizen.org/git/?a=commitdiff_plain;h=55accd7dd38c2e18ba16d63cad232f447b4c8d4c;p=platform%2Fupstream%2Fllvm.git [InstCombine] allow fsub+fmul FMF folds for vectors llvm-svn: 339368 --- diff --git a/llvm/lib/Transforms/InstCombine/InstCombineAddSub.cpp b/llvm/lib/Transforms/InstCombine/InstCombineAddSub.cpp index 16e3d74..e339134 100644 --- a/llvm/lib/Transforms/InstCombine/InstCombineAddSub.cpp +++ b/llvm/lib/Transforms/InstCombine/InstCombineAddSub.cpp @@ -1914,6 +1914,17 @@ Instruction *InstCombiner::visitFSub(BinaryOperator &I) { if (match(Op1, m_c_FAdd(m_Specific(Op0), m_Value(X)))) return BinaryOperator::CreateFNegFMF(X, &I); + // (X * C) - X --> X * (C - 1.0) + if (match(Op0, m_FMul(m_Specific(Op1), m_Constant(C)))) { + Constant *CSubOne = ConstantExpr::getFSub(C, ConstantFP::get(Ty, 1.0)); + return BinaryOperator::CreateFMulFMF(Op1, CSubOne, &I); + } + // X - (X * C) --> X * (1.0 - C) + if (match(Op1, m_FMul(m_Specific(Op0), m_Constant(C)))) { + Constant *OneSubC = ConstantExpr::getFSub(ConstantFP::get(Ty, 1.0), C); + return BinaryOperator::CreateFMulFMF(Op0, OneSubC, &I); + } + // TODO: This performs reassociative folds for FP ops. Some fraction of the // functionality has been subsumed by simple pattern matching here and in // InstSimplify. We should let a dedicated reassociation pass handle more diff --git a/llvm/test/Transforms/InstCombine/fast-math.ll b/llvm/test/Transforms/InstCombine/fast-math.ll index 7b5b34e..8a0766d 100644 --- a/llvm/test/Transforms/InstCombine/fast-math.ll +++ b/llvm/test/Transforms/InstCombine/fast-math.ll @@ -442,8 +442,8 @@ define double @fail2(double %f1, double %f2) { define float @fsub_op0_fmul_const(float %x) { ; CHECK-LABEL: @fsub_op0_fmul_const( -; CHECK-NEXT: [[TMP1:%.*]] = fmul reassoc nsz float [[X:%.*]], 6.000000e+00 -; CHECK-NEXT: ret float [[TMP1]] +; CHECK-NEXT: [[SUB:%.*]] = fmul reassoc nsz float [[X:%.*]], 6.000000e+00 +; CHECK-NEXT: ret float [[SUB]] ; %mul = fmul float %x, 7.0 %sub = fsub reassoc nsz float %mul, %x @@ -454,8 +454,7 @@ define float @fsub_op0_fmul_const(float %x) { define <2 x float> @fsub_op0_fmul_const_vec(<2 x float> %x) { ; CHECK-LABEL: @fsub_op0_fmul_const_vec( -; CHECK-NEXT: [[MUL:%.*]] = fmul <2 x float> [[X:%.*]], -; CHECK-NEXT: [[SUB:%.*]] = fsub reassoc nsz <2 x float> [[MUL]], [[X]] +; CHECK-NEXT: [[SUB:%.*]] = fmul reassoc nsz <2 x float> [[X:%.*]], ; CHECK-NEXT: ret <2 x float> [[SUB]] ; %mul = fmul <2 x float> %x, @@ -467,8 +466,8 @@ define <2 x float> @fsub_op0_fmul_const_vec(<2 x float> %x) { define float @fsub_op1_fmul_const(float %x) { ; CHECK-LABEL: @fsub_op1_fmul_const( -; CHECK-NEXT: [[TMP1:%.*]] = fmul reassoc nsz float [[X:%.*]], -6.000000e+00 -; CHECK-NEXT: ret float [[TMP1]] +; CHECK-NEXT: [[SUB:%.*]] = fmul reassoc nsz float [[X:%.*]], -6.000000e+00 +; CHECK-NEXT: ret float [[SUB]] ; %mul = fmul float %x, 7.0 %sub = fsub reassoc nsz float %x, %mul @@ -479,8 +478,7 @@ define float @fsub_op1_fmul_const(float %x) { define <2 x float> @fsub_op1_fmul_const_vec(<2 x float> %x) { ; CHECK-LABEL: @fsub_op1_fmul_const_vec( -; CHECK-NEXT: [[MUL:%.*]] = fmul <2 x float> [[X:%.*]], -; CHECK-NEXT: [[SUB:%.*]] = fsub reassoc nsz <2 x float> [[X]], [[MUL]] +; CHECK-NEXT: [[SUB:%.*]] = fmul reassoc nsz <2 x float> [[X:%.*]], ; CHECK-NEXT: ret <2 x float> [[SUB]] ; %mul = fmul <2 x float> %x,