From 3f364aa9081b305245963b3298c31aecbd2acdaf Mon Sep 17 00:00:00 2001 From: Craig Topper Date: Fri, 22 Sep 2017 19:54:15 +0000 Subject: [PATCH] [InstCombine] Add constant splat handling to one of the ICMP_SLT/SGT cases in foldICmpUsingKnownBits. llvm-svn: 314025 --- .../Transforms/InstCombine/InstCombineCompares.cpp | 11 +++--- llvm/test/Transforms/InstCombine/icmp-add.ll | 41 ++++++++++++++++++++-- 2 files changed, 44 insertions(+), 8 deletions(-) diff --git a/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp b/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp index cd59366..a9911f4 100644 --- a/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp +++ b/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp @@ -4247,10 +4247,10 @@ Instruction *InstCombiner::foldICmpUsingKnownBits(ICmpInst &I) { return replaceInstUsesWith(I, ConstantInt::getFalse(I.getType())); if (Op1Min == Op0Max) // A A != B if max(A) == min(B) return new ICmpInst(ICmpInst::ICMP_NE, Op0, Op1); - if (ConstantInt *CI = dyn_cast(Op1)) { - if (Op1Max == Op0Min + 1) // A A == C-1 if min(A)+1 == C + if (Op1Min == Op1Max) { // Constant RHS + if (Op1Min == Op0Min + 1) // A A == C-1 if min(A)+1 == C return new ICmpInst(ICmpInst::ICMP_EQ, Op0, - Builder.getInt(CI->getValue() - 1)); + ConstantInt::get(Op1->getType(), Op1Min - 1)); } break; case ICmpInst::ICMP_SGT: @@ -4258,13 +4258,12 @@ Instruction *InstCombiner::foldICmpUsingKnownBits(ICmpInst &I) { return replaceInstUsesWith(I, ConstantInt::getTrue(I.getType())); if (Op0Max.sle(Op1Min)) // A >s B -> false if max(A) <= min(B) return replaceInstUsesWith(I, ConstantInt::getFalse(I.getType())); - if (Op1Max == Op0Min) // A >s B -> A != B if min(A) == max(B) return new ICmpInst(ICmpInst::ICMP_NE, Op0, Op1); - if (ConstantInt *CI = dyn_cast(Op1)) { + if (Op1Min == Op1Max) { // Constant RHS if (Op1Min == Op0Max - 1) // A >s C -> A == C+1 if max(A)-1 == C return new ICmpInst(ICmpInst::ICMP_EQ, Op0, - Builder.getInt(CI->getValue() + 1)); + ConstantInt::get(Op1->getType(), Op1Min + 1)); } break; case ICmpInst::ICMP_SGE: diff --git a/llvm/test/Transforms/InstCombine/icmp-add.ll b/llvm/test/Transforms/InstCombine/icmp-add.ll index efeb9d5..c9e1371 100644 --- a/llvm/test/Transforms/InstCombine/icmp-add.ll +++ b/llvm/test/Transforms/InstCombine/icmp-add.ll @@ -96,6 +96,16 @@ define i1 @nsw_slt1(i8 %a) { ret i1 %c } +define <2 x i1> @nsw_slt1_splat_vec(<2 x i8> %a) { +; CHECK-LABEL: @nsw_slt1_splat_vec( +; CHECK-NEXT: [[C:%.*]] = icmp eq <2 x i8> [[A:%.*]], +; CHECK-NEXT: ret <2 x i1> [[C]] +; + %b = add nsw <2 x i8> %a, + %c = icmp slt <2 x i8> %b, + ret <2 x i1> %c +} + ; icmp Pred (add nsw X, C2), C --> icmp Pred X, (C - C2), when C - C2 does not overflow. ; This becomes equality because it's at the limit. @@ -109,6 +119,16 @@ define i1 @nsw_slt2(i8 %a) { ret i1 %c } +define <2 x i1> @nsw_slt2_splat_vec(<2 x i8> %a) { +; CHECK-LABEL: @nsw_slt2_splat_vec( +; CHECK-NEXT: [[C:%.*]] = icmp ne <2 x i8> [[A:%.*]], +; CHECK-NEXT: ret <2 x i1> [[C]] +; + %b = add nsw <2 x i8> %a, + %c = icmp slt <2 x i8> %b, + ret <2 x i1> %c +} + ; icmp Pred (add nsw X, C2), C --> icmp Pred X, (C - C2), when C - C2 does not overflow. ; Less than the limit, so the predicate doesn't change. @@ -148,9 +168,26 @@ define i1 @nsw_sgt1(i8 %a) { ret i1 %c } -; icmp Pred (add nsw X, C2), C --> icmp Pred X, (C - C2), when C - C2 does not overflow. -; Try a vector type to make sure that works too. ; FIXME: This should be 'eq 127' as above. +define <2 x i1> @nsw_sgt1_splat_vec(<2 x i8> %a) { +; CHECK-LABEL: @nsw_sgt1_splat_vec( +; CHECK-NEXT: [[C:%.*]] = icmp eq <2 x i8> [[A:%.*]], +; CHECK-NEXT: ret <2 x i1> [[C]] +; + %b = add nsw <2 x i8> %a, + %c = icmp sgt <2 x i8> %b, + ret <2 x i1> %c +} + +define i1 @nsw_sgt2(i8 %a) { +; CHECK-LABEL: @nsw_sgt2( +; CHECK-NEXT: [[C:%.*]] = icmp sgt i8 [[A:%.*]], -126 +; CHECK-NEXT: ret i1 [[C]] +; + %b = add nsw i8 %a, 100 + %c = icmp sgt i8 %b, -26 + ret i1 %c +} define <2 x i1> @nsw_sgt2_splat_vec(<2 x i8> %a) { ; CHECK-LABEL: @nsw_sgt2_splat_vec( -- 2.7.4