brintos

brintos / llvm-project-archived public Read only

0
0
Text · 14.1 KiB · 7f10ce6 Raw
519 lines · plain
1; NOTE: Assertions have been autogenerated by utils/update_test_checks.py2; RUN: opt < %s -passes=correlated-propagation -S | FileCheck %s3 4declare void @llvm.assume(i1)5declare i32 @llvm.abs.i32(i32, i1)6declare i8 @llvm.abs.i8(i8, i1)7declare i1 @llvm.abs.i1(i1, i1)8 9; If we don't know anything about the argument, we can't do anything.10 11define i8 @test0(i8 %x) {12; CHECK-LABEL: @test0(13; CHECK-NEXT:    [[R:%.*]] = call i8 @llvm.abs.i8(i8 [[X:%.*]], i1 false)14; CHECK-NEXT:    ret i8 [[R]]15;16  %r = call i8 @llvm.abs.i8(i8 %x, i1 0)17  ret i8 %r18}19define i8 @test1(i8 %x) {20; CHECK-LABEL: @test1(21; CHECK-NEXT:    [[R:%.*]] = call i8 @llvm.abs.i8(i8 [[X:%.*]], i1 true)22; CHECK-NEXT:    ret i8 [[R]]23;24  %r = call i8 @llvm.abs.i8(i8 %x, i1 1)25  ret i8 %r26}27 28; But if we know that the argument is always positive, we can bypass @llvm.abs.29 30define i8 @test2(i8 %x) {31; CHECK-LABEL: @test2(32; CHECK-NEXT:    [[LIM:%.*]] = icmp sge i8 [[X:%.*]], -133; CHECK-NEXT:    call void @llvm.assume(i1 [[LIM]])34; CHECK-NEXT:    [[R:%.*]] = call i8 @llvm.abs.i8(i8 [[X]], i1 true)35; CHECK-NEXT:    ret i8 [[R]]36;37 38  %lim = icmp sge i8 %x, -139  call void @llvm.assume(i1 %lim)40  %r = call i8 @llvm.abs.i8(i8 %x, i1 0)41  ret i8 %r42}43define i8 @test3(i8 %x) {44; CHECK-LABEL: @test3(45; CHECK-NEXT:    [[LIM:%.*]] = icmp sge i8 [[X:%.*]], -146; CHECK-NEXT:    call void @llvm.assume(i1 [[LIM]])47; CHECK-NEXT:    [[R:%.*]] = call i8 @llvm.abs.i8(i8 [[X]], i1 true)48; CHECK-NEXT:    ret i8 [[R]]49;50 51  %lim = icmp sge i8 %x, -152  call void @llvm.assume(i1 %lim)53  %r = call i8 @llvm.abs.i8(i8 %x, i1 1)54  ret i8 %r55}56 57define i8 @test4(i8 %x) {58; CHECK-LABEL: @test4(59; CHECK-NEXT:    [[LIM:%.*]] = icmp sge i8 [[X:%.*]], 060; CHECK-NEXT:    call void @llvm.assume(i1 [[LIM]])61; CHECK-NEXT:    ret i8 [[X]]62;63 64  %lim = icmp sge i8 %x, 065  call void @llvm.assume(i1 %lim)66  %r = call i8 @llvm.abs.i8(i8 %x, i1 0)67  ret i8 %r68}69define i8 @test5(i8 %x) {70; CHECK-LABEL: @test5(71; CHECK-NEXT:    [[LIM:%.*]] = icmp sge i8 [[X:%.*]], 072; CHECK-NEXT:    call void @llvm.assume(i1 [[LIM]])73; CHECK-NEXT:    ret i8 [[X]]74;75 76  %lim = icmp sge i8 %x, 077  call void @llvm.assume(i1 %lim)78  %r = call i8 @llvm.abs.i8(i8 %x, i1 1)79  ret i8 %r80}81 82define i8 @test6(i8 %x) {83; CHECK-LABEL: @test6(84; CHECK-NEXT:    [[LIM:%.*]] = icmp sge i8 [[X:%.*]], 185; CHECK-NEXT:    call void @llvm.assume(i1 [[LIM]])86; CHECK-NEXT:    ret i8 [[X]]87;88 89  %lim = icmp sge i8 %x, 190  call void @llvm.assume(i1 %lim)91  %r = call i8 @llvm.abs.i8(i8 %x, i1 0)92  ret i8 %r93}94define i8 @test7(i8 %x) {95; CHECK-LABEL: @test7(96; CHECK-NEXT:    [[LIM:%.*]] = icmp sge i8 [[X:%.*]], 197; CHECK-NEXT:    call void @llvm.assume(i1 [[LIM]])98; CHECK-NEXT:    ret i8 [[X]]99;100 101  %lim = icmp sge i8 %x, 1102  call void @llvm.assume(i1 %lim)103  %r = call i8 @llvm.abs.i8(i8 %x, i1 1)104  ret i8 %r105}106 107; Likewise, INT_MIN is fine for otherwise-positive value.108 109define i8 @test8(i8 %x) {110; CHECK-LABEL: @test8(111; CHECK-NEXT:    [[LIM:%.*]] = icmp ule i8 [[X:%.*]], 127112; CHECK-NEXT:    call void @llvm.assume(i1 [[LIM]])113; CHECK-NEXT:    ret i8 [[X]]114;115 116  %lim = icmp ule i8 %x, 127117  call void @llvm.assume(i1 %lim)118  %r = call i8 @llvm.abs.i8(i8 %x, i1 0)119  ret i8 %r120}121define i8 @test9(i8 %x) {122; CHECK-LABEL: @test9(123; CHECK-NEXT:    [[LIM:%.*]] = icmp ule i8 [[X:%.*]], 127124; CHECK-NEXT:    call void @llvm.assume(i1 [[LIM]])125; CHECK-NEXT:    ret i8 [[X]]126;127 128  %lim = icmp ule i8 %x, 127129  call void @llvm.assume(i1 %lim)130  %r = call i8 @llvm.abs.i8(i8 %x, i1 1)131  ret i8 %r132}133 134define i8 @test10(i8 %x) {135; CHECK-LABEL: @test10(136; CHECK-NEXT:    [[LIM:%.*]] = icmp ule i8 [[X:%.*]], -128137; CHECK-NEXT:    call void @llvm.assume(i1 [[LIM]])138; CHECK-NEXT:    ret i8 [[X]]139;140 141  %lim = icmp ule i8 %x, 128142  call void @llvm.assume(i1 %lim)143  %r = call i8 @llvm.abs.i8(i8 %x, i1 0)144  ret i8 %r145}146define i8 @test11(i8 %x) {147; CHECK-LABEL: @test11(148; CHECK-NEXT:    [[LIM:%.*]] = icmp ule i8 [[X:%.*]], -128149; CHECK-NEXT:    call void @llvm.assume(i1 [[LIM]])150; CHECK-NEXT:    ret i8 [[X]]151;152 153  %lim = icmp ule i8 %x, 128154  call void @llvm.assume(i1 %lim)155  %r = call i8 @llvm.abs.i8(i8 %x, i1 1)156  ret i8 %r157}158 159define i8 @test12(i8 %x) {160; CHECK-LABEL: @test12(161; CHECK-NEXT:    [[LIM:%.*]] = icmp ule i8 [[X:%.*]], -127162; CHECK-NEXT:    call void @llvm.assume(i1 [[LIM]])163; CHECK-NEXT:    [[R:%.*]] = call i8 @llvm.abs.i8(i8 [[X]], i1 false)164; CHECK-NEXT:    ret i8 [[R]]165;166 167  %lim = icmp ule i8 %x, 129168  call void @llvm.assume(i1 %lim)169  %r = call i8 @llvm.abs.i8(i8 %x, i1 0)170  ret i8 %r171}172define i8 @test13(i8 %x) {173; CHECK-LABEL: @test13(174; CHECK-NEXT:    [[LIM:%.*]] = icmp ule i8 [[X:%.*]], -127175; CHECK-NEXT:    call void @llvm.assume(i1 [[LIM]])176; CHECK-NEXT:    [[R:%.*]] = call i8 @llvm.abs.i8(i8 [[X]], i1 true)177; CHECK-NEXT:    ret i8 [[R]]178;179 180  %lim = icmp ule i8 %x, 129181  call void @llvm.assume(i1 %lim)182  %r = call i8 @llvm.abs.i8(i8 %x, i1 1)183  ret i8 %r184}185 186; Likewise, if we know that argument is always negative,187; we can expand @llvm.abs into a direct negation.188; For negative arguments, we must be careful to include 0 though.189 190define i8 @test14(i8 %x) {191; CHECK-LABEL: @test14(192; CHECK-NEXT:    [[LIM:%.*]] = icmp sle i8 [[X:%.*]], -1193; CHECK-NEXT:    call void @llvm.assume(i1 [[LIM]])194; CHECK-NEXT:    [[R1:%.*]] = sub i8 0, [[X]]195; CHECK-NEXT:    ret i8 [[R1]]196;197 198  %lim = icmp sle i8 %x, -1199  call void @llvm.assume(i1 %lim)200  %r = call i8 @llvm.abs.i8(i8 %x, i1 0)201  ret i8 %r202}203define i8 @test15(i8 %x) {204; CHECK-LABEL: @test15(205; CHECK-NEXT:    [[LIM:%.*]] = icmp sle i8 [[X:%.*]], -1206; CHECK-NEXT:    call void @llvm.assume(i1 [[LIM]])207; CHECK-NEXT:    [[R1:%.*]] = sub nsw i8 0, [[X]]208; CHECK-NEXT:    ret i8 [[R1]]209;210 211  %lim = icmp sle i8 %x, -1212  call void @llvm.assume(i1 %lim)213  %r = call i8 @llvm.abs.i8(i8 %x, i1 1)214  ret i8 %r215}216 217define i8 @test16(i8 %x) {218; CHECK-LABEL: @test16(219; CHECK-NEXT:    [[LIM:%.*]] = icmp sle i8 [[X:%.*]], 0220; CHECK-NEXT:    call void @llvm.assume(i1 [[LIM]])221; CHECK-NEXT:    [[R1:%.*]] = sub i8 0, [[X]]222; CHECK-NEXT:    ret i8 [[R1]]223;224 225  %lim = icmp sle i8 %x, 0226  call void @llvm.assume(i1 %lim)227  %r = call i8 @llvm.abs.i8(i8 %x, i1 0)228  ret i8 %r229}230define i8 @test17(i8 %x) {231; CHECK-LABEL: @test17(232; CHECK-NEXT:    [[LIM:%.*]] = icmp sle i8 [[X:%.*]], 0233; CHECK-NEXT:    call void @llvm.assume(i1 [[LIM]])234; CHECK-NEXT:    [[R1:%.*]] = sub nsw i8 0, [[X]]235; CHECK-NEXT:    ret i8 [[R1]]236;237 238  %lim = icmp sle i8 %x, 0239  call void @llvm.assume(i1 %lim)240  %r = call i8 @llvm.abs.i8(i8 %x, i1 1)241  ret i8 %r242}243 244define i8 @test18(i8 %x) {245; CHECK-LABEL: @test18(246; CHECK-NEXT:    [[LIM:%.*]] = icmp sle i8 [[X:%.*]], 1247; CHECK-NEXT:    call void @llvm.assume(i1 [[LIM]])248; CHECK-NEXT:    [[R:%.*]] = call i8 @llvm.abs.i8(i8 [[X]], i1 false)249; CHECK-NEXT:    ret i8 [[R]]250;251 252  %lim = icmp sle i8 %x, 1253  call void @llvm.assume(i1 %lim)254  %r = call i8 @llvm.abs.i8(i8 %x, i1 0)255  ret i8 %r256}257define i8 @test19(i8 %x) {258; CHECK-LABEL: @test19(259; CHECK-NEXT:    [[LIM:%.*]] = icmp sle i8 [[X:%.*]], 1260; CHECK-NEXT:    call void @llvm.assume(i1 [[LIM]])261; CHECK-NEXT:    [[R:%.*]] = call i8 @llvm.abs.i8(i8 [[X]], i1 true)262; CHECK-NEXT:    ret i8 [[R]]263;264 265  %lim = icmp sle i8 %x, 1266  call void @llvm.assume(i1 %lim)267  %r = call i8 @llvm.abs.i8(i8 %x, i1 1)268  ret i8 %r269}270 271; And again, INT_MIN is also fine for otherwise-negative range.272 273define i8 @test20(i8 %x) {274; CHECK-LABEL: @test20(275; CHECK-NEXT:    [[LIM:%.*]] = icmp uge i8 [[X:%.*]], 127276; CHECK-NEXT:    call void @llvm.assume(i1 [[LIM]])277; CHECK-NEXT:    [[R:%.*]] = call i8 @llvm.abs.i8(i8 [[X]], i1 false)278; CHECK-NEXT:    ret i8 [[R]]279;280 281  %lim = icmp uge i8 %x, 127282  call void @llvm.assume(i1 %lim)283  %r = call i8 @llvm.abs.i8(i8 %x, i1 0)284  ret i8 %r285}286define i8 @test21(i8 %x) {287; CHECK-LABEL: @test21(288; CHECK-NEXT:    [[LIM:%.*]] = icmp uge i8 [[X:%.*]], 127289; CHECK-NEXT:    call void @llvm.assume(i1 [[LIM]])290; CHECK-NEXT:    [[R:%.*]] = call i8 @llvm.abs.i8(i8 [[X]], i1 true)291; CHECK-NEXT:    ret i8 [[R]]292;293 294  %lim = icmp uge i8 %x, 127295  call void @llvm.assume(i1 %lim)296  %r = call i8 @llvm.abs.i8(i8 %x, i1 1)297  ret i8 %r298}299 300define i8 @test22(i8 %x) {301; CHECK-LABEL: @test22(302; CHECK-NEXT:    [[LIM:%.*]] = icmp uge i8 [[X:%.*]], -128303; CHECK-NEXT:    call void @llvm.assume(i1 [[LIM]])304; CHECK-NEXT:    [[R1:%.*]] = sub i8 0, [[X]]305; CHECK-NEXT:    ret i8 [[R1]]306;307 308  %lim = icmp uge i8 %x, 128309  call void @llvm.assume(i1 %lim)310  %r = call i8 @llvm.abs.i8(i8 %x, i1 0)311  ret i8 %r312}313define i8 @test23(i8 %x) {314; CHECK-LABEL: @test23(315; CHECK-NEXT:    [[LIM:%.*]] = icmp uge i8 [[X:%.*]], -128316; CHECK-NEXT:    call void @llvm.assume(i1 [[LIM]])317; CHECK-NEXT:    [[R1:%.*]] = sub nsw i8 0, [[X]]318; CHECK-NEXT:    ret i8 [[R1]]319;320 321  %lim = icmp uge i8 %x, 128322  call void @llvm.assume(i1 %lim)323  %r = call i8 @llvm.abs.i8(i8 %x, i1 1)324  ret i8 %r325}326 327define i8 @test24(i8 %x) {328; CHECK-LABEL: @test24(329; CHECK-NEXT:    [[LIM:%.*]] = icmp uge i8 [[X:%.*]], -127330; CHECK-NEXT:    call void @llvm.assume(i1 [[LIM]])331; CHECK-NEXT:    [[R1:%.*]] = sub nsw i8 0, [[X]]332; CHECK-NEXT:    ret i8 [[R1]]333;334 335  %lim = icmp uge i8 %x, 129336  call void @llvm.assume(i1 %lim)337  %r = call i8 @llvm.abs.i8(i8 %x, i1 0)338  ret i8 %r339}340define i8 @test25(i8 %x) {341; CHECK-LABEL: @test25(342; CHECK-NEXT:    [[LIM:%.*]] = icmp uge i8 [[X:%.*]], -127343; CHECK-NEXT:    call void @llvm.assume(i1 [[LIM]])344; CHECK-NEXT:    [[R1:%.*]] = sub nsw i8 0, [[X]]345; CHECK-NEXT:    ret i8 [[R1]]346;347 348  %lim = icmp uge i8 %x, 129349  call void @llvm.assume(i1 %lim)350  %r = call i8 @llvm.abs.i8(i8 %x, i1 1)351  ret i8 %r352}353 354; If all else fails, we can sometimes at least inferr NSW.355 356define i8 @test26(i8 %x) {357; CHECK-LABEL: @test26(358; CHECK-NEXT:    [[LIM:%.*]] = icmp ne i8 [[X:%.*]], -128359; CHECK-NEXT:    call void @llvm.assume(i1 [[LIM]])360; CHECK-NEXT:    [[R:%.*]] = call i8 @llvm.abs.i8(i8 [[X]], i1 true)361; CHECK-NEXT:    ret i8 [[R]]362;363  %lim = icmp ne i8 %x, 128364  call void @llvm.assume(i1 %lim)365  %r = call i8 @llvm.abs.i8(i8 %x, i1 0)366  ret i8 %r367}368define i8 @test27(i8 %x) {369; CHECK-LABEL: @test27(370; CHECK-NEXT:    [[LIM:%.*]] = icmp ne i8 [[X:%.*]], -128371; CHECK-NEXT:    call void @llvm.assume(i1 [[LIM]])372; CHECK-NEXT:    [[R:%.*]] = call i8 @llvm.abs.i8(i8 [[X]], i1 true)373; CHECK-NEXT:    ret i8 [[R]]374;375  %lim = icmp ne i8 %x, 128376  call void @llvm.assume(i1 %lim)377  %r = call i8 @llvm.abs.i8(i8 %x, i1 1)378  ret i8 %r379}380 381define i1 @pr59887(i1 %x, i1 %c) {382; CHECK-LABEL: @pr59887(383; CHECK-NEXT:    [[RES:%.*]] = select i1 [[C:%.*]], i1 [[X:%.*]], i1 false384; CHECK-NEXT:    ret i1 [[RES]]385;386  %abs = call i1 @llvm.abs.i1(i1 %x, i1 false)387  %res = select i1 %c, i1 %abs, i1 false388  ret i1 %res389}390 391; Because of `undef`, We can't delete `abs`.392; We can't replace the `abs` argument with true either.393define i32 @pr68381_undef_abs_false(i1 %c0, i1 %c1, i8 %v1) {394; CHECK-LABEL: @pr68381_undef_abs_false(395; CHECK-NEXT:  start:396; CHECK-NEXT:    br i1 [[C0:%.*]], label [[BB0:%.*]], label [[BB1:%.*]]397; CHECK:       bb0:398; CHECK-NEXT:    [[V1_I32:%.*]] = zext i8 [[V1:%.*]] to i32399; CHECK-NEXT:    br label [[BB1]]400; CHECK:       bb1:401; CHECK-NEXT:    [[X:%.*]] = phi i32 [ [[V1_I32]], [[BB0]] ], [ undef, [[START:%.*]] ]402; CHECK-NEXT:    br i1 [[C1:%.*]], label [[BB0]], label [[BB2:%.*]]403; CHECK:       bb2:404; CHECK-NEXT:    [[Z:%.*]] = call i32 @llvm.abs.i32(i32 [[X]], i1 false)405; CHECK-NEXT:    ret i32 [[Z]]406;407start:408  br i1 %c0, label %bb0, label %bb1409 410bb0:411  %v1_i32 = zext i8 %v1 to i32412  br label %bb1413 414bb1:415  %x = phi i32 [ %v1_i32, %bb0 ], [ undef, %start ]416  br i1 %c1, label %bb0, label %bb2417 418bb2:419  %z = call i32 @llvm.abs.i32(i32 %x, i1 false)420  ret i32 %z421}422 423; Because of `and`, we can delete `abs`.424define i32 @pr68381_undef_abs_false_and(i1 %c0, i1 %c1, i8 %v1) {425; CHECK-LABEL: @pr68381_undef_abs_false_and(426; CHECK-NEXT:  start:427; CHECK-NEXT:    br i1 [[C0:%.*]], label [[BB0:%.*]], label [[BB1:%.*]]428; CHECK:       bb0:429; CHECK-NEXT:    [[V1_I32:%.*]] = zext i8 [[V1:%.*]] to i32430; CHECK-NEXT:    br label [[BB1]]431; CHECK:       bb1:432; CHECK-NEXT:    [[X:%.*]] = phi i32 [ [[V1_I32]], [[BB0]] ], [ undef, [[START:%.*]] ]433; CHECK-NEXT:    br i1 [[C1:%.*]], label [[BB0]], label [[BB2:%.*]]434; CHECK:       bb2:435; CHECK-NEXT:    [[Y:%.*]] = and i32 [[X]], 255436; CHECK-NEXT:    ret i32 [[Y]]437;438start:439  br i1 %c0, label %bb0, label %bb1440 441bb0:442  %v1_i32 = zext i8 %v1 to i32443  br label %bb1444 445bb1:446  %x = phi i32 [ %v1_i32, %bb0 ], [ undef, %start ]447  br i1 %c1, label %bb0, label %bb2448 449bb2:450  %y = and i32 %x, 255451  %z = call i32 @llvm.abs.i32(i32 %y, i1 false)452  ret i32 %z453}454 455; Because of `undef`, we can't replace `abs` with `sub`.456define i32 @pr68381_undef_abs_false_sub(i1 %c0, i1 %c1, i32 %v1, i32 %v2) {457; CHECK-LABEL: @pr68381_undef_abs_false_sub(458; CHECK-NEXT:  start:459; CHECK-NEXT:    br i1 [[C0:%.*]], label [[BB0:%.*]], label [[BB1:%.*]]460; CHECK:       bb0:461; CHECK-NEXT:    [[V3:%.*]] = add i32 [[V1:%.*]], [[V2:%.*]]462; CHECK-NEXT:    [[LIM:%.*]] = icmp sle i32 [[V3]], -1463; CHECK-NEXT:    call void @llvm.assume(i1 [[LIM]])464; CHECK-NEXT:    br label [[BB1]]465; CHECK:       bb1:466; CHECK-NEXT:    [[X:%.*]] = phi i32 [ [[V3]], [[BB0]] ], [ undef, [[START:%.*]] ]467; CHECK-NEXT:    br i1 [[C1:%.*]], label [[BB0]], label [[BB2:%.*]]468; CHECK:       bb2:469; CHECK-NEXT:    [[Z:%.*]] = call i32 @llvm.abs.i32(i32 [[X]], i1 false)470; CHECK-NEXT:    ret i32 [[Z]]471;472start:473  br i1 %c0, label %bb0, label %bb1474 475bb0:476  %v3 = add i32 %v1, %v2477  %lim = icmp sle i32 %v3, -1478  call void @llvm.assume(i1 %lim)479  br label %bb1480 481bb1:482  %x = phi i32 [ %v3, %bb0 ], [ undef, %start ]483  br i1 %c1, label %bb0, label %bb2484 485bb2:486  %z = call i32 @llvm.abs.i32(i32 %x, i1 false)487  ret i32 %z488}489 490; We can delete `abs`.491define i32 @pr68381_undef_abs_true(i1 %c0, i1 %c1, i8 %v1) {492; CHECK-LABEL: @pr68381_undef_abs_true(493; CHECK-NEXT:  start:494; CHECK-NEXT:    br i1 [[C0:%.*]], label [[BB0:%.*]], label [[BB1:%.*]]495; CHECK:       bb0:496; CHECK-NEXT:    [[V1_I32:%.*]] = zext i8 [[V1:%.*]] to i32497; CHECK-NEXT:    br label [[BB1]]498; CHECK:       bb1:499; CHECK-NEXT:    [[X:%.*]] = phi i32 [ [[V1_I32]], [[BB0]] ], [ undef, [[START:%.*]] ]500; CHECK-NEXT:    br i1 [[C1:%.*]], label [[BB0]], label [[BB2:%.*]]501; CHECK:       bb2:502; CHECK-NEXT:    ret i32 [[X]]503;504start:505  br i1 %c0, label %bb0, label %bb1506 507bb0:508  %v1_i32 = zext i8 %v1 to i32509  br label %bb1510 511bb1:512  %x = phi i32 [ %v1_i32, %bb0 ], [ undef, %start ]513  br i1 %c1, label %bb0, label %bb2514 515bb2:516  %z = call i32 @llvm.abs.i32(i32 %x, i1 true)517  ret i32 %z518}519