https://github.com/MaskRay updated https://github.com/llvm/llvm-project/pull/237615
>From d8f86cee73312aabfe7cded264b005a95e4547f7 Mon Sep 17 00:00:00 2001 From: Fangrui Song <[email protected]> Date: Sat, 31 Oct 2026 12:20:12 -0700 Subject: [PATCH 1/2] [Passes] Make PipelineTuningOptions take a LibraryOptionsContext reference Delete the default ctor, which reads the global values of library options. Make the constructor and the getters it calls take a reference. lto::Config::PTO becomes std::optional. If unset, the LTO backend reads the tuning options from the module's LLVMContext. LLVMPassBuilderOptions reads cl::getCAPILibraryOptions(), which LLVMParseCommandLineOptions sets along with the global values. LLM-aided --- clang/lib/CodeGen/BackendUtil.cpp | 18 +++++++++--------- .../ClangNVLinkWrapper.cpp | 2 +- flang/lib/Frontend/FrontendActions.cpp | 2 +- lld/COFF/LTO.cpp | 6 +++--- lld/ELF/LTO.cpp | 6 +++--- lld/MachO/LTO.cpp | 6 +++--- lld/wasm/LTO.cpp | 2 +- llvm/include/llvm/Analysis/CallGraphSCCPass.h | 2 +- llvm/include/llvm/LTO/Config.h | 5 +++-- llvm/include/llvm/Passes/PassBuilder.h | 11 +++-------- llvm/include/llvm/Transforms/Scalar/LICM.h | 10 ++++------ .../llvm/Transforms/Scalar/LoopUnrollPass.h | 5 ++--- llvm/lib/Analysis/CallGraphSCCPass.cpp | 5 ++--- llvm/lib/DTLTO/DTLTO.cpp | 2 +- llvm/lib/LTO/LTOCodeGenerator.cpp | 6 +++--- llvm/lib/LTO/ThinLTOCodeGenerator.cpp | 2 +- llvm/lib/Passes/PassBuilder.cpp | 2 +- llvm/lib/Passes/PassBuilderBindings.cpp | 4 +++- llvm/lib/Passes/PassBuilderPipelines.cpp | 5 ++--- llvm/lib/Passes/RunCodeGen.cpp | 2 +- llvm/lib/Transforms/Scalar/LICM.cpp | 10 ++++------ llvm/lib/Transforms/Scalar/LoopUnrollPass.cpp | 5 ++--- llvm/tools/gold/gold-plugin.cpp | 10 +++++----- llvm/tools/llvm-lto2/llvm-lto2.cpp | 6 +++--- llvm/tools/opt/NewPMDriver.cpp | 2 +- mlir/lib/ExecutionEngine/OptUtils.cpp | 2 +- 26 files changed, 64 insertions(+), 74 deletions(-) diff --git a/clang/lib/CodeGen/BackendUtil.cpp b/clang/lib/CodeGen/BackendUtil.cpp index fe1454026f569d..d56185146f63df 100644 --- a/clang/lib/CodeGen/BackendUtil.cpp +++ b/clang/lib/CodeGen/BackendUtil.cpp @@ -903,7 +903,7 @@ void EmitAssemblyHelper::RunOptimizationPipeline( if (TM) TM->setPGOOption(PGOOpt); - PipelineTuningOptions PTO(&LibraryOptions); + PipelineTuningOptions PTO(LibraryOptions); PTO.LoopUnrolling = CodeGenOpts.UnrollLoops; PTO.LoopInterchange = CodeGenOpts.InterchangeLoops; PTO.LoopFusion = CodeGenOpts.FuseLoops; @@ -1380,18 +1380,18 @@ runThinLTOBackend(CompilerInstance &CI, ModuleSummaryIndex *CombinedIndex, Conf.SampleProfile = std::move(SampleProfile); const cl::LibraryOptionsContext &LibraryOptions = M->getContext().getLibraryOptions(); - Conf.PTO = PipelineTuningOptions(&LibraryOptions); - Conf.PTO.LoopUnrolling = CGOpts.UnrollLoops; - Conf.PTO.LoopInterchange = CGOpts.InterchangeLoops; - Conf.PTO.LoopFusion = CGOpts.FuseLoops; + Conf.PTO.emplace(LibraryOptions); + Conf.PTO->LoopUnrolling = CGOpts.UnrollLoops; + Conf.PTO->LoopInterchange = CGOpts.InterchangeLoops; + Conf.PTO->LoopFusion = CGOpts.FuseLoops; // For historical reasons, loop interleaving is set to mirror setting for loop // unrolling. - Conf.PTO.LoopInterleaving = CGOpts.UnrollLoops; - Conf.PTO.LoopVectorization = CGOpts.VectorizeLoop; - Conf.PTO.SLPVectorization = CGOpts.VectorizeSLP; + Conf.PTO->LoopInterleaving = CGOpts.UnrollLoops; + Conf.PTO->LoopVectorization = CGOpts.VectorizeLoop; + Conf.PTO->SLPVectorization = CGOpts.VectorizeSLP; // Only enable CGProfilePass when using integrated assembler, since // non-integrated assemblers don't recognize .cgprofile section. - Conf.PTO.CallGraphProfile = !CGOpts.DisableIntegratedAS; + Conf.PTO->CallGraphProfile = !CGOpts.DisableIntegratedAS; // Context sensitive profile. if (CGOpts.hasProfileCSIRInstr()) { diff --git a/clang/tools/clang-nvlink-wrapper/ClangNVLinkWrapper.cpp b/clang/tools/clang-nvlink-wrapper/ClangNVLinkWrapper.cpp index 6550902a6a6551..e0803212092a0b 100644 --- a/clang/tools/clang-nvlink-wrapper/ClangNVLinkWrapper.cpp +++ b/clang/tools/clang-nvlink-wrapper/ClangNVLinkWrapper.cpp @@ -376,7 +376,7 @@ createLTO(const cl::LibraryOptionsContext &LibraryOptions, const llvm::Triple Triple("nvptx64-nvidia-cuda"); lto::Config Conf; Conf.LibraryOptions = &LibraryOptions; - Conf.PTO = PipelineTuningOptions(&LibraryOptions); + Conf.PTO.emplace(LibraryOptions); lto::ThinBackend Backend; unsigned Jobs = 0; if (auto *Arg = Args.getLastArg(OPT_jobs)) diff --git a/flang/lib/Frontend/FrontendActions.cpp b/flang/lib/Frontend/FrontendActions.cpp index 823b437d6e83fc..d497d4d6278ddd 100644 --- a/flang/lib/Frontend/FrontendActions.cpp +++ b/flang/lib/Frontend/FrontendActions.cpp @@ -966,7 +966,7 @@ void CodeGenAction::runOptimizationPipeline(llvm::raw_pwrite_stream &os) { llvm::PassInstrumentationCallbacks pic; const llvm::cl::LibraryOptionsContext &libraryOptions = llvmModule->getContext().getLibraryOptions(); - llvm::PipelineTuningOptions pto(&libraryOptions); + llvm::PipelineTuningOptions pto(libraryOptions); std::optional<llvm::PGOOptions> pgoOpt; if (opts.hasProfileIRInstr()) { diff --git a/lld/COFF/LTO.cpp b/lld/COFF/LTO.cpp index 20209019a3e6fe..17fda23f63d4b6 100644 --- a/lld/COFF/LTO.cpp +++ b/lld/COFF/LTO.cpp @@ -57,7 +57,7 @@ std::string BitcodeCompiler::getThinLTOOutputFile(StringRef path) { lto::Config BitcodeCompiler::createConfig() { lto::Config c; c.LibraryOptions = &ctx.config.libraryOptions; - c.PTO = PipelineTuningOptions(c.LibraryOptions); + c.PTO.emplace(*c.LibraryOptions); c.Options = initTargetOptionsFromCodeGenFlags(); c.Options.EmitAddrsig = true; for (StringRef C : ctx.config.mllvmOpts) @@ -120,8 +120,8 @@ lto::Config BitcodeCompiler::createConfig() { /*UseInputModulePath*/ true, ctx.config.saveTempsArgs)); - c.PTO.LoopVectorization = c.OptLevel > 1; - c.PTO.SLPVectorization = c.OptLevel > 1; + c.PTO->LoopVectorization = c.OptLevel > 1; + c.PTO->SLPVectorization = c.OptLevel > 1; return c; } diff --git a/lld/ELF/LTO.cpp b/lld/ELF/LTO.cpp index 0fa5673ed0f25b..96d14a65d57cea 100644 --- a/lld/ELF/LTO.cpp +++ b/lld/ELF/LTO.cpp @@ -56,7 +56,7 @@ static std::string getThinLTOOutputFile(Ctx &ctx, StringRef modulePath) { static lto::Config createConfig(Ctx &ctx) { lto::Config c; c.LibraryOptions = &ctx.arg.libraryOptions; - c.PTO = PipelineTuningOptions(c.LibraryOptions); + c.PTO.emplace(*c.LibraryOptions); // LLD supports the new relocations and address-significance tables. c.Options = initTargetOptionsFromCodeGenFlags(); @@ -117,8 +117,8 @@ static lto::Config createConfig(Ctx &ctx) { c.MAttrs = getMAttrs(); c.CGOptLevel = ctx.arg.ltoCgo; - c.PTO.LoopVectorization = c.OptLevel > 1; - c.PTO.SLPVectorization = c.OptLevel > 1; + c.PTO->LoopVectorization = c.OptLevel > 1; + c.PTO->SLPVectorization = c.OptLevel > 1; // Set up a custom pipeline if we've been asked to. c.OptPipeline = std::string(ctx.arg.ltoNewPmPasses); diff --git a/lld/MachO/LTO.cpp b/lld/MachO/LTO.cpp index 8eb008c990fe6c..7c5187b2a5f960 100644 --- a/lld/MachO/LTO.cpp +++ b/lld/MachO/LTO.cpp @@ -39,7 +39,7 @@ static std::string getThinLTOOutputFile(StringRef modulePath) { static lto::Config createConfig() { lto::Config c; c.LibraryOptions = &config->libraryOptions; - c.PTO = PipelineTuningOptions(c.LibraryOptions); + c.PTO.emplace(*c.LibraryOptions); c.Options = initTargetOptionsFromCodeGenFlags(); c.Options.EmitAddrsig = config->icfLevel == ICFLevel::safe || config->icfLevel == ICFLevel::safe_thunks; @@ -65,8 +65,8 @@ static lto::Config createConfig() { c.OptLevel = config->ltoo; c.CGOptLevel = config->ltoCgo; - c.PTO.LoopVectorization = c.OptLevel > 1; - c.PTO.SLPVectorization = c.OptLevel > 1; + c.PTO->LoopVectorization = c.OptLevel > 1; + c.PTO->SLPVectorization = c.OptLevel > 1; if (config->saveTemps) checkError(c.addSaveTemps(config->outputFile.str() + ".", diff --git a/lld/wasm/LTO.cpp b/lld/wasm/LTO.cpp index 8bafd95a258688..0c158058e93725 100644 --- a/lld/wasm/LTO.cpp +++ b/lld/wasm/LTO.cpp @@ -43,7 +43,7 @@ static std::string getThinLTOOutputFile(StringRef modulePath) { static lto::Config createConfig() { lto::Config c; c.LibraryOptions = &ctx.arg.libraryOptions; - c.PTO = PipelineTuningOptions(c.LibraryOptions); + c.PTO.emplace(*c.LibraryOptions); c.Options = initTargetOptionsFromCodeGenFlags(); // Always emit a section per function/data with LTO. diff --git a/llvm/include/llvm/Analysis/CallGraphSCCPass.h b/llvm/include/llvm/Analysis/CallGraphSCCPass.h index a9042a43fec700..68c0277e9fb63d 100644 --- a/llvm/include/llvm/Analysis/CallGraphSCCPass.h +++ b/llvm/include/llvm/Analysis/CallGraphSCCPass.h @@ -35,7 +35,7 @@ namespace cl { class LibraryOptionsContext; } // namespace cl -LLVM_ABI unsigned getMaxDevirtIterations(const cl::LibraryOptionsContext *); +LLVM_ABI unsigned getMaxDevirtIterations(const cl::LibraryOptionsContext &); class LLVM_ABI CallGraphSCCPass : public Pass { public: diff --git a/llvm/include/llvm/LTO/Config.h b/llvm/include/llvm/LTO/Config.h index 60cb2a08c0381b..916875068d8e5e 100644 --- a/llvm/include/llvm/LTO/Config.h +++ b/llvm/include/llvm/LTO/Config.h @@ -211,8 +211,9 @@ struct Config { /// with llvm-lto2. std::unique_ptr<raw_ostream> ResolutionFile; - /// Tunable parameters for passes in the default pipelines. - PipelineTuningOptions PTO; + /// Tunable parameters for passes in the default pipelines. If unset, the + /// backend reads them from the module's LLVMContext. + std::optional<PipelineTuningOptions> PTO; /// The following callbacks deal with tasks, which normally represent the /// entire optimization and code generation pipeline for what will become a diff --git a/llvm/include/llvm/Passes/PassBuilder.h b/llvm/include/llvm/Passes/PassBuilder.h index 3512c9c9a9ca29..c5fbb5a064d0be 100644 --- a/llvm/include/llvm/Passes/PassBuilder.h +++ b/llvm/include/llvm/Passes/PassBuilder.h @@ -45,15 +45,10 @@ class LibraryOptionsContext; /// Tunable parameters for passes in the default pipelines. class PipelineTuningOptions { public: - /// Constructor sets pipeline tuning defaults based on the global values of - /// the library options. Each option can be set in the PassBuilder when using - /// a LLVM as a library. - PipelineTuningOptions() : PipelineTuningOptions(nullptr) {} - - /// Reads the defaults from \p LibraryOptions, or their global values if - /// null. + /// Reads the defaults from \p LibraryOptions. Each option can be set in the + /// PassBuilder when using LLVM as a library. LLVM_ABI explicit PipelineTuningOptions( - const cl::LibraryOptionsContext *LibraryOptions); + const cl::LibraryOptionsContext &LibraryOptions); /// Tuning option to set loop interleaving on/off, set based on opt level. bool LoopInterleaving; diff --git a/llvm/include/llvm/Transforms/Scalar/LICM.h b/llvm/include/llvm/Transforms/Scalar/LICM.h index 7eb460e7b33599..379dbd2152a308 100644 --- a/llvm/include/llvm/Transforms/Scalar/LICM.h +++ b/llvm/include/llvm/Transforms/Scalar/LICM.h @@ -45,14 +45,12 @@ namespace cl { class LibraryOptionsContext; } // namespace cl -/// Returns -licm-mssa-optimization-cap of LibraryOptions, or its global value -/// if null. +/// Return -licm-mssa-optimization-cap. LLVM_ABI unsigned -getLicmMssaOptCap(const cl::LibraryOptionsContext *LibraryOptions); -/// Returns -licm-mssa-max-acc-promotion of LibraryOptions, or its global value -/// if null. +getLicmMssaOptCap(const cl::LibraryOptionsContext &LibraryOptions); +/// Return -licm-mssa-max-acc-promotion. LLVM_ABI unsigned getLicmMssaNoAccForPromotionCap( - const cl::LibraryOptionsContext *LibraryOptions); + const cl::LibraryOptionsContext &LibraryOptions); struct LICMOptions { // Unset means the -licm-mssa-* value of the loop's LLVMContext. diff --git a/llvm/include/llvm/Transforms/Scalar/LoopUnrollPass.h b/llvm/include/llvm/Transforms/Scalar/LoopUnrollPass.h index 7955d8f79dc5c0..f2e50353b9b42e 100644 --- a/llvm/include/llvm/Transforms/Scalar/LoopUnrollPass.h +++ b/llvm/include/llvm/Transforms/Scalar/LoopUnrollPass.h @@ -19,10 +19,9 @@ namespace cl { class LibraryOptionsContext; } // namespace cl -/// Returns -forget-scev-loop-unroll of LibraryOptions, or its global value if -/// null. +/// Return -forget-scev-loop-unroll. LLVM_ABI bool -getForgetSCEVInLoopUnroll(const cl::LibraryOptionsContext *LibraryOptions); +getForgetSCEVInLoopUnroll(const cl::LibraryOptionsContext &LibraryOptions); class Function; class Loop; diff --git a/llvm/lib/Analysis/CallGraphSCCPass.cpp b/llvm/lib/Analysis/CallGraphSCCPass.cpp index ba120b245275df..bff6aee0cad972 100644 --- a/llvm/lib/Analysis/CallGraphSCCPass.cpp +++ b/llvm/lib/Analysis/CallGraphSCCPass.cpp @@ -44,9 +44,8 @@ using namespace llvm; #define DEBUG_TYPE "cgscc-passmgr" unsigned -llvm::getMaxDevirtIterations(const cl::LibraryOptionsContext *LibraryOptions) { - return cl::LibraryOptionsContext::get<AnalysisOptions>(LibraryOptions) - .max_devirt_iterations; +llvm::getMaxDevirtIterations(const cl::LibraryOptionsContext &LibraryOptions) { + return LibraryOptions.get<AnalysisOptions>().max_devirt_iterations; } STATISTIC(MaxSCCIterations, "Maximum CGSCCPassMgr iterations on one SCC"); diff --git a/llvm/lib/DTLTO/DTLTO.cpp b/llvm/lib/DTLTO/DTLTO.cpp index 669ba75c80d4b6..dc103d3d461cc8 100644 --- a/llvm/lib/DTLTO/DTLTO.cpp +++ b/llvm/lib/DTLTO/DTLTO.cpp @@ -226,7 +226,7 @@ void lto::DTLTO::buildCommonRemoteCompilerOptions() { Ops.push_back("-ffunction-sections"); if (C.Options.DataSections) Ops.push_back("-fdata-sections"); - if (C.PTO.LoopInterchange) + if (C.PTO && C.PTO->LoopInterchange) Ops.push_back("-floop-interchange"); if (C.RelocModel == Reloc::PIC_) diff --git a/llvm/lib/LTO/LTOCodeGenerator.cpp b/llvm/lib/LTO/LTOCodeGenerator.cpp index ad58b4fc3cf239..fe34c24975dc1e 100644 --- a/llvm/lib/LTO/LTOCodeGenerator.cpp +++ b/llvm/lib/LTO/LTOCodeGenerator.cpp @@ -564,9 +564,9 @@ bool LTOCodeGenerator::optimize() { Config.RunCSIRInstr = LTORunCSIRInstr; Config.CSIRProfile = LTOCSIRProfile; Config.SampleProfile = SampleProfileFile; - Config.PTO = PipelineTuningOptions(Config.LibraryOptions); - Config.PTO.LoopVectorization = Config.OptLevel > 1; - Config.PTO.SLPVectorization = Config.OptLevel > 1; + Config.PTO.emplace(*Config.LibraryOptions); + Config.PTO->LoopVectorization = Config.OptLevel > 1; + Config.PTO->SLPVectorization = Config.OptLevel > 1; auto DiagFileOrErr = lto::setupLLVMOptimizationRemarks( Context, RemarksFilename, RemarksPasses, RemarksFormat, diff --git a/llvm/lib/LTO/ThinLTOCodeGenerator.cpp b/llvm/lib/LTO/ThinLTOCodeGenerator.cpp index 13e4c7bb5fc6f6..0709b8b0724f7c 100644 --- a/llvm/lib/LTO/ThinLTOCodeGenerator.cpp +++ b/llvm/lib/LTO/ThinLTOCodeGenerator.cpp @@ -261,7 +261,7 @@ static void optimizeModule(Module &TheModule, TargetMachine &TM, PassInstrumentationCallbacks PIC; StandardInstrumentations SI(TheModule.getContext(), DebugPassManager); SI.registerCallbacks(PIC, &MAM); - PipelineTuningOptions PTO(&TheModule.getContext().getLibraryOptions()); + PipelineTuningOptions PTO(TheModule.getContext().getLibraryOptions()); PTO.LoopVectorization = true; PTO.SLPVectorization = true; PassBuilder PB(TheModule.getContext(), &TM, PTO, PGOOpt, &PIC); diff --git a/llvm/lib/Passes/PassBuilder.cpp b/llvm/lib/Passes/PassBuilder.cpp index 4e9a38be994505..db933577e3d35f 100644 --- a/llvm/lib/Passes/PassBuilder.cpp +++ b/llvm/lib/Passes/PassBuilder.cpp @@ -573,7 +573,7 @@ PassBuilder::PassBuilder(LLVMContext &Context, TargetMachine *TM, PassInstrumentationCallbacks *PIC, IntrusiveRefCntPtr<vfs::FileSystem> FS) : Context(Context), Opts(getPassesOptions(Context)), TM(TM), - PTO(PTO ? *PTO : PipelineTuningOptions(&Context.getLibraryOptions())), + PTO(PTO ? *PTO : PipelineTuningOptions(Context.getLibraryOptions())), PGOOpt(PGOOpt), PIC(PIC), FS(std::move(FS)) { if (TM) TM->registerPassBuilderCallbacks(*this); diff --git a/llvm/lib/Passes/PassBuilderBindings.cpp b/llvm/lib/Passes/PassBuilderBindings.cpp index d9f2f887c6467d..1fe73932ed0f5f 100644 --- a/llvm/lib/Passes/PassBuilderBindings.cpp +++ b/llvm/lib/Passes/PassBuilderBindings.cpp @@ -18,6 +18,7 @@ #include "llvm/Passes/PassBuilder.h" #include "llvm/Passes/StandardInstrumentations.h" #include "llvm/Support/CBindingWrapping.h" +#include "llvm/Support/CommandLine.h" using namespace llvm; @@ -30,7 +31,8 @@ class LLVMPassBuilderOptions { explicit LLVMPassBuilderOptions( bool DebugLogging = false, bool VerifyEach = false, const char *AAPipeline = nullptr, - PipelineTuningOptions PTO = PipelineTuningOptions()) + PipelineTuningOptions PTO = + PipelineTuningOptions(cl::getCAPILibraryOptions())) : DebugLogging(DebugLogging), VerifyEach(VerifyEach), AAPipeline(AAPipeline), PTO(PTO) {} diff --git a/llvm/lib/Passes/PassBuilderPipelines.cpp b/llvm/lib/Passes/PassBuilderPipelines.cpp index 1987ceb6b06c02..c8235d14e22099 100644 --- a/llvm/lib/Passes/PassBuilderPipelines.cpp +++ b/llvm/lib/Passes/PassBuilderPipelines.cpp @@ -171,9 +171,8 @@ extern cl::opt<bool> EnableProfcheckInPipeline; } // namespace llvm PipelineTuningOptions::PipelineTuningOptions( - const cl::LibraryOptionsContext *LibraryOptions) { - const PassesOptions &Opts = - cl::LibraryOptionsContext::get<PassesOptions>(LibraryOptions); + const cl::LibraryOptionsContext &LibraryOptions) { + const PassesOptions &Opts = LibraryOptions.get<PassesOptions>(); LoopInterleaving = true; LoopVectorization = true; SLPVectorization = false; diff --git a/llvm/lib/Passes/RunCodeGen.cpp b/llvm/lib/Passes/RunCodeGen.cpp index 67aecdb6f5494c..c64f387ab61654 100644 --- a/llvm/lib/Passes/RunCodeGen.cpp +++ b/llvm/lib/Passes/RunCodeGen.cpp @@ -66,7 +66,7 @@ static Error runCodeGenPipelineNewPM(TargetMachine &TM, Module &M, MachineModuleInfo MMI(&TM); PassInstrumentationCallbacks PIC; const auto &LibraryOptions = M.getContext().getLibraryOptions(); - PipelineTuningOptions PTOptions(&LibraryOptions); + PipelineTuningOptions PTOptions(LibraryOptions); PassBuilder PB(M.getContext(), &TM, PTOptions, std::nullopt, &PIC, VFS); PB.registerModuleAnalyses(MAM); PB.registerCGSCCAnalyses(CGAM); diff --git a/llvm/lib/Transforms/Scalar/LICM.cpp b/llvm/lib/Transforms/Scalar/LICM.cpp index df0f7eda307d31..beacb150e56287 100644 --- a/llvm/lib/Transforms/Scalar/LICM.cpp +++ b/llvm/lib/Transforms/Scalar/LICM.cpp @@ -117,15 +117,13 @@ STATISTIC(NumBOAssociationsHoisted, "Number of invariant BinaryOp expressions " "reassociated and hoisted out of the loop"); unsigned -llvm::getLicmMssaOptCap(const cl::LibraryOptionsContext *LibraryOptions) { - return cl::LibraryOptionsContext::get<ScalarOptions>(LibraryOptions) - .licm_mssa_optimization_cap; +llvm::getLicmMssaOptCap(const cl::LibraryOptionsContext &LibraryOptions) { + return LibraryOptions.get<ScalarOptions>().licm_mssa_optimization_cap; } unsigned llvm::getLicmMssaNoAccForPromotionCap( - const cl::LibraryOptionsContext *LibraryOptions) { - return cl::LibraryOptionsContext::get<ScalarOptions>(LibraryOptions) - .licm_mssa_max_acc_promotion; + const cl::LibraryOptionsContext &LibraryOptions) { + return LibraryOptions.get<ScalarOptions>().licm_mssa_max_acc_promotion; } static bool inSubLoop(BasicBlock *BB, Loop *CurLoop, LoopInfo *LI); diff --git a/llvm/lib/Transforms/Scalar/LoopUnrollPass.cpp b/llvm/lib/Transforms/Scalar/LoopUnrollPass.cpp index d21de774096345..a68cd506eecfe3 100644 --- a/llvm/lib/Transforms/Scalar/LoopUnrollPass.cpp +++ b/llvm/lib/Transforms/Scalar/LoopUnrollPass.cpp @@ -75,9 +75,8 @@ using namespace llvm; #define DEBUG_TYPE "loop-unroll" bool llvm::getForgetSCEVInLoopUnroll( - const cl::LibraryOptionsContext *LibraryOptions) { - return cl::LibraryOptionsContext::get<ScalarOptions>(LibraryOptions) - .forget_scev_loop_unroll; + const cl::LibraryOptionsContext &LibraryOptions) { + return LibraryOptions.get<ScalarOptions>().forget_scev_loop_unroll; } /// A magic value for use with the Threshold parameter to indicate diff --git a/llvm/tools/gold/gold-plugin.cpp b/llvm/tools/gold/gold-plugin.cpp index 17bdac650512cf..f95f4ef05f5687 100644 --- a/llvm/tools/gold/gold-plugin.cpp +++ b/llvm/tools/gold/gold-plugin.cpp @@ -902,11 +902,11 @@ createLTO(const cl::LibraryOptionsContext &LibraryOptions, Conf.CGOptLevel = *CGOptLevelOrNone; Conf.DisableVerify = options::DisableVerify; Conf.OptLevel = options::OptLevel; - Conf.PTO = PipelineTuningOptions(&LibraryOptions); - Conf.PTO.LoopVectorization = options::OptLevel > 1; - Conf.PTO.SLPVectorization = options::OptLevel > 1; - Conf.PTO.MergeFunctions = options::merge_functions; - Conf.PTO.UnifiedLTO = options::unifiedlto; + Conf.PTO.emplace(LibraryOptions); + Conf.PTO->LoopVectorization = options::OptLevel > 1; + Conf.PTO->SLPVectorization = options::OptLevel > 1; + Conf.PTO->MergeFunctions = options::merge_functions; + Conf.PTO->UnifiedLTO = options::unifiedlto; Conf.AlwaysEmitRegularLTOObj = !options::obj_path.empty(); if (options::thinlto_index_only) { diff --git a/llvm/tools/llvm-lto2/llvm-lto2.cpp b/llvm/tools/llvm-lto2/llvm-lto2.cpp index 8cf21ef909b740..b4cf1dbf7f7783 100644 --- a/llvm/tools/llvm-lto2/llvm-lto2.cpp +++ b/llvm/tools/llvm-lto2/llvm-lto2.cpp @@ -346,7 +346,7 @@ static int run(int argc, char **argv) { Config Conf; Conf.LibraryOptions = &LibraryOptions; - Conf.PTO = PipelineTuningOptions(&LibraryOptions); + Conf.PTO.emplace(LibraryOptions); if (TimeTrace) { Conf.TimeTraceEnabled = TimeTrace; Conf.TimeTraceGranularity = TimeTraceGranularity; @@ -408,8 +408,8 @@ static int run(int argc, char **argv) { Conf.OverrideTriple = OverrideTriple; Conf.DefaultTriple = DefaultTriple; Conf.StatsFile = StatsFile; - Conf.PTO.LoopVectorization = Conf.OptLevel > 1; - Conf.PTO.SLPVectorization = Conf.OptLevel > 1; + Conf.PTO->LoopVectorization = Conf.OptLevel > 1; + Conf.PTO->SLPVectorization = Conf.OptLevel > 1; if (WholeProgramVisibilityEnabledInLTO.getNumOccurrences() > 0) Conf.HasWholeProgramVisibility = WholeProgramVisibilityEnabledInLTO; diff --git a/llvm/tools/opt/NewPMDriver.cpp b/llvm/tools/opt/NewPMDriver.cpp index 22899f4eb8ccbb..667cbf8c3c0538 100644 --- a/llvm/tools/opt/NewPMDriver.cpp +++ b/llvm/tools/opt/NewPMDriver.cpp @@ -473,7 +473,7 @@ bool llvm::runPassPipeline( Debugify.registerCallbacks(PIC, MAM); } - PipelineTuningOptions PTO(&M.getContext().getLibraryOptions()); + PipelineTuningOptions PTO(M.getContext().getLibraryOptions()); // LoopUnrolling defaults on to true and DisableLoopUnrolling is initialized // to false above so we shouldn't necessarily need to check whether or not the // option has been enabled. diff --git a/mlir/lib/ExecutionEngine/OptUtils.cpp b/mlir/lib/ExecutionEngine/OptUtils.cpp index 2e2f36a35c1afc..003d5af6764cbd 100644 --- a/mlir/lib/ExecutionEngine/OptUtils.cpp +++ b/mlir/lib/ExecutionEngine/OptUtils.cpp @@ -60,7 +60,7 @@ mlir::makeOptimizingTransformer(unsigned optLevel, unsigned sizeLevel, CGSCCAnalysisManager cgam; ModuleAnalysisManager mam; - PipelineTuningOptions tuningOptions(&m->getContext().getLibraryOptions()); + PipelineTuningOptions tuningOptions(m->getContext().getLibraryOptions()); tuningOptions.LoopUnrolling = true; tuningOptions.LoopInterleaving = true; tuningOptions.LoopVectorization = true; >From d9e78875d44d532fe19d3e8e563e96528b3b7630 Mon Sep 17 00:00:00 2001 From: Fangrui Song <[email protected]> Date: Sat, 31 Oct 2026 12:26:55 -0700 Subject: [PATCH 2/2] simplify --- clang/lib/CodeGen/BackendUtil.cpp | 16 ++++++++-------- .../clang-nvlink-wrapper/ClangNVLinkWrapper.cpp | 1 - lld/wasm/LTO.cpp | 1 - llvm/lib/DTLTO/DTLTO.cpp | 8 +++++++- llvm/tools/gold/gold-plugin.cpp | 10 +++++----- 5 files changed, 20 insertions(+), 16 deletions(-) diff --git a/clang/lib/CodeGen/BackendUtil.cpp b/clang/lib/CodeGen/BackendUtil.cpp index d56185146f63df..249755e937f2f9 100644 --- a/clang/lib/CodeGen/BackendUtil.cpp +++ b/clang/lib/CodeGen/BackendUtil.cpp @@ -1380,18 +1380,18 @@ runThinLTOBackend(CompilerInstance &CI, ModuleSummaryIndex *CombinedIndex, Conf.SampleProfile = std::move(SampleProfile); const cl::LibraryOptionsContext &LibraryOptions = M->getContext().getLibraryOptions(); - Conf.PTO.emplace(LibraryOptions); - Conf.PTO->LoopUnrolling = CGOpts.UnrollLoops; - Conf.PTO->LoopInterchange = CGOpts.InterchangeLoops; - Conf.PTO->LoopFusion = CGOpts.FuseLoops; + PipelineTuningOptions &PTO = Conf.PTO.emplace(LibraryOptions); + PTO.LoopUnrolling = CGOpts.UnrollLoops; + PTO.LoopInterchange = CGOpts.InterchangeLoops; + PTO.LoopFusion = CGOpts.FuseLoops; // For historical reasons, loop interleaving is set to mirror setting for loop // unrolling. - Conf.PTO->LoopInterleaving = CGOpts.UnrollLoops; - Conf.PTO->LoopVectorization = CGOpts.VectorizeLoop; - Conf.PTO->SLPVectorization = CGOpts.VectorizeSLP; + PTO.LoopInterleaving = CGOpts.UnrollLoops; + PTO.LoopVectorization = CGOpts.VectorizeLoop; + PTO.SLPVectorization = CGOpts.VectorizeSLP; // Only enable CGProfilePass when using integrated assembler, since // non-integrated assemblers don't recognize .cgprofile section. - Conf.PTO->CallGraphProfile = !CGOpts.DisableIntegratedAS; + PTO.CallGraphProfile = !CGOpts.DisableIntegratedAS; // Context sensitive profile. if (CGOpts.hasProfileCSIRInstr()) { diff --git a/clang/tools/clang-nvlink-wrapper/ClangNVLinkWrapper.cpp b/clang/tools/clang-nvlink-wrapper/ClangNVLinkWrapper.cpp index e0803212092a0b..7bd9b007c74087 100644 --- a/clang/tools/clang-nvlink-wrapper/ClangNVLinkWrapper.cpp +++ b/clang/tools/clang-nvlink-wrapper/ClangNVLinkWrapper.cpp @@ -376,7 +376,6 @@ createLTO(const cl::LibraryOptionsContext &LibraryOptions, const llvm::Triple Triple("nvptx64-nvidia-cuda"); lto::Config Conf; Conf.LibraryOptions = &LibraryOptions; - Conf.PTO.emplace(LibraryOptions); lto::ThinBackend Backend; unsigned Jobs = 0; if (auto *Arg = Args.getLastArg(OPT_jobs)) diff --git a/lld/wasm/LTO.cpp b/lld/wasm/LTO.cpp index 0c158058e93725..774908babc84de 100644 --- a/lld/wasm/LTO.cpp +++ b/lld/wasm/LTO.cpp @@ -43,7 +43,6 @@ static std::string getThinLTOOutputFile(StringRef modulePath) { static lto::Config createConfig() { lto::Config c; c.LibraryOptions = &ctx.arg.libraryOptions; - c.PTO.emplace(*c.LibraryOptions); c.Options = initTargetOptionsFromCodeGenFlags(); // Always emit a section per function/data with LTO. diff --git a/llvm/lib/DTLTO/DTLTO.cpp b/llvm/lib/DTLTO/DTLTO.cpp index dc103d3d461cc8..e92758523ef237 100644 --- a/llvm/lib/DTLTO/DTLTO.cpp +++ b/llvm/lib/DTLTO/DTLTO.cpp @@ -226,7 +226,13 @@ void lto::DTLTO::buildCommonRemoteCompilerOptions() { Ops.push_back("-ffunction-sections"); if (C.Options.DataSections) Ops.push_back("-fdata-sections"); - if (C.PTO && C.PTO->LoopInterchange) + // An unset PTO means the defaults of the backend's LLVMContext, which copies + // C.LibraryOptions. + cl::LibraryOptionsContext NoLibraryOptions; + if (C.PTO ? C.PTO->LoopInterchange + : PipelineTuningOptions(C.LibraryOptions ? *C.LibraryOptions + : NoLibraryOptions) + .LoopInterchange) Ops.push_back("-floop-interchange"); if (C.RelocModel == Reloc::PIC_) diff --git a/llvm/tools/gold/gold-plugin.cpp b/llvm/tools/gold/gold-plugin.cpp index f95f4ef05f5687..5d23292f77c2d1 100644 --- a/llvm/tools/gold/gold-plugin.cpp +++ b/llvm/tools/gold/gold-plugin.cpp @@ -902,11 +902,11 @@ createLTO(const cl::LibraryOptionsContext &LibraryOptions, Conf.CGOptLevel = *CGOptLevelOrNone; Conf.DisableVerify = options::DisableVerify; Conf.OptLevel = options::OptLevel; - Conf.PTO.emplace(LibraryOptions); - Conf.PTO->LoopVectorization = options::OptLevel > 1; - Conf.PTO->SLPVectorization = options::OptLevel > 1; - Conf.PTO->MergeFunctions = options::merge_functions; - Conf.PTO->UnifiedLTO = options::unifiedlto; + PipelineTuningOptions &PTO = Conf.PTO.emplace(LibraryOptions); + PTO.LoopVectorization = options::OptLevel > 1; + PTO.SLPVectorization = options::OptLevel > 1; + PTO.MergeFunctions = options::merge_functions; + PTO.UnifiedLTO = options::unifiedlto; Conf.AlwaysEmitRegularLTOObj = !options::obj_path.empty(); if (options::thinlto_index_only) { _______________________________________________ cfe-commits mailing list [email protected] https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
