summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/wasm/wat-parser.cpp31
-rw-r--r--test/lit/wat-kitchen-sink.wast9
2 files changed, 35 insertions, 5 deletions
diff --git a/src/wasm/wat-parser.cpp b/src/wasm/wat-parser.cpp
index 23961ac3f..1ee2bd2c8 100644
--- a/src/wasm/wat-parser.cpp
+++ b/src/wasm/wat-parser.cpp
@@ -583,6 +583,8 @@ struct NullInstrParserCtx {
InstrT makeF64Const(Index, double) { return Ok{}; }
InstrT makeLocalGet(Index pos, LocalT local) { return Ok{}; }
+ InstrT makeLocalTee(Index pos, LocalT local) { return Ok{}; }
+ InstrT makeLocalSet(Index pos, LocalT local) { return Ok{}; }
template<typename HeapTypeT> InstrT makeRefNull(Index, HeapTypeT) {
return {};
@@ -1258,6 +1260,27 @@ struct ParseDefsCtx : InstrParserCtx<ParseDefsCtx> {
assert(local < func->getNumLocals());
return push(pos, builder.makeLocalGet(local, func->getLocalType(local)));
}
+
+ Result<> makeLocalTee(Index pos, Index local) {
+ if (!func) {
+ return in.err(pos, "local.tee must be inside a function");
+ }
+ assert(local < func->getNumLocals());
+ auto val = pop(pos);
+ CHECK_ERR(val);
+ return push(pos,
+ builder.makeLocalTee(local, *val, func->getLocalType(local)));
+ }
+
+ Result<> makeLocalSet(Index pos, Index local) {
+ if (!func) {
+ return in.err(pos, "local.set must be inside a function");
+ }
+ assert(local < func->getNumLocals());
+ auto val = pop(pos);
+ CHECK_ERR(val);
+ return push(pos, builder.makeLocalSet(local, *val));
+ }
};
// ================
@@ -1881,12 +1904,16 @@ Result<typename Ctx::InstrT> makeLocalGet(Ctx& ctx, Index pos) {
template<typename Ctx>
Result<typename Ctx::InstrT> makeLocalTee(Ctx& ctx, Index pos) {
- return ctx.in.err("unimplemented instruction");
+ auto local = localidx(ctx);
+ CHECK_ERR(local);
+ return ctx.makeLocalTee(pos, *local);
}
template<typename Ctx>
Result<typename Ctx::InstrT> makeLocalSet(Ctx& ctx, Index pos) {
- return ctx.in.err("unimplemented instruction");
+ auto local = localidx(ctx);
+ CHECK_ERR(local);
+ return ctx.makeLocalSet(pos, *local);
}
template<typename Ctx>
diff --git a/test/lit/wat-kitchen-sink.wast b/test/lit/wat-kitchen-sink.wast
index 1482e87f6..10b2287b3 100644
--- a/test/lit/wat-kitchen-sink.wast
+++ b/test/lit/wat-kitchen-sink.wast
@@ -574,11 +574,13 @@
;; CHECK-NEXT: (drop
;; CHECK-NEXT: (local.get $y)
;; CHECK-NEXT: )
- ;; CHECK-NEXT: (drop
+ ;; CHECK-NEXT: (local.set $x
;; CHECK-NEXT: (local.get $x)
;; CHECK-NEXT: )
;; CHECK-NEXT: (drop
- ;; CHECK-NEXT: (local.get $y)
+ ;; CHECK-NEXT: (local.tee $y
+ ;; CHECK-NEXT: (local.get $y)
+ ;; CHECK-NEXT: )
;; CHECK-NEXT: )
;; CHECK-NEXT: )
(func $locals (param i32) (param $x i32)
@@ -593,8 +595,9 @@
local.get 3
drop
local.get $x
- drop
+ local.set 1
local.get $y
+ local.tee 3
drop
)