qiongsiwu1 created this revision. qiongsiwu1 added reviewers: w2yehia, MaskRay. qiongsiwu1 added a project: clang. Herald added subscribers: ormris, StephenFan, steven_wu, hiraditya, inglorion. Herald added a project: All. qiongsiwu1 requested review of this revision. Herald added a subscriber: cfe-commits.
This patch teaches `clang` to use the prefix `-bplugin_opt:` (instead of `-plugin-opt`) on AIX, when passing plugin options to the linker. This patch follows https://reviews.llvm.org/D134668. We put the code that decides what plugin option prefix to use at the top of the function `tools::addLTOOptions` and the plugin option prefix, the mcpu prefix, and the opt level prefix are different on AIX. We thought about choosing the strings in a function that reads the linker name and the target triple, or we could push the logic into different derived `ToolChain` classes. But this logic would not be used anywhere else, so these alternatives looked too complicated for what they did. Therefore we are doing it the current way. That said, I am all ears for suggestions to improve this code! Subsequent code uses the `PluginOptPrefix` variable consistently instead of the hardcoded `-plugin-opt`. Repository: rG LLVM Github Monorepo https://reviews.llvm.org/D134820 Files: clang/lib/Driver/ToolChains/AIX.cpp clang/lib/Driver/ToolChains/CommonArgs.cpp clang/lib/Driver/ToolChains/CommonArgs.h clang/test/Driver/lto-aix.c
Index: clang/test/Driver/lto-aix.c =================================================================== --- /dev/null +++ clang/test/Driver/lto-aix.c @@ -0,0 +1,6 @@ +// Test LTO path, mcpu and opt level options +// RUN: %clang -target powerpc-ibm-aix -### %s -flto -fuse-ld=ld -O3 2>&1 \ +// RUN: | FileCheck -check-prefixes=LTOPATH,MCPUOPTLEVEL %s +// +// LTOPATH: "-bplugin:{{.*}}/libLTO.so" +// MCPUOPTLEVEL: "-bplugin_opt:-mcpu={{.*}}" "-bplugin_opt:-O3" Index: clang/lib/Driver/ToolChains/CommonArgs.h =================================================================== --- clang/lib/Driver/ToolChains/CommonArgs.h +++ clang/lib/Driver/ToolChains/CommonArgs.h @@ -190,7 +190,8 @@ Multilib::flags_list &Flags); void addX86AlignBranchArgs(const Driver &D, const llvm::opt::ArgList &Args, - llvm::opt::ArgStringList &CmdArgs, bool IsLTO); + llvm::opt::ArgStringList &CmdArgs, bool IsLTO, + const StringRef PluginOptPrefix = ""); void checkAMDGPUCodeObjectVersion(const Driver &D, const llvm::opt::ArgList &Args); @@ -203,7 +204,8 @@ void addMachineOutlinerArgs(const Driver &D, const llvm::opt::ArgList &Args, llvm::opt::ArgStringList &CmdArgs, - const llvm::Triple &Triple, bool IsLTO); + const llvm::Triple &Triple, bool IsLTO, + const StringRef PluginOptPrefix = ""); void addOpenMPDeviceRTL(const Driver &D, const llvm::opt::ArgList &DriverArgs, llvm::opt::ArgStringList &CC1Args, Index: clang/lib/Driver/ToolChains/CommonArgs.cpp =================================================================== --- clang/lib/Driver/ToolChains/CommonArgs.cpp +++ clang/lib/Driver/ToolChains/CommonArgs.cpp @@ -65,24 +65,28 @@ using namespace clang; using namespace llvm::opt; -static void renderRpassOptions(const ArgList &Args, ArgStringList &CmdArgs) { +static void renderRpassOptions(const ArgList &Args, ArgStringList &CmdArgs, + const StringRef PluginOptPrefix) { if (const Arg *A = Args.getLastArg(options::OPT_Rpass_EQ)) - CmdArgs.push_back(Args.MakeArgString(Twine("-plugin-opt=-pass-remarks=") + - A->getValue())); + CmdArgs.push_back(Args.MakeArgString( + Twine(PluginOptPrefix) + Twine("-pass-remarks=") + A->getValue())); if (const Arg *A = Args.getLastArg(options::OPT_Rpass_missed_EQ)) - CmdArgs.push_back(Args.MakeArgString( - Twine("-plugin-opt=-pass-remarks-missed=") + A->getValue())); + CmdArgs.push_back(Args.MakeArgString(Twine(PluginOptPrefix) + + Twine("-pass-remarks-missed=") + + A->getValue())); if (const Arg *A = Args.getLastArg(options::OPT_Rpass_analysis_EQ)) - CmdArgs.push_back(Args.MakeArgString( - Twine("-plugin-opt=-pass-remarks-analysis=") + A->getValue())); + CmdArgs.push_back(Args.MakeArgString(Twine(PluginOptPrefix) + + Twine("-pass-remarks-analysis=") + + A->getValue())); } static void renderRemarksOptions(const ArgList &Args, ArgStringList &CmdArgs, const llvm::Triple &Triple, const InputInfo &Input, - const InputInfo &Output) { + const InputInfo &Output, + const StringRef PluginOptPrefix) { StringRef Format = "yaml"; if (const Arg *A = Args.getLastArg(options::OPT_fsave_optimization_record_EQ)) Format = A->getValue(); @@ -96,29 +100,32 @@ assert(!F.empty() && "Cannot determine remarks output name."); // Append "opt.ld.<format>" to the end of the file name. - CmdArgs.push_back( - Args.MakeArgString(Twine("-plugin-opt=opt-remarks-filename=") + F + - Twine(".opt.ld.") + Format)); + CmdArgs.push_back(Args.MakeArgString(Twine(PluginOptPrefix) + + Twine("opt-remarks-filename=") + F + + Twine(".opt.ld.") + Format)); if (const Arg *A = Args.getLastArg(options::OPT_foptimization_record_passes_EQ)) CmdArgs.push_back(Args.MakeArgString( - Twine("-plugin-opt=opt-remarks-passes=") + A->getValue())); + Twine(PluginOptPrefix) + Twine("opt-remarks-passes=") + A->getValue())); CmdArgs.push_back(Args.MakeArgString( - Twine("-plugin-opt=opt-remarks-format=") + Format.data())); + Twine(PluginOptPrefix) + Twine("opt-remarks-format=") + Format.data())); } static void renderRemarksHotnessOptions(const ArgList &Args, - ArgStringList &CmdArgs) { + ArgStringList &CmdArgs, + const StringRef PluginOptPrefix) { if (Args.hasFlag(options::OPT_fdiagnostics_show_hotness, options::OPT_fno_diagnostics_show_hotness, false)) - CmdArgs.push_back("-plugin-opt=opt-remarks-with-hotness"); + CmdArgs.push_back(Args.MakeArgString(Twine(PluginOptPrefix) + + "opt-remarks-with-hotness")); if (const Arg *A = Args.getLastArg(options::OPT_fdiagnostics_hotness_threshold_EQ)) CmdArgs.push_back(Args.MakeArgString( - Twine("-plugin-opt=opt-remarks-hotness-threshold=") + A->getValue())); + Twine(PluginOptPrefix) + Twine("opt-remarks-hotness-threshold=") + + A->getValue())); } void tools::addPathIfExists(const Driver &D, const Twine &Path, @@ -484,14 +491,20 @@ void tools::addLTOOptions(const ToolChain &ToolChain, const ArgList &Args, ArgStringList &CmdArgs, const InputInfo &Output, const InputInfo &Input, bool IsThinLTO) { + const bool IsOSAIX = ToolChain.getTriple().isOSAIX(); + const char *Linker = Args.MakeArgString(ToolChain.GetLinkerPath()); const Driver &D = ToolChain.getDriver(); if (llvm::sys::path::filename(Linker) != "ld.lld" && llvm::sys::path::stem(Linker) != "ld.lld") { // Tell the linker to load the plugin. This has to come before - // AddLinkerInputs as gold requires -plugin to come before any -plugin-opt - // that -Wl might forward. - CmdArgs.push_back("-plugin"); + // AddLinkerInputs as gold requires -plugin and AIX ld requires -bplugin to + // come before any -plugin-opt/-bplugin_opt that -Wl might forward. + const char *PluginPrefix = IsOSAIX ? "-bplugin:" : ""; + const char *PluginName = IsOSAIX ? "/libLTO" : "/LLVMgold"; + + if (!IsOSAIX) + CmdArgs.push_back("-plugin"); #if defined(_WIN32) const char *Suffix = ".dll"; @@ -502,20 +515,24 @@ #endif SmallString<1024> Plugin; - llvm::sys::path::native( - Twine(D.Dir) + "/../" CLANG_INSTALL_LIBDIR_BASENAME "/LLVMgold" + - Suffix, - Plugin); - CmdArgs.push_back(Args.MakeArgString(Plugin)); + llvm::sys::path::native(Twine(D.Dir) + + "/../" CLANG_INSTALL_LIBDIR_BASENAME + + PluginName + Suffix, + Plugin); + CmdArgs.push_back(Args.MakeArgString(Twine(PluginPrefix) + Plugin)); } // Try to pass driver level flags relevant to LTO code generation down to // the plugin. + const char *PluginOptPrefix = IsOSAIX ? "-bplugin_opt:" : "-plugin-opt="; + const char *mcpuOptPrefix = IsOSAIX ? "-mcpu=" : "mcpu="; + const char *OptLevelPrefix = IsOSAIX ? "-O" : "O"; // Handle flags for selecting CPU variants. std::string CPU = getCPUName(D, Args, ToolChain.getTriple()); if (!CPU.empty()) - CmdArgs.push_back(Args.MakeArgString(Twine("-plugin-opt=mcpu=") + CPU)); + CmdArgs.push_back(Args.MakeArgString(Twine(PluginOptPrefix) + + Twine(mcpuOptPrefix) + CPU)); if (Arg *A = Args.getLastArg(options::OPT_O_Group)) { // The optimization level matches @@ -533,37 +550,43 @@ } else if (A->getOption().matches(options::OPT_O0)) OOpt = "0"; if (!OOpt.empty()) - CmdArgs.push_back(Args.MakeArgString(Twine("-plugin-opt=O") + OOpt)); + CmdArgs.push_back(Args.MakeArgString(Twine(PluginOptPrefix) + + Twine(OptLevelPrefix) + OOpt)); } if (Args.hasArg(options::OPT_gsplit_dwarf)) { - CmdArgs.push_back( - Args.MakeArgString(Twine("-plugin-opt=dwo_dir=") + - Output.getFilename() + "_dwo")); + CmdArgs.push_back(Args.MakeArgString(Twine(PluginOptPrefix) + + Twine("dwo_dir=") + + Output.getFilename() + "_dwo")); } if (IsThinLTO) - CmdArgs.push_back("-plugin-opt=thinlto"); + CmdArgs.push_back(Args.MakeArgString(Twine(PluginOptPrefix) + "thinlto")); StringRef Parallelism = getLTOParallelism(Args, D); if (!Parallelism.empty()) - CmdArgs.push_back( - Args.MakeArgString("-plugin-opt=jobs=" + Twine(Parallelism))); + CmdArgs.push_back(Args.MakeArgString(Twine(PluginOptPrefix) + + "jobs=" + Twine(Parallelism))); if (!CLANG_ENABLE_OPAQUE_POINTERS_INTERNAL) - CmdArgs.push_back(Args.MakeArgString("-plugin-opt=no-opaque-pointers")); + CmdArgs.push_back( + Args.MakeArgString(Twine(PluginOptPrefix) + "no-opaque-pointers")); // If an explicit debugger tuning argument appeared, pass it along. - if (Arg *A = Args.getLastArg(options::OPT_gTune_Group, - options::OPT_ggdbN_Group)) { + if (Arg *A = + Args.getLastArg(options::OPT_gTune_Group, options::OPT_ggdbN_Group)) { if (A->getOption().matches(options::OPT_glldb)) - CmdArgs.push_back("-plugin-opt=-debugger-tune=lldb"); + CmdArgs.push_back( + Args.MakeArgString(Twine(PluginOptPrefix) + "-debugger-tune=lldb")); else if (A->getOption().matches(options::OPT_gsce)) - CmdArgs.push_back("-plugin-opt=-debugger-tune=sce"); + CmdArgs.push_back( + Args.MakeArgString(Twine(PluginOptPrefix) + "-debugger-tune=sce")); else if (A->getOption().matches(options::OPT_gdbx)) - CmdArgs.push_back("-plugin-opt=-debugger-tune=dbx"); + CmdArgs.push_back( + Args.MakeArgString(Twine(PluginOptPrefix) + "-debugger-tune=dbx")); else - CmdArgs.push_back("-plugin-opt=-debugger-tune=gdb"); + CmdArgs.push_back( + Args.MakeArgString(Twine(PluginOptPrefix) + "-debugger-tune=gdb")); } bool UseSeparateSections = @@ -571,21 +594,26 @@ if (Args.hasFlag(options::OPT_ffunction_sections, options::OPT_fno_function_sections, UseSeparateSections)) - CmdArgs.push_back("-plugin-opt=-function-sections=1"); + CmdArgs.push_back( + Args.MakeArgString(Twine(PluginOptPrefix) + "-function-sections=1")); else if (Args.hasArg(options::OPT_fno_function_sections)) - CmdArgs.push_back("-plugin-opt=-function-sections=0"); + CmdArgs.push_back( + Args.MakeArgString(Twine(PluginOptPrefix) + "-function-sections=0")); if (Args.hasFlag(options::OPT_fdata_sections, options::OPT_fno_data_sections, UseSeparateSections)) - CmdArgs.push_back("-plugin-opt=-data-sections=1"); + CmdArgs.push_back( + Args.MakeArgString(Twine(PluginOptPrefix) + "-data-sections=1")); else if (Args.hasArg(options::OPT_fno_data_sections)) - CmdArgs.push_back("-plugin-opt=-data-sections=0"); + CmdArgs.push_back( + Args.MakeArgString(Twine(PluginOptPrefix) + "-data-sections=0")); // Pass an option to enable split machine functions. if (auto *A = Args.getLastArg(options::OPT_fsplit_machine_functions, options::OPT_fno_split_machine_functions)) { if (A->getOption().matches(options::OPT_fsplit_machine_functions)) - CmdArgs.push_back("-plugin-opt=-split-machine-functions"); + CmdArgs.push_back(Args.MakeArgString(Twine(PluginOptPrefix) + + "-split-machine-functions")); } if (Arg *A = getLastProfileSampleUseArg(Args)) { @@ -593,8 +621,8 @@ if (!llvm::sys::fs::exists(FName)) D.Diag(diag::err_drv_no_such_file) << FName; else - CmdArgs.push_back( - Args.MakeArgString(Twine("-plugin-opt=sample-profile=") + FName)); + CmdArgs.push_back(Args.MakeArgString(Twine(PluginOptPrefix) + + Twine("sample-profile=") + FName)); } auto *CSPGOGenerateArg = Args.getLastArg(options::OPT_fcs_profile_generate, @@ -607,29 +635,31 @@ auto *ProfileUseArg = getLastProfileUseArg(Args); if (CSPGOGenerateArg) { - CmdArgs.push_back(Args.MakeArgString("-plugin-opt=cs-profile-generate")); + CmdArgs.push_back( + Args.MakeArgString(Twine(PluginOptPrefix) + "cs-profile-generate")); if (CSPGOGenerateArg->getOption().matches( options::OPT_fcs_profile_generate_EQ)) { SmallString<128> Path(CSPGOGenerateArg->getValue()); llvm::sys::path::append(Path, "default_%m.profraw"); - CmdArgs.push_back( - Args.MakeArgString(Twine("-plugin-opt=cs-profile-path=") + Path)); + CmdArgs.push_back(Args.MakeArgString(Twine(PluginOptPrefix) + + Twine("cs-profile-path=") + Path)); } else - CmdArgs.push_back( - Args.MakeArgString("-plugin-opt=cs-profile-path=default_%m.profraw")); + CmdArgs.push_back(Args.MakeArgString( + Twine(PluginOptPrefix) + "cs-profile-path=default_%m.profraw")); } else if (ProfileUseArg) { SmallString<128> Path( ProfileUseArg->getNumValues() == 0 ? "" : ProfileUseArg->getValue()); if (Path.empty() || llvm::sys::fs::is_directory(Path)) llvm::sys::path::append(Path, "default.profdata"); - CmdArgs.push_back(Args.MakeArgString(Twine("-plugin-opt=cs-profile-path=") + - Path)); + CmdArgs.push_back(Args.MakeArgString(Twine(PluginOptPrefix) + + Twine("cs-profile-path=") + Path)); } // This controls whether or not we perform JustMyCode instrumentation. if (Args.hasFlag(options::OPT_fjmc, options::OPT_fno_jmc, false)) { if (ToolChain.getEffectiveTriple().isOSBinFormatELF()) - CmdArgs.push_back("-plugin-opt=-enable-jmc-instrument"); + CmdArgs.push_back(Args.MakeArgString(Twine(PluginOptPrefix) + + "-enable-jmc-instrument")); else D.Diag(clang::diag::warn_drv_fjmc_for_elf_only); } @@ -637,30 +667,31 @@ // Setup statistics file output. SmallString<128> StatsFile = getStatsFileName(Args, Output, Input, D); if (!StatsFile.empty()) - CmdArgs.push_back( - Args.MakeArgString(Twine("-plugin-opt=stats-file=") + StatsFile)); + CmdArgs.push_back(Args.MakeArgString(Twine(PluginOptPrefix) + + Twine("stats-file=") + StatsFile)); // Setup crash diagnostics dir. if (Arg *A = Args.getLastArg(options::OPT_fcrash_diagnostics_dir)) - CmdArgs.push_back(Args.MakeArgString( - Twine("-plugin-opt=-crash-diagnostics-dir=") + A->getValue())); + CmdArgs.push_back(Args.MakeArgString(Twine(PluginOptPrefix) + + Twine("-crash-diagnostics-dir=") + + A->getValue())); - addX86AlignBranchArgs(D, Args, CmdArgs, /*IsLTO=*/true); + addX86AlignBranchArgs(D, Args, CmdArgs, /*IsLTO=*/true, PluginOptPrefix); // Handle remark diagnostics on screen options: '-Rpass-*'. - renderRpassOptions(Args, CmdArgs); + renderRpassOptions(Args, CmdArgs, PluginOptPrefix); // Handle serialized remarks options: '-fsave-optimization-record' // and '-foptimization-record-*'. if (willEmitRemarks(Args)) renderRemarksOptions(Args, CmdArgs, ToolChain.getEffectiveTriple(), Input, - Output); + Output, PluginOptPrefix); // Handle remarks hotness/threshold related options. - renderRemarksHotnessOptions(Args, CmdArgs); + renderRemarksHotnessOptions(Args, CmdArgs, PluginOptPrefix); addMachineOutlinerArgs(D, Args, CmdArgs, ToolChain.getEffectiveTriple(), - /*IsLTO=*/true); + /*IsLTO=*/true, PluginOptPrefix); } void tools::addOpenMPRuntimeSpecificRPath(const ToolChain &TC, @@ -1664,10 +1695,12 @@ } void tools::addX86AlignBranchArgs(const Driver &D, const ArgList &Args, - ArgStringList &CmdArgs, bool IsLTO) { + ArgStringList &CmdArgs, bool IsLTO, + const StringRef PluginOptPrefix) { auto addArg = [&, IsLTO](const Twine &Arg) { if (IsLTO) { - CmdArgs.push_back(Args.MakeArgString("-plugin-opt=" + Arg)); + assert(!PluginOptPrefix.empty() && "Cannot have empty PluginOptPrefix!"); + CmdArgs.push_back(Args.MakeArgString(Twine(PluginOptPrefix) + Arg)); } else { CmdArgs.push_back("-mllvm"); CmdArgs.push_back(Args.MakeArgString(Arg)); @@ -2101,10 +2134,12 @@ void tools::addMachineOutlinerArgs(const Driver &D, const llvm::opt::ArgList &Args, llvm::opt::ArgStringList &CmdArgs, - const llvm::Triple &Triple, bool IsLTO) { + const llvm::Triple &Triple, bool IsLTO, + const StringRef PluginOptPrefix) { auto addArg = [&, IsLTO](const Twine &Arg) { if (IsLTO) { - CmdArgs.push_back(Args.MakeArgString("-plugin-opt=" + Arg)); + assert(!PluginOptPrefix.empty() && "Cannot have empty PluginOptPrefix!"); + CmdArgs.push_back(Args.MakeArgString(Twine(PluginOptPrefix) + Arg)); } else { CmdArgs.push_back("-mllvm"); CmdArgs.push_back(Args.MakeArgString(Arg)); Index: clang/lib/Driver/ToolChains/AIX.cpp =================================================================== --- clang/lib/Driver/ToolChains/AIX.cpp +++ clang/lib/Driver/ToolChains/AIX.cpp @@ -191,6 +191,12 @@ // Specify linker input file(s). AddLinkerInputs(ToolChain, Inputs, Args, CmdArgs, JA); + if (D.isUsingLTO()) { + assert(!Inputs.empty() && "Must have at least one input."); + addLTOOptions(ToolChain, Args, CmdArgs, Output, Inputs[0], + D.getLTOMode() == LTOK_Thin); + } + if (Args.hasArg(options::OPT_shared) && !hasExportListLinkerOpts(CmdArgs)) { const char *CreateExportListExec = Args.MakeArgString(
_______________________________________________ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits