diff options
-rw-r--r-- | llvm/lib/Transforms/InstCombine/InstCombineAddSub.cpp | 5 | ||||
-rw-r--r-- | llvm/test/Transforms/InstCombine/fsub.ll | 44 |
2 files changed, 49 insertions, 0 deletions
diff --git a/llvm/lib/Transforms/InstCombine/InstCombineAddSub.cpp b/llvm/lib/Transforms/InstCombine/InstCombineAddSub.cpp index 05f34e9eaa0..e946acf84f5 100644 --- a/llvm/lib/Transforms/InstCombine/InstCombineAddSub.cpp +++ b/llvm/lib/Transforms/InstCombine/InstCombineAddSub.cpp @@ -794,6 +794,11 @@ unsigned FAddCombine::calcInstrNumber(const AddendVect &Opnds) { if (Opnd->isConstant()) continue; + // The constant check above is really for a few special constant + // coefficients. + if (isa<UndefValue>(Opnd->getSymVal())) + continue; + const FAddendCoef &CE = Opnd->getCoef(); if (CE.isMinusOne() || CE.isMinusTwo()) NegOpndNum++; diff --git a/llvm/test/Transforms/InstCombine/fsub.ll b/llvm/test/Transforms/InstCombine/fsub.ll index af2fadd2867..6b62f5dd7e3 100644 --- a/llvm/test/Transforms/InstCombine/fsub.ll +++ b/llvm/test/Transforms/InstCombine/fsub.ll @@ -21,3 +21,47 @@ define double @test2(double %x, double %y) nounwind { ret double %t2 } + +; CHECK-LABEL: @fsub_undef( +; CHECK: %sub = fsub float %val, undef +define float @fsub_undef(float %val) { +bb: + %sub = fsub float %val, undef + ret float %sub +} + +; XXX - Why doesn't this fold to undef? +; CHECK-LABEL: @fsub_fast_undef( +; CHCK: %sub = fsub fast float %val, undef +define float @fsub_fast_undef(float %val) { +bb: + %sub = fsub fast float %val, undef + ret float %sub +} + +; CHECK-LABEL: @fneg_undef( +; CHECK: ret float fsub (float -0.000000e+00, float undef) +define float @fneg_undef(float %val) { +bb: + %sub = fsub float -0.0, undef + ret float %sub +} + +; CHECK-LABEL: @fneg_fast_undef( +; CHECK: ret float fsub (float -0.000000e+00, float undef) +define float @fneg_fast_undef(float %val) { +bb: + %sub = fsub fast float -0.0, undef + ret float %sub +} + +; This folds to a constant expression, which produced 0 instructions +; contrary to the expected one for negation. +; CHECK-LABEL: @inconsistent_numbers_fsub_undef( +; CHECK: ret float fsub (float -0.000000e+00, float undef) +define float @inconsistent_numbers_fsub_undef(float %val) { +bb: + %sub0 = fsub fast float %val, undef + %sub1 = fsub fast float %sub0, %val + ret float %sub1 +} |