1 ; RUN: opt -S -instcombine < %s | FileCheck %s 2 3 ; CHECK-LABEL: @t1 4 ; CHECK-NEXT: icmp 5 ; CHECK-NEXT: select 6 ; CHECK-NEXT: sext 7 define i64 @t1(i32 %a) { 8 ; This is the canonical form for a type-changing min/max. 9 %1 = icmp slt i32 %a, 5 10 %2 = select i1 %1, i32 %a, i32 5 11 %3 = sext i32 %2 to i64 12 ret i64 %3 13 } 14 15 ; CHECK-LABEL: @t2 16 ; CHECK-NEXT: icmp 17 ; CHECK-NEXT: select 18 ; CHECK-NEXT: sext 19 define i64 @t2(i32 %a) { 20 ; Check this is converted into canonical form, as above. 21 %1 = icmp slt i32 %a, 5 22 %2 = sext i32 %a to i64 23 %3 = select i1 %1, i64 %2, i64 5 24 ret i64 %3 25 } 26 27 ; CHECK-LABEL: @t3 28 ; CHECK-NEXT: icmp 29 ; CHECK-NEXT: select 30 ; CHECK-NEXT: zext 31 define i64 @t3(i32 %a) { 32 ; Same as @t2, with flipped operands and zext instead of sext. 33 %1 = icmp ult i32 %a, 5 34 %2 = zext i32 %a to i64 35 %3 = select i1 %1, i64 5, i64 %2 36 ret i64 %3 37 } 38 39 ; CHECK-LABEL: @t4 40 ; CHECK-NEXT: icmp 41 ; CHECK-NEXT: select 42 ; CHECK-NEXT: trunc 43 define i32 @t4(i64 %a) { 44 ; Same again, with trunc. 45 %1 = icmp slt i64 %a, 5 46 %2 = trunc i64 %a to i32 47 %3 = select i1 %1, i32 %2, i32 5 48 ret i32 %3 49 } 50 51 ; CHECK-LABEL: @t5 52 ; CHECK-NEXT: icmp 53 ; CHECK-NEXT: zext 54 ; CHECK-NEXT: select 55 define i64 @t5(i32 %a) { 56 ; Same as @t3, but with mismatched signedness between icmp and zext. 57 ; InstCombine should leave this alone. 58 %1 = icmp slt i32 %a, 5 59 %2 = zext i32 %a to i64 60 %3 = select i1 %1, i64 5, i64 %2 61 ret i64 %3 62 } 63 64 ; CHECK-LABEL: @t6 65 ; CHECK-NEXT: icmp 66 ; CHECK-NEXT: select 67 ; CHECK-NEXT: sitofp 68 define float @t6(i32 %a) { 69 %1 = icmp slt i32 %a, 0 70 %2 = select i1 %1, i32 %a, i32 0 71 %3 = sitofp i32 %2 to float 72 ret float %3 73 } 74 75 ; CHECK-LABEL: @t7 76 ; CHECK-NEXT: icmp 77 ; CHECK-NEXT: select 78 ; CHECK-NEXT: trunc 79 define i16 @t7(i32 %a) { 80 %1 = icmp slt i32 %a, -32768 81 %2 = trunc i32 %a to i16 82 %3 = select i1 %1, i16 %2, i16 -32768 83 ret i16 %3 84 } 85 86 ; Just check for no infinite loop. InstSimplify liked to 87 ; "simplify" -32767 by removing all the sign bits, 88 ; which led to a canonicalization fight between different 89 ; parts of instcombine. 90 define i32 @t8(i64 %a, i32 %b) { 91 %1 = icmp slt i64 %a, -32767 92 %2 = select i1 %1, i64 %a, i64 -32767 93 %3 = trunc i64 %2 to i32 94 %4 = icmp slt i32 %b, 42 95 %5 = select i1 %4, i32 42, i32 %3 96 %6 = icmp ne i32 %5, %b 97 %7 = zext i1 %6 to i32 98 ret i32 %7 99 } 100 101 ; Ensure this doesn't get converted to a min/max. 102 ; CHECK-LABEL: @t9 103 ; CHECK-NEXT: icmp 104 ; CHECK-NEXT: sext 105 ; CHECK-NEXT: 4294967295 106 ; CHECK-NEXT: ret 107 define i64 @t9(i32 %a) { 108 %1 = icmp sgt i32 %a, -1 109 %2 = sext i32 %a to i64 110 %3 = select i1 %1, i64 %2, i64 4294967295 111 ret i64 %3 112 } 113