diff --git a/llvm/tools/llc/llc.cpp b/llvm/tools/llc/llc.cpp --- a/llvm/tools/llc/llc.cpp +++ b/llvm/tools/llc/llc.cpp @@ -21,6 +21,7 @@ #include "llvm/CodeGen/MIRParser/MIRParser.h" #include "llvm/CodeGen/MachineFunctionPass.h" #include "llvm/CodeGen/MachineModuleInfo.h" +#include "llvm/CodeGen/PassManager.h" #include "llvm/CodeGen/TargetPassConfig.h" #include "llvm/CodeGen/TargetSubtargetInfo.h" #include "llvm/IR/AutoUpgrade.h" @@ -36,6 +37,7 @@ #include "llvm/IRReader/IRReader.h" #include "llvm/MC/SubtargetFeature.h" #include "llvm/Pass.h" +#include "llvm/Passes/PassBuilder.h" #include "llvm/Support/CommandLine.h" #include "llvm/Support/Debug.h" #include "llvm/Support/FileSystem.h" @@ -52,6 +54,12 @@ #include "llvm/Target/TargetMachine.h" #include "llvm/Transforms/Utils/Cloning.h" #include + +#include +#include +#include +#include +#include using namespace llvm; // General options for llc. Other pass-specific options are specified @@ -163,6 +171,8 @@ namespace { static ManagedStatic> RunPassNames; +static ManagedStatic> RunPassNewNames; + struct RunPassOption { void operator=(const std::string &Val) const { if (Val.empty()) @@ -173,6 +183,17 @@ RunPassNames->push_back(PassName); } }; + +struct RunPassNewOption { + void operator=(const std::string &Val) const { + if (Val.empty()) + return; + SmallVector PassNames; + StringRef(Val).split(PassNames, ',', -1, false); + for (auto PassName : PassNames) + RunPassNewNames->push_back(PassName); + } +}; } static RunPassOption RunPassOpt; @@ -182,6 +203,15 @@ cl::desc("Run compiler only for specified passes (comma separated list)"), cl::value_desc("pass-name"), cl::ZeroOrMore, cl::location(RunPassOpt)); +static RunPassNewOption RunPassNewOpt; + +static cl::opt> RunPassNew( + "run-pass-new", + cl::desc( + "Run compiler only for specified new passes (comma separated list)"), + cl::value_desc("new-pass-name"), cl::ZeroOrMore, + cl::location(RunPassNewOpt)); + static int compileModule(char **, LLVMContext &); static std::unique_ptr GetOutputStream(const char *TargetName, @@ -360,6 +390,18 @@ return 0; } +static bool addNewPass(ModulePassManager &PM, MachineFunctionPassManager &MFPM, + const char *argv0, StringRef PassName, + TargetPassConfig &TPC) { +#define MACHINE_FUNCTION_PASS(NAME, CREATE_PASS) \ + if (PassName == NAME) \ + MFPM.addPass(CREATE_PASS); +#include "../../lib/Passes/PassRegistry.def" + std::string Banner = std::string("After ") + std::string("machine-cp"); + TPC.printAndVerify(Banner); + return false; +} + static bool addPass(PassManagerBase &PM, const char *argv0, StringRef PassName, TargetPassConfig &TPC) { if (PassName == "none") @@ -490,6 +532,38 @@ // Build up all of the passes that we want to do to the module. legacy::PassManager PM; + LLVMTargetMachine &LLVMTM = static_cast(*Target); + + PassInstrumentationCallbacks PIC; + PassBuilder PB(TheTarget->createTargetMachine( + TheTriple.getTriple(), CPUStr, FeaturesStr, Options, getRelocModel(), + getCodeModel(), OLvl)); + AAManager AA = PB.buildDefaultAAPipeline(); + MachineFunctionAnalysisManager MFAM; + FunctionAnalysisManager FAM; + ModuleAnalysisManager MAM; + + PB.registerModuleAnalyses(MAM); + PB.registerFunctionAnalyses(FAM); + MAM.registerPass([&] { return FunctionAnalysisManagerModuleProxy(FAM); }); + FAM.registerPass([&] { return ModuleAnalysisManagerFunctionProxy(MAM); }); + FAM.registerPass( + [&] { return MachineFunctionAnalysisManagerFunctionProxy(MFAM); }); + FAM.registerPass([&] { return AA; }); + MFAM.registerPass( + [&] { return FunctionAnalysisManagerMachineFunctionProxy(FAM); }); +#define MACHINE_FUNCTION_ANALYSIS(NAME, CREATE_PASS) \ + MFAM.registerPass([&] { return CREATE_PASS; }); + + MAM.registerPass([&] { return PassInstrumentationAnalysis(&PIC); }); + FAM.registerPass([&] { return PassInstrumentationAnalysis(&PIC); }); + MFAM.registerPass([&] { return PassInstrumentationAnalysis(&PIC); }); + +#include "../../lib/Passes/PassRegistry.def" + + ModulePassManager MPM; + MachineFunctionPassManager MFPM; + // Add an appropriate TargetLibraryInfo pass for the module's triple. TargetLibraryInfoImpl TLII(Triple(M->getTargetTriple())); @@ -498,6 +572,11 @@ TLII.disableAllFunctions(); PM.add(new TargetLibraryInfoWrapperPass(TLII)); + FAM.registerPass([&] { return TargetLibraryAnalysis(TLII); }); + MAM.registerPass([&] { return TargetLibraryAnalysis(TLII); }); + + MAM.registerPass([&] { return MachineModuleAnalysis(&LLVMTM); }); + // Add the target data from the target machine, if it exists, or the module. M->setDataLayout(Target->createDataLayout()); @@ -541,6 +620,8 @@ MachineModuleInfoWrapperPass *MMIWP = new MachineModuleInfoWrapperPass(&LLVMTM); + const bool UsingNewPM = !RunPassNewNames->empty(); + // Construct a custom pass pipeline that starts after instruction // selection. if (!RunPassNames->empty()) { @@ -559,18 +640,30 @@ TPC.setDisableVerify(NoVerify); PM.add(&TPC); - PM.add(MMI); + PM.add(MMIWP); TPC.printAndVerify(""); for (const std::string &RunPassName : *RunPassNames) { if (addPass(PM, argv0, RunPassName, TPC)) return 1; } + for (const std::string &RunPassName : *RunPassNewNames) { + if (addNewPass(MPM, MFPM, argv0, RunPassName, TPC)) + return 1; + } TPC.setInitialized(); - PM.add(createPrintMIRPass(*OS)); + + if (UsingNewPM) + MPM.addPass(createModuleToFunctionPassAdaptor( + createFunctionToMachineFunctionPassAdaptor(std::move(MFPM)))); + + if (UsingNewPM) + MPM.addPass(MIRPrintingPass(*OS)); + else + PM.add(createPrintMIRPass(*OS)); PM.add(createFreeMachineFunctionPass()); } else if (Target->addPassesToEmitFile(PM, *OS, DwoOut ? &DwoOut->os() : nullptr, - FileType, NoVerify, MMI)) { + FileType, NoVerify, MMIWP)) { WithColor::warning(errs(), argv[0]) << "target does not support generation of this" << " file type!\n"; @@ -579,7 +672,11 @@ if (MIR) { assert(MMIWP && "Forgot to create MMIWP?"); - if (MIR->parseMachineFunctions(*M, MMIWP->getMMI())) + if (UsingNewPM) { + if (MIR->parseMachineFunctions( + *M, MAM.getResult(*M))) + return 1; + } else if (MIR->parseMachineFunctions(*M, MMIWP->getMMI())) return 1; } @@ -598,6 +695,12 @@ Buffer.clear(); } + // Now that we have all of the passes ready, run them. + { + PrettyStackTraceString CrashInfo("Optimizer"); + MPM.run(*M, MAM); + } + PM.run(*M); auto HasError =