diff options
Diffstat (limited to 'src/parser')
-rw-r--r-- | src/parser/contexts.h | 42 | ||||
-rw-r--r-- | src/parser/parsers.h | 20 |
2 files changed, 53 insertions, 9 deletions
diff --git a/src/parser/contexts.h b/src/parser/contexts.h index 544851859..ab82f3963 100644 --- a/src/parser/contexts.h +++ b/src/parser/contexts.h @@ -310,6 +310,7 @@ struct NullInstrParserCtx { using ExprT = Ok; using CatchT = Ok; using CatchListT = Ok; + using TagLabelListT = Ok; using FieldIdxT = Ok; using FuncIdxT = Ok; @@ -386,6 +387,9 @@ struct NullInstrParserCtx { return Ok{}; } + TagLabelListT makeTagLabelList() { return Ok{}; } + void appendTagLabel(TagLabelListT&, TagIdxT, LabelIdxT) {} + Result<> makeUnreachable(Index) { return Ok{}; } Result<> makeNop(Index) { return Ok{}; } Result<> makeBinary(Index, BinaryOp) { return Ok{}; } @@ -566,6 +570,10 @@ struct NullInstrParserCtx { Result<> makeStringIterMove(Index, StringIterMoveOp) { return Ok{}; } Result<> makeStringSliceWTF(Index, StringSliceWTFOp) { return Ok{}; } Result<> makeStringSliceIter(Index) { return Ok{}; } + template<typename HeapTypeT> + Result<> makeResume(Index, HeapTypeT, const TagLabelListT&) { + return Ok{}; + } }; struct NullCtx : NullTypeParserCtx, NullInstrParserCtx { @@ -1069,13 +1077,6 @@ struct ParseDefsCtx : TypeParserCtx<ParseDefsCtx> { using TableTypeT = Ok; using TypeUseT = HeapType; - using ExprT = Expression*; - using ElemListT = std::vector<Expression*>; - - struct CatchInfo; - using CatchT = CatchInfo; - using CatchListT = std::vector<CatchInfo>; - using FieldIdxT = Index; using FuncIdxT = Name; using LocalIdxT = Index; @@ -1089,6 +1090,15 @@ struct ParseDefsCtx : TypeParserCtx<ParseDefsCtx> { using MemargT = Memarg; + using ExprT = Expression*; + using ElemListT = std::vector<Expression*>; + + struct CatchInfo; + using CatchT = CatchInfo; + using CatchListT = std::vector<CatchInfo>; + + using TagLabelListT = std::vector<std::pair<TagIdxT, LabelIdxT>>; + ParseInput in; Module& wasm; @@ -1179,6 +1189,11 @@ struct ParseDefsCtx : TypeParserCtx<ParseDefsCtx> { CatchInfo makeCatchAll(Index label) { return {{}, label, false}; } CatchInfo makeCatchAllRef(Index label) { return {{}, label, true}; } + TagLabelListT makeTagLabelList() { return {}; } + void appendTagLabel(TagLabelListT& tagLabels, Name tag, Index label) { + tagLabels.push_back({tag, label}); + } + Result<HeapTypeT> getHeapTypeFromIdx(Index idx) { if (idx >= types.size()) { return in.err("type index out of bounds"); @@ -1994,6 +2009,19 @@ struct ParseDefsCtx : TypeParserCtx<ParseDefsCtx> { Result<> makeStringSliceIter(Index pos) { return withLoc(pos, irBuilder.makeStringSliceIter()); } + + Result<> + makeResume(Index pos, HeapType type, const TagLabelListT& tagLabels) { + std::vector<Name> tags; + std::vector<Index> labels; + tags.reserve(tagLabels.size()); + labels.reserve(tagLabels.size()); + for (auto& [tag, label] : tagLabels) { + tags.push_back(tag); + labels.push_back(label); + } + return withLoc(pos, irBuilder.makeResume(type, tags, labels)); + } }; } // namespace wasm::WATParser diff --git a/src/parser/parsers.h b/src/parser/parsers.h index db4c716f1..960ccb26d 100644 --- a/src/parser/parsers.h +++ b/src/parser/parsers.h @@ -1228,7 +1228,7 @@ template<typename Ctx> MaybeResult<typename Ctx::CatchT> catchinstr(Ctx& ctx) { return result; } -// trytable ::= 'try_table' label blocktype catchinstr* instr* end id? +// trytable ::= 'try_table' label blocktype catchinstr* instr* 'end' id? // | '(' 'try_table' label blocktype catchinstr* instr* ')' template<typename Ctx> MaybeResult<> trytable(Ctx& ctx, bool folded) { auto pos = ctx.in.getPos(); @@ -1992,8 +1992,24 @@ template<typename Ctx> Result<> makeStringSliceIter(Ctx& ctx, Index pos) { return ctx.makeStringSliceIter(pos); } +// resume ::= 'resume' typeidx ('(' 'tag' tagidx labelidx ')')* template<typename Ctx> Result<> makeResume(Ctx& ctx, Index pos) { - return ctx.in.err("unimplemented instruction"); + auto type = typeidx(ctx); + CHECK_ERR(type); + + auto tagLabels = ctx.makeTagLabelList(); + while (ctx.in.takeSExprStart("tag"sv)) { + auto tag = tagidx(ctx); + CHECK_ERR(tag); + auto label = labelidx(ctx); + CHECK_ERR(label); + ctx.appendTagLabel(tagLabels, *tag, *label); + if (!ctx.in.takeRParen()) { + return ctx.in.err("expected ')' at end of handler clause"); + } + } + + return ctx.makeResume(pos, *type, tagLabels); } // ======= |