From 04d0ac7a18b2cfe47902e9d763b26627d7fb2107 Mon Sep 17 00:00:00 2001 From: Chandler Carruth Date: Sun, 13 Jan 2013 11:46:33 +0000 Subject: Refactor the x86 CPU name logic in the driver and pass -march and -mcpu flag information down from the Clang driver into the Gold linker plugin for LTO. This allows specifying -march on the linker commandline and should hopefully have it pass all the way through to the LTO optimizer. Fixes PR14697. git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@172354 91177308-0d34-0410-b5e6-96231b3b80d8 (cherry picked from commit 700d4e44793697288dd827c272ad363945f590a9) Signed-off-by: Abdoulaye Walsimou Gaye --- lib/Driver/Tools.cpp | 132 ++++++++++++++++++++++++++----------------------- test/Driver/gold-lto.c | 25 ++++++++-- 2 files changed, 91 insertions(+), 66 deletions(-) diff --git a/lib/Driver/Tools.cpp b/lib/Driver/Tools.cpp index a91f78315e..7ee6eb1caa 100644 --- a/lib/Driver/Tools.cpp +++ b/lib/Driver/Tools.cpp @@ -1147,10 +1147,59 @@ void Clang::AddSparcTargetArgs(const ArgList &Args, } } +static const char *getX86TargetCPU(const ArgList &Args, + const llvm::Triple &Triple) { + if (const Arg *A = Args.getLastArg(options::OPT_march_EQ)) { + if (StringRef(A->getValue()) != "native") + return A->getValue(); + + // FIXME: Reject attempts to use -march=native unless the target matches + // the host. + // + // FIXME: We should also incorporate the detected target features for use + // with -native. + std::string CPU = llvm::sys::getHostCPUName(); + if (!CPU.empty() && CPU != "generic") + return Args.MakeArgString(CPU); + } + + // Select the default CPU if none was given (or detection failed). + + if (Triple.getArch() != llvm::Triple::x86_64 && + Triple.getArch() != llvm::Triple::x86) + return 0; // This routine is only handling x86 targets. + + bool Is64Bit = Triple.getArch() == llvm::Triple::x86_64; + + // FIXME: Need target hooks. + if (Triple.isOSDarwin()) + return Is64Bit ? "core2" : "yonah"; + + // Everything else goes to x86-64 in 64-bit mode. + if (Is64Bit) + return "x86-64"; + + if (Triple.getOSName().startswith("haiku")) + return "i586"; + if (Triple.getOSName().startswith("openbsd")) + return "i486"; + if (Triple.getOSName().startswith("bitrig")) + return "i686"; + if (Triple.getOSName().startswith("freebsd")) + return "i486"; + if (Triple.getOSName().startswith("netbsd")) + return "i486"; + // All x86 devices running Android have core2 as their common + // denominator. This makes a better choice than pentium4. + if (Triple.getEnvironment() == llvm::Triple::Android) + return "core2"; + + // Fallback to p4. + return "pentium4"; +} + void Clang::AddX86TargetArgs(const ArgList &Args, ArgStringList &CmdArgs) const { - const bool isAndroid = - getToolChain().getTriple().getEnvironment() == llvm::Triple::Android; if (!Args.hasFlag(options::OPT_mred_zone, options::OPT_mno_red_zone, true) || @@ -1163,65 +1212,7 @@ void Clang::AddX86TargetArgs(const ArgList &Args, false)) CmdArgs.push_back("-no-implicit-float"); - const char *CPUName = 0; - if (const Arg *A = Args.getLastArg(options::OPT_march_EQ)) { - if (StringRef(A->getValue()) == "native") { - // FIXME: Reject attempts to use -march=native unless the target matches - // the host. - // - // FIXME: We should also incorporate the detected target features for use - // with -native. - std::string CPU = llvm::sys::getHostCPUName(); - if (!CPU.empty() && CPU != "generic") - CPUName = Args.MakeArgString(CPU); - } else - CPUName = A->getValue(); - } - - // Select the default CPU if none was given (or detection failed). - if (!CPUName) { - // FIXME: Need target hooks. - if (getToolChain().getTriple().isOSDarwin()) { - if (getToolChain().getArch() == llvm::Triple::x86_64) - CPUName = "core2"; - else if (getToolChain().getArch() == llvm::Triple::x86) - CPUName = "yonah"; - } else if (getToolChain().getOS().startswith("haiku")) { - if (getToolChain().getArch() == llvm::Triple::x86_64) - CPUName = "x86-64"; - else if (getToolChain().getArch() == llvm::Triple::x86) - CPUName = "i586"; - } else if (getToolChain().getOS().startswith("openbsd")) { - if (getToolChain().getArch() == llvm::Triple::x86_64) - CPUName = "x86-64"; - else if (getToolChain().getArch() == llvm::Triple::x86) - CPUName = "i486"; - } else if (getToolChain().getOS().startswith("bitrig")) { - if (getToolChain().getArch() == llvm::Triple::x86_64) - CPUName = "x86-64"; - else if (getToolChain().getArch() == llvm::Triple::x86) - CPUName = "i686"; - } else if (getToolChain().getOS().startswith("freebsd")) { - if (getToolChain().getArch() == llvm::Triple::x86_64) - CPUName = "x86-64"; - else if (getToolChain().getArch() == llvm::Triple::x86) - CPUName = "i486"; - } else if (getToolChain().getOS().startswith("netbsd")) { - if (getToolChain().getArch() == llvm::Triple::x86_64) - CPUName = "x86-64"; - else if (getToolChain().getArch() == llvm::Triple::x86) - CPUName = "i486"; - } else { - if (getToolChain().getArch() == llvm::Triple::x86_64) - CPUName = "x86-64"; - else if (getToolChain().getArch() == llvm::Triple::x86) - // All x86 devices running Android have core2 as their common - // denominator. This makes a better choice than pentium4. - CPUName = isAndroid ? "core2" : "pentium4"; - } - } - - if (CPUName) { + if (const char *CPUName = getX86TargetCPU(Args, getToolChain().getTriple())) { CmdArgs.push_back("-target-cpu"); CmdArgs.push_back(CPUName); } @@ -6105,8 +6096,27 @@ void linuxtools::Link::ConstructJob(Compilation &C, const JobAction &JA, CmdArgs.push_back("-plugin"); std::string Plugin = ToolChain.getDriver().Dir + "/../lib/LLVMgold.so"; CmdArgs.push_back(Args.MakeArgString(Plugin)); + + // Try to pass driver level flags relevant to LTO code generation down to + // the plugin. + + // Handle architecture-specific flags for selecting CPU variants. + if (ToolChain.getArch() == llvm::Triple::x86 || + ToolChain.getArch() == llvm::Triple::x86_64) + CmdArgs.push_back( + Args.MakeArgString(Twine("-plugin-opt=mcpu=") + + getX86TargetCPU(Args, ToolChain.getTriple()))); + else if (ToolChain.getArch() == llvm::Triple::arm || + ToolChain.getArch() == llvm::Triple::thumb) + CmdArgs.push_back( + Args.MakeArgString(Twine("-plugin-opt=mcpu=") + + getARMTargetCPU(Args, ToolChain.getTriple()))); + + // FIXME: Factor out logic for MIPS, PPC, and other targets to support this + // as well. } + if (Args.hasArg(options::OPT_Z_Xlinker__no_demangle)) CmdArgs.push_back("--no-demangle"); diff --git a/test/Driver/gold-lto.c b/test/Driver/gold-lto.c index 05ac27aab9..c2e8bdfbc7 100644 --- a/test/Driver/gold-lto.c +++ b/test/Driver/gold-lto.c @@ -1,6 +1,21 @@ // RUN: touch %t.o -// RUN: %clang -target x86_64-pc-linux-gnu -### %t.o -O4 -Wl,-plugin-opt=foo 2> %t.log -// RUN: FileCheck %s < %t.log - -// CHECK: "-plugin" "{{.*}}/LLVMgold.so" -// CHECK: "-plugin-opt=foo" +// +// RUN: %clang -target x86_64-unknown-linux -### %t.o -flto 2>&1 \ +// RUN: -Wl,-plugin-opt=foo \ +// RUN: | FileCheck %s --check-prefix=CHECK-X86-64-BASIC +// CHECK-X86-64-BASIC: "-plugin" "{{.*}}/LLVMgold.so" +// CHECK-X86-64-BASIC: "-plugin-opt=foo" +// +// RUN: %clang -target x86_64-unknown-linux -### %t.o -flto 2>&1 \ +// RUN: -march=corei7 -Wl,-plugin-opt=foo \ +// RUN: | FileCheck %s --check-prefix=CHECK-X86-64-COREI7 +// CHECK-X86-64-COREI7: "-plugin" "{{.*}}/LLVMgold.so" +// CHECK-X86-64-COREI7: "-plugin-opt=mcpu=corei7" +// CHECK-X86-64-COREI7: "-plugin-opt=foo" +// +// RUN: %clang -target arm-unknown-linux -### %t.o -flto 2>&1 \ +// RUN: -march=armv7a -Wl,-plugin-opt=foo \ +// RUN: | FileCheck %s --check-prefix=CHECK-ARM-V7A +// CHECK-ARM-V7A: "-plugin" "{{.*}}/LLVMgold.so" +// CHECK-ARM-V7A: "-plugin-opt=mcpu=cortex-a8" +// CHECK-ARM-V7A: "-plugin-opt=foo" -- cgit v1.2.3