diff options
Diffstat (limited to 'llvm/lib')
-rw-r--r-- | llvm/lib/LTO/LTOBackend.cpp | 14 | ||||
-rw-r--r-- | llvm/lib/Passes/PassBuilder.cpp | 366 |
2 files changed, 218 insertions, 162 deletions
diff --git a/llvm/lib/LTO/LTOBackend.cpp b/llvm/lib/LTO/LTOBackend.cpp index 20fc40de4b9..1f9d60a5bdf 100644 --- a/llvm/lib/LTO/LTOBackend.cpp +++ b/llvm/lib/LTO/LTOBackend.cpp @@ -162,7 +162,7 @@ static void runNewPMPasses(Config &Conf, Module &Mod, TargetMachine *TM, AAManager AA; // Parse a custom AA pipeline if asked to. - if (!PB.parseAAPipeline(AA, "default")) + if (auto Err = PB.parseAAPipeline(AA, "default")) report_fatal_error("Error parsing default AA pipeline"); LoopAnalysisManager LAM(Conf.DebugPassManager); @@ -221,9 +221,9 @@ static void runNewPMCustomPasses(Module &Mod, TargetMachine *TM, // Parse a custom AA pipeline if asked to. if (!AAPipelineDesc.empty()) - if (!PB.parseAAPipeline(AA, AAPipelineDesc)) - report_fatal_error("unable to parse AA pipeline description: " + - AAPipelineDesc); + if (auto Err = PB.parseAAPipeline(AA, AAPipelineDesc)) + report_fatal_error("unable to parse AA pipeline description '" + + AAPipelineDesc + "': " + toString(std::move(Err))); LoopAnalysisManager LAM; FunctionAnalysisManager FAM; @@ -246,9 +246,9 @@ static void runNewPMCustomPasses(Module &Mod, TargetMachine *TM, MPM.addPass(VerifierPass()); // Now, add all the passes we've been requested to. - if (!PB.parsePassPipeline(MPM, PipelineDesc)) - report_fatal_error("unable to parse pass pipeline description: " + - PipelineDesc); + if (auto Err = PB.parsePassPipeline(MPM, PipelineDesc)) + report_fatal_error("unable to parse pass pipeline description '" + + PipelineDesc + "': " + toString(std::move(Err))); if (!DisableVerify) MPM.addPass(VerifierPass()); diff --git a/llvm/lib/Passes/PassBuilder.cpp b/llvm/lib/Passes/PassBuilder.cpp index 09758dc5651..f6313d23e2d 100644 --- a/llvm/lib/Passes/PassBuilder.cpp +++ b/llvm/lib/Passes/PassBuilder.cpp @@ -58,6 +58,7 @@ #include "llvm/IR/PassManager.h" #include "llvm/IR/Verifier.h" #include "llvm/Support/Debug.h" +#include "llvm/Support/FormatVariadic.h" #include "llvm/Support/Regex.h" #include "llvm/Target/TargetMachine.h" #include "llvm/Transforms/AggressiveInstCombine/AggressiveInstCombine.h" @@ -1402,9 +1403,9 @@ PassBuilder::parsePipelineText(StringRef Text) { return {std::move(ResultPipeline)}; } -bool PassBuilder::parseModulePass(ModulePassManager &MPM, - const PipelineElement &E, bool VerifyEachPass, - bool DebugLogging) { +Error PassBuilder::parseModulePass(ModulePassManager &MPM, + const PipelineElement &E, + bool VerifyEachPass, bool DebugLogging) { auto &Name = E.Name; auto &InnerPipeline = E.InnerPipeline; @@ -1412,50 +1413,56 @@ bool PassBuilder::parseModulePass(ModulePassManager &MPM, if (!InnerPipeline.empty()) { if (Name == "module") { ModulePassManager NestedMPM(DebugLogging); - if (!parseModulePassPipeline(NestedMPM, InnerPipeline, VerifyEachPass, - DebugLogging)) - return false; + if (auto Err = parseModulePassPipeline(NestedMPM, InnerPipeline, + VerifyEachPass, DebugLogging)) + return Err; MPM.addPass(std::move(NestedMPM)); - return true; + return Error::success(); } if (Name == "cgscc") { CGSCCPassManager CGPM(DebugLogging); - if (!parseCGSCCPassPipeline(CGPM, InnerPipeline, VerifyEachPass, - DebugLogging)) - return false; + if (auto Err = parseCGSCCPassPipeline(CGPM, InnerPipeline, VerifyEachPass, + DebugLogging)) + return Err; MPM.addPass(createModuleToPostOrderCGSCCPassAdaptor(std::move(CGPM))); - return true; + return Error::success(); } if (Name == "function") { FunctionPassManager FPM(DebugLogging); - if (!parseFunctionPassPipeline(FPM, InnerPipeline, VerifyEachPass, - DebugLogging)) - return false; + if (auto Err = parseFunctionPassPipeline(FPM, InnerPipeline, + VerifyEachPass, DebugLogging)) + return Err; MPM.addPass(createModuleToFunctionPassAdaptor(std::move(FPM))); - return true; + return Error::success(); } if (auto Count = parseRepeatPassName(Name)) { ModulePassManager NestedMPM(DebugLogging); - if (!parseModulePassPipeline(NestedMPM, InnerPipeline, VerifyEachPass, - DebugLogging)) - return false; + if (auto Err = parseModulePassPipeline(NestedMPM, InnerPipeline, + VerifyEachPass, DebugLogging)) + return Err; MPM.addPass(createRepeatedPass(*Count, std::move(NestedMPM))); - return true; + return Error::success(); } for (auto &C : ModulePipelineParsingCallbacks) if (C(Name, MPM, InnerPipeline)) - return true; + return Error::success(); // Normal passes can't have pipelines. - return false; + return make_error<StringError>( + formatv("invalid use of '{0}' pass as module pipeline", Name).str(), + inconvertibleErrorCode()); + ; } // Manually handle aliases for pre-configured pipeline fragments. if (startsWithDefaultPipelineAliasPrefix(Name)) { SmallVector<StringRef, 3> Matches; if (!DefaultAliasRegex.match(Name, &Matches)) - return false; + return make_error<StringError>( + formatv("unknown default pipeline alias '{0}'", Name).str(), + inconvertibleErrorCode()); + assert(Matches.size() == 3 && "Must capture two matched strings!"); OptimizationLevel L = StringSwitch<OptimizationLevel>(Matches[2]) @@ -1467,7 +1474,7 @@ bool PassBuilder::parseModulePass(ModulePassManager &MPM, .Case("Oz", Oz); if (L == O0) // At O0 we do nothing at all! - return true; + return Error::success(); if (Matches[1] == "default") { MPM.addPass(buildPerModuleDefaultPipeline(L, DebugLogging)); @@ -1481,38 +1488,40 @@ bool PassBuilder::parseModulePass(ModulePassManager &MPM, assert(Matches[1] == "lto" && "Not one of the matched options!"); MPM.addPass(buildLTODefaultPipeline(L, DebugLogging, nullptr)); } - return true; + return Error::success(); } // Finally expand the basic registered passes from the .inc file. #define MODULE_PASS(NAME, CREATE_PASS) \ if (Name == NAME) { \ MPM.addPass(CREATE_PASS); \ - return true; \ + return Error::success(); \ } #define MODULE_ANALYSIS(NAME, CREATE_PASS) \ if (Name == "require<" NAME ">") { \ MPM.addPass( \ RequireAnalysisPass< \ std::remove_reference<decltype(CREATE_PASS)>::type, Module>()); \ - return true; \ + return Error::success(); \ } \ if (Name == "invalidate<" NAME ">") { \ MPM.addPass(InvalidateAnalysisPass< \ std::remove_reference<decltype(CREATE_PASS)>::type>()); \ - return true; \ + return Error::success(); \ } #include "PassRegistry.def" for (auto &C : ModulePipelineParsingCallbacks) if (C(Name, MPM, InnerPipeline)) - return true; - return false; + return Error::success(); + return make_error<StringError>( + formatv("unknown module pass '{0}'", Name).str(), + inconvertibleErrorCode()); } -bool PassBuilder::parseCGSCCPass(CGSCCPassManager &CGPM, - const PipelineElement &E, bool VerifyEachPass, - bool DebugLogging) { +Error PassBuilder::parseCGSCCPass(CGSCCPassManager &CGPM, + const PipelineElement &E, bool VerifyEachPass, + bool DebugLogging) { auto &Name = E.Name; auto &InnerPipeline = E.InnerPipeline; @@ -1520,53 +1529,55 @@ bool PassBuilder::parseCGSCCPass(CGSCCPassManager &CGPM, if (!InnerPipeline.empty()) { if (Name == "cgscc") { CGSCCPassManager NestedCGPM(DebugLogging); - if (!parseCGSCCPassPipeline(NestedCGPM, InnerPipeline, VerifyEachPass, - DebugLogging)) - return false; + if (auto Err = parseCGSCCPassPipeline(NestedCGPM, InnerPipeline, + VerifyEachPass, DebugLogging)) + return Err; // Add the nested pass manager with the appropriate adaptor. CGPM.addPass(std::move(NestedCGPM)); - return true; + return Error::success(); } if (Name == "function") { FunctionPassManager FPM(DebugLogging); - if (!parseFunctionPassPipeline(FPM, InnerPipeline, VerifyEachPass, - DebugLogging)) - return false; + if (auto Err = parseFunctionPassPipeline(FPM, InnerPipeline, + VerifyEachPass, DebugLogging)) + return Err; // Add the nested pass manager with the appropriate adaptor. CGPM.addPass(createCGSCCToFunctionPassAdaptor(std::move(FPM))); - return true; + return Error::success(); } if (auto Count = parseRepeatPassName(Name)) { CGSCCPassManager NestedCGPM(DebugLogging); - if (!parseCGSCCPassPipeline(NestedCGPM, InnerPipeline, VerifyEachPass, - DebugLogging)) - return false; + if (auto Err = parseCGSCCPassPipeline(NestedCGPM, InnerPipeline, + VerifyEachPass, DebugLogging)) + return Err; CGPM.addPass(createRepeatedPass(*Count, std::move(NestedCGPM))); - return true; + return Error::success(); } if (auto MaxRepetitions = parseDevirtPassName(Name)) { CGSCCPassManager NestedCGPM(DebugLogging); - if (!parseCGSCCPassPipeline(NestedCGPM, InnerPipeline, VerifyEachPass, - DebugLogging)) - return false; + if (auto Err = parseCGSCCPassPipeline(NestedCGPM, InnerPipeline, + VerifyEachPass, DebugLogging)) + return Err; CGPM.addPass( createDevirtSCCRepeatedPass(std::move(NestedCGPM), *MaxRepetitions)); - return true; + return Error::success(); } for (auto &C : CGSCCPipelineParsingCallbacks) if (C(Name, CGPM, InnerPipeline)) - return true; + return Error::success(); // Normal passes can't have pipelines. - return false; + return make_error<StringError>( + formatv("invalid use of '{0}' pass as cgscc pipeline", Name).str(), + inconvertibleErrorCode()); } // Now expand the basic registered passes from the .inc file. #define CGSCC_PASS(NAME, CREATE_PASS) \ if (Name == NAME) { \ CGPM.addPass(CREATE_PASS); \ - return true; \ + return Error::success(); \ } #define CGSCC_ANALYSIS(NAME, CREATE_PASS) \ if (Name == "require<" NAME ">") { \ @@ -1574,24 +1585,26 @@ bool PassBuilder::parseCGSCCPass(CGSCCPassManager &CGPM, std::remove_reference<decltype(CREATE_PASS)>::type, \ LazyCallGraph::SCC, CGSCCAnalysisManager, LazyCallGraph &, \ CGSCCUpdateResult &>()); \ - return true; \ + return Error::success(); \ } \ if (Name == "invalidate<" NAME ">") { \ CGPM.addPass(InvalidateAnalysisPass< \ std::remove_reference<decltype(CREATE_PASS)>::type>()); \ - return true; \ + return Error::success(); \ } #include "PassRegistry.def" for (auto &C : CGSCCPipelineParsingCallbacks) if (C(Name, CGPM, InnerPipeline)) - return true; - return false; + return Error::success(); + return make_error<StringError>( + formatv("unknown cgscc pass '{0}'", Name).str(), + inconvertibleErrorCode()); } -bool PassBuilder::parseFunctionPass(FunctionPassManager &FPM, - const PipelineElement &E, - bool VerifyEachPass, bool DebugLogging) { +Error PassBuilder::parseFunctionPass(FunctionPassManager &FPM, + const PipelineElement &E, + bool VerifyEachPass, bool DebugLogging) { auto &Name = E.Name; auto &InnerPipeline = E.InnerPipeline; @@ -1599,68 +1612,72 @@ bool PassBuilder::parseFunctionPass(FunctionPassManager &FPM, if (!InnerPipeline.empty()) { if (Name == "function") { FunctionPassManager NestedFPM(DebugLogging); - if (!parseFunctionPassPipeline(NestedFPM, InnerPipeline, VerifyEachPass, - DebugLogging)) - return false; + if (auto Err = parseFunctionPassPipeline(NestedFPM, InnerPipeline, + VerifyEachPass, DebugLogging)) + return Err; // Add the nested pass manager with the appropriate adaptor. FPM.addPass(std::move(NestedFPM)); - return true; + return Error::success(); } if (Name == "loop") { LoopPassManager LPM(DebugLogging); - if (!parseLoopPassPipeline(LPM, InnerPipeline, VerifyEachPass, - DebugLogging)) - return false; + if (auto Err = parseLoopPassPipeline(LPM, InnerPipeline, VerifyEachPass, + DebugLogging)) + return Err; // Add the nested pass manager with the appropriate adaptor. FPM.addPass( createFunctionToLoopPassAdaptor(std::move(LPM), DebugLogging)); - return true; + return Error::success(); } if (auto Count = parseRepeatPassName(Name)) { FunctionPassManager NestedFPM(DebugLogging); - if (!parseFunctionPassPipeline(NestedFPM, InnerPipeline, VerifyEachPass, - DebugLogging)) - return false; + if (auto Err = parseFunctionPassPipeline(NestedFPM, InnerPipeline, + VerifyEachPass, DebugLogging)) + return Err; FPM.addPass(createRepeatedPass(*Count, std::move(NestedFPM))); - return true; + return Error::success(); } for (auto &C : FunctionPipelineParsingCallbacks) if (C(Name, FPM, InnerPipeline)) - return true; + return Error::success(); // Normal passes can't have pipelines. - return false; + return make_error<StringError>( + formatv("invalid use of '{0}' pass as function pipeline", Name).str(), + inconvertibleErrorCode()); } // Now expand the basic registered passes from the .inc file. #define FUNCTION_PASS(NAME, CREATE_PASS) \ if (Name == NAME) { \ FPM.addPass(CREATE_PASS); \ - return true; \ + return Error::success(); \ } #define FUNCTION_ANALYSIS(NAME, CREATE_PASS) \ if (Name == "require<" NAME ">") { \ FPM.addPass( \ RequireAnalysisPass< \ std::remove_reference<decltype(CREATE_PASS)>::type, Function>()); \ - return true; \ + return Error::success(); \ } \ if (Name == "invalidate<" NAME ">") { \ FPM.addPass(InvalidateAnalysisPass< \ std::remove_reference<decltype(CREATE_PASS)>::type>()); \ - return true; \ + return Error::success(); \ } #include "PassRegistry.def" for (auto &C : FunctionPipelineParsingCallbacks) if (C(Name, FPM, InnerPipeline)) - return true; - return false; + return Error::success(); + return make_error<StringError>( + formatv("unknown function pass '{0}'", Name).str(), + inconvertibleErrorCode()); } -bool PassBuilder::parseLoopPass(LoopPassManager &LPM, const PipelineElement &E, - bool VerifyEachPass, bool DebugLogging) { +Error PassBuilder::parseLoopPass(LoopPassManager &LPM, const PipelineElement &E, + bool VerifyEachPass, bool DebugLogging) { StringRef Name = E.Name; auto &InnerPipeline = E.InnerPipeline; @@ -1668,35 +1685,37 @@ bool PassBuilder::parseLoopPass(LoopPassManager &LPM, const PipelineElement &E, if (!InnerPipeline.empty()) { if (Name == "loop") { LoopPassManager NestedLPM(DebugLogging); - if (!parseLoopPassPipeline(NestedLPM, InnerPipeline, VerifyEachPass, - DebugLogging)) - return false; + if (auto Err = parseLoopPassPipeline(NestedLPM, InnerPipeline, + VerifyEachPass, DebugLogging)) + return Err; // Add the nested pass manager with the appropriate adaptor. LPM.addPass(std::move(NestedLPM)); - return true; + return Error::success(); } if (auto Count = parseRepeatPassName(Name)) { LoopPassManager NestedLPM(DebugLogging); - if (!parseLoopPassPipeline(NestedLPM, InnerPipeline, VerifyEachPass, - DebugLogging)) - return false; + if (auto Err = parseLoopPassPipeline(NestedLPM, InnerPipeline, + VerifyEachPass, DebugLogging)) + return Err; LPM.addPass(createRepeatedPass(*Count, std::move(NestedLPM))); - return true; + return Error::success(); } for (auto &C : LoopPipelineParsingCallbacks) if (C(Name, LPM, InnerPipeline)) - return true; + return Error::success(); // Normal passes can't have pipelines. - return false; + return make_error<StringError>( + formatv("invalid use of '{0}' pass as loop pipeline", Name).str(), + inconvertibleErrorCode()); } // Now expand the basic registered passes from the .inc file. #define LOOP_PASS(NAME, CREATE_PASS) \ if (Name == NAME) { \ LPM.addPass(CREATE_PASS); \ - return true; \ + return Error::success(); \ } #define LOOP_ANALYSIS(NAME, CREATE_PASS) \ if (Name == "require<" NAME ">") { \ @@ -1704,19 +1723,20 @@ bool PassBuilder::parseLoopPass(LoopPassManager &LPM, const PipelineElement &E, std::remove_reference<decltype(CREATE_PASS)>::type, Loop, \ LoopAnalysisManager, LoopStandardAnalysisResults &, \ LPMUpdater &>()); \ - return true; \ + return Error::success(); \ } \ if (Name == "invalidate<" NAME ">") { \ LPM.addPass(InvalidateAnalysisPass< \ std::remove_reference<decltype(CREATE_PASS)>::type>()); \ - return true; \ + return Error::success(); \ } #include "PassRegistry.def" for (auto &C : LoopPipelineParsingCallbacks) if (C(Name, LPM, InnerPipeline)) - return true; - return false; + return Error::success(); + return make_error<StringError>(formatv("unknown loop pass '{0}'", Name).str(), + inconvertibleErrorCode()); } bool PassBuilder::parseAAPassName(AAManager &AA, StringRef Name) { @@ -1740,41 +1760,42 @@ bool PassBuilder::parseAAPassName(AAManager &AA, StringRef Name) { return false; } -bool PassBuilder::parseLoopPassPipeline(LoopPassManager &LPM, - ArrayRef<PipelineElement> Pipeline, - bool VerifyEachPass, - bool DebugLogging) { +Error PassBuilder::parseLoopPassPipeline(LoopPassManager &LPM, + ArrayRef<PipelineElement> Pipeline, + bool VerifyEachPass, + bool DebugLogging) { for (const auto &Element : Pipeline) { - if (!parseLoopPass(LPM, Element, VerifyEachPass, DebugLogging)) - return false; + if (auto Err = parseLoopPass(LPM, Element, VerifyEachPass, DebugLogging)) + return Err; // FIXME: No verifier support for Loop passes! } - return true; + return Error::success(); } -bool PassBuilder::parseFunctionPassPipeline(FunctionPassManager &FPM, - ArrayRef<PipelineElement> Pipeline, - bool VerifyEachPass, - bool DebugLogging) { +Error PassBuilder::parseFunctionPassPipeline(FunctionPassManager &FPM, + ArrayRef<PipelineElement> Pipeline, + bool VerifyEachPass, + bool DebugLogging) { for (const auto &Element : Pipeline) { - if (!parseFunctionPass(FPM, Element, VerifyEachPass, DebugLogging)) - return false; + if (auto Err = + parseFunctionPass(FPM, Element, VerifyEachPass, DebugLogging)) + return Err; if (VerifyEachPass) FPM.addPass(VerifierPass()); } - return true; + return Error::success(); } -bool PassBuilder::parseCGSCCPassPipeline(CGSCCPassManager &CGPM, - ArrayRef<PipelineElement> Pipeline, - bool VerifyEachPass, - bool DebugLogging) { +Error PassBuilder::parseCGSCCPassPipeline(CGSCCPassManager &CGPM, + ArrayRef<PipelineElement> Pipeline, + bool VerifyEachPass, + bool DebugLogging) { for (const auto &Element : Pipeline) { - if (!parseCGSCCPass(CGPM, Element, VerifyEachPass, DebugLogging)) - return false; + if (auto Err = parseCGSCCPass(CGPM, Element, VerifyEachPass, DebugLogging)) + return Err; // FIXME: No verifier support for CGSCC passes! } - return true; + return Error::success(); } void PassBuilder::crossRegisterProxies(LoopAnalysisManager &LAM, @@ -1790,28 +1811,30 @@ void PassBuilder::crossRegisterProxies(LoopAnalysisManager &LAM, LAM.registerPass([&] { return FunctionAnalysisManagerLoopProxy(FAM); }); } -bool PassBuilder::parseModulePassPipeline(ModulePassManager &MPM, - ArrayRef<PipelineElement> Pipeline, - bool VerifyEachPass, - bool DebugLogging) { +Error PassBuilder::parseModulePassPipeline(ModulePassManager &MPM, + ArrayRef<PipelineElement> Pipeline, + bool VerifyEachPass, + bool DebugLogging) { for (const auto &Element : Pipeline) { - if (!parseModulePass(MPM, Element, VerifyEachPass, DebugLogging)) - return false; + if (auto Err = parseModulePass(MPM, Element, VerifyEachPass, DebugLogging)) + return Err; if (VerifyEachPass) MPM.addPass(VerifierPass()); } - return true; + return Error::success(); } // Primary pass pipeline description parsing routine for a \c ModulePassManager // FIXME: Should this routine accept a TargetMachine or require the caller to // pre-populate the analysis managers with target-specific stuff? -bool PassBuilder::parsePassPipeline(ModulePassManager &MPM, - StringRef PipelineText, bool VerifyEachPass, - bool DebugLogging) { +Error PassBuilder::parsePassPipeline(ModulePassManager &MPM, + StringRef PipelineText, + bool VerifyEachPass, bool DebugLogging) { auto Pipeline = parsePipelineText(PipelineText); if (!Pipeline || Pipeline->empty()) - return false; + return make_error<StringError>( + formatv("invalid pipeline '{0}'", PipelineText).str(), + inconvertibleErrorCode()); // If the first name isn't at the module layer, wrap the pipeline up // automatically. @@ -1828,73 +1851,106 @@ bool PassBuilder::parsePassPipeline(ModulePassManager &MPM, } else { for (auto &C : TopLevelPipelineParsingCallbacks) if (C(MPM, *Pipeline, VerifyEachPass, DebugLogging)) - return true; - - // Unknown pass name! - return false; + return Error::success(); + + // Unknown pass or pipeline name! + auto &InnerPipeline = Pipeline->front().InnerPipeline; + return make_error<StringError>( + formatv("unknown {0} name '{1}'", + (InnerPipeline.empty() ? "pass" : "pipeline"), FirstName) + .str(), + inconvertibleErrorCode()); } } - return parseModulePassPipeline(MPM, *Pipeline, VerifyEachPass, DebugLogging); + if (auto Err = + parseModulePassPipeline(MPM, *Pipeline, VerifyEachPass, DebugLogging)) + return Err; + return Error::success(); } // Primary pass pipeline description parsing routine for a \c CGSCCPassManager -bool PassBuilder::parsePassPipeline(CGSCCPassManager &CGPM, - StringRef PipelineText, bool VerifyEachPass, - bool DebugLogging) { +Error PassBuilder::parsePassPipeline(CGSCCPassManager &CGPM, + StringRef PipelineText, + bool VerifyEachPass, bool DebugLogging) { auto Pipeline = parsePipelineText(PipelineText); if (!Pipeline || Pipeline->empty()) - return false; + return make_error<StringError>( + formatv("invalid pipeline '{0}'", PipelineText).str(), + inconvertibleErrorCode()); StringRef FirstName = Pipeline->front().Name; if (!isCGSCCPassName(FirstName, CGSCCPipelineParsingCallbacks)) - return false; - - return parseCGSCCPassPipeline(CGPM, *Pipeline, VerifyEachPass, DebugLogging); + return make_error<StringError>( + formatv("unknown cgscc pass '{0}' in pipeline '{1}'", FirstName, + PipelineText) + .str(), + inconvertibleErrorCode()); + + if (auto Err = + parseCGSCCPassPipeline(CGPM, *Pipeline, VerifyEachPass, DebugLogging)) + return Err; + return Error::success(); } // Primary pass pipeline description parsing routine for a \c // FunctionPassManager -bool PassBuilder::parsePassPipeline(FunctionPassManager &FPM, - StringRef PipelineText, bool VerifyEachPass, - bool DebugLogging) { +Error PassBuilder::parsePassPipeline(FunctionPassManager &FPM, + StringRef PipelineText, + bool VerifyEachPass, bool DebugLogging) { auto Pipeline = parsePipelineText(PipelineText); if (!Pipeline || Pipeline->empty()) - return false; + return make_error<StringError>( + formatv("invalid pipeline '{0}'", PipelineText).str(), + inconvertibleErrorCode()); StringRef FirstName = Pipeline->front().Name; if (!isFunctionPassName(FirstName, FunctionPipelineParsingCallbacks)) - return false; - - return parseFunctionPassPipeline(FPM, *Pipeline, VerifyEachPass, - DebugLogging); + return make_error<StringError>( + formatv("unknown function pass '{0}' in pipeline '{1}'", FirstName, + PipelineText) + .str(), + inconvertibleErrorCode()); + + if (auto Err = parseFunctionPassPipeline(FPM, *Pipeline, VerifyEachPass, + DebugLogging)) + return Err; + return Error::success(); } // Primary pass pipeline description parsing routine for a \c LoopPassManager -bool PassBuilder::parsePassPipeline(LoopPassManager &CGPM, - StringRef PipelineText, bool VerifyEachPass, - bool DebugLogging) { +Error PassBuilder::parsePassPipeline(LoopPassManager &CGPM, + StringRef PipelineText, + bool VerifyEachPass, bool DebugLogging) { auto Pipeline = parsePipelineText(PipelineText); if (!Pipeline || Pipeline->empty()) - return false; + return make_error<StringError>( + formatv("invalid pipeline '{0}'", PipelineText).str(), + inconvertibleErrorCode()); - return parseLoopPassPipeline(CGPM, *Pipeline, VerifyEachPass, DebugLogging); + if (auto Err = + parseLoopPassPipeline(CGPM, *Pipeline, VerifyEachPass, DebugLogging)) + return Err; + + return Error::success(); } -bool PassBuilder::parseAAPipeline(AAManager &AA, StringRef PipelineText) { +Error PassBuilder::parseAAPipeline(AAManager &AA, StringRef PipelineText) { // If the pipeline just consists of the word 'default' just replace the AA // manager with our default one. if (PipelineText == "default") { AA = buildDefaultAAPipeline(); - return true; + return Error::success(); } while (!PipelineText.empty()) { StringRef Name; std::tie(Name, PipelineText) = PipelineText.split(','); if (!parseAAPassName(AA, Name)) - return false; + return make_error<StringError>( + formatv("unknown alias analysis name '{0}'", Name).str(), + inconvertibleErrorCode()); } - return true; + return Error::success(); } |