Wasmtime bindings for Zig
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

77 lines
3.2 KiB

# wasmslime
.. is a library providing [Wasmtime] bindings for use with the [Zig] language. This is my first project I've tackled with Zig, as I wanted to play around with WebAssembly for sandboxing reasons, and the libraries I have found are both outdated and incomplete. Though they did provide some starting help.
Of course, this library too is likely very much incomplete, maybe even broken. I just wanted to share it as I'm quite proud and perhaps someone else finds some use in it. Feel free to yoink anything from `wasmslime` as you see fit.
## Example
```zig
const wat_bytes =
\\(module
\\ (func $hello (import "env" "print_hello"))
\\ (func (export "main") (call $hello)))
;
fn print_hello() void {
const stdout = @import("std").io.getStdOut().writer();
stdout.print("Hello, Slime!\n", .{}) catch unreachable;
}
pub fn main() !void {
const wasm = @import("wasmslime");
// Should deinit Wasm objects, but this is omitted for brevity.
var engine = try wasm.Engine.initDefault();
var module = try wasm.Module.initFromWat(engine, wat_bytes, null);
var linker = wasm.Linker.init(engine);
try linker.defineFuncFromFn("env", "print_hello", print_hello, null);
var store = wasm.Store.init(engine);
var context = store.getContext();
var instance = try linker.instantiate(context, module, null);
const run_func = try instance.get(context, "main", wasm.Func);
try run_func.call(context, .{}, void, null);
}
```
## Setup as Dependency
Currently requires [Wasmtime] to be installed as a system library. Unsure about the possibility of statically linking it instead, and the up- and downsides that come with that. I may look into this in the future.
`wasmslime` uses Zig version `0.11` and thus makes use of its new [Package Management] feature. Since this is a pretty new feature that currently isn't documented beyond what's shared in the release notes, I'll give a brief overview of how to add it as a dependency to your project.
### `build.zig.zon`
```zig
.{
.name = "my_amazing_project",
.version = "0.1.0",
.dependencies = .{
.wasmslime = .{
.url = "https://git.mcft.net/copygirl/wasmslime/archive/main.tar.gz",
.hash = "00000000000000000000000000000000000000000000000000000000000000000000",
},
},
}
```
Providing an invalid hash will make the build system complain about what it should actually be. Keep in mind the string needs to be the correct length, however. This way I don't have to update the README each commit.
Downloaded packages end up in `~/.cache/zig/`. If the hash already matches an existing package here, it will be used regardless of the source URL. If you run into issues, you could consider clearing Zig's cache folder.
### `build.zig`
```zig
...
const exe = b.addExecutable(...);
const wasmslime = b.dependency("wasmslime", .{ .target = target, .optimize = optimize });
exe.addModule("wasmslime", wasmslime.module("wasmslime"));
exe.linkLibrary(wasmslime.artifact("wasmslime"));
b.installArtifact(exe);
...
```
[Wasmtime]: https://wasmtime.dev/
[Zig]: https://ziglang.org/
[Package Management]: https://ziglang.org/download/0.11.0/release-notes.html#Package-Management