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.

227 lines
7.8 KiB

const Engine = @import("./engine.zig").Engine;
const Store = @import("./store.zig").Store;
const Module = @import("./module.zig").Module;
const Instance = @import("./instance.zig").Instance;
const Func = @import("./func.zig").Func;
const FuncType = @import("./func.zig").FuncType;
const Extern = @import("./extern.zig").Extern;
const Diagnostics = @import("./diagnostics.zig").Diagnostics;
const Error = @import("./error.zig").Error;
const Trap = @import("./trap.zig").Trap;
/// Object used to conveniently link together and instantiate Wasm modules.
/// This type is intended to make it easier to manage a set of modules that
/// link together, or to make it easier to link WebAssembly modules to WASI.
///
/// A `Linker` is a higher level way to instantiate a module than
/// `Instance.init` since it works at the "string" level of imports rather
/// than requiring 1:1 mappings.
pub const Linker = opaque {
/// Creates a new linker for the specified engine.
pub fn init(engine: *Engine) *Linker {
return wasmtime_linker_new(engine);
}
/// Deletes a linker
pub fn deinit(self: *Linker) void {
wasmtime_linker_delete(self);
}
/// Configures whether this linker allows later definitions to shadow
/// previous definitions. (The default is `false`.)
pub fn setAllowShadowing(self: *Linker, value: bool) void {
wasmtime_linker_allow_shadowing(self, value);
}
/// Defines a new item in this linker.
pub fn define(
self: *Linker,
context: *Store.Context,
module: []const u8,
name: []const u8,
item: *Extern,
diag: ?*Diagnostics,
) !void {
const err = wasmtime_linker_define(self, context, module.ptr, module.len, name.ptr, name.len, item);
try Diagnostics.handleError(err, error.LinkerDefine, {}, diag);
}
/// Defines a new function in this linker.
///
/// Note that this function does not create a `Func`. This creates a
/// store-independent function within the linker, allowing this function
/// definition to be used with multiple stores.
pub fn defineFunc(
self: *Linker,
module: []const u8,
name: []const u8,
func_type: *FuncType,
callback: *const Func.Callback,
env: ?*anyopaque,
env_finalizer: ?*const Func.Finalizer,
diag: ?*Diagnostics,
) !void {
const err = wasmtime_linker_define_func(self, module.ptr, module.len, name.ptr, name.len, func_type, callback, env, env_finalizer);
try Diagnostics.handleError(err, error.LinkerDefineFunc, {}, diag);
}
pub fn defineFuncFromFn(
self: *Linker,
module: []const u8,
name: []const u8,
func: anytype,
diag: ?*Diagnostics,
) !void {
const func_type = FuncType.fromFn(func);
const wrapped = Func.Wrapped.init(func);
try defineFunc(self, module, name, func_type, wrapped.callback, wrapped.env, wrapped.env_finalizer, diag);
}
/// Defines an instance under the specified name in this linker.
///
/// This function will take all of the exports of the `instance` provided
/// and defined them under a module called `name` with a field name as the
/// export's own name.
pub fn defineInstance(
self: *Linker,
context: *Store.Context,
name: []const u8,
instance: *const Instance,
diag: ?*Diagnostics,
) !void {
const err = wasmtime_linker_define_instance(self, context, name.ptr, name.len, instance);
try Diagnostics.handleError(err, error.LinkerDefineInstance, {}, diag);
}
/// Instantiates a `Module` with the items defined in this linker.
///
/// This function will attempt to satisfy all of the imports of the
/// `module` provided with items previously defined in this linker. If any
/// name isn't defined in the linker (or if the previously defined item is
/// of the wrong type) then an error is returned.
pub fn instantiate(
linker: *const Linker,
context: *Store.Context,
module: *const Module,
diag: ?*Diagnostics,
) !Instance {
var result: Instance = undefined;
var trap: ?*Trap = null;
const err = wasmtime_linker_instantiate(linker, context, module, &result, &trap);
return Diagnostics.handleErrorOrTrap(err, error.LinkerInstantiate, trap, result, diag);
}
/// Defines automatic instantiations of a `Module` in this linker.
pub fn autoInstantiateModule(
linker: *const Linker,
context: *Store.Context,
name: []const u8,
module: *const Module,
diag: ?*Diagnostics,
) !void {
const err = wasmtime_linker_module(linker, context, name.ptr, name.len, module);
try Diagnostics.handleError(err, error.LinkerAutoInstantiateModule, {}, diag);
}
/// Acquires the "default export" of the named module in this linker.
///
/// Returns an error if the default export is not a function.
pub fn getDefault(
linker: *const Linker,
context: *Store.Context,
module: []const u8,
diag: ?*Diagnostics,
) !Func {
var result: Func = undefined;
const err = wasmtime_linker_get_default(linker, context, module.ptr, module.len, &result);
return Diagnostics.handleError(err, error.LinkerGetDefault, result, diag);
}
/// Loads an item by name from this linker, converted to the
/// specified type. If `T` is `Extern` no conversion is done.
///
/// Returns `error.ExportNotFound` if export with that name is not found.
/// Returns `error.IncorrectType` if the export isn't the right type.
pub fn get(
linker: *const Linker,
context: *Store.Context,
module: []const u8,
name: []const u8,
comptime T: type,
) !Extern {
var result: Extern = undefined;
return if (wasmtime_linker_get(linker, context, module.ptr, module.len, name.ptr, name.len, &result)) result.as(T) else error.ExportNotFound;
}
extern "c" fn wasmtime_linker_new(*Engine) *Linker;
extern "c" fn wasmtime_linker_delete(*Linker) void;
extern "c" fn wasmtime_linker_allow_shadowing(*Linker, bool) void;
extern "c" fn wasmtime_linker_define(
linker: *Linker,
context: *Store.Context,
module: [*]const u8,
module_len: usize,
name: [*]const u8,
name_len: usize,
item: *Extern,
) ?*Error;
extern "c" fn wasmtime_linker_define_func(
linker: *Linker,
module: [*]const u8,
module_len: usize,
name: [*]const u8,
name_len: usize,
func_type: *FuncType,
callback: *const Func.Callback,
env: ?*anyopaque,
env_finalizer: ?*const Func.Finalizer,
) ?*Error;
// extern "c" fn wasmtime_linker_define_wasi(
// linker: *Linker,
// ) ?*Error;
extern "c" fn wasmtime_linker_define_instance(
linker: *Linker,
context: *Store.Context,
name: [*]const u8,
name_len: usize,
instance: *const Instance,
) ?*Error;
extern "c" fn wasmtime_linker_instantiate(
linker: *const Linker,
context: *Store.Context,
module: *const Module,
result: *Instance,
trap: *?*Trap,
) ?*Error;
extern "c" fn wasmtime_linker_module(
linker: *Linker,
context: *Store.Context,
name: [*]const u8,
name_len: usize,
module: *const Module,
) ?*Error;
extern "c" fn wasmtime_linker_get_default(
linker: *const Linker,
context: *Store.Context,
name: [*]const u8,
name_len: usize,
result: *Func,
) ?*Error;
extern "c" fn wasmtime_linker_get(
linker: *const Linker,
context: *Store.Context,
module: [*]const u8,
module_len: usize,
name: [*]const u8,
name_len: usize,
result: *Extern,
) bool;
};