955 lines · plain
1; NOTE: Assertions have been autogenerated by utils/update_test_checks.py2; RUN: opt -S -passes=instcombine < %s | FileCheck %s3 4declare void @use(i8)5declare void @use.i1(i1)6declare i8 @llvm.umin.i8(i8, i8)7 8define i1 @icmp_select_const(i8 %x, i8 %y) {9; CHECK-LABEL: @icmp_select_const(10; CHECK-NEXT: [[CMP1:%.*]] = icmp eq i8 [[X:%.*]], 011; CHECK-NEXT: [[CMP21:%.*]] = icmp eq i8 [[Y:%.*]], 012; CHECK-NEXT: [[CMP2:%.*]] = select i1 [[CMP1]], i1 true, i1 [[CMP21]]13; CHECK-NEXT: ret i1 [[CMP2]]14;15 %cmp1 = icmp eq i8 %x, 016 %sel = select i1 %cmp1, i8 0, i8 %y17 %cmp2 = icmp eq i8 %sel, 018 ret i1 %cmp219}20 21define i1 @icmp_select_var(i8 %x, i8 %y, i8 %z) {22; CHECK-LABEL: @icmp_select_var(23; CHECK-NEXT: [[CMP1:%.*]] = icmp eq i8 [[X:%.*]], 024; CHECK-NEXT: [[CMP21:%.*]] = icmp eq i8 [[Y:%.*]], [[Z:%.*]]25; CHECK-NEXT: [[CMP2:%.*]] = select i1 [[CMP1]], i1 true, i1 [[CMP21]]26; CHECK-NEXT: ret i1 [[CMP2]]27;28 %cmp1 = icmp eq i8 %x, 029 %sel = select i1 %cmp1, i8 %z, i8 %y30 %cmp2 = icmp eq i8 %sel, %z31 ret i1 %cmp232}33 34define i1 @icmp_select_var_commuted(i8 %x, i8 %y, i8 %_z) {35; CHECK-LABEL: @icmp_select_var_commuted(36; CHECK-NEXT: [[Z:%.*]] = udiv i8 42, [[_Z:%.*]]37; CHECK-NEXT: [[CMP1:%.*]] = icmp eq i8 [[X:%.*]], 038; CHECK-NEXT: [[CMP21:%.*]] = icmp eq i8 [[Y:%.*]], [[Z]]39; CHECK-NEXT: [[CMP2:%.*]] = select i1 [[CMP1]], i1 true, i1 [[CMP21]]40; CHECK-NEXT: ret i1 [[CMP2]]41;42 %z = udiv i8 42, %_z ; thwart complexity-based canonicalization43 %cmp1 = icmp eq i8 %x, 044 %sel = select i1 %cmp1, i8 %z, i8 %y45 %cmp2 = icmp eq i8 %z, %sel46 ret i1 %cmp247}48 49define i1 @icmp_select_var_select(i8 %x, i8 %y, i1 %c) {50; CHECK-LABEL: @icmp_select_var_select(51; CHECK-NEXT: [[CMP1:%.*]] = icmp eq i8 [[X:%.*]], 052; CHECK-NEXT: [[CMP212:%.*]] = icmp eq i8 [[X]], [[Y:%.*]]53; CHECK-NEXT: [[NOT_C:%.*]] = xor i1 [[C:%.*]], true54; CHECK-NEXT: [[TMP1:%.*]] = select i1 [[CMP1]], i1 true, i1 [[NOT_C]]55; CHECK-NEXT: [[CMP2:%.*]] = select i1 [[TMP1]], i1 true, i1 [[CMP212]]56; CHECK-NEXT: ret i1 [[CMP2]]57;58 %z = select i1 %c, i8 %x, i8 %y59 %cmp1 = icmp eq i8 %x, 060 %sel = select i1 %cmp1, i8 %z, i8 %y61 %cmp2 = icmp eq i8 %z, %sel62 ret i1 %cmp263}64 65define i1 @icmp_select_var_both_fold(i8 %x, i8 %y, i8 %_z) {66; CHECK-LABEL: @icmp_select_var_both_fold(67; CHECK-NEXT: [[CMP1:%.*]] = icmp eq i8 [[X:%.*]], 068; CHECK-NEXT: ret i1 [[CMP1]]69;70 %z = or i8 %_z, 171 %cmp1 = icmp eq i8 %x, 072 %sel = select i1 %cmp1, i8 %z, i8 273 %cmp2 = icmp eq i8 %sel, %z74 ret i1 %cmp275}76 77define i1 @icmp_select_var_extra_use(i8 %x, i8 %y, i8 %z) {78; CHECK-LABEL: @icmp_select_var_extra_use(79; CHECK-NEXT: [[CMP1:%.*]] = icmp eq i8 [[X:%.*]], 080; CHECK-NEXT: [[SEL:%.*]] = select i1 [[CMP1]], i8 [[Z:%.*]], i8 [[Y:%.*]]81; CHECK-NEXT: call void @use(i8 [[SEL]])82; CHECK-NEXT: [[CMP2:%.*]] = icmp eq i8 [[SEL]], [[Z]]83; CHECK-NEXT: ret i1 [[CMP2]]84;85 %cmp1 = icmp eq i8 %x, 086 %sel = select i1 %cmp1, i8 %z, i8 %y87 call void @use(i8 %sel)88 %cmp2 = icmp eq i8 %sel, %z89 ret i1 %cmp290}91 92define i1 @icmp_select_var_both_fold_extra_use(i8 %x, i8 %y, i8 %_z) {93; CHECK-LABEL: @icmp_select_var_both_fold_extra_use(94; CHECK-NEXT: [[Z:%.*]] = or i8 [[_Z:%.*]], 195; CHECK-NEXT: [[CMP1:%.*]] = icmp eq i8 [[X:%.*]], 096; CHECK-NEXT: [[SEL:%.*]] = select i1 [[CMP1]], i8 [[Z]], i8 297; CHECK-NEXT: call void @use(i8 [[SEL]])98; CHECK-NEXT: ret i1 [[CMP1]]99;100 %z = or i8 %_z, 1101 %cmp1 = icmp eq i8 %x, 0102 %sel = select i1 %cmp1, i8 %z, i8 2103 call void @use(i8 %sel)104 %cmp2 = icmp eq i8 %sel, %z105 ret i1 %cmp2106}107 108define i1 @icmp_select_var_pred_ne(i8 %x, i8 %y, i8 %z) {109; CHECK-LABEL: @icmp_select_var_pred_ne(110; CHECK-NEXT: [[CMP1:%.*]] = icmp ne i8 [[X:%.*]], 0111; CHECK-NEXT: [[CMP21:%.*]] = icmp ne i8 [[Y:%.*]], [[Z:%.*]]112; CHECK-NEXT: [[CMP2:%.*]] = select i1 [[CMP1]], i1 [[CMP21]], i1 false113; CHECK-NEXT: ret i1 [[CMP2]]114;115 %cmp1 = icmp eq i8 %x, 0116 %sel = select i1 %cmp1, i8 %z, i8 %y117 %cmp2 = icmp ne i8 %sel, %z118 ret i1 %cmp2119}120 121define i1 @icmp_select_var_pred_ult(i8 %x, i8 %y, i8 %z) {122; CHECK-LABEL: @icmp_select_var_pred_ult(123; CHECK-NEXT: [[Z1:%.*]] = add nuw i8 [[Z:%.*]], 2124; CHECK-NEXT: [[CMP1:%.*]] = icmp eq i8 [[X:%.*]], 0125; CHECK-NEXT: [[CMP21:%.*]] = icmp ult i8 [[Y:%.*]], [[Z1]]126; CHECK-NEXT: [[CMP2:%.*]] = select i1 [[CMP1]], i1 true, i1 [[CMP21]]127; CHECK-NEXT: ret i1 [[CMP2]]128;129 %z1 = add nuw i8 %z, 2130 %cmp1 = icmp eq i8 %x, 0131 %sel = select i1 %cmp1, i8 %z, i8 %y132 %cmp2 = icmp ult i8 %sel, %z1133 ret i1 %cmp2134}135 136define i1 @icmp_select_var_pred_uge(i8 %x, i8 %y, i8 %z) {137; CHECK-LABEL: @icmp_select_var_pred_uge(138; CHECK-NEXT: [[Z1:%.*]] = add nuw i8 [[Z:%.*]], 2139; CHECK-NEXT: [[CMP1:%.*]] = icmp ne i8 [[X:%.*]], 0140; CHECK-NEXT: [[CMP21:%.*]] = icmp uge i8 [[Y:%.*]], [[Z1]]141; CHECK-NEXT: [[CMP2:%.*]] = select i1 [[CMP1]], i1 [[CMP21]], i1 false142; CHECK-NEXT: ret i1 [[CMP2]]143;144 %z1 = add nuw i8 %z, 2145 %cmp1 = icmp eq i8 %x, 0146 %sel = select i1 %cmp1, i8 %z, i8 %y147 %cmp2 = icmp uge i8 %sel, %z1148 ret i1 %cmp2149}150 151define i1 @icmp_select_var_pred_uge_commuted(i8 %x, i8 %y, i8 %z) {152; CHECK-LABEL: @icmp_select_var_pred_uge_commuted(153; CHECK-NEXT: [[Z1:%.*]] = add nuw i8 [[Z:%.*]], 2154; CHECK-NEXT: [[CMP1:%.*]] = icmp eq i8 [[X:%.*]], 0155; CHECK-NEXT: [[CMP21:%.*]] = icmp ule i8 [[Y:%.*]], [[Z1]]156; CHECK-NEXT: [[CMP2:%.*]] = select i1 [[CMP1]], i1 true, i1 [[CMP21]]157; CHECK-NEXT: ret i1 [[CMP2]]158;159 %z1 = add nuw i8 %z, 2160 %cmp1 = icmp eq i8 %x, 0161 %sel = select i1 %cmp1, i8 %z, i8 %y162 %cmp2 = icmp uge i8 %z1, %sel163 ret i1 %cmp2164}165 166define i1 @icmp_select_implied_cond(i8 %x, i8 %y) {167; CHECK-LABEL: @icmp_select_implied_cond(168; CHECK-NEXT: [[CMP1:%.*]] = icmp eq i8 [[X:%.*]], 0169; CHECK-NEXT: [[CMP21:%.*]] = icmp eq i8 [[Y:%.*]], [[X]]170; CHECK-NEXT: [[CMP2:%.*]] = select i1 [[CMP1]], i1 true, i1 [[CMP21]]171; CHECK-NEXT: ret i1 [[CMP2]]172;173 %cmp1 = icmp eq i8 %x, 0174 %sel = select i1 %cmp1, i8 0, i8 %y175 %cmp2 = icmp eq i8 %sel, %x176 ret i1 %cmp2177}178 179define i1 @icmp_select_implied_cond_ne(i8 %x, i8 %y) {180; CHECK-LABEL: @icmp_select_implied_cond_ne(181; CHECK-NEXT: [[CMP1:%.*]] = icmp ne i8 [[X:%.*]], 0182; CHECK-NEXT: [[CMP21:%.*]] = icmp ne i8 [[Y:%.*]], [[X]]183; CHECK-NEXT: [[CMP2:%.*]] = select i1 [[CMP1]], i1 [[CMP21]], i1 false184; CHECK-NEXT: ret i1 [[CMP2]]185;186 %cmp1 = icmp eq i8 %x, 0187 %sel = select i1 %cmp1, i8 0, i8 %y188 %cmp2 = icmp ne i8 %sel, %x189 ret i1 %cmp2190}191 192define i1 @icmp_select_implied_cond_swapped_select(i8 %x, i8 %y) {193; CHECK-LABEL: @icmp_select_implied_cond_swapped_select(194; CHECK-NEXT: [[CMP1:%.*]] = icmp eq i8 [[X:%.*]], 0195; CHECK-NEXT: [[TMP1:%.*]] = icmp eq i8 [[Y:%.*]], 0196; CHECK-NEXT: [[CMP2:%.*]] = select i1 [[CMP1]], i1 [[TMP1]], i1 false197; CHECK-NEXT: ret i1 [[CMP2]]198;199 %cmp1 = icmp eq i8 %x, 0200 %sel = select i1 %cmp1, i8 %y, i8 0201 %cmp2 = icmp eq i8 %sel, %x202 ret i1 %cmp2203}204 205define i1 @icmp_select_implied_cond_swapped_select_with_inv_cond(i8 %x, i8 %y) {206; CHECK-LABEL: @icmp_select_implied_cond_swapped_select_with_inv_cond(207; CHECK-NEXT: [[CMP1:%.*]] = icmp ne i8 [[X:%.*]], 0208; CHECK-NEXT: call void @use.i1(i1 [[CMP1]])209; CHECK-NEXT: [[CMP21:%.*]] = icmp eq i8 [[Y:%.*]], [[X]]210; CHECK-NEXT: [[NOT_CMP1:%.*]] = xor i1 [[CMP1]], true211; CHECK-NEXT: [[CMP2:%.*]] = select i1 [[NOT_CMP1]], i1 true, i1 [[CMP21]]212; CHECK-NEXT: ret i1 [[CMP2]]213;214 %cmp1 = icmp ne i8 %x, 0215 call void @use.i1(i1 %cmp1)216 %sel = select i1 %cmp1, i8 %y, i8 0217 %cmp2 = icmp eq i8 %sel, %x218 ret i1 %cmp2219}220 221define i1 @icmp_select_implied_cond_relational(i8 %x, i8 %y) {222; CHECK-LABEL: @icmp_select_implied_cond_relational(223; CHECK-NEXT: [[CMP1:%.*]] = icmp ugt i8 [[X:%.*]], 10224; CHECK-NEXT: [[CMP21:%.*]] = icmp ult i8 [[Y:%.*]], [[X]]225; CHECK-NEXT: [[CMP2:%.*]] = select i1 [[CMP1]], i1 true, i1 [[CMP21]]226; CHECK-NEXT: ret i1 [[CMP2]]227;228 %cmp1 = icmp ugt i8 %x, 10229 %sel = select i1 %cmp1, i8 10, i8 %y230 %cmp2 = icmp ult i8 %sel, %x231 ret i1 %cmp2232}233 234define i1 @icmp_select_implied_cond_relational_off_by_one(i8 %x, i8 %y) {235; CHECK-LABEL: @icmp_select_implied_cond_relational_off_by_one(236; CHECK-NEXT: [[CMP1:%.*]] = icmp ugt i8 [[X:%.*]], 10237; CHECK-NEXT: call void @use.i1(i1 [[CMP1]])238; CHECK-NEXT: [[SEL:%.*]] = select i1 [[CMP1]], i8 11, i8 [[Y:%.*]]239; CHECK-NEXT: [[CMP2:%.*]] = icmp ult i8 [[SEL]], [[X]]240; CHECK-NEXT: ret i1 [[CMP2]]241;242 %cmp1 = icmp ugt i8 %x, 10243 call void @use.i1(i1 %cmp1)244 %sel = select i1 %cmp1, i8 11, i8 %y245 %cmp2 = icmp ult i8 %sel, %x246 ret i1 %cmp2247}248 249define i1 @umin_seq_comparison(i8 %x, i8 %y) {250; CHECK-LABEL: @umin_seq_comparison(251; CHECK-NEXT: [[Y:%.*]] = freeze i8 [[Y1:%.*]]252; CHECK-NEXT: [[CMP21:%.*]] = icmp ule i8 [[X:%.*]], [[Y]]253; CHECK-NEXT: ret i1 [[CMP21]]254;255 %min = call i8 @llvm.umin.i8(i8 %x, i8 %y)256 %cmp1 = icmp eq i8 %x, 0257 %sel = select i1 %cmp1, i8 0, i8 %min258 %cmp2 = icmp eq i8 %sel, %x259 ret i1 %cmp2260}261 262; ((A ? TC : FC) & (B ? TC : FC)) == 0 --> xor A, B263 264define i1 @select_constants_and_icmp_eq0(i1 %x, i1 %y) {265; CHECK-LABEL: @select_constants_and_icmp_eq0(266; CHECK-NEXT: [[CMP:%.*]] = xor i1 [[X:%.*]], [[Y:%.*]]267; CHECK-NEXT: ret i1 [[CMP]]268;269 %s1 = select i1 %x, i8 2, i8 1270 %s2 = select i1 %y, i8 2, i8 1271 %and = and i8 %s1, %s2272 %cmp = icmp eq i8 %and, 0273 ret i1 %cmp274}275 276; extra uses on all intermediates are ok277 278define i1 @select_constants_and_icmp_eq0_uses(i1 %x, i1 %y) {279; CHECK-LABEL: @select_constants_and_icmp_eq0_uses(280; CHECK-NEXT: [[S1:%.*]] = select i1 [[X:%.*]], i8 2, i8 1281; CHECK-NEXT: call void @use(i8 [[S1]])282; CHECK-NEXT: [[S2:%.*]] = select i1 [[Y:%.*]], i8 2, i8 1283; CHECK-NEXT: call void @use(i8 [[S2]])284; CHECK-NEXT: [[AND:%.*]] = and i8 [[S1]], [[S2]]285; CHECK-NEXT: call void @use(i8 [[AND]])286; CHECK-NEXT: [[CMP:%.*]] = xor i1 [[X]], [[Y]]287; CHECK-NEXT: ret i1 [[CMP]]288;289 %s1 = select i1 %x, i8 2, i8 1290 call void @use(i8 %s1)291 %s2 = select i1 %y, i8 2, i8 1292 call void @use(i8 %s2)293 %and = and i8 %s1, %s2294 call void @use(i8 %and)295 %cmp = icmp eq i8 %and, 0296 ret i1 %cmp297}298 299; vector splat constants are ok300 301define <2 x i1> @select_constants_and_icmp_eq0_vec_splat(<2 x i1> %x, <2 x i1> %y) {302; CHECK-LABEL: @select_constants_and_icmp_eq0_vec_splat(303; CHECK-NEXT: [[CMP:%.*]] = xor <2 x i1> [[X:%.*]], [[Y:%.*]]304; CHECK-NEXT: ret <2 x i1> [[CMP]]305;306 %s1 = select <2 x i1> %x, <2 x i9> <i9 3, i9 3>, <2 x i9> <i9 48, i9 48>307 %s2 = select <2 x i1> %y, <2 x i9> <i9 3, i9 3>, <2 x i9> <i9 48, i9 48>308 %and = and <2 x i9> %s1, %s2309 %cmp = icmp eq <2 x i9> %and, zeroinitializer310 ret <2 x i1> %cmp311}312 313; common bit set - simplified via known bits314 315define i1 @select_constants_and_icmp_eq0_common_bit(i1 %x, i1 %y) {316; CHECK-LABEL: @select_constants_and_icmp_eq0_common_bit(317; CHECK-NEXT: ret i1 false318;319 %s1 = select i1 %x, i8 2, i8 3320 %s2 = select i1 %y, i8 2, i8 3321 %and = and i8 %s1, %s2322 %cmp = icmp eq i8 %and, 0323 ret i1 %cmp324}325 326; negative test - need matching constants327 328define i1 @select_constants_and_icmp_eq0_no_common_op1(i1 %x, i1 %y) {329; CHECK-LABEL: @select_constants_and_icmp_eq0_no_common_op1(330; CHECK-NEXT: [[CMP:%.*]] = xor i1 [[X:%.*]], [[Y:%.*]]331; CHECK-NEXT: ret i1 [[CMP]]332;333 %s1 = select i1 %x, i8 16, i8 3334 %s2 = select i1 %y, i8 24, i8 3335 %and = and i8 %s1, %s2336 %cmp = icmp eq i8 %and, 0337 ret i1 %cmp338}339 340; negative test - need matching constants341 342define i1 @select_constants_and_icmp_eq0_no_common_op2(i1 %x, i1 %y) {343; CHECK-LABEL: @select_constants_and_icmp_eq0_no_common_op2(344; CHECK-NEXT: [[CMP:%.*]] = xor i1 [[X:%.*]], [[Y:%.*]]345; CHECK-NEXT: ret i1 [[CMP]]346;347 %s1 = select i1 %x, i8 16, i8 3348 %s2 = select i1 %y, i8 16, i8 7349 %and = and i8 %s1, %s2350 %cmp = icmp eq i8 %and, 0351 ret i1 %cmp352}353 354; reduces via FoldOpInstSelect, but this could be a simple 'or'355 356define i1 @select_constants_and_icmp_eq0_zero_tval(i1 %x, i1 %y) {357; CHECK-LABEL: @select_constants_and_icmp_eq0_zero_tval(358; CHECK-NEXT: [[TMP1:%.*]] = select i1 [[X:%.*]], i1 true, i1 [[Y:%.*]]359; CHECK-NEXT: ret i1 [[TMP1]]360;361 %s1 = select i1 %x, i8 0, i8 12362 %s2 = select i1 %y, i8 0, i8 12363 %and = and i8 %s1, %s2364 %cmp = icmp eq i8 %and, 0365 ret i1 %cmp366}367 368; reduces via FoldOpInstSelect, but this could be a simple 'not-of-and'369 370define i1 @select_constants_and_icmp_eq0_zero_fval(i1 %x, i1 %y) {371; CHECK-LABEL: @select_constants_and_icmp_eq0_zero_fval(372; CHECK-NEXT: [[TMP1:%.*]] = select i1 [[X:%.*]], i1 [[Y:%.*]], i1 false373; CHECK-NEXT: [[NOT_:%.*]] = xor i1 [[TMP1]], true374; CHECK-NEXT: ret i1 [[NOT_]]375;376 %s1 = select i1 %x, i8 12, i8 0377 %s2 = select i1 %y, i8 12, i8 0378 %and = and i8 %s1, %s2379 %cmp = icmp eq i8 %and, 0380 ret i1 %cmp381}382 383define i1 @select_constants_and_icmp_eq_tval(i1 %x, i1 %y) {384; CHECK-LABEL: @select_constants_and_icmp_eq_tval(385; CHECK-NEXT: [[CMP:%.*]] = and i1 [[X:%.*]], [[Y:%.*]]386; CHECK-NEXT: ret i1 [[CMP]]387;388 %s1 = select i1 %x, i8 6, i8 1389 %s2 = select i1 %y, i8 6, i8 1390 %and = and i8 %s1, %s2391 %cmp = icmp eq i8 %and, 6392 ret i1 %cmp393}394 395define i1 @select_constants_and_icmp_eq_fval(i1 %x, i1 %y) {396; CHECK-LABEL: @select_constants_and_icmp_eq_fval(397; CHECK-NEXT: [[TMP1:%.*]] = or i1 [[X:%.*]], [[Y:%.*]]398; CHECK-NEXT: [[CMP:%.*]] = xor i1 [[TMP1]], true399; CHECK-NEXT: ret i1 [[CMP]]400;401 %s1 = select i1 %x, i8 12, i8 3402 %s2 = select i1 %y, i8 12, i8 3403 %and = and i8 %s1, %s2404 %cmp = icmp eq i8 %and, 3405 ret i1 %cmp406}407 408; ((A ? TC : FC) & (B ? TC : FC)) != 0 --> not(xor A, B)409 410define i1 @select_constants_and_icmp_ne0(i1 %x, i1 %y) {411; CHECK-LABEL: @select_constants_and_icmp_ne0(412; CHECK-NEXT: [[TMP1:%.*]] = xor i1 [[X:%.*]], [[Y:%.*]]413; CHECK-NEXT: [[CMP:%.*]] = xor i1 [[TMP1]], true414; CHECK-NEXT: ret i1 [[CMP]]415;416 %s1 = select i1 %x, i8 2, i8 1417 %s2 = select i1 %y, i8 2, i8 1418 %and = and i8 %s1, %s2419 %cmp = icmp ne i8 %and, 0420 ret i1 %cmp421}422 423; extra uses on select intermediates are ok424 425define i1 @select_constants_and_icmp_ne0_uses(i1 %x, i1 %y) {426; CHECK-LABEL: @select_constants_and_icmp_ne0_uses(427; CHECK-NEXT: [[S1:%.*]] = select i1 [[X:%.*]], i8 2, i8 1428; CHECK-NEXT: call void @use(i8 [[S1]])429; CHECK-NEXT: [[S2:%.*]] = select i1 [[Y:%.*]], i8 2, i8 1430; CHECK-NEXT: call void @use(i8 [[S2]])431; CHECK-NEXT: [[TMP1:%.*]] = xor i1 [[X]], [[Y]]432; CHECK-NEXT: [[CMP:%.*]] = xor i1 [[TMP1]], true433; CHECK-NEXT: ret i1 [[CMP]]434;435 %s1 = select i1 %x, i8 2, i8 1436 call void @use(i8 %s1)437 %s2 = select i1 %y, i8 2, i8 1438 call void @use(i8 %s2)439 %and = and i8 %s1, %s2440 %cmp = icmp ne i8 %and, 0441 ret i1 %cmp442}443 444; negative test - don't create extra instructions445 446define i1 @select_constants_and_icmp_ne0_all_uses(i1 %x, i1 %y) {447; CHECK-LABEL: @select_constants_and_icmp_ne0_all_uses(448; CHECK-NEXT: [[S1:%.*]] = select i1 [[X:%.*]], i8 2, i8 1449; CHECK-NEXT: call void @use(i8 [[S1]])450; CHECK-NEXT: [[S2:%.*]] = select i1 [[Y:%.*]], i8 2, i8 1451; CHECK-NEXT: call void @use(i8 [[S2]])452; CHECK-NEXT: [[AND:%.*]] = and i8 [[S1]], [[S2]]453; CHECK-NEXT: call void @use(i8 [[AND]])454; CHECK-NEXT: [[CMP:%.*]] = icmp ne i8 [[AND]], 0455; CHECK-NEXT: ret i1 [[CMP]]456;457 %s1 = select i1 %x, i8 2, i8 1458 call void @use(i8 %s1)459 %s2 = select i1 %y, i8 2, i8 1460 call void @use(i8 %s2)461 %and = and i8 %s1, %s2462 call void @use(i8 %and)463 %cmp = icmp ne i8 %and, 0464 ret i1 %cmp465}466 467; vector splat constants are ok468 469define <2 x i1> @select_constants_and_icmp_ne0_vec_splat(<2 x i1> %x, <2 x i1> %y) {470; CHECK-LABEL: @select_constants_and_icmp_ne0_vec_splat(471; CHECK-NEXT: [[TMP1:%.*]] = xor <2 x i1> [[X:%.*]], [[Y:%.*]]472; CHECK-NEXT: [[CMP:%.*]] = xor <2 x i1> [[TMP1]], splat (i1 true)473; CHECK-NEXT: ret <2 x i1> [[CMP]]474;475 %s1 = select <2 x i1> %x, <2 x i9> <i9 3, i9 3>, <2 x i9> <i9 48, i9 48>476 %s2 = select <2 x i1> %y, <2 x i9> <i9 3, i9 3>, <2 x i9> <i9 48, i9 48>477 %and = and <2 x i9> %s1, %s2478 %cmp = icmp ne <2 x i9> %and, zeroinitializer479 ret <2 x i1> %cmp480}481 482; common bit set - simplified via known bits483 484define i1 @select_constants_and_icmp_ne0_common_bit(i1 %x, i1 %y) {485; CHECK-LABEL: @select_constants_and_icmp_ne0_common_bit(486; CHECK-NEXT: ret i1 true487;488 %s1 = select i1 %x, i8 2, i8 3489 %s2 = select i1 %y, i8 2, i8 3490 %and = and i8 %s1, %s2491 %cmp = icmp ne i8 %and, 0492 ret i1 %cmp493}494 495; negative test - need matching constants496 497define i1 @select_constants_and_icmp_ne0_no_common_op1(i1 %x, i1 %y) {498; CHECK-LABEL: @select_constants_and_icmp_ne0_no_common_op1(499; CHECK-NEXT: [[TMP1:%.*]] = xor i1 [[X:%.*]], [[Y:%.*]]500; CHECK-NEXT: [[CMP:%.*]] = xor i1 [[TMP1]], true501; CHECK-NEXT: ret i1 [[CMP]]502;503 %s1 = select i1 %x, i8 16, i8 3504 %s2 = select i1 %y, i8 24, i8 3505 %and = and i8 %s1, %s2506 %cmp = icmp ne i8 %and, 0507 ret i1 %cmp508}509 510; negative test - need matching constants511 512define i1 @select_constants_and_icmp_ne0_no_common_op2(i1 %x, i1 %y) {513; CHECK-LABEL: @select_constants_and_icmp_ne0_no_common_op2(514; CHECK-NEXT: [[TMP1:%.*]] = xor i1 [[X:%.*]], [[Y:%.*]]515; CHECK-NEXT: [[CMP:%.*]] = xor i1 [[TMP1]], true516; CHECK-NEXT: ret i1 [[CMP]]517;518 %s1 = select i1 %x, i8 16, i8 3519 %s2 = select i1 %y, i8 16, i8 7520 %and = and i8 %s1, %s2521 %cmp = icmp ne i8 %and, 0522 ret i1 %cmp523}524 525; reduces via FoldOpInstSelect, but this could be a simple 'nor'526 527define i1 @select_constants_and_icmp_ne0_zero_tval(i1 %x, i1 %y) {528; CHECK-LABEL: @select_constants_and_icmp_ne0_zero_tval(529; CHECK-NEXT: [[TMP1:%.*]] = select i1 [[X:%.*]], i1 true, i1 [[Y:%.*]]530; CHECK-NEXT: [[NOT_:%.*]] = xor i1 [[TMP1]], true531; CHECK-NEXT: ret i1 [[NOT_]]532;533 %s1 = select i1 %x, i8 0, i8 12534 %s2 = select i1 %y, i8 0, i8 12535 %and = and i8 %s1, %s2536 %cmp = icmp ne i8 %and, 0537 ret i1 %cmp538}539 540; reduces via FoldOpInstSelect, but this could be a simple 'and'541 542define i1 @select_constants_and_icmp_ne0_zero_fval(i1 %x, i1 %y) {543; CHECK-LABEL: @select_constants_and_icmp_ne0_zero_fval(544; CHECK-NEXT: [[TMP1:%.*]] = select i1 [[X:%.*]], i1 [[Y:%.*]], i1 false545; CHECK-NEXT: ret i1 [[TMP1]]546;547 %s1 = select i1 %x, i8 12, i8 0548 %s2 = select i1 %y, i8 12, i8 0549 %and = and i8 %s1, %s2550 %cmp = icmp ne i8 %and, 0551 ret i1 %cmp552}553 554define i1 @select_constants_and_icmp_ne_tval(i1 %x, i1 %y) {555; CHECK-LABEL: @select_constants_and_icmp_ne_tval(556; CHECK-NEXT: [[TMP1:%.*]] = and i1 [[X:%.*]], [[Y:%.*]]557; CHECK-NEXT: [[CMP:%.*]] = xor i1 [[TMP1]], true558; CHECK-NEXT: ret i1 [[CMP]]559;560 %s1 = select i1 %x, i8 6, i8 1561 %s2 = select i1 %y, i8 6, i8 1562 %and = and i8 %s1, %s2563 %cmp = icmp ne i8 %and, 6564 ret i1 %cmp565}566 567define i1 @select_constants_and_icmp_ne_fval(i1 %x, i1 %y) {568; CHECK-LABEL: @select_constants_and_icmp_ne_fval(569; CHECK-NEXT: [[CMP:%.*]] = or i1 [[X:%.*]], [[Y:%.*]]570; CHECK-NEXT: ret i1 [[CMP]]571;572 %s1 = select i1 %x, i8 12, i8 3573 %s2 = select i1 %y, i8 12, i8 3574 %and = and i8 %s1, %s2575 %cmp = icmp ne i8 %and, 3576 ret i1 %cmp577}578 579define i1 @icmp_eq_select(i1 %cond, i32 %a, i32 %b) {580; CHECK-LABEL: @icmp_eq_select(581; CHECK-NEXT: [[RES:%.*]] = icmp eq i32 [[A:%.*]], [[B:%.*]]582; CHECK-NEXT: ret i1 [[RES]]583;584 %lhs = select i1 %cond, i32 %a, i32 %b585 %rhs = select i1 %cond, i32 %b, i32 %a586 %res = icmp eq i32 %lhs, %rhs587 ret i1 %res588}589 590define i1 @icmp_slt_select(i1 %cond, i32 %a, i32 %b) {591; CHECK-LABEL: @icmp_slt_select(592; CHECK-NEXT: [[LHS:%.*]] = select i1 [[COND:%.*]], i32 [[A:%.*]], i32 [[B:%.*]]593; CHECK-NEXT: [[RHS:%.*]] = select i1 [[COND]], i32 [[B]], i32 [[A]]594; CHECK-NEXT: [[RES:%.*]] = icmp slt i32 [[LHS]], [[RHS]]595; CHECK-NEXT: ret i1 [[RES]]596;597 %lhs = select i1 %cond, i32 %a, i32 %b598 %rhs = select i1 %cond, i32 %b, i32 %a599 %res = icmp slt i32 %lhs, %rhs600 ret i1 %res601}602 603define i1 @discr_eq(i8 %a, i8 %b) {604; CHECK-LABEL: @discr_eq(605; CHECK-NEXT: entry:606; CHECK-NEXT: [[CMP1:%.*]] = icmp ugt i8 [[A:%.*]], 1607; CHECK-NEXT: [[CMP2:%.*]] = icmp ugt i8 [[B:%.*]], 1608; CHECK-NEXT: [[TMP0:%.*]] = select i1 [[CMP1]], i8 [[A]], i8 3609; CHECK-NEXT: [[TMP1:%.*]] = select i1 [[CMP2]], i8 [[B]], i8 3610; CHECK-NEXT: [[RES:%.*]] = icmp eq i8 [[TMP0]], [[TMP1]]611; CHECK-NEXT: ret i1 [[RES]]612;613entry:614 %add1 = add i8 %a, -2615 %cmp1 = icmp ugt i8 %a, 1616 %sel1 = select i1 %cmp1, i8 %add1, i8 1617 %add2 = add i8 %b, -2618 %cmp2 = icmp ugt i8 %b, 1619 %sel2 = select i1 %cmp2, i8 %add2, i8 1620 %res = icmp eq i8 %sel1, %sel2621 ret i1 %res622}623 624define i1 @discr_ne(i8 %a, i8 %b) {625; CHECK-LABEL: @discr_ne(626; CHECK-NEXT: entry:627; CHECK-NEXT: [[CMP1:%.*]] = icmp ugt i8 [[A:%.*]], 1628; CHECK-NEXT: [[CMP2:%.*]] = icmp ugt i8 [[B:%.*]], 1629; CHECK-NEXT: [[TMP0:%.*]] = select i1 [[CMP1]], i8 [[A]], i8 3630; CHECK-NEXT: [[TMP1:%.*]] = select i1 [[CMP2]], i8 [[B]], i8 3631; CHECK-NEXT: [[RES:%.*]] = icmp ne i8 [[TMP0]], [[TMP1]]632; CHECK-NEXT: ret i1 [[RES]]633;634entry:635 %add1 = add i8 %a, -2636 %cmp1 = icmp ugt i8 %a, 1637 %sel1 = select i1 %cmp1, i8 %add1, i8 1638 %add2 = add i8 %b, -2639 %cmp2 = icmp ugt i8 %b, 1640 %sel2 = select i1 %cmp2, i8 %add2, i8 1641 %res = icmp ne i8 %sel1, %sel2642 ret i1 %res643}644 645define i1 @discr_xor_eq(i8 %a, i8 %b) {646; CHECK-LABEL: @discr_xor_eq(647; CHECK-NEXT: entry:648; CHECK-NEXT: [[CMP1:%.*]] = icmp ugt i8 [[A:%.*]], 1649; CHECK-NEXT: [[CMP2:%.*]] = icmp ugt i8 [[B:%.*]], 1650; CHECK-NEXT: [[TMP0:%.*]] = select i1 [[CMP1]], i8 [[A]], i8 -4651; CHECK-NEXT: [[TMP1:%.*]] = select i1 [[CMP2]], i8 [[B]], i8 -4652; CHECK-NEXT: [[RES:%.*]] = icmp eq i8 [[TMP0]], [[TMP1]]653; CHECK-NEXT: ret i1 [[RES]]654;655entry:656 %xor1 = xor i8 %a, -3657 %cmp1 = icmp ugt i8 %a, 1658 %sel1 = select i1 %cmp1, i8 %xor1, i8 1659 %xor2 = xor i8 %b, -3660 %cmp2 = icmp ugt i8 %b, 1661 %sel2 = select i1 %cmp2, i8 %xor2, i8 1662 %res = icmp eq i8 %sel1, %sel2663 ret i1 %res664}665 666define i1 @discr_eq_simple(i8 %a, i8 %b) {667; CHECK-LABEL: @discr_eq_simple(668; CHECK-NEXT: entry:669; CHECK-NEXT: [[CMP1:%.*]] = icmp ugt i8 [[A:%.*]], 1670; CHECK-NEXT: [[TMP0:%.*]] = select i1 [[CMP1]], i8 [[A]], i8 3671; CHECK-NEXT: [[RES:%.*]] = icmp eq i8 [[TMP0]], [[B:%.*]]672; CHECK-NEXT: ret i1 [[RES]]673;674entry:675 %add1 = add i8 %a, -2676 %cmp1 = icmp ugt i8 %a, 1677 %sel1 = select i1 %cmp1, i8 %add1, i8 1678 %add2 = add i8 %b, -2679 %res = icmp eq i8 %sel1, %add2680 ret i1 %res681}682 683define i1 @discr_eq_add_commuted(i8 noundef %a, i8 %b, i8 %c, i1 %cond1, i1 %cond2) {684; CHECK-LABEL: @discr_eq_add_commuted(685; CHECK-NEXT: entry:686; CHECK-NEXT: [[TMP0:%.*]] = select i1 [[COND1:%.*]], i8 [[B:%.*]], i8 0687; CHECK-NEXT: [[TMP1:%.*]] = select i1 [[COND2:%.*]], i8 [[C:%.*]], i8 [[B]]688; CHECK-NEXT: [[RES:%.*]] = icmp eq i8 [[TMP0]], [[TMP1]]689; CHECK-NEXT: ret i1 [[RES]]690;691entry:692 %add1 = add i8 %a, %b693 %sel1 = select i1 %cond1, i8 %add1, i8 %a694 %add2 = add i8 %c, %a695 %sel2 = select i1 %cond2, i8 %add2, i8 %add1696 %res = icmp eq i8 %sel1, %sel2697 ret i1 %res698}699 700define i1 @discr_eq_add_commuted_implies_poison(i8 %a, i8 %b, i8 %c, i1 %cond1, i1 %cond2) {701; CHECK-LABEL: @discr_eq_add_commuted_implies_poison(702; CHECK-NEXT: entry:703; CHECK-NEXT: [[TMP0:%.*]] = select i1 [[COND1:%.*]], i8 [[B:%.*]], i8 0704; CHECK-NEXT: [[TMP1:%.*]] = select i1 [[COND2:%.*]], i8 [[C:%.*]], i8 [[B]]705; CHECK-NEXT: [[RES:%.*]] = icmp eq i8 [[TMP0]], [[TMP1]]706; CHECK-NEXT: ret i1 [[RES]]707;708entry:709 %add1 = add i8 %a, %b710 %sel1 = select i1 %cond1, i8 %add1, i8 %a711 %add2 = add i8 %c, %a712 %sel2 = select i1 %cond2, i8 %add2, i8 %add1713 %res = icmp eq i8 %sel1, %sel2714 ret i1 %res715}716 717define i1 @discr_eq_sub(i8 noundef %a, i8 %b, i8 %c, i1 %cond1, i1 %cond2) {718; CHECK-LABEL: @discr_eq_sub(719; CHECK-NEXT: entry:720; CHECK-NEXT: [[TMP0:%.*]] = select i1 [[COND1:%.*]], i8 [[B:%.*]], i8 0721; CHECK-NEXT: [[TMP1:%.*]] = select i1 [[COND2:%.*]], i8 [[C:%.*]], i8 0722; CHECK-NEXT: [[RES:%.*]] = icmp eq i8 [[TMP0]], [[TMP1]]723; CHECK-NEXT: ret i1 [[RES]]724;725entry:726 %neg = sub i8 0, %a727 %sub1 = sub i8 %b, %a728 %sel1 = select i1 %cond1, i8 %sub1, i8 %neg729 %sub2 = sub i8 %c, %a730 %sel2 = select i1 %cond2, i8 %sub2, i8 %neg731 %res = icmp eq i8 %sel1, %sel2732 ret i1 %res733}734 735; Negative tests736 737define i1 @discr_eq_multi_use(i8 %a, i8 %b) {738; CHECK-LABEL: @discr_eq_multi_use(739; CHECK-NEXT: entry:740; CHECK-NEXT: [[ADD1:%.*]] = add i8 [[A:%.*]], -2741; CHECK-NEXT: [[CMP1:%.*]] = icmp ugt i8 [[A]], 1742; CHECK-NEXT: [[SEL1:%.*]] = select i1 [[CMP1]], i8 [[ADD1]], i8 1743; CHECK-NEXT: call void @use(i8 [[SEL1]])744; CHECK-NEXT: [[ADD2:%.*]] = add i8 [[B:%.*]], -2745; CHECK-NEXT: [[CMP2:%.*]] = icmp ugt i8 [[B]], 1746; CHECK-NEXT: [[SEL2:%.*]] = select i1 [[CMP2]], i8 [[ADD2]], i8 1747; CHECK-NEXT: [[RES:%.*]] = icmp eq i8 [[SEL1]], [[SEL2]]748; CHECK-NEXT: ret i1 [[RES]]749;750entry:751 %add1 = add i8 %a, -2752 %cmp1 = icmp ugt i8 %a, 1753 %sel1 = select i1 %cmp1, i8 %add1, i8 1754 call void @use(i8 %sel1)755 %add2 = add i8 %b, -2756 %cmp2 = icmp ugt i8 %b, 1757 %sel2 = select i1 %cmp2, i8 %add2, i8 1758 %res = icmp eq i8 %sel1, %sel2759 ret i1 %res760}761 762define i1 @discr_eq_failed_to_simplify(i8 %a, i8 %b) {763; CHECK-LABEL: @discr_eq_failed_to_simplify(764; CHECK-NEXT: entry:765; CHECK-NEXT: [[ADD1:%.*]] = add i8 [[A:%.*]], -3766; CHECK-NEXT: [[CMP1:%.*]] = icmp ugt i8 [[A]], 1767; CHECK-NEXT: [[SEL1:%.*]] = select i1 [[CMP1]], i8 [[ADD1]], i8 1768; CHECK-NEXT: [[ADD2:%.*]] = add i8 [[B:%.*]], -2769; CHECK-NEXT: [[CMP2:%.*]] = icmp ugt i8 [[B]], 1770; CHECK-NEXT: [[SEL2:%.*]] = select i1 [[CMP2]], i8 [[ADD2]], i8 1771; CHECK-NEXT: [[RES:%.*]] = icmp eq i8 [[SEL1]], [[SEL2]]772; CHECK-NEXT: ret i1 [[RES]]773;774entry:775 %add1 = add i8 %a, -3776 %cmp1 = icmp ugt i8 %a, 1777 %sel1 = select i1 %cmp1, i8 %add1, i8 1778 %add2 = add i8 %b, -2779 %cmp2 = icmp ugt i8 %b, 1780 %sel2 = select i1 %cmp2, i8 %add2, i8 1781 %res = icmp eq i8 %sel1, %sel2782 ret i1 %res783}784 785define <2 x i1> @discr_eq_simple_vec(<2 x i8> %a, <2 x i8> %b, i1 %cond) {786; CHECK-LABEL: @discr_eq_simple_vec(787; CHECK-NEXT: entry:788; CHECK-NEXT: [[ADD1:%.*]] = add <2 x i8> [[A:%.*]], <i8 poison, i8 -2>789; CHECK-NEXT: [[SEL1:%.*]] = select i1 [[COND:%.*]], <2 x i8> [[ADD1]], <2 x i8> splat (i8 1)790; CHECK-NEXT: [[ADD2:%.*]] = add <2 x i8> [[B:%.*]], <i8 -2, i8 poison>791; CHECK-NEXT: [[RES:%.*]] = icmp eq <2 x i8> [[SEL1]], [[ADD2]]792; CHECK-NEXT: ret <2 x i1> [[RES]]793;794entry:795 %add1 = add <2 x i8> %a, <i8 poison, i8 -2>796 %sel1 = select i1 %cond, <2 x i8> %add1, <2 x i8> splat(i8 1)797 %add2 = add <2 x i8> %b, <i8 -2, i8 poison>798 %res = icmp eq <2 x i8> %sel1, %add2799 ret <2 x i1> %res800}801 802define i1 @discr_eq_sub_commuted(i8 noundef %a, i8 %b, i8 %c, i1 %cond1, i1 %cond2) {803; CHECK-LABEL: @discr_eq_sub_commuted(804; CHECK-NEXT: entry:805; CHECK-NEXT: [[NEG:%.*]] = sub i8 0, [[A:%.*]]806; CHECK-NEXT: [[SUB1:%.*]] = sub i8 [[A]], [[B:%.*]]807; CHECK-NEXT: [[SEL1:%.*]] = select i1 [[COND1:%.*]], i8 [[SUB1]], i8 [[NEG]]808; CHECK-NEXT: [[SUB2:%.*]] = sub i8 [[A]], [[C:%.*]]809; CHECK-NEXT: [[SEL2:%.*]] = select i1 [[COND2:%.*]], i8 [[SUB2]], i8 [[NEG]]810; CHECK-NEXT: [[RES:%.*]] = icmp eq i8 [[SEL1]], [[SEL2]]811; CHECK-NEXT: ret i1 [[RES]]812;813entry:814 %neg = sub i8 0, %a815 %sub1 = sub i8 %a, %b816 %sel1 = select i1 %cond1, i8 %sub1, i8 %neg817 %sub2 = sub i8 %a, %c818 %sel2 = select i1 %cond2, i8 %sub2, i8 %neg819 %res = icmp eq i8 %sel1, %sel2820 ret i1 %res821}822 823@g = external global i8824 825; Do not introduce constant expressions.826define i1 @discr_eq_constantexpr(ptr %p) {827; CHECK-LABEL: @discr_eq_constantexpr(828; CHECK-NEXT: [[I:%.*]] = ptrtoint ptr [[P:%.*]] to i64829; CHECK-NEXT: [[SUB:%.*]] = sub i64 [[I]], ptrtoint (ptr @g to i64)830; CHECK-NEXT: [[CMP:%.*]] = icmp eq i64 [[SUB]], -1831; CHECK-NEXT: ret i1 [[CMP]]832;833 %i = ptrtoint ptr %p to i64834 %sub = sub i64 %i, ptrtoint (ptr @g to i64)835 %cmp = icmp eq i64 %sub, -1836 ret i1 %cmp837}838 839define i1 @shl_nsw_eq_simplify_zero_to_self(i8 %a, i1 %cond) {840; CHECK-LABEL: @shl_nsw_eq_simplify_zero_to_self(841; CHECK-NEXT: [[TMP1:%.*]] = zext i1 [[COND:%.*]] to i8842; CHECK-NEXT: [[CMP:%.*]] = icmp eq i8 [[A:%.*]], [[TMP1]]843; CHECK-NEXT: ret i1 [[CMP]]844;845 %shl = shl nsw i8 %a, 3846 %sel = select i1 %cond, i8 8, i8 0847 %cmp = icmp eq i8 %shl, %sel848 ret i1 %cmp849}850 851define i1 @shl_nsw_eq(i8 %a, i1 %cond) {852; CHECK-LABEL: @shl_nsw_eq(853; CHECK-NEXT: [[TMP1:%.*]] = select i1 [[COND:%.*]], i8 1, i8 -15854; CHECK-NEXT: [[CMP:%.*]] = icmp eq i8 [[A:%.*]], [[TMP1]]855; CHECK-NEXT: ret i1 [[CMP]]856;857 %shl = shl nsw i8 %a, 3858 %sel = select i1 %cond, i8 8, i8 -120859 %cmp = icmp eq i8 %shl, %sel860 ret i1 %cmp861}862 863define i1 @shl_nuw_eq(i8 %a, i1 %cond) {864; CHECK-LABEL: @shl_nuw_eq(865; CHECK-NEXT: [[TMP1:%.*]] = select i1 [[COND:%.*]], i8 1, i8 17866; CHECK-NEXT: [[CMP:%.*]] = icmp eq i8 [[A:%.*]], [[TMP1]]867; CHECK-NEXT: ret i1 [[CMP]]868;869 %shl = shl nuw i8 %a, 3870 %sel = select i1 %cond, i8 8, i8 -120871 %cmp = icmp eq i8 %shl, %sel872 ret i1 %cmp873}874 875define i1 @shl_nsw_failed_to_simplify(i8 %a, i1 %cond) {876; CHECK-LABEL: @shl_nsw_failed_to_simplify(877; CHECK-NEXT: [[CMP1:%.*]] = icmp eq i8 [[A:%.*]], 1878; CHECK-NEXT: [[NOT_COND:%.*]] = xor i1 [[COND:%.*]], true879; CHECK-NEXT: [[CMP:%.*]] = select i1 [[NOT_COND]], i1 [[CMP1]], i1 false880; CHECK-NEXT: ret i1 [[CMP]]881;882 %shl = shl nsw i8 %a, 4883 %sel = select i1 %cond, i8 8, i8 16884 %cmp = icmp eq i8 %shl, %sel885 ret i1 %cmp886}887 888define i1 @shl_nuw_failed_to_simplify(i8 %a, i1 %cond) {889; CHECK-LABEL: @shl_nuw_failed_to_simplify(890; CHECK-NEXT: [[CMP1:%.*]] = icmp eq i8 [[A:%.*]], 4891; CHECK-NEXT: [[NOT_COND:%.*]] = xor i1 [[COND:%.*]], true892; CHECK-NEXT: [[CMP:%.*]] = select i1 [[NOT_COND]], i1 [[CMP1]], i1 false893; CHECK-NEXT: ret i1 [[CMP]]894;895 %shl = shl nuw i8 %a, 3896 %sel = select i1 %cond, i8 -1, i8 32897 %cmp = icmp eq i8 %shl, %sel898 ret i1 %cmp899}900 901define i1 @shl_failed_to_simplify(i8 %a, i1 %cond) {902; CHECK-LABEL: @shl_failed_to_simplify(903; CHECK-NEXT: [[SHL:%.*]] = shl i8 [[A:%.*]], 3904; CHECK-NEXT: [[SEL:%.*]] = select i1 [[COND:%.*]], i8 8, i8 32905; CHECK-NEXT: [[CMP:%.*]] = icmp eq i8 [[SHL]], [[SEL]]906; CHECK-NEXT: ret i1 [[CMP]]907;908 %shl = shl i8 %a, 3909 %sel = select i1 %cond, i8 8, i8 32910 %cmp = icmp eq i8 %shl, %sel911 ret i1 %cmp912}913 914define i1 @shl_nuw_ne(i8 %a, i8 %b, i8 %c, i1 %cond) {915; CHECK-LABEL: @shl_nuw_ne(916; CHECK-NEXT: [[TMP1:%.*]] = select i1 [[COND:%.*]], i8 [[B:%.*]], i8 4917; CHECK-NEXT: [[CMP:%.*]] = icmp ne i8 [[TMP1]], [[A:%.*]]918; CHECK-NEXT: ret i1 [[CMP]]919;920 %shl_a = shl nuw i8 %a, 3921 %shl_b = shl nuw i8 %b, 3922 %sel = select i1 %cond, i8 %shl_b, i8 32923 %cmp = icmp ne i8 %sel, %shl_a924 ret i1 %cmp925}926 927define i1 @shl_const_phi_failed_to_simplify(i64 %indvars, i32 %conv) {928; CHECK-LABEL: @shl_const_phi_failed_to_simplify(929; CHECK-NEXT: entry:930; CHECK-NEXT: [[CMP_SLT:%.*]] = icmp slt i64 [[INDVARS:%.*]], 1931; CHECK-NEXT: br i1 [[CMP_SLT]], label [[END:%.*]], label [[THEN:%.*]]932; CHECK: then:933; CHECK-NEXT: br label [[END]]934; CHECK: end:935; CHECK-NEXT: [[CONST_PHI:%.*]] = phi i32 [ 0, [[THEN]] ], [ 65535, [[ENTRY:%.*]] ]936; CHECK-NEXT: [[SHL_NUW:%.*]] = shl nuw i32 [[CONV:%.*]], 31937; CHECK-NEXT: [[SEL:%.*]] = select i1 [[CMP_SLT]], i32 [[CONST_PHI]], i32 [[SHL_NUW]]938; CHECK-NEXT: [[CMP:%.*]] = icmp eq i32 [[SEL]], 0939; CHECK-NEXT: ret i1 [[CMP]]940;941entry:942 %cmp_slt = icmp slt i64 %indvars, 1943 br i1 %cmp_slt, label %end, label %then944 945then:946 br label %end947 948end:949 %const_phi = phi i32 [ 0, %then ], [ 65535, %entry ]950 %shl_nuw = shl nuw i32 %conv, 31951 %sel = select i1 %cmp_slt, i32 %const_phi, i32 %shl_nuw952 %cmp = icmp eq i32 %sel, 0953 ret i1 %cmp954}955