1; NOTE: Assertions have been autogenerated by utils/update_test_checks.py
2; RUN: opt < %s -passes=instcombine -S | FileCheck %s
3
4declare void @use.i8(i8)
5declare void @use.v2i4(<2 x i4>)
6declare void @use.i1(i1)
7
8declare void @llvm.assume(i1)
9
10; Basic pattern
11define i8 @t0(i8 %x) {
12; CHECK-LABEL: @t0(
13; CHECK-NEXT:    [[X_BIASED1:%.*]] = add i8 [[X:%.*]], 15
14; CHECK-NEXT:    [[X_ROUNDEDUP:%.*]] = and i8 [[X_BIASED1]], -16
15; CHECK-NEXT:    ret i8 [[X_ROUNDEDUP]]
16;
17  %x.lowbits = and i8 %x, 15
18  %x.lowbits.are.zero = icmp eq i8 %x.lowbits, 0
19  %x.biased = add i8 %x, 16
20  %x.biased.highbits = and i8 %x.biased, -16
21  %x.roundedup = select i1 %x.lowbits.are.zero, i8 %x, i8 %x.biased.highbits
22  ret i8 %x.roundedup
23}
24
25; Another alignment is fine
26define i8 @t1(i8 %x) {
27; CHECK-LABEL: @t1(
28; CHECK-NEXT:    [[X_BIASED1:%.*]] = add i8 [[X:%.*]], 31
29; CHECK-NEXT:    [[X_ROUNDEDUP:%.*]] = and i8 [[X_BIASED1]], -32
30; CHECK-NEXT:    ret i8 [[X_ROUNDEDUP]]
31;
32  %x.lowbits = and i8 %x, 31
33  %x.lowbits.are.zero = icmp eq i8 %x.lowbits, 0
34  %x.biased = add i8 %x, 32
35  %x.biased.highbits = and i8 %x.biased, -32
36  %x.roundedup = select i1 %x.lowbits.are.zero, i8 %x, i8 %x.biased.highbits
37  ret i8 %x.roundedup
38}
39
40; Bias can be either the alignment or alignment-1
41define i8 @t2(i8 %x) {
42; CHECK-LABEL: @t2(
43; CHECK-NEXT:    [[X_BIASED1:%.*]] = add i8 [[X:%.*]], 15
44; CHECK-NEXT:    [[X_ROUNDEDUP:%.*]] = and i8 [[X_BIASED1]], -16
45; CHECK-NEXT:    ret i8 [[X_ROUNDEDUP]]
46;
47  %x.lowbits = and i8 %x, 15
48  %x.lowbits.are.zero = icmp eq i8 %x.lowbits, 0
49  %x.biased = add i8 %x, 15
50  %x.biased.highbits = and i8 %x.biased, -16
51  %x.roundedup = select i1 %x.lowbits.are.zero, i8 %x, i8 %x.biased.highbits
52  ret i8 %x.roundedup
53}
54
55; select is commutative
56define i8 @t3_commutative(i8 %x) {
57; CHECK-LABEL: @t3_commutative(
58; CHECK-NEXT:    [[X_LOWBITS:%.*]] = and i8 [[X:%.*]], 15
59; CHECK-NEXT:    [[X_LOWBITS_ARE_NOT_ZERO:%.*]] = icmp ne i8 [[X_LOWBITS]], 0
60; CHECK-NEXT:    call void @use.i1(i1 [[X_LOWBITS_ARE_NOT_ZERO]])
61; CHECK-NEXT:    [[X_BIASED1:%.*]] = add i8 [[X]], 15
62; CHECK-NEXT:    [[X_ROUNDEDUP:%.*]] = and i8 [[X_BIASED1]], -16
63; CHECK-NEXT:    ret i8 [[X_ROUNDEDUP]]
64;
65  %x.lowbits = and i8 %x, 15
66  %x.lowbits.are.not.zero = icmp ne i8 %x.lowbits, 0
67  call void @use.i1(i1 %x.lowbits.are.not.zero)
68  %x.biased = add i8 %x, 16
69  %x.biased.highbits = and i8 %x.biased, -16
70  %x.roundedup = select i1 %x.lowbits.are.not.zero, i8 %x.biased.highbits, i8 %x
71  ret i8 %x.roundedup
72}
73
74; Basic splat vector test
75define <2 x i8> @t4_splat(<2 x i8> %x) {
76; CHECK-LABEL: @t4_splat(
77; CHECK-NEXT:    [[X_BIASED1:%.*]] = add <2 x i8> [[X:%.*]], <i8 15, i8 15>
78; CHECK-NEXT:    [[X_ROUNDEDUP:%.*]] = and <2 x i8> [[X_BIASED1]], <i8 -16, i8 -16>
79; CHECK-NEXT:    ret <2 x i8> [[X_ROUNDEDUP]]
80;
81  %x.lowbits = and <2 x i8> %x, <i8 15, i8 15>
82  %x.lowbits.are.zero = icmp eq <2 x i8> %x.lowbits, <i8 0, i8 0>
83  %x.biased = add <2 x i8> %x, <i8 16, i8 16>
84  %x.biased.highbits = and <2 x i8> %x.biased, <i8 -16, i8 -16>
85  %x.roundedup = select <2 x i1> %x.lowbits.are.zero, <2 x i8> %x, <2 x i8> %x.biased.highbits
86  ret <2 x i8> %x.roundedup
87}
88
89; Splat-with-undef
90define <2 x i8> @t5_splat_undef_0b0001(<2 x i8> %x) {
91; CHECK-LABEL: @t5_splat_undef_0b0001(
92; CHECK-NEXT:    [[X_BIASED1:%.*]] = add <2 x i8> [[X:%.*]], <i8 15, i8 15>
93; CHECK-NEXT:    [[X_ROUNDEDUP:%.*]] = and <2 x i8> [[X_BIASED1]], <i8 -16, i8 -16>
94; CHECK-NEXT:    ret <2 x i8> [[X_ROUNDEDUP]]
95;
96  %x.lowbits = and <2 x i8> %x, <i8 15, i8 15>
97  %x.lowbits.are.zero = icmp eq <2 x i8> %x.lowbits, <i8 0, i8 0>
98  %x.biased = add <2 x i8> %x, <i8 16, i8 16>
99  %x.biased.highbits = and <2 x i8> %x.biased, <i8 -16, i8 undef>
100  %x.roundedup = select <2 x i1> %x.lowbits.are.zero, <2 x i8> %x, <2 x i8> %x.biased.highbits
101  ret <2 x i8> %x.roundedup
102}
103define <2 x i8> @t5_splat_undef_0b0010(<2 x i8> %x) {
104; CHECK-LABEL: @t5_splat_undef_0b0010(
105; CHECK-NEXT:    [[X_BIASED1:%.*]] = add <2 x i8> [[X:%.*]], <i8 15, i8 15>
106; CHECK-NEXT:    [[X_ROUNDEDUP:%.*]] = and <2 x i8> [[X_BIASED1]], <i8 -16, i8 -16>
107; CHECK-NEXT:    ret <2 x i8> [[X_ROUNDEDUP]]
108;
109  %x.lowbits = and <2 x i8> %x, <i8 15, i8 15>
110  %x.lowbits.are.zero = icmp eq <2 x i8> %x.lowbits, <i8 0, i8 0>
111  %x.biased = add <2 x i8> %x, <i8 16, i8 undef>
112  %x.biased.highbits = and <2 x i8> %x.biased, <i8 -16, i8 -16>
113  %x.roundedup = select <2 x i1> %x.lowbits.are.zero, <2 x i8> %x, <2 x i8> %x.biased.highbits
114  ret <2 x i8> %x.roundedup
115}
116define <2 x i8> @t5_splat_undef_0b0100(<2 x i8> %x) {
117; CHECK-LABEL: @t5_splat_undef_0b0100(
118; CHECK-NEXT:    [[X_BIASED1:%.*]] = add <2 x i8> [[X:%.*]], <i8 15, i8 15>
119; CHECK-NEXT:    [[X_ROUNDEDUP:%.*]] = and <2 x i8> [[X_BIASED1]], <i8 -16, i8 -16>
120; CHECK-NEXT:    ret <2 x i8> [[X_ROUNDEDUP]]
121;
122  %x.lowbits = and <2 x i8> %x, <i8 15, i8 15>
123  %x.lowbits.are.zero = icmp eq <2 x i8> %x.lowbits, <i8 0, i8 undef>
124  %x.biased = add <2 x i8> %x, <i8 16, i8 16>
125  %x.biased.highbits = and <2 x i8> %x.biased, <i8 -16, i8 -16>
126  %x.roundedup = select <2 x i1> %x.lowbits.are.zero, <2 x i8> %x, <2 x i8> %x.biased.highbits
127  ret <2 x i8> %x.roundedup
128}
129define <2 x i8> @t5_splat_undef_0b1000(<2 x i8> %x) {
130; CHECK-LABEL: @t5_splat_undef_0b1000(
131; CHECK-NEXT:    [[X_BIASED1:%.*]] = add <2 x i8> [[X:%.*]], <i8 15, i8 15>
132; CHECK-NEXT:    [[X_ROUNDEDUP:%.*]] = and <2 x i8> [[X_BIASED1]], <i8 -16, i8 -16>
133; CHECK-NEXT:    ret <2 x i8> [[X_ROUNDEDUP]]
134;
135  %x.lowbits = and <2 x i8> %x, <i8 15, i8 undef>
136  %x.lowbits.are.zero = icmp eq <2 x i8> %x.lowbits, <i8 0, i8 0>
137  %x.biased = add <2 x i8> %x, <i8 16, i8 16>
138  %x.biased.highbits = and <2 x i8> %x.biased, <i8 -16, i8 -16>
139  %x.roundedup = select <2 x i1> %x.lowbits.are.zero, <2 x i8> %x, <2 x i8> %x.biased.highbits
140  ret <2 x i8> %x.roundedup
141}
142
143; Basic non-splat vector test
144define <2 x i8> @t6_nonsplat(<2 x i8> %x) {
145; CHECK-LABEL: @t6_nonsplat(
146; CHECK-NEXT:    [[X_LOWBITS:%.*]] = and <2 x i8> [[X:%.*]], <i8 15, i8 31>
147; CHECK-NEXT:    [[X_LOWBITS_ARE_ZERO:%.*]] = icmp eq <2 x i8> [[X_LOWBITS]], zeroinitializer
148; CHECK-NEXT:    [[X_BIASED:%.*]] = add <2 x i8> [[X]], <i8 16, i8 32>
149; CHECK-NEXT:    [[X_BIASED_HIGHBITS:%.*]] = and <2 x i8> [[X_BIASED]], <i8 -16, i8 -32>
150; CHECK-NEXT:    [[X_ROUNDEDUP:%.*]] = select <2 x i1> [[X_LOWBITS_ARE_ZERO]], <2 x i8> [[X]], <2 x i8> [[X_BIASED_HIGHBITS]]
151; CHECK-NEXT:    ret <2 x i8> [[X_ROUNDEDUP]]
152;
153  %x.lowbits = and <2 x i8> %x, <i8 15, i8 31>
154  %x.lowbits.are.zero = icmp eq <2 x i8> %x.lowbits, <i8 0, i8 0>
155  %x.biased = add <2 x i8> %x, <i8 16, i8 32>
156  %x.biased.highbits = and <2 x i8> %x.biased, <i8 -16, i8 -32>
157  %x.roundedup = select <2 x i1> %x.lowbits.are.zero, <2 x i8> %x, <2 x i8> %x.biased.highbits
158  ret <2 x i8> %x.roundedup
159}
160
161; Even if the alignment (and masks) are splat, the bias could be non-splat
162define <2 x i8> @t7_nonsplat_bias(<2 x i8> %x) {
163; CHECK-LABEL: @t7_nonsplat_bias(
164; CHECK-NEXT:    [[X_LOWBITS:%.*]] = and <2 x i8> [[X:%.*]], <i8 15, i8 15>
165; CHECK-NEXT:    [[X_LOWBITS_ARE_ZERO:%.*]] = icmp eq <2 x i8> [[X_LOWBITS]], zeroinitializer
166; CHECK-NEXT:    [[X_BIASED:%.*]] = add <2 x i8> [[X]], <i8 15, i8 16>
167; CHECK-NEXT:    [[X_BIASED_HIGHBITS:%.*]] = and <2 x i8> [[X_BIASED]], <i8 -16, i8 -16>
168; CHECK-NEXT:    [[X_ROUNDEDUP:%.*]] = select <2 x i1> [[X_LOWBITS_ARE_ZERO]], <2 x i8> [[X]], <2 x i8> [[X_BIASED_HIGHBITS]]
169; CHECK-NEXT:    ret <2 x i8> [[X_ROUNDEDUP]]
170;
171  %x.lowbits = and <2 x i8> %x, <i8 15, i8 15>
172  %x.lowbits.are.zero = icmp eq <2 x i8> %x.lowbits, <i8 0, i8 0>
173  %x.biased = add <2 x i8> %x, <i8 15, i8 16>
174  %x.biased.highbits = and <2 x i8> %x.biased, <i8 -16, i8 -16>
175  %x.roundedup = select <2 x i1> %x.lowbits.are.zero, <2 x i8> %x, <2 x i8> %x.biased.highbits
176  ret <2 x i8> %x.roundedup
177}
178
179; Splat-in-disguise vector tests
180define <2 x i8> @t8_nonsplat_masked_by_undef_0b0001(<2 x i8> %x) {
181; CHECK-LABEL: @t8_nonsplat_masked_by_undef_0b0001(
182; CHECK-NEXT:    [[X_LOWBITS:%.*]] = and <2 x i8> [[X:%.*]], <i8 15, i8 31>
183; CHECK-NEXT:    [[X_LOWBITS_ARE_ZERO:%.*]] = icmp eq <2 x i8> [[X_LOWBITS]], zeroinitializer
184; CHECK-NEXT:    [[X_BIASED:%.*]] = add <2 x i8> [[X]], <i8 16, i8 32>
185; CHECK-NEXT:    [[X_BIASED_HIGHBITS:%.*]] = and <2 x i8> [[X_BIASED]], <i8 -16, i8 undef>
186; CHECK-NEXT:    [[X_ROUNDEDUP:%.*]] = select <2 x i1> [[X_LOWBITS_ARE_ZERO]], <2 x i8> [[X]], <2 x i8> [[X_BIASED_HIGHBITS]]
187; CHECK-NEXT:    ret <2 x i8> [[X_ROUNDEDUP]]
188;
189  %x.lowbits = and <2 x i8> %x, <i8 15, i8 31>
190  %x.lowbits.are.zero = icmp eq <2 x i8> %x.lowbits, <i8 0, i8 0>
191  %x.biased = add <2 x i8> %x, <i8 16, i8 32>
192  %x.biased.highbits = and <2 x i8> %x.biased, <i8 -16, i8 undef>
193  %x.roundedup = select <2 x i1> %x.lowbits.are.zero, <2 x i8> %x, <2 x i8> %x.biased.highbits
194  ret <2 x i8> %x.roundedup
195}
196define <2 x i8> @t8_nonsplat_masked_by_undef_0b0010(<2 x i8> %x) {
197; CHECK-LABEL: @t8_nonsplat_masked_by_undef_0b0010(
198; CHECK-NEXT:    [[X_LOWBITS:%.*]] = and <2 x i8> [[X:%.*]], <i8 15, i8 31>
199; CHECK-NEXT:    [[X_LOWBITS_ARE_ZERO:%.*]] = icmp eq <2 x i8> [[X_LOWBITS]], zeroinitializer
200; CHECK-NEXT:    [[X_BIASED:%.*]] = add <2 x i8> [[X]], <i8 16, i8 undef>
201; CHECK-NEXT:    [[X_BIASED_HIGHBITS:%.*]] = and <2 x i8> [[X_BIASED]], <i8 -16, i8 -32>
202; CHECK-NEXT:    [[X_ROUNDEDUP:%.*]] = select <2 x i1> [[X_LOWBITS_ARE_ZERO]], <2 x i8> [[X]], <2 x i8> [[X_BIASED_HIGHBITS]]
203; CHECK-NEXT:    ret <2 x i8> [[X_ROUNDEDUP]]
204;
205  %x.lowbits = and <2 x i8> %x, <i8 15, i8 31>
206  %x.lowbits.are.zero = icmp eq <2 x i8> %x.lowbits, <i8 0, i8 0>
207  %x.biased = add <2 x i8> %x, <i8 16, i8 undef>
208  %x.biased.highbits = and <2 x i8> %x.biased, <i8 -16, i8 -32>
209  %x.roundedup = select <2 x i1> %x.lowbits.are.zero, <2 x i8> %x, <2 x i8> %x.biased.highbits
210  ret <2 x i8> %x.roundedup
211}
212define <2 x i8> @t8_nonsplat_masked_by_undef_0b0100(<2 x i8> %x) {
213; CHECK-LABEL: @t8_nonsplat_masked_by_undef_0b0100(
214; CHECK-NEXT:    [[X_LOWBITS:%.*]] = and <2 x i8> [[X:%.*]], <i8 15, i8 31>
215; CHECK-NEXT:    [[X_LOWBITS_ARE_ZERO:%.*]] = icmp eq <2 x i8> [[X_LOWBITS]], <i8 0, i8 undef>
216; CHECK-NEXT:    [[X_BIASED:%.*]] = add <2 x i8> [[X]], <i8 16, i8 32>
217; CHECK-NEXT:    [[X_BIASED_HIGHBITS:%.*]] = and <2 x i8> [[X_BIASED]], <i8 -16, i8 -32>
218; CHECK-NEXT:    [[X_ROUNDEDUP:%.*]] = select <2 x i1> [[X_LOWBITS_ARE_ZERO]], <2 x i8> [[X]], <2 x i8> [[X_BIASED_HIGHBITS]]
219; CHECK-NEXT:    ret <2 x i8> [[X_ROUNDEDUP]]
220;
221  %x.lowbits = and <2 x i8> %x, <i8 15, i8 31>
222  %x.lowbits.are.zero = icmp eq <2 x i8> %x.lowbits, <i8 0, i8 undef>
223  %x.biased = add <2 x i8> %x, <i8 16, i8 32>
224  %x.biased.highbits = and <2 x i8> %x.biased, <i8 -16, i8 -32>
225  %x.roundedup = select <2 x i1> %x.lowbits.are.zero, <2 x i8> %x, <2 x i8> %x.biased.highbits
226  ret <2 x i8> %x.roundedup
227}
228define <2 x i8> @t8_nonsplat_masked_by_undef_0b1000(<2 x i8> %x) {
229; CHECK-LABEL: @t8_nonsplat_masked_by_undef_0b1000(
230; CHECK-NEXT:    [[X_LOWBITS:%.*]] = and <2 x i8> [[X:%.*]], <i8 15, i8 undef>
231; CHECK-NEXT:    [[X_LOWBITS_ARE_ZERO:%.*]] = icmp eq <2 x i8> [[X_LOWBITS]], zeroinitializer
232; CHECK-NEXT:    [[X_BIASED:%.*]] = add <2 x i8> [[X]], <i8 16, i8 32>
233; CHECK-NEXT:    [[X_BIASED_HIGHBITS:%.*]] = and <2 x i8> [[X_BIASED]], <i8 -16, i8 -32>
234; CHECK-NEXT:    [[X_ROUNDEDUP:%.*]] = select <2 x i1> [[X_LOWBITS_ARE_ZERO]], <2 x i8> [[X]], <2 x i8> [[X_BIASED_HIGHBITS]]
235; CHECK-NEXT:    ret <2 x i8> [[X_ROUNDEDUP]]
236;
237  %x.lowbits = and <2 x i8> %x, <i8 15, i8 undef>
238  %x.lowbits.are.zero = icmp eq <2 x i8> %x.lowbits, <i8 0, i8 0>
239  %x.biased = add <2 x i8> %x, <i8 16, i8 32>
240  %x.biased.highbits = and <2 x i8> %x.biased, <i8 -16, i8 -32>
241  %x.roundedup = select <2 x i1> %x.lowbits.are.zero, <2 x i8> %x, <2 x i8> %x.biased.highbits
242  ret <2 x i8> %x.roundedup
243}
244
245; The X are different
246define i8 @n9_wrong_x0(i8 %x.0, i8 %x.1) {
247; CHECK-LABEL: @n9_wrong_x0(
248; CHECK-NEXT:    [[X_LOWBITS:%.*]] = and i8 [[X_0:%.*]], 15
249; CHECK-NEXT:    [[X_LOWBITS_ARE_ZERO:%.*]] = icmp eq i8 [[X_LOWBITS]], 0
250; CHECK-NEXT:    [[X_BIASED:%.*]] = add i8 [[X_0]], 16
251; CHECK-NEXT:    [[X_BIASED_HIGHBITS:%.*]] = and i8 [[X_BIASED]], -16
252; CHECK-NEXT:    [[X_ROUNDEDUP:%.*]] = select i1 [[X_LOWBITS_ARE_ZERO]], i8 [[X_1:%.*]], i8 [[X_BIASED_HIGHBITS]]
253; CHECK-NEXT:    ret i8 [[X_ROUNDEDUP]]
254;
255  %x.lowbits = and i8 %x.0, 15
256  %x.lowbits.are.zero = icmp eq i8 %x.lowbits, 0
257  %x.biased = add i8 %x.0, 16
258  %x.biased.highbits = and i8 %x.biased, -16
259  %x.roundedup = select i1 %x.lowbits.are.zero, i8 %x.1, i8 %x.biased.highbits
260  ret i8 %x.roundedup
261}
262define i8 @n9_wrong_x1(i8 %x.0, i8 %x.1) {
263; CHECK-LABEL: @n9_wrong_x1(
264; CHECK-NEXT:    [[X_LOWBITS:%.*]] = and i8 [[X_0:%.*]], 15
265; CHECK-NEXT:    [[X_LOWBITS_ARE_ZERO:%.*]] = icmp eq i8 [[X_LOWBITS]], 0
266; CHECK-NEXT:    [[X_BIASED:%.*]] = add i8 [[X_1:%.*]], 16
267; CHECK-NEXT:    [[X_BIASED_HIGHBITS:%.*]] = and i8 [[X_BIASED]], -16
268; CHECK-NEXT:    [[X_ROUNDEDUP:%.*]] = select i1 [[X_LOWBITS_ARE_ZERO]], i8 [[X_0]], i8 [[X_BIASED_HIGHBITS]]
269; CHECK-NEXT:    ret i8 [[X_ROUNDEDUP]]
270;
271  %x.lowbits = and i8 %x.0, 15
272  %x.lowbits.are.zero = icmp eq i8 %x.lowbits, 0
273  %x.biased = add i8 %x.1, 16
274  %x.biased.highbits = and i8 %x.biased, -16
275  %x.roundedup = select i1 %x.lowbits.are.zero, i8 %x.0, i8 %x.biased.highbits
276  ret i8 %x.roundedup
277}
278define i8 @n9_wrong_x2(i8 %x.0, i8 %x.1) {
279; CHECK-LABEL: @n9_wrong_x2(
280; CHECK-NEXT:    [[X_LOWBITS:%.*]] = and i8 [[X_1:%.*]], 15
281; CHECK-NEXT:    [[X_LOWBITS_ARE_ZERO:%.*]] = icmp eq i8 [[X_LOWBITS]], 0
282; CHECK-NEXT:    [[X_BIASED:%.*]] = add i8 [[X_0:%.*]], 16
283; CHECK-NEXT:    [[X_BIASED_HIGHBITS:%.*]] = and i8 [[X_BIASED]], -16
284; CHECK-NEXT:    [[X_ROUNDEDUP:%.*]] = select i1 [[X_LOWBITS_ARE_ZERO]], i8 [[X_0]], i8 [[X_BIASED_HIGHBITS]]
285; CHECK-NEXT:    ret i8 [[X_ROUNDEDUP]]
286;
287  %x.lowbits = and i8 %x.1, 15
288  %x.lowbits.are.zero = icmp eq i8 %x.lowbits, 0
289  %x.biased = add i8 %x.0, 16
290  %x.biased.highbits = and i8 %x.biased, -16
291  %x.roundedup = select i1 %x.lowbits.are.zero, i8 %x.0, i8 %x.biased.highbits
292  ret i8 %x.roundedup
293}
294
295; Wrong low-bit mask
296define i8 @n10_wrong_low_bit_mask(i8 %x) {
297; CHECK-LABEL: @n10_wrong_low_bit_mask(
298; CHECK-NEXT:    [[X_LOWBITS:%.*]] = and i8 [[X:%.*]], 31
299; CHECK-NEXT:    [[X_LOWBITS_ARE_ZERO:%.*]] = icmp eq i8 [[X_LOWBITS]], 0
300; CHECK-NEXT:    [[X_BIASED:%.*]] = add i8 [[X]], 16
301; CHECK-NEXT:    [[X_BIASED_HIGHBITS:%.*]] = and i8 [[X_BIASED]], -16
302; CHECK-NEXT:    [[X_ROUNDEDUP:%.*]] = select i1 [[X_LOWBITS_ARE_ZERO]], i8 [[X]], i8 [[X_BIASED_HIGHBITS]]
303; CHECK-NEXT:    ret i8 [[X_ROUNDEDUP]]
304;
305  %x.lowbits = and i8 %x, 31
306  %x.lowbits.are.zero = icmp eq i8 %x.lowbits, 0
307  %x.biased = add i8 %x, 16
308  %x.biased.highbits = and i8 %x.biased, -16
309  %x.roundedup = select i1 %x.lowbits.are.zero, i8 %x, i8 %x.biased.highbits
310  ret i8 %x.roundedup
311}
312
313; Wrong high-bit mask
314define i8 @n11_wrong_high_bit_mask(i8 %x) {
315; CHECK-LABEL: @n11_wrong_high_bit_mask(
316; CHECK-NEXT:    [[X_LOWBITS:%.*]] = and i8 [[X:%.*]], 15
317; CHECK-NEXT:    [[X_LOWBITS_ARE_ZERO:%.*]] = icmp eq i8 [[X_LOWBITS]], 0
318; CHECK-NEXT:    [[X_BIASED:%.*]] = add i8 [[X]], 16
319; CHECK-NEXT:    [[X_BIASED_HIGHBITS:%.*]] = and i8 [[X_BIASED]], -32
320; CHECK-NEXT:    [[X_ROUNDEDUP:%.*]] = select i1 [[X_LOWBITS_ARE_ZERO]], i8 [[X]], i8 [[X_BIASED_HIGHBITS]]
321; CHECK-NEXT:    ret i8 [[X_ROUNDEDUP]]
322;
323  %x.lowbits = and i8 %x, 15
324  %x.lowbits.are.zero = icmp eq i8 %x.lowbits, 0
325  %x.biased = add i8 %x, 16
326  %x.biased.highbits = and i8 %x.biased, -32
327  %x.roundedup = select i1 %x.lowbits.are.zero, i8 %x, i8 %x.biased.highbits
328  ret i8 %x.roundedup
329}
330
331; Wrong bias
332define i8 @n12_wrong_bias(i8 %x) {
333; CHECK-LABEL: @n12_wrong_bias(
334; CHECK-NEXT:    [[X_LOWBITS:%.*]] = and i8 [[X:%.*]], 15
335; CHECK-NEXT:    [[X_LOWBITS_ARE_ZERO:%.*]] = icmp eq i8 [[X_LOWBITS]], 0
336; CHECK-NEXT:    [[X_BIASED:%.*]] = add i8 [[X]], 32
337; CHECK-NEXT:    [[X_BIASED_HIGHBITS:%.*]] = and i8 [[X_BIASED]], -16
338; CHECK-NEXT:    [[X_ROUNDEDUP:%.*]] = select i1 [[X_LOWBITS_ARE_ZERO]], i8 [[X]], i8 [[X_BIASED_HIGHBITS]]
339; CHECK-NEXT:    ret i8 [[X_ROUNDEDUP]]
340;
341  %x.lowbits = and i8 %x, 15
342  %x.lowbits.are.zero = icmp eq i8 %x.lowbits, 0
343  %x.biased = add i8 %x, 32
344  %x.biased.highbits = and i8 %x.biased, -16
345  %x.roundedup = select i1 %x.lowbits.are.zero, i8 %x, i8 %x.biased.highbits
346  ret i8 %x.roundedup
347}
348
349; Wrong constants
350define i8 @n13_wrong_constants_alignment_is_not_power_of_two(i8 %x) {
351; CHECK-LABEL: @n13_wrong_constants_alignment_is_not_power_of_two(
352; CHECK-NEXT:    [[X_LOWBITS:%.*]] = and i8 [[X:%.*]], 2
353; CHECK-NEXT:    [[X_LOWBITS_ARE_ZERO:%.*]] = icmp eq i8 [[X_LOWBITS]], 0
354; CHECK-NEXT:    [[X_BIASED:%.*]] = add i8 [[X]], 3
355; CHECK-NEXT:    [[X_BIASED_HIGHBITS:%.*]] = and i8 [[X_BIASED]], -3
356; CHECK-NEXT:    [[X_ROUNDEDUP:%.*]] = select i1 [[X_LOWBITS_ARE_ZERO]], i8 [[X]], i8 [[X_BIASED_HIGHBITS]]
357; CHECK-NEXT:    ret i8 [[X_ROUNDEDUP]]
358;
359  %x.lowbits = and i8 %x, 2
360  %x.lowbits.are.zero = icmp eq i8 %x.lowbits, 0
361  %x.biased = add i8 %x, 3
362  %x.biased.highbits = and i8 %x.biased, -3
363  %x.roundedup = select i1 %x.lowbits.are.zero, i8 %x, i8 %x.biased.highbits
364  ret i8 %x.roundedup
365}
366
367; Comparison is not with zero
368define i8 @n14_wrong_comparison_constant(i8 %x) {
369; CHECK-LABEL: @n14_wrong_comparison_constant(
370; CHECK-NEXT:    [[X_LOWBITS:%.*]] = and i8 [[X:%.*]], 15
371; CHECK-NEXT:    [[X_LOWBITS_ARE_ZERO:%.*]] = icmp eq i8 [[X_LOWBITS]], 1
372; CHECK-NEXT:    [[X_BIASED:%.*]] = add i8 [[X]], 16
373; CHECK-NEXT:    [[X_BIASED_HIGHBITS:%.*]] = and i8 [[X_BIASED]], -16
374; CHECK-NEXT:    [[X_ROUNDEDUP:%.*]] = select i1 [[X_LOWBITS_ARE_ZERO]], i8 [[X]], i8 [[X_BIASED_HIGHBITS]]
375; CHECK-NEXT:    ret i8 [[X_ROUNDEDUP]]
376;
377  %x.lowbits = and i8 %x, 15
378  %x.lowbits.are.zero = icmp eq i8 %x.lowbits, 1
379  %x.biased = add i8 %x, 16
380  %x.biased.highbits = and i8 %x.biased, -16
381  %x.roundedup = select i1 %x.lowbits.are.zero, i8 %x, i8 %x.biased.highbits
382  ret i8 %x.roundedup
383}
384
385; Wrong comparison
386define i8 @n15_wrong_comparison_predicate_and_constant(i8 %x) {
387; CHECK-LABEL: @n15_wrong_comparison_predicate_and_constant(
388; CHECK-NEXT:    [[X_LOWBITS:%.*]] = and i8 [[X:%.*]], 14
389; CHECK-NEXT:    [[X_LOWBITS_ARE_ZERO:%.*]] = icmp eq i8 [[X_LOWBITS]], 0
390; CHECK-NEXT:    [[X_BIASED:%.*]] = add i8 [[X]], 16
391; CHECK-NEXT:    [[X_BIASED_HIGHBITS:%.*]] = and i8 [[X_BIASED]], -16
392; CHECK-NEXT:    [[X_ROUNDEDUP:%.*]] = select i1 [[X_LOWBITS_ARE_ZERO]], i8 [[X]], i8 [[X_BIASED_HIGHBITS]]
393; CHECK-NEXT:    ret i8 [[X_ROUNDEDUP]]
394;
395  %x.lowbits = and i8 %x, 15
396  %x.lowbits.are.zero = icmp ult i8 %x.lowbits, 2
397  %x.biased = add i8 %x, 16
398  %x.biased.highbits = and i8 %x.biased, -16
399  %x.roundedup = select i1 %x.lowbits.are.zero, i8 %x, i8 %x.biased.highbits
400  ret i8 %x.roundedup
401}
402
403; %x.biased.highbits must not have other uses
404define i8 @n16_oneuse(i8 %x) {
405; CHECK-LABEL: @n16_oneuse(
406; CHECK-NEXT:    [[X_LOWBITS:%.*]] = and i8 [[X:%.*]], 15
407; CHECK-NEXT:    [[X_LOWBITS_ARE_ZERO:%.*]] = icmp eq i8 [[X_LOWBITS]], 0
408; CHECK-NEXT:    [[X_BIASED:%.*]] = add i8 [[X]], 16
409; CHECK-NEXT:    [[X_BIASED_HIGHBITS:%.*]] = and i8 [[X_BIASED]], -16
410; CHECK-NEXT:    call void @use.i8(i8 [[X_BIASED_HIGHBITS]])
411; CHECK-NEXT:    [[X_ROUNDEDUP:%.*]] = select i1 [[X_LOWBITS_ARE_ZERO]], i8 [[X]], i8 [[X_BIASED_HIGHBITS]]
412; CHECK-NEXT:    ret i8 [[X_ROUNDEDUP]]
413;
414  %x.lowbits = and i8 %x, 15
415  %x.lowbits.are.zero = icmp eq i8 %x.lowbits, 0
416  %x.biased = add i8 %x, 16
417  %x.biased.highbits = and i8 %x.biased, -16
418  call void @use.i8(i8 %x.biased.highbits)
419  %x.roundedup = select i1 %x.lowbits.are.zero, i8 %x, i8 %x.biased.highbits
420  ret i8 %x.roundedup
421}
422
423; But if bias is equal to low-bit mask, then we *could* just replace %x.roundedup with %x.biased.highbits
424define i8 @t17_oneuse(i8 %x) {
425; CHECK-LABEL: @t17_oneuse(
426; CHECK-NEXT:    [[X_BIASED:%.*]] = add i8 [[X:%.*]], 15
427; CHECK-NEXT:    [[X_BIASED_HIGHBITS:%.*]] = and i8 [[X_BIASED]], -16
428; CHECK-NEXT:    call void @use.i8(i8 [[X_BIASED_HIGHBITS]])
429; CHECK-NEXT:    ret i8 [[X_BIASED_HIGHBITS]]
430;
431  %x.lowbits = and i8 %x, 15
432  %x.lowbits.are.zero = icmp eq i8 %x.lowbits, 0
433  %x.biased = add i8 %x, 15
434  %x.biased.highbits = and i8 %x.biased, -16
435  call void @use.i8(i8 %x.biased.highbits)
436  %x.roundedup = select i1 %x.lowbits.are.zero, i8 %x, i8 %x.biased.highbits
437  ret i8 %x.roundedup
438}
439
440; Bias is equal to the alignment-1 (as opposed to alignment),
441; so we can just replace %x.roundedup with %x.biased.highbits
442define <2 x i4> @t18_replacement_0b0001(<2 x i4> %x) {
443; CHECK-LABEL: @t18_replacement_0b0001(
444; CHECK-NEXT:    [[X_BIASED:%.*]] = add <2 x i4> [[X:%.*]], <i4 3, i4 3>
445; CHECK-NEXT:    [[X_BIASED_HIGHBITS:%.*]] = and <2 x i4> [[X_BIASED]], <i4 -4, i4 undef>
446; CHECK-NEXT:    call void @use.v2i4(<2 x i4> [[X_BIASED_HIGHBITS]])
447; CHECK-NEXT:    ret <2 x i4> [[X_BIASED_HIGHBITS]]
448;
449  %x.lowbits = and <2 x i4> %x, <i4 3, i4 3>
450  %x.lowbits.are.zero = icmp eq <2 x i4> %x.lowbits, <i4 0, i4 0>
451  %x.biased = add <2 x i4> %x, <i4 3, i4 3>
452  %x.biased.highbits = and <2 x i4> %x.biased, <i4 -4, i4 undef>
453  call void @use.v2i4(<2 x i4> %x.biased.highbits)
454  %x.roundedup = select <2 x i1> %x.lowbits.are.zero, <2 x i4> %x, <2 x i4> %x.biased.highbits
455  ret <2 x i4> %x.roundedup
456}
457define <2 x i4> @t18_replacement_0b0010(<2 x i4> %x) {
458; CHECK-LABEL: @t18_replacement_0b0010(
459; CHECK-NEXT:    [[X_BIASED:%.*]] = add <2 x i4> [[X:%.*]], <i4 3, i4 undef>
460; CHECK-NEXT:    [[X_BIASED_HIGHBITS:%.*]] = and <2 x i4> [[X_BIASED]], <i4 -4, i4 -4>
461; CHECK-NEXT:    call void @use.v2i4(<2 x i4> [[X_BIASED_HIGHBITS]])
462; CHECK-NEXT:    ret <2 x i4> [[X_BIASED_HIGHBITS]]
463;
464  %x.lowbits = and <2 x i4> %x, <i4 3, i4 3>
465  %x.lowbits.are.zero = icmp eq <2 x i4> %x.lowbits, <i4 0, i4 0>
466  %x.biased = add <2 x i4> %x, <i4 3, i4 undef>
467  %x.biased.highbits = and <2 x i4> %x.biased, <i4 -4, i4 -4>
468  call void @use.v2i4(<2 x i4> %x.biased.highbits)
469  %x.roundedup = select <2 x i1> %x.lowbits.are.zero, <2 x i4> %x, <2 x i4> %x.biased.highbits
470  ret <2 x i4> %x.roundedup
471}
472define <2 x i4> @t18_replacement_0b0100(<2 x i4> %x) {
473; CHECK-LABEL: @t18_replacement_0b0100(
474; CHECK-NEXT:    [[X_BIASED:%.*]] = add <2 x i4> [[X:%.*]], <i4 3, i4 3>
475; CHECK-NEXT:    [[X_BIASED_HIGHBITS:%.*]] = and <2 x i4> [[X_BIASED]], <i4 -4, i4 -4>
476; CHECK-NEXT:    call void @use.v2i4(<2 x i4> [[X_BIASED_HIGHBITS]])
477; CHECK-NEXT:    ret <2 x i4> [[X_BIASED_HIGHBITS]]
478;
479  %x.lowbits = and <2 x i4> %x, <i4 3, i4 3>
480  %x.lowbits.are.zero = icmp eq <2 x i4> %x.lowbits, <i4 0, i4 undef>
481  %x.biased = add <2 x i4> %x, <i4 3, i4 3>
482  %x.biased.highbits = and <2 x i4> %x.biased, <i4 -4, i4 -4>
483  call void @use.v2i4(<2 x i4> %x.biased.highbits)
484  %x.roundedup = select <2 x i1> %x.lowbits.are.zero, <2 x i4> %x, <2 x i4> %x.biased.highbits
485  ret <2 x i4> %x.roundedup
486}
487define <2 x i4> @t18_replacement_0b1000(<2 x i4> %x) {
488; CHECK-LABEL: @t18_replacement_0b1000(
489; CHECK-NEXT:    [[X_BIASED:%.*]] = add <2 x i4> [[X:%.*]], <i4 3, i4 3>
490; CHECK-NEXT:    [[X_BIASED_HIGHBITS:%.*]] = and <2 x i4> [[X_BIASED]], <i4 -4, i4 -4>
491; CHECK-NEXT:    call void @use.v2i4(<2 x i4> [[X_BIASED_HIGHBITS]])
492; CHECK-NEXT:    ret <2 x i4> [[X_BIASED_HIGHBITS]]
493;
494  %x.lowbits = and <2 x i4> %x, <i4 3, i4 undef>
495  %x.lowbits.are.zero = icmp eq <2 x i4> %x.lowbits, <i4 0, i4 0>
496  %x.biased = add <2 x i4> %x, <i4 3, i4 3>
497  %x.biased.highbits = and <2 x i4> %x.biased, <i4 -4, i4 -4>
498  call void @use.v2i4(<2 x i4> %x.biased.highbits)
499  %x.roundedup = select <2 x i1> %x.lowbits.are.zero, <2 x i4> %x, <2 x i4> %x.biased.highbits
500  ret <2 x i4> %x.roundedup
501}
502