1; NOTE: Assertions have been autogenerated by utils/update_test_checks.py 2; RUN: opt < %s -instcombine -S | FileCheck %s 3 4define i32 @select_icmp_eq_and_1_0_or_2(i32 %x, i32 %y) { 5; CHECK-LABEL: @select_icmp_eq_and_1_0_or_2( 6; CHECK-NEXT: [[AND:%.*]] = shl i32 %x, 1 7; CHECK-NEXT: [[TMP1:%.*]] = and i32 [[AND]], 2 8; CHECK-NEXT: [[TMP2:%.*]] = or i32 [[TMP1]], %y 9; CHECK-NEXT: ret i32 [[TMP2]] 10; 11 %and = and i32 %x, 1 12 %cmp = icmp eq i32 %and, 0 13 %or = or i32 %y, 2 14 %select = select i1 %cmp, i32 %y, i32 %or 15 ret i32 %select 16} 17 18define i32 @select_icmp_eq_and_32_0_or_8(i32 %x, i32 %y) { 19; CHECK-LABEL: @select_icmp_eq_and_32_0_or_8( 20; CHECK-NEXT: [[AND:%.*]] = lshr i32 %x, 2 21; CHECK-NEXT: [[TMP1:%.*]] = and i32 [[AND]], 8 22; CHECK-NEXT: [[TMP2:%.*]] = or i32 [[TMP1]], %y 23; CHECK-NEXT: ret i32 [[TMP2]] 24; 25 %and = and i32 %x, 32 26 %cmp = icmp eq i32 %and, 0 27 %or = or i32 %y, 8 28 %select = select i1 %cmp, i32 %y, i32 %or 29 ret i32 %select 30} 31 32define i32 @select_icmp_ne_0_and_4096_or_4096(i32 %x, i32 %y) { 33; CHECK-LABEL: @select_icmp_ne_0_and_4096_or_4096( 34; CHECK-NEXT: [[AND:%.*]] = and i32 %x, 4096 35; CHECK-NEXT: [[TMP1:%.*]] = xor i32 [[AND]], 4096 36; CHECK-NEXT: [[TMP2:%.*]] = or i32 [[TMP1]], %y 37; CHECK-NEXT: ret i32 [[TMP2]] 38; 39 %and = and i32 %x, 4096 40 %cmp = icmp ne i32 0, %and 41 %or = or i32 %y, 4096 42 %select = select i1 %cmp, i32 %y, i32 %or 43 ret i32 %select 44} 45 46define i32 @select_icmp_eq_and_4096_0_or_4096(i32 %x, i32 %y) { 47; CHECK-LABEL: @select_icmp_eq_and_4096_0_or_4096( 48; CHECK-NEXT: [[AND:%.*]] = and i32 %x, 4096 49; CHECK-NEXT: [[TMP1:%.*]] = or i32 [[AND]], %y 50; CHECK-NEXT: ret i32 [[TMP1]] 51; 52 %and = and i32 %x, 4096 53 %cmp = icmp eq i32 %and, 0 54 %or = or i32 %y, 4096 55 %select = select i1 %cmp, i32 %y, i32 %or 56 ret i32 %select 57} 58 59define i32 @select_icmp_eq_0_and_1_or_1(i64 %x, i32 %y) { 60; CHECK-LABEL: @select_icmp_eq_0_and_1_or_1( 61; CHECK-NEXT: [[X_TR:%.*]] = trunc i64 %x to i32 62; CHECK-NEXT: [[TMP1:%.*]] = and i32 [[X_TR]], 1 63; CHECK-NEXT: [[TMP2:%.*]] = or i32 [[TMP1]], %y 64; CHECK-NEXT: ret i32 [[TMP2]] 65; 66 %and = and i64 %x, 1 67 %cmp = icmp eq i64 %and, 0 68 %or = or i32 %y, 1 69 %select = select i1 %cmp, i32 %y, i32 %or 70 ret i32 %select 71} 72 73define i32 @select_icmp_ne_0_and_4096_or_32(i32 %x, i32 %y) { 74; CHECK-LABEL: @select_icmp_ne_0_and_4096_or_32( 75; CHECK-NEXT: [[AND:%.*]] = lshr i32 %x, 7 76; CHECK-NEXT: [[TMP1:%.*]] = and i32 [[AND]], 32 77; CHECK-NEXT: [[TMP2:%.*]] = xor i32 [[TMP1]], 32 78; CHECK-NEXT: [[TMP3:%.*]] = or i32 [[TMP2]], %y 79; CHECK-NEXT: ret i32 [[TMP3]] 80; 81 %and = and i32 %x, 4096 82 %cmp = icmp ne i32 0, %and 83 %or = or i32 %y, 32 84 %select = select i1 %cmp, i32 %y, i32 %or 85 ret i32 %select 86} 87 88define i32 @select_icmp_ne_0_and_32_or_4096(i32 %x, i32 %y) { 89; CHECK-LABEL: @select_icmp_ne_0_and_32_or_4096( 90; CHECK-NEXT: [[AND:%.*]] = shl i32 %x, 7 91; CHECK-NEXT: [[TMP1:%.*]] = and i32 [[AND]], 4096 92; CHECK-NEXT: [[TMP2:%.*]] = xor i32 [[TMP1]], 4096 93; CHECK-NEXT: [[TMP3:%.*]] = or i32 [[TMP2]], %y 94; CHECK-NEXT: ret i32 [[TMP3]] 95; 96 %and = and i32 %x, 32 97 %cmp = icmp ne i32 0, %and 98 %or = or i32 %y, 4096 99 %select = select i1 %cmp, i32 %y, i32 %or 100 ret i32 %select 101} 102 103define i8 @select_icmp_ne_0_and_1073741824_or_8(i32 %x, i8 %y) { 104; CHECK-LABEL: @select_icmp_ne_0_and_1073741824_or_8( 105; CHECK-NEXT: [[AND:%.*]] = lshr i32 %x, 27 106; CHECK-NEXT: [[AND_TR:%.*]] = trunc i32 [[AND]] to i8 107; CHECK-NEXT: [[TMP1:%.*]] = and i8 [[AND_TR]], 8 108; CHECK-NEXT: [[TMP2:%.*]] = xor i8 [[TMP1]], 8 109; CHECK-NEXT: [[TMP3:%.*]] = or i8 [[TMP2]], %y 110; CHECK-NEXT: ret i8 [[TMP3]] 111; 112 %and = and i32 %x, 1073741824 113 %cmp = icmp ne i32 0, %and 114 %or = or i8 %y, 8 115 %select = select i1 %cmp, i8 %y, i8 %or 116 ret i8 %select 117} 118 119define i32 @select_icmp_ne_0_and_8_or_1073741824(i8 %x, i32 %y) { 120; CHECK-LABEL: @select_icmp_ne_0_and_8_or_1073741824( 121; CHECK-NEXT: [[AND:%.*]] = and i8 %x, 8 122; CHECK-NEXT: [[TMP1:%.*]] = zext i8 [[AND]] to i32 123; CHECK-NEXT: [[TMP2:%.*]] = shl nuw nsw i32 [[TMP1]], 27 124; CHECK-NEXT: [[TMP3:%.*]] = xor i32 [[TMP2]], 1073741824 125; CHECK-NEXT: [[TMP4:%.*]] = or i32 [[TMP3]], %y 126; CHECK-NEXT: ret i32 [[TMP4]] 127; 128 %and = and i8 %x, 8 129 %cmp = icmp ne i8 0, %and 130 %or = or i32 %y, 1073741824 131 %select = select i1 %cmp, i32 %y, i32 %or 132 ret i32 %select 133} 134 135; We can't combine here, because the cmp is scalar and the or vector. 136; Just make sure we don't assert. 137define <2 x i32> @select_icmp_eq_and_1_0_or_vector_of_2s(i32 %x, <2 x i32> %y) { 138; CHECK-LABEL: @select_icmp_eq_and_1_0_or_vector_of_2s( 139; CHECK-NEXT: [[AND:%.*]] = and i32 %x, 1 140; CHECK-NEXT: [[CMP:%.*]] = icmp eq i32 [[AND]], 0 141; CHECK-NEXT: [[OR:%.*]] = or <2 x i32> %y, <i32 2, i32 2> 142; CHECK-NEXT: [[SELECT:%.*]] = select i1 [[CMP]], <2 x i32> %y, <2 x i32> [[OR]] 143; CHECK-NEXT: ret <2 x i32> [[SELECT]] 144; 145 %and = and i32 %x, 1 146 %cmp = icmp eq i32 %and, 0 147 %or = or <2 x i32> %y, <i32 2, i32 2> 148 %select = select i1 %cmp, <2 x i32> %y, <2 x i32> %or 149 ret <2 x i32> %select 150} 151 152define i32 @select_icmp_and_8_ne_0_xor_8(i32 %x) { 153; CHECK-LABEL: @select_icmp_and_8_ne_0_xor_8( 154; CHECK-NEXT: [[TMP1:%.*]] = and i32 %x, -9 155; CHECK-NEXT: ret i32 [[TMP1]] 156; 157 %and = and i32 %x, 8 158 %cmp = icmp eq i32 %and, 0 159 %xor = xor i32 %x, 8 160 %x.xor = select i1 %cmp, i32 %x, i32 %xor 161 ret i32 %x.xor 162} 163 164define i32 @select_icmp_and_8_eq_0_xor_8(i32 %x) { 165; CHECK-LABEL: @select_icmp_and_8_eq_0_xor_8( 166; CHECK-NEXT: [[TMP1:%.*]] = or i32 %x, 8 167; CHECK-NEXT: ret i32 [[TMP1]] 168; 169 %and = and i32 %x, 8 170 %cmp = icmp eq i32 %and, 0 171 %xor = xor i32 %x, 8 172 %xor.x = select i1 %cmp, i32 %xor, i32 %x 173 ret i32 %xor.x 174} 175 176define i64 @select_icmp_x_and_8_eq_0_y_xor_8(i32 %x, i64 %y) { 177; CHECK-LABEL: @select_icmp_x_and_8_eq_0_y_xor_8( 178; CHECK-NEXT: [[AND:%.*]] = and i32 %x, 8 179; CHECK-NEXT: [[CMP:%.*]] = icmp eq i32 [[AND]], 0 180; CHECK-NEXT: [[XOR:%.*]] = xor i64 %y, 8 181; CHECK-NEXT: [[Y_XOR:%.*]] = select i1 [[CMP]], i64 %y, i64 [[XOR]] 182; CHECK-NEXT: ret i64 [[Y_XOR]] 183; 184 %and = and i32 %x, 8 185 %cmp = icmp eq i32 %and, 0 186 %xor = xor i64 %y, 8 187 %y.xor = select i1 %cmp, i64 %y, i64 %xor 188 ret i64 %y.xor 189} 190 191define i64 @select_icmp_x_and_8_ne_0_y_xor_8(i32 %x, i64 %y) { 192; CHECK-LABEL: @select_icmp_x_and_8_ne_0_y_xor_8( 193; CHECK-NEXT: [[AND:%.*]] = and i32 %x, 8 194; CHECK-NEXT: [[CMP:%.*]] = icmp eq i32 [[AND]], 0 195; CHECK-NEXT: [[XOR:%.*]] = xor i64 %y, 8 196; CHECK-NEXT: [[XOR_Y:%.*]] = select i1 [[CMP]], i64 [[XOR]], i64 %y 197; CHECK-NEXT: ret i64 [[XOR_Y]] 198; 199 %and = and i32 %x, 8 200 %cmp = icmp eq i32 %and, 0 201 %xor = xor i64 %y, 8 202 %xor.y = select i1 %cmp, i64 %xor, i64 %y 203 ret i64 %xor.y 204} 205 206define i64 @select_icmp_x_and_8_ne_0_y_or_8(i32 %x, i64 %y) { 207; CHECK-LABEL: @select_icmp_x_and_8_ne_0_y_or_8( 208; CHECK-NEXT: [[AND:%.*]] = and i32 %x, 8 209; CHECK-NEXT: [[TMP1:%.*]] = xor i32 [[AND]], 8 210; CHECK-NEXT: [[TMP2:%.*]] = zext i32 [[TMP1]] to i64 211; CHECK-NEXT: [[TMP3:%.*]] = or i64 [[TMP2]], %y 212; CHECK-NEXT: ret i64 [[TMP3]] 213; 214 %and = and i32 %x, 8 215 %cmp = icmp eq i32 %and, 0 216 %or = or i64 %y, 8 217 %or.y = select i1 %cmp, i64 %or, i64 %y 218 ret i64 %or.y 219} 220 221define i32 @select_icmp_and_2147483648_ne_0_xor_2147483648(i32 %x) { 222; CHECK-LABEL: @select_icmp_and_2147483648_ne_0_xor_2147483648( 223; CHECK-NEXT: [[TMP1:%.*]] = and i32 %x, 2147483647 224; CHECK-NEXT: ret i32 [[TMP1]] 225; 226 %and = and i32 %x, 2147483648 227 %cmp = icmp eq i32 %and, 0 228 %xor = xor i32 %x, 2147483648 229 %x.xor = select i1 %cmp, i32 %x, i32 %xor 230 ret i32 %x.xor 231} 232 233define i32 @select_icmp_and_2147483648_eq_0_xor_2147483648(i32 %x) { 234; CHECK-LABEL: @select_icmp_and_2147483648_eq_0_xor_2147483648( 235; CHECK-NEXT: [[TMP1:%.*]] = or i32 %x, -2147483648 236; CHECK-NEXT: ret i32 [[TMP1]] 237; 238 %and = and i32 %x, 2147483648 239 %cmp = icmp eq i32 %and, 0 240 %xor = xor i32 %x, 2147483648 241 %xor.x = select i1 %cmp, i32 %xor, i32 %x 242 ret i32 %xor.x 243} 244 245define i32 @select_icmp_x_and_2147483648_ne_0_or_2147483648(i32 %x) { 246; CHECK-LABEL: @select_icmp_x_and_2147483648_ne_0_or_2147483648( 247; CHECK-NEXT: [[OR:%.*]] = or i32 %x, -2147483648 248; CHECK-NEXT: ret i32 [[OR]] 249; 250 %and = and i32 %x, 2147483648 251 %cmp = icmp eq i32 %and, 0 252 %or = or i32 %x, 2147483648 253 %or.x = select i1 %cmp, i32 %or, i32 %x 254 ret i32 %or.x 255} 256 257define i32 @test65(i64 %x) { 258; CHECK-LABEL: @test65( 259; CHECK-NEXT: [[X_TR:%.*]] = trunc i64 %x to i32 260; CHECK-NEXT: [[TMP1:%.*]] = lshr i32 [[X_TR]], 3 261; CHECK-NEXT: [[TMP2:%.*]] = and i32 [[TMP1]], 2 262; CHECK-NEXT: [[TMP3:%.*]] = xor i32 [[TMP2]], 42 263; CHECK-NEXT: ret i32 [[TMP3]] 264; 265 %1 = and i64 %x, 16 266 %2 = icmp ne i64 %1, 0 267 %3 = select i1 %2, i32 40, i32 42 268 ret i32 %3 269} 270 271define i32 @test66(i64 %x) { 272; CHECK-LABEL: @test66( 273; CHECK-NEXT: [[TMP1:%.*]] = and i64 %x, 4294967296 274; CHECK-NEXT: [[TMP2:%.*]] = icmp ne i64 [[TMP1]], 0 275; CHECK-NEXT: [[TMP3:%.*]] = select i1 [[TMP2]], i32 40, i32 42 276; CHECK-NEXT: ret i32 [[TMP3]] 277; 278 %1 = and i64 %x, 4294967296 279 %2 = icmp ne i64 %1, 0 280 %3 = select i1 %2, i32 40, i32 42 281 ret i32 %3 282} 283 284define i32 @test67(i16 %x) { 285; CHECK-LABEL: @test67( 286; CHECK-NEXT: [[TMP1:%.*]] = and i16 %x, 4 287; CHECK-NEXT: [[TMP2:%.*]] = zext i16 [[TMP1]] to i32 288; CHECK-NEXT: [[TMP3:%.*]] = lshr exact i32 [[TMP2]], 1 289; CHECK-NEXT: [[TMP4:%.*]] = xor i32 [[TMP3]], 42 290; CHECK-NEXT: ret i32 [[TMP4]] 291; 292 %1 = and i16 %x, 4 293 %2 = icmp ne i16 %1, 0 294 %3 = select i1 %2, i32 40, i32 42 295 ret i32 %3 296} 297 298