Skip to content

Commit ee46e02

Browse files
committed
Pre-commit test (NFC)
1 parent c5f1c69 commit ee46e02

File tree

1 file changed

+190
-0
lines changed

1 file changed

+190
-0
lines changed

llvm/test/Transforms/InstCombine/sext-a-lt-b-plus-zext-a-gt-b-to-uscmp.ll

Lines changed: 190 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -182,3 +182,193 @@ define i8 @signed_add_neg5(i32 %a, i32 %b) {
182182
%r = add i8 %lt8, %gt8
183183
ret i8 %r
184184
}
185+
186+
; sext(A s<= B) + zext(A s>= B) => scmp(A, B)
187+
define i8 @signed_add_ge_le(i32 %a, i32 %b) {
188+
; CHECK-LABEL: define i8 @signed_add_ge_le(
189+
; CHECK-SAME: i32 [[A:%.*]], i32 [[B:%.*]]) {
190+
; CHECK-NEXT: [[LE:%.*]] = icmp sle i32 [[A]], [[B]]
191+
; CHECK-NEXT: [[LE8:%.*]] = sext i1 [[LE]] to i8
192+
; CHECK-NEXT: [[GE:%.*]] = icmp sge i32 [[A]], [[B]]
193+
; CHECK-NEXT: [[GE8:%.*]] = zext i1 [[GE]] to i8
194+
; CHECK-NEXT: [[R:%.*]] = add nsw i8 [[LE8]], [[GE8]]
195+
; CHECK-NEXT: ret i8 [[R]]
196+
;
197+
%le = icmp sle i32 %a, %b
198+
%le8 = sext i1 %le to i8
199+
%ge = icmp sge i32 %a, %b
200+
%ge8 = zext i1 %ge to i8
201+
%r = add i8 %le8, %ge8
202+
ret i8 %r
203+
}
204+
205+
; Unsigned version of >= and <=
206+
define i8 @unsigned_add_ge_le(i32 %a, i32 %b) {
207+
; CHECK-LABEL: define i8 @unsigned_add_ge_le(
208+
; CHECK-SAME: i32 [[A:%.*]], i32 [[B:%.*]]) {
209+
; CHECK-NEXT: [[LE:%.*]] = icmp ule i32 [[A]], [[B]]
210+
; CHECK-NEXT: [[LE8:%.*]] = sext i1 [[LE]] to i8
211+
; CHECK-NEXT: [[GE:%.*]] = icmp uge i32 [[A]], [[B]]
212+
; CHECK-NEXT: [[GE8:%.*]] = zext i1 [[GE]] to i8
213+
; CHECK-NEXT: [[R:%.*]] = add nsw i8 [[LE8]], [[GE8]]
214+
; CHECK-NEXT: ret i8 [[R]]
215+
;
216+
%le = icmp ule i32 %a, %b
217+
%le8 = sext i1 %le to i8
218+
%ge = icmp uge i32 %a, %b
219+
%ge8 = zext i1 %ge to i8
220+
%r = add i8 %le8, %ge8
221+
ret i8 %r
222+
}
223+
224+
; zext(A s>= B) - zext(A s<= B) => scmp(A, B)
225+
define i8 @signed_sub_ge_le(i32 %a, i32 %b) {
226+
; CHECK-LABEL: define i8 @signed_sub_ge_le(
227+
; CHECK-SAME: i32 [[A:%.*]], i32 [[B:%.*]]) {
228+
; CHECK-NEXT: [[LE:%.*]] = icmp sle i32 [[A]], [[B]]
229+
; CHECK-NEXT: [[LE8_NEG:%.*]] = sext i1 [[LE]] to i8
230+
; CHECK-NEXT: [[GE:%.*]] = icmp sge i32 [[A]], [[B]]
231+
; CHECK-NEXT: [[GE8:%.*]] = zext i1 [[GE]] to i8
232+
; CHECK-NEXT: [[R:%.*]] = add nsw i8 [[LE8_NEG]], [[GE8]]
233+
; CHECK-NEXT: ret i8 [[R]]
234+
;
235+
%le = icmp sle i32 %a, %b
236+
%le8 = zext i1 %le to i8
237+
%ge = icmp sge i32 %a, %b
238+
%ge8 = zext i1 %ge to i8
239+
%r = sub i8 %ge8, %le8
240+
ret i8 %r
241+
}
242+
243+
; Unsigned version of >= and <= subtraction
244+
define i8 @unsigned_sub_ge_le(i32 %a, i32 %b) {
245+
; CHECK-LABEL: define i8 @unsigned_sub_ge_le(
246+
; CHECK-SAME: i32 [[A:%.*]], i32 [[B:%.*]]) {
247+
; CHECK-NEXT: [[LE:%.*]] = icmp ule i32 [[A]], [[B]]
248+
; CHECK-NEXT: [[LE8_NEG:%.*]] = sext i1 [[LE]] to i8
249+
; CHECK-NEXT: [[GE:%.*]] = icmp uge i32 [[A]], [[B]]
250+
; CHECK-NEXT: [[GE8:%.*]] = zext i1 [[GE]] to i8
251+
; CHECK-NEXT: [[R:%.*]] = add nsw i8 [[LE8_NEG]], [[GE8]]
252+
; CHECK-NEXT: ret i8 [[R]]
253+
;
254+
%le = icmp ule i32 %a, %b
255+
%le8 = zext i1 %le to i8
256+
%ge = icmp uge i32 %a, %b
257+
%ge8 = zext i1 %ge to i8
258+
%r = sub i8 %ge8, %le8
259+
ret i8 %r
260+
}
261+
262+
; Constant canonicalization: (a > 4) - (a < 6) => scmp(a, 5)
263+
define i8 @signed_sub_const_canonicalization(i32 %a) {
264+
; CHECK-LABEL: define i8 @signed_sub_const_canonicalization(
265+
; CHECK-SAME: i32 [[A:%.*]]) {
266+
; CHECK-NEXT: [[LT:%.*]] = icmp slt i32 [[A]], 6
267+
; CHECK-NEXT: [[LT8_NEG:%.*]] = sext i1 [[LT]] to i8
268+
; CHECK-NEXT: [[GT:%.*]] = icmp sgt i32 [[A]], 4
269+
; CHECK-NEXT: [[GT8:%.*]] = zext i1 [[GT]] to i8
270+
; CHECK-NEXT: [[R:%.*]] = add nsw i8 [[LT8_NEG]], [[GT8]]
271+
; CHECK-NEXT: ret i8 [[R]]
272+
;
273+
%lt = icmp slt i32 %a, 6
274+
%lt8 = zext i1 %lt to i8
275+
%gt = icmp sgt i32 %a, 4
276+
%gt8 = zext i1 %gt to i8
277+
%r = sub i8 %gt8, %lt8
278+
ret i8 %r
279+
}
280+
281+
; Constant canonicalization: (a >= 5) - (a <= 5) => scmp(a, 5)
282+
define i8 @signed_sub_const_canonicalization2(i32 %a) {
283+
; CHECK-LABEL: define i8 @signed_sub_const_canonicalization2(
284+
; CHECK-SAME: i32 [[A:%.*]]) {
285+
; CHECK-NEXT: [[LE:%.*]] = icmp slt i32 [[A]], 6
286+
; CHECK-NEXT: [[LE8_NEG:%.*]] = sext i1 [[LE]] to i8
287+
; CHECK-NEXT: [[GE:%.*]] = icmp sgt i32 [[A]], 4
288+
; CHECK-NEXT: [[GE8:%.*]] = zext i1 [[GE]] to i8
289+
; CHECK-NEXT: [[R:%.*]] = add nsw i8 [[LE8_NEG]], [[GE8]]
290+
; CHECK-NEXT: ret i8 [[R]]
291+
;
292+
%le = icmp sle i32 %a, 5
293+
%le8 = zext i1 %le to i8
294+
%ge = icmp sge i32 %a, 5
295+
%ge8 = zext i1 %ge to i8
296+
%r = sub i8 %ge8, %le8
297+
ret i8 %r
298+
}
299+
300+
; Unsigned constant canonicalization: (a > 4) - (a < 6) => ucmp(a, 5)
301+
define i8 @unsigned_sub_const_canonicalization(i32 %a) {
302+
; CHECK-LABEL: define i8 @unsigned_sub_const_canonicalization(
303+
; CHECK-SAME: i32 [[A:%.*]]) {
304+
; CHECK-NEXT: [[LT:%.*]] = icmp ult i32 [[A]], 6
305+
; CHECK-NEXT: [[LT8_NEG:%.*]] = sext i1 [[LT]] to i8
306+
; CHECK-NEXT: [[GT:%.*]] = icmp ugt i32 [[A]], 4
307+
; CHECK-NEXT: [[GT8:%.*]] = zext i1 [[GT]] to i8
308+
; CHECK-NEXT: [[R:%.*]] = add nsw i8 [[LT8_NEG]], [[GT8]]
309+
; CHECK-NEXT: ret i8 [[R]]
310+
;
311+
%lt = icmp ult i32 %a, 6
312+
%lt8 = zext i1 %lt to i8
313+
%gt = icmp ugt i32 %a, 4
314+
%gt8 = zext i1 %gt to i8
315+
%r = sub i8 %gt8, %lt8
316+
ret i8 %r
317+
}
318+
319+
; Constant canonicalization with >= and <=: (a >= 5) - (a <= 5) => scmp(a, 5)
320+
define i8 @signed_sub_const_canonicalization_ge_le(i32 %a) {
321+
; CHECK-LABEL: define i8 @signed_sub_const_canonicalization_ge_le(
322+
; CHECK-SAME: i32 [[A:%.*]]) {
323+
; CHECK-NEXT: [[LE:%.*]] = icmp slt i32 [[A]], 6
324+
; CHECK-NEXT: [[LE8_NEG:%.*]] = sext i1 [[LE]] to i8
325+
; CHECK-NEXT: [[GE:%.*]] = icmp sgt i32 [[A]], 4
326+
; CHECK-NEXT: [[GE8:%.*]] = zext i1 [[GE]] to i8
327+
; CHECK-NEXT: [[R:%.*]] = add nsw i8 [[LE8_NEG]], [[GE8]]
328+
; CHECK-NEXT: ret i8 [[R]]
329+
;
330+
%le = icmp sle i32 %a, 5
331+
%le8 = zext i1 %le to i8
332+
%ge = icmp sge i32 %a, 5
333+
%ge8 = zext i1 %ge to i8
334+
%r = sub i8 %ge8, %le8
335+
ret i8 %r
336+
}
337+
338+
; More constant canonicalization: (a > 2) - (a < 4) => scmp(a, 3)
339+
define i8 @signed_sub_const_canonicalization3(i32 %a) {
340+
; CHECK-LABEL: define i8 @signed_sub_const_canonicalization3(
341+
; CHECK-SAME: i32 [[A:%.*]]) {
342+
; CHECK-NEXT: [[LT:%.*]] = icmp slt i32 [[A]], 4
343+
; CHECK-NEXT: [[LT8_NEG:%.*]] = sext i1 [[LT]] to i8
344+
; CHECK-NEXT: [[GT:%.*]] = icmp sgt i32 [[A]], 2
345+
; CHECK-NEXT: [[GT8:%.*]] = zext i1 [[GT]] to i8
346+
; CHECK-NEXT: [[R:%.*]] = add nsw i8 [[LT8_NEG]], [[GT8]]
347+
; CHECK-NEXT: ret i8 [[R]]
348+
;
349+
%lt = icmp slt i32 %a, 4
350+
%lt8 = zext i1 %lt to i8
351+
%gt = icmp sgt i32 %a, 2
352+
%gt8 = zext i1 %gt to i8
353+
%r = sub i8 %gt8, %lt8
354+
ret i8 %r
355+
}
356+
357+
; Negative test: constants that are more than one apart - should NOT canonicalize
358+
define i8 @signed_sub_const_no_canonicalization(i32 %a) {
359+
; CHECK-LABEL: define i8 @signed_sub_const_no_canonicalization(
360+
; CHECK-SAME: i32 [[A:%.*]]) {
361+
; CHECK-NEXT: [[LT:%.*]] = icmp slt i32 [[A]], 10
362+
; CHECK-NEXT: [[LT8_NEG:%.*]] = sext i1 [[LT]] to i8
363+
; CHECK-NEXT: [[GT:%.*]] = icmp sgt i32 [[A]], 4
364+
; CHECK-NEXT: [[GT8:%.*]] = zext i1 [[GT]] to i8
365+
; CHECK-NEXT: [[R:%.*]] = add nsw i8 [[LT8_NEG]], [[GT8]]
366+
; CHECK-NEXT: ret i8 [[R]]
367+
;
368+
%lt = icmp slt i32 %a, 10
369+
%lt8 = zext i1 %lt to i8
370+
%gt = icmp sgt i32 %a, 4
371+
%gt8 = zext i1 %gt to i8
372+
%r = sub i8 %gt8, %lt8
373+
ret i8 %r
374+
}

0 commit comments

Comments
 (0)