1; NOTE: Assertions have been autogenerated by utils/update_test_checks.py
2; RUN: opt < %s -passes=instcombine -S | FileCheck %s
3
4; Given a pattern like:
5;   %old_cmp1 = icmp slt i32 %x, C2
6;   %old_replacement = select i1 %old_cmp1, i32 %target_low, i32 %target_high
7;   %old_x_offseted = add i32 %x, C1
8;   %old_cmp0 = icmp ult i32 %old_x_offseted, C0
9;   %r = select i1 %old_cmp0, i32 %x, i32 %old_replacement
10; it can be rewriten as more canonical pattern:
11;   %new_cmp1 = icmp slt i32 %x, -C1
12;   %new_cmp2 = icmp sge i32 %x, C0-C1
13;   %new_clamped_low = select i1 %new_cmp1, i32 %target_low, i32 %x
14;   %r = select i1 %new_cmp2, i32 %target_high, i32 %new_clamped_low
15; Iff -C1 s<= C2 s<= C0-C1
16; Also, ULT predicate can also be UGE; or UGT iff C0 != -1 (+invert result)
17; Also, SLT predicate can also be SGE; or SGT iff C2 != INT_MAX (+invert res.)
18
19;-------------------------------------------------------------------------------
20
21; Basic pattern. There is no 'and', so lower threshold is 0 (inclusive).
22; The upper threshold is 65535 (inclusive).
23; There are 2 icmp's so for scalars there are 4 possible combinations.
24; The constant in %t0 has to be between the thresholds, i.e 65536 <= Ct0 <= 0.
25
26define i32 @t0_ult_slt_65536(i32 %x, i32 %replacement_low, i32 %replacement_high) {
27; CHECK-LABEL: @t0_ult_slt_65536(
28; CHECK-NEXT:    [[TMP1:%.*]] = icmp slt i32 [[X:%.*]], 0
29; CHECK-NEXT:    [[TMP2:%.*]] = icmp sgt i32 [[X]], 65535
30; CHECK-NEXT:    [[TMP3:%.*]] = select i1 [[TMP1]], i32 [[REPLACEMENT_LOW:%.*]], i32 [[X]]
31; CHECK-NEXT:    [[R:%.*]] = select i1 [[TMP2]], i32 [[REPLACEMENT_HIGH:%.*]], i32 [[TMP3]]
32; CHECK-NEXT:    ret i32 [[R]]
33;
34  %t0 = icmp slt i32 %x, 65536
35  %t1 = select i1 %t0, i32 %replacement_low, i32 %replacement_high
36  %t2 = icmp ult i32 %x, 65536
37  %r = select i1 %t2, i32 %x, i32 %t1
38  ret i32 %r
39}
40define i32 @t1_ult_slt_0(i32 %x, i32 %replacement_low, i32 %replacement_high) {
41; CHECK-LABEL: @t1_ult_slt_0(
42; CHECK-NEXT:    [[TMP1:%.*]] = icmp slt i32 [[X:%.*]], 0
43; CHECK-NEXT:    [[TMP2:%.*]] = icmp sgt i32 [[X]], 65535
44; CHECK-NEXT:    [[TMP3:%.*]] = select i1 [[TMP1]], i32 [[REPLACEMENT_LOW:%.*]], i32 [[X]]
45; CHECK-NEXT:    [[R:%.*]] = select i1 [[TMP2]], i32 [[REPLACEMENT_HIGH:%.*]], i32 [[TMP3]]
46; CHECK-NEXT:    ret i32 [[R]]
47;
48  %t0 = icmp slt i32 %x, 0
49  %t1 = select i1 %t0, i32 %replacement_low, i32 %replacement_high
50  %t2 = icmp ult i32 %x, 65536
51  %r = select i1 %t2, i32 %x, i32 %t1
52  ret i32 %r
53}
54
55define i32 @t2_ult_sgt_65536(i32 %x, i32 %replacement_low, i32 %replacement_high) {
56; CHECK-LABEL: @t2_ult_sgt_65536(
57; CHECK-NEXT:    [[TMP1:%.*]] = icmp slt i32 [[X:%.*]], 0
58; CHECK-NEXT:    [[TMP2:%.*]] = icmp sgt i32 [[X]], 65535
59; CHECK-NEXT:    [[TMP3:%.*]] = select i1 [[TMP1]], i32 [[REPLACEMENT_LOW:%.*]], i32 [[X]]
60; CHECK-NEXT:    [[R:%.*]] = select i1 [[TMP2]], i32 [[REPLACEMENT_HIGH:%.*]], i32 [[TMP3]]
61; CHECK-NEXT:    ret i32 [[R]]
62;
63  %t0 = icmp sgt i32 %x, 65535
64  %t1 = select i1 %t0, i32 %replacement_high, i32 %replacement_low
65  %t2 = icmp ult i32 %x, 65536
66  %r = select i1 %t2, i32 %x, i32 %t1
67  ret i32 %r
68}
69define i32 @t3_ult_sgt_neg1(i32 %x, i32 %replacement_low, i32 %replacement_high) {
70; CHECK-LABEL: @t3_ult_sgt_neg1(
71; CHECK-NEXT:    [[TMP1:%.*]] = icmp slt i32 [[X:%.*]], 0
72; CHECK-NEXT:    [[TMP2:%.*]] = icmp sgt i32 [[X]], 65535
73; CHECK-NEXT:    [[TMP3:%.*]] = select i1 [[TMP1]], i32 [[REPLACEMENT_LOW:%.*]], i32 [[X]]
74; CHECK-NEXT:    [[R:%.*]] = select i1 [[TMP2]], i32 [[REPLACEMENT_HIGH:%.*]], i32 [[TMP3]]
75; CHECK-NEXT:    ret i32 [[R]]
76;
77  %t0 = icmp sgt i32 %x, -1
78  %t1 = select i1 %t0, i32 %replacement_high, i32 %replacement_low
79  %t2 = icmp ult i32 %x, 65536
80  %r = select i1 %t2, i32 %x, i32 %t1
81  ret i32 %r
82}
83
84define i32 @t4_ugt_slt_65536(i32 %x, i32 %replacement_low, i32 %replacement_high) {
85; CHECK-LABEL: @t4_ugt_slt_65536(
86; CHECK-NEXT:    [[TMP1:%.*]] = icmp slt i32 [[X:%.*]], 0
87; CHECK-NEXT:    [[TMP2:%.*]] = icmp sgt i32 [[X]], 65535
88; CHECK-NEXT:    [[TMP3:%.*]] = select i1 [[TMP1]], i32 [[REPLACEMENT_LOW:%.*]], i32 [[X]]
89; CHECK-NEXT:    [[R:%.*]] = select i1 [[TMP2]], i32 [[REPLACEMENT_HIGH:%.*]], i32 [[TMP3]]
90; CHECK-NEXT:    ret i32 [[R]]
91;
92  %t0 = icmp slt i32 %x, 65536
93  %t1 = select i1 %t0, i32 %replacement_low, i32 %replacement_high
94  %t2 = icmp ugt i32 %x, 65535
95  %r = select i1 %t2, i32 %t1, i32 %x
96  ret i32 %r
97}
98define i32 @t5_ugt_slt_0(i32 %x, i32 %replacement_low, i32 %replacement_high) {
99; CHECK-LABEL: @t5_ugt_slt_0(
100; CHECK-NEXT:    [[TMP1:%.*]] = icmp slt i32 [[X:%.*]], 0
101; CHECK-NEXT:    [[TMP2:%.*]] = icmp sgt i32 [[X]], 65535
102; CHECK-NEXT:    [[TMP3:%.*]] = select i1 [[TMP1]], i32 [[REPLACEMENT_LOW:%.*]], i32 [[X]]
103; CHECK-NEXT:    [[R:%.*]] = select i1 [[TMP2]], i32 [[REPLACEMENT_HIGH:%.*]], i32 [[TMP3]]
104; CHECK-NEXT:    ret i32 [[R]]
105;
106  %t0 = icmp slt i32 %x, 0
107  %t1 = select i1 %t0, i32 %replacement_low, i32 %replacement_high
108  %t2 = icmp ugt i32 %x, 65535
109  %r = select i1 %t2, i32 %t1, i32 %x
110  ret i32 %r
111}
112
113define i32 @t6_ugt_sgt_65536(i32 %x, i32 %replacement_low, i32 %replacement_high) {
114; CHECK-LABEL: @t6_ugt_sgt_65536(
115; CHECK-NEXT:    [[TMP1:%.*]] = icmp slt i32 [[X:%.*]], 0
116; CHECK-NEXT:    [[TMP2:%.*]] = icmp sgt i32 [[X]], 65535
117; CHECK-NEXT:    [[TMP3:%.*]] = select i1 [[TMP1]], i32 [[REPLACEMENT_LOW:%.*]], i32 [[X]]
118; CHECK-NEXT:    [[R:%.*]] = select i1 [[TMP2]], i32 [[REPLACEMENT_HIGH:%.*]], i32 [[TMP3]]
119; CHECK-NEXT:    ret i32 [[R]]
120;
121  %t0 = icmp sgt i32 %x, 65535
122  %t1 = select i1 %t0, i32 %replacement_high, i32 %replacement_low
123  %t2 = icmp ugt i32 %x, 65535
124  %r = select i1 %t2, i32 %t1, i32 %x
125  ret i32 %r
126}
127define i32 @t7_ugt_sgt_neg1(i32 %x, i32 %replacement_low, i32 %replacement_high) {
128; CHECK-LABEL: @t7_ugt_sgt_neg1(
129; CHECK-NEXT:    [[TMP1:%.*]] = icmp slt i32 [[X:%.*]], 0
130; CHECK-NEXT:    [[TMP2:%.*]] = icmp sgt i32 [[X]], 65535
131; CHECK-NEXT:    [[TMP3:%.*]] = select i1 [[TMP1]], i32 [[REPLACEMENT_LOW:%.*]], i32 [[X]]
132; CHECK-NEXT:    [[R:%.*]] = select i1 [[TMP2]], i32 [[REPLACEMENT_HIGH:%.*]], i32 [[TMP3]]
133; CHECK-NEXT:    ret i32 [[R]]
134;
135  %t0 = icmp sgt i32 %x, -1
136  %t1 = select i1 %t0, i32 %replacement_high, i32 %replacement_low
137  %t2 = icmp ugt i32 %x, 65535
138  %r = select i1 %t2, i32 %t1, i32 %x
139  ret i32 %r
140}
141
142;-------------------------------------------------------------------------------
143
144; So Ct0 can not be s> 65536, or s< 0
145
146define i32 @n8_ult_slt_65537(i32 %x, i32 %replacement_low, i32 %replacement_high) {
147; CHECK-LABEL: @n8_ult_slt_65537(
148; CHECK-NEXT:    [[T0:%.*]] = icmp slt i32 [[X:%.*]], 65537
149; CHECK-NEXT:    [[T1:%.*]] = select i1 [[T0]], i32 [[REPLACEMENT_LOW:%.*]], i32 [[REPLACEMENT_HIGH:%.*]]
150; CHECK-NEXT:    [[T2:%.*]] = icmp ult i32 [[X]], 65536
151; CHECK-NEXT:    [[R:%.*]] = select i1 [[T2]], i32 [[X]], i32 [[T1]]
152; CHECK-NEXT:    ret i32 [[R]]
153;
154  %t0 = icmp slt i32 %x, 65537
155  %t1 = select i1 %t0, i32 %replacement_low, i32 %replacement_high
156  %t2 = icmp ult i32 %x, 65536
157  %r = select i1 %t2, i32 %x, i32 %t1
158  ret i32 %r
159}
160define i32 @n9_ult_slt_neg1(i32 %x, i32 %replacement_low, i32 %replacement_high) {
161; CHECK-LABEL: @n9_ult_slt_neg1(
162; CHECK-NEXT:    [[T0:%.*]] = icmp slt i32 [[X:%.*]], -1
163; CHECK-NEXT:    [[T1:%.*]] = select i1 [[T0]], i32 [[REPLACEMENT_LOW:%.*]], i32 [[REPLACEMENT_HIGH:%.*]]
164; CHECK-NEXT:    [[T2:%.*]] = icmp ult i32 [[X]], 65536
165; CHECK-NEXT:    [[R:%.*]] = select i1 [[T2]], i32 [[X]], i32 [[T1]]
166; CHECK-NEXT:    ret i32 [[R]]
167;
168  %t0 = icmp slt i32 %x, -1
169  %t1 = select i1 %t0, i32 %replacement_low, i32 %replacement_high
170  %t2 = icmp ult i32 %x, 65536
171  %r = select i1 %t2, i32 %x, i32 %t1
172  ret i32 %r
173}
174
175;-------------------------------------------------------------------------------
176
177declare void @use32(i32)
178declare void @use1(i1)
179
180; One-use restrictions: here the entire pattern needs to be one-use.
181; FIXME: if %t0 could be reused then it's less restrictive.
182
183define i32 @n10_oneuse0(i32 %x, i32 %replacement_low, i32 %replacement_high) {
184; CHECK-LABEL: @n10_oneuse0(
185; CHECK-NEXT:    [[T0:%.*]] = icmp slt i32 [[X:%.*]], 32768
186; CHECK-NEXT:    [[T1:%.*]] = select i1 [[T0]], i32 [[REPLACEMENT_LOW:%.*]], i32 [[REPLACEMENT_HIGH:%.*]]
187; CHECK-NEXT:    [[T2:%.*]] = icmp ult i32 [[X]], 65536
188; CHECK-NEXT:    call void @use1(i1 [[T2]])
189; CHECK-NEXT:    [[R:%.*]] = select i1 [[T2]], i32 [[X]], i32 [[T1]]
190; CHECK-NEXT:    ret i32 [[R]]
191;
192  %t0 = icmp slt i32 %x, 32768
193  %t1 = select i1 %t0, i32 %replacement_low, i32 %replacement_high
194  %t2 = icmp ult i32 %x, 65536
195  call void @use1(i1 %t2)
196  %r = select i1 %t2, i32 %x, i32 %t1
197  ret i32 %r
198}
199define i32 @n11_oneuse1(i32 %x, i32 %replacement_low, i32 %replacement_high) {
200; CHECK-LABEL: @n11_oneuse1(
201; CHECK-NEXT:    [[T0:%.*]] = icmp slt i32 [[X:%.*]], 32768
202; CHECK-NEXT:    call void @use1(i1 [[T0]])
203; CHECK-NEXT:    [[T1:%.*]] = select i1 [[T0]], i32 [[REPLACEMENT_LOW:%.*]], i32 [[REPLACEMENT_HIGH:%.*]]
204; CHECK-NEXT:    [[T2:%.*]] = icmp ult i32 [[X]], 65536
205; CHECK-NEXT:    [[R:%.*]] = select i1 [[T2]], i32 [[X]], i32 [[T1]]
206; CHECK-NEXT:    ret i32 [[R]]
207;
208  %t0 = icmp slt i32 %x, 32768
209  call void @use1(i1 %t0)
210  %t1 = select i1 %t0, i32 %replacement_low, i32 %replacement_high
211  %t2 = icmp ult i32 %x, 65536
212  %r = select i1 %t2, i32 %x, i32 %t1
213  ret i32 %r
214}
215define i32 @n12_oneuse2(i32 %x, i32 %replacement_low, i32 %replacement_high) {
216; CHECK-LABEL: @n12_oneuse2(
217; CHECK-NEXT:    [[T0:%.*]] = icmp slt i32 [[X:%.*]], 32768
218; CHECK-NEXT:    [[T1:%.*]] = select i1 [[T0]], i32 [[REPLACEMENT_LOW:%.*]], i32 [[REPLACEMENT_HIGH:%.*]]
219; CHECK-NEXT:    call void @use32(i32 [[T1]])
220; CHECK-NEXT:    [[T2:%.*]] = icmp ult i32 [[X]], 65536
221; CHECK-NEXT:    [[R:%.*]] = select i1 [[T2]], i32 [[X]], i32 [[T1]]
222; CHECK-NEXT:    ret i32 [[R]]
223;
224  %t0 = icmp slt i32 %x, 32768
225  %t1 = select i1 %t0, i32 %replacement_low, i32 %replacement_high
226  call void @use32(i32 %t1)
227  %t2 = icmp ult i32 %x, 65536
228  %r = select i1 %t2, i32 %x, i32 %t1
229  ret i32 %r
230}
231
232define i32 @n13_oneuse3(i32 %x, i32 %replacement_low, i32 %replacement_high) {
233; CHECK-LABEL: @n13_oneuse3(
234; CHECK-NEXT:    [[T0:%.*]] = icmp slt i32 [[X:%.*]], 32768
235; CHECK-NEXT:    call void @use1(i1 [[T0]])
236; CHECK-NEXT:    [[T1:%.*]] = select i1 [[T0]], i32 [[REPLACEMENT_LOW:%.*]], i32 [[REPLACEMENT_HIGH:%.*]]
237; CHECK-NEXT:    [[T2:%.*]] = icmp ult i32 [[X]], 65536
238; CHECK-NEXT:    call void @use1(i1 [[T2]])
239; CHECK-NEXT:    [[R:%.*]] = select i1 [[T2]], i32 [[X]], i32 [[T1]]
240; CHECK-NEXT:    ret i32 [[R]]
241;
242  %t0 = icmp slt i32 %x, 32768
243  call void @use1(i1 %t0)
244  %t1 = select i1 %t0, i32 %replacement_low, i32 %replacement_high
245  %t2 = icmp ult i32 %x, 65536
246  call void @use1(i1 %t2)
247  %r = select i1 %t2, i32 %x, i32 %t1
248  ret i32 %r
249}
250define i32 @n14_oneuse4(i32 %x, i32 %replacement_low, i32 %replacement_high) {
251; CHECK-LABEL: @n14_oneuse4(
252; CHECK-NEXT:    [[T0:%.*]] = icmp slt i32 [[X:%.*]], 32768
253; CHECK-NEXT:    call void @use1(i1 [[T0]])
254; CHECK-NEXT:    [[T1:%.*]] = select i1 [[T0]], i32 [[REPLACEMENT_LOW:%.*]], i32 [[REPLACEMENT_HIGH:%.*]]
255; CHECK-NEXT:    call void @use32(i32 [[T1]])
256; CHECK-NEXT:    [[T2:%.*]] = icmp ult i32 [[X]], 65536
257; CHECK-NEXT:    [[R:%.*]] = select i1 [[T2]], i32 [[X]], i32 [[T1]]
258; CHECK-NEXT:    ret i32 [[R]]
259;
260  %t0 = icmp slt i32 %x, 32768
261  call void @use1(i1 %t0)
262  %t1 = select i1 %t0, i32 %replacement_low, i32 %replacement_high
263  call void @use32(i32 %t1)
264  %t2 = icmp ult i32 %x, 65536
265  %r = select i1 %t2, i32 %x, i32 %t1
266  ret i32 %r
267}
268define i32 @n15_oneuse5(i32 %x, i32 %replacement_low, i32 %replacement_high) {
269; CHECK-LABEL: @n15_oneuse5(
270; CHECK-NEXT:    [[T0:%.*]] = icmp slt i32 [[X:%.*]], 32768
271; CHECK-NEXT:    [[T1:%.*]] = select i1 [[T0]], i32 [[REPLACEMENT_LOW:%.*]], i32 [[REPLACEMENT_HIGH:%.*]]
272; CHECK-NEXT:    call void @use32(i32 [[T1]])
273; CHECK-NEXT:    [[T2:%.*]] = icmp ult i32 [[X]], 65536
274; CHECK-NEXT:    call void @use1(i1 [[T2]])
275; CHECK-NEXT:    [[R:%.*]] = select i1 [[T2]], i32 [[X]], i32 [[T1]]
276; CHECK-NEXT:    ret i32 [[R]]
277;
278  %t0 = icmp slt i32 %x, 32768
279  %t1 = select i1 %t0, i32 %replacement_low, i32 %replacement_high
280  call void @use32(i32 %t1)
281  %t2 = icmp ult i32 %x, 65536
282  call void @use1(i1 %t2)
283  %r = select i1 %t2, i32 %x, i32 %t1
284  ret i32 %r
285}
286
287define i32 @n16_oneuse6(i32 %x, i32 %replacement_low, i32 %replacement_high) {
288; CHECK-LABEL: @n16_oneuse6(
289; CHECK-NEXT:    [[T0:%.*]] = icmp slt i32 [[X:%.*]], 32768
290; CHECK-NEXT:    call void @use1(i1 [[T0]])
291; CHECK-NEXT:    [[T1:%.*]] = select i1 [[T0]], i32 [[REPLACEMENT_LOW:%.*]], i32 [[REPLACEMENT_HIGH:%.*]]
292; CHECK-NEXT:    call void @use32(i32 [[T1]])
293; CHECK-NEXT:    [[T2:%.*]] = icmp ult i32 [[X]], 65536
294; CHECK-NEXT:    call void @use1(i1 [[T2]])
295; CHECK-NEXT:    [[R:%.*]] = select i1 [[T2]], i32 [[X]], i32 [[T1]]
296; CHECK-NEXT:    ret i32 [[R]]
297;
298  %t0 = icmp slt i32 %x, 32768
299  call void @use1(i1 %t0)
300  %t1 = select i1 %t0, i32 %replacement_low, i32 %replacement_high
301  call void @use32(i32 %t1)
302  %t2 = icmp ult i32 %x, 65536
303  call void @use1(i1 %t2)
304  %r = select i1 %t2, i32 %x, i32 %t1
305  ret i32 %r
306}
307
308;-------------------------------------------------------------------------------
309
310; Vectors
311
312define <2 x i32> @t17_ult_slt_vec_splat(<2 x i32> %x, <2 x i32> %replacement_low, <2 x i32> %replacement_high) {
313; CHECK-LABEL: @t17_ult_slt_vec_splat(
314; CHECK-NEXT:    [[TMP1:%.*]] = icmp slt <2 x i32> [[X:%.*]], zeroinitializer
315; CHECK-NEXT:    [[TMP2:%.*]] = icmp sgt <2 x i32> [[X]], splat (i32 65535)
316; CHECK-NEXT:    [[TMP3:%.*]] = select <2 x i1> [[TMP1]], <2 x i32> [[REPLACEMENT_LOW:%.*]], <2 x i32> [[X]]
317; CHECK-NEXT:    [[R:%.*]] = select <2 x i1> [[TMP2]], <2 x i32> [[REPLACEMENT_HIGH:%.*]], <2 x i32> [[TMP3]]
318; CHECK-NEXT:    ret <2 x i32> [[R]]
319;
320  %t0 = icmp slt <2 x i32> %x, <i32 65536, i32 65536>
321  %t1 = select <2 x i1> %t0, <2 x i32> %replacement_low, <2 x i32> %replacement_high
322  %t2 = icmp ult <2 x i32> %x, <i32 65536, i32 65536>
323  %r = select <2 x i1> %t2, <2 x i32> %x, <2 x i32> %t1
324  ret <2 x i32> %r
325}
326define <2 x i32> @t18_ult_slt_vec_nonsplat(<2 x i32> %x, <2 x i32> %replacement_low, <2 x i32> %replacement_high) {
327; CHECK-LABEL: @t18_ult_slt_vec_nonsplat(
328; CHECK-NEXT:    [[TMP1:%.*]] = icmp slt <2 x i32> [[X:%.*]], zeroinitializer
329; CHECK-NEXT:    [[TMP2:%.*]] = icmp sgt <2 x i32> [[X]], <i32 65535, i32 32767>
330; CHECK-NEXT:    [[TMP3:%.*]] = select <2 x i1> [[TMP1]], <2 x i32> [[REPLACEMENT_LOW:%.*]], <2 x i32> [[X]]
331; CHECK-NEXT:    [[R:%.*]] = select <2 x i1> [[TMP2]], <2 x i32> [[REPLACEMENT_HIGH:%.*]], <2 x i32> [[TMP3]]
332; CHECK-NEXT:    ret <2 x i32> [[R]]
333;
334  %t0 = icmp slt <2 x i32> %x, <i32 65536, i32 32768>
335  %t1 = select <2 x i1> %t0, <2 x i32> %replacement_low, <2 x i32> %replacement_high
336  %t2 = icmp ult <2 x i32> %x, <i32 65536, i32 32768>
337  %r = select <2 x i1> %t2, <2 x i32> %x, <2 x i32> %t1
338  ret <2 x i32> %r
339}
340
341define <3 x i32> @t19_ult_slt_vec_poison0(<3 x i32> %x, <3 x i32> %replacement_low, <3 x i32> %replacement_high) {
342; CHECK-LABEL: @t19_ult_slt_vec_poison0(
343; CHECK-NEXT:    [[TMP1:%.*]] = icmp slt <3 x i32> [[X:%.*]], zeroinitializer
344; CHECK-NEXT:    [[TMP2:%.*]] = icmp sgt <3 x i32> [[X]], splat (i32 65535)
345; CHECK-NEXT:    [[TMP3:%.*]] = select <3 x i1> [[TMP1]], <3 x i32> [[REPLACEMENT_LOW:%.*]], <3 x i32> [[X]]
346; CHECK-NEXT:    [[R:%.*]] = select <3 x i1> [[TMP2]], <3 x i32> [[REPLACEMENT_HIGH:%.*]], <3 x i32> [[TMP3]]
347; CHECK-NEXT:    ret <3 x i32> [[R]]
348;
349  %t0 = icmp slt <3 x i32> %x, <i32 65536, i32 poison, i32 65536>
350  %t1 = select <3 x i1> %t0, <3 x i32> %replacement_low, <3 x i32> %replacement_high
351  %t2 = icmp ult <3 x i32> %x, <i32 65536, i32 65536, i32 65536>
352  %r = select <3 x i1> %t2, <3 x i32> %x, <3 x i32> %t1
353  ret <3 x i32> %r
354}
355define <3 x i32> @t20_ult_slt_vec_poison1(<3 x i32> %x, <3 x i32> %replacement_low, <3 x i32> %replacement_high) {
356; CHECK-LABEL: @t20_ult_slt_vec_poison1(
357; CHECK-NEXT:    [[TMP1:%.*]] = icmp slt <3 x i32> [[X:%.*]], zeroinitializer
358; CHECK-NEXT:    [[TMP2:%.*]] = icmp sgt <3 x i32> [[X]], splat (i32 65535)
359; CHECK-NEXT:    [[TMP3:%.*]] = select <3 x i1> [[TMP1]], <3 x i32> [[REPLACEMENT_LOW:%.*]], <3 x i32> [[X]]
360; CHECK-NEXT:    [[R:%.*]] = select <3 x i1> [[TMP2]], <3 x i32> [[REPLACEMENT_HIGH:%.*]], <3 x i32> [[TMP3]]
361; CHECK-NEXT:    ret <3 x i32> [[R]]
362;
363  %t0 = icmp slt <3 x i32> %x, <i32 65536, i32 65537, i32 65536>
364  %t1 = select <3 x i1> %t0, <3 x i32> %replacement_low, <3 x i32> %replacement_high
365  %t2 = icmp ult <3 x i32> %x, <i32 65536, i32 poison, i32 65536>
366  %r = select <3 x i1> %t2, <3 x i32> %x, <3 x i32> %t1
367  ret <3 x i32> %r
368}
369define <3 x i32> @t21_ult_slt_vec_poison2(<3 x i32> %x, <3 x i32> %replacement_low, <3 x i32> %replacement_high) {
370; CHECK-LABEL: @t21_ult_slt_vec_poison2(
371; CHECK-NEXT:    [[TMP1:%.*]] = icmp slt <3 x i32> [[X:%.*]], zeroinitializer
372; CHECK-NEXT:    [[TMP2:%.*]] = icmp sgt <3 x i32> [[X]], splat (i32 65535)
373; CHECK-NEXT:    [[TMP3:%.*]] = select <3 x i1> [[TMP1]], <3 x i32> [[REPLACEMENT_LOW:%.*]], <3 x i32> [[X]]
374; CHECK-NEXT:    [[R:%.*]] = select <3 x i1> [[TMP2]], <3 x i32> [[REPLACEMENT_HIGH:%.*]], <3 x i32> [[TMP3]]
375; CHECK-NEXT:    ret <3 x i32> [[R]]
376;
377  %t0 = icmp slt <3 x i32> %x, <i32 65536, i32 poison, i32 65536>
378  %t1 = select <3 x i1> %t0, <3 x i32> %replacement_low, <3 x i32> %replacement_high
379  %t2 = icmp ult <3 x i32> %x, <i32 65536, i32 poison, i32 65536>
380  %r = select <3 x i1> %t2, <3 x i32> %x, <3 x i32> %t1
381  ret <3 x i32> %r
382}
383
384;-------------------------------------------------------------------------------
385
386define ptr @t22_pointers(ptr %x, ptr %replacement_low, ptr %replacement_high) {
387; CHECK-LABEL: @t22_pointers(
388; CHECK-NEXT:    [[T0:%.*]] = icmp slt ptr [[X:%.*]], inttoptr (i64 65536 to ptr)
389; CHECK-NEXT:    [[T1:%.*]] = select i1 [[T0]], ptr [[REPLACEMENT_LOW:%.*]], ptr [[REPLACEMENT_HIGH:%.*]]
390; CHECK-NEXT:    [[T2:%.*]] = icmp ult ptr [[X]], inttoptr (i64 65536 to ptr)
391; CHECK-NEXT:    [[R:%.*]] = select i1 [[T2]], ptr [[X]], ptr [[T1]]
392; CHECK-NEXT:    ret ptr [[R]]
393;
394  %t0 = icmp slt ptr %x, inttoptr (i64 65536 to ptr)
395  %t1 = select i1 %t0, ptr %replacement_low, ptr %replacement_high
396  %t2 = icmp ult ptr %x, inttoptr (i64 65536 to ptr)
397  %r = select i1 %t2, ptr %x, ptr %t1
398  ret ptr %r
399}
400