diff options
-rw-r--r-- | src/passes/Bysyncify.cpp | 16 | ||||
-rw-r--r-- | src/support/name.h | 6 | ||||
-rw-r--r-- | src/support/string.h | 69 |
3 files changed, 82 insertions, 9 deletions
diff --git a/src/passes/Bysyncify.cpp b/src/passes/Bysyncify.cpp index 5e2f73e5c..cb85f0b0a 100644 --- a/src/passes/Bysyncify.cpp +++ b/src/passes/Bysyncify.cpp @@ -185,6 +185,7 @@ // Each module.base in that comma-separated list will be considered to // be an import that can unwind/rewind, and all others are assumed not to // (aside from the bysyncify.* imports, which are always assumed to). +// Each entry can end in a '*' in which case it is matched as a prefix. // // --pass-arg=bysyncify-ignore-imports // @@ -206,6 +207,7 @@ #include "ir/module-utils.h" #include "ir/utils.h" #include "pass.h" +#include "support/string.h" #include "support/unique_deferring_queue.h" #include "wasm-builder.h" #include "wasm.h" @@ -960,14 +962,11 @@ struct Bysyncify : public Pass { // Find which things can change the state. auto stateChangingImports = runner->options.getArgumentOrDefault("bysyncify-imports", ""); - std::string separator = ","; auto ignoreImports = runner->options.getArgumentOrDefault("bysyncify-ignore-imports", ""); bool allImportsCanChangeState = stateChangingImports == "" && ignoreImports == ""; - if (!allImportsCanChangeState) { - stateChangingImports = separator + stateChangingImports + separator; - } + String::Split listedImports(stateChangingImports, ","); auto ignoreIndirect = runner->options.getArgumentOrDefault("bysyncify-ignore-indirect", ""); @@ -978,8 +977,13 @@ struct Bysyncify : public Pass { if (allImportsCanChangeState) { return true; } - std::string full = separator + module.str + '.' + base.str + separator; - return stateChangingImports.find(full) != std::string::npos; + std::string full = std::string(module.str) + '.' + base.str; + for (auto& listedImport : listedImports) { + if (String::wildcardMatch(listedImport, full)) { + return true; + } + } + return false; }, ignoreIndirect == ""); diff --git a/src/support/name.h b/src/support/name.h index 6f17c3ebf..b6242aabc 100644 --- a/src/support/name.h +++ b/src/support/name.h @@ -14,8 +14,8 @@ * limitations under the License. */ -#ifndef wasm_support_string_h -#define wasm_support_string_h +#ifndef wasm_support_name_h +#define wasm_support_name_h #include <cstring> @@ -65,4 +65,4 @@ template<> struct hash<wasm::Name> : hash<cashew::IString> {}; } // namespace std -#endif // wasm_support_string_h +#endif // wasm_support_name_h diff --git a/src/support/string.h b/src/support/string.h new file mode 100644 index 000000000..c8a8cb445 --- /dev/null +++ b/src/support/string.h @@ -0,0 +1,69 @@ +/* + * Copyright 2019 WebAssembly Community Group participants + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +// +// String helpers. +// + +#ifndef wasm_support_string_h +#define wasm_support_string_h + +#include <string> +#include <vector> + +namespace wasm { + +namespace String { + +// Creates a vector of the split parts of a string, by a delimiter. +class Split : public std::vector<std::string> { +public: + Split(const std::string& input, const std::string& delim) { + size_t lastEnd = 0; + while (lastEnd < input.size()) { + auto nextDelim = input.find(delim, lastEnd); + if (nextDelim == std::string::npos) { + nextDelim = input.size(); + } + (*this).push_back(input.substr(lastEnd, nextDelim - lastEnd)); + lastEnd = nextDelim + delim.size(); + } + } +}; + +// Does a simple wildcard match between a pattern and a value. Currently +// supports a '*' at the end of the pattern. +inline bool wildcardMatch(const std::string& pattern, + const std::string& value) { + for (size_t i = 0; i < pattern.size(); i++) { + if (i >= value.size()) { + return false; + } + if (pattern[i] == '*') { + return true; + } + if (pattern[i] != value[i]) { + return false; + } + } + return value.size() == pattern.size(); +} + +} // namespace String + +} // namespace wasm + +#endif // wasm_support_string_h |