# Wasm3 Cookbook ## WASM module examples ### Rust WASI app Create a new project: ```sh $ cargo new --bin hello $ cd hello $ rustup target add wasm32-wasi ``` Build and run: ```sh $ cargo build --release --target wasm32-wasi $ wasm3 ./target/wasm32-wasi/release/hello.wasm Hello, world! ``` ### AssemblyScript WASI app Create `hello.ts`: ```ts import "wasi" import {Console} from "as-wasi" Console.log('Hello World!'); ``` Create `package.json`: ```json { "name": "hello", "version": "1.0.0", "description": "Hello world with AssemblyScript and as-wasi", "main": "hello.ts", "scripts": { "build": "asc hello.ts -b hello.wasm" }, "devDependencies": { "assemblyscript": "^0.18.30", "as-wasi": "^0.4.4" } } ``` Build and run: ```sh $ npm install $ npm run build $ wasm3 hello.wasm Hello World! ``` ### TinyGo WASI app Create `hello.go`: ```go package main import "fmt" func main() { fmt.Printf("Hello, %s!\n", "world") } ``` Build and run: ```sh $ tinygo build -o hello.wasm -target wasi ./hello.go $ wasm3 hello.wasm Hello, world! ``` ### Zig WASI app Create `hello.zig`: ```zig const std = @import("std"); pub fn main() !void { const stdout = std.io.getStdOut().writer(); try stdout.print("Hello, {s}!\n", .{"world"}); } ``` Build and run: ```sh $ zig build-exe -O ReleaseSmall -target wasm32-wasi hello.zig $ wasm3 hello.wasm Hello, world! ``` ## Zig library Create `add.zig`: ```zig export fn add(a: i32, b: i32) i64 { return a + b; } ``` Build and run: ```sh $ zig build-lib add.zig -O ReleaseSmall -target wasm32-freestanding $ wasm3 --repl add.wasm wasm3> add 1 2 Result: 3 ``` ### C/C++ WASI app The easiest way to start is to use [Wasienv](https://github.com/wasienv/wasienv). Create `hello.cpp`: ```cpp #include int main() { std::cout << "Hello, world!" << std::endl; return 0; } ``` Or `hello.c`: ```c #include int main() { printf("Hello, %s!\n", "world"); return 0; } ``` Build and run: ```sh $ wasic++ -O3 hello.cpp -o hello.wasm $ wasicc -O3 hello.c -o hello.wasm $ wasm3 hello.wasm Hello World! ``` Limitations: - `setjmp/longjmp` and `C++ exceptions` are not available - no support for `threads` and `atomics` - no support for `dynamic libraries` ### WAT WASI app Create `hello.wat`: ```wat (module ;; wasi_snapshot_preview1!fd_write(file_descriptor, *iovs, iovs_len, nwritten) -> status_code (import "wasi_snapshot_preview1" "fd_write" (func $fd_write (param i32 i32 i32 i32) (result i32))) (memory 1) (export "memory" (memory 0)) ;; Put a message to linear memory at offset 32 (data (i32.const 32) "Hello, world!\n") (func $main (export "_start") ;; Create a new io vector at address 0x4 (i32.store (i32.const 4) (i32.const 32)) ;; iov.iov_base - pointer to the start of the message (i32.store (i32.const 8) (i32.const 14)) ;; iov.iov_len - length of the message (call $fd_write (i32.const 1) ;; file_descriptor - 1 for stdout (i32.const 4) ;; *iovs - pointer to the io vector (i32.const 1) ;; iovs_len - count of items in io vector (i32.const 20) ;; nwritten - where to store the number of bytes written ) drop ;; discard the WASI status code ) ) ``` Build and run: ```sh $ wat2wasm hello.wat -o hello.wasm $ wasm3 hello.wasm Hello, world! ``` ### WAT library Create `swap.wat`: ```wat (module (func (export "swap") (param i32 i32) (result i32 i32) (get_local 1) (get_local 0) ) ) ``` Build and run: ```sh $ wat2wasm swap.wat -o swap.wasm $ wasm3 --repl swap.wasm wasm3> :invoke swap 123 456 Result: 456:i32, 123:i32 ```