@@ -359,3 +359,111 @@ define i1 @test_icmp_sgt_and_negpow2_invalid_c(i32 %add) {
359359 %cmp = icmp sgt i32 %and , 48
360360 ret i1 %cmp
361361}
362+
363+ define i1 @icmp_eq_or_of_selects_with_constant (i1 %a , i1 %b ) {
364+ ; CHECK-LABEL: @icmp_eq_or_of_selects_with_constant(
365+ ; CHECK-NEXT: [[S1:%.*]] = select i1 [[A:%.*]], i64 65536, i64 0
366+ ; CHECK-NEXT: [[S2:%.*]] = select i1 [[B:%.*]], i64 256, i64 0
367+ ; CHECK-NEXT: [[OR:%.*]] = or disjoint i64 [[S1]], [[S2]]
368+ ; CHECK-NEXT: [[CMP:%.*]] = icmp eq i64 [[OR]], 65792
369+ ; CHECK-NEXT: ret i1 [[CMP]]
370+ ;
371+ %s1 = select i1 %a , i64 65536 , i64 0
372+ %s2 = select i1 %b , i64 256 , i64 0
373+ %or = or i64 %s1 , %s2
374+ %cmp = icmp eq i64 %or , 65792
375+ ret i1 %cmp
376+ }
377+
378+ define i1 @icmp_slt_and_of_selects_with_constant (i1 %a , i1 %b ) {
379+ ; CHECK-LABEL: @icmp_slt_and_of_selects_with_constant(
380+ ; CHECK-NEXT: [[S1:%.*]] = select i1 [[A:%.*]], i8 1, i8 -4
381+ ; CHECK-NEXT: [[S2:%.*]] = select i1 [[B:%.*]], i8 1, i8 -3
382+ ; CHECK-NEXT: [[AND:%.*]] = and i8 [[S1]], [[S2]]
383+ ; CHECK-NEXT: [[CMP:%.*]] = icmp slt i8 [[AND]], -2
384+ ; CHECK-NEXT: ret i1 [[CMP]]
385+ ;
386+ %s1 = select i1 %a , i8 1 , i8 254
387+ %s2 = select i1 %b , i8 1 , i8 253
388+ %and = and i8 %s1 , %s2
389+ %cmp = icmp slt i8 %and , 254
390+ ret i1 %cmp
391+ }
392+
393+ define i1 @icmp_sge_add_of_selects_with_constant (i1 %a , i1 %b ) {
394+ ; CHECK-LABEL: @icmp_sge_add_of_selects_with_constant(
395+ ; CHECK-NEXT: [[S1:%.*]] = select i1 [[A:%.*]], i8 -8, i8 7
396+ ; CHECK-NEXT: [[S2:%.*]] = select i1 [[B:%.*]], i8 16, i8 0
397+ ; CHECK-NEXT: [[ADD:%.*]] = add nsw i8 [[S1]], [[S2]]
398+ ; CHECK-NEXT: [[CMP:%.*]] = icmp sgt i8 [[ADD]], -10
399+ ; CHECK-NEXT: ret i1 [[CMP]]
400+ ;
401+ %s1 = select i1 %a , i8 248 , i8 7
402+ %s2 = select i1 %b , i8 16 , i8 0
403+ %add = add i8 %s1 , %s2
404+ %cmp = icmp sge i8 %add , 247
405+ ret i1 %cmp
406+ }
407+
408+ define <2 x i1 > @icmp_eq_or_of_selects_with_constant_vectorized (<2 x i1 > %a , <2 x i1 > %b ) {
409+ ; CHECK-LABEL: @icmp_eq_or_of_selects_with_constant_vectorized(
410+ ; CHECK-NEXT: [[S1:%.*]] = select <2 x i1> [[A:%.*]], <2 x i64> splat (i64 65536), <2 x i64> zeroinitializer
411+ ; CHECK-NEXT: [[S2:%.*]] = select <2 x i1> [[B:%.*]], <2 x i64> splat (i64 256), <2 x i64> zeroinitializer
412+ ; CHECK-NEXT: [[OR:%.*]] = or disjoint <2 x i64> [[S1]], [[S2]]
413+ ; CHECK-NEXT: [[CMP:%.*]] = icmp eq <2 x i64> [[OR]], splat (i64 65792)
414+ ; CHECK-NEXT: ret <2 x i1> [[CMP]]
415+ ;
416+ %s1 = select <2 x i1 > %a , <2 x i64 > <i64 65536 , i64 65536 >, <2 x i64 > zeroinitializer
417+ %s2 = select <2 x i1 > %b , <2 x i64 > <i64 256 , i64 256 >, <2 x i64 > zeroinitializer
418+ %or = or <2 x i64 > %s1 , %s2
419+ %cmp = icmp eq <2 x i64 > %or , <i64 65792 , i64 65792 >
420+ ret <2 x i1 > %cmp
421+ }
422+
423+ ; Negative tests.
424+ define i1 @icmp_eq_or_of_selects_with_constant_and_arg (i1 %a , i1 %b , i64 %arg ) {
425+ ; CHECK-LABEL: @icmp_eq_or_of_selects_with_constant_and_arg(
426+ ; CHECK-NEXT: [[S1:%.*]] = select i1 [[A:%.*]], i64 65536, i64 [[ARG:%.*]]
427+ ; CHECK-NEXT: [[S2:%.*]] = select i1 [[B:%.*]], i64 256, i64 0
428+ ; CHECK-NEXT: [[OR:%.*]] = or i64 [[S1]], [[S2]]
429+ ; CHECK-NEXT: [[CMP:%.*]] = icmp eq i64 [[OR]], 65792
430+ ; CHECK-NEXT: ret i1 [[CMP]]
431+ ;
432+ %s1 = select i1 %a , i64 65536 , i64 %arg
433+ %s2 = select i1 %b , i64 256 , i64 0
434+ %or = or i64 %s1 , %s2
435+ %cmp = icmp eq i64 %or , 65792
436+ ret i1 %cmp
437+ }
438+
439+ define i1 @icmp_eq_or_of_selects_with_constant_multiuse (i1 %a , i1 %b ) {
440+ ; CHECK-LABEL: @icmp_eq_or_of_selects_with_constant_multiuse(
441+ ; CHECK-NEXT: [[S1:%.*]] = select i1 [[A:%.*]], i64 0, i64 65536
442+ ; CHECK-NEXT: [[S2:%.*]] = select i1 [[B:%.*]], i64 0, i64 256
443+ ; CHECK-NEXT: [[OR:%.*]] = or disjoint i64 [[S1]], [[S2]]
444+ ; CHECK-NEXT: call void @use64(i64 [[OR]])
445+ ; CHECK-NEXT: [[CMP:%.*]] = icmp eq i64 [[OR]], 65792
446+ ; CHECK-NEXT: ret i1 [[CMP]]
447+ ;
448+ %s1 = select i1 %a , i64 0 , i64 65536
449+ %s2 = select i1 %b , i64 0 , i64 256
450+ %or = or i64 %s1 , %s2
451+ call void @use64 (i64 %or )
452+ %cmp = icmp eq i64 %or , 65792
453+ ret i1 %cmp
454+ }
455+
456+ define <2 x i1 > @icmp_eq_or_of_selects_with_constant_vectorized_nonsplat (<2 x i1 > %a , <2 x i1 > %b ) {
457+ ; CHECK-LABEL: @icmp_eq_or_of_selects_with_constant_vectorized_nonsplat(
458+ ; CHECK-NEXT: [[S1:%.*]] = select <2 x i1> [[A:%.*]], <2 x i64> splat (i64 65536), <2 x i64> zeroinitializer
459+ ; CHECK-NEXT: [[S2:%.*]] = select <2 x i1> [[B:%.*]], <2 x i64> <i64 256, i64 128>, <2 x i64> zeroinitializer
460+ ; CHECK-NEXT: [[OR:%.*]] = or disjoint <2 x i64> [[S1]], [[S2]]
461+ ; CHECK-NEXT: [[CMP:%.*]] = icmp eq <2 x i64> [[OR]], <i64 65792, i64 65664>
462+ ; CHECK-NEXT: ret <2 x i1> [[CMP]]
463+ ;
464+ %s1 = select <2 x i1 > %a , <2 x i64 > <i64 65536 , i64 65536 >, <2 x i64 > zeroinitializer
465+ %s2 = select <2 x i1 > %b , <2 x i64 > <i64 256 , i64 128 >, <2 x i64 > zeroinitializer
466+ %or = or <2 x i64 > %s1 , %s2
467+ %cmp = icmp eq <2 x i64 > %or , <i64 65792 , i64 65664 >
468+ ret <2 x i1 > %cmp
469+ }
0 commit comments