1*fe950cbaSDaniil Suchkov; RUN: opt -S -passes='require<scalar-evolution>,require<lazy-value-info>,loop-mssa(loop-predication)' -debug-pass-manager < %s 2>&1 | FileCheck %s 25f2b7879SDaniil Suchkov 3*fe950cbaSDaniil Suchkov; NOTE: LazyValueAnalysis is an arbitrary analysis that just isn't preserved by 4*fe950cbaSDaniil Suchkov; this pass. If after your change this analysis is preserved by the pass, 5*fe950cbaSDaniil Suchkov; please update this test some other analysis that isn't preserved. 65f2b7879SDaniil Suchkov 7*fe950cbaSDaniil Suchkov; CHECK: Running analysis: LazyValueAnalysis on drop_a_wc_and_leave_early 85f2b7879SDaniil Suchkov; CHECK: Running pass: LoopPredicationPass on Loop at depth 1 containing: %loop<header><exiting>,%guarded<exiting>,%guarded2<latch><exiting> 9*fe950cbaSDaniil Suchkov; CHECK: Invalidating analysis: LazyValueAnalysis on drop_a_wc_and_leave_early 10*fe950cbaSDaniil Suchkov; CHECK: Running analysis: LazyValueAnalysis on drop_a_wc_and_leave 115f2b7879SDaniil Suchkov; CHECK: Running pass: LoopPredicationPass on Loop at depth 1 containing: %loop<header><exiting>,%guarded<exiting>,%guarded2<latch><exiting> 12*fe950cbaSDaniil Suchkov; CHECK: Invalidating analysis: LazyValueAnalysis on drop_a_wc_and_leave 135f2b7879SDaniil Suchkov 145f2b7879SDaniil Suchkov 155f2b7879SDaniil Suchkov; This test makes the pass drop its attempts to optimize the exit condition in 165f2b7879SDaniil Suchkov; `%loop` BB by using unanalyzable `%cond_0` as an exit condition. 175f2b7879SDaniil Suchkovdefine i64 @drop_a_wc_and_leave_early(i64 %length, i64 %n, i1 %cond_0, i1 %cond_1) { 185f2b7879SDaniil Suchkov; Make sure the pass has only replaced `%wc2` with `true` in the definition of `%wb_cond`. 195f2b7879SDaniil Suchkov; CHECK-LABEL: define i64 @drop_a_wc_and_leave_early(i64 %length, i64 %n, i1 %cond_0, i1 %cond_1) { 205f2b7879SDaniil Suchkov; CHECK-NEXT: entry: 215f2b7879SDaniil Suchkov; CHECK-NEXT: %wc1 = call i1 @llvm.experimental.widenable.condition() 225f2b7879SDaniil Suchkov; CHECK-NEXT: %wc2 = call i1 @llvm.experimental.widenable.condition() 235f2b7879SDaniil Suchkov; CHECK-NEXT: %exiplicit_guard_cond = and i1 %cond_0, %wc1 245f2b7879SDaniil Suchkov; CHECK-NEXT: br i1 %exiplicit_guard_cond, label %loop.preheader, label %deopt, !prof !0 255f2b7879SDaniil Suchkov; CHECK: deopt: 265f2b7879SDaniil Suchkov; CHECK-NEXT: %deoptret = call i64 (...) @llvm.experimental.deoptimize.i64() [ "deopt"() ] 275f2b7879SDaniil Suchkov; CHECK-NEXT: ret i64 %deoptret 285f2b7879SDaniil Suchkov; CHECK: loop.preheader: 295f2b7879SDaniil Suchkov; CHECK-NEXT: br label %loop 305f2b7879SDaniil Suchkov; CHECK: loop: 315f2b7879SDaniil Suchkov; CHECK-NEXT: %i = phi i64 [ %i.next, %guarded2 ], [ 0, %loop.preheader ] 325f2b7879SDaniil Suchkov; CHECK-NEXT: br i1 %cond_0, label %guarded, label %deopt2, !prof !0 335f2b7879SDaniil Suchkov; CHECK: deopt2: 345f2b7879SDaniil Suchkov; CHECK-NEXT: %deoptret2 = call i64 (...) @llvm.experimental.deoptimize.i64() [ "deopt"() ] 355f2b7879SDaniil Suchkov; CHECK-NEXT: ret i64 %deoptret2 365f2b7879SDaniil Suchkov; CHECK: guarded: 375f2b7879SDaniil Suchkov; CHECK-NEXT: %wb_cond = and i1 %cond_1, true 385f2b7879SDaniil Suchkov; CHECK-NEXT: br i1 %wb_cond, label %guarded2, label %deopt3, !prof !0 395f2b7879SDaniil Suchkov; CHECK: deopt3: 405f2b7879SDaniil Suchkov; CHECK-NEXT: %deoptret3 = call i64 (...) @llvm.experimental.deoptimize.i64() [ "deopt"() ] 415f2b7879SDaniil Suchkov; CHECK-NEXT: ret i64 %deoptret3 425f2b7879SDaniil Suchkov; CHECK: guarded2: 435f2b7879SDaniil Suchkov; CHECK-NEXT: %i.next = add nuw i64 %i, 1 445f2b7879SDaniil Suchkov; CHECK-NEXT: %continue = icmp ult i64 %i.next, %n 455f2b7879SDaniil Suchkov; CHECK-NEXT: br i1 %continue, label %loop, label %exit 465f2b7879SDaniil Suchkov; CHECK: exit: 475f2b7879SDaniil Suchkov; CHECK-NEXT: ret i64 0 485f2b7879SDaniil Suchkov; CHECK-NEXT: } 495f2b7879SDaniil Suchkov 505f2b7879SDaniil Suchkoventry: 515f2b7879SDaniil Suchkov %wc1 = call i1 @llvm.experimental.widenable.condition() 525f2b7879SDaniil Suchkov %wc2 = call i1 @llvm.experimental.widenable.condition() 535f2b7879SDaniil Suchkov %exiplicit_guard_cond = and i1 %cond_0, %wc1 545f2b7879SDaniil Suchkov br i1 %exiplicit_guard_cond, label %loop.preheader, label %deopt, !prof !0 555f2b7879SDaniil Suchkov 565f2b7879SDaniil Suchkovdeopt: 575f2b7879SDaniil Suchkov %deoptret = call i64 (...) @llvm.experimental.deoptimize.i64() [ "deopt"() ] 585f2b7879SDaniil Suchkov ret i64 %deoptret 595f2b7879SDaniil Suchkov 605f2b7879SDaniil Suchkovloop.preheader: 615f2b7879SDaniil Suchkov br label %loop 625f2b7879SDaniil Suchkov 635f2b7879SDaniil Suchkovloop: 645f2b7879SDaniil Suchkov %i = phi i64 [ %i.next, %guarded2 ], [ 0, %loop.preheader ] 655f2b7879SDaniil Suchkov br i1 %cond_0, label %guarded, label %deopt2, !prof !0 665f2b7879SDaniil Suchkov 675f2b7879SDaniil Suchkovdeopt2: 685f2b7879SDaniil Suchkov %deoptret2 = call i64 (...) @llvm.experimental.deoptimize.i64() [ "deopt"() ] 695f2b7879SDaniil Suchkov ret i64 %deoptret2 705f2b7879SDaniil Suchkov 715f2b7879SDaniil Suchkovguarded: 725f2b7879SDaniil Suchkov %wb_cond = and i1 %cond_1, %wc2 735f2b7879SDaniil Suchkov br i1 %wb_cond, label %guarded2, label %deopt3, !prof !0 745f2b7879SDaniil Suchkov 755f2b7879SDaniil Suchkovdeopt3: 765f2b7879SDaniil Suchkov %deoptret3 = call i64 (...) @llvm.experimental.deoptimize.i64() [ "deopt"() ] 775f2b7879SDaniil Suchkov ret i64 %deoptret3 785f2b7879SDaniil Suchkov 795f2b7879SDaniil Suchkovguarded2: 805f2b7879SDaniil Suchkov %i.next = add nuw i64 %i, 1 815f2b7879SDaniil Suchkov %continue = icmp ult i64 %i.next, %n 825f2b7879SDaniil Suchkov br i1 %continue, label %loop, label %exit 835f2b7879SDaniil Suchkov 845f2b7879SDaniil Suchkovexit: 855f2b7879SDaniil Suchkov ret i64 0 865f2b7879SDaniil Suchkov} 875f2b7879SDaniil Suchkov 885f2b7879SDaniil Suchkov; This test makes the pass drop its attempts to optimize the exit condition in 895f2b7879SDaniil Suchkov; `%loop` BB by using trivial `false` as an exit condition. 905f2b7879SDaniil Suchkovdefine i64 @drop_a_wc_and_leave(i64 %n, i1 %cond_0, i1 %cond_1) { 915f2b7879SDaniil Suchkov; Make sure the pass has only replaced `%wc2` with `true` in the definition of `%wb_cond`. 925f2b7879SDaniil Suchkov; CHECK-LABEL: define i64 @drop_a_wc_and_leave(i64 %n, i1 %cond_0, i1 %cond_1) { 935f2b7879SDaniil Suchkov; CHECK-NEXT: entry: 945f2b7879SDaniil Suchkov; CHECK-NEXT: %wc1 = call i1 @llvm.experimental.widenable.condition() 955f2b7879SDaniil Suchkov; CHECK-NEXT: %wc2 = call i1 @llvm.experimental.widenable.condition() 965f2b7879SDaniil Suchkov; CHECK-NEXT: %exiplicit_guard_cond = and i1 %cond_0, %wc1 975f2b7879SDaniil Suchkov; CHECK-NEXT: br i1 %exiplicit_guard_cond, label %loop.preheader, label %deopt, !prof !0 985f2b7879SDaniil Suchkov; CHECK: deopt: 995f2b7879SDaniil Suchkov; CHECK-NEXT: %deoptret = call i64 (...) @llvm.experimental.deoptimize.i64() [ "deopt"() ] 1005f2b7879SDaniil Suchkov; CHECK-NEXT: ret i64 %deoptret 1015f2b7879SDaniil Suchkov; CHECK: loop.preheader: 1025f2b7879SDaniil Suchkov; CHECK-NEXT: br label %loop 1035f2b7879SDaniil Suchkov; CHECK: loop: 1045f2b7879SDaniil Suchkov; CHECK-NEXT: %i = phi i64 [ %i.next, %guarded2 ], [ 0, %loop.preheader ] 1055f2b7879SDaniil Suchkov; CHECK-NEXT: br i1 false, label %guarded, label %deopt2, !prof !0 1065f2b7879SDaniil Suchkov; CHECK: deopt2: 1075f2b7879SDaniil Suchkov; CHECK-NEXT: %deoptret2 = call i64 (...) @llvm.experimental.deoptimize.i64() [ "deopt"() ] 1085f2b7879SDaniil Suchkov; CHECK-NEXT: ret i64 %deoptret2 1095f2b7879SDaniil Suchkov; CHECK: guarded: 1105f2b7879SDaniil Suchkov; CHECK-NEXT: %wb_cond = and i1 %cond_1, true 1115f2b7879SDaniil Suchkov; CHECK-NEXT: br i1 %wb_cond, label %guarded2, label %deopt3, !prof !0 1125f2b7879SDaniil Suchkov; CHECK: deopt3: 1135f2b7879SDaniil Suchkov; CHECK-NEXT: %deoptret3 = call i64 (...) @llvm.experimental.deoptimize.i64() [ "deopt"() ] 1145f2b7879SDaniil Suchkov; CHECK-NEXT: ret i64 %deoptret3 1155f2b7879SDaniil Suchkov; CHECK: guarded2: 1165f2b7879SDaniil Suchkov; CHECK-NEXT: %i.next = add nuw i64 %i, 1 1175f2b7879SDaniil Suchkov; CHECK-NEXT: %continue = icmp ult i64 %i.next, %n 1185f2b7879SDaniil Suchkov; CHECK-NEXT: br i1 %continue, label %loop, label %exit 1195f2b7879SDaniil Suchkov; CHECK: exit: 1205f2b7879SDaniil Suchkov; CHECK-NEXT: ret i64 0 1215f2b7879SDaniil Suchkov; CHECK-NEXT: } 1225f2b7879SDaniil Suchkov 1235f2b7879SDaniil Suchkoventry: 1245f2b7879SDaniil Suchkov %wc1 = call i1 @llvm.experimental.widenable.condition() 1255f2b7879SDaniil Suchkov %wc2 = call i1 @llvm.experimental.widenable.condition() 1265f2b7879SDaniil Suchkov %exiplicit_guard_cond = and i1 %cond_0, %wc1 1275f2b7879SDaniil Suchkov br i1 %exiplicit_guard_cond, label %loop.preheader, label %deopt, !prof !0 1285f2b7879SDaniil Suchkov 1295f2b7879SDaniil Suchkovdeopt: 1305f2b7879SDaniil Suchkov %deoptret = call i64 (...) @llvm.experimental.deoptimize.i64() [ "deopt"() ] 1315f2b7879SDaniil Suchkov ret i64 %deoptret 1325f2b7879SDaniil Suchkov 1335f2b7879SDaniil Suchkovloop.preheader: 1345f2b7879SDaniil Suchkov br label %loop 1355f2b7879SDaniil Suchkov 1365f2b7879SDaniil Suchkovloop: 1375f2b7879SDaniil Suchkov %i = phi i64 [ %i.next, %guarded2 ], [ 0, %loop.preheader ] 1385f2b7879SDaniil Suchkov br i1 false, label %guarded, label %deopt2, !prof !0 1395f2b7879SDaniil Suchkov 1405f2b7879SDaniil Suchkovdeopt2: 1415f2b7879SDaniil Suchkov %deoptret2 = call i64 (...) @llvm.experimental.deoptimize.i64() [ "deopt"() ] 1425f2b7879SDaniil Suchkov ret i64 %deoptret2 1435f2b7879SDaniil Suchkov 1445f2b7879SDaniil Suchkovguarded: 1455f2b7879SDaniil Suchkov %wb_cond = and i1 %cond_1, %wc2 1465f2b7879SDaniil Suchkov br i1 %wb_cond, label %guarded2, label %deopt3, !prof !0 1475f2b7879SDaniil Suchkov 1485f2b7879SDaniil Suchkovdeopt3: 1495f2b7879SDaniil Suchkov %deoptret3 = call i64 (...) @llvm.experimental.deoptimize.i64() [ "deopt"() ] 1505f2b7879SDaniil Suchkov ret i64 %deoptret3 1515f2b7879SDaniil Suchkov 1525f2b7879SDaniil Suchkovguarded2: 1535f2b7879SDaniil Suchkov %i.next = add nuw i64 %i, 1 1545f2b7879SDaniil Suchkov %continue = icmp ult i64 %i.next, %n 1555f2b7879SDaniil Suchkov br i1 %continue, label %loop, label %exit 1565f2b7879SDaniil Suchkov 1575f2b7879SDaniil Suchkovexit: 1585f2b7879SDaniil Suchkov ret i64 0 1595f2b7879SDaniil Suchkov} 1605f2b7879SDaniil Suchkov 1615f2b7879SDaniil Suchkov 1625f2b7879SDaniil Suchkovdeclare i1 @llvm.experimental.widenable.condition() 1635f2b7879SDaniil Suchkovdeclare i64 @llvm.experimental.deoptimize.i64(...) 1645f2b7879SDaniil Suchkov 1655f2b7879SDaniil Suchkov!0 = !{!"branch_weights", i64 1048576, i64 1} 166