Home | History | Annotate | Download | only in InstCombine
      1 ; NOTE: Assertions have been autogenerated by utils/update_test_checks.py
      2 ; RUN: opt < %s -instcombine -S | FileCheck %s
      3 
      4 ; Widen a select of constants to eliminate an extend.
      5 
      6 define i16 @sel_sext_constants(i1 %cmp) {
      7 ; CHECK-LABEL: @sel_sext_constants(
      8 ; CHECK-NEXT:    [[EXT:%.*]] = select i1 %cmp, i16 -1, i16 42
      9 ; CHECK-NEXT:    ret i16 [[EXT]]
     10 ;
     11   %sel = select i1 %cmp, i8 255, i8 42
     12   %ext = sext i8 %sel to i16
     13   ret i16 %ext
     14 }
     15 
     16 define i16 @sel_zext_constants(i1 %cmp) {
     17 ; CHECK-LABEL: @sel_zext_constants(
     18 ; CHECK-NEXT:    [[EXT:%.*]] = select i1 %cmp, i16 255, i16 42
     19 ; CHECK-NEXT:    ret i16 [[EXT]]
     20 ;
     21   %sel = select i1 %cmp, i8 255, i8 42
     22   %ext = zext i8 %sel to i16
     23   ret i16 %ext
     24 }
     25 
     26 define double @sel_fpext_constants(i1 %cmp) {
     27 ; CHECK-LABEL: @sel_fpext_constants(
     28 ; CHECK-NEXT:    [[EXT:%.*]] = select i1 %cmp, double -2.550000e+02, double 4.200000e+01
     29 ; CHECK-NEXT:    ret double [[EXT]]
     30 ;
     31   %sel = select i1 %cmp, float -255.0, float 42.0
     32   %ext = fpext float %sel to double
     33   ret double %ext
     34 }
     35 
     36 ; FIXME: We should not grow the size of the select in the next 4 cases.
     37 
     38 define i64 @sel_sext(i32 %a, i1 %cmp) {
     39 ; CHECK-LABEL: @sel_sext(
     40 ; CHECK-NEXT:    [[TMP1:%.*]] = sext i32 %a to i64
     41 ; CHECK-NEXT:    [[EXT:%.*]] = select i1 %cmp, i64 [[TMP1]], i64 42
     42 ; CHECK-NEXT:    ret i64 [[EXT]]
     43 ;
     44   %sel = select i1 %cmp, i32 %a, i32 42
     45   %ext = sext i32 %sel to i64
     46   ret i64 %ext
     47 }
     48 
     49 define <4 x i64> @sel_sext_vec(<4 x i32> %a, <4 x i1> %cmp) {
     50 ; CHECK-LABEL: @sel_sext_vec(
     51 ; CHECK-NEXT:    [[TMP1:%.*]] = sext <4 x i32> %a to <4 x i64>
     52 ; CHECK-NEXT:    [[EXT:%.*]] = select <4 x i1> %cmp, <4 x i64> [[TMP1]], <4 x i64> <i64 42, i64 42, i64 42, i64 42>
     53 ; CHECK-NEXT:    ret <4 x i64> [[EXT]]
     54 ;
     55   %sel = select <4 x i1> %cmp, <4 x i32> %a, <4 x i32> <i32 42, i32 42, i32 42, i32 42>
     56   %ext = sext <4 x i32> %sel to <4 x i64>
     57   ret <4 x i64> %ext
     58 }
     59 
     60 define i64 @sel_zext(i32 %a, i1 %cmp) {
     61 ; CHECK-LABEL: @sel_zext(
     62 ; CHECK-NEXT:    [[TMP1:%.*]] = zext i32 %a to i64
     63 ; CHECK-NEXT:    [[EXT:%.*]] = select i1 %cmp, i64 [[TMP1]], i64 42
     64 ; CHECK-NEXT:    ret i64 [[EXT]]
     65 ;
     66   %sel = select i1 %cmp, i32 %a, i32 42
     67   %ext = zext i32 %sel to i64
     68   ret i64 %ext
     69 }
     70 
     71 define <4 x i64> @sel_zext_vec(<4 x i32> %a, <4 x i1> %cmp) {
     72 ; CHECK-LABEL: @sel_zext_vec(
     73 ; CHECK-NEXT:    [[TMP1:%.*]] = zext <4 x i32> %a to <4 x i64>
     74 ; CHECK-NEXT:    [[EXT:%.*]] = select <4 x i1> %cmp, <4 x i64> [[TMP1]], <4 x i64> <i64 42, i64 42, i64 42, i64 42>
     75 ; CHECK-NEXT:    ret <4 x i64> [[EXT]]
     76 ;
     77   %sel = select <4 x i1> %cmp, <4 x i32> %a, <4 x i32> <i32 42, i32 42, i32 42, i32 42>
     78   %ext = zext <4 x i32> %sel to <4 x i64>
     79   ret <4 x i64> %ext
     80 }
     81 
     82 ; FIXME: The next 18 tests cycle through trunc+select and {larger,smaller,equal} {sext,zext,fpext} {scalar,vector}.
     83 ; The only cases where we eliminate an instruction are equal zext with scalar/vector, so that's probably the only
     84 ; way to justify widening the select.
     85 
     86 define i64 @trunc_sel_larger_sext(i32 %a, i1 %cmp) {
     87 ; CHECK-LABEL: @trunc_sel_larger_sext(
     88 ; CHECK-NEXT:    [[TRUNC:%.*]] = trunc i32 %a to i16
     89 ; CHECK-NEXT:    [[TMP1:%.*]] = sext i16 [[TRUNC]] to i64
     90 ; CHECK-NEXT:    [[EXT:%.*]] = select i1 %cmp, i64 [[TMP1]], i64 42
     91 ; CHECK-NEXT:    ret i64 [[EXT]]
     92 ;
     93   %trunc = trunc i32 %a to i16
     94   %sel = select i1 %cmp, i16 %trunc, i16 42
     95   %ext = sext i16 %sel to i64
     96   ret i64 %ext
     97 }
     98 
     99 define <2 x i64> @trunc_sel_larger_sext_vec(<2 x i32> %a, <2 x i1> %cmp) {
    100 ; CHECK-LABEL: @trunc_sel_larger_sext_vec(
    101 ; CHECK-NEXT:    [[TRUNC:%.*]] = zext <2 x i32> %a to <2 x i64>
    102 ; CHECK-NEXT:    [[SEXT:%.*]] = shl <2 x i64> [[TRUNC]], <i64 48, i64 48>
    103 ; CHECK-NEXT:    [[TMP1:%.*]] = ashr exact <2 x i64> [[SEXT]], <i64 48, i64 48>
    104 ; CHECK-NEXT:    [[EXT:%.*]] = select <2 x i1> %cmp, <2 x i64> [[TMP1]], <2 x i64> <i64 42, i64 43>
    105 ; CHECK-NEXT:    ret <2 x i64> [[EXT]]
    106 ;
    107   %trunc = trunc <2 x i32> %a to <2 x i16>
    108   %sel = select <2 x i1> %cmp, <2 x i16> %trunc, <2 x i16> <i16 42, i16 43>
    109   %ext = sext <2 x i16> %sel to <2 x i64>
    110   ret <2 x i64> %ext
    111 }
    112 
    113 define i32 @trunc_sel_smaller_sext(i64 %a, i1 %cmp) {
    114 ; CHECK-LABEL: @trunc_sel_smaller_sext(
    115 ; CHECK-NEXT:    [[TRUNC:%.*]] = trunc i64 %a to i16
    116 ; CHECK-NEXT:    [[TMP1:%.*]] = sext i16 [[TRUNC]] to i32
    117 ; CHECK-NEXT:    [[EXT:%.*]] = select i1 %cmp, i32 [[TMP1]], i32 42
    118 ; CHECK-NEXT:    ret i32 [[EXT]]
    119 ;
    120   %trunc = trunc i64 %a to i16
    121   %sel = select i1 %cmp, i16 %trunc, i16 42
    122   %ext = sext i16 %sel to i32
    123   ret i32 %ext
    124 }
    125 
    126 define <2 x i32> @trunc_sel_smaller_sext_vec(<2 x i64> %a, <2 x i1> %cmp) {
    127 ; CHECK-LABEL: @trunc_sel_smaller_sext_vec(
    128 ; CHECK-NEXT:    [[TRUNC:%.*]] = trunc <2 x i64> %a to <2 x i32>
    129 ; CHECK-NEXT:    [[SEXT:%.*]] = shl <2 x i32> [[TRUNC]], <i32 16, i32 16>
    130 ; CHECK-NEXT:    [[TMP1:%.*]] = ashr exact <2 x i32> [[SEXT]], <i32 16, i32 16>
    131 ; CHECK-NEXT:    [[EXT:%.*]] = select <2 x i1> %cmp, <2 x i32> [[TMP1]], <2 x i32> <i32 42, i32 43>
    132 ; CHECK-NEXT:    ret <2 x i32> [[EXT]]
    133 ;
    134   %trunc = trunc <2 x i64> %a to <2 x i16>
    135   %sel = select <2 x i1> %cmp, <2 x i16> %trunc, <2 x i16> <i16 42, i16 43>
    136   %ext = sext <2 x i16> %sel to <2 x i32>
    137   ret <2 x i32> %ext
    138 }
    139 
    140 define i32 @trunc_sel_equal_sext(i32 %a, i1 %cmp) {
    141 ; CHECK-LABEL: @trunc_sel_equal_sext(
    142 ; CHECK-NEXT:    [[SEXT:%.*]] = shl i32 %a, 16
    143 ; CHECK-NEXT:    [[TMP1:%.*]] = ashr exact i32 [[SEXT]], 16
    144 ; CHECK-NEXT:    [[EXT:%.*]] = select i1 %cmp, i32 [[TMP1]], i32 42
    145 ; CHECK-NEXT:    ret i32 [[EXT]]
    146 ;
    147   %trunc = trunc i32 %a to i16
    148   %sel = select i1 %cmp, i16 %trunc, i16 42
    149   %ext = sext i16 %sel to i32
    150   ret i32 %ext
    151 }
    152 
    153 define <2 x i32> @trunc_sel_equal_sext_vec(<2 x i32> %a, <2 x i1> %cmp) {
    154 ; CHECK-LABEL: @trunc_sel_equal_sext_vec(
    155 ; CHECK-NEXT:    [[SEXT:%.*]] = shl <2 x i32> %a, <i32 16, i32 16>
    156 ; CHECK-NEXT:    [[TMP1:%.*]] = ashr exact <2 x i32> [[SEXT]], <i32 16, i32 16>
    157 ; CHECK-NEXT:    [[EXT:%.*]] = select <2 x i1> %cmp, <2 x i32> [[TMP1]], <2 x i32> <i32 42, i32 43>
    158 ; CHECK-NEXT:    ret <2 x i32> [[EXT]]
    159 ;
    160   %trunc = trunc <2 x i32> %a to <2 x i16>
    161   %sel = select <2 x i1> %cmp, <2 x i16> %trunc, <2 x i16> <i16 42, i16 43>
    162   %ext = sext <2 x i16> %sel to <2 x i32>
    163   ret <2 x i32> %ext
    164 }
    165 
    166 define i64 @trunc_sel_larger_zext(i32 %a, i1 %cmp) {
    167 ; CHECK-LABEL: @trunc_sel_larger_zext(
    168 ; CHECK-NEXT:    [[TRUNC_MASK:%.*]] = and i32 %a, 65535
    169 ; CHECK-NEXT:    [[TMP1:%.*]] = zext i32 [[TRUNC_MASK]] to i64
    170 ; CHECK-NEXT:    [[EXT:%.*]] = select i1 %cmp, i64 [[TMP1]], i64 42
    171 ; CHECK-NEXT:    ret i64 [[EXT]]
    172 ;
    173   %trunc = trunc i32 %a to i16
    174   %sel = select i1 %cmp, i16 %trunc, i16 42
    175   %ext = zext i16 %sel to i64
    176   ret i64 %ext
    177 }
    178 
    179 define <2 x i64> @trunc_sel_larger_zext_vec(<2 x i32> %a, <2 x i1> %cmp) {
    180 ; CHECK-LABEL: @trunc_sel_larger_zext_vec(
    181 ; CHECK-NEXT:    [[TMP1:%.*]] = and <2 x i32> %a, <i32 65535, i32 65535>
    182 ; CHECK-NEXT:    [[TMP2:%.*]] = zext <2 x i32> [[TMP1]] to <2 x i64>
    183 ; CHECK-NEXT:    [[EXT:%.*]] = select <2 x i1> %cmp, <2 x i64> [[TMP2]], <2 x i64> <i64 42, i64 43>
    184 ; CHECK-NEXT:    ret <2 x i64> [[EXT]]
    185 ;
    186   %trunc = trunc <2 x i32> %a to <2 x i16>
    187   %sel = select <2 x i1> %cmp, <2 x i16> %trunc, <2 x i16> <i16 42, i16 43>
    188   %ext = zext <2 x i16> %sel to <2 x i64>
    189   ret <2 x i64> %ext
    190 }
    191 
    192 define i32 @trunc_sel_smaller_zext(i64 %a, i1 %cmp) {
    193 ; CHECK-LABEL: @trunc_sel_smaller_zext(
    194 ; CHECK-NEXT:    [[TMP1:%.*]] = trunc i64 %a to i32
    195 ; CHECK-NEXT:    [[TMP2:%.*]] = and i32 [[TMP1]], 65535
    196 ; CHECK-NEXT:    [[EXT:%.*]] = select i1 %cmp, i32 [[TMP2]], i32 42
    197 ; CHECK-NEXT:    ret i32 [[EXT]]
    198 ;
    199   %trunc = trunc i64 %a to i16
    200   %sel = select i1 %cmp, i16 %trunc, i16 42
    201   %ext = zext i16 %sel to i32
    202   ret i32 %ext
    203 }
    204 
    205 define <2 x i32> @trunc_sel_smaller_zext_vec(<2 x i64> %a, <2 x i1> %cmp) {
    206 ; CHECK-LABEL: @trunc_sel_smaller_zext_vec(
    207 ; CHECK-NEXT:    [[TRUNC:%.*]] = trunc <2 x i64> %a to <2 x i32>
    208 ; CHECK-NEXT:    [[TMP1:%.*]] = and <2 x i32> [[TRUNC]], <i32 65535, i32 65535>
    209 ; CHECK-NEXT:    [[EXT:%.*]] = select <2 x i1> %cmp, <2 x i32> [[TMP1]], <2 x i32> <i32 42, i32 43>
    210 ; CHECK-NEXT:    ret <2 x i32> [[EXT]]
    211 ;
    212   %trunc = trunc <2 x i64> %a to <2 x i16>
    213   %sel = select <2 x i1> %cmp, <2 x i16> %trunc, <2 x i16> <i16 42, i16 43>
    214   %ext = zext <2 x i16> %sel to <2 x i32>
    215   ret <2 x i32> %ext
    216 }
    217 
    218 define i32 @trunc_sel_equal_zext(i32 %a, i1 %cmp) {
    219 ; CHECK-LABEL: @trunc_sel_equal_zext(
    220 ; CHECK-NEXT:    [[TMP1:%.*]] = and i32 %a, 65535
    221 ; CHECK-NEXT:    [[EXT:%.*]] = select i1 %cmp, i32 [[TMP1]], i32 42
    222 ; CHECK-NEXT:    ret i32 [[EXT]]
    223 ;
    224   %trunc = trunc i32 %a to i16
    225   %sel = select i1 %cmp, i16 %trunc, i16 42
    226   %ext = zext i16 %sel to i32
    227   ret i32 %ext
    228 }
    229 
    230 define <2 x i32> @trunc_sel_equal_zext_vec(<2 x i32> %a, <2 x i1> %cmp) {
    231 ; CHECK-LABEL: @trunc_sel_equal_zext_vec(
    232 ; CHECK-NEXT:    [[TMP1:%.*]] = and <2 x i32> %a, <i32 65535, i32 65535>
    233 ; CHECK-NEXT:    [[EXT:%.*]] = select <2 x i1> %cmp, <2 x i32> [[TMP1]], <2 x i32> <i32 42, i32 43>
    234 ; CHECK-NEXT:    ret <2 x i32> [[EXT]]
    235 ;
    236   %trunc = trunc <2 x i32> %a to <2 x i16>
    237   %sel = select <2 x i1> %cmp, <2 x i16> %trunc, <2 x i16> <i16 42, i16 43>
    238   %ext = zext <2 x i16> %sel to <2 x i32>
    239   ret <2 x i32> %ext
    240 }
    241 
    242 define double @trunc_sel_larger_fpext(float %a, i1 %cmp) {
    243 ; CHECK-LABEL: @trunc_sel_larger_fpext(
    244 ; CHECK-NEXT:    [[TRUNC:%.*]] = fptrunc float %a to half
    245 ; CHECK-NEXT:    [[TMP1:%.*]] = fpext half [[TRUNC]] to double
    246 ; CHECK-NEXT:    [[EXT:%.*]] = select i1 %cmp, double [[TMP1]], double 4.200000e+01
    247 ; CHECK-NEXT:    ret double [[EXT]]
    248 ;
    249   %trunc = fptrunc float %a to half
    250   %sel = select i1 %cmp, half %trunc, half 42.0
    251   %ext = fpext half %sel to double
    252   ret double %ext
    253 }
    254 
    255 define <2 x double> @trunc_sel_larger_fpext_vec(<2 x float> %a, <2 x i1> %cmp) {
    256 ; CHECK-LABEL: @trunc_sel_larger_fpext_vec(
    257 ; CHECK-NEXT:    [[TRUNC:%.*]] = fptrunc <2 x float> %a to <2 x half>
    258 ; CHECK-NEXT:    [[TMP1:%.*]] = fpext <2 x half> [[TRUNC]] to <2 x double>
    259 ; CHECK-NEXT:    [[EXT:%.*]] = select <2 x i1> %cmp, <2 x double> [[TMP1]], <2 x double> <double 4.200000e+01, double 4.300000e+01>
    260 ; CHECK-NEXT:    ret <2 x double> [[EXT]]
    261 ;
    262   %trunc = fptrunc <2 x float> %a to <2 x half>
    263   %sel = select <2 x i1> %cmp, <2 x half> %trunc, <2 x half> <half 42.0, half 43.0>
    264   %ext = fpext <2 x half> %sel to <2 x double>
    265   ret <2 x double> %ext
    266 }
    267 
    268 define float @trunc_sel_smaller_fpext(double %a, i1 %cmp) {
    269 ; CHECK-LABEL: @trunc_sel_smaller_fpext(
    270 ; CHECK-NEXT:    [[TRUNC:%.*]] = fptrunc double %a to half
    271 ; CHECK-NEXT:    [[TMP1:%.*]] = fpext half [[TRUNC]] to float
    272 ; CHECK-NEXT:    [[EXT:%.*]] = select i1 %cmp, float [[TMP1]], float 4.200000e+01
    273 ; CHECK-NEXT:    ret float [[EXT]]
    274 ;
    275   %trunc = fptrunc double %a to half
    276   %sel = select i1 %cmp, half %trunc, half 42.0
    277   %ext = fpext half %sel to float
    278   ret float %ext
    279 }
    280 
    281 define <2 x float> @trunc_sel_smaller_fpext_vec(<2 x double> %a, <2 x i1> %cmp) {
    282 ; CHECK-LABEL: @trunc_sel_smaller_fpext_vec(
    283 ; CHECK-NEXT:    [[TRUNC:%.*]] = fptrunc <2 x double> %a to <2 x half>
    284 ; CHECK-NEXT:    [[TMP1:%.*]] = fpext <2 x half> [[TRUNC]] to <2 x float>
    285 ; CHECK-NEXT:    [[EXT:%.*]] = select <2 x i1> %cmp, <2 x float> [[TMP1]], <2 x float> <float 4.200000e+01, float 4.300000e+01>
    286 ; CHECK-NEXT:    ret <2 x float> [[EXT]]
    287 ;
    288   %trunc = fptrunc <2 x double> %a to <2 x half>
    289   %sel = select <2 x i1> %cmp, <2 x half> %trunc, <2 x half> <half 42.0, half 43.0>
    290   %ext = fpext <2 x half> %sel to <2 x float>
    291   ret <2 x float> %ext
    292 }
    293 
    294 define float @trunc_sel_equal_fpext(float %a, i1 %cmp) {
    295 ; CHECK-LABEL: @trunc_sel_equal_fpext(
    296 ; CHECK-NEXT:    [[TRUNC:%.*]] = fptrunc float %a to half
    297 ; CHECK-NEXT:    [[TMP1:%.*]] = fpext half [[TRUNC]] to float
    298 ; CHECK-NEXT:    [[EXT:%.*]] = select i1 %cmp, float [[TMP1]], float 4.200000e+01
    299 ; CHECK-NEXT:    ret float [[EXT]]
    300 ;
    301   %trunc = fptrunc float %a to half
    302   %sel = select i1 %cmp, half %trunc, half 42.0
    303   %ext = fpext half %sel to float
    304   ret float %ext
    305 }
    306 
    307 define <2 x float> @trunc_sel_equal_fpext_vec(<2 x float> %a, <2 x i1> %cmp) {
    308 ; CHECK-LABEL: @trunc_sel_equal_fpext_vec(
    309 ; CHECK-NEXT:    [[TRUNC:%.*]] = fptrunc <2 x float> %a to <2 x half>
    310 ; CHECK-NEXT:    [[TMP1:%.*]] = fpext <2 x half> [[TRUNC]] to <2 x float>
    311 ; CHECK-NEXT:    [[EXT:%.*]] = select <2 x i1> %cmp, <2 x float> [[TMP1]], <2 x float> <float 4.200000e+01, float 4.300000e+01>
    312 ; CHECK-NEXT:    ret <2 x float> [[EXT]]
    313 ;
    314   %trunc = fptrunc <2 x float> %a to <2 x half>
    315   %sel = select <2 x i1> %cmp, <2 x half> %trunc, <2 x half> <half 42.0, half 43.0>
    316   %ext = fpext <2 x half> %sel to <2 x float>
    317   ret <2 x float> %ext
    318 }
    319 
    320 define i32 @test_sext1(i1 %cca, i1 %ccb) {
    321 ; CHECK-LABEL: @test_sext1(
    322 ; CHECK-NEXT:    [[FOLD_R:%.*]] = and i1 %ccb, %cca
    323 ; CHECK-NEXT:    [[R:%.*]] = sext i1 [[FOLD_R]] to i32
    324 ; CHECK-NEXT:    ret i32 [[R]]
    325 ;
    326   %ccax = sext i1 %cca to i32
    327   %r = select i1 %ccb, i32 %ccax, i32 0
    328   ret i32 %r
    329 }
    330 
    331 define i32 @test_sext2(i1 %cca, i1 %ccb) {
    332 ; CHECK-LABEL: @test_sext2(
    333 ; CHECK-NEXT:    [[FOLD_R:%.*]] = or i1 %ccb, %cca
    334 ; CHECK-NEXT:    [[R:%.*]] = sext i1 [[FOLD_R]] to i32
    335 ; CHECK-NEXT:    ret i32 [[R]]
    336 ;
    337   %ccax = sext i1 %cca to i32
    338   %r = select i1 %ccb, i32 -1, i32 %ccax
    339   ret i32 %r
    340 }
    341 
    342 define i32 @test_sext3(i1 %cca, i1 %ccb) {
    343 ; CHECK-LABEL: @test_sext3(
    344 ; CHECK-NEXT:    [[NOT_CCB:%.*]] = xor i1 %ccb, true
    345 ; CHECK-NEXT:    [[FOLD_R:%.*]] = and i1 [[NOT_CCB]], %cca
    346 ; CHECK-NEXT:    [[R:%.*]] = sext i1 [[FOLD_R]] to i32
    347 ; CHECK-NEXT:    ret i32 [[R]]
    348 ;
    349   %ccax = sext i1 %cca to i32
    350   %r = select i1 %ccb, i32 0, i32 %ccax
    351   ret i32 %r
    352 }
    353 
    354 define i32 @test_sext4(i1 %cca, i1 %ccb) {
    355 ; CHECK-LABEL: @test_sext4(
    356 ; CHECK-NEXT:    [[NOT_CCB:%.*]] = xor i1 %ccb, true
    357 ; CHECK-NEXT:    [[FOLD_R:%.*]] = or i1 [[NOT_CCB]], %cca
    358 ; CHECK-NEXT:    [[R:%.*]] = sext i1 [[FOLD_R]] to i32
    359 ; CHECK-NEXT:    ret i32 [[R]]
    360 ;
    361   %ccax = sext i1 %cca to i32
    362   %r = select i1 %ccb, i32 %ccax, i32 -1
    363   ret i32 %r
    364 }
    365 
    366 define i32 @test_zext1(i1 %cca, i1 %ccb) {
    367 ; CHECK-LABEL: @test_zext1(
    368 ; CHECK-NEXT:    [[FOLD_R:%.*]] = and i1 %ccb, %cca
    369 ; CHECK-NEXT:    [[R:%.*]] = zext i1 [[FOLD_R]] to i32
    370 ; CHECK-NEXT:    ret i32 [[R]]
    371 ;
    372   %ccax = zext i1 %cca to i32
    373   %r = select i1 %ccb, i32 %ccax, i32 0
    374   ret i32 %r
    375 }
    376 
    377 define i32 @test_zext2(i1 %cca, i1 %ccb) {
    378 ; CHECK-LABEL: @test_zext2(
    379 ; CHECK-NEXT:    [[FOLD_R:%.*]] = or i1 %ccb, %cca
    380 ; CHECK-NEXT:    [[R:%.*]] = zext i1 [[FOLD_R]] to i32
    381 ; CHECK-NEXT:    ret i32 [[R]]
    382 ;
    383   %ccax = zext i1 %cca to i32
    384   %r = select i1 %ccb, i32 1, i32 %ccax
    385   ret i32 %r
    386 }
    387 
    388 define i32 @test_zext3(i1 %cca, i1 %ccb) {
    389 ; CHECK-LABEL: @test_zext3(
    390 ; CHECK-NEXT:    [[NOT_CCB:%.*]] = xor i1 %ccb, true
    391 ; CHECK-NEXT:    [[FOLD_R:%.*]] = and i1 [[NOT_CCB]], %cca
    392 ; CHECK-NEXT:    [[R:%.*]] = zext i1 [[FOLD_R]] to i32
    393 ; CHECK-NEXT:    ret i32 [[R]]
    394 ;
    395   %ccax = zext i1 %cca to i32
    396   %r = select i1 %ccb, i32 0, i32 %ccax
    397   ret i32 %r
    398 }
    399 
    400 define i32 @test_zext4(i1 %cca, i1 %ccb) {
    401 ; CHECK-LABEL: @test_zext4(
    402 ; CHECK-NEXT:    [[NOT_CCB:%.*]] = xor i1 %ccb, true
    403 ; CHECK-NEXT:    [[FOLD_R:%.*]] = or i1 [[NOT_CCB]], %cca
    404 ; CHECK-NEXT:    [[R:%.*]] = zext i1 [[FOLD_R]] to i32
    405 ; CHECK-NEXT:    ret i32 [[R]]
    406 ;
    407   %ccax = zext i1 %cca to i32
    408   %r = select i1 %ccb, i32 %ccax, i32 1
    409   ret i32 %r
    410 }
    411 
    412 define i32 @test_negative_sext(i1 %a, i1 %cc) {
    413 ; CHECK-LABEL: @test_negative_sext(
    414 ; CHECK-NEXT:    [[A_EXT:%.*]] = sext i1 %a to i32
    415 ; CHECK-NEXT:    [[R:%.*]] = select i1 %cc, i32 [[A_EXT]], i32 1
    416 ; CHECK-NEXT:    ret i32 [[R]]
    417 ;
    418   %a.ext = sext i1 %a to i32
    419   %r = select i1 %cc, i32 %a.ext, i32 1
    420   ret i32 %r
    421 }
    422 
    423 define i32 @test_negative_zext(i1 %a, i1 %cc) {
    424 ; CHECK-LABEL: @test_negative_zext(
    425 ; CHECK-NEXT:    [[A_EXT:%.*]] = zext i1 %a to i32
    426 ; CHECK-NEXT:    [[R:%.*]] = select i1 %cc, i32 [[A_EXT]], i32 -1
    427 ; CHECK-NEXT:    ret i32 [[R]]
    428 ;
    429   %a.ext = zext i1 %a to i32
    430   %r = select i1 %cc, i32 %a.ext, i32 -1
    431   ret i32 %r
    432 }
    433 
    434 define i32 @test_bits_sext(i8 %a, i1 %cc) {
    435 ; CHECK-LABEL: @test_bits_sext(
    436 ; CHECK-NEXT:    [[A_EXT:%.*]] = sext i8 %a to i32
    437 ; CHECK-NEXT:    [[R:%.*]] = select i1 %cc, i32 [[A_EXT]], i32 -128
    438 ; CHECK-NEXT:    ret i32 [[R]]
    439 ;
    440   %a.ext = sext i8 %a to i32
    441   %r = select i1 %cc, i32 %a.ext, i32 -128
    442   ret i32 %r
    443 }
    444 
    445 define i32 @test_bits_zext(i8 %a, i1 %cc) {
    446 ; CHECK-LABEL: @test_bits_zext(
    447 ; CHECK-NEXT:    [[A_EXT:%.*]] = zext i8 %a to i32
    448 ; CHECK-NEXT:    [[R:%.*]] = select i1 %cc, i32 [[A_EXT]], i32 255
    449 ; CHECK-NEXT:    ret i32 [[R]]
    450 ;
    451   %a.ext = zext i8 %a to i32
    452   %r = select i1 %cc, i32 %a.ext, i32 255
    453   ret i32 %r
    454 }
    455 
    456 define i32 @test_op_op(i32 %a, i32 %b, i32 %c) {
    457 ; CHECK-LABEL: @test_op_op(
    458 ; CHECK-NEXT:    [[CCA:%.*]] = icmp sgt i32 %a, 0
    459 ; CHECK-NEXT:    [[CCB:%.*]] = icmp sgt i32 %b, 0
    460 ; CHECK-NEXT:    [[CCC:%.*]] = icmp sgt i32 %c, 0
    461 ; CHECK-NEXT:    [[R_V:%.*]] = select i1 [[CCC]], i1 [[CCA]], i1 [[CCB]]
    462 ; CHECK-NEXT:    [[R:%.*]] = sext i1 [[R:%.*]].v to i32
    463 ; CHECK-NEXT:    ret i32 [[R]]
    464 ;
    465   %cca = icmp sgt i32 %a, 0
    466   %ccax = sext i1 %cca to i32
    467   %ccb = icmp sgt i32 %b, 0
    468   %ccbx = sext i1 %ccb to i32
    469   %ccc = icmp sgt i32 %c, 0
    470   %r = select i1 %ccc, i32 %ccax, i32 %ccbx
    471   ret i32 %r
    472 }
    473 
    474 define <2 x i32> @test_vectors_sext(<2 x i1> %cca, <2 x i1> %ccb) {
    475 ; CHECK-LABEL: @test_vectors_sext(
    476 ; CHECK-NEXT:    [[FOLD_R:%.*]] = and <2 x i1> %ccb, %cca
    477 ; CHECK-NEXT:    [[R:%.*]] = sext <2 x i1> [[FOLD_R]] to <2 x i32>
    478 ; CHECK-NEXT:    ret <2 x i32> [[R]]
    479 ;
    480   %ccax = sext <2 x i1> %cca to <2 x i32>
    481   %r = select <2 x i1> %ccb, <2 x i32> %ccax, <2 x i32> <i32 0, i32 0>
    482   ret <2 x i32> %r
    483 }
    484 
    485 define <2 x i32> @test_vectors_sext_nonsplat(<2 x i1> %cca, <2 x i1> %ccb) {
    486 ; CHECK-LABEL: @test_vectors_sext_nonsplat(
    487 ; CHECK-NEXT:    [[NARROW:%.*]] = select <2 x i1> %ccb, <2 x i1> %cca, <2 x i1> <i1 false, i1 true>
    488 ; CHECK-NEXT:    [[R:%.*]] = sext <2 x i1> [[NARROW]] to <2 x i32>
    489 ; CHECK-NEXT:    ret <2 x i32> [[R]]
    490 ;
    491   %ccax = sext <2 x i1> %cca to <2 x i32>
    492   %r = select <2 x i1> %ccb, <2 x i32> %ccax, <2 x i32> <i32 0, i32 -1>
    493   ret <2 x i32> %r
    494 }
    495 
    496 define <2 x i32> @test_vectors_zext(<2 x i1> %cca, <2 x i1> %ccb) {
    497 ; CHECK-LABEL: @test_vectors_zext(
    498 ; CHECK-NEXT:    [[FOLD_R:%.*]] = and <2 x i1> %ccb, %cca
    499 ; CHECK-NEXT:    [[R:%.*]] = zext <2 x i1> [[FOLD_R]] to <2 x i32>
    500 ; CHECK-NEXT:    ret <2 x i32> [[R]]
    501 ;
    502   %ccax = zext <2 x i1> %cca to <2 x i32>
    503   %r = select <2 x i1> %ccb, <2 x i32> %ccax, <2 x i32> <i32 0, i32 0>
    504   ret <2 x i32> %r
    505 }
    506 
    507 define <2 x i32> @test_vectors_zext_nonsplat(<2 x i1> %cca, <2 x i1> %ccb) {
    508 ; CHECK-LABEL: @test_vectors_zext_nonsplat(
    509 ; CHECK-NEXT:    [[NARROW:%.*]] = select <2 x i1> %ccb, <2 x i1> %cca, <2 x i1> <i1 true, i1 false>
    510 ; CHECK-NEXT:    [[R:%.*]] = zext <2 x i1> [[NARROW]] to <2 x i32>
    511 ; CHECK-NEXT:    ret <2 x i32> [[R]]
    512 ;
    513   %ccax = zext <2 x i1> %cca to <2 x i32>
    514   %r = select <2 x i1> %ccb, <2 x i32> %ccax, <2 x i32> <i32 1, i32 0>
    515   ret <2 x i32> %r
    516 }
    517 
    518 define <2 x i32> @scalar_select_of_vectors_sext(<2 x i1> %cca, i1 %ccb) {
    519 ; CHECK-LABEL: @scalar_select_of_vectors_sext(
    520 ; CHECK-NEXT:    [[FOLD_R:%.*]] = select i1 %ccb, <2 x i1> %cca, <2 x i1> zeroinitializer
    521 ; CHECK-NEXT:    [[R:%.*]] = sext <2 x i1> [[FOLD_R]] to <2 x i32>
    522 ; CHECK-NEXT:    ret <2 x i32> [[R]]
    523 ;
    524   %ccax = sext <2 x i1> %cca to <2 x i32>
    525   %r = select i1 %ccb, <2 x i32> %ccax, <2 x i32> <i32 0, i32 0>
    526   ret <2 x i32> %r
    527 }
    528 
    529 define <2 x i32> @scalar_select_of_vectors_zext(<2 x i1> %cca, i1 %ccb) {
    530 ; CHECK-LABEL: @scalar_select_of_vectors_zext(
    531 ; CHECK-NEXT:    [[FOLD_R:%.*]] = select i1 %ccb, <2 x i1> %cca, <2 x i1> zeroinitializer
    532 ; CHECK-NEXT:    [[R:%.*]] = zext <2 x i1> [[FOLD_R]] to <2 x i32>
    533 ; CHECK-NEXT:    ret <2 x i32> [[R]]
    534 ;
    535   %ccax = zext <2 x i1> %cca to <2 x i32>
    536   %r = select i1 %ccb, <2 x i32> %ccax, <2 x i32> <i32 0, i32 0>
    537   ret <2 x i32> %r
    538 }
    539 
    540 define i32 @sext_true_val_must_be_all_ones(i1 %x) {
    541 ; CHECK-LABEL: @sext_true_val_must_be_all_ones(
    542 ; CHECK-NEXT:    [[SEL:%.*]] = select i1 %x, i32 -1, i32 42, !prof !0
    543 ; CHECK-NEXT:    ret i32 [[SEL]]
    544 ;
    545   %ext = sext i1 %x to i32
    546   %sel = select i1 %x, i32 %ext, i32 42, !prof !0
    547   ret i32 %sel
    548 }
    549 
    550 define <2 x i32> @sext_true_val_must_be_all_ones_vec(<2 x i1> %x) {
    551 ; CHECK-LABEL: @sext_true_val_must_be_all_ones_vec(
    552 ; CHECK-NEXT:    [[SEL:%.*]] = select <2 x i1> %x, <2 x i32> <i32 -1, i32 -1>, <2 x i32> <i32 42, i32 12>, !prof !0
    553 ; CHECK-NEXT:    ret <2 x i32> [[SEL]]
    554 ;
    555   %ext = sext <2 x i1> %x to <2 x i32>
    556   %sel = select <2 x i1> %x, <2 x i32> %ext, <2 x i32> <i32 42, i32 12>, !prof !0
    557   ret <2 x i32> %sel
    558 }
    559 
    560 define i32 @zext_true_val_must_be_one(i1 %x) {
    561 ; CHECK-LABEL: @zext_true_val_must_be_one(
    562 ; CHECK-NEXT:    [[SEL:%.*]] = select i1 %x, i32 1, i32 42, !prof !0
    563 ; CHECK-NEXT:    ret i32 [[SEL]]
    564 ;
    565   %ext = zext i1 %x to i32
    566   %sel = select i1 %x, i32 %ext, i32 42, !prof !0
    567   ret i32 %sel
    568 }
    569 
    570 define <2 x i32> @zext_true_val_must_be_one_vec(<2 x i1> %x) {
    571 ; CHECK-LABEL: @zext_true_val_must_be_one_vec(
    572 ; CHECK-NEXT:    [[SEL:%.*]] = select <2 x i1> %x, <2 x i32> <i32 1, i32 1>, <2 x i32> <i32 42, i32 12>, !prof !0
    573 ; CHECK-NEXT:    ret <2 x i32> [[SEL]]
    574 ;
    575   %ext = zext <2 x i1> %x to <2 x i32>
    576   %sel = select <2 x i1> %x, <2 x i32> %ext, <2 x i32> <i32 42, i32 12>, !prof !0
    577   ret <2 x i32> %sel
    578 }
    579 
    580 define i32 @sext_false_val_must_be_zero(i1 %x) {
    581 ; CHECK-LABEL: @sext_false_val_must_be_zero(
    582 ; CHECK-NEXT:    [[SEL:%.*]] = select i1 %x, i32 42, i32 0, !prof !0
    583 ; CHECK-NEXT:    ret i32 [[SEL]]
    584 ;
    585   %ext = sext i1 %x to i32
    586   %sel = select i1 %x, i32 42, i32 %ext, !prof !0
    587   ret i32 %sel
    588 }
    589 
    590 define <2 x i32> @sext_false_val_must_be_zero_vec(<2 x i1> %x) {
    591 ; CHECK-LABEL: @sext_false_val_must_be_zero_vec(
    592 ; CHECK-NEXT:    [[SEL:%.*]] = select <2 x i1> %x, <2 x i32> <i32 42, i32 12>, <2 x i32> zeroinitializer, !prof !0
    593 ; CHECK-NEXT:    ret <2 x i32> [[SEL]]
    594 ;
    595   %ext = sext <2 x i1> %x to <2 x i32>
    596   %sel = select <2 x i1> %x, <2 x i32> <i32 42, i32 12>, <2 x i32> %ext, !prof !0
    597   ret <2 x i32> %sel
    598 }
    599 
    600 define i32 @zext_false_val_must_be_zero(i1 %x) {
    601 ; CHECK-LABEL: @zext_false_val_must_be_zero(
    602 ; CHECK-NEXT:    [[SEL:%.*]] = select i1 %x, i32 42, i32 0, !prof !0
    603 ; CHECK-NEXT:    ret i32 [[SEL]]
    604 ;
    605   %ext = zext i1 %x to i32
    606   %sel = select i1 %x, i32 42, i32 %ext, !prof !0
    607   ret i32 %sel
    608 }
    609 
    610 define <2 x i32> @zext_false_val_must_be_zero_vec(<2 x i1> %x) {
    611 ; CHECK-LABEL: @zext_false_val_must_be_zero_vec(
    612 ; CHECK-NEXT:    [[SEL:%.*]] = select <2 x i1> %x, <2 x i32> <i32 42, i32 12>, <2 x i32> zeroinitializer, !prof !0
    613 ; CHECK-NEXT:    ret <2 x i32> [[SEL]]
    614 ;
    615   %ext = zext <2 x i1> %x to <2 x i32>
    616   %sel = select <2 x i1> %x, <2 x i32> <i32 42, i32 12>, <2 x i32> %ext, !prof !0
    617   ret <2 x i32> %sel
    618 }
    619 
    620 !0 = !{!"branch_weights", i32 3, i32 5}
    621 
    622