summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorRui Ueyama <ruiu@google.com>2013-07-29 23:32:22 +0000
committerRui Ueyama <ruiu@google.com>2013-07-29 23:32:22 +0000
commit85cd10ffa0159f1dd4ba4b5401abb48792ea0ffa (patch)
tree91c4619f7ef6204abd64510cd805c0fdca89eeb5
parent4d3de853a2c944a658d3e8470341da75c217fdaa (diff)
downloadbcm5719-llvm-85cd10ffa0159f1dd4ba4b5401abb48792ea0ffa.tar.gz
bcm5719-llvm-85cd10ffa0159f1dd4ba4b5401abb48792ea0ffa.zip
[PECOFF][Driver] Remove quotes from command line arguments.
The command line option in .drectve section may be quoted by double quotes, and if that's the case we have to remove them. llvm-svn: 187390
-rw-r--r--lld/lib/Driver/WinLinkDriver.cpp33
-rw-r--r--lld/unittests/DriverTests/WinLinkDriverTest.cpp12
2 files changed, 32 insertions, 13 deletions
diff --git a/lld/lib/Driver/WinLinkDriver.cpp b/lld/lib/Driver/WinLinkDriver.cpp
index c4516b35d58..768a36d3e60 100644
--- a/lld/lib/Driver/WinLinkDriver.cpp
+++ b/lld/lib/Driver/WinLinkDriver.cpp
@@ -216,6 +216,14 @@ std::vector<StringRef> splitPathList(StringRef str) {
return std::move(ret);
}
+// Removes surrounding single or double quotes from the string. If it's not
+// quoted, return the argument as is.
+StringRef unquote(StringRef str) {
+ bool isQuoted = (str.startswith("\"") && str.endswith("\"")) ||
+ (str.startswith("'") && str.endswith("'"));
+ return isQuoted ? str.substr(1, str.size() - 2) : str;
+}
+
// Handle /failifmatch option.
bool handleFailIfMismatchOption(StringRef option,
std::map<StringRef, StringRef> &mustMatch,
@@ -345,33 +353,33 @@ bool WinLinkDriver::parse(int argc, const char *argv[],
// handle /base
if (llvm::opt::Arg *arg = parsedArgs->getLastArg(OPT_base))
- if (!parseBaseOption(info, arg->getValue(), diagnostics))
+ if (!parseBaseOption(info, unquote(arg->getValue()), diagnostics))
return true;
// handle /stack
if (llvm::opt::Arg *arg = parsedArgs->getLastArg(OPT_stack))
- if (!parseStackOption(info, arg->getValue(), diagnostics))
+ if (!parseStackOption(info, unquote(arg->getValue()), diagnostics))
return true;
// handle /heap
if (llvm::opt::Arg *arg = parsedArgs->getLastArg(OPT_heap))
- if (!parseHeapOption(info, arg->getValue(), diagnostics))
+ if (!parseHeapOption(info, unquote(arg->getValue()), diagnostics))
return true;
// handle /subsystem
if (llvm::opt::Arg *arg = parsedArgs->getLastArg(OPT_subsystem))
- if (!parseSubsystemOption(info, arg->getValue(), diagnostics))
+ if (!parseSubsystemOption(info, unquote(arg->getValue()), diagnostics))
return true;
// handle /entry
if (llvm::opt::Arg *arg = parsedArgs->getLastArg(OPT_entry))
- info.setEntrySymbolName(arg->getValue());
+ info.setEntrySymbolName(unquote(arg->getValue()));
// handle /libpath
for (llvm::opt::arg_iterator it = parsedArgs->filtered_begin(OPT_libpath),
ie = parsedArgs->filtered_end();
it != ie; ++it) {
- info.appendInputSearchPath((*it)->getValue());
+ info.appendInputSearchPath(unquote((*it)->getValue()));
}
// handle /force
@@ -398,19 +406,19 @@ bool WinLinkDriver::parse(int argc, const char *argv[],
for (llvm::opt::arg_iterator it = parsedArgs->filtered_begin(OPT_incl),
ie = parsedArgs->filtered_end();
it != ie; ++it) {
- info.addInitialUndefinedSymbol((*it)->getValue());
+ info.addInitialUndefinedSymbol(unquote((*it)->getValue()));
}
// handle /out
if (llvm::opt::Arg *outpath = parsedArgs->getLastArg(OPT_out))
- info.setOutputPath(outpath->getValue());
+ info.setOutputPath(unquote(outpath->getValue()));
// handle /defaultlib
std::vector<StringRef> defaultLibs;
for (llvm::opt::arg_iterator it = parsedArgs->filtered_begin(OPT_defaultlib),
ie = parsedArgs->filtered_end();
it != ie; ++it) {
- defaultLibs.push_back((*it)->getValue());
+ defaultLibs.push_back(unquote((*it)->getValue()));
}
// Handle /failifmismatch. /failifmismatch is the hidden linker option behind
@@ -426,7 +434,8 @@ bool WinLinkDriver::parse(int argc, const char *argv[],
it = parsedArgs->filtered_begin(OPT_failifmismatch),
ie = parsedArgs->filtered_end();
it != ie; ++it) {
- if (!handleFailIfMismatchOption((*it)->getValue(), mustMatch, diagnostics))
+ if (!handleFailIfMismatchOption(unquote((*it)->getValue()),
+ mustMatch, diagnostics))
return true;
}
@@ -435,13 +444,13 @@ bool WinLinkDriver::parse(int argc, const char *argv[],
for (llvm::opt::arg_iterator it = parsedArgs->filtered_begin(OPT_INPUT),
ie = parsedArgs->filtered_end();
it != ie; ++it) {
- inputPaths.push_back((*it)->getValue());
+ inputPaths.push_back(unquote((*it)->getValue()));
}
// Arguments after "--" are also input files
if (doubleDashPosition > 0)
for (int i = doubleDashPosition + 1; i < argc; ++i)
- inputPaths.push_back(argv[i]);
+ inputPaths.push_back(unquote(argv[i]));
// Add input files specified via the command line.
for (const StringRef path : inputPaths)
diff --git a/lld/unittests/DriverTests/WinLinkDriverTest.cpp b/lld/unittests/DriverTests/WinLinkDriverTest.cpp
index d32f22259b4..f4fd29df084 100644
--- a/lld/unittests/DriverTests/WinLinkDriverTest.cpp
+++ b/lld/unittests/DriverTests/WinLinkDriverTest.cpp
@@ -66,6 +66,16 @@ TEST_F(WinLinkParserTest, UnixStyleOption) {
EXPECT_EQ("a.obj", inputFile(0));
}
+TEST_F(WinLinkParserTest, Quote) {
+ EXPECT_FALSE(parse("link.exe", "/subsystem:\"console\"", "-out:'a.exe'",
+ "/defaultlib:'user32.lib'", "'a.obj'", nullptr));
+ EXPECT_EQ(llvm::COFF::IMAGE_SUBSYSTEM_WINDOWS_CUI, _info.getSubsystem());
+ EXPECT_EQ("a.exe", _info.outputPath());
+ EXPECT_EQ(2, inputFileCount());
+ EXPECT_EQ("a.obj", inputFile(0));
+ EXPECT_EQ("user32.lib", inputFile(1));
+}
+
TEST_F(WinLinkParserTest, Mllvm) {
EXPECT_FALSE(parse("link.exe", "-mllvm", "-debug", "a.obj", nullptr));
const std::vector<const char *> &options = _info.llvmOptions();
@@ -205,7 +215,7 @@ TEST_F(WinLinkParserTest, NoInputFiles) {
TEST_F(WinLinkParserTest, FailIfMismatch_Match) {
EXPECT_FALSE(parse("link.exe", "/failifmismatch:foo=bar",
- "/failifmismatch:foo=bar", "/failifmismatch:abc=def",
+ "/failifmismatch:\"foo=bar\"", "/failifmismatch:abc=def",
"a.out", nullptr));
}
OpenPOWER on IntegriCloud