Skip to content

Commit 0f3a9ef

Browse files
committed
[InstCombine] Add tests for transforming (icmp eq/ne trunc(x), truncOrZext(y)); NFC
1 parent ed7c97e commit 0f3a9ef

File tree

1 file changed

+280
-0
lines changed

1 file changed

+280
-0
lines changed
Lines changed: 280 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,280 @@
1+
; NOTE: Assertions have been autogenerated by utils/update_test_checks.py
2+
; RUN: opt -S -passes=instcombine < %s | FileCheck %s
3+
4+
declare void @llvm.assume(i1)
5+
declare void @use(i16)
6+
define i1 @icmp_trunc_x_trunc_y(i32 %x, i32 %y) {
7+
; CHECK-LABEL: @icmp_trunc_x_trunc_y(
8+
; CHECK-NEXT: [[X_LB_ONLY:%.*]] = icmp ult i32 [[X:%.*]], 65536
9+
; CHECK-NEXT: [[Y_LB_ONLY:%.*]] = icmp ult i32 [[Y:%.*]], 65536
10+
; CHECK-NEXT: call void @llvm.assume(i1 [[X_LB_ONLY]])
11+
; CHECK-NEXT: call void @llvm.assume(i1 [[Y_LB_ONLY]])
12+
; CHECK-NEXT: [[X16:%.*]] = trunc i32 [[X]] to i16
13+
; CHECK-NEXT: [[Y16:%.*]] = trunc i32 [[Y]] to i16
14+
; CHECK-NEXT: [[R:%.*]] = icmp eq i16 [[X16]], [[Y16]]
15+
; CHECK-NEXT: ret i1 [[R]]
16+
;
17+
%x_lb_only = icmp ult i32 %x, 65536
18+
%y_lb_only = icmp ult i32 %y, 65536
19+
call void @llvm.assume(i1 %x_lb_only)
20+
call void @llvm.assume(i1 %y_lb_only)
21+
%x16 = trunc i32 %x to i16
22+
%y16 = trunc i32 %y to i16
23+
%r = icmp eq i16 %x16, %y16
24+
ret i1 %r
25+
}
26+
27+
define i1 @icmp_trunc_x_trunc_y_fail_from_illegal1(i256 %x, i256 %y) {
28+
; CHECK-LABEL: @icmp_trunc_x_trunc_y_fail_from_illegal1(
29+
; CHECK-NEXT: [[X_LB_ONLY:%.*]] = icmp ult i256 [[X:%.*]], 65536
30+
; CHECK-NEXT: [[Y_LB_ONLY:%.*]] = icmp ult i256 [[Y:%.*]], 65536
31+
; CHECK-NEXT: call void @llvm.assume(i1 [[X_LB_ONLY]])
32+
; CHECK-NEXT: call void @llvm.assume(i1 [[Y_LB_ONLY]])
33+
; CHECK-NEXT: [[X16:%.*]] = trunc i256 [[X]] to i16
34+
; CHECK-NEXT: [[Y16:%.*]] = trunc i256 [[Y]] to i16
35+
; CHECK-NEXT: [[R:%.*]] = icmp eq i16 [[X16]], [[Y16]]
36+
; CHECK-NEXT: ret i1 [[R]]
37+
;
38+
%x_lb_only = icmp ult i256 %x, 65536
39+
%y_lb_only = icmp ult i256 %y, 65536
40+
call void @llvm.assume(i1 %x_lb_only)
41+
call void @llvm.assume(i1 %y_lb_only)
42+
%x16 = trunc i256 %x to i16
43+
%y16 = trunc i256 %y to i16
44+
%r = icmp eq i16 %x16, %y16
45+
ret i1 %r
46+
}
47+
48+
define i1 @icmp_trunc_x_trunc_y_illegal_trunc_to_legal_anyways(i123 %x, i32 %y) {
49+
; CHECK-LABEL: @icmp_trunc_x_trunc_y_illegal_trunc_to_legal_anyways(
50+
; CHECK-NEXT: [[X_LB_ONLY:%.*]] = icmp ult i123 [[X:%.*]], 65536
51+
; CHECK-NEXT: [[Y_LB_ONLY:%.*]] = icmp ult i32 [[Y:%.*]], 65536
52+
; CHECK-NEXT: call void @llvm.assume(i1 [[X_LB_ONLY]])
53+
; CHECK-NEXT: call void @llvm.assume(i1 [[Y_LB_ONLY]])
54+
; CHECK-NEXT: [[X16:%.*]] = trunc i123 [[X]] to i16
55+
; CHECK-NEXT: [[Y16:%.*]] = trunc i32 [[Y]] to i16
56+
; CHECK-NEXT: [[R:%.*]] = icmp eq i16 [[X16]], [[Y16]]
57+
; CHECK-NEXT: ret i1 [[R]]
58+
;
59+
%x_lb_only = icmp ult i123 %x, 65536
60+
%y_lb_only = icmp ult i32 %y, 65536
61+
call void @llvm.assume(i1 %x_lb_only)
62+
call void @llvm.assume(i1 %y_lb_only)
63+
%x16 = trunc i123 %x to i16
64+
%y16 = trunc i32 %y to i16
65+
%r = icmp eq i16 %x16, %y16
66+
ret i1 %r
67+
}
68+
69+
define i1 @icmp_trunc_x_trunc_y_2_illegal_anyways(i33 %x, i63 %y) {
70+
; CHECK-LABEL: @icmp_trunc_x_trunc_y_2_illegal_anyways(
71+
; CHECK-NEXT: [[X_LB_ONLY:%.*]] = icmp ult i33 [[X:%.*]], 512
72+
; CHECK-NEXT: [[Y_LB_ONLY:%.*]] = icmp ult i63 [[Y:%.*]], 512
73+
; CHECK-NEXT: call void @llvm.assume(i1 [[X_LB_ONLY]])
74+
; CHECK-NEXT: call void @llvm.assume(i1 [[Y_LB_ONLY]])
75+
; CHECK-NEXT: [[X16:%.*]] = trunc i33 [[X]] to i9
76+
; CHECK-NEXT: [[Y16:%.*]] = trunc i63 [[Y]] to i9
77+
; CHECK-NEXT: [[R:%.*]] = icmp ult i9 [[Y16]], [[X16]]
78+
; CHECK-NEXT: ret i1 [[R]]
79+
;
80+
%x_lb_only = icmp ult i33 %x, 512
81+
%y_lb_only = icmp ult i63 %y, 512
82+
call void @llvm.assume(i1 %x_lb_only)
83+
call void @llvm.assume(i1 %y_lb_only)
84+
%x16 = trunc i33 %x to i9
85+
%y16 = trunc i63 %y to i9
86+
%r = icmp ult i9 %y16, %x16
87+
ret i1 %r
88+
}
89+
90+
define i1 @icmp_trunc_x_trunc_y_3(i64 %x, i32 %y) {
91+
; CHECK-LABEL: @icmp_trunc_x_trunc_y_3(
92+
; CHECK-NEXT: [[X_LB_ONLY:%.*]] = icmp ult i64 [[X:%.*]], 123
93+
; CHECK-NEXT: [[Y_LB_ONLY:%.*]] = icmp ult i32 [[Y:%.*]], 256
94+
; CHECK-NEXT: call void @llvm.assume(i1 [[X_LB_ONLY]])
95+
; CHECK-NEXT: call void @llvm.assume(i1 [[Y_LB_ONLY]])
96+
; CHECK-NEXT: [[XI8:%.*]] = trunc i64 [[X]] to i8
97+
; CHECK-NEXT: [[YI8:%.*]] = trunc i32 [[Y]] to i8
98+
; CHECK-NEXT: [[R:%.*]] = icmp ule i8 [[YI8]], [[XI8]]
99+
; CHECK-NEXT: ret i1 [[R]]
100+
;
101+
%x_lb_only = icmp ult i64 %x, 123
102+
%y_lb_only = icmp ult i32 %y, 256
103+
call void @llvm.assume(i1 %x_lb_only)
104+
call void @llvm.assume(i1 %y_lb_only)
105+
%xi8 = trunc i64 %x to i8
106+
%yi8 = trunc i32 %y to i8
107+
%r = icmp ule i8 %yi8, %xi8
108+
ret i1 %r
109+
}
110+
111+
define i1 @icmp_trunc_x_trunc_y_fail_maybe_dirty_upper(i32 %x, i32 %y) {
112+
; CHECK-LABEL: @icmp_trunc_x_trunc_y_fail_maybe_dirty_upper(
113+
; CHECK-NEXT: [[X_LB_ONLY:%.*]] = icmp ult i32 [[X:%.*]], 65536
114+
; CHECK-NEXT: [[Y_LB_ONLY:%.*]] = icmp ult i32 [[Y:%.*]], 65537
115+
; CHECK-NEXT: call void @llvm.assume(i1 [[X_LB_ONLY]])
116+
; CHECK-NEXT: call void @llvm.assume(i1 [[Y_LB_ONLY]])
117+
; CHECK-NEXT: [[X16:%.*]] = trunc i32 [[X]] to i16
118+
; CHECK-NEXT: [[Y16:%.*]] = trunc i32 [[Y]] to i16
119+
; CHECK-NEXT: [[R:%.*]] = icmp ne i16 [[X16]], [[Y16]]
120+
; CHECK-NEXT: ret i1 [[R]]
121+
;
122+
%x_lb_only = icmp ult i32 %x, 65536
123+
%y_lb_only = icmp ult i32 %y, 65537
124+
call void @llvm.assume(i1 %x_lb_only)
125+
call void @llvm.assume(i1 %y_lb_only)
126+
%x16 = trunc i32 %x to i16
127+
%y16 = trunc i32 %y to i16
128+
%r = icmp ne i16 %x16, %y16
129+
ret i1 %r
130+
}
131+
132+
define i1 @icmp_trunc_x_trunc_y_fail_maybe_dirty_upper_2(i32 %x, i32 %y) {
133+
; CHECK-LABEL: @icmp_trunc_x_trunc_y_fail_maybe_dirty_upper_2(
134+
; CHECK-NEXT: [[X_LB_ONLY:%.*]] = icmp slt i32 [[X:%.*]], 65536
135+
; CHECK-NEXT: [[Y_LB_ONLY:%.*]] = icmp ult i32 [[Y:%.*]], 65536
136+
; CHECK-NEXT: call void @llvm.assume(i1 [[X_LB_ONLY]])
137+
; CHECK-NEXT: call void @llvm.assume(i1 [[Y_LB_ONLY]])
138+
; CHECK-NEXT: [[X16:%.*]] = trunc i32 [[X]] to i16
139+
; CHECK-NEXT: [[Y16:%.*]] = trunc i32 [[Y]] to i16
140+
; CHECK-NEXT: [[R:%.*]] = icmp ne i16 [[X16]], [[Y16]]
141+
; CHECK-NEXT: ret i1 [[R]]
142+
;
143+
%x_lb_only = icmp slt i32 %x, 65536
144+
%y_lb_only = icmp ult i32 %y, 65536
145+
call void @llvm.assume(i1 %x_lb_only)
146+
call void @llvm.assume(i1 %y_lb_only)
147+
%x16 = trunc i32 %x to i16
148+
%y16 = trunc i32 %y to i16
149+
%r = icmp ne i16 %x16, %y16
150+
ret i1 %r
151+
}
152+
153+
define i1 @icmp_trunc_x_trunc_y_swap0(i33 %x, i32 %y) {
154+
; CHECK-LABEL: @icmp_trunc_x_trunc_y_swap0(
155+
; CHECK-NEXT: [[X_LB_ONLY:%.*]] = icmp ult i33 [[X:%.*]], 65536
156+
; CHECK-NEXT: [[Y_LB_ONLY:%.*]] = icmp ult i32 [[Y:%.*]], 65536
157+
; CHECK-NEXT: call void @llvm.assume(i1 [[X_LB_ONLY]])
158+
; CHECK-NEXT: call void @llvm.assume(i1 [[Y_LB_ONLY]])
159+
; CHECK-NEXT: [[X16:%.*]] = trunc i33 [[X]] to i16
160+
; CHECK-NEXT: [[Y16:%.*]] = trunc i32 [[Y]] to i16
161+
; CHECK-NEXT: [[R:%.*]] = icmp ule i16 [[X16]], [[Y16]]
162+
; CHECK-NEXT: ret i1 [[R]]
163+
;
164+
%x_lb_only = icmp ult i33 %x, 65536
165+
%y_lb_only = icmp ult i32 %y, 65536
166+
call void @llvm.assume(i1 %x_lb_only)
167+
call void @llvm.assume(i1 %y_lb_only)
168+
%x16 = trunc i33 %x to i16
169+
%y16 = trunc i32 %y to i16
170+
%r = icmp ule i16 %x16, %y16
171+
ret i1 %r
172+
}
173+
174+
define i1 @icmp_trunc_x_trunc_y_swap1(i33 %x, i32 %y) {
175+
; CHECK-LABEL: @icmp_trunc_x_trunc_y_swap1(
176+
; CHECK-NEXT: [[X_LB_ONLY:%.*]] = icmp ult i33 [[X:%.*]], 65536
177+
; CHECK-NEXT: [[Y_LB_ONLY:%.*]] = icmp ult i32 [[Y:%.*]], 65536
178+
; CHECK-NEXT: call void @llvm.assume(i1 [[X_LB_ONLY]])
179+
; CHECK-NEXT: call void @llvm.assume(i1 [[Y_LB_ONLY]])
180+
; CHECK-NEXT: [[X16:%.*]] = trunc i33 [[X]] to i16
181+
; CHECK-NEXT: [[Y16:%.*]] = trunc i32 [[Y]] to i16
182+
; CHECK-NEXT: [[R:%.*]] = icmp ule i16 [[Y16]], [[X16]]
183+
; CHECK-NEXT: ret i1 [[R]]
184+
;
185+
%x_lb_only = icmp ult i33 %x, 65536
186+
%y_lb_only = icmp ult i32 %y, 65536
187+
call void @llvm.assume(i1 %x_lb_only)
188+
call void @llvm.assume(i1 %y_lb_only)
189+
%x16 = trunc i33 %x to i16
190+
%y16 = trunc i32 %y to i16
191+
%r = icmp ule i16 %y16, %x16
192+
ret i1 %r
193+
}
194+
195+
define i1 @icmp_trunc_x_zext_y(i32 %x, i8 %y) {
196+
; CHECK-LABEL: @icmp_trunc_x_zext_y(
197+
; CHECK-NEXT: [[X_LB_ONLY:%.*]] = icmp ult i32 [[X:%.*]], 65536
198+
; CHECK-NEXT: call void @llvm.assume(i1 [[X_LB_ONLY]])
199+
; CHECK-NEXT: [[X16:%.*]] = trunc i32 [[X]] to i16
200+
; CHECK-NEXT: [[Y16:%.*]] = zext i8 [[Y:%.*]] to i16
201+
; CHECK-NEXT: [[R:%.*]] = icmp ugt i16 [[X16]], [[Y16]]
202+
; CHECK-NEXT: ret i1 [[R]]
203+
;
204+
%x_lb_only = icmp ult i32 %x, 65536
205+
call void @llvm.assume(i1 %x_lb_only)
206+
%x16 = trunc i32 %x to i16
207+
%y16 = zext i8 %y to i16
208+
%r = icmp ugt i16 %x16, %y16
209+
ret i1 %r
210+
}
211+
212+
define i1 @icmp_trunc_x_zext_y_2(i32 %x, i8 %y) {
213+
; CHECK-LABEL: @icmp_trunc_x_zext_y_2(
214+
; CHECK-NEXT: [[X_LB_ONLY:%.*]] = icmp ult i32 [[X:%.*]], 65536
215+
; CHECK-NEXT: call void @llvm.assume(i1 [[X_LB_ONLY]])
216+
; CHECK-NEXT: [[X16:%.*]] = trunc i32 [[X]] to i16
217+
; CHECK-NEXT: [[Y16:%.*]] = zext i8 [[Y:%.*]] to i16
218+
; CHECK-NEXT: [[R:%.*]] = icmp uge i16 [[Y16]], [[X16]]
219+
; CHECK-NEXT: ret i1 [[R]]
220+
;
221+
%x_lb_only = icmp ult i32 %x, 65536
222+
call void @llvm.assume(i1 %x_lb_only)
223+
%x16 = trunc i32 %x to i16
224+
%y16 = zext i8 %y to i16
225+
%r = icmp uge i16 %y16, %x16
226+
ret i1 %r
227+
}
228+
229+
define i1 @icmp_trunc_x_zext_y_3(i6 %x, i32 %y) {
230+
; CHECK-LABEL: @icmp_trunc_x_zext_y_3(
231+
; CHECK-NEXT: [[Y_LB_ONLY:%.*]] = icmp ult i32 [[Y:%.*]], 65536
232+
; CHECK-NEXT: call void @llvm.assume(i1 [[Y_LB_ONLY]])
233+
; CHECK-NEXT: [[X16:%.*]] = zext i6 [[X:%.*]] to i16
234+
; CHECK-NEXT: [[Y16:%.*]] = trunc i32 [[Y]] to i16
235+
; CHECK-NEXT: [[R:%.*]] = icmp ne i16 [[Y16]], [[X16]]
236+
; CHECK-NEXT: ret i1 [[R]]
237+
;
238+
%y_lb_only = icmp ult i32 %y, 65536
239+
call void @llvm.assume(i1 %y_lb_only)
240+
%x16 = zext i6 %x to i16
241+
%y16 = trunc i32 %y to i16
242+
%r = icmp ne i16 %y16, %x16
243+
ret i1 %r
244+
}
245+
246+
define i1 @icmp_trunc_x_zext_y_3_fail_illegal(i6 %x, i45 %y) {
247+
; CHECK-LABEL: @icmp_trunc_x_zext_y_3_fail_illegal(
248+
; CHECK-NEXT: [[Y_LB_ONLY:%.*]] = icmp ult i45 [[Y:%.*]], 65536
249+
; CHECK-NEXT: call void @llvm.assume(i1 [[Y_LB_ONLY]])
250+
; CHECK-NEXT: [[X16:%.*]] = zext i6 [[X:%.*]] to i16
251+
; CHECK-NEXT: [[Y16:%.*]] = trunc i45 [[Y]] to i16
252+
; CHECK-NEXT: [[R:%.*]] = icmp ne i16 [[Y16]], [[X16]]
253+
; CHECK-NEXT: ret i1 [[R]]
254+
;
255+
%y_lb_only = icmp ult i45 %y, 65536
256+
call void @llvm.assume(i1 %y_lb_only)
257+
%x16 = zext i6 %x to i16
258+
%y16 = trunc i45 %y to i16
259+
%r = icmp ne i16 %y16, %x16
260+
ret i1 %r
261+
}
262+
263+
define i1 @icmp_trunc_x_zext_y_fail_multiuse(i32 %x, i8 %y) {
264+
; CHECK-LABEL: @icmp_trunc_x_zext_y_fail_multiuse(
265+
; CHECK-NEXT: [[X_LB_ONLY:%.*]] = icmp ult i32 [[X:%.*]], 65536
266+
; CHECK-NEXT: call void @llvm.assume(i1 [[X_LB_ONLY]])
267+
; CHECK-NEXT: [[X16:%.*]] = trunc i32 [[X]] to i16
268+
; CHECK-NEXT: [[Y16:%.*]] = zext i8 [[Y:%.*]] to i16
269+
; CHECK-NEXT: call void @use(i16 [[Y16]])
270+
; CHECK-NEXT: [[R:%.*]] = icmp ule i16 [[X16]], [[Y16]]
271+
; CHECK-NEXT: ret i1 [[R]]
272+
;
273+
%x_lb_only = icmp ult i32 %x, 65536
274+
call void @llvm.assume(i1 %x_lb_only)
275+
%x16 = trunc i32 %x to i16
276+
%y16 = zext i8 %y to i16
277+
call void @use(i16 %y16)
278+
%r = icmp ule i16 %x16, %y16
279+
ret i1 %r
280+
}

0 commit comments

Comments
 (0)