Crate hibana
Expand description
Hibana is a Rust 2024 no_std / no-alloc-oriented runtime for affine
multiparty session types.
The crate intentionally has two faces:
- app authors use
gandEndpoint; - protocol implementors use
runtimeandruntime::program.
Everything starts from one global choreography and ends in a small localside endpoint:
g choreography -> project role program -> attach endpoint -> drive localside§App path
Application code writes choreography with g and drives an endpoint that a
protocol crate has already attached.
use hibana::g;
let app = g::seq(
g::send::<0, 1, g::Msg<1, u32>>(),
g::send::<1, 0, g::Msg<2, u32>>(),
);
endpoint.send::<g::Msg<1, u32>>(&7).await?;
let reply = endpoint.recv::<g::Msg<2, u32>>().await?;The localside API is deliberately small:
Endpoint::sendsends the next projected message;Endpoint::recvreceives a message after descriptor evidence matches;Endpoint::offerobserves a route branch;RouteBranch::labelreports the selected arm’s first logical label;RouteBranch::recvreceives the first payload in a selected receive arm;RouteBranch::sendsends the first payload in a selected send arm.
A route branch whose selected arm begins with a send is handled by
RouteBranch::send. Dropping the returned future restores the branch
preview before any progress commits.
Successful sends, receives, and route branch first-step operations consume
progress.
let branch = endpoint.offer().await?;
match branch.label() {
10 => {
let value = branch.recv::<g::Msg<10, [u8; 4]>>().await?;
}
11 => {
branch.send::<g::Msg<11, ()>>(&()).await?;
}
label => panic!("unexpected route label {label}"),
}§Protocol path
Protocol crates compose prefixes around an app choreography, project a role-local witness, bind transport state, and return an attached endpoint.
use hibana::{g, runtime};
use hibana::runtime::program::{RoleProgram, project};
let program = g::seq(transport_prefix, app);
let role0: RoleProgram<0> = project(&program);
let mut slab = [0u8; 4096];
let mut kit_storage = runtime::SessionKitStorage::<MyTransport>::uninit();
let kit = kit_storage.init();
let rv = kit.rendezvous(&mut slab, transport)?;
let endpoint = rv.enter(sid, &role0)?;Runtime capacities are derived from Hibana’s wire/domain limits and
projected descriptors, not chosen by callers.
Hidden timeout fuses are not protocol API or attach config.
Protocol-invisible carrier watchdogs live inside the transport implementation:
terminal I/O waits are reported as runtime::transport::TransportError
from poll_send or poll_recv, not as Hibana timeout branches.
runtime::transport::Transport owns I/O readiness, wire buffers, and
ingress demux evidence. runtime::resolver owns dynamic resolver input.
None of those layers become app concepts.
§Payloads, receive evidence, and resolvers
Payload types implement runtime::wire::WireEncode for sends and
runtime::wire::WirePayload for receives. Decoded values may borrow from
the received frame. Built-in exact codecs cover (), integers, bool,
byte slices, and fixed byte arrays.
Branch choice is either an in-band protocol message, a projected first visible endpoint operation confirmed by descriptor-checked receive evidence, or an explicit resolver decision. Transport evidence is descriptor evidence only; it is not route authority and it does not create a public branch-authority catalogue.
§Boundary contract
Hibana keeps the public API small because the projection boundary carries the proof work:
- route shape, ambiguous simultaneous endpoint operations, and intrinsic route controller mismatch are rejected before runtime;
- parallel composition rejects empty arms and ambiguous simultaneous endpoint operations;
- labels are choreography identities, while transport frame labels are descriptor facts;
- endpoint progress is affine: successful sends, receives, and route branch first-step operations commit progress, while dropped previews restore the endpoint;
EndpointErrorfails closed, carries compact endpoint operation evidence, and never authorizes hidden progress.
Modules§
- g
- Choreography language used by app authors.
- runtime
- Runtime surface for protocol implementors. Protocol-neutral runtime surface for protocol implementors.
Structs§
- Endpoint
- App-facing affine executor for a projected role.
- Endpoint
Error - Domain error for endpoint progress.
- Route
Branch - Preview of a selected route branch returned by
Endpoint::offer.