//===- llvm/unittest/Analysis/LoopPassManagerTest.cpp - LPM tests ---------===//
//
// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
// See https://llvm.org/LICENSE.txt for license information.
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
//
//===----------------------------------------------------------------------===//

#include "llvm/Transforms/Scalar/LoopPassManager.h"
#include "llvm/Analysis/AliasAnalysis.h"
#include "llvm/Analysis/AssumptionCache.h"
#include "llvm/Analysis/ScalarEvolution.h"
#include "llvm/Analysis/TargetLibraryInfo.h"
#include "llvm/Analysis/TargetTransformInfo.h"
#include "llvm/AsmParser/Parser.h"
#include "llvm/IR/Dominators.h"
#include "llvm/IR/Function.h"
#include "llvm/IR/LLVMContext.h"
#include "llvm/IR/Module.h"
#include "llvm/IR/PassManager.h"
#include "llvm/Support/SourceMgr.h"

// Workaround for the gcc 6.1 bug PR80916.
#if defined(__GNUC__) && __GNUC__ > 5
#  pragma GCC diagnostic push
#  pragma GCC diagnostic ignored "-Wunused-function"
#endif

#include "gmock/gmock.h"
#include "gtest/gtest.h"

#if defined(__GNUC__) && __GNUC__ > 5
#  pragma GCC diagnostic pop
#endif

using namespace llvm;

namespace {

using testing::DoDefault;
using testing::Return;
using testing::Expectation;
using testing::Invoke;
using testing::InvokeWithoutArgs;
using testing::_;

template <typename DerivedT, typename IRUnitT,
          typename AnalysisManagerT = AnalysisManager<IRUnitT>,
          typename... ExtraArgTs>
class MockAnalysisHandleBase {
public:
  class Analysis : public AnalysisInfoMixin<Analysis> {
    friend AnalysisInfoMixin<Analysis>;
    friend MockAnalysisHandleBase;
    static AnalysisKey Key;

    DerivedT *Handle;

    Analysis(DerivedT &Handle) : Handle(&Handle) {
      static_assert(std::is_base_of<MockAnalysisHandleBase, DerivedT>::value,
                    "Must pass the derived type to this template!");
    }

  public:
    class Result {
      friend MockAnalysisHandleBase;

      DerivedT *Handle;

      Result(DerivedT &Handle) : Handle(&Handle) {}

    public:
      // Forward invalidation events to the mock handle.
      bool invalidate(IRUnitT &IR, const PreservedAnalyses &PA,
                      typename AnalysisManagerT::Invalidator &Inv) {
        return Handle->invalidate(IR, PA, Inv);
      }
    };

    Result run(IRUnitT &IR, AnalysisManagerT &AM, ExtraArgTs... ExtraArgs) {
      return Handle->run(IR, AM, ExtraArgs...);
    }
  };

  Analysis getAnalysis() { return Analysis(static_cast<DerivedT &>(*this)); }
  typename Analysis::Result getResult() {
    return typename Analysis::Result(static_cast<DerivedT &>(*this));
  }

protected:
  // FIXME: MSVC seems unable to handle a lambda argument to Invoke from within
  // the template, so we use a boring static function.
  static bool invalidateCallback(IRUnitT &IR, const PreservedAnalyses &PA,
                                 typename AnalysisManagerT::Invalidator &Inv) {
    auto PAC = PA.template getChecker<Analysis>();
    return !PAC.preserved() &&
           !PAC.template preservedSet<AllAnalysesOn<IRUnitT>>();
  }

  /// Derived classes should call this in their constructor to set up default
  /// mock actions. (We can't do this in our constructor because this has to
  /// run after the DerivedT is constructed.)
  void setDefaults() {
    ON_CALL(static_cast<DerivedT &>(*this),
            run(_, _, testing::Matcher<ExtraArgTs>(_)...))
        .WillByDefault(Return(this->getResult()));
    ON_CALL(static_cast<DerivedT &>(*this), invalidate(_, _, _))
        .WillByDefault(Invoke(&invalidateCallback));
  }
};

template <typename DerivedT, typename IRUnitT, typename AnalysisManagerT,
          typename... ExtraArgTs>
AnalysisKey MockAnalysisHandleBase<DerivedT, IRUnitT, AnalysisManagerT,
                                   ExtraArgTs...>::Analysis::Key;

/// Mock handle for loop analyses.
///
/// This is provided as a template accepting an (optional) integer. Because
/// analyses are identified and queried by type, this allows constructing
/// multiple handles with distinctly typed nested 'Analysis' types that can be
/// registered and queried. If you want to register multiple loop analysis
/// passes, you'll need to instantiate this type with different values for I.
/// For example:
///
///   MockLoopAnalysisHandleTemplate<0> h0;
///   MockLoopAnalysisHandleTemplate<1> h1;
///   typedef decltype(h0)::Analysis Analysis0;
///   typedef decltype(h1)::Analysis Analysis1;
template <size_t I = static_cast<size_t>(-1)>
struct MockLoopAnalysisHandleTemplate
    : MockAnalysisHandleBase<MockLoopAnalysisHandleTemplate<I>, Loop,
                             LoopAnalysisManager,
                             LoopStandardAnalysisResults &> {
  typedef typename MockLoopAnalysisHandleTemplate::Analysis Analysis;

  MOCK_METHOD3_T(run, typename Analysis::Result(Loop &, LoopAnalysisManager &,
                                                LoopStandardAnalysisResults &));

  MOCK_METHOD3_T(invalidate, bool(Loop &, const PreservedAnalyses &,
                                  LoopAnalysisManager::Invalidator &));

  MockLoopAnalysisHandleTemplate() { this->setDefaults(); }
};

typedef MockLoopAnalysisHandleTemplate<> MockLoopAnalysisHandle;

struct MockFunctionAnalysisHandle
    : MockAnalysisHandleBase<MockFunctionAnalysisHandle, Function> {
  MOCK_METHOD2(run, Analysis::Result(Function &, FunctionAnalysisManager &));

  MOCK_METHOD3(invalidate, bool(Function &, const PreservedAnalyses &,
                                FunctionAnalysisManager::Invalidator &));

  MockFunctionAnalysisHandle() { setDefaults(); }
};

template <typename DerivedT, typename IRUnitT,
          typename AnalysisManagerT = AnalysisManager<IRUnitT>,
          typename... ExtraArgTs>
class MockPassHandleBase {
public:
  class Pass : public PassInfoMixin<Pass> {
    friend MockPassHandleBase;

    DerivedT *Handle;

    Pass(DerivedT &Handle) : Handle(&Handle) {
      static_assert(std::is_base_of<MockPassHandleBase, DerivedT>::value,
                    "Must pass the derived type to this template!");
    }

  public:
    PreservedAnalyses run(IRUnitT &IR, AnalysisManagerT &AM,
                          ExtraArgTs... ExtraArgs) {
      return Handle->run(IR, AM, ExtraArgs...);
    }
  };

  Pass getPass() { return Pass(static_cast<DerivedT &>(*this)); }

protected:
  /// Derived classes should call this in their constructor to set up default
  /// mock actions. (We can't do this in our constructor because this has to
  /// run after the DerivedT is constructed.)
  void setDefaults() {
    ON_CALL(static_cast<DerivedT &>(*this),
            run(_, _, testing::Matcher<ExtraArgTs>(_)...))
        .WillByDefault(Return(PreservedAnalyses::all()));
  }
};

struct MockLoopPassHandle
    : MockPassHandleBase<MockLoopPassHandle, Loop, LoopAnalysisManager,
                         LoopStandardAnalysisResults &, LPMUpdater &> {
  MOCK_METHOD4(run,
               PreservedAnalyses(Loop &, LoopAnalysisManager &,
                                 LoopStandardAnalysisResults &, LPMUpdater &));
  MockLoopPassHandle() { setDefaults(); }
};

struct MockFunctionPassHandle
    : MockPassHandleBase<MockFunctionPassHandle, Function> {
  MOCK_METHOD2(run, PreservedAnalyses(Function &, FunctionAnalysisManager &));

  MockFunctionPassHandle() { setDefaults(); }
};

struct MockModulePassHandle : MockPassHandleBase<MockModulePassHandle, Module> {
  MOCK_METHOD2(run, PreservedAnalyses(Module &, ModuleAnalysisManager &));

  MockModulePassHandle() { setDefaults(); }
};

/// Define a custom matcher for objects which support a 'getName' method
/// returning a StringRef.
///
/// LLVM often has IR objects or analysis objects which expose a StringRef name
/// and in tests it is convenient to match these by name for readability. This
/// matcher supports any type exposing a getName() method of this form.
///
/// It should be used as:
///
///   HasName("my_function")
///
/// No namespace or other qualification is required.
MATCHER_P(HasName, Name, "") {
  // The matcher's name and argument are printed in the case of failure, but we
  // also want to print out the name of the argument. This uses an implicitly
  // avaiable std::ostream, so we have to construct a std::string.
  *result_listener << "has name '" << arg.getName().str() << "'";
  return Name == arg.getName();
}

std::unique_ptr<Module> parseIR(LLVMContext &C, const char *IR) {
  SMDiagnostic Err;
  return parseAssemblyString(IR, Err, C);
}

class LoopPassManagerTest : public ::testing::Test {
protected:
  LLVMContext Context;
  std::unique_ptr<Module> M;

  LoopAnalysisManager LAM;
  FunctionAnalysisManager FAM;
  ModuleAnalysisManager MAM;

  MockLoopAnalysisHandle MLAHandle;
  MockLoopPassHandle MLPHandle;
  MockFunctionPassHandle MFPHandle;
  MockModulePassHandle MMPHandle;

  static PreservedAnalyses
  getLoopAnalysisResult(Loop &L, LoopAnalysisManager &AM,
                        LoopStandardAnalysisResults &AR, LPMUpdater &) {
    (void)AM.getResult<MockLoopAnalysisHandle::Analysis>(L, AR);
    return PreservedAnalyses::all();
  };

public:
  LoopPassManagerTest()
      : M(parseIR(Context,
                  "define void @f(i1* %ptr) {\n"
                  "entry:\n"
                  "  br label %loop.0\n"
                  "loop.0:\n"
                  "  %cond.0 = load volatile i1, i1* %ptr\n"
                  "  br i1 %cond.0, label %loop.0.0.ph, label %end\n"
                  "loop.0.0.ph:\n"
                  "  br label %loop.0.0\n"
                  "loop.0.0:\n"
                  "  %cond.0.0 = load volatile i1, i1* %ptr\n"
                  "  br i1 %cond.0.0, label %loop.0.0, label %loop.0.1.ph\n"
                  "loop.0.1.ph:\n"
                  "  br label %loop.0.1\n"
                  "loop.0.1:\n"
                  "  %cond.0.1 = load volatile i1, i1* %ptr\n"
                  "  br i1 %cond.0.1, label %loop.0.1, label %loop.0.latch\n"
                  "loop.0.latch:\n"
                  "  br label %loop.0\n"
                  "end:\n"
                  "  ret void\n"
                  "}\n"
                  "\n"
                  "define void @g(i1* %ptr) {\n"
                  "entry:\n"
                  "  br label %loop.g.0\n"
                  "loop.g.0:\n"
                  "  %cond.0 = load volatile i1, i1* %ptr\n"
                  "  br i1 %cond.0, label %loop.g.0, label %end\n"
                  "end:\n"
                  "  ret void\n"
                  "}\n")),
        LAM(true), FAM(true), MAM(true) {
    // Register our mock analysis.
    LAM.registerPass([&] { return MLAHandle.getAnalysis(); });

    // We need DominatorTreeAnalysis for LoopAnalysis.
    FAM.registerPass([&] { return DominatorTreeAnalysis(); });
    FAM.registerPass([&] { return LoopAnalysis(); });
    // We also allow loop passes to assume a set of other analyses and so need
    // those.
    FAM.registerPass([&] { return AAManager(); });
    FAM.registerPass([&] { return AssumptionAnalysis(); });
    if (EnableMSSALoopDependency)
      FAM.registerPass([&] { return MemorySSAAnalysis(); });
    FAM.registerPass([&] { return ScalarEvolutionAnalysis(); });
    FAM.registerPass([&] { return TargetLibraryAnalysis(); });
    FAM.registerPass([&] { return TargetIRAnalysis(); });

    // Register required pass instrumentation analysis.
    LAM.registerPass([&] { return PassInstrumentationAnalysis(); });
    FAM.registerPass([&] { return PassInstrumentationAnalysis(); });
    MAM.registerPass([&] { return PassInstrumentationAnalysis(); });

    // Cross-register proxies.
    LAM.registerPass([&] { return FunctionAnalysisManagerLoopProxy(FAM); });
    FAM.registerPass([&] { return LoopAnalysisManagerFunctionProxy(LAM); });
    FAM.registerPass([&] { return ModuleAnalysisManagerFunctionProxy(MAM); });
    MAM.registerPass([&] { return FunctionAnalysisManagerModuleProxy(FAM); });
  }
};

TEST_F(LoopPassManagerTest, Basic) {
  ModulePassManager MPM(true);
  ::testing::InSequence MakeExpectationsSequenced;

  // First we just visit all the loops in all the functions and get their
  // analysis results. This will run the analysis a total of four times,
  // once for each loop.
  EXPECT_CALL(MLPHandle, run(HasName("loop.0.0"), _, _, _))
      .WillOnce(Invoke(getLoopAnalysisResult));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0.0"), _, _));
  EXPECT_CALL(MLPHandle, run(HasName("loop.0.1"), _, _, _))
      .WillOnce(Invoke(getLoopAnalysisResult));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0.1"), _, _));
  EXPECT_CALL(MLPHandle, run(HasName("loop.0"), _, _, _))
      .WillOnce(Invoke(getLoopAnalysisResult));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0"), _, _));
  EXPECT_CALL(MLPHandle, run(HasName("loop.g.0"), _, _, _))
      .WillOnce(Invoke(getLoopAnalysisResult));
  EXPECT_CALL(MLAHandle, run(HasName("loop.g.0"), _, _));
  // Wire the loop pass through pass managers into the module pipeline.
  {
    LoopPassManager LPM(true);
    LPM.addPass(MLPHandle.getPass());
    FunctionPassManager FPM(true);
    FPM.addPass(createFunctionToLoopPassAdaptor(std::move(LPM)));
    MPM.addPass(createModuleToFunctionPassAdaptor(std::move(FPM)));
  }

  // Next we run two passes over the loops. The first one invalidates the
  // analyses for one loop, the second ones try to get the analysis results.
  // This should force only one analysis to re-run within the loop PM, but will
  // also invalidate everything after the loop pass manager finishes.
  EXPECT_CALL(MLPHandle, run(HasName("loop.0.0"), _, _, _))
      .WillOnce(DoDefault())
      .WillOnce(Invoke(getLoopAnalysisResult));
  EXPECT_CALL(MLPHandle, run(HasName("loop.0.1"), _, _, _))
      .WillOnce(InvokeWithoutArgs([] { return PreservedAnalyses::none(); }))
      .WillOnce(Invoke(getLoopAnalysisResult));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0.1"), _, _));
  EXPECT_CALL(MLPHandle, run(HasName("loop.0"), _, _, _))
      .WillOnce(DoDefault())
      .WillOnce(Invoke(getLoopAnalysisResult));
  EXPECT_CALL(MLPHandle, run(HasName("loop.g.0"), _, _, _))
      .WillOnce(DoDefault())
      .WillOnce(Invoke(getLoopAnalysisResult));
  // Wire two loop pass runs into the module pipeline.
  {
    LoopPassManager LPM(true);
    LPM.addPass(MLPHandle.getPass());
    LPM.addPass(MLPHandle.getPass());
    FunctionPassManager FPM(true);
    FPM.addPass(createFunctionToLoopPassAdaptor(std::move(LPM)));
    MPM.addPass(createModuleToFunctionPassAdaptor(std::move(FPM)));
  }

  // And now run the pipeline across the module.
  MPM.run(*M, MAM);
}

TEST_F(LoopPassManagerTest, FunctionPassInvalidationOfLoopAnalyses) {
  ModulePassManager MPM(true);
  FunctionPassManager FPM(true);
  // We process each function completely in sequence.
  ::testing::Sequence FSequence, GSequence;

  // First, force the analysis result to be computed for each loop.
  EXPECT_CALL(MLAHandle, run(HasName("loop.0.0"), _, _))
      .InSequence(FSequence)
      .WillOnce(DoDefault());
  EXPECT_CALL(MLAHandle, run(HasName("loop.0.1"), _, _))
      .InSequence(FSequence)
      .WillOnce(DoDefault());
  EXPECT_CALL(MLAHandle, run(HasName("loop.0"), _, _))
      .InSequence(FSequence)
      .WillOnce(DoDefault());
  EXPECT_CALL(MLAHandle, run(HasName("loop.g.0"), _, _))
      .InSequence(GSequence)
      .WillOnce(DoDefault());
  FPM.addPass(createFunctionToLoopPassAdaptor(
      RequireAnalysisLoopPass<MockLoopAnalysisHandle::Analysis>()));

  // No need to re-run if we require again from a fresh loop pass manager.
  FPM.addPass(createFunctionToLoopPassAdaptor(
      RequireAnalysisLoopPass<MockLoopAnalysisHandle::Analysis>()));

  // For 'f', preserve most things but not the specific loop analyses.
  EXPECT_CALL(MFPHandle, run(HasName("f"), _))
      .InSequence(FSequence)
      .WillOnce(Return(getLoopPassPreservedAnalyses()));
  EXPECT_CALL(MLAHandle, invalidate(HasName("loop.0.0"), _, _))
      .InSequence(FSequence)
      .WillOnce(DoDefault());
  // On one loop, skip the invalidation (as though we did an internal update).
  EXPECT_CALL(MLAHandle, invalidate(HasName("loop.0.1"), _, _))
      .InSequence(FSequence)
      .WillOnce(Return(false));
  EXPECT_CALL(MLAHandle, invalidate(HasName("loop.0"), _, _))
      .InSequence(FSequence)
      .WillOnce(DoDefault());
  // Now two loops still have to be recomputed.
  EXPECT_CALL(MLAHandle, run(HasName("loop.0.0"), _, _))
      .InSequence(FSequence)
      .WillOnce(DoDefault());
  EXPECT_CALL(MLAHandle, run(HasName("loop.0"), _, _))
      .InSequence(FSequence)
      .WillOnce(DoDefault());
  // Preserve things in the second function to ensure invalidation remains
  // isolated to one function.
  EXPECT_CALL(MFPHandle, run(HasName("g"), _))
      .InSequence(GSequence)
      .WillOnce(DoDefault());
  FPM.addPass(MFPHandle.getPass());
  FPM.addPass(createFunctionToLoopPassAdaptor(
      RequireAnalysisLoopPass<MockLoopAnalysisHandle::Analysis>()));

  EXPECT_CALL(MFPHandle, run(HasName("f"), _))
      .InSequence(FSequence)
      .WillOnce(DoDefault());
  // For 'g', fail to preserve anything, causing the loops themselves to be
  // cleared. We don't get an invalidation event here as the loop is gone, but
  // we should still have to recompute the analysis.
  EXPECT_CALL(MFPHandle, run(HasName("g"), _))
      .InSequence(GSequence)
      .WillOnce(Return(PreservedAnalyses::none()));
  EXPECT_CALL(MLAHandle, run(HasName("loop.g.0"), _, _))
      .InSequence(GSequence)
      .WillOnce(DoDefault());
  FPM.addPass(MFPHandle.getPass());
  FPM.addPass(createFunctionToLoopPassAdaptor(
      RequireAnalysisLoopPass<MockLoopAnalysisHandle::Analysis>()));

  MPM.addPass(createModuleToFunctionPassAdaptor(std::move(FPM)));

  // Verify with a separate function pass run that we didn't mess up 'f's
  // cache. No analysis runs should be necessary here.
  MPM.addPass(createModuleToFunctionPassAdaptor(createFunctionToLoopPassAdaptor(
      RequireAnalysisLoopPass<MockLoopAnalysisHandle::Analysis>())));

  MPM.run(*M, MAM);
}

TEST_F(LoopPassManagerTest, ModulePassInvalidationOfLoopAnalyses) {
  ModulePassManager MPM(true);
  ::testing::InSequence MakeExpectationsSequenced;

  // First, force the analysis result to be computed for each loop.
  EXPECT_CALL(MLAHandle, run(HasName("loop.0.0"), _, _));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0.1"), _, _));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0"), _, _));
  EXPECT_CALL(MLAHandle, run(HasName("loop.g.0"), _, _));
  MPM.addPass(createModuleToFunctionPassAdaptor(createFunctionToLoopPassAdaptor(
      RequireAnalysisLoopPass<MockLoopAnalysisHandle::Analysis>())));

  // Walking all the way out and all the way back in doesn't re-run the
  // analysis.
  MPM.addPass(createModuleToFunctionPassAdaptor(createFunctionToLoopPassAdaptor(
      RequireAnalysisLoopPass<MockLoopAnalysisHandle::Analysis>())));

  // But a module pass that doesn't preserve the actual mock loop analysis
  // invalidates all the way down and forces recomputing.
  EXPECT_CALL(MMPHandle, run(_, _)).WillOnce(InvokeWithoutArgs([] {
    auto PA = getLoopPassPreservedAnalyses();
    PA.preserve<FunctionAnalysisManagerModuleProxy>();
    return PA;
  }));
  // All the loop analyses from both functions get invalidated before we
  // recompute anything.
  EXPECT_CALL(MLAHandle, invalidate(HasName("loop.0.0"), _, _));
  // On one loop, again skip the invalidation (as though we did an internal
  // update).
  EXPECT_CALL(MLAHandle, invalidate(HasName("loop.0.1"), _, _))
      .WillOnce(Return(false));
  EXPECT_CALL(MLAHandle, invalidate(HasName("loop.0"), _, _));
  EXPECT_CALL(MLAHandle, invalidate(HasName("loop.g.0"), _, _));
  // Now all but one of the loops gets re-analyzed.
  EXPECT_CALL(MLAHandle, run(HasName("loop.0.0"), _, _));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0"), _, _));
  EXPECT_CALL(MLAHandle, run(HasName("loop.g.0"), _, _));
  MPM.addPass(MMPHandle.getPass());
  MPM.addPass(createModuleToFunctionPassAdaptor(createFunctionToLoopPassAdaptor(
      RequireAnalysisLoopPass<MockLoopAnalysisHandle::Analysis>())));

  // Verify that the cached values persist.
  MPM.addPass(createModuleToFunctionPassAdaptor(createFunctionToLoopPassAdaptor(
      RequireAnalysisLoopPass<MockLoopAnalysisHandle::Analysis>())));

  // Now we fail to preserve the loop analysis and observe that the loop
  // analyses are cleared (so no invalidation event) as the loops themselves
  // are no longer valid.
  EXPECT_CALL(MMPHandle, run(_, _)).WillOnce(InvokeWithoutArgs([] {
    auto PA = PreservedAnalyses::none();
    PA.preserve<FunctionAnalysisManagerModuleProxy>();
    return PA;
  }));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0.0"), _, _));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0.1"), _, _));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0"), _, _));
  EXPECT_CALL(MLAHandle, run(HasName("loop.g.0"), _, _));
  MPM.addPass(MMPHandle.getPass());
  MPM.addPass(createModuleToFunctionPassAdaptor(createFunctionToLoopPassAdaptor(
      RequireAnalysisLoopPass<MockLoopAnalysisHandle::Analysis>())));

  // Verify that the cached values persist.
  MPM.addPass(createModuleToFunctionPassAdaptor(createFunctionToLoopPassAdaptor(
      RequireAnalysisLoopPass<MockLoopAnalysisHandle::Analysis>())));

  // Next, check that even if we preserve everything within the function itelf,
  // if the function's module pass proxy isn't preserved and the potential set
  // of functions changes, the clear reaches the loop analyses as well. This
  // will again trigger re-runs but not invalidation events.
  EXPECT_CALL(MMPHandle, run(_, _)).WillOnce(InvokeWithoutArgs([] {
    auto PA = PreservedAnalyses::none();
    PA.preserveSet<AllAnalysesOn<Function>>();
    PA.preserveSet<AllAnalysesOn<Loop>>();
    return PA;
  }));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0.0"), _, _));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0.1"), _, _));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0"), _, _));
  EXPECT_CALL(MLAHandle, run(HasName("loop.g.0"), _, _));
  MPM.addPass(MMPHandle.getPass());
  MPM.addPass(createModuleToFunctionPassAdaptor(createFunctionToLoopPassAdaptor(
      RequireAnalysisLoopPass<MockLoopAnalysisHandle::Analysis>())));

  MPM.run(*M, MAM);
}

// Test that if any of the bundled analyses provided in the LPM's signature
// become invalid, the analysis proxy itself becomes invalid and we clear all
// loop analysis results.
TEST_F(LoopPassManagerTest, InvalidationOfBundledAnalyses) {
  ModulePassManager MPM(true);
  FunctionPassManager FPM(true);
  ::testing::InSequence MakeExpectationsSequenced;

  // First, force the analysis result to be computed for each loop.
  EXPECT_CALL(MLAHandle, run(HasName("loop.0.0"), _, _));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0.1"), _, _));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0"), _, _));
  FPM.addPass(createFunctionToLoopPassAdaptor(
      RequireAnalysisLoopPass<MockLoopAnalysisHandle::Analysis>()));

  // No need to re-run if we require again from a fresh loop pass manager.
  FPM.addPass(createFunctionToLoopPassAdaptor(
      RequireAnalysisLoopPass<MockLoopAnalysisHandle::Analysis>()));

  // Preserving everything but the loop analyses themselves results in
  // invalidation and running.
  EXPECT_CALL(MFPHandle, run(HasName("f"), _))
      .WillOnce(Return(getLoopPassPreservedAnalyses()));
  EXPECT_CALL(MLAHandle, invalidate(_, _, _)).Times(3);
  EXPECT_CALL(MLAHandle, run(HasName("loop.0.0"), _, _));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0.1"), _, _));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0"), _, _));
  FPM.addPass(MFPHandle.getPass());
  FPM.addPass(createFunctionToLoopPassAdaptor(
      RequireAnalysisLoopPass<MockLoopAnalysisHandle::Analysis>()));

  // The rest don't invalidate analyses, they only trigger re-runs because we
  // clear the cache completely.
  EXPECT_CALL(MFPHandle, run(HasName("f"), _)).WillOnce(InvokeWithoutArgs([] {
    auto PA = PreservedAnalyses::none();
    // Not preserving `AAManager`.
    PA.preserve<DominatorTreeAnalysis>();
    PA.preserve<LoopAnalysis>();
    PA.preserve<LoopAnalysisManagerFunctionProxy>();
    PA.preserve<ScalarEvolutionAnalysis>();
    return PA;
  }));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0.0"), _, _));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0.1"), _, _));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0"), _, _));
  FPM.addPass(MFPHandle.getPass());
  FPM.addPass(createFunctionToLoopPassAdaptor(
      RequireAnalysisLoopPass<MockLoopAnalysisHandle::Analysis>()));

  EXPECT_CALL(MFPHandle, run(HasName("f"), _)).WillOnce(InvokeWithoutArgs([] {
    auto PA = PreservedAnalyses::none();
    PA.preserve<AAManager>();
    // Not preserving `DominatorTreeAnalysis`.
    PA.preserve<LoopAnalysis>();
    PA.preserve<LoopAnalysisManagerFunctionProxy>();
    PA.preserve<ScalarEvolutionAnalysis>();
    return PA;
  }));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0.0"), _, _));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0.1"), _, _));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0"), _, _));
  FPM.addPass(MFPHandle.getPass());
  FPM.addPass(createFunctionToLoopPassAdaptor(
      RequireAnalysisLoopPass<MockLoopAnalysisHandle::Analysis>()));

  EXPECT_CALL(MFPHandle, run(HasName("f"), _)).WillOnce(InvokeWithoutArgs([] {
    auto PA = PreservedAnalyses::none();
    PA.preserve<AAManager>();
    PA.preserve<DominatorTreeAnalysis>();
    // Not preserving the `LoopAnalysis`.
    PA.preserve<LoopAnalysisManagerFunctionProxy>();
    PA.preserve<ScalarEvolutionAnalysis>();
    return PA;
  }));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0.0"), _, _));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0.1"), _, _));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0"), _, _));
  FPM.addPass(MFPHandle.getPass());
  FPM.addPass(createFunctionToLoopPassAdaptor(
      RequireAnalysisLoopPass<MockLoopAnalysisHandle::Analysis>()));

  EXPECT_CALL(MFPHandle, run(HasName("f"), _)).WillOnce(InvokeWithoutArgs([] {
    auto PA = PreservedAnalyses::none();
    PA.preserve<AAManager>();
    PA.preserve<DominatorTreeAnalysis>();
    PA.preserve<LoopAnalysis>();
    // Not preserving the `LoopAnalysisManagerFunctionProxy`.
    PA.preserve<ScalarEvolutionAnalysis>();
    return PA;
  }));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0.0"), _, _));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0.1"), _, _));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0"), _, _));
  FPM.addPass(MFPHandle.getPass());
  FPM.addPass(createFunctionToLoopPassAdaptor(
      RequireAnalysisLoopPass<MockLoopAnalysisHandle::Analysis>()));

  EXPECT_CALL(MFPHandle, run(HasName("f"), _)).WillOnce(InvokeWithoutArgs([] {
    auto PA = PreservedAnalyses::none();
    PA.preserve<AAManager>();
    PA.preserve<DominatorTreeAnalysis>();
    PA.preserve<LoopAnalysis>();
    PA.preserve<LoopAnalysisManagerFunctionProxy>();
    // Not preserving `ScalarEvolutionAnalysis`.
    return PA;
  }));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0.0"), _, _));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0.1"), _, _));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0"), _, _));
  FPM.addPass(MFPHandle.getPass());
  FPM.addPass(createFunctionToLoopPassAdaptor(
      RequireAnalysisLoopPass<MockLoopAnalysisHandle::Analysis>()));

  // After all the churn on 'f', we'll compute the loop analysis results for
  // 'g' once with a requires pass and then run our mock pass over g a bunch
  // but just get cached results each time.
  EXPECT_CALL(MLAHandle, run(HasName("loop.g.0"), _, _));
  EXPECT_CALL(MFPHandle, run(HasName("g"), _)).Times(6);

  MPM.addPass(createModuleToFunctionPassAdaptor(std::move(FPM)));
  MPM.run(*M, MAM);
}

TEST_F(LoopPassManagerTest, IndirectInvalidation) {
  // We need two distinct analysis types and handles.
  enum { A, B };
  MockLoopAnalysisHandleTemplate<A> MLAHandleA;
  MockLoopAnalysisHandleTemplate<B> MLAHandleB;
  LAM.registerPass([&] { return MLAHandleA.getAnalysis(); });
  LAM.registerPass([&] { return MLAHandleB.getAnalysis(); });
  typedef decltype(MLAHandleA)::Analysis AnalysisA;
  typedef decltype(MLAHandleB)::Analysis AnalysisB;

  // Set up AnalysisA to depend on our AnalysisB. For testing purposes we just
  // need to get the AnalysisB results in AnalysisA's run method and check if
  // AnalysisB gets invalidated in AnalysisA's invalidate method.
  ON_CALL(MLAHandleA, run(_, _, _))
      .WillByDefault(Invoke([&](Loop &L, LoopAnalysisManager &AM,
                                LoopStandardAnalysisResults &AR) {
        (void)AM.getResult<AnalysisB>(L, AR);
        return MLAHandleA.getResult();
      }));
  ON_CALL(MLAHandleA, invalidate(_, _, _))
      .WillByDefault(Invoke([](Loop &L, const PreservedAnalyses &PA,
                               LoopAnalysisManager::Invalidator &Inv) {
        auto PAC = PA.getChecker<AnalysisA>();
        return !(PAC.preserved() || PAC.preservedSet<AllAnalysesOn<Loop>>()) ||
               Inv.invalidate<AnalysisB>(L, PA);
      }));

  ::testing::InSequence MakeExpectationsSequenced;

  // Compute the analyses across all of 'f' first.
  EXPECT_CALL(MLAHandleA, run(HasName("loop.0.0"), _, _));
  EXPECT_CALL(MLAHandleB, run(HasName("loop.0.0"), _, _));
  EXPECT_CALL(MLAHandleA, run(HasName("loop.0.1"), _, _));
  EXPECT_CALL(MLAHandleB, run(HasName("loop.0.1"), _, _));
  EXPECT_CALL(MLAHandleA, run(HasName("loop.0"), _, _));
  EXPECT_CALL(MLAHandleB, run(HasName("loop.0"), _, _));

  // Now we invalidate AnalysisB (but not AnalysisA) for one of the loops and
  // preserve everything for the rest. This in turn triggers that one loop to
  // recompute both AnalysisB *and* AnalysisA if indirect invalidation is
  // working.
  EXPECT_CALL(MLPHandle, run(HasName("loop.0.0"), _, _, _))
      .WillOnce(InvokeWithoutArgs([] {
        auto PA = getLoopPassPreservedAnalyses();
        // Specifically preserve AnalysisA so that it would survive if it
        // didn't depend on AnalysisB.
        PA.preserve<AnalysisA>();
        return PA;
      }));
  // It happens that AnalysisB is invalidated first. That shouldn't matter
  // though, and we should still call AnalysisA's invalidation.
  EXPECT_CALL(MLAHandleB, invalidate(HasName("loop.0.0"), _, _));
  EXPECT_CALL(MLAHandleA, invalidate(HasName("loop.0.0"), _, _));
  EXPECT_CALL(MLPHandle, run(HasName("loop.0.0"), _, _, _))
      .WillOnce(Invoke([](Loop &L, LoopAnalysisManager &AM,
                          LoopStandardAnalysisResults &AR, LPMUpdater &) {
        (void)AM.getResult<AnalysisA>(L, AR);
        return PreservedAnalyses::all();
      }));
  EXPECT_CALL(MLAHandleA, run(HasName("loop.0.0"), _, _));
  EXPECT_CALL(MLAHandleB, run(HasName("loop.0.0"), _, _));
  // The rest of the loops should run and get cached results.
  EXPECT_CALL(MLPHandle, run(HasName("loop.0.1"), _, _, _))
      .Times(2)
      .WillRepeatedly(Invoke([](Loop &L, LoopAnalysisManager &AM,
                                LoopStandardAnalysisResults &AR, LPMUpdater &) {
        (void)AM.getResult<AnalysisA>(L, AR);
        return PreservedAnalyses::all();
      }));
  EXPECT_CALL(MLPHandle, run(HasName("loop.0"), _, _, _))
      .Times(2)
      .WillRepeatedly(Invoke([](Loop &L, LoopAnalysisManager &AM,
                                LoopStandardAnalysisResults &AR, LPMUpdater &) {
        (void)AM.getResult<AnalysisA>(L, AR);
        return PreservedAnalyses::all();
      }));

  // The run over 'g' should be boring, with us just computing the analyses once
  // up front and then running loop passes and getting cached results.
  EXPECT_CALL(MLAHandleA, run(HasName("loop.g.0"), _, _));
  EXPECT_CALL(MLAHandleB, run(HasName("loop.g.0"), _, _));
  EXPECT_CALL(MLPHandle, run(HasName("loop.g.0"), _, _, _))
      .Times(2)
      .WillRepeatedly(Invoke([](Loop &L, LoopAnalysisManager &AM,
                                LoopStandardAnalysisResults &AR, LPMUpdater &) {
        (void)AM.getResult<AnalysisA>(L, AR);
        return PreservedAnalyses::all();
      }));

  // Build the pipeline and run it.
  ModulePassManager MPM(true);
  FunctionPassManager FPM(true);
  FPM.addPass(
      createFunctionToLoopPassAdaptor(RequireAnalysisLoopPass<AnalysisA>()));
  LoopPassManager LPM(true);
  LPM.addPass(MLPHandle.getPass());
  LPM.addPass(MLPHandle.getPass());
  FPM.addPass(createFunctionToLoopPassAdaptor(std::move(LPM)));
  MPM.addPass(createModuleToFunctionPassAdaptor(std::move(FPM)));
  MPM.run(*M, MAM);
}

TEST_F(LoopPassManagerTest, IndirectOuterPassInvalidation) {
  typedef decltype(MLAHandle)::Analysis LoopAnalysis;

  MockFunctionAnalysisHandle MFAHandle;
  FAM.registerPass([&] { return MFAHandle.getAnalysis(); });
  typedef decltype(MFAHandle)::Analysis FunctionAnalysis;

  // Set up the loop analysis to depend on both the function and module
  // analysis.
  ON_CALL(MLAHandle, run(_, _, _))
      .WillByDefault(Invoke([&](Loop &L, LoopAnalysisManager &AM,
                                LoopStandardAnalysisResults &AR) {
        auto &FAMP = AM.getResult<FunctionAnalysisManagerLoopProxy>(L, AR);
        auto &FAM = FAMP.getManager();
        Function &F = *L.getHeader()->getParent();
        if (FAM.getCachedResult<FunctionAnalysis>(F))
          FAMP.registerOuterAnalysisInvalidation<FunctionAnalysis,
                                                 LoopAnalysis>();
        return MLAHandle.getResult();
      }));

  ::testing::InSequence MakeExpectationsSequenced;

  // Compute the analyses across all of 'f' first.
  EXPECT_CALL(MFPHandle, run(HasName("f"), _))
      .WillOnce(Invoke([](Function &F, FunctionAnalysisManager &AM) {
        // Force the computing of the function analysis so it is available in
        // this function.
        (void)AM.getResult<FunctionAnalysis>(F);
        return PreservedAnalyses::all();
      }));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0.0"), _, _));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0.1"), _, _));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0"), _, _));

  // Now invalidate the function analysis but preserve the loop analyses.
  // This should trigger immediate invalidation of the loop analyses, despite
  // the fact that they were preserved.
  EXPECT_CALL(MFPHandle, run(HasName("f"), _)).WillOnce(InvokeWithoutArgs([] {
    auto PA = getLoopPassPreservedAnalyses();
    PA.preserveSet<AllAnalysesOn<Loop>>();
    return PA;
  }));
  EXPECT_CALL(MLAHandle, invalidate(HasName("loop.0.0"), _, _));
  EXPECT_CALL(MLAHandle, invalidate(HasName("loop.0.1"), _, _));
  EXPECT_CALL(MLAHandle, invalidate(HasName("loop.0"), _, _));

  // And re-running a requires pass recomputes them.
  EXPECT_CALL(MLAHandle, run(HasName("loop.0.0"), _, _));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0.1"), _, _));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0"), _, _));

  // When we run over 'g' we don't populate the cache with the function
  // analysis.
  EXPECT_CALL(MFPHandle, run(HasName("g"), _))
      .WillOnce(Return(PreservedAnalyses::all()));
  EXPECT_CALL(MLAHandle, run(HasName("loop.g.0"), _, _));

  // Which means that no extra invalidation occurs and cached values are used.
  EXPECT_CALL(MFPHandle, run(HasName("g"), _)).WillOnce(InvokeWithoutArgs([] {
    auto PA = getLoopPassPreservedAnalyses();
    PA.preserveSet<AllAnalysesOn<Loop>>();
    return PA;
  }));

  // Build the pipeline and run it.
  ModulePassManager MPM(true);
  FunctionPassManager FPM(true);
  FPM.addPass(MFPHandle.getPass());
  FPM.addPass(
      createFunctionToLoopPassAdaptor(RequireAnalysisLoopPass<LoopAnalysis>()));
  FPM.addPass(MFPHandle.getPass());
  FPM.addPass(
      createFunctionToLoopPassAdaptor(RequireAnalysisLoopPass<LoopAnalysis>()));
  MPM.addPass(createModuleToFunctionPassAdaptor(std::move(FPM)));
  MPM.run(*M, MAM);
}

TEST_F(LoopPassManagerTest, LoopChildInsertion) {
  // Super boring module with three loops in a single loop nest.
  M = parseIR(Context, "define void @f(i1* %ptr) {\n"
                       "entry:\n"
                       "  br label %loop.0\n"
                       "loop.0:\n"
                       "  %cond.0 = load volatile i1, i1* %ptr\n"
                       "  br i1 %cond.0, label %loop.0.0.ph, label %end\n"
                       "loop.0.0.ph:\n"
                       "  br label %loop.0.0\n"
                       "loop.0.0:\n"
                       "  %cond.0.0 = load volatile i1, i1* %ptr\n"
                       "  br i1 %cond.0.0, label %loop.0.0, label %loop.0.1.ph\n"
                       "loop.0.1.ph:\n"
                       "  br label %loop.0.1\n"
                       "loop.0.1:\n"
                       "  %cond.0.1 = load volatile i1, i1* %ptr\n"
                       "  br i1 %cond.0.1, label %loop.0.1, label %loop.0.2.ph\n"
                       "loop.0.2.ph:\n"
                       "  br label %loop.0.2\n"
                       "loop.0.2:\n"
                       "  %cond.0.2 = load volatile i1, i1* %ptr\n"
                       "  br i1 %cond.0.2, label %loop.0.2, label %loop.0.latch\n"
                       "loop.0.latch:\n"
                       "  br label %loop.0\n"
                       "end:\n"
                       "  ret void\n"
                       "}\n");

  // Build up variables referring into the IR so we can rewrite it below
  // easily.
  Function &F = *M->begin();
  ASSERT_THAT(F, HasName("f"));
  Argument &Ptr = *F.arg_begin();
  auto BBI = F.begin();
  BasicBlock &EntryBB = *BBI++;
  ASSERT_THAT(EntryBB, HasName("entry"));
  BasicBlock &Loop0BB = *BBI++;
  ASSERT_THAT(Loop0BB, HasName("loop.0"));
  BasicBlock &Loop00PHBB = *BBI++;
  ASSERT_THAT(Loop00PHBB, HasName("loop.0.0.ph"));
  BasicBlock &Loop00BB = *BBI++;
  ASSERT_THAT(Loop00BB, HasName("loop.0.0"));
  BasicBlock &Loop01PHBB = *BBI++;
  ASSERT_THAT(Loop01PHBB, HasName("loop.0.1.ph"));
  BasicBlock &Loop01BB = *BBI++;
  ASSERT_THAT(Loop01BB, HasName("loop.0.1"));
  BasicBlock &Loop02PHBB = *BBI++;
  ASSERT_THAT(Loop02PHBB, HasName("loop.0.2.ph"));
  BasicBlock &Loop02BB = *BBI++;
  ASSERT_THAT(Loop02BB, HasName("loop.0.2"));
  BasicBlock &Loop0LatchBB = *BBI++;
  ASSERT_THAT(Loop0LatchBB, HasName("loop.0.latch"));
  BasicBlock &EndBB = *BBI++;
  ASSERT_THAT(EndBB, HasName("end"));
  ASSERT_THAT(BBI, F.end());
  auto CreateCondBr = [&](BasicBlock *TrueBB, BasicBlock *FalseBB,
                          const char *Name, BasicBlock *BB) {
    auto *Cond = new LoadInst(Type::getInt1Ty(Context), &Ptr, Name,
                              /*isVolatile*/ true, BB);
    BranchInst::Create(TrueBB, FalseBB, Cond, BB);
  };

  // Build the pass managers and register our pipeline. We build a single loop
  // pass pipeline consisting of three mock pass runs over each loop. After
  // this we run both domtree and loop verification passes to make sure that
  // the IR remained valid during our mutations.
  ModulePassManager MPM(true);
  FunctionPassManager FPM(true);
  LoopPassManager LPM(true);
  LPM.addPass(MLPHandle.getPass());
  LPM.addPass(MLPHandle.getPass());
  LPM.addPass(MLPHandle.getPass());
  FPM.addPass(createFunctionToLoopPassAdaptor(std::move(LPM)));
  FPM.addPass(DominatorTreeVerifierPass());
  FPM.addPass(LoopVerifierPass());
  MPM.addPass(createModuleToFunctionPassAdaptor(std::move(FPM)));

  // All the visit orders are deterministic, so we use simple fully order
  // expectations.
  ::testing::InSequence MakeExpectationsSequenced;

  // We run loop passes three times over each of the loops.
  EXPECT_CALL(MLPHandle, run(HasName("loop.0.0"), _, _, _))
      .WillOnce(Invoke(getLoopAnalysisResult));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0.0"), _, _));
  EXPECT_CALL(MLPHandle, run(HasName("loop.0.0"), _, _, _))
      .Times(2)
      .WillRepeatedly(Invoke(getLoopAnalysisResult));

  EXPECT_CALL(MLPHandle, run(HasName("loop.0.1"), _, _, _))
      .WillOnce(Invoke(getLoopAnalysisResult));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0.1"), _, _));

  // When running over the middle loop, the second run inserts two new child
  // loops, inserting them and itself into the worklist.
  BasicBlock *NewLoop010BB, *NewLoop01LatchBB;
  EXPECT_CALL(MLPHandle, run(HasName("loop.0.1"), _, _, _))
      .WillOnce(Invoke([&](Loop &L, LoopAnalysisManager &AM,
                           LoopStandardAnalysisResults &AR,
                           LPMUpdater &Updater) {
        auto *NewLoop = AR.LI.AllocateLoop();
        L.addChildLoop(NewLoop);
        auto *NewLoop010PHBB =
            BasicBlock::Create(Context, "loop.0.1.0.ph", &F, &Loop02PHBB);
        NewLoop010BB =
            BasicBlock::Create(Context, "loop.0.1.0", &F, &Loop02PHBB);
        NewLoop01LatchBB =
            BasicBlock::Create(Context, "loop.0.1.latch", &F, &Loop02PHBB);
        Loop01BB.getTerminator()->replaceUsesOfWith(&Loop01BB, NewLoop010PHBB);
        BranchInst::Create(NewLoop010BB, NewLoop010PHBB);
        CreateCondBr(NewLoop01LatchBB, NewLoop010BB, "cond.0.1.0",
                     NewLoop010BB);
        BranchInst::Create(&Loop01BB, NewLoop01LatchBB);
        AR.DT.addNewBlock(NewLoop010PHBB, &Loop01BB);
        AR.DT.addNewBlock(NewLoop010BB, NewLoop010PHBB);
        AR.DT.addNewBlock(NewLoop01LatchBB, NewLoop010BB);
        EXPECT_TRUE(AR.DT.verify());
        L.addBasicBlockToLoop(NewLoop010PHBB, AR.LI);
        NewLoop->addBasicBlockToLoop(NewLoop010BB, AR.LI);
        L.addBasicBlockToLoop(NewLoop01LatchBB, AR.LI);
        NewLoop->verifyLoop();
        L.verifyLoop();
        Updater.addChildLoops({NewLoop});
        return PreservedAnalyses::all();
      }));

  // We should immediately drop down to fully visit the new inner loop.
  EXPECT_CALL(MLPHandle, run(HasName("loop.0.1.0"), _, _, _))
      .WillOnce(Invoke(getLoopAnalysisResult));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0.1.0"), _, _));
  EXPECT_CALL(MLPHandle, run(HasName("loop.0.1.0"), _, _, _))
      .Times(2)
      .WillRepeatedly(Invoke(getLoopAnalysisResult));

  // After visiting the inner loop, we should re-visit the second loop
  // reflecting its new loop nest structure.
  EXPECT_CALL(MLPHandle, run(HasName("loop.0.1"), _, _, _))
      .WillOnce(Invoke(getLoopAnalysisResult));

  // In the second run over the middle loop after we've visited the new child,
  // we add another child to check that we can repeatedly add children, and add
  // children to a loop that already has children.
  EXPECT_CALL(MLPHandle, run(HasName("loop.0.1"), _, _, _))
      .WillOnce(Invoke([&](Loop &L, LoopAnalysisManager &AM,
                           LoopStandardAnalysisResults &AR,
                           LPMUpdater &Updater) {
        auto *NewLoop = AR.LI.AllocateLoop();
        L.addChildLoop(NewLoop);
        auto *NewLoop011PHBB = BasicBlock::Create(Context, "loop.0.1.1.ph", &F, NewLoop01LatchBB);
        auto *NewLoop011BB = BasicBlock::Create(Context, "loop.0.1.1", &F, NewLoop01LatchBB);
        NewLoop010BB->getTerminator()->replaceUsesOfWith(NewLoop01LatchBB,
                                                         NewLoop011PHBB);
        BranchInst::Create(NewLoop011BB, NewLoop011PHBB);
        CreateCondBr(NewLoop01LatchBB, NewLoop011BB, "cond.0.1.1",
                     NewLoop011BB);
        AR.DT.addNewBlock(NewLoop011PHBB, NewLoop010BB);
        auto *NewDTNode = AR.DT.addNewBlock(NewLoop011BB, NewLoop011PHBB);
        AR.DT.changeImmediateDominator(AR.DT[NewLoop01LatchBB], NewDTNode);
        EXPECT_TRUE(AR.DT.verify());
        L.addBasicBlockToLoop(NewLoop011PHBB, AR.LI);
        NewLoop->addBasicBlockToLoop(NewLoop011BB, AR.LI);
        NewLoop->verifyLoop();
        L.verifyLoop();
        Updater.addChildLoops({NewLoop});
        return PreservedAnalyses::all();
      }));

  // Again, we should immediately drop down to visit the new, unvisited child
  // loop. We don't need to revisit the other child though.
  EXPECT_CALL(MLPHandle, run(HasName("loop.0.1.1"), _, _, _))
      .WillOnce(Invoke(getLoopAnalysisResult));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0.1.1"), _, _));
  EXPECT_CALL(MLPHandle, run(HasName("loop.0.1.1"), _, _, _))
      .Times(2)
      .WillRepeatedly(Invoke(getLoopAnalysisResult));

  // And now we should pop back up to the second loop and do a full pipeline of
  // three passes on its current form.
  EXPECT_CALL(MLPHandle, run(HasName("loop.0.1"), _, _, _))
      .Times(3)
      .WillRepeatedly(Invoke(getLoopAnalysisResult));

  EXPECT_CALL(MLPHandle, run(HasName("loop.0.2"), _, _, _))
      .WillOnce(Invoke(getLoopAnalysisResult));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0.2"), _, _));
  EXPECT_CALL(MLPHandle, run(HasName("loop.0.2"), _, _, _))
      .Times(2)
      .WillRepeatedly(Invoke(getLoopAnalysisResult));

  EXPECT_CALL(MLPHandle, run(HasName("loop.0"), _, _, _))
      .WillOnce(Invoke(getLoopAnalysisResult));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0"), _, _));
  EXPECT_CALL(MLPHandle, run(HasName("loop.0"), _, _, _))
      .Times(2)
      .WillRepeatedly(Invoke(getLoopAnalysisResult));

  // Now that all the expected actions are registered, run the pipeline over
  // our module. All of our expectations are verified when the test finishes.
  MPM.run(*M, MAM);
}

TEST_F(LoopPassManagerTest, LoopPeerInsertion) {
  // Super boring module with two loop nests and loop nest with two child
  // loops.
  M = parseIR(Context, "define void @f(i1* %ptr) {\n"
                       "entry:\n"
                       "  br label %loop.0\n"
                       "loop.0:\n"
                       "  %cond.0 = load volatile i1, i1* %ptr\n"
                       "  br i1 %cond.0, label %loop.0.0.ph, label %loop.2.ph\n"
                       "loop.0.0.ph:\n"
                       "  br label %loop.0.0\n"
                       "loop.0.0:\n"
                       "  %cond.0.0 = load volatile i1, i1* %ptr\n"
                       "  br i1 %cond.0.0, label %loop.0.0, label %loop.0.2.ph\n"
                       "loop.0.2.ph:\n"
                       "  br label %loop.0.2\n"
                       "loop.0.2:\n"
                       "  %cond.0.2 = load volatile i1, i1* %ptr\n"
                       "  br i1 %cond.0.2, label %loop.0.2, label %loop.0.latch\n"
                       "loop.0.latch:\n"
                       "  br label %loop.0\n"
                       "loop.2.ph:\n"
                       "  br label %loop.2\n"
                       "loop.2:\n"
                       "  %cond.2 = load volatile i1, i1* %ptr\n"
                       "  br i1 %cond.2, label %loop.2, label %end\n"
                       "end:\n"
                       "  ret void\n"
                       "}\n");

  // Build up variables referring into the IR so we can rewrite it below
  // easily.
  Function &F = *M->begin();
  ASSERT_THAT(F, HasName("f"));
  Argument &Ptr = *F.arg_begin();
  auto BBI = F.begin();
  BasicBlock &EntryBB = *BBI++;
  ASSERT_THAT(EntryBB, HasName("entry"));
  BasicBlock &Loop0BB = *BBI++;
  ASSERT_THAT(Loop0BB, HasName("loop.0"));
  BasicBlock &Loop00PHBB = *BBI++;
  ASSERT_THAT(Loop00PHBB, HasName("loop.0.0.ph"));
  BasicBlock &Loop00BB = *BBI++;
  ASSERT_THAT(Loop00BB, HasName("loop.0.0"));
  BasicBlock &Loop02PHBB = *BBI++;
  ASSERT_THAT(Loop02PHBB, HasName("loop.0.2.ph"));
  BasicBlock &Loop02BB = *BBI++;
  ASSERT_THAT(Loop02BB, HasName("loop.0.2"));
  BasicBlock &Loop0LatchBB = *BBI++;
  ASSERT_THAT(Loop0LatchBB, HasName("loop.0.latch"));
  BasicBlock &Loop2PHBB = *BBI++;
  ASSERT_THAT(Loop2PHBB, HasName("loop.2.ph"));
  BasicBlock &Loop2BB = *BBI++;
  ASSERT_THAT(Loop2BB, HasName("loop.2"));
  BasicBlock &EndBB = *BBI++;
  ASSERT_THAT(EndBB, HasName("end"));
  ASSERT_THAT(BBI, F.end());
  auto CreateCondBr = [&](BasicBlock *TrueBB, BasicBlock *FalseBB,
                          const char *Name, BasicBlock *BB) {
    auto *Cond = new LoadInst(Type::getInt1Ty(Context), &Ptr, Name,
                              /*isVolatile*/ true, BB);
    BranchInst::Create(TrueBB, FalseBB, Cond, BB);
  };

  // Build the pass managers and register our pipeline. We build a single loop
  // pass pipeline consisting of three mock pass runs over each loop. After
  // this we run both domtree and loop verification passes to make sure that
  // the IR remained valid during our mutations.
  ModulePassManager MPM(true);
  FunctionPassManager FPM(true);
  LoopPassManager LPM(true);
  LPM.addPass(MLPHandle.getPass());
  LPM.addPass(MLPHandle.getPass());
  LPM.addPass(MLPHandle.getPass());
  FPM.addPass(createFunctionToLoopPassAdaptor(std::move(LPM)));
  FPM.addPass(DominatorTreeVerifierPass());
  FPM.addPass(LoopVerifierPass());
  MPM.addPass(createModuleToFunctionPassAdaptor(std::move(FPM)));

  // All the visit orders are deterministic, so we use simple fully order
  // expectations.
  ::testing::InSequence MakeExpectationsSequenced;

  // We run loop passes three times over each of the loops.
  EXPECT_CALL(MLPHandle, run(HasName("loop.0.0"), _, _, _))
      .WillOnce(Invoke(getLoopAnalysisResult));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0.0"), _, _));

  // On the second run, we insert a sibling loop.
  EXPECT_CALL(MLPHandle, run(HasName("loop.0.0"), _, _, _))
      .WillOnce(Invoke([&](Loop &L, LoopAnalysisManager &AM,
                           LoopStandardAnalysisResults &AR,
                           LPMUpdater &Updater) {
        auto *NewLoop = AR.LI.AllocateLoop();
        L.getParentLoop()->addChildLoop(NewLoop);
        auto *NewLoop01PHBB = BasicBlock::Create(Context, "loop.0.1.ph", &F, &Loop02PHBB);
        auto *NewLoop01BB = BasicBlock::Create(Context, "loop.0.1", &F, &Loop02PHBB);
        BranchInst::Create(NewLoop01BB, NewLoop01PHBB);
        CreateCondBr(&Loop02PHBB, NewLoop01BB, "cond.0.1", NewLoop01BB);
        Loop00BB.getTerminator()->replaceUsesOfWith(&Loop02PHBB, NewLoop01PHBB);
        AR.DT.addNewBlock(NewLoop01PHBB, &Loop00BB);
        auto *NewDTNode = AR.DT.addNewBlock(NewLoop01BB, NewLoop01PHBB);
        AR.DT.changeImmediateDominator(AR.DT[&Loop02PHBB], NewDTNode);
        EXPECT_TRUE(AR.DT.verify());
        L.getParentLoop()->addBasicBlockToLoop(NewLoop01PHBB, AR.LI);
        NewLoop->addBasicBlockToLoop(NewLoop01BB, AR.LI);
        L.getParentLoop()->verifyLoop();
        Updater.addSiblingLoops({NewLoop});
        return PreservedAnalyses::all();
      }));
  // We finish processing this loop as sibling loops don't perturb the
  // postorder walk.
  EXPECT_CALL(MLPHandle, run(HasName("loop.0.0"), _, _, _))
      .WillOnce(Invoke(getLoopAnalysisResult));

  // We visit the inserted sibling next.
  EXPECT_CALL(MLPHandle, run(HasName("loop.0.1"), _, _, _))
      .WillOnce(Invoke(getLoopAnalysisResult));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0.1"), _, _));
  EXPECT_CALL(MLPHandle, run(HasName("loop.0.1"), _, _, _))
      .Times(2)
      .WillRepeatedly(Invoke(getLoopAnalysisResult));

  EXPECT_CALL(MLPHandle, run(HasName("loop.0.2"), _, _, _))
      .WillOnce(Invoke(getLoopAnalysisResult));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0.2"), _, _));
  EXPECT_CALL(MLPHandle, run(HasName("loop.0.2"), _, _, _))
      .WillOnce(Invoke(getLoopAnalysisResult));
  // Next, on the third pass run on the last inner loop we add more new
  // siblings, more than one, and one with nested child loops. By doing this at
  // the end we make sure that edge case works well.
  EXPECT_CALL(MLPHandle, run(HasName("loop.0.2"), _, _, _))
      .WillOnce(Invoke([&](Loop &L, LoopAnalysisManager &AM,
                           LoopStandardAnalysisResults &AR,
                           LPMUpdater &Updater) {
        Loop *NewLoops[] = {AR.LI.AllocateLoop(), AR.LI.AllocateLoop(),
                            AR.LI.AllocateLoop()};
        L.getParentLoop()->addChildLoop(NewLoops[0]);
        L.getParentLoop()->addChildLoop(NewLoops[1]);
        NewLoops[1]->addChildLoop(NewLoops[2]);
        auto *NewLoop03PHBB =
            BasicBlock::Create(Context, "loop.0.3.ph", &F, &Loop0LatchBB);
        auto *NewLoop03BB =
            BasicBlock::Create(Context, "loop.0.3", &F, &Loop0LatchBB);
        auto *NewLoop04PHBB =
            BasicBlock::Create(Context, "loop.0.4.ph", &F, &Loop0LatchBB);
        auto *NewLoop04BB =
            BasicBlock::Create(Context, "loop.0.4", &F, &Loop0LatchBB);
        auto *NewLoop040PHBB =
            BasicBlock::Create(Context, "loop.0.4.0.ph", &F, &Loop0LatchBB);
        auto *NewLoop040BB =
            BasicBlock::Create(Context, "loop.0.4.0", &F, &Loop0LatchBB);
        auto *NewLoop04LatchBB =
            BasicBlock::Create(Context, "loop.0.4.latch", &F, &Loop0LatchBB);
        Loop02BB.getTerminator()->replaceUsesOfWith(&Loop0LatchBB, NewLoop03PHBB);
        BranchInst::Create(NewLoop03BB, NewLoop03PHBB);
        CreateCondBr(NewLoop04PHBB, NewLoop03BB, "cond.0.3", NewLoop03BB);
        BranchInst::Create(NewLoop04BB, NewLoop04PHBB);
        CreateCondBr(&Loop0LatchBB, NewLoop040PHBB, "cond.0.4", NewLoop04BB);
        BranchInst::Create(NewLoop040BB, NewLoop040PHBB);
        CreateCondBr(NewLoop04LatchBB, NewLoop040BB, "cond.0.4.0", NewLoop040BB);
        BranchInst::Create(NewLoop04BB, NewLoop04LatchBB);
        AR.DT.addNewBlock(NewLoop03PHBB, &Loop02BB);
        AR.DT.addNewBlock(NewLoop03BB, NewLoop03PHBB);
        AR.DT.addNewBlock(NewLoop04PHBB, NewLoop03BB);
        auto *NewDTNode = AR.DT.addNewBlock(NewLoop04BB, NewLoop04PHBB);
        AR.DT.changeImmediateDominator(AR.DT[&Loop0LatchBB], NewDTNode);
        AR.DT.addNewBlock(NewLoop040PHBB, NewLoop04BB);
        AR.DT.addNewBlock(NewLoop040BB, NewLoop040PHBB);
        AR.DT.addNewBlock(NewLoop04LatchBB, NewLoop040BB);
        EXPECT_TRUE(AR.DT.verify());
        L.getParentLoop()->addBasicBlockToLoop(NewLoop03PHBB, AR.LI);
        NewLoops[0]->addBasicBlockToLoop(NewLoop03BB, AR.LI);
        L.getParentLoop()->addBasicBlockToLoop(NewLoop04PHBB, AR.LI);
        NewLoops[1]->addBasicBlockToLoop(NewLoop04BB, AR.LI);
        NewLoops[1]->addBasicBlockToLoop(NewLoop040PHBB, AR.LI);
        NewLoops[2]->addBasicBlockToLoop(NewLoop040BB, AR.LI);
        NewLoops[1]->addBasicBlockToLoop(NewLoop04LatchBB, AR.LI);
        L.getParentLoop()->verifyLoop();
        Updater.addSiblingLoops({NewLoops[0], NewLoops[1]});
        return PreservedAnalyses::all();
      }));

  EXPECT_CALL(MLPHandle, run(HasName("loop.0.3"), _, _, _))
      .WillOnce(Invoke(getLoopAnalysisResult));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0.3"), _, _));
  EXPECT_CALL(MLPHandle, run(HasName("loop.0.3"), _, _, _))
      .Times(2)
      .WillRepeatedly(Invoke(getLoopAnalysisResult));

  // Note that we need to visit the inner loop of this added sibling before the
  // sibling itself!
  EXPECT_CALL(MLPHandle, run(HasName("loop.0.4.0"), _, _, _))
      .WillOnce(Invoke(getLoopAnalysisResult));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0.4.0"), _, _));
  EXPECT_CALL(MLPHandle, run(HasName("loop.0.4.0"), _, _, _))
      .Times(2)
      .WillRepeatedly(Invoke(getLoopAnalysisResult));

  EXPECT_CALL(MLPHandle, run(HasName("loop.0.4"), _, _, _))
      .WillOnce(Invoke(getLoopAnalysisResult));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0.4"), _, _));
  EXPECT_CALL(MLPHandle, run(HasName("loop.0.4"), _, _, _))
      .Times(2)
      .WillRepeatedly(Invoke(getLoopAnalysisResult));

  // And only now do we visit the outermost loop of the nest.
  EXPECT_CALL(MLPHandle, run(HasName("loop.0"), _, _, _))
      .WillOnce(Invoke(getLoopAnalysisResult));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0"), _, _));
  // On the second pass, we add sibling loops which become new top-level loops.
  EXPECT_CALL(MLPHandle, run(HasName("loop.0"), _, _, _))
      .WillOnce(Invoke([&](Loop &L, LoopAnalysisManager &AM,
                           LoopStandardAnalysisResults &AR,
                           LPMUpdater &Updater) {
        auto *NewLoop = AR.LI.AllocateLoop();
        AR.LI.addTopLevelLoop(NewLoop);
        auto *NewLoop1PHBB = BasicBlock::Create(Context, "loop.1.ph", &F, &Loop2BB);
        auto *NewLoop1BB = BasicBlock::Create(Context, "loop.1", &F, &Loop2BB);
        BranchInst::Create(NewLoop1BB, NewLoop1PHBB);
        CreateCondBr(&Loop2PHBB, NewLoop1BB, "cond.1", NewLoop1BB);
        Loop0BB.getTerminator()->replaceUsesOfWith(&Loop2PHBB, NewLoop1PHBB);
        AR.DT.addNewBlock(NewLoop1PHBB, &Loop0BB);
        auto *NewDTNode = AR.DT.addNewBlock(NewLoop1BB, NewLoop1PHBB);
        AR.DT.changeImmediateDominator(AR.DT[&Loop2PHBB], NewDTNode);
        EXPECT_TRUE(AR.DT.verify());
        NewLoop->addBasicBlockToLoop(NewLoop1BB, AR.LI);
        NewLoop->verifyLoop();
        Updater.addSiblingLoops({NewLoop});
        return PreservedAnalyses::all();
      }));
  EXPECT_CALL(MLPHandle, run(HasName("loop.0"), _, _, _))
      .WillOnce(Invoke(getLoopAnalysisResult));

  EXPECT_CALL(MLPHandle, run(HasName("loop.1"), _, _, _))
      .WillOnce(Invoke(getLoopAnalysisResult));
  EXPECT_CALL(MLAHandle, run(HasName("loop.1"), _, _));
  EXPECT_CALL(MLPHandle, run(HasName("loop.1"), _, _, _))
      .Times(2)
      .WillRepeatedly(Invoke(getLoopAnalysisResult));

  EXPECT_CALL(MLPHandle, run(HasName("loop.2"), _, _, _))
      .WillOnce(Invoke(getLoopAnalysisResult));
  EXPECT_CALL(MLAHandle, run(HasName("loop.2"), _, _));
  EXPECT_CALL(MLPHandle, run(HasName("loop.2"), _, _, _))
      .Times(2)
      .WillRepeatedly(Invoke(getLoopAnalysisResult));

  // Now that all the expected actions are registered, run the pipeline over
  // our module. All of our expectations are verified when the test finishes.
  MPM.run(*M, MAM);
}

TEST_F(LoopPassManagerTest, LoopDeletion) {
  // Build a module with a single loop nest that contains one outer loop with
  // three subloops, and one of those with its own subloop. We will
  // incrementally delete all of these to test different deletion scenarios.
  M = parseIR(Context, "define void @f(i1* %ptr) {\n"
                       "entry:\n"
                       "  br label %loop.0\n"
                       "loop.0:\n"
                       "  %cond.0 = load volatile i1, i1* %ptr\n"
                       "  br i1 %cond.0, label %loop.0.0.ph, label %end\n"
                       "loop.0.0.ph:\n"
                       "  br label %loop.0.0\n"
                       "loop.0.0:\n"
                       "  %cond.0.0 = load volatile i1, i1* %ptr\n"
                       "  br i1 %cond.0.0, label %loop.0.0, label %loop.0.1.ph\n"
                       "loop.0.1.ph:\n"
                       "  br label %loop.0.1\n"
                       "loop.0.1:\n"
                       "  %cond.0.1 = load volatile i1, i1* %ptr\n"
                       "  br i1 %cond.0.1, label %loop.0.1, label %loop.0.2.ph\n"
                       "loop.0.2.ph:\n"
                       "  br label %loop.0.2\n"
                       "loop.0.2:\n"
                       "  %cond.0.2 = load volatile i1, i1* %ptr\n"
                       "  br i1 %cond.0.2, label %loop.0.2.0.ph, label %loop.0.latch\n"
                       "loop.0.2.0.ph:\n"
                       "  br label %loop.0.2.0\n"
                       "loop.0.2.0:\n"
                       "  %cond.0.2.0 = load volatile i1, i1* %ptr\n"
                       "  br i1 %cond.0.2.0, label %loop.0.2.0, label %loop.0.2.latch\n"
                       "loop.0.2.latch:\n"
                       "  br label %loop.0.2\n"
                       "loop.0.latch:\n"
                       "  br label %loop.0\n"
                       "end:\n"
                       "  ret void\n"
                       "}\n");

  // Build up variables referring into the IR so we can rewrite it below
  // easily.
  Function &F = *M->begin();
  ASSERT_THAT(F, HasName("f"));
  Argument &Ptr = *F.arg_begin();
  auto BBI = F.begin();
  BasicBlock &EntryBB = *BBI++;
  ASSERT_THAT(EntryBB, HasName("entry"));
  BasicBlock &Loop0BB = *BBI++;
  ASSERT_THAT(Loop0BB, HasName("loop.0"));
  BasicBlock &Loop00PHBB = *BBI++;
  ASSERT_THAT(Loop00PHBB, HasName("loop.0.0.ph"));
  BasicBlock &Loop00BB = *BBI++;
  ASSERT_THAT(Loop00BB, HasName("loop.0.0"));
  BasicBlock &Loop01PHBB = *BBI++;
  ASSERT_THAT(Loop01PHBB, HasName("loop.0.1.ph"));
  BasicBlock &Loop01BB = *BBI++;
  ASSERT_THAT(Loop01BB, HasName("loop.0.1"));
  BasicBlock &Loop02PHBB = *BBI++;
  ASSERT_THAT(Loop02PHBB, HasName("loop.0.2.ph"));
  BasicBlock &Loop02BB = *BBI++;
  ASSERT_THAT(Loop02BB, HasName("loop.0.2"));
  BasicBlock &Loop020PHBB = *BBI++;
  ASSERT_THAT(Loop020PHBB, HasName("loop.0.2.0.ph"));
  BasicBlock &Loop020BB = *BBI++;
  ASSERT_THAT(Loop020BB, HasName("loop.0.2.0"));
  BasicBlock &Loop02LatchBB = *BBI++;
  ASSERT_THAT(Loop02LatchBB, HasName("loop.0.2.latch"));
  BasicBlock &Loop0LatchBB = *BBI++;
  ASSERT_THAT(Loop0LatchBB, HasName("loop.0.latch"));
  BasicBlock &EndBB = *BBI++;
  ASSERT_THAT(EndBB, HasName("end"));
  ASSERT_THAT(BBI, F.end());

  // Helper to do the actual deletion of a loop. We directly encode this here
  // to isolate ourselves from the rest of LLVM and for simplicity. Here we can
  // egregiously cheat based on knowledge of the test case. For example, we
  // have no PHI nodes and there is always a single i-dom.
  auto EraseLoop = [](Loop &L, BasicBlock &IDomBB,
                      LoopStandardAnalysisResults &AR, LPMUpdater &Updater) {
    assert(L.empty() && "Can only delete leaf loops with this routine!");
    SmallVector<BasicBlock *, 4> LoopBBs(L.block_begin(), L.block_end());
    Updater.markLoopAsDeleted(L, L.getName());
    IDomBB.getTerminator()->replaceUsesOfWith(L.getHeader(),
                                              L.getUniqueExitBlock());
    for (BasicBlock *LoopBB : LoopBBs) {
      SmallVector<DomTreeNode *, 4> ChildNodes(AR.DT[LoopBB]->begin(),
                                               AR.DT[LoopBB]->end());
      for (DomTreeNode *ChildNode : ChildNodes)
        AR.DT.changeImmediateDominator(ChildNode, AR.DT[&IDomBB]);
      AR.DT.eraseNode(LoopBB);
      AR.LI.removeBlock(LoopBB);
      LoopBB->dropAllReferences();
    }
    for (BasicBlock *LoopBB : LoopBBs)
      LoopBB->eraseFromParent();

    AR.LI.erase(&L);
  };

  // Build up the pass managers.
  ModulePassManager MPM(true);
  FunctionPassManager FPM(true);
  // We run several loop pass pipelines across the loop nest, but they all take
  // the same form of three mock pass runs in a loop pipeline followed by
  // domtree and loop verification. We use a lambda to stamp this out each
  // time.
  auto AddLoopPipelineAndVerificationPasses = [&] {
    LoopPassManager LPM(true);
    LPM.addPass(MLPHandle.getPass());
    LPM.addPass(MLPHandle.getPass());
    LPM.addPass(MLPHandle.getPass());
    FPM.addPass(createFunctionToLoopPassAdaptor(std::move(LPM)));
    FPM.addPass(DominatorTreeVerifierPass());
    FPM.addPass(LoopVerifierPass());
  };

  // All the visit orders are deterministic so we use simple fully order
  // expectations.
  ::testing::InSequence MakeExpectationsSequenced;

  // We run the loop pipeline with three passes over each of the loops. When
  // running over the middle loop, the second pass in the pipeline deletes it.
  // This should prevent the third pass from visiting it but otherwise leave
  // the process unimpacted.
  AddLoopPipelineAndVerificationPasses();
  EXPECT_CALL(MLPHandle, run(HasName("loop.0.0"), _, _, _))
      .WillOnce(Invoke(getLoopAnalysisResult));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0.0"), _, _));
  EXPECT_CALL(MLPHandle, run(HasName("loop.0.0"), _, _, _))
      .Times(2)
      .WillRepeatedly(Invoke(getLoopAnalysisResult));

  EXPECT_CALL(MLPHandle, run(HasName("loop.0.1"), _, _, _))
      .WillOnce(Invoke(getLoopAnalysisResult));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0.1"), _, _));
  EXPECT_CALL(MLPHandle, run(HasName("loop.0.1"), _, _, _))
      .WillOnce(
          Invoke([&](Loop &L, LoopAnalysisManager &AM,
                     LoopStandardAnalysisResults &AR, LPMUpdater &Updater) {
            Loop *ParentL = L.getParentLoop();
            AR.SE.forgetLoop(&L);
            EraseLoop(L, Loop01PHBB, AR, Updater);
            ParentL->verifyLoop();
            return PreservedAnalyses::all();
          }));

  EXPECT_CALL(MLPHandle, run(HasName("loop.0.2.0"), _, _, _))
      .WillOnce(Invoke(getLoopAnalysisResult));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0.2.0"), _, _));
  EXPECT_CALL(MLPHandle, run(HasName("loop.0.2.0"), _, _, _))
      .Times(2)
      .WillRepeatedly(Invoke(getLoopAnalysisResult));

  EXPECT_CALL(MLPHandle, run(HasName("loop.0.2"), _, _, _))
      .WillOnce(Invoke(getLoopAnalysisResult));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0.2"), _, _));
  EXPECT_CALL(MLPHandle, run(HasName("loop.0.2"), _, _, _))
      .Times(2)
      .WillRepeatedly(Invoke(getLoopAnalysisResult));

  EXPECT_CALL(MLPHandle, run(HasName("loop.0"), _, _, _))
      .WillOnce(Invoke(getLoopAnalysisResult));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0"), _, _));
  EXPECT_CALL(MLPHandle, run(HasName("loop.0"), _, _, _))
      .Times(2)
      .WillRepeatedly(Invoke(getLoopAnalysisResult));

  // Run the loop pipeline again. This time we delete the last loop, which
  // contains a nested loop within it and insert a new loop into the nest. This
  // makes sure we can handle nested loop deletion.
  AddLoopPipelineAndVerificationPasses();
  EXPECT_CALL(MLPHandle, run(HasName("loop.0.0"), _, _, _))
      .Times(3)
      .WillRepeatedly(Invoke(getLoopAnalysisResult));

  EXPECT_CALL(MLPHandle, run(HasName("loop.0.2.0"), _, _, _))
      .Times(3)
      .WillRepeatedly(Invoke(getLoopAnalysisResult));

  EXPECT_CALL(MLPHandle, run(HasName("loop.0.2"), _, _, _))
      .WillOnce(Invoke(getLoopAnalysisResult));
  BasicBlock *NewLoop03PHBB;
  EXPECT_CALL(MLPHandle, run(HasName("loop.0.2"), _, _, _))
      .WillOnce(
          Invoke([&](Loop &L, LoopAnalysisManager &AM,
                     LoopStandardAnalysisResults &AR, LPMUpdater &Updater) {
            AR.SE.forgetLoop(*L.begin());
            EraseLoop(**L.begin(), Loop020PHBB, AR, Updater);

            auto *ParentL = L.getParentLoop();
            AR.SE.forgetLoop(&L);
            EraseLoop(L, Loop02PHBB, AR, Updater);

            // Now insert a new sibling loop.
            auto *NewSibling = AR.LI.AllocateLoop();
            ParentL->addChildLoop(NewSibling);
            NewLoop03PHBB =
                BasicBlock::Create(Context, "loop.0.3.ph", &F, &Loop0LatchBB);
            auto *NewLoop03BB =
                BasicBlock::Create(Context, "loop.0.3", &F, &Loop0LatchBB);
            BranchInst::Create(NewLoop03BB, NewLoop03PHBB);
            auto *Cond =
                new LoadInst(Type::getInt1Ty(Context), &Ptr, "cond.0.3",
                             /*isVolatile*/ true, NewLoop03BB);
            BranchInst::Create(&Loop0LatchBB, NewLoop03BB, Cond, NewLoop03BB);
            Loop02PHBB.getTerminator()->replaceUsesOfWith(&Loop0LatchBB,
                                                          NewLoop03PHBB);
            AR.DT.addNewBlock(NewLoop03PHBB, &Loop02PHBB);
            AR.DT.addNewBlock(NewLoop03BB, NewLoop03PHBB);
            AR.DT.changeImmediateDominator(AR.DT[&Loop0LatchBB],
                                           AR.DT[NewLoop03BB]);
            EXPECT_TRUE(AR.DT.verify());
            ParentL->addBasicBlockToLoop(NewLoop03PHBB, AR.LI);
            NewSibling->addBasicBlockToLoop(NewLoop03BB, AR.LI);
            NewSibling->verifyLoop();
            ParentL->verifyLoop();
            Updater.addSiblingLoops({NewSibling});
            return PreservedAnalyses::all();
          }));

  // To respect our inner-to-outer traversal order, we must visit the
  // newly-inserted sibling of the loop we just deleted before we visit the
  // outer loop. When we do so, this must compute a fresh analysis result, even
  // though our new loop has the same pointer value as the loop we deleted.
  EXPECT_CALL(MLPHandle, run(HasName("loop.0.3"), _, _, _))
      .WillOnce(Invoke(getLoopAnalysisResult));
  EXPECT_CALL(MLAHandle, run(HasName("loop.0.3"), _, _));
  EXPECT_CALL(MLPHandle, run(HasName("loop.0.3"), _, _, _))
      .Times(2)
      .WillRepeatedly(Invoke(getLoopAnalysisResult));

  EXPECT_CALL(MLPHandle, run(HasName("loop.0"), _, _, _))
      .Times(3)
      .WillRepeatedly(Invoke(getLoopAnalysisResult));

  // In the final loop pipeline run we delete every loop, including the last
  // loop of the nest. We do this again in the second pass in the pipeline, and
  // as a consequence we never make it to three runs on any loop. We also cover
  // deleting multiple loops in a single pipeline, deleting the first loop and
  // deleting the (last) top level loop.
  AddLoopPipelineAndVerificationPasses();
  EXPECT_CALL(MLPHandle, run(HasName("loop.0.0"), _, _, _))
      .WillOnce(Invoke(getLoopAnalysisResult));
  EXPECT_CALL(MLPHandle, run(HasName("loop.0.0"), _, _, _))
      .WillOnce(
          Invoke([&](Loop &L, LoopAnalysisManager &AM,
                     LoopStandardAnalysisResults &AR, LPMUpdater &Updater) {
            AR.SE.forgetLoop(&L);
            EraseLoop(L, Loop00PHBB, AR, Updater);
            return PreservedAnalyses::all();
          }));

  EXPECT_CALL(MLPHandle, run(HasName("loop.0.3"), _, _, _))
      .WillOnce(Invoke(getLoopAnalysisResult));
  EXPECT_CALL(MLPHandle, run(HasName("loop.0.3"), _, _, _))
      .WillOnce(
          Invoke([&](Loop &L, LoopAnalysisManager &AM,
                     LoopStandardAnalysisResults &AR, LPMUpdater &Updater) {
            AR.SE.forgetLoop(&L);
            EraseLoop(L, *NewLoop03PHBB, AR, Updater);
            return PreservedAnalyses::all();
          }));

  EXPECT_CALL(MLPHandle, run(HasName("loop.0"), _, _, _))
      .WillOnce(Invoke(getLoopAnalysisResult));
  EXPECT_CALL(MLPHandle, run(HasName("loop.0"), _, _, _))
      .WillOnce(
          Invoke([&](Loop &L, LoopAnalysisManager &AM,
                     LoopStandardAnalysisResults &AR, LPMUpdater &Updater) {
            AR.SE.forgetLoop(&L);
            EraseLoop(L, EntryBB, AR, Updater);
            return PreservedAnalyses::all();
          }));

  // Add the function pass pipeline now that it is fully built up and run it
  // over the module's one function.
  MPM.addPass(createModuleToFunctionPassAdaptor(std::move(FPM)));
  MPM.run(*M, MAM);
}
}
