109467b48Spatrick //===- LoopPassManager.cpp - Loop pass management -------------------------===//
209467b48Spatrick //
309467b48Spatrick // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
409467b48Spatrick // See https://llvm.org/LICENSE.txt for license information.
509467b48Spatrick // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
609467b48Spatrick //
709467b48Spatrick //===----------------------------------------------------------------------===//
809467b48Spatrick
909467b48Spatrick #include "llvm/Transforms/Scalar/LoopPassManager.h"
1073471bf0Spatrick #include "llvm/Analysis/AssumptionCache.h"
1173471bf0Spatrick #include "llvm/Analysis/BlockFrequencyInfo.h"
12*d415bd75Srobert #include "llvm/Analysis/BranchProbabilityInfo.h"
1373471bf0Spatrick #include "llvm/Analysis/MemorySSA.h"
14*d415bd75Srobert #include "llvm/Analysis/ScalarEvolution.h"
1573471bf0Spatrick #include "llvm/Analysis/TargetLibraryInfo.h"
16*d415bd75Srobert #include "llvm/Analysis/TargetTransformInfo.h"
1773471bf0Spatrick #include "llvm/Support/TimeProfiler.h"
1809467b48Spatrick
1909467b48Spatrick using namespace llvm;
2009467b48Spatrick
2109467b48Spatrick namespace llvm {
2209467b48Spatrick
2309467b48Spatrick /// Explicitly specialize the pass manager's run method to handle loop nest
2409467b48Spatrick /// structure updates.
2509467b48Spatrick PreservedAnalyses
2609467b48Spatrick PassManager<Loop, LoopAnalysisManager, LoopStandardAnalysisResults &,
run(Loop & L,LoopAnalysisManager & AM,LoopStandardAnalysisResults & AR,LPMUpdater & U)2709467b48Spatrick LPMUpdater &>::run(Loop &L, LoopAnalysisManager &AM,
2809467b48Spatrick LoopStandardAnalysisResults &AR, LPMUpdater &U) {
2973471bf0Spatrick // Runs loop-nest passes only when the current loop is a top-level one.
3073471bf0Spatrick PreservedAnalyses PA = (L.isOutermost() && !LoopNestPasses.empty())
3173471bf0Spatrick ? runWithLoopNestPasses(L, AM, AR, U)
3273471bf0Spatrick : runWithoutLoopNestPasses(L, AM, AR, U);
3309467b48Spatrick
3409467b48Spatrick // Invalidation for the current loop should be handled above, and other loop
3509467b48Spatrick // analysis results shouldn't be impacted by runs over this loop. Therefore,
3609467b48Spatrick // the remaining analysis results in the AnalysisManager are preserved. We
3709467b48Spatrick // mark this with a set so that we don't need to inspect each one
3809467b48Spatrick // individually.
3909467b48Spatrick // FIXME: This isn't correct! This loop and all nested loops' analyses should
4009467b48Spatrick // be preserved, but unrolling should invalidate the parent loop's analyses.
4109467b48Spatrick PA.preserveSet<AllAnalysesOn<Loop>>();
4209467b48Spatrick
4309467b48Spatrick return PA;
4409467b48Spatrick }
4573471bf0Spatrick
46*d415bd75Srobert void PassManager<Loop, LoopAnalysisManager, LoopStandardAnalysisResults &,
printPipeline(raw_ostream & OS,function_ref<StringRef (StringRef)> MapClassName2PassName)47*d415bd75Srobert LPMUpdater &>::printPipeline(raw_ostream &OS,
48*d415bd75Srobert function_ref<StringRef(StringRef)>
49*d415bd75Srobert MapClassName2PassName) {
50*d415bd75Srobert assert(LoopPasses.size() + LoopNestPasses.size() == IsLoopNestPass.size());
51*d415bd75Srobert
52*d415bd75Srobert unsigned IdxLP = 0, IdxLNP = 0;
53*d415bd75Srobert for (unsigned Idx = 0, Size = IsLoopNestPass.size(); Idx != Size; ++Idx) {
54*d415bd75Srobert if (IsLoopNestPass[Idx]) {
55*d415bd75Srobert auto *P = LoopNestPasses[IdxLNP++].get();
56*d415bd75Srobert P->printPipeline(OS, MapClassName2PassName);
57*d415bd75Srobert } else {
58*d415bd75Srobert auto *P = LoopPasses[IdxLP++].get();
59*d415bd75Srobert P->printPipeline(OS, MapClassName2PassName);
60*d415bd75Srobert }
61*d415bd75Srobert if (Idx + 1 < Size)
62*d415bd75Srobert OS << ",";
63*d415bd75Srobert }
64*d415bd75Srobert }
65*d415bd75Srobert
6673471bf0Spatrick // Run both loop passes and loop-nest passes on top-level loop \p L.
6773471bf0Spatrick PreservedAnalyses
runWithLoopNestPasses(Loop & L,LoopAnalysisManager & AM,LoopStandardAnalysisResults & AR,LPMUpdater & U)6873471bf0Spatrick LoopPassManager::runWithLoopNestPasses(Loop &L, LoopAnalysisManager &AM,
6973471bf0Spatrick LoopStandardAnalysisResults &AR,
7073471bf0Spatrick LPMUpdater &U) {
7173471bf0Spatrick assert(L.isOutermost() &&
7273471bf0Spatrick "Loop-nest passes should only run on top-level loops.");
7373471bf0Spatrick PreservedAnalyses PA = PreservedAnalyses::all();
7473471bf0Spatrick
7573471bf0Spatrick // Request PassInstrumentation from analysis manager, will use it to run
7673471bf0Spatrick // instrumenting callbacks for the passes later.
7773471bf0Spatrick PassInstrumentation PI = AM.getResult<PassInstrumentationAnalysis>(L, AR);
7873471bf0Spatrick
7973471bf0Spatrick unsigned LoopPassIndex = 0, LoopNestPassIndex = 0;
8073471bf0Spatrick
8173471bf0Spatrick // `LoopNestPtr` points to the `LoopNest` object for the current top-level
8273471bf0Spatrick // loop and `IsLoopNestPtrValid` indicates whether the pointer is still valid.
8373471bf0Spatrick // The `LoopNest` object will have to be re-constructed if the pointer is
8473471bf0Spatrick // invalid when encountering a loop-nest pass.
8573471bf0Spatrick std::unique_ptr<LoopNest> LoopNestPtr;
8673471bf0Spatrick bool IsLoopNestPtrValid = false;
87*d415bd75Srobert Loop *OuterMostLoop = &L;
8873471bf0Spatrick
8973471bf0Spatrick for (size_t I = 0, E = IsLoopNestPass.size(); I != E; ++I) {
90*d415bd75Srobert std::optional<PreservedAnalyses> PassPA;
9173471bf0Spatrick if (!IsLoopNestPass[I]) {
9273471bf0Spatrick // The `I`-th pass is a loop pass.
9373471bf0Spatrick auto &Pass = LoopPasses[LoopPassIndex++];
9473471bf0Spatrick PassPA = runSinglePass(L, Pass, AM, AR, U, PI);
9573471bf0Spatrick } else {
9673471bf0Spatrick // The `I`-th pass is a loop-nest pass.
9773471bf0Spatrick auto &Pass = LoopNestPasses[LoopNestPassIndex++];
9873471bf0Spatrick
9973471bf0Spatrick // If the loop-nest object calculated before is no longer valid,
10073471bf0Spatrick // re-calculate it here before running the loop-nest pass.
101*d415bd75Srobert //
102*d415bd75Srobert // FIXME: PreservedAnalysis should not be abused to tell if the
103*d415bd75Srobert // status of loopnest has been changed. We should use and only
104*d415bd75Srobert // use LPMUpdater for this purpose.
105*d415bd75Srobert if (!IsLoopNestPtrValid || U.isLoopNestChanged()) {
106*d415bd75Srobert while (auto *ParentLoop = OuterMostLoop->getParentLoop())
107*d415bd75Srobert OuterMostLoop = ParentLoop;
108*d415bd75Srobert LoopNestPtr = LoopNest::getLoopNest(*OuterMostLoop, AR.SE);
10973471bf0Spatrick IsLoopNestPtrValid = true;
110*d415bd75Srobert U.markLoopNestChanged(false);
11173471bf0Spatrick }
112*d415bd75Srobert
11373471bf0Spatrick PassPA = runSinglePass(*LoopNestPtr, Pass, AM, AR, U, PI);
11473471bf0Spatrick }
11573471bf0Spatrick
11673471bf0Spatrick // `PassPA` is `None` means that the before-pass callbacks in
11773471bf0Spatrick // `PassInstrumentation` return false. The pass does not run in this case,
11873471bf0Spatrick // so we can skip the following procedure.
11973471bf0Spatrick if (!PassPA)
12073471bf0Spatrick continue;
12173471bf0Spatrick
12273471bf0Spatrick // If the loop was deleted, abort the run and return to the outer walk.
12373471bf0Spatrick if (U.skipCurrentLoop()) {
12473471bf0Spatrick PA.intersect(std::move(*PassPA));
12573471bf0Spatrick break;
12673471bf0Spatrick }
12773471bf0Spatrick
12873471bf0Spatrick // Update the analysis manager as each pass runs and potentially
12973471bf0Spatrick // invalidates analyses.
130*d415bd75Srobert AM.invalidate(IsLoopNestPass[I] ? *OuterMostLoop : L, *PassPA);
13173471bf0Spatrick
13273471bf0Spatrick // Finally, we intersect the final preserved analyses to compute the
13373471bf0Spatrick // aggregate preserved set for this pass manager.
13473471bf0Spatrick PA.intersect(std::move(*PassPA));
13573471bf0Spatrick
13673471bf0Spatrick // Check if the current pass preserved the loop-nest object or not.
13773471bf0Spatrick IsLoopNestPtrValid &= PassPA->getChecker<LoopNestAnalysis>().preserved();
13873471bf0Spatrick
13973471bf0Spatrick // After running the loop pass, the parent loop might change and we need to
14073471bf0Spatrick // notify the updater, otherwise U.ParentL might gets outdated and triggers
14173471bf0Spatrick // assertion failures in addSiblingLoops and addChildLoops.
142*d415bd75Srobert U.setParentLoop((IsLoopNestPass[I] ? *OuterMostLoop : L).getParentLoop());
14373471bf0Spatrick }
14473471bf0Spatrick return PA;
14573471bf0Spatrick }
14673471bf0Spatrick
14773471bf0Spatrick // Run all loop passes on loop \p L. Loop-nest passes don't run either because
14873471bf0Spatrick // \p L is not a top-level one or simply because there are no loop-nest passes
14973471bf0Spatrick // in the pass manager at all.
15073471bf0Spatrick PreservedAnalyses
runWithoutLoopNestPasses(Loop & L,LoopAnalysisManager & AM,LoopStandardAnalysisResults & AR,LPMUpdater & U)15173471bf0Spatrick LoopPassManager::runWithoutLoopNestPasses(Loop &L, LoopAnalysisManager &AM,
15273471bf0Spatrick LoopStandardAnalysisResults &AR,
15373471bf0Spatrick LPMUpdater &U) {
15473471bf0Spatrick PreservedAnalyses PA = PreservedAnalyses::all();
15573471bf0Spatrick
15673471bf0Spatrick // Request PassInstrumentation from analysis manager, will use it to run
15773471bf0Spatrick // instrumenting callbacks for the passes later.
15873471bf0Spatrick PassInstrumentation PI = AM.getResult<PassInstrumentationAnalysis>(L, AR);
15973471bf0Spatrick for (auto &Pass : LoopPasses) {
160*d415bd75Srobert std::optional<PreservedAnalyses> PassPA =
161*d415bd75Srobert runSinglePass(L, Pass, AM, AR, U, PI);
16273471bf0Spatrick
16373471bf0Spatrick // `PassPA` is `None` means that the before-pass callbacks in
16473471bf0Spatrick // `PassInstrumentation` return false. The pass does not run in this case,
16573471bf0Spatrick // so we can skip the following procedure.
16673471bf0Spatrick if (!PassPA)
16773471bf0Spatrick continue;
16873471bf0Spatrick
16973471bf0Spatrick // If the loop was deleted, abort the run and return to the outer walk.
17073471bf0Spatrick if (U.skipCurrentLoop()) {
17173471bf0Spatrick PA.intersect(std::move(*PassPA));
17273471bf0Spatrick break;
17373471bf0Spatrick }
17473471bf0Spatrick
17573471bf0Spatrick // Update the analysis manager as each pass runs and potentially
17673471bf0Spatrick // invalidates analyses.
17773471bf0Spatrick AM.invalidate(L, *PassPA);
17873471bf0Spatrick
17973471bf0Spatrick // Finally, we intersect the final preserved analyses to compute the
18073471bf0Spatrick // aggregate preserved set for this pass manager.
18173471bf0Spatrick PA.intersect(std::move(*PassPA));
18273471bf0Spatrick
18373471bf0Spatrick // After running the loop pass, the parent loop might change and we need to
18473471bf0Spatrick // notify the updater, otherwise U.ParentL might gets outdated and triggers
18573471bf0Spatrick // assertion failures in addSiblingLoops and addChildLoops.
18673471bf0Spatrick U.setParentLoop(L.getParentLoop());
18773471bf0Spatrick }
18873471bf0Spatrick return PA;
18973471bf0Spatrick }
19073471bf0Spatrick } // namespace llvm
19173471bf0Spatrick
printPipeline(raw_ostream & OS,function_ref<StringRef (StringRef)> MapClassName2PassName)192*d415bd75Srobert void FunctionToLoopPassAdaptor::printPipeline(
193*d415bd75Srobert raw_ostream &OS, function_ref<StringRef(StringRef)> MapClassName2PassName) {
194*d415bd75Srobert OS << (UseMemorySSA ? "loop-mssa(" : "loop(");
195*d415bd75Srobert Pass->printPipeline(OS, MapClassName2PassName);
196*d415bd75Srobert OS << ")";
197*d415bd75Srobert }
run(Function & F,FunctionAnalysisManager & AM)19873471bf0Spatrick PreservedAnalyses FunctionToLoopPassAdaptor::run(Function &F,
19973471bf0Spatrick FunctionAnalysisManager &AM) {
20073471bf0Spatrick // Before we even compute any loop analyses, first run a miniature function
20173471bf0Spatrick // pass pipeline to put loops into their canonical form. Note that we can
20273471bf0Spatrick // directly build up function analyses after this as the function pass
20373471bf0Spatrick // manager handles all the invalidation at that layer.
20473471bf0Spatrick PassInstrumentation PI = AM.getResult<PassInstrumentationAnalysis>(F);
20573471bf0Spatrick
20673471bf0Spatrick PreservedAnalyses PA = PreservedAnalyses::all();
20773471bf0Spatrick // Check the PassInstrumentation's BeforePass callbacks before running the
20873471bf0Spatrick // canonicalization pipeline.
20973471bf0Spatrick if (PI.runBeforePass<Function>(LoopCanonicalizationFPM, F)) {
21073471bf0Spatrick PA = LoopCanonicalizationFPM.run(F, AM);
21173471bf0Spatrick PI.runAfterPass<Function>(LoopCanonicalizationFPM, F, PA);
21273471bf0Spatrick }
21373471bf0Spatrick
21473471bf0Spatrick // Get the loop structure for this function
21573471bf0Spatrick LoopInfo &LI = AM.getResult<LoopAnalysis>(F);
21673471bf0Spatrick
21773471bf0Spatrick // If there are no loops, there is nothing to do here.
21873471bf0Spatrick if (LI.empty())
21973471bf0Spatrick return PA;
22073471bf0Spatrick
22173471bf0Spatrick // Get the analysis results needed by loop passes.
22273471bf0Spatrick MemorySSA *MSSA =
22373471bf0Spatrick UseMemorySSA ? (&AM.getResult<MemorySSAAnalysis>(F).getMSSA()) : nullptr;
22473471bf0Spatrick BlockFrequencyInfo *BFI = UseBlockFrequencyInfo && F.hasProfileData()
22573471bf0Spatrick ? (&AM.getResult<BlockFrequencyAnalysis>(F))
22673471bf0Spatrick : nullptr;
227*d415bd75Srobert BranchProbabilityInfo *BPI =
228*d415bd75Srobert UseBranchProbabilityInfo && F.hasProfileData()
229*d415bd75Srobert ? (&AM.getResult<BranchProbabilityAnalysis>(F))
230*d415bd75Srobert : nullptr;
23173471bf0Spatrick LoopStandardAnalysisResults LAR = {AM.getResult<AAManager>(F),
23273471bf0Spatrick AM.getResult<AssumptionAnalysis>(F),
23373471bf0Spatrick AM.getResult<DominatorTreeAnalysis>(F),
23473471bf0Spatrick AM.getResult<LoopAnalysis>(F),
23573471bf0Spatrick AM.getResult<ScalarEvolutionAnalysis>(F),
23673471bf0Spatrick AM.getResult<TargetLibraryAnalysis>(F),
23773471bf0Spatrick AM.getResult<TargetIRAnalysis>(F),
23873471bf0Spatrick BFI,
239*d415bd75Srobert BPI,
24073471bf0Spatrick MSSA};
24173471bf0Spatrick
24273471bf0Spatrick // Setup the loop analysis manager from its proxy. It is important that
24373471bf0Spatrick // this is only done when there are loops to process and we have built the
24473471bf0Spatrick // LoopStandardAnalysisResults object. The loop analyses cached in this
24573471bf0Spatrick // manager have access to those analysis results and so it must invalidate
24673471bf0Spatrick // itself when they go away.
24773471bf0Spatrick auto &LAMFP = AM.getResult<LoopAnalysisManagerFunctionProxy>(F);
24873471bf0Spatrick if (UseMemorySSA)
24973471bf0Spatrick LAMFP.markMSSAUsed();
25073471bf0Spatrick LoopAnalysisManager &LAM = LAMFP.getManager();
25173471bf0Spatrick
25273471bf0Spatrick // A postorder worklist of loops to process.
25373471bf0Spatrick SmallPriorityWorklist<Loop *, 4> Worklist;
25473471bf0Spatrick
25573471bf0Spatrick // Register the worklist and loop analysis manager so that loop passes can
25673471bf0Spatrick // update them when they mutate the loop nest structure.
25773471bf0Spatrick LPMUpdater Updater(Worklist, LAM, LoopNestMode);
25873471bf0Spatrick
25973471bf0Spatrick // Add the loop nests in the reverse order of LoopInfo. See method
26073471bf0Spatrick // declaration.
26173471bf0Spatrick if (!LoopNestMode) {
26273471bf0Spatrick appendLoopsToWorklist(LI, Worklist);
26373471bf0Spatrick } else {
26473471bf0Spatrick for (Loop *L : LI)
26573471bf0Spatrick Worklist.insert(L);
26673471bf0Spatrick }
26773471bf0Spatrick
26873471bf0Spatrick #ifndef NDEBUG
26973471bf0Spatrick PI.pushBeforeNonSkippedPassCallback([&LAR, &LI](StringRef PassID, Any IR) {
27073471bf0Spatrick if (isSpecialPass(PassID, {"PassManager"}))
27173471bf0Spatrick return;
272*d415bd75Srobert assert(any_cast<const Loop *>(&IR) || any_cast<const LoopNest *>(&IR));
273*d415bd75Srobert const Loop **LPtr = any_cast<const Loop *>(&IR);
274*d415bd75Srobert const Loop *L = LPtr ? *LPtr : nullptr;
275*d415bd75Srobert if (!L)
276*d415bd75Srobert L = &any_cast<const LoopNest *>(IR)->getOutermostLoop();
27773471bf0Spatrick assert(L && "Loop should be valid for printing");
27873471bf0Spatrick
27973471bf0Spatrick // Verify the loop structure and LCSSA form before visiting the loop.
28073471bf0Spatrick L->verifyLoop();
28173471bf0Spatrick assert(L->isRecursivelyLCSSAForm(LAR.DT, LI) &&
28273471bf0Spatrick "Loops must remain in LCSSA form!");
28373471bf0Spatrick });
28473471bf0Spatrick #endif
28573471bf0Spatrick
28673471bf0Spatrick do {
28773471bf0Spatrick Loop *L = Worklist.pop_back_val();
28873471bf0Spatrick assert(!(LoopNestMode && L->getParentLoop()) &&
28973471bf0Spatrick "L should be a top-level loop in loop-nest mode.");
29073471bf0Spatrick
29173471bf0Spatrick // Reset the update structure for this loop.
29273471bf0Spatrick Updater.CurrentL = L;
29373471bf0Spatrick Updater.SkipCurrentLoop = false;
29473471bf0Spatrick
29573471bf0Spatrick #ifndef NDEBUG
29673471bf0Spatrick // Save a parent loop pointer for asserts.
29773471bf0Spatrick Updater.ParentL = L->getParentLoop();
29873471bf0Spatrick #endif
29973471bf0Spatrick // Check the PassInstrumentation's BeforePass callbacks before running the
30073471bf0Spatrick // pass, skip its execution completely if asked to (callback returns
30173471bf0Spatrick // false).
30273471bf0Spatrick if (!PI.runBeforePass<Loop>(*Pass, *L))
30373471bf0Spatrick continue;
30473471bf0Spatrick
305*d415bd75Srobert PreservedAnalyses PassPA = Pass->run(*L, LAM, LAR, Updater);
30673471bf0Spatrick
30773471bf0Spatrick // Do not pass deleted Loop into the instrumentation.
30873471bf0Spatrick if (Updater.skipCurrentLoop())
30973471bf0Spatrick PI.runAfterPassInvalidated<Loop>(*Pass, PassPA);
31073471bf0Spatrick else
31173471bf0Spatrick PI.runAfterPass<Loop>(*Pass, *L, PassPA);
31273471bf0Spatrick
313*d415bd75Srobert if (LAR.MSSA && !PassPA.getChecker<MemorySSAAnalysis>().preserved())
314*d415bd75Srobert report_fatal_error("Loop pass manager using MemorySSA contains a pass "
315*d415bd75Srobert "that does not preserve MemorySSA");
316*d415bd75Srobert
31773471bf0Spatrick #ifndef NDEBUG
31873471bf0Spatrick // LoopAnalysisResults should always be valid.
31973471bf0Spatrick if (VerifyDomInfo)
32073471bf0Spatrick LAR.DT.verify();
32173471bf0Spatrick if (VerifyLoopInfo)
32273471bf0Spatrick LAR.LI.verify(LAR.DT);
323*d415bd75Srobert if (VerifySCEV)
324*d415bd75Srobert LAR.SE.verify();
32573471bf0Spatrick if (LAR.MSSA && VerifyMemorySSA)
32673471bf0Spatrick LAR.MSSA->verifyMemorySSA();
32773471bf0Spatrick #endif
32873471bf0Spatrick
32973471bf0Spatrick // If the loop hasn't been deleted, we need to handle invalidation here.
33073471bf0Spatrick if (!Updater.skipCurrentLoop())
33173471bf0Spatrick // We know that the loop pass couldn't have invalidated any other
33273471bf0Spatrick // loop's analyses (that's the contract of a loop pass), so directly
33373471bf0Spatrick // handle the loop analysis manager's invalidation here.
33473471bf0Spatrick LAM.invalidate(*L, PassPA);
33573471bf0Spatrick
33673471bf0Spatrick // Then intersect the preserved set so that invalidation of module
33773471bf0Spatrick // analyses will eventually occur when the module pass completes.
33873471bf0Spatrick PA.intersect(std::move(PassPA));
33973471bf0Spatrick } while (!Worklist.empty());
34073471bf0Spatrick
34173471bf0Spatrick #ifndef NDEBUG
34273471bf0Spatrick PI.popBeforeNonSkippedPassCallback();
34373471bf0Spatrick #endif
34473471bf0Spatrick
34573471bf0Spatrick // By definition we preserve the proxy. We also preserve all analyses on
34673471bf0Spatrick // Loops. This precludes *any* invalidation of loop analyses by the proxy,
34773471bf0Spatrick // but that's OK because we've taken care to invalidate analyses in the
34873471bf0Spatrick // loop analysis manager incrementally above.
34973471bf0Spatrick PA.preserveSet<AllAnalysesOn<Loop>>();
35073471bf0Spatrick PA.preserve<LoopAnalysisManagerFunctionProxy>();
35173471bf0Spatrick // We also preserve the set of standard analyses.
35273471bf0Spatrick PA.preserve<DominatorTreeAnalysis>();
35373471bf0Spatrick PA.preserve<LoopAnalysis>();
35473471bf0Spatrick PA.preserve<ScalarEvolutionAnalysis>();
35573471bf0Spatrick if (UseBlockFrequencyInfo && F.hasProfileData())
35673471bf0Spatrick PA.preserve<BlockFrequencyAnalysis>();
357*d415bd75Srobert if (UseBranchProbabilityInfo && F.hasProfileData())
358*d415bd75Srobert PA.preserve<BranchProbabilityAnalysis>();
35973471bf0Spatrick if (UseMemorySSA)
36073471bf0Spatrick PA.preserve<MemorySSAAnalysis>();
36173471bf0Spatrick return PA;
36209467b48Spatrick }
36309467b48Spatrick
PrintLoopPass()36409467b48Spatrick PrintLoopPass::PrintLoopPass() : OS(dbgs()) {}
PrintLoopPass(raw_ostream & OS,const std::string & Banner)36509467b48Spatrick PrintLoopPass::PrintLoopPass(raw_ostream &OS, const std::string &Banner)
36609467b48Spatrick : OS(OS), Banner(Banner) {}
36709467b48Spatrick
run(Loop & L,LoopAnalysisManager &,LoopStandardAnalysisResults &,LPMUpdater &)36809467b48Spatrick PreservedAnalyses PrintLoopPass::run(Loop &L, LoopAnalysisManager &,
36909467b48Spatrick LoopStandardAnalysisResults &,
37009467b48Spatrick LPMUpdater &) {
37109467b48Spatrick printLoop(L, OS, Banner);
37209467b48Spatrick return PreservedAnalyses::all();
37309467b48Spatrick }
374