summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorNico Weber <nicolasweber@gmx.de>2016-04-25 21:15:49 +0000
committerNico Weber <nicolasweber@gmx.de>2016-04-25 21:15:49 +0000
commit3d299b5bbdd7713c52dd495ec818100ceba1f80e (patch)
treed72288beb85cf1114a2da98aba0cfdad08738676
parent15a13f4ca1516737c5e4d1d8d72ba56a6a77005e (diff)
driver: Add a `--rsp-quoting` flag to pick response file quoting.
Currently, clang-cl always uses Windows style for unquoting, and clang always uses POSIX style for unquoting. With this flag, it's possible to change these defaults. In general, response file quoting should match the shell the response file is used in. On Windows, it's possible to run clang-cl in a bash shell, or clang in cmd.exe, so a flag for overriding the default behavior is natural there. On non-Windows, Windows quoting probably never makes sense (except maybe in Wine), but having clang-cl behave differently based on the host OS seems strange too. So require that people who want to use posix-style response files with clang-cl on non-Windows pass --rsp-quoting=posix. http://reviews.llvm.org/D19425 git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@267474 91177308-0d34-0410-b5e6-96231b3b80d8
-rw-r--r--include/clang/Driver/Options.td3
-rw-r--r--lib/Driver/Driver.cpp3
-rw-r--r--test/Driver/at_file_win.c34
-rw-r--r--test/Driver/at_file_win.c.args13
-rw-r--r--tools/driver/driver.cpp17
5 files changed, 64 insertions, 6 deletions
diff --git a/include/clang/Driver/Options.td b/include/clang/Driver/Options.td
index 9bc6bbc697..d2e6657288 100644
--- a/include/clang/Driver/Options.td
+++ b/include/clang/Driver/Options.td
@@ -152,6 +152,9 @@ class InternalDriverOpt : Group<internal_driver_Group>,
def driver_mode : Joined<["--"], "driver-mode=">, Group<internal_driver_Group>,
Flags<[CoreOption, DriverOption, HelpHidden]>,
HelpText<"Set the driver mode to either 'gcc', 'g++', 'cpp', or 'cl'">;
+def rsp_quoting : Joined<["--"], "rsp-quoting=">, Group<internal_driver_Group>,
+ Flags<[CoreOption, DriverOption, HelpHidden]>,
+ HelpText<"Set the rsp quoting to either 'posix', or 'windows'">;
def ccc_gcc_name : Separate<["-"], "ccc-gcc-name">, InternalDriverOpt,
HelpText<"Name for native GCC compiler">,
MetaVarName<"<gcc-path>">;
diff --git a/lib/Driver/Driver.cpp b/lib/Driver/Driver.cpp
index b855b9c592..7ff403baff 100644
--- a/lib/Driver/Driver.cpp
+++ b/lib/Driver/Driver.cpp
@@ -1813,8 +1813,9 @@ void Driver::BuildJobs(Compilation &C) const {
// Claim -### here.
(void)C.getArgs().hasArg(options::OPT__HASH_HASH_HASH);
- // Claim --driver-mode, it was handled earlier.
+ // Claim --driver-mode, --rsp-quoting, it was handled earlier.
(void)C.getArgs().hasArg(options::OPT_driver_mode);
+ (void)C.getArgs().hasArg(options::OPT_rsp_quoting);
for (Arg *A : C.getArgs()) {
// FIXME: It would be nice to be able to send the argument to the
diff --git a/test/Driver/at_file_win.c b/test/Driver/at_file_win.c
new file mode 100644
index 0000000000..9a8ede548a
--- /dev/null
+++ b/test/Driver/at_file_win.c
@@ -0,0 +1,34 @@
+// RUN: %clang --rsp-quoting=windows -E %s @%s.args -o %t.log
+// RUN: FileCheck --input-file=%t.log %s
+
+// CHECK: bar1
+// CHECK-NEXT: bar2 zed2
+// CHECK-NEXT: bar3 zed3
+// CHECK-NEXT: bar4 zed4
+// CHECK-NEXT: bar5 zed5
+// CHECK-NEXT: 'bar6 zed6'
+// CHECK-NEXT: 'bar7 zed7'
+// CHECK-NEXT: foo8bar8zed8
+// CHECK-NEXT: foo9\'bar9\'zed9
+// CHECK-NEXT: foo10"bar10"zed10
+// CHECK: bar
+// CHECK: zed12
+// CHECK: one\two
+// CHECK: c:\foo\bar.c
+
+foo1
+foo2
+foo3
+foo4
+foo5
+foo6
+foo7
+foo8
+foo9
+foo10
+#ifdef foo11
+bar
+#endif
+foo12
+foo13
+foo14
diff --git a/test/Driver/at_file_win.c.args b/test/Driver/at_file_win.c.args
new file mode 100644
index 0000000000..df109e4d5f
--- /dev/null
+++ b/test/Driver/at_file_win.c.args
@@ -0,0 +1,13 @@
+-Dfoo1=bar1 -Dfoo2="bar2 zed2"
+-Dfoo3="bar3 zed3"
+"-Dfoo4=bar4 zed4"
+"-Dfoo5=bar5 zed5"
+-Dfoo6="'bar6 zed6'"
+-Dfoo7='"bar7 zed7"'
+-Dfoo8=foo8"bar8"zed8
+-Dfoo9=foo9\'bar9\'zed9
+-Dfoo10=foo10\"bar10\"zed10
+-D foo11
+-Dfoo12=zed12
+-Dfoo13=one\two
+-Dfoo14=c:\foo\bar.c
diff --git a/tools/driver/driver.cpp b/tools/driver/driver.cpp
index b7097e3faf..b74de08199 100644
--- a/tools/driver/driver.cpp
+++ b/tools/driver/driver.cpp
@@ -345,17 +345,24 @@ int main(int argc_, const char **argv_) {
}) != argv.end()) {
ClangCLMode = true;
}
+ enum { Default, POSIX, Windows } RSPQuoting = Default;
+ for (const char *F : argv) {
+ if (strcmp(F, "--rsp-quoting=posix") == 0)
+ RSPQuoting = POSIX;
+ else if (strcmp(F, "--rsp-quoting=windows") == 0)
+ RSPQuoting = Windows;
+ }
// Determines whether we want nullptr markers in argv to indicate response
// files end-of-lines. We only use this for the /LINK driver argument with
// clang-cl.exe on Windows.
- bool MarkEOLs = false;
+ bool MarkEOLs = ClangCLMode;
- llvm::cl::TokenizerCallback Tokenizer = &llvm::cl::TokenizeGNUCommandLine;
- if (ClangCLMode) {
+ llvm::cl::TokenizerCallback Tokenizer;
+ if (RSPQuoting == Windows || (RSPQuoting == Default && ClangCLMode))
Tokenizer = &llvm::cl::TokenizeWindowsCommandLine;
- MarkEOLs = true;
- }
+ else
+ Tokenizer = &llvm::cl::TokenizeGNUCommandLine;
if (MarkEOLs && argv.size() > 1 && StringRef(argv[1]).startswith("-cc1"))
MarkEOLs = false;