diff options
author | Thomas Lively <tlively@google.com> | 2024-05-17 17:49:45 -0700 |
---|---|---|
committer | GitHub <noreply@github.com> | 2024-05-17 17:49:45 -0700 |
commit | 921644ca65afbafb84fb82d58dacc4a028e2d720 (patch) | |
tree | 9253fbcf3f1dd9930dd1b9bc9f545234399b918e /src/parser/parsers.h | |
parent | 369cddfb44ddbada2ef7742a9ebef54727d12dd5 (diff) | |
download | binaryen-921644ca65afbafb84fb82d58dacc4a028e2d720.tar.gz binaryen-921644ca65afbafb84fb82d58dacc4a028e2d720.tar.bz2 binaryen-921644ca65afbafb84fb82d58dacc4a028e2d720.zip |
Rewrite wasm-shell to use new wast parser (#6601)
Use the new wast parser to parse a full script up front, then traverse the
parsed script data structure and execute the commands. wasm-shell had previously
used the new wat parser for top-level modules, but it now uses the new parser
for module assertions as well. Fix various bugs this uncovered.
After this change, wasm-shell supports all the assertions used in the upstream
spec tests (although not new kinds of assertions introduced in any proposals).
Uncomment various `assert_exhaustion` tests that we can now execute.
Other kinds of assertions remain commented out in our tests: wasm-shell now
supports `assert_unlinkable`, but the interpreter does not eagerly check for the
existence of imports, so those tests do not pass. Tests that check for NaNs also
remain commented out because they do not yet use the standard syntax that
wasm-shell now supports for canonical and arithmetic NaN results, and our
interpreter would not pass all of those tests even if they did use the standard
syntax.
Diffstat (limited to 'src/parser/parsers.h')
-rw-r--r-- | src/parser/parsers.h | 22 |
1 files changed, 15 insertions, 7 deletions
diff --git a/src/parser/parsers.h b/src/parser/parsers.h index 88600fec3..5900deb27 100644 --- a/src/parser/parsers.h +++ b/src/parser/parsers.h @@ -30,7 +30,8 @@ template<typename Ctx> Result<typename Ctx::HeapTypeT> heaptype(Ctx&); template<typename Ctx> MaybeResult<typename Ctx::RefTypeT> reftype(Ctx&); template<typename Ctx> MaybeResult<typename Ctx::TypeT> tupletype(Ctx&); template<typename Ctx> Result<typename Ctx::TypeT> valtype(Ctx&); -template<typename Ctx> MaybeResult<typename Ctx::ParamsT> params(Ctx&); +template<typename Ctx> +MaybeResult<typename Ctx::ParamsT> params(Ctx&, bool allowNames = true); template<typename Ctx> MaybeResult<typename Ctx::ResultsT> results(Ctx&); template<typename Ctx> MaybeResult<typename Ctx::SignatureT> functype(Ctx&); template<typename Ctx> Result<typename Ctx::FieldT> storagetype(Ctx&); @@ -325,7 +326,8 @@ MaybeResult<typename Ctx::LabelIdxT> maybeLabelidx(Ctx&, template<typename Ctx> Result<typename Ctx::LabelIdxT> labelidx(Ctx&, bool inDelegate = false); template<typename Ctx> Result<typename Ctx::TagIdxT> tagidx(Ctx&); -template<typename Ctx> Result<typename Ctx::TypeUseT> typeuse(Ctx&); +template<typename Ctx> +Result<typename Ctx::TypeUseT> typeuse(Ctx&, bool allowNames = true); MaybeResult<ImportNames> inlineImport(Lexer&); Result<std::vector<Name>> inlineExports(Lexer&); template<typename Ctx> Result<> strtype(Ctx&); @@ -561,13 +563,18 @@ template<typename Ctx> Result<typename Ctx::TypeT> valtype(Ctx& ctx) { // param ::= '(' 'param id? t:valtype ')' => [t] // | '(' 'param t*:valtype* ')' => [t*] // params ::= param* -template<typename Ctx> MaybeResult<typename Ctx::ParamsT> params(Ctx& ctx) { +template<typename Ctx> +MaybeResult<typename Ctx::ParamsT> params(Ctx& ctx, bool allowNames) { bool hasAny = false; auto res = ctx.makeParams(); while (ctx.in.takeSExprStart("param"sv)) { hasAny = true; + auto pos = ctx.in.getPos(); if (auto id = ctx.in.takeID()) { // Single named param + if (!allowNames) { + return ctx.in.err(pos, "unexpected named parameter"); + } auto type = valtype(ctx); CHECK_ERR(type); if (!ctx.in.takeRParen()) { @@ -1065,7 +1072,7 @@ template<typename Ctx> Result<typename Ctx::BlockTypeT> blocktype(Ctx& ctx) { // We either had no results or multiple results. Reset and parse again as a // type use. ctx.in = initialLexer; - auto use = typeuse(ctx); + auto use = typeuse(ctx, false); CHECK_ERR(use); auto type = ctx.getBlockTypeFromTypeUse(pos, *use); @@ -1935,7 +1942,7 @@ Result<> makeCallIndirect(Ctx& ctx, bool isReturn) { auto table = maybeTableidx(ctx); CHECK_ERR(table); - auto type = typeuse(ctx); + auto type = typeuse(ctx, false); CHECK_ERR(type); return ctx.makeCallIndirect( pos, annotations, table.getPtr(), *type, isReturn); @@ -2669,7 +2676,8 @@ template<typename Ctx> Result<typename Ctx::TagIdxT> tagidx(Ctx& ctx) { // (if typedefs[x] = [t1*] -> [t2*]) // | ((t1,IDs):param)* (t2:result)* => x, IDs // (if x is minimum s.t. typedefs[x] = [t1*] -> [t2*]) -template<typename Ctx> Result<typename Ctx::TypeUseT> typeuse(Ctx& ctx) { +template<typename Ctx> +Result<typename Ctx::TypeUseT> typeuse(Ctx& ctx, bool allowNames) { auto pos = ctx.in.getPos(); std::optional<typename Ctx::HeapTypeT> type; if (ctx.in.takeSExprStart("type"sv)) { @@ -2683,7 +2691,7 @@ template<typename Ctx> Result<typename Ctx::TypeUseT> typeuse(Ctx& ctx) { type = *x; } - auto namedParams = params(ctx); + auto namedParams = params(ctx, allowNames); CHECK_ERR(namedParams); auto resultTypes = results(ctx); |