diff options
-rw-r--r-- | std/wasi/snapshot_preview1.ts | 21 | ||||
-rw-r--r-- | std/wasi/snapshot_preview1_test.ts | 66 |
2 files changed, 84 insertions, 3 deletions
diff --git a/std/wasi/snapshot_preview1.ts b/std/wasi/snapshot_preview1.ts index bc63e82dd..b3d5274e6 100644 --- a/std/wasi/snapshot_preview1.ts +++ b/std/wasi/snapshot_preview1.ts @@ -306,6 +306,21 @@ export interface ContextOptions { * Determines if calls to exit from within the WebAssembly module will terminate the proess or return. */ exitOnReturn?: boolean; + + /** + * The resource descriptor used as standard input in the WebAssembly module. + */ + stdin?: number; + + /** + * The resource descriptor used as standard output in the WebAssembly module. + */ + stdout?: number; + + /** + * The resource descriptor used as standard error in the WebAssembly module. + */ + stderr?: number; } /** @@ -335,17 +350,17 @@ export default class Context { this.fds = [ { - rid: Deno.stdin.rid, + rid: options.stdin ?? Deno.stdin.rid, type: FILETYPE_CHARACTER_DEVICE, flags: FDFLAGS_APPEND, }, { - rid: Deno.stdout.rid, + rid: options.stdout ?? Deno.stdout.rid, type: FILETYPE_CHARACTER_DEVICE, flags: FDFLAGS_APPEND, }, { - rid: Deno.stderr.rid, + rid: options.stderr ?? Deno.stderr.rid, type: FILETYPE_CHARACTER_DEVICE, flags: FDFLAGS_APPEND, }, diff --git a/std/wasi/snapshot_preview1_test.ts b/std/wasi/snapshot_preview1_test.ts index 55982545f..1fe94a4cc 100644 --- a/std/wasi/snapshot_preview1_test.ts +++ b/std/wasi/snapshot_preview1_test.ts @@ -274,3 +274,69 @@ Deno.test("context_initialize", function () { "WebAssembly.Instance has already started", ); }); + +Deno.test("std_io_stdin.wasm with stdin as file", function () { + const stdinPath = Deno.makeTempFileSync(); + Deno.writeTextFileSync(stdinPath, "Hello, stdin!"); + + const stdinFile = Deno.openSync(stdinPath); + + const context = new Context({ + exitOnReturn: false, + stdin: stdinFile.rid, + }); + + const binary = Deno.readFileSync(path.join(testdir, "std_io_stdin.wasm")); + const module = new WebAssembly.Module(binary); + const instance = new WebAssembly.Instance(module, { + wasi_snapshot_preview1: context.exports, + }); + + context.start(instance); + + stdinFile.close(); +}); + +Deno.test("std_io_stdout.wasm with stdout as file", function () { + const stdoutPath = Deno.makeTempFileSync(); + const stdoutFile = Deno.openSync(stdoutPath, { create: true, write: true }); + + const context = new Context({ + exitOnReturn: false, + stdout: stdoutFile.rid, + }); + + const binary = Deno.readFileSync(path.join(testdir, "std_io_stdout.wasm")); + const module = new WebAssembly.Module(binary); + const instance = new WebAssembly.Instance(module, { + wasi_snapshot_preview1: context.exports, + }); + + context.start(instance); + + stdoutFile.close(); + + assertEquals(Deno.readTextFileSync(stdoutPath), "Hello, stdout!"); +}); + +Deno.test("std_io_stderr.wasm with stderr as file", function () { + const stderrPath = Deno.makeTempFileSync(); + const stderrFile = Deno.openSync(stderrPath, { create: true, write: true }); + + const context = new Context({ + exitOnReturn: false, + stderr: stderrFile.rid, + }); + + const binary = Deno.readFileSync(path.join(testdir, "std_io_stderr.wasm")); + const module = new WebAssembly.Module(binary); + const instance = new WebAssembly.Instance(module, { + wasi_snapshot_preview1: context.exports, + }); + + context.start(instance); + + stderrFile.close(); + + assertEquals(Deno.readTextFileSync(stderrPath), "Hello, stderr!"); +}); |