Skip to content

Commit bee7479

Browse files
committedAug 20, 2018
[InstCombine] Add splat vector constant support to foldICmpAddOpConst.
Differential Revision: https://reviews.llvm.org/D50946 llvm-svn: 340231
1 parent c2c33c8 commit bee7479

File tree

3 files changed

+62
-23
lines changed

3 files changed

+62
-23
lines changed
 

‎llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp

+18-16
Original file line numberDiff line numberDiff line change
@@ -1079,31 +1079,31 @@ Instruction *InstCombiner::foldAllocaCmp(ICmpInst &ICI,
10791079
ConstantInt::get(CmpTy, !CmpInst::isTrueWhenEqual(ICI.getPredicate())));
10801080
}
10811081

1082-
/// Fold "icmp pred (X+CI), X".
1083-
Instruction *InstCombiner::foldICmpAddOpConst(Value *X, ConstantInt *CI,
1082+
/// Fold "icmp pred (X+C), X".
1083+
Instruction *InstCombiner::foldICmpAddOpConst(Value *X, const APInt &C,
10841084
ICmpInst::Predicate Pred) {
10851085
// From this point on, we know that (X+C <= X) --> (X+C < X) because C != 0,
10861086
// so the values can never be equal. Similarly for all other "or equals"
10871087
// operators.
1088+
assert(!!C && "C should not be zero!");
10881089

10891090
// (X+1) <u X --> X >u (MAXUINT-1) --> X == 255
10901091
// (X+2) <u X --> X >u (MAXUINT-2) --> X > 253
10911092
// (X+MAXUINT) <u X --> X >u (MAXUINT-MAXUINT) --> X != 0
10921093
if (Pred == ICmpInst::ICMP_ULT || Pred == ICmpInst::ICMP_ULE) {
1093-
Value *R =
1094-
ConstantExpr::getSub(ConstantInt::getAllOnesValue(CI->getType()), CI);
1094+
Constant *R = ConstantInt::get(X->getType(),
1095+
APInt::getMaxValue(C.getBitWidth()) - C);
10951096
return new ICmpInst(ICmpInst::ICMP_UGT, X, R);
10961097
}
10971098

10981099
// (X+1) >u X --> X <u (0-1) --> X != 255
10991100
// (X+2) >u X --> X <u (0-2) --> X <u 254
11001101
// (X+MAXUINT) >u X --> X <u (0-MAXUINT) --> X <u 1 --> X == 0
11011102
if (Pred == ICmpInst::ICMP_UGT || Pred == ICmpInst::ICMP_UGE)
1102-
return new ICmpInst(ICmpInst::ICMP_ULT, X, ConstantExpr::getNeg(CI));
1103+
return new ICmpInst(ICmpInst::ICMP_ULT, X,
1104+
ConstantInt::get(X->getType(), -C));
11031105

1104-
unsigned BitWidth = CI->getType()->getPrimitiveSizeInBits();
1105-
ConstantInt *SMax = ConstantInt::get(X->getContext(),
1106-
APInt::getSignedMaxValue(BitWidth));
1106+
APInt SMax = APInt::getSignedMaxValue(C.getBitWidth());
11071107

11081108
// (X+ 1) <s X --> X >s (MAXSINT-1) --> X == 127
11091109
// (X+ 2) <s X --> X >s (MAXSINT-2) --> X >s 125
@@ -1112,7 +1112,8 @@ Instruction *InstCombiner::foldICmpAddOpConst(Value *X, ConstantInt *CI,
11121112
// (X+ -2) <s X --> X >s (MAXSINT- -2) --> X >s 126
11131113
// (X+ -1) <s X --> X >s (MAXSINT- -1) --> X != 127
11141114
if (Pred == ICmpInst::ICMP_SLT || Pred == ICmpInst::ICMP_SLE)
1115-
return new ICmpInst(ICmpInst::ICMP_SGT, X, ConstantExpr::getSub(SMax, CI));
1115+
return new ICmpInst(ICmpInst::ICMP_SGT, X,
1116+
ConstantInt::get(X->getType(), SMax - C));
11161117

11171118
// (X+ 1) >s X --> X <s (MAXSINT-(1-1)) --> X != 127
11181119
// (X+ 2) >s X --> X <s (MAXSINT-(2-1)) --> X <s 126
@@ -1122,8 +1123,8 @@ Instruction *InstCombiner::foldICmpAddOpConst(Value *X, ConstantInt *CI,
11221123
// (X+ -1) >s X --> X <s (MAXSINT-(-1-1)) --> X == -128
11231124

11241125
assert(Pred == ICmpInst::ICMP_SGT || Pred == ICmpInst::ICMP_SGE);
1125-
Constant *C = Builder.getInt(CI->getValue() - 1);
1126-
return new ICmpInst(ICmpInst::ICMP_SLT, X, ConstantExpr::getSub(SMax, C));
1126+
return new ICmpInst(ICmpInst::ICMP_SLT, X,
1127+
ConstantInt::get(X->getType(), SMax - (C - 1)));
11271128
}
11281129

11291130
/// Handle "(icmp eq/ne (ashr/lshr AP2, A), AP1)" ->
@@ -4877,14 +4878,15 @@ Instruction *InstCombiner::visitICmpInst(ICmpInst &I) {
48774878
return ExtractValueInst::Create(ACXI, 1);
48784879

48794880
{
4880-
Value *X; ConstantInt *Cst;
4881+
Value *X;
4882+
const APInt *C;
48814883
// icmp X+Cst, X
4882-
if (match(Op0, m_Add(m_Value(X), m_ConstantInt(Cst))) && Op1 == X)
4883-
return foldICmpAddOpConst(X, Cst, I.getPredicate());
4884+
if (match(Op0, m_Add(m_Value(X), m_APInt(C))) && Op1 == X)
4885+
return foldICmpAddOpConst(X, *C, I.getPredicate());
48844886

48854887
// icmp X, X+Cst
4886-
if (match(Op1, m_Add(m_Value(X), m_ConstantInt(Cst))) && Op0 == X)
4887-
return foldICmpAddOpConst(X, Cst, I.getSwappedPredicate());
4888+
if (match(Op1, m_Add(m_Value(X), m_APInt(C))) && Op0 == X)
4889+
return foldICmpAddOpConst(X, *C, I.getSwappedPredicate());
48884890
}
48894891

48904892
if (I.getType()->isVectorTy())

‎llvm/lib/Transforms/InstCombine/InstCombineInternal.h

+1-1
Original file line numberDiff line numberDiff line change
@@ -813,7 +813,7 @@ class LLVM_LIBRARY_VISIBILITY InstCombiner
813813
ConstantInt *AndCst = nullptr);
814814
Instruction *foldFCmpIntToFPConst(FCmpInst &I, Instruction *LHSI,
815815
Constant *RHSC);
816-
Instruction *foldICmpAddOpConst(Value *X, ConstantInt *CI,
816+
Instruction *foldICmpAddOpConst(Value *X, const APInt &C,
817817
ICmpInst::Predicate Pred);
818818
Instruction *foldICmpWithCastAndCast(ICmpInst &ICI);
819819

‎llvm/test/Transforms/InstCombine/icmp.ll

+43-6
Original file line numberDiff line numberDiff line change
@@ -101,8 +101,7 @@ define i1 @test7(i32 %x) {
101101

102102
define <2 x i1> @test7_vec(<2 x i32> %x) {
103103
; CHECK-LABEL: @test7_vec(
104-
; CHECK-NEXT: [[A:%.*]] = add <2 x i32> [[X:%.*]], <i32 -1, i32 -1>
105-
; CHECK-NEXT: [[B:%.*]] = icmp ult <2 x i32> [[A]], [[X]]
104+
; CHECK-NEXT: [[B:%.*]] = icmp ne <2 x i32> [[X:%.*]], zeroinitializer
106105
; CHECK-NEXT: ret <2 x i1> [[B]]
107106
;
108107
%a = add <2 x i32> %x, <i32 -1, i32 -1>
@@ -140,15 +139,34 @@ define i1 @test9(i32 %x) {
140139

141140
define <2 x i1> @test9_vec(<2 x i32> %x) {
142141
; CHECK-LABEL: @test9_vec(
143-
; CHECK-NEXT: [[A:%.*]] = add <2 x i32> [[X:%.*]], <i32 -2, i32 -2>
144-
; CHECK-NEXT: [[B:%.*]] = icmp ult <2 x i32> [[A]], [[X]]
142+
; CHECK-NEXT: [[B:%.*]] = icmp ugt <2 x i32> [[X:%.*]], <i32 1, i32 1>
145143
; CHECK-NEXT: ret <2 x i1> [[B]]
146144
;
147145
%a = add <2 x i32> %x, <i32 -2, i32 -2>
148146
%b = icmp ugt <2 x i32> %x, %a
149147
ret <2 x i1> %b
150148
}
151149

150+
define i1 @test9b(i32 %x) {
151+
; CHECK-LABEL: @test9b(
152+
; CHECK-NEXT: [[B:%.*]] = icmp ult i32 [[X:%.*]], 2
153+
; CHECK-NEXT: ret i1 [[B]]
154+
;
155+
%a = add i32 %x, -2
156+
%b = icmp ugt i32 %a, %x
157+
ret i1 %b
158+
}
159+
160+
define <2 x i1> @test9b_vec(<2 x i32> %x) {
161+
; CHECK-LABEL: @test9b_vec(
162+
; CHECK-NEXT: [[B:%.*]] = icmp ult <2 x i32> [[X:%.*]], <i32 2, i32 2>
163+
; CHECK-NEXT: ret <2 x i1> [[B]]
164+
;
165+
%a = add <2 x i32> %x, <i32 -2, i32 -2>
166+
%b = icmp ugt <2 x i32> %a, %x
167+
ret <2 x i1> %b
168+
}
169+
152170
define i1 @test10(i32 %x) {
153171
; CHECK-LABEL: @test10(
154172
; CHECK-NEXT: [[B:%.*]] = icmp ne i32 %x, -2147483648
@@ -161,15 +179,34 @@ define i1 @test10(i32 %x) {
161179

162180
define <2 x i1> @test10_vec(<2 x i32> %x) {
163181
; CHECK-LABEL: @test10_vec(
164-
; CHECK-NEXT: [[A:%.*]] = add <2 x i32> [[X:%.*]], <i32 -1, i32 -1>
165-
; CHECK-NEXT: [[B:%.*]] = icmp slt <2 x i32> [[A]], [[X]]
182+
; CHECK-NEXT: [[B:%.*]] = icmp ne <2 x i32> [[X:%.*]], <i32 -2147483648, i32 -2147483648>
166183
; CHECK-NEXT: ret <2 x i1> [[B]]
167184
;
168185
%a = add <2 x i32> %x, <i32 -1, i32 -1>
169186
%b = icmp slt <2 x i32> %a, %x
170187
ret <2 x i1> %b
171188
}
172189

190+
define i1 @test10b(i32 %x) {
191+
; CHECK-LABEL: @test10b(
192+
; CHECK-NEXT: [[B:%.*]] = icmp eq i32 [[X:%.*]], -2147483648
193+
; CHECK-NEXT: ret i1 [[B]]
194+
;
195+
%a = add i32 %x, -1
196+
%b = icmp sgt i32 %a, %x
197+
ret i1 %b
198+
}
199+
200+
define <2 x i1> @test10b_vec(<2 x i32> %x) {
201+
; CHECK-LABEL: @test10b_vec(
202+
; CHECK-NEXT: [[B:%.*]] = icmp eq <2 x i32> [[X:%.*]], <i32 -2147483648, i32 -2147483648>
203+
; CHECK-NEXT: ret <2 x i1> [[B]]
204+
;
205+
%a = add <2 x i32> %x, <i32 -1, i32 -1>
206+
%b = icmp sgt <2 x i32> %a, %x
207+
ret <2 x i1> %b
208+
}
209+
173210
define i1 @test11(i32 %x) {
174211
; CHECK-LABEL: @test11(
175212
; CHECK-NEXT: ret i1 true

0 commit comments

Comments
 (0)
Please sign in to comment.