diff options
author | Alon Zakai <alonzakai@gmail.com> | 2017-09-18 16:33:06 -0700 |
---|---|---|
committer | GitHub <noreply@github.com> | 2017-09-18 16:33:06 -0700 |
commit | 0532093e5856662a11cf66cbf59feaeb3acb9c29 (patch) | |
tree | f0ec2dfa924c6a57f8d29886d89a23c5980ced45 /src | |
parent | 8f2f6a13736336ca13d6b4bccb1af6d34f3aae48 (diff) | |
download | binaryen-0532093e5856662a11cf66cbf59feaeb3acb9c29.tar.gz binaryen-0532093e5856662a11cf66cbf59feaeb3acb9c29.tar.bz2 binaryen-0532093e5856662a11cf66cbf59feaeb3acb9c29.zip |
Expressions should not appear twice in the ast (#1191)
Diffstat (limited to 'src')
-rw-r--r-- | src/wasm-emscripten.cpp | 3 | ||||
-rw-r--r-- | src/wasm-validator.h | 3 | ||||
-rw-r--r-- | src/wasm/wasm-validator.cpp | 18 |
3 files changed, 23 insertions, 1 deletions
diff --git a/src/wasm-emscripten.cpp b/src/wasm-emscripten.cpp index 7463ec594..9c617a31e 100644 --- a/src/wasm-emscripten.cpp +++ b/src/wasm-emscripten.cpp @@ -129,7 +129,8 @@ void generateStackAllocFunction(LinkerObject& linker) { Block* block = builder.makeBlock(); block->list.push_back(setStackLocal); block->list.push_back(storeStack); - block->list.push_back(getStackLocal); + GetLocal* getStackLocal2 = builder.makeGetLocal(1, i32); + block->list.push_back(getStackLocal2); block->type = i32; function->body = block; diff --git a/src/wasm-validator.h b/src/wasm-validator.h index 0851d33e8..ceaaee890 100644 --- a/src/wasm-validator.h +++ b/src/wasm-validator.h @@ -39,6 +39,7 @@ #include <set> #include <sstream> +#include <unordered_set> #include "wasm.h" #include "wasm-printing.h" @@ -83,6 +84,8 @@ struct WasmValidator : public PostWalker<WasmValidator> { std::set<Name> labelNames; // Binaryen IR requires that label names must be unique - IR generators must ensure that + std::unordered_set<Expression*> seenExpressions; // expressions must not appear twice + void noteLabelName(Name name); public: diff --git a/src/wasm/wasm-validator.cpp b/src/wasm/wasm-validator.cpp index 5534eb7b9..85e2193fa 100644 --- a/src/wasm/wasm-validator.cpp +++ b/src/wasm/wasm-validator.cpp @@ -559,6 +559,24 @@ void WasmValidator::visitFunction(Function *curr) { shouldBeTrue(breakTargets.empty(), curr->body, "all named break targets must exist"); returnType = unreachable; labelNames.clear(); + // expressions must not be seen more than once + struct Walker : public PostWalker<Walker, UnifiedExpressionVisitor<Walker>> { + std::unordered_set<Expression*>& seen; + std::vector<Expression*> dupes; + + Walker(std::unordered_set<Expression*>& seen) : seen(seen) {} + + void visitExpression(Expression* curr) { + bool inserted; + std::tie(std::ignore, inserted) = seen.insert(curr); + if (!inserted) dupes.push_back(curr); + } + }; + Walker walker(seenExpressions); + walker.walk(curr->body); + for (auto* bad : walker.dupes) { + fail("expression seen more than once in the tree", bad); + } } static bool checkOffset(Expression* curr, Address add, Address max) { |