https://github.com/NuriAmari updated https://github.com/llvm/llvm-project/pull/183525
>From cfe82951e17fd541e9eb436161a827fc0032dc70 Mon Sep 17 00:00:00 2001 From: Nuri Amari <[email protected]> Date: Tue, 24 Feb 2026 14:34:51 -0800 Subject: [PATCH 1/2] Support -fpass-plugin + -fthinlto-index together Without this change, passing -fthinlto-index causes -fpass-plugin arguments to be ignored. We want to be able to use plugins with distributed thin-lto, so add support for this. --- clang/lib/CodeGen/BackendUtil.cpp | 1 + .../distributed-thin-lto/pass-plugin.ll | 25 +++++++++++++++++++ 2 files changed, 26 insertions(+) create mode 100644 clang/test/CodeGen/distributed-thin-lto/pass-plugin.ll diff --git a/clang/lib/CodeGen/BackendUtil.cpp b/clang/lib/CodeGen/BackendUtil.cpp index 94257fb96fc7f..9b7c7cef8a5d3 100644 --- a/clang/lib/CodeGen/BackendUtil.cpp +++ b/clang/lib/CodeGen/BackendUtil.cpp @@ -1382,6 +1382,7 @@ runThinLTOBackend(CompilerInstance &CI, ModuleSummaryIndex *CombinedIndex, Conf.RemarksFormat = CGOpts.OptRecordFormat; Conf.SplitDwarfFile = CGOpts.SplitDwarfFile; Conf.SplitDwarfOutput = CGOpts.SplitDwarfOutput; + Conf.PassPlugins = CGOpts.PassPlugins; switch (Action) { case Backend_EmitNothing: Conf.PreCodeGenModuleHook = [](size_t Task, const llvm::Module &Mod) { diff --git a/clang/test/CodeGen/distributed-thin-lto/pass-plugin.ll b/clang/test/CodeGen/distributed-thin-lto/pass-plugin.ll new file mode 100644 index 0000000000000..fef5f1f3c2c0c --- /dev/null +++ b/clang/test/CodeGen/distributed-thin-lto/pass-plugin.ll @@ -0,0 +1,25 @@ +; REQUIRES: x86-registered-target, plugins, examples + +;; Validate that -fpass-plugin works for distributed ThinLTO backends. + +; RUN: opt -thinlto-bc -o %t.o %s + +; RUN: llvm-lto2 run -thinlto-distributed-indexes %t.o \ +; RUN: -o %t2.index \ +; RUN: -r=%t.o,main,px + +; RUN: %clang_cc1 -triple x86_64-grtev4-linux-gnu \ +; RUN: -O2 -emit-obj -fthinlto-index=%t.o.thinlto.bc \ +; RUN: -fpass-plugin=%llvmshlibdir/Bye%pluginext \ +; RUN: -mllvm -wave-goodbye \ +; RUN: -o %t.native.o -x ir %t.o 2>&1 | FileCheck %s + +; CHECK: Bye: main + +target datalayout = "e-m:e-p270:32:32-p271:32:32-p272:64:64-i64:64-f80:128-n8:16:32:64-S128" +target triple = "x86_64-grtev4-linux-gnu" + +define i32 @main() { +entry: + ret i32 0 +} >From bfad5809605ccc093583d0a53ed58e1ea86460c0 Mon Sep 17 00:00:00 2001 From: Nuri Amari <[email protected]> Date: Thu, 26 Feb 2026 11:55:09 -0800 Subject: [PATCH 2/2] Use already loaded pass plugins instead of loading twice Based on PR feedback, add an extra field to LTO::Config allowing clients to pass already loaded PassPlugin objects. This is useful for distributed thin-lto where the LTO client creating the LTO backend has already loaded the plugins and it would be a waste to load them again. Rename the existing field for clarity. I also switched from REQUIRES: example to llvm-example, which I mistakenly used looking at related tests. --- clang/lib/CodeGen/BackendUtil.cpp | 3 ++- clang/test/CodeGen/distributed-thin-lto/pass-plugin.ll | 2 +- .../tools/clang-nvlink-wrapper/ClangNVLinkWrapper.cpp | 2 +- lld/ELF/LTO.cpp | 2 +- lld/MachO/LTO.cpp | 2 +- llvm/include/llvm/LTO/Config.h | 8 +++++++- llvm/lib/LTO/LTOBackend.cpp | 10 +++++++--- llvm/tools/llvm-lto2/llvm-lto2.cpp | 2 +- 8 files changed, 21 insertions(+), 10 deletions(-) diff --git a/clang/lib/CodeGen/BackendUtil.cpp b/clang/lib/CodeGen/BackendUtil.cpp index 9b7c7cef8a5d3..3c168adac8f02 100644 --- a/clang/lib/CodeGen/BackendUtil.cpp +++ b/clang/lib/CodeGen/BackendUtil.cpp @@ -1382,7 +1382,8 @@ runThinLTOBackend(CompilerInstance &CI, ModuleSummaryIndex *CombinedIndex, Conf.RemarksFormat = CGOpts.OptRecordFormat; Conf.SplitDwarfFile = CGOpts.SplitDwarfFile; Conf.SplitDwarfOutput = CGOpts.SplitDwarfOutput; - Conf.PassPlugins = CGOpts.PassPlugins; + for (auto &Plugin : CI.getPassPlugins()) + Conf.LoadedPassPlugins.push_back(Plugin.get()); switch (Action) { case Backend_EmitNothing: Conf.PreCodeGenModuleHook = [](size_t Task, const llvm::Module &Mod) { diff --git a/clang/test/CodeGen/distributed-thin-lto/pass-plugin.ll b/clang/test/CodeGen/distributed-thin-lto/pass-plugin.ll index fef5f1f3c2c0c..5bb96722bfd72 100644 --- a/clang/test/CodeGen/distributed-thin-lto/pass-plugin.ll +++ b/clang/test/CodeGen/distributed-thin-lto/pass-plugin.ll @@ -1,4 +1,4 @@ -; REQUIRES: x86-registered-target, plugins, examples +; REQUIRES: x86-registered-target, plugins, llvm-examples ;; Validate that -fpass-plugin works for distributed ThinLTO backends. diff --git a/clang/tools/clang-nvlink-wrapper/ClangNVLinkWrapper.cpp b/clang/tools/clang-nvlink-wrapper/ClangNVLinkWrapper.cpp index 3ebd4ea979322..70178568f76c6 100644 --- a/clang/tools/clang-nvlink-wrapper/ClangNVLinkWrapper.cpp +++ b/clang/tools/clang-nvlink-wrapper/ClangNVLinkWrapper.cpp @@ -380,7 +380,7 @@ Expected<std::unique_ptr<lto::LTO>> createLTO(const ArgList &Args) { Conf.DefaultTriple = Triple.getTriple(); Conf.OptPipeline = Args.getLastArgValue(OPT_lto_newpm_passes, ""); - Conf.PassPlugins = PassPlugins; + Conf.PassPluginFilenames = PassPlugins; Conf.DebugPassManager = Args.hasArg(OPT_lto_debug_pass_manager); Conf.DiagHandler = diagnosticHandler; diff --git a/lld/ELF/LTO.cpp b/lld/ELF/LTO.cpp index 6f916a501a262..ff8d44e0d7f64 100644 --- a/lld/ELF/LTO.cpp +++ b/lld/ELF/LTO.cpp @@ -124,7 +124,7 @@ static lto::Config createConfig(Ctx &ctx) { c.SampleProfile = std::string(ctx.arg.ltoSampleProfile); for (StringRef pluginFn : ctx.arg.passPlugins) - c.PassPlugins.push_back(std::string(pluginFn)); + c.PassPluginFilenames.push_back(std::string(pluginFn)); c.DebugPassManager = ctx.arg.ltoDebugPassManager; c.DwoDir = std::string(ctx.arg.dwoDir); diff --git a/lld/MachO/LTO.cpp b/lld/MachO/LTO.cpp index df2b0cb8b4a29..c8b7a4e797250 100644 --- a/lld/MachO/LTO.cpp +++ b/lld/MachO/LTO.cpp @@ -43,7 +43,7 @@ static lto::Config createConfig() { for (StringRef C : config->mllvmOpts) c.MllvmArgs.emplace_back(C.str()); for (StringRef pluginFn : config->passPlugins) - c.PassPlugins.push_back(std::string(pluginFn)); + c.PassPluginFilenames.push_back(std::string(pluginFn)); c.OptPipeline = std::string(config->ltoNewPmPasses); c.CodeModel = getCodeModelFromCMModel(); c.CPU = getCPUStr(); diff --git a/llvm/include/llvm/LTO/Config.h b/llvm/include/llvm/LTO/Config.h index 566a87ed1a790..97c8259141473 100644 --- a/llvm/include/llvm/LTO/Config.h +++ b/llvm/include/llvm/LTO/Config.h @@ -34,6 +34,7 @@ class Error; class Module; class ModuleSummaryIndex; class raw_pwrite_stream; +class PassPlugin; namespace lto { @@ -50,7 +51,12 @@ struct Config { TargetOptions Options; std::vector<std::string> MAttrs; std::vector<std::string> MllvmArgs; - std::vector<std::string> PassPlugins; + // LTO will register both lists of plugins, but + // if an LTO client has already loaded a set of plugins, + // they should register them via LoadedPassPlugins. + // This is currently used by distributed thin-lto. + std::vector<std::string> PassPluginFilenames; + std::vector<llvm::PassPlugin*> LoadedPassPlugins; /// For adding passes that run right before codegen. std::function<void(legacy::PassManager &)> PreCodeGenPassesHook; std::optional<Reloc::Model> RelocModel = Reloc::PIC_; diff --git a/llvm/lib/LTO/LTOBackend.cpp b/llvm/lib/LTO/LTOBackend.cpp index 43e5c3b398372..45a222245dc3b 100644 --- a/llvm/lib/LTO/LTOBackend.cpp +++ b/llvm/lib/LTO/LTOBackend.cpp @@ -199,7 +199,7 @@ Error Config::addSaveTemps(std::string OutputFileName, bool UseInputModulePath, #include "llvm/Support/Extension.def" #undef HANDLE_EXTENSION -static void RegisterPassPlugins(ArrayRef<std::string> PassPlugins, +static void RegisterPassPlugins(const Config &Conf, PassBuilder &PB) { #define HANDLE_EXTENSION(Ext) \ get##Ext##PluginInfo().RegisterPassBuilderCallbacks(PB); @@ -207,12 +207,16 @@ static void RegisterPassPlugins(ArrayRef<std::string> PassPlugins, #undef HANDLE_EXTENSION // Load requested pass plugins and let them register pass builder callbacks - for (auto &PluginFN : PassPlugins) { + for (auto &PluginFN : Conf.PassPluginFilenames) { auto PassPlugin = PassPlugin::Load(PluginFN); if (!PassPlugin) reportFatalUsageError(PassPlugin.takeError()); PassPlugin->registerPassBuilderCallbacks(PB); } + + // Register already loaded plugins + for (auto *LoadedPlugin : Conf.LoadedPassPlugins) + LoadedPlugin->registerPassBuilderCallbacks(PB); } static std::unique_ptr<TargetMachine> @@ -292,7 +296,7 @@ static void runNewPMPasses(const Config &Conf, Module &Mod, TargetMachine *TM, SI.registerCallbacks(PIC, &MAM); PassBuilder PB(TM, Conf.PTO, PGOOpt, &PIC); - RegisterPassPlugins(Conf.PassPlugins, PB); + RegisterPassPlugins(Conf, PB); std::unique_ptr<TargetLibraryInfoImpl> TLII( new TargetLibraryInfoImpl(TM->getTargetTriple(), TM->Options.VecLib)); diff --git a/llvm/tools/llvm-lto2/llvm-lto2.cpp b/llvm/tools/llvm-lto2/llvm-lto2.cpp index 955c1130e9f4c..95e8053dab32d 100644 --- a/llvm/tools/llvm-lto2/llvm-lto2.cpp +++ b/llvm/tools/llvm-lto2/llvm-lto2.cpp @@ -376,7 +376,7 @@ static int run(int argc, char **argv) { Conf.OptLevel = OptLevel - '0'; Conf.Freestanding = EnableFreestanding; - llvm::append_range(Conf.PassPlugins, PassPlugins); + llvm::append_range(Conf.PassPluginFilenames, PassPlugins); if (auto Level = CodeGenOpt::parseLevel(CGOptLevel)) { Conf.CGOptLevel = *Level; } else { _______________________________________________ cfe-commits mailing list [email protected] https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
