[Mesa-dev] [PATCH v3] clover: Pass unquoted compiler arguments to Clang
Vedran Miletić
vedran at miletic.net
Mon Sep 19 18:36:56 UTC 2016
OpenCL apps can quote arguments they pass to the OpenCL compiler, most
commonly include paths containing spaces.
If the Clang OpenCL compiler was called via a shell, the shell would
split the arguments with respect to to quotes and then remove quotes
before passing the arguments to the compiler. Since we call Clang as a
library, we have to split the argument with respect to quotes and then
remove quotes before passing the arguments.
v2: move to tokenize(), remove throwing of CL_INVALID_COMPILER_OPTIONS
v3: simplify parsing logic, use more C++11
---
src/gallium/state_trackers/clover/llvm/util.hpp | 33 ++++++++++++++++++++++---
1 file changed, 29 insertions(+), 4 deletions(-)
diff --git a/src/gallium/state_trackers/clover/llvm/util.hpp b/src/gallium/state_trackers/clover/llvm/util.hpp
index 8db6f20..c770dd8 100644
--- a/src/gallium/state_trackers/clover/llvm/util.hpp
+++ b/src/gallium/state_trackers/clover/llvm/util.hpp
@@ -42,11 +42,36 @@ namespace clover {
inline std::vector<std::string>
tokenize(const std::string &s) {
std::vector<std::string> ss;
- std::istringstream iss(s);
- std::string t;
+ std::ostringstream oss;
- while (getline(iss, t, ' '))
- ss.push_back(t);
+ // OpenCL programs can pass a single or double quoted argument, most
+ // frequently include path. This is useful so that the path containing
+ // spaces is treated as a single argument, but we should anyhow unquote
+ // quoted arguments before passing them to the compiler.
+ // We do not want to avoid using std::string::replace here, as include
+ // path can contain quotes in file names.
+ bool escape_next = false;
+ bool in_quote_double = false;
+ bool in_quote_single = false;
+ for (auto c : s) {
+ if (escape_next) {
+ oss.put(c);
+ escape_next = false;
+ } else if (c == '\\') {
+ escape_next = true;
+ } else if (c == '"' && !in_quote_single) {
+ in_quote_double = !in_quote_double;
+ } else if (c == '\'' && !in_quote_double) {
+ in_quote_single = !in_quote_single;
+ } else if (c != ' ' || in_quote_single || in_quote_double) {
+ oss.put(c);
+ } else if (oss.tellp() > 0) {
+ ss.emplace_back(oss.str());
+ oss.str("");
+ }
+ }
+ if (oss.tellp() > 0)
+ ss.emplace_back(oss.str());
return ss;
}
--
2.7.4
More information about the mesa-dev
mailing list