diff --git a/clang/include/clang/Basic/DiagnosticDriverKinds.td b/clang/include/clang/Basic/DiagnosticDriverKinds.td index 9a055b8..176d5b7 100644 --- a/clang/include/clang/Basic/DiagnosticDriverKinds.td +++ b/clang/include/clang/Basic/DiagnosticDriverKinds.td @@ -168,6 +168,9 @@ def warn_drv_enabling_rtti_with_exceptions : Warning< def warn_drv_disabling_vptr_no_rtti_default : Warning< "implicitly disabling vptr sanitizer because rtti wasn't enabled">, InGroup>; +def warn_mdynamic_no_pic_override : Warning< + "'-mdynamic-no-pic' overrides '-fpic', '-fPIC', '-fpie' or '-fPIE'">, + InGroup; def note_drv_command_failed_diag_msg : Note< "diagnostic msg: %0">; diff --git a/clang/include/clang/Driver/Options.td b/clang/include/clang/Driver/Options.td index 4e1afbe..16022ea 100644 --- a/clang/include/clang/Driver/Options.td +++ b/clang/include/clang/Driver/Options.td @@ -1136,6 +1136,7 @@ def mcmodel_EQ : Joined<["-"], "mcmodel=">, Group; def mconstant_cfstrings : Flag<["-"], "mconstant-cfstrings">, Group; def mcpu_EQ : Joined<["-"], "mcpu=">, Group; def mdynamic_no_pic : Joined<["-"], "mdynamic-no-pic">, Group; +def mno_dynamic_no_pic : Joined<["-"], "mno-dynamic-no-pic">, Group; def mfix_and_continue : Flag<["-"], "mfix-and-continue">, Group; def mieee_fp : Flag<["-"], "mieee-fp">, Group; def minline_all_stringops : Flag<["-"], "minline-all-stringops">, Group; diff --git a/clang/lib/Driver/Tools.cpp b/clang/lib/Driver/Tools.cpp index 7b661a7..d81f584 100644 --- a/clang/lib/Driver/Tools.cpp +++ b/clang/lib/Driver/Tools.cpp @@ -2836,14 +2836,27 @@ void Clang::ConstructJob(Compilation &C, const JobAction &JA, if (Args.hasArg(options::OPT_static)) PIC = PIE = false; - if (Arg *A = Args.getLastArg(options::OPT_mdynamic_no_pic)) { - // This is a very special mode. It trumps the other modes, almost no one - // uses it, and it isn't even valid on any OS but Darwin. - if (!getToolChain().getTriple().isOSDarwin()) - D.Diag(diag::err_drv_unsupported_opt_for_target) - << A->getSpelling() << getToolChain().getTriple().str(); + // Deal with the special case of mdynamic-no-pic. + bool IsDynamicNoPic = false; + if (Arg *A = Args.getLastArg(options::OPT_mdynamic_no_pic, + options::OPT_mno_dynamic_no_pic)) { + if (A->getOption().getID() == options::OPT_mdynamic_no_pic) { + // This is a very special mode which isn't valid on any OS but + // Darwin. + if (getToolChain().getTriple().isOSDarwin()) + IsDynamicNoPic = true; + else + D.Diag(diag::err_drv_unsupported_opt_for_target) + << A->getSpelling() << getToolChain().getTriple().str(); + } + } - // FIXME: Warn when this flag trumps some other PIC or PIE flag. + if (IsDynamicNoPic) { + // This mode trumps all other PIC and PIE modes. The only current use + // case is for 32bit binaries (on Darwin, as noted above). + // Warn if it's presented along with any other PIC or PIE option. + if (LastPICArg) + D.Diag(diag::warn_mdynamic_no_pic_override); CmdArgs.push_back("-mrelocation-model"); CmdArgs.push_back("dynamic-no-pic"); diff --git a/clang/test/Driver/pic.c b/clang/test/Driver/pic.c index 3a14d61..10d8ee9 100644 --- a/clang/test/Driver/pic.c +++ b/clang/test/Driver/pic.c @@ -42,6 +42,8 @@ // // CHECK-NO-UNUSED-ARG-NOT: argument unused during compilation // +// CHECK-DARWIN-DYNAMIC-NO-PIC-OVERRIDE: warning: '-mdynamic-no-pic' overrides '-fpic', '-fPIC', '-fpie' or '-fPIE' +// // RUN: %clang -c %s -target i386-unknown-unknown -### 2>&1 \ // RUN: | FileCheck %s --check-prefix=CHECK-NO-PIC // RUN: %clang -c %s -target i386-unknown-unknown -fpic -### 2>&1 \ @@ -187,12 +189,21 @@ // RUN: | FileCheck %s --check-prefix=CHECK-DYNAMIC-NO-PIC-32 // RUN: %clang -c %s -target i386-apple-darwin -mdynamic-no-pic -fpie -### 2>&1 \ // RUN: | FileCheck %s --check-prefix=CHECK-DYNAMIC-NO-PIC-32 +// RUN: %clang -c %s -target i386-apple-darwin -mdynamic-no-pic \ +// RUN: -mno-dynamic-no-pic -### 2>&1 | FileCheck %s --check-prefix=CHECK-PIC2 +// RUN: %clang -c %s -target i386-apple-darwin -mdynamic-no-pic -fPIC -### 2>&1 \ +// RUN: | FileCheck %s --check-prefix=CHECK-DARWIN-DYNAMIC-NO-PIC-OVERRIDE +// // RUN: %clang -c %s -target x86_64-apple-darwin -mdynamic-no-pic -### 2>&1 \ // RUN: | FileCheck %s --check-prefix=CHECK-DYNAMIC-NO-PIC-64 // RUN: %clang -c %s -target x86_64-apple-darwin -mdynamic-no-pic -fno-pic -### 2>&1 \ // RUN: | FileCheck %s --check-prefix=CHECK-DYNAMIC-NO-PIC-64 // RUN: %clang -c %s -target x86_64-apple-darwin -mdynamic-no-pic -fpie -### 2>&1 \ // RUN: | FileCheck %s --check-prefix=CHECK-DYNAMIC-NO-PIC-64 +// RUN: %clang -c %s -target x86_64-apple-darwin -mdynamic-no-pic \ +// RUN: -mno-dynamic-no-pic -### 2>&1 | FileCheck %s --check-prefix=CHECK-PIC2 +// RUN: %clang -c %s -target x86_64-apple-darwin -mdynamic-no-pic -fPIC -### 2>&1 \ +// RUN: | FileCheck %s --check-prefix=CHECK-DARWIN-DYNAMIC-NO-PIC-OVERRIDE // // Checks for ARM+Apple+IOS including -fapple-kext, -mkernel, and iphoneos // version boundaries.