Session VM — WIT interface¶
The LOKUST Session VM is a Rust library compiled to a WebAssembly Component (WASI Preview 2). It exposes a WIT-defined interface for session lifecycle operations.
Component size: ~113 KB. Runtime: Wasmtime 31+ (or any runtime implementing the Component Model).
WIT package¶
Definition path: session-vm/crates/session-guest/wit/world.wit.
Interfaces¶
types¶
Shared record and enum definitions used by other interfaces.
interface types {
record session-id {
inner: string,
}
enum session-status { idle, running, paused, completed, failed }
enum agent-status { queued, running, paused, completed, failed }
record agent-config {
agent-id: string,
name: string,
role: string,
phase-index: u32,
}
record phase-snapshot {
agent-id: string,
status: agent-status,
output: list<u8>,
duration-ms: u64,
tokens-used: u64,
}
record session-snapshot {
id: session-id,
status: session-status,
phases: list<phase-snapshot>,
current-phase-index: u32,
total-duration-ms: u64,
total-tokens: u64,
created-at-ms: u64,
}
record coordination-metrics {
phases-completed: u32,
phases-total: u32,
total-duration-ms: u64,
total-tokens: u64,
compression-ratio: f64,
}
}
gpu (host import)¶
Defined by the guest, implemented by the host. Lets the session VM request GPU acceleration without compiling GPU code into the WASM binary.
interface gpu {
record tensor {
shape: list<u32>,
data: list<f32>,
}
available: func() -> bool;
device-info: func() -> string;
infer: func(model-id: string, input: tensor) -> result<tensor, string>;
}
Reference implementation (CPU fallback): session-vm/crates/gpu-backend/src/lib.rs. Production hosts wire this to native CUDA/Metal/Vulkan via cudarc/metal-rs/ash.
agent-runtime (host import)¶
Host-provided agent execution. The guest invokes this whenever a phase needs an agent's work done — the host routes to the Claude API or any other model backend.
interface agent-runtime {
record agent-task {
agent-id: string,
system-prompt: string,
user-prompt: string,
prior-context: list<u8>,
}
record agent-result {
output: list<u8>,
tokens-used: u64,
duration-ms: u64,
}
execute: func(task: agent-task) -> result<agent-result, string>;
}
Reference implementation: session-vm/crates/session-host/src/claude.rs.
session-ops (guest export)¶
The primary surface. Host applications call these functions on the instantiated component.
interface session-ops {
use types.{session-id, session-status, agent-config, phase-snapshot,
session-snapshot, coordination-metrics};
create-session: func(agents: list<agent-config>) -> session-id;
run-next-phase: func(id: session-id) -> result<phase-snapshot, string>;
pause-session: func(id: session-id) -> result<session-status, string>;
resume-session: func(id: session-id) -> result<session-status, string>;
get-snapshot: func(id: session-id) -> option<session-snapshot>;
import-snapshot:func(snapshot: session-snapshot) -> session-id;
get-metrics: func(id: session-id) -> option<coordination-metrics>;
}
World¶
world session-vm {
import wasi:clocks/monotonic-clock@0.2.11;
import wasi:random/random@0.2.11;
import gpu;
import agent-runtime;
export session-ops;
}
Building¶
# Install cargo-component
cargo install cargo-component --locked
# Add wasm32-wasip2 target
rustup target add wasm32-wasip2
# Build the component
cd session-vm
cargo component build -p session-guest --release
Output: target/wasm32-wasip1/release/session_guest.wasm (despite the target name, cargo-component writes to the wasip1 directory for compatibility).
Hosting¶
The reference host is session-vm/crates/session-host/. It:
- Creates a Wasmtime
Enginewith the component model enabled - Loads the component file
- Builds a Linker, registers the WASI P2 adapters + the custom
gpuandagent-runtimeimports - Configures WASI preopens (
./session-data→/data) - Instantiates the component and navigates to the
session-opsinterface - Calls exported functions via
Func.call
Full host implementation: session-vm/crates/session-host/src/main.rs.
Design notes¶
Why Component Model and not core WASM? Component Model handles record/variant/list marshaling across the boundary natively. The guest sees typed Rust structs; the host sees typed Rust structs; no manual pointer+length packing.
Why host-side GPU?
cudarc does not compile to WASM. General CUDA access inside a WASM sandbox is not supported by any production runtime in 2026. The gpu WIT interface lets the guest treat GPU as an abstract capability provided by the host.
Why a separate agent-runtime import?
So the same compiled component can run on different backends — Claude today, a local model tomorrow, a heuristic planner in tests. The guest has no knowledge of which.