brintos

brintos / llvm-project-archived public Read only

0
0
Text · 17.3 KiB · 13ed7ba Raw
647 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(i32)5declare void @use_vec(<2 x i8>)6 7define i1 @test_nuw_and_unsigned_pred(i64 %x) {8; CHECK-LABEL: @test_nuw_and_unsigned_pred(9; CHECK-NEXT:    [[Z:%.*]] = icmp ugt i64 [[X:%.*]], 710; CHECK-NEXT:    ret i1 [[Z]]11;12  %y = sub nuw i64 10, %x13  %z = icmp ult i64 %y, 314  ret i1 %z15}16 17define i1 @test_nsw_and_signed_pred(i64 %x) {18; CHECK-LABEL: @test_nsw_and_signed_pred(19; CHECK-NEXT:    [[Z:%.*]] = icmp slt i64 [[X:%.*]], -720; CHECK-NEXT:    ret i1 [[Z]]21;22  %y = sub nsw i64 3, %x23  %z = icmp sgt i64 %y, 1024  ret i1 %z25}26 27define i1 @test_nuw_nsw_and_unsigned_pred(i64 %x) {28; CHECK-LABEL: @test_nuw_nsw_and_unsigned_pred(29; CHECK-NEXT:    [[Z:%.*]] = icmp ugt i64 [[X:%.*]], 630; CHECK-NEXT:    ret i1 [[Z]]31;32  %y = sub nuw nsw i64 10, %x33  %z = icmp ule i64 %y, 334  ret i1 %z35}36 37define i1 @test_nuw_nsw_and_signed_pred(i64 %x) {38; CHECK-LABEL: @test_nuw_nsw_and_signed_pred(39; CHECK-NEXT:    [[Z:%.*]] = icmp ugt i64 [[X:%.*]], 740; CHECK-NEXT:    ret i1 [[Z]]41;42  %y = sub nuw nsw i64 10, %x43  %z = icmp slt i64 %y, 344  ret i1 %z45}46 47define i1 @test_negative_nuw_and_signed_pred(i64 %x) {48; CHECK-LABEL: @test_negative_nuw_and_signed_pred(49; CHECK-NEXT:    [[Z:%.*]] = icmp ugt i64 [[X:%.*]], 750; CHECK-NEXT:    ret i1 [[Z]]51;52  %y = sub nuw i64 10, %x53  %z = icmp slt i64 %y, 354  ret i1 %z55}56 57define i1 @test_negative_nsw_and_unsigned_pred(i64 %x) {58; CHECK-LABEL: @test_negative_nsw_and_unsigned_pred(59; CHECK-NEXT:    [[TMP1:%.*]] = add i64 [[X:%.*]], -860; CHECK-NEXT:    [[Z:%.*]] = icmp ult i64 [[TMP1]], 361; CHECK-NEXT:    ret i1 [[Z]]62;63  %y = sub nsw i64 10, %x64  %z = icmp ult i64 %y, 365  ret i1 %z66}67 68define i1 @test_negative_combined_sub_unsigned_overflow(i64 %x) {69; CHECK-LABEL: @test_negative_combined_sub_unsigned_overflow(70; CHECK-NEXT:    ret i1 true71;72  %y = sub nuw i64 10, %x73  %z = icmp ult i64 %y, 1174  ret i1 %z75}76 77define i1 @test_negative_combined_sub_signed_overflow(i8 %x) {78; CHECK-LABEL: @test_negative_combined_sub_signed_overflow(79; CHECK-NEXT:    ret i1 false80;81  %y = sub nsw i8 127, %x82  %z = icmp slt i8 %y, -183  ret i1 %z84}85 86define i1 @test_sub_0_Y_eq_0(i8 %y) {87; CHECK-LABEL: @test_sub_0_Y_eq_0(88; CHECK-NEXT:    [[Z:%.*]] = icmp eq i8 [[Y:%.*]], 089; CHECK-NEXT:    ret i1 [[Z]]90;91  %s = sub i8 0, %y92  %z = icmp eq i8 %s, 093  ret i1 %z94}95 96define i1 @test_sub_0_Y_ne_0(i8 %y) {97; CHECK-LABEL: @test_sub_0_Y_ne_0(98; CHECK-NEXT:    [[Z:%.*]] = icmp ne i8 [[Y:%.*]], 099; CHECK-NEXT:    ret i1 [[Z]]100;101  %s = sub i8 0, %y102  %z = icmp ne i8 %s, 0103  ret i1 %z104}105 106define i1 @test_sub_4_Y_ne_4(i8 %y) {107; CHECK-LABEL: @test_sub_4_Y_ne_4(108; CHECK-NEXT:    [[Z:%.*]] = icmp ne i8 [[Y:%.*]], 0109; CHECK-NEXT:    ret i1 [[Z]]110;111  %s = sub i8 4, %y112  %z = icmp ne i8 %s, 4113  ret i1 %z114}115 116define i1 @test_sub_127_Y_eq_127(i8 %y) {117; CHECK-LABEL: @test_sub_127_Y_eq_127(118; CHECK-NEXT:    [[Z:%.*]] = icmp eq i8 [[Y:%.*]], 0119; CHECK-NEXT:    ret i1 [[Z]]120;121  %s = sub i8 127, %y122  %z = icmp eq i8 %s, 127123  ret i1 %z124}125 126define i1 @test_sub_255_Y_eq_255(i8 %y) {127; CHECK-LABEL: @test_sub_255_Y_eq_255(128; CHECK-NEXT:    [[Z:%.*]] = icmp eq i8 [[Y:%.*]], 0129; CHECK-NEXT:    ret i1 [[Z]]130;131  %s = sub i8 255, %y132  %z = icmp eq i8 %s, 255133  ret i1 %z134}135define <2 x i1> @test_sub_255_Y_eq_255_vec(<2 x i8> %y) {136; CHECK-LABEL: @test_sub_255_Y_eq_255_vec(137; CHECK-NEXT:    [[Z:%.*]] = icmp eq <2 x i8> [[Y:%.*]], zeroinitializer138; CHECK-NEXT:    ret <2 x i1> [[Z]]139;140  %s = sub <2 x i8> <i8 255, i8 255>, %y141  %z = icmp eq <2 x i8> %s, <i8 255, i8 255>142  ret <2 x i1> %z143}144 145define <2 x i1> @icmp_eq_sub_undef(<2 x i32> %a) {146; CHECK-LABEL: @icmp_eq_sub_undef(147; CHECK-NEXT:    [[CMP:%.*]] = icmp eq <2 x i32> [[A:%.*]], <i32 5, i32 undef>148; CHECK-NEXT:    ret <2 x i1> [[CMP]]149;150  %sub = sub <2 x i32> <i32 15, i32 undef>, %a151  %cmp = icmp eq <2 x i32> %sub, <i32 10, i32 10>152  ret <2 x i1> %cmp153}154 155define <2 x i1> @icmp_eq_sub_non_splat(<2 x i32> %a) {156; CHECK-LABEL: @icmp_eq_sub_non_splat(157; CHECK-NEXT:    [[CMP:%.*]] = icmp eq <2 x i32> [[A:%.*]], <i32 5, i32 6>158; CHECK-NEXT:    ret <2 x i1> [[CMP]]159;160  %sub = sub <2 x i32> <i32 15, i32 16>, %a161  %cmp = icmp eq <2 x i32> %sub, <i32 10, i32 10>162  ret <2 x i1> %cmp163}164 165define <2 x i1> @icmp_eq_sub_undef2(<2 x i32> %a) {166; CHECK-LABEL: @icmp_eq_sub_undef2(167; CHECK-NEXT:    [[SUB:%.*]] = sub <2 x i32> splat (i32 15), [[A:%.*]]168; CHECK-NEXT:    [[CMP:%.*]] = icmp eq <2 x i32> [[SUB]], <i32 10, i32 undef>169; CHECK-NEXT:    ret <2 x i1> [[CMP]]170;171  %sub = sub <2 x i32> <i32 15, i32 15>, %a172  %cmp = icmp eq <2 x i32> %sub, <i32 10, i32 undef>173  ret <2 x i1> %cmp174}175 176define <2 x i1> @icmp_eq_sub_non_splat2(<2 x i32> %a) {177; CHECK-LABEL: @icmp_eq_sub_non_splat2(178; CHECK-NEXT:    [[SUB:%.*]] = sub <2 x i32> splat (i32 15), [[A:%.*]]179; CHECK-NEXT:    [[CMP:%.*]] = icmp eq <2 x i32> [[SUB]], <i32 10, i32 11>180; CHECK-NEXT:    ret <2 x i1> [[CMP]]181;182  %sub = sub <2 x i32> <i32 15, i32 15>, %a183  %cmp = icmp eq <2 x i32> %sub, <i32 10, i32 11>184  ret <2 x i1> %cmp185}186 187define i1 @neg_sgt_42(i32 %x) {188; CHECK-LABEL: @neg_sgt_42(189; CHECK-NEXT:    [[NOTSUB:%.*]] = add i32 [[X:%.*]], -1190; CHECK-NEXT:    [[R:%.*]] = icmp slt i32 [[NOTSUB]], -43191; CHECK-NEXT:    ret i1 [[R]]192;193  %negx = sub i32 0, %x194  %r = icmp sgt i32 %negx, 42195  ret i1 %r196}197 198define i1 @neg_eq_43(i32 %x) {199; CHECK-LABEL: @neg_eq_43(200; CHECK-NEXT:    [[NEGX:%.*]] = sub i32 0, [[X:%.*]]201; CHECK-NEXT:    call void @use(i32 [[NEGX]])202; CHECK-NEXT:    [[R:%.*]] = icmp eq i32 [[X]], -43203; CHECK-NEXT:    ret i1 [[R]]204;205  %negx = sub i32 0, %x206  call void @use(i32 %negx)207  %r = icmp eq i32 %negx, 43208  ret i1 %r209}210 211define i1 @neg_ne_44(i32 %x) {212; CHECK-LABEL: @neg_ne_44(213; CHECK-NEXT:    [[NEGX:%.*]] = sub i32 0, [[X:%.*]]214; CHECK-NEXT:    call void @use(i32 [[NEGX]])215; CHECK-NEXT:    [[R:%.*]] = icmp ne i32 [[X]], -44216; CHECK-NEXT:    ret i1 [[R]]217;218  %negx = sub i32 0, %x219  call void @use(i32 %negx)220  %r = icmp ne i32 %negx, 44221  ret i1 %r222}223 224define i1 @neg_nsw_eq_45(i32 %x) {225; CHECK-LABEL: @neg_nsw_eq_45(226; CHECK-NEXT:    [[NEGX:%.*]] = sub nsw i32 0, [[X:%.*]]227; CHECK-NEXT:    call void @use(i32 [[NEGX]])228; CHECK-NEXT:    [[R:%.*]] = icmp eq i32 [[X]], -45229; CHECK-NEXT:    ret i1 [[R]]230;231  %negx = sub nsw i32 0, %x232  call void @use(i32 %negx)233  %r = icmp eq i32 %negx, 45234  ret i1 %r235}236 237define i1 @neg_nsw_ne_46(i32 %x) {238; CHECK-LABEL: @neg_nsw_ne_46(239; CHECK-NEXT:    [[NEGX:%.*]] = sub nsw i32 0, [[X:%.*]]240; CHECK-NEXT:    call void @use(i32 [[NEGX]])241; CHECK-NEXT:    [[R:%.*]] = icmp ne i32 [[X]], -46242; CHECK-NEXT:    ret i1 [[R]]243;244  %negx = sub nsw i32 0, %x245  call void @use(i32 %negx)246  %r = icmp ne i32 %negx, 46247  ret i1 %r248}249 250define i1 @subC_eq(i32 %x) {251; CHECK-LABEL: @subC_eq(252; CHECK-NEXT:    [[SUBX:%.*]] = sub i32 -2147483648, [[X:%.*]]253; CHECK-NEXT:    call void @use(i32 [[SUBX]])254; CHECK-NEXT:    [[R:%.*]] = icmp eq i32 [[X]], 2147483605255; CHECK-NEXT:    ret i1 [[R]]256;257  %subx = sub i32 -2147483648, %x258  call void @use(i32 %subx)259  %r = icmp eq i32 %subx, 43260  ret i1 %r261}262 263define <2 x i1> @subC_ne(<2 x i8> %x) {264; CHECK-LABEL: @subC_ne(265; CHECK-NEXT:    [[SUBX:%.*]] = sub <2 x i8> <i8 -6, i8 -128>, [[X:%.*]]266; CHECK-NEXT:    call void @use_vec(<2 x i8> [[SUBX]])267; CHECK-NEXT:    [[R:%.*]] = icmp ne <2 x i8> [[X]], <i8 38, i8 -84>268; CHECK-NEXT:    ret <2 x i1> [[R]]269;270  %subx = sub <2 x i8> <i8 -6, i8 -128>, %x271  call void @use_vec(<2 x i8> %subx)272  %r = icmp ne <2 x i8> %subx, <i8 -44, i8 -44>273  ret <2 x i1> %r274}275 276define i1 @subC_nsw_eq(i32 %x) {277; CHECK-LABEL: @subC_nsw_eq(278; CHECK-NEXT:    [[SUBX:%.*]] = sub nsw i32 -100, [[X:%.*]]279; CHECK-NEXT:    call void @use(i32 [[SUBX]])280; CHECK-NEXT:    [[R:%.*]] = icmp eq i32 [[X]], 2147483548281; CHECK-NEXT:    ret i1 [[R]]282;283  %subx = sub nsw i32 -100, %x284  call void @use(i32 %subx)285  %r = icmp eq i32 %subx, -2147483648286  ret i1 %r287}288 289define i1 @subC_nsw_ne(i32 %x) {290; CHECK-LABEL: @subC_nsw_ne(291; CHECK-NEXT:    [[SUBX:%.*]] = sub nsw i32 -2147483647, [[X:%.*]]292; CHECK-NEXT:    call void @use(i32 [[SUBX]])293; CHECK-NEXT:    ret i1 true294;295  %subx = sub nsw i32 -2147483647, %x296  call void @use(i32 %subx)297  %r = icmp ne i32 %subx, 46298  ret i1 %r299}300 301define i1 @neg_slt_42(i128 %x) {302; CHECK-LABEL: @neg_slt_42(303; CHECK-NEXT:    [[NOTSUB:%.*]] = add i128 [[X:%.*]], -1304; CHECK-NEXT:    [[R:%.*]] = icmp sgt i128 [[NOTSUB]], -43305; CHECK-NEXT:    ret i1 [[R]]306;307  %negx = sub i128 0, %x308  %r = icmp slt i128 %negx, 42309  ret i1 %r310}311 312define <2 x i1> @neg_ugt_42_splat(<2 x i7> %x) {313; CHECK-LABEL: @neg_ugt_42_splat(314; CHECK-NEXT:    [[NOTSUB:%.*]] = add <2 x i7> [[X:%.*]], splat (i7 -1)315; CHECK-NEXT:    [[R:%.*]] = icmp ult <2 x i7> [[NOTSUB]], splat (i7 -43)316; CHECK-NEXT:    ret <2 x i1> [[R]]317;318  %negx = sub <2 x i7> zeroinitializer, %x319  %r = icmp ugt <2 x i7> %negx, <i7 42, i7 42>320  ret <2 x i1> %r321}322 323define i1 @neg_sgt_42_use(i32 %x) {324; CHECK-LABEL: @neg_sgt_42_use(325; CHECK-NEXT:    [[NEGX:%.*]] = sub i32 0, [[X:%.*]]326; CHECK-NEXT:    call void @use(i32 [[NEGX]])327; CHECK-NEXT:    [[R:%.*]] = icmp sgt i32 [[NEGX]], 42328; CHECK-NEXT:    ret i1 [[R]]329;330  %negx = sub i32 0, %x331  call void @use(i32 %negx)332  %r = icmp sgt i32 %negx, 42333  ret i1 %r334}335 336; Test common/edge cases with signed pred.337 338define i1 @neg_slt_n1(i8 %x) {339; CHECK-LABEL: @neg_slt_n1(340; CHECK-NEXT:    [[NOTSUB:%.*]] = add i8 [[X:%.*]], -1341; CHECK-NEXT:    [[R:%.*]] = icmp sgt i8 [[NOTSUB]], 0342; CHECK-NEXT:    ret i1 [[R]]343;344  %negx = sub i8 0, %x345  %r = icmp slt i8 %negx, -1346  ret i1 %r347}348 349define i1 @neg_slt_0(i8 %x) {350; CHECK-LABEL: @neg_slt_0(351; CHECK-NEXT:    [[NOTSUB:%.*]] = add i8 [[X:%.*]], -1352; CHECK-NEXT:    [[ISNEGNEG:%.*]] = icmp sgt i8 [[NOTSUB]], -1353; CHECK-NEXT:    ret i1 [[ISNEGNEG]]354;355  %negx = sub i8 0, %x356  %isnegneg = icmp slt i8 %negx, 0357  ret i1 %isnegneg358}359 360define i1 @neg_slt_1(i8 %x) {361; CHECK-LABEL: @neg_slt_1(362; CHECK-NEXT:    [[R:%.*]] = icmp ult i8 [[X:%.*]], -127363; CHECK-NEXT:    ret i1 [[R]]364;365  %negx = sub i8 0, %x366  %r = icmp slt i8 %negx, 1367  ret i1 %r368}369 370define i1 @neg_sgt_n1(i8 %x) {371; CHECK-LABEL: @neg_sgt_n1(372; CHECK-NEXT:    [[NOTSUB:%.*]] = add i8 [[X:%.*]], -1373; CHECK-NEXT:    [[R:%.*]] = icmp slt i8 [[NOTSUB]], 0374; CHECK-NEXT:    ret i1 [[R]]375;376  %negx = sub i8 0, %x377  %r = icmp sgt i8 %negx, -1378  ret i1 %r379}380 381define i1 @neg_sgt_0(i8 %x) {382; CHECK-LABEL: @neg_sgt_0(383; CHECK-NEXT:    [[R:%.*]] = icmp ugt i8 [[X:%.*]], -128384; CHECK-NEXT:    ret i1 [[R]]385;386  %negx = sub i8 0, %x387  %r = icmp sgt i8 %negx, 0388  ret i1 %r389}390 391define i1 @neg_sgt_1(i8 %x) {392; CHECK-LABEL: @neg_sgt_1(393; CHECK-NEXT:    [[NOTSUB:%.*]] = add i8 [[X:%.*]], -1394; CHECK-NEXT:    [[R:%.*]] = icmp slt i8 [[NOTSUB]], -2395; CHECK-NEXT:    ret i1 [[R]]396;397  %negx = sub i8 0, %x398  %r = icmp sgt i8 %negx, 1399  ret i1 %r400}401 402; Test common/edge cases with signed pred and nsw.403 404define i1 @neg_nsw_slt_n1(i8 %x) {405; CHECK-LABEL: @neg_nsw_slt_n1(406; CHECK-NEXT:    [[R:%.*]] = icmp sgt i8 [[X:%.*]], 1407; CHECK-NEXT:    ret i1 [[R]]408;409  %negx = sub nsw i8 0, %x410  %r = icmp slt i8 %negx, -1411  ret i1 %r412}413 414define i1 @neg_nsw_slt_0(i8 %x) {415; CHECK-LABEL: @neg_nsw_slt_0(416; CHECK-NEXT:    [[ISNEGNEG:%.*]] = icmp sgt i8 [[X:%.*]], 0417; CHECK-NEXT:    ret i1 [[ISNEGNEG]]418;419  %negx = sub nsw i8 0, %x420  %isnegneg = icmp slt i8 %negx, 0421  ret i1 %isnegneg422}423 424define i1 @neg_nsw_slt_1(i8 %x) {425; CHECK-LABEL: @neg_nsw_slt_1(426; CHECK-NEXT:    [[R:%.*]] = icmp sgt i8 [[X:%.*]], -1427; CHECK-NEXT:    ret i1 [[R]]428;429  %negx = sub nsw i8 0, %x430  %r = icmp slt i8 %negx, 1431  ret i1 %r432}433 434define i1 @neg_nsw_sgt_n1(i8 %x) {435; CHECK-LABEL: @neg_nsw_sgt_n1(436; CHECK-NEXT:    [[R:%.*]] = icmp slt i8 [[X:%.*]], 1437; CHECK-NEXT:    ret i1 [[R]]438;439  %negx = sub nsw i8 0, %x440  %r = icmp sgt i8 %negx, -1441  ret i1 %r442}443 444define i1 @neg_nsw_sgt_0(i8 %x) {445; CHECK-LABEL: @neg_nsw_sgt_0(446; CHECK-NEXT:    [[R:%.*]] = icmp slt i8 [[X:%.*]], 0447; CHECK-NEXT:    ret i1 [[R]]448;449  %negx = sub nsw i8 0, %x450  %r = icmp sgt i8 %negx, 0451  ret i1 %r452}453 454define i1 @neg_nsw_sgt_1(i8 %x) {455; CHECK-LABEL: @neg_nsw_sgt_1(456; CHECK-NEXT:    [[R:%.*]] = icmp slt i8 [[X:%.*]], -1457; CHECK-NEXT:    ret i1 [[R]]458;459  %negx = sub nsw i8 0, %x460  %r = icmp sgt i8 %negx, 1461  ret i1 %r462}463 464define i1 @sub_eq_zero_use(i32 %x, i32 %y) {465; CHECK-LABEL: @sub_eq_zero_use(466; CHECK-NEXT:    [[SUB:%.*]] = sub i32 [[X:%.*]], [[Y:%.*]]467; CHECK-NEXT:    call void @use(i32 [[SUB]])468; CHECK-NEXT:    [[R:%.*]] = icmp eq i32 [[X]], [[Y]]469; CHECK-NEXT:    ret i1 [[R]]470;471  %sub = sub i32 %x, %y472  call void @use(i32 %sub)473  %r = icmp eq i32 %sub, 0474  ret i1 %r475}476 477define <2 x i1> @sub_ne_zero_use(<2 x i8> %x, <2 x i8> %y) {478; CHECK-LABEL: @sub_ne_zero_use(479; CHECK-NEXT:    [[SUB:%.*]] = sub <2 x i8> [[X:%.*]], [[Y:%.*]]480; CHECK-NEXT:    call void @use_vec(<2 x i8> [[SUB]])481; CHECK-NEXT:    [[R:%.*]] = icmp eq <2 x i8> [[X]], [[Y]]482; CHECK-NEXT:    ret <2 x i1> [[R]]483;484  %sub = sub <2 x i8> %x, %y485  call void @use_vec(<2 x i8> %sub)486  %r = icmp eq <2 x i8> %sub, zeroinitializer487  ret <2 x i1> %r488}489 490define i32 @sub_eq_zero_select(i32 %a, i32 %b, ptr %p) {491; CHECK-LABEL: @sub_eq_zero_select(492; CHECK-NEXT:    [[SUB:%.*]] = sub i32 [[A:%.*]], [[B:%.*]]493; CHECK-NEXT:    store i32 [[SUB]], ptr [[P:%.*]], align 4494; CHECK-NEXT:    ret i32 [[B]]495;496  %sub = sub i32 %a, %b497  store i32 %sub, ptr %p498  %cmp = icmp eq i32 %sub, 0499  %sel = select i1 %cmp, i32 %a, i32 %b500  ret i32 %sel501}502 503; Replacing the "SUB == 0" regresses codegen, and it may be hard to recover from that.504 505declare i32 @llvm.umin.i32(i32, i32)506 507define void @PR54558_reduced(i32 %arg) {508; CHECK-LABEL: @PR54558_reduced(509; CHECK-NEXT:  bb_entry:510; CHECK-NEXT:    br label [[BB_LOOP:%.*]]511; CHECK:       bb_loop:512; CHECK-NEXT:    [[PHI_OUTER:%.*]] = phi i32 [ [[SUB:%.*]], [[BB_LOOP]] ], [ [[ARG:%.*]], [[BB_ENTRY:%.*]] ]513; CHECK-NEXT:    [[MIN:%.*]] = tail call i32 @llvm.umin.i32(i32 [[PHI_OUTER]], i32 43)514; CHECK-NEXT:    call void @use(i32 [[MIN]])515; CHECK-NEXT:    [[SUB]] = sub i32 [[PHI_OUTER]], [[MIN]]516; CHECK-NEXT:    [[COND_OUTER:%.*]] = icmp eq i32 [[SUB]], 0517; CHECK-NEXT:    br i1 [[COND_OUTER]], label [[BB_EXIT:%.*]], label [[BB_LOOP]]518; CHECK:       bb_exit:519; CHECK-NEXT:    ret void520;521bb_entry:522  br label %bb_loop523 524bb_loop:525  %phi_outer = phi i32 [ %sub, %bb_loop ], [ %arg, %bb_entry ]526  %min = tail call i32 @llvm.umin.i32(i32 %phi_outer, i32 43)527  call void @use(i32 %min)528  %sub = sub i32 %phi_outer, %min529  %cond_outer = icmp eq i32 %sub, 0530  br i1 %cond_outer, label %bb_exit, label %bb_loop531 532bb_exit:533  ret void534}535 536; TODO: It might be ok to replace the "SUB == 0" in this example if codegen can invert it.537 538define void @PR54558_reduced_more(i32 %x, i32 %y) {539; CHECK-LABEL: @PR54558_reduced_more(540; CHECK-NEXT:  bb_entry:541; CHECK-NEXT:    br label [[BB_LOOP:%.*]]542; CHECK:       bb_loop:543; CHECK-NEXT:    [[PHI_OUTER:%.*]] = phi i32 [ [[SUB:%.*]], [[BB_LOOP]] ], [ [[X:%.*]], [[BB_ENTRY:%.*]] ]544; CHECK-NEXT:    [[SUB]] = sub i32 [[PHI_OUTER]], [[Y:%.*]]545; CHECK-NEXT:    [[COND_OUTER:%.*]] = icmp eq i32 [[SUB]], 0546; CHECK-NEXT:    br i1 [[COND_OUTER]], label [[BB_EXIT:%.*]], label [[BB_LOOP]]547; CHECK:       bb_exit:548; CHECK-NEXT:    ret void549;550bb_entry:551  br label %bb_loop552 553bb_loop:554  %phi_outer = phi i32 [ %sub, %bb_loop ], [ %x, %bb_entry ]555  %sub = sub i32 %phi_outer, %y556  %cond_outer = icmp eq i32 %sub, 0557  br i1 %cond_outer, label %bb_exit, label %bb_loop558 559bb_exit:560  ret void561}562 563; https://alive2.llvm.org/ce/z/D2Aph4564define i1 @PR60818_ne(i32 %a) {565; CHECK-LABEL: @PR60818_ne(566; CHECK-NEXT:  entry:567; CHECK-NEXT:    [[TMP0:%.*]] = and i32 [[A:%.*]], 2147483647568; CHECK-NEXT:    [[CMP:%.*]] = icmp ne i32 [[TMP0]], 0569; CHECK-NEXT:    ret i1 [[CMP]]570;571entry:572  %sub = sub i32 0, %a573  %cmp = icmp ne i32 %sub, %a574  ret i1 %cmp575}576 577define i1 @PR60818_eq(i32 %a) {578; CHECK-LABEL: @PR60818_eq(579; CHECK-NEXT:  entry:580; CHECK-NEXT:    [[TMP0:%.*]] = and i32 [[A:%.*]], 2147483647581; CHECK-NEXT:    [[CMP:%.*]] = icmp eq i32 [[TMP0]], 0582; CHECK-NEXT:    ret i1 [[CMP]]583;584entry:585  %sub = sub i32 0, %a586  %cmp = icmp eq i32 %sub, %a587  ret i1 %cmp588}589 590define i1 @PR60818_eq_commuted(i32 %x) {591; CHECK-LABEL: @PR60818_eq_commuted(592; CHECK-NEXT:  entry:593; CHECK-NEXT:    [[A:%.*]] = mul i32 [[X:%.*]], 43594; CHECK-NEXT:    [[TMP0:%.*]] = and i32 [[A]], 2147483647595; CHECK-NEXT:    [[CMP:%.*]] = icmp eq i32 [[TMP0]], 0596; CHECK-NEXT:    ret i1 [[CMP]]597;598entry:599  %a = mul i32 %x, 43         ; thwart complexity-based canonicalization600  %sub = sub i32 0, %a601  %cmp = icmp eq i32 %a, %sub ; negation on RHS602  ret i1 %cmp603}604 605define <2 x i1> @PR60818_ne_vector(<2 x i32> %a) {606; CHECK-LABEL: @PR60818_ne_vector(607; CHECK-NEXT:  entry:608; CHECK-NEXT:    [[TMP0:%.*]] = and <2 x i32> [[A:%.*]], splat (i32 2147483647)609; CHECK-NEXT:    [[CMP:%.*]] = icmp ne <2 x i32> [[TMP0]], zeroinitializer610; CHECK-NEXT:    ret <2 x i1> [[CMP]]611;612entry:613  %sub = sub <2 x i32> zeroinitializer, %a614  %cmp = icmp ne <2 x i32> %a, %sub615  ret <2 x i1> %cmp616}617 618; Negative as multi-use619define i1 @PR60818_eq_multi_use(i32 %a) {620; CHECK-LABEL: @PR60818_eq_multi_use(621; CHECK-NEXT:  entry:622; CHECK-NEXT:    [[SUB:%.*]] = sub i32 0, [[A:%.*]]623; CHECK-NEXT:    call void @use(i32 [[SUB]])624; CHECK-NEXT:    [[CMP:%.*]] = icmp eq i32 [[A]], [[SUB]]625; CHECK-NEXT:    ret i1 [[CMP]]626;627entry:628  %sub = sub i32 0, %a629  call void @use(i32 %sub)  ; add new user630  %cmp = icmp eq i32 %sub, %a631  ret i1 %cmp632}633 634; Negative as non-equality predicate635define i1 @PR60818_sgt(i32 %a) {636; CHECK-LABEL: @PR60818_sgt(637; CHECK-NEXT:  entry:638; CHECK-NEXT:    [[SUB:%.*]] = sub i32 0, [[A:%.*]]639; CHECK-NEXT:    [[CMP:%.*]] = icmp slt i32 [[A]], [[SUB]]640; CHECK-NEXT:    ret i1 [[CMP]]641;642entry:643  %sub = sub i32 0, %a644  %cmp = icmp sgt i32 %sub, %a645  ret i1 %cmp646}647