Let -static-pie win if it is specified along with -pie or -static.

Also, disallow specifying -no-pie/-nopie along with -static-pie.

Differential Revision: https://reviews.llvm.org/D59841

llvm-svn: 361312
This commit is contained in:
Siva Chandra 2019-05-21 21:09:05 +00:00
parent 17fdf1d383
commit 8692af253c
3 changed files with 62 additions and 7 deletions

View File

@ -458,4 +458,5 @@ def warn_drv_libstdcxx_not_found : Warning<
"command line to use the libc++ standard library instead">, "command line to use the libc++ standard library instead">,
InGroup<DiagGroup<"stdlibcxx-not-found">>; InGroup<DiagGroup<"stdlibcxx-not-found">>;
def err_drv_cannot_mix_options : Error<"cannot specify '%1' along with '%0'">;
} }

View File

@ -311,7 +311,7 @@ static const char *getLDMOption(const llvm::Triple &T, const ArgList &Args) {
static bool getPIE(const ArgList &Args, const toolchains::Linux &ToolChain) { static bool getPIE(const ArgList &Args, const toolchains::Linux &ToolChain) {
if (Args.hasArg(options::OPT_shared) || Args.hasArg(options::OPT_static) || if (Args.hasArg(options::OPT_shared) || Args.hasArg(options::OPT_static) ||
Args.hasArg(options::OPT_r)) Args.hasArg(options::OPT_r) || Args.hasArg(options::OPT_static_pie))
return false; return false;
Arg *A = Args.getLastArg(options::OPT_pie, options::OPT_no_pie, Arg *A = Args.getLastArg(options::OPT_pie, options::OPT_no_pie,
@ -321,6 +321,26 @@ static bool getPIE(const ArgList &Args, const toolchains::Linux &ToolChain) {
return A->getOption().matches(options::OPT_pie); return A->getOption().matches(options::OPT_pie);
} }
static bool getStaticPIE(const ArgList &Args,
const toolchains::Linux &ToolChain) {
bool HasStaticPIE = Args.hasArg(options::OPT_static_pie);
// -no-pie is an alias for -nopie. So, handling -nopie takes care of
// -no-pie as well.
if (HasStaticPIE && Args.hasArg(options::OPT_nopie)) {
const Driver &D = ToolChain.getDriver();
const llvm::opt::OptTable &Opts = D.getOpts();
const char *StaticPIEName = Opts.getOptionName(options::OPT_static_pie);
const char *NoPIEName = Opts.getOptionName(options::OPT_nopie);
D.Diag(diag::err_drv_cannot_mix_options) << StaticPIEName << NoPIEName;
}
return HasStaticPIE;
}
static bool getStatic(const ArgList &Args) {
return Args.hasArg(options::OPT_static) &&
!Args.hasArg(options::OPT_static_pie);
}
void tools::gnutools::Linker::ConstructJob(Compilation &C, const JobAction &JA, void tools::gnutools::Linker::ConstructJob(Compilation &C, const JobAction &JA,
const InputInfo &Output, const InputInfo &Output,
const InputInfoList &Inputs, const InputInfoList &Inputs,
@ -336,7 +356,8 @@ void tools::gnutools::Linker::ConstructJob(Compilation &C, const JobAction &JA,
const bool isAndroid = ToolChain.getTriple().isAndroid(); const bool isAndroid = ToolChain.getTriple().isAndroid();
const bool IsIAMCU = ToolChain.getTriple().isOSIAMCU(); const bool IsIAMCU = ToolChain.getTriple().isOSIAMCU();
const bool IsPIE = getPIE(Args, ToolChain); const bool IsPIE = getPIE(Args, ToolChain);
const bool IsStaticPIE = Args.hasArg(options::OPT_static_pie); const bool IsStaticPIE = getStaticPIE(Args, ToolChain);
const bool IsStatic = getStatic(Args);
const bool HasCRTBeginEndFiles = const bool HasCRTBeginEndFiles =
ToolChain.getTriple().hasEnvironment() || ToolChain.getTriple().hasEnvironment() ||
(ToolChain.getTriple().getVendor() != llvm::Triple::MipsTechnologies); (ToolChain.getTriple().getVendor() != llvm::Triple::MipsTechnologies);
@ -408,7 +429,7 @@ void tools::gnutools::Linker::ConstructJob(Compilation &C, const JobAction &JA,
return; return;
} }
if (Args.hasArg(options::OPT_static)) { if (IsStatic) {
if (Arch == llvm::Triple::arm || Arch == llvm::Triple::armeb || if (Arch == llvm::Triple::arm || Arch == llvm::Triple::armeb ||
Arch == llvm::Triple::thumb || Arch == llvm::Triple::thumbeb) Arch == llvm::Triple::thumb || Arch == llvm::Triple::thumbeb)
CmdArgs.push_back("-Bstatic"); CmdArgs.push_back("-Bstatic");
@ -418,7 +439,7 @@ void tools::gnutools::Linker::ConstructJob(Compilation &C, const JobAction &JA,
CmdArgs.push_back("-shared"); CmdArgs.push_back("-shared");
} }
if (!Args.hasArg(options::OPT_static)) { if (!IsStatic) {
if (Args.hasArg(options::OPT_rdynamic)) if (Args.hasArg(options::OPT_rdynamic))
CmdArgs.push_back("-export-dynamic"); CmdArgs.push_back("-export-dynamic");
@ -465,7 +486,7 @@ void tools::gnutools::Linker::ConstructJob(Compilation &C, const JobAction &JA,
} }
if (P.empty()) { if (P.empty()) {
const char *crtbegin; const char *crtbegin;
if (Args.hasArg(options::OPT_static)) if (IsStatic)
crtbegin = isAndroid ? "crtbegin_static.o" : "crtbeginT.o"; crtbegin = isAndroid ? "crtbegin_static.o" : "crtbeginT.o";
else if (Args.hasArg(options::OPT_shared)) else if (Args.hasArg(options::OPT_shared))
crtbegin = isAndroid ? "crtbegin_so.o" : "crtbeginS.o"; crtbegin = isAndroid ? "crtbegin_so.o" : "crtbeginS.o";
@ -520,7 +541,7 @@ void tools::gnutools::Linker::ConstructJob(Compilation &C, const JobAction &JA,
if (!Args.hasArg(options::OPT_nostdlib)) { if (!Args.hasArg(options::OPT_nostdlib)) {
if (!Args.hasArg(options::OPT_nodefaultlibs)) { if (!Args.hasArg(options::OPT_nodefaultlibs)) {
if (Args.hasArg(options::OPT_static) || IsStaticPIE) if (IsStatic || IsStaticPIE)
CmdArgs.push_back("--start-group"); CmdArgs.push_back("--start-group");
if (NeedsSanitizerDeps) if (NeedsSanitizerDeps)
@ -556,7 +577,7 @@ void tools::gnutools::Linker::ConstructJob(Compilation &C, const JobAction &JA,
if (IsIAMCU) if (IsIAMCU)
CmdArgs.push_back("-lgloss"); CmdArgs.push_back("-lgloss");
if (Args.hasArg(options::OPT_static) || IsStaticPIE) if (IsStatic || IsStaticPIE)
CmdArgs.push_back("--end-group"); CmdArgs.push_back("--end-group");
else else
AddRunTimeLibs(ToolChain, D, CmdArgs, Args); AddRunTimeLibs(ToolChain, D, CmdArgs, Args);

View File

@ -194,6 +194,39 @@
// CHECK-CLANG-LD-STATIC-PIE: "{{.*}}rcrt1.o" // CHECK-CLANG-LD-STATIC-PIE: "{{.*}}rcrt1.o"
// CHECK-CLANG-LD-STATIC-PIE: "--start-group" "-lgcc" "-lgcc_eh" "-lc" "--end-group" // CHECK-CLANG-LD-STATIC-PIE: "--start-group" "-lgcc" "-lgcc_eh" "-lc" "--end-group"
// //
// RUN: %clang -static-pie -pie -no-canonical-prefixes %s -### -o %t.o 2>&1 \
// RUN: --target=x86_64-unknown-linux -rtlib=platform \
// RUN: --gcc-toolchain="" \
// RUN: --sysroot=%S/Inputs/basic_linux_tree \
// RUN: | FileCheck --check-prefix=CHECK-CLANG-LD-STATIC-PIE-PIE %s
// CHECK-CLANG-LD-STATIC-PIE-PIE: "{{.*}}ld{{(.exe)?}}" "--sysroot=[[SYSROOT:[^"]+]]"
// CHECK-CLANG-LD-STATIC-PIE-PIE: "-static"
// CHECK-CLANG-LD-STATIC-PIE-PIE: "-pie"
// CHECK-CLANG-LD-STATIC-PIE-PIE: "--no-dynamic-linker"
// CHECK-CLANG-LD-STATIC-PIE-PIE: "-m" "elf_x86_64"
// CHECK-CLANG-LD-STATIC-PIE-PIE: "{{.*}}rcrt1.o"
// CHECK-CLANG-LD-STATIC-PIE-PIE: "--start-group" "-lgcc" "-lgcc_eh" "-lc" "--end-group"
//
// RUN: %clang -static-pie -static -no-canonical-prefixes %s -### -o %t.o 2>&1 \
// RUN: --target=x86_64-unknown-linux -rtlib=platform \
// RUN: --gcc-toolchain="" \
// RUN: --sysroot=%S/Inputs/basic_linux_tree \
// RUN: | FileCheck --check-prefix=CHECK-CLANG-LD-STATIC-PIE-STATIC %s
// CHECK-CLANG-LD-STATIC-PIE-STATIC: "{{.*}}ld{{(.exe)?}}" "--sysroot=[[SYSROOT:[^"]+]]"
// CHECK-CLANG-LD-STATIC-PIE-STATIC: "-static"
// CHECK-CLANG-LD-STATIC-PIE-STATIC: "-pie"
// CHECK-CLANG-LD-STATIC-PIE-STATIC: "--no-dynamic-linker"
// CHECK-CLANG-LD-STATIC-PIE-STATIC: "-m" "elf_x86_64"
// CHECK-CLANG-LD-STATIC-PIE-STATIC: "{{.*}}rcrt1.o"
// CHECK-CLANG-LD-STATIC-PIE-STATIC: "--start-group" "-lgcc" "-lgcc_eh" "-lc" "--end-group"
//
// RUN: %clang -static-pie -nopie -no-canonical-prefixes %s -### -o %t.o 2>&1 \
// RUN: --target=x86_64-unknown-linux -rtlib=platform \
// RUN: --gcc-toolchain="" \
// RUN: --sysroot=%S/Inputs/basic_linux_tree \
// RUN: | FileCheck --check-prefix=CHECK-CLANG-LD-STATIC-PIE-NOPIE %s
// CHECK-CLANG-LD-STATIC-PIE-NOPIE: error: cannot specify 'nopie' along with 'static-pie'
//
// RUN: %clang -dynamic -no-canonical-prefixes %s -### -o %t.o 2>&1 \ // RUN: %clang -dynamic -no-canonical-prefixes %s -### -o %t.o 2>&1 \
// RUN: --target=x86_64-unknown-linux -rtlib=platform \ // RUN: --target=x86_64-unknown-linux -rtlib=platform \
// RUN: --gcc-toolchain="" \ // RUN: --gcc-toolchain="" \