summaryrefslogtreecommitdiff
path: root/src/ast_utils.h
diff options
context:
space:
mode:
authorAlon Zakai <alonzakai@gmail.com>2016-09-16 10:34:44 -0700
committerGitHub <noreply@github.com>2016-09-16 10:34:44 -0700
commit7292ef9c863a0766c697cc0a77516447ff652820 (patch)
treee296b38cf2181d3a51a293664509000bbd625bc4 /src/ast_utils.h
parent22548bf789359be1f3c14aa41ffd4a23fda38542 (diff)
parent88c92cbfe7d9f69fa8605fa406e5dbb2ac628172 (diff)
downloadbinaryen-7292ef9c863a0766c697cc0a77516447ff652820.tar.gz
binaryen-7292ef9c863a0766c697cc0a77516447ff652820.tar.bz2
binaryen-7292ef9c863a0766c697cc0a77516447ff652820.zip
Merge pull request #699 from WebAssembly/opts
Fuzz bug fixes
Diffstat (limited to 'src/ast_utils.h')
-rw-r--r--src/ast_utils.h20
1 files changed, 10 insertions, 10 deletions
diff --git a/src/ast_utils.h b/src/ast_utils.h
index 4664f22ae..ff5d93e02 100644
--- a/src/ast_utils.h
+++ b/src/ast_utils.h
@@ -51,12 +51,14 @@ struct BreakSeeker : public PostWalker<BreakSeeker, Visitor<BreakSeeker>> {
}
static bool has(Expression* tree, Name target) {
+ if (!target.is()) return false;
BreakSeeker breakSeeker(target);
breakSeeker.walk(tree);
return breakSeeker.found > 0;
}
static Index count(Expression* tree, Name target) {
+ if (!target.is()) return 0;
BreakSeeker breakSeeker(target);
breakSeeker.walk(tree);
return breakSeeker.found;
@@ -425,18 +427,16 @@ struct ExpressionAnalyzer {
return !curr->condition && !curr->value;
}
- // Checks if an expression ends with a simple break,
- // and returns a pointer to it if so.
- // (It might also have other internal branches.)
- static Expression* getEndingSimpleBreak(Expression* curr) {
+ // Checks if an expression does not flow out in an obvious way.
+ // We return true if it cannot flow out. If it can flow out, we
+ // might still return true, as the analysis here is simple and fast.
+ static bool obviouslyDoesNotFlowOut(Expression* curr) {
if (auto* br = curr->dynCast<Break>()) {
- if (isSimple(br)) return br;
- return nullptr;
+ if (!br->condition) return true;
+ } else if (auto* block = curr->dynCast<Block>()) {
+ if (block->list.size() > 0 && obviouslyDoesNotFlowOut(block->list.back()) && !BreakSeeker::has(block, block->name)) return true;
}
- if (auto* block = curr->dynCast<Block>()) {
- if (block->list.size() > 0) return getEndingSimpleBreak(block->list.back());
- }
- return nullptr;
+ return false;
}
template<typename T>