Skip to documentation
SLOP

tiny.choir.backends.wasm.emission

Reference tiny.choir backends wasm emission

Defined in backends.wasm.

API (32)

Actions

Public operations.

Types and contracts

Public types and contracts.

Namespaces

Public namespaces.

Values and defaults

Public values and defaults.

No direct callersNo direct callsbackends.wasmemission
Static calls · unresolved targets: unknown · external targets: unknown.

Source

Source: lib/choir/src/backends/wasm/emission/capacity.zig:19

zig
pub const Capacity = struct {    facts: emission.Facts,    frame_count: usize,    function_index_slots: usize,    value_index_slots: usize,    function_plan_bytes: usize,    function_index_bytes: usize,    value_plan_bytes: usize,    value_index_bytes: usize,    frame_bytes: usize,    working_bytes: usize,    pub fn derive(limits: Limits) error{CapacityOverflow}!Capacity {        const frame_count = if (limits.facts.definition_count == 0)            0        else frame_count: {            const controls = std.math.mul(                usize,                limits.facts.nesting_depth,                2,            ) catch return error.CapacityOverflow;            break :frame_count std.math.add(usize, controls, 1) catch                return error.CapacityOverflow;        };        const function_plan_bytes = try bytesFor(            emission.FunctionPlan,            limits.facts.function_count,        );        const function_index_slots = try emission.plan.index.slotsFor(            limits.facts.function_count,        );        const function_index_bytes = try bytesFor(u32, function_index_slots);        const value_plan_bytes = try bytesFor(emission.ValuePlan, limits.facts.value_count);        const value_index_slots = try emission.plan.index.slotsFor(limits.facts.value_count);        const value_index_bytes = try bytesFor(u32, value_index_slots);        const frame_bytes = try bytesFor(emission.function.Frame, frame_count);        var working_bytes = try add(function_plan_bytes, function_index_bytes);        working_bytes = try add(working_bytes, value_plan_bytes);        working_bytes = try add(working_bytes, value_index_bytes);        working_bytes = try add(working_bytes, frame_bytes);        return .{            .facts = limits.facts,            .frame_count = frame_count,            .function_index_slots = function_index_slots,            .value_index_slots = value_index_slots,            .function_plan_bytes = function_plan_bytes,            .function_index_bytes = function_index_bytes,            .value_plan_bytes = value_plan_bytes,            .value_index_bytes = value_index_bytes,            .frame_bytes = frame_bytes,            .working_bytes = working_bytes,        };    }};

Source: lib/choir/src/backends/wasm/emission/capacity.zig:5

zig
pub const Limits = struct {    module: *ir.Operation,    options: emission.Options,    facts: emission.Facts,    pub fn inspect(module: *ir.Operation, options: emission.Options) emission.Error!Limits {        return .{            .module = module,            .options = options,            .facts = try emission.inspection.inspect(module, options),        };    }};

Source: lib/choir/src/backends/wasm/emission/capacity.zig:74

zig
pub const OutputCapacity = struct {    output_bytes: usize,    initialization_bytes: usize,    steady_bytes: usize,    pub fn derive(        capacity: Capacity,        output_bytes: usize,    ) error{CapacityOverflow}!OutputCapacity {        return .{            .output_bytes = output_bytes,            .initialization_bytes = try add(capacity.working_bytes, output_bytes),            .steady_bytes = output_bytes,        };    }};

Source: lib/choir/src/backends/wasm/emission/model.zig:5

zig
pub const Error = error{    AlreadyActive,    AlreadyEmitted,    CapacityOverflow,    CodeGenFailed,    FunctionNotFound,    InputChanged,    NestingLimitExceeded,    NotActive,    OutOfMemory,    OutputOverflow,    OutputUnderflow,    UnsupportedOperation,};

Source: lib/choir/src/backends/wasm/emission/model.zig:22

zig
pub const Facts = struct {    function_count: usize,    import_count: usize,    definition_count: usize,    value_count: usize,    local_count: usize,    nesting_depth: usize,    needs_memory: bool,};

Source: lib/choir/src/backends/wasm/emission/model.zig:32

zig
pub const SectionSizes = struct {    type: usize = 0,    import: usize = 0,    function: usize = 0,    memory: usize = 0,    export_: usize = 0,    code: usize = 0,};

Source: lib/choir/src/backends/wasm/emission/owner.zig:10

zig
pub const Module = struct {    bytes: []u8,    pub fn deinit(self: *Module, allocator: Allocator) void {        allocator.free(self.bytes);        self.* = undefined;    }};

Source: lib/choir/src/backends/wasm/emission/owner.zig:19

zig
pub const ModuleEmitter = struct {    pub const claim: alloc_phase.capacity.Declaration = .{        .source = .{            .id = "choir.wasm_module_emitter",            .kind = .phase_static,            .limit_source = .caller,            .storage = .{                .covered = &.{                    .{                        .id = "exact_function_and_value_plans_indices_and_control_frames",                        .lifetime = .initialization,                        .detail = "exact function and value plans, indices, and control frames",                    },                    .{                        .id = "exact_count_and_fixed_encoded_output_snapshot",                        .lifetime = .steady,                        .detail = "exact Count and Fixed encoded output snapshot",                    },                    .{                        .id = "the_same_exact_output_allocation_after_take",                        .lifetime = .transferred,                        .detail = "the same exact output allocation after take",                    },                },                .excluded = &.{                    "borrowed IR and options after initialization",                    "dynamic artifact and linkage copies outside ModuleEmitter",                },            },            .capacity = .{                .inputs = &.{                    alloc_phase.capacity.bindInput(Limits, "facts_definition_count", "facts.definition_count"),                    alloc_phase.capacity.bindInput(Limits, "facts_function_count", "facts.function_count"),                    alloc_phase.capacity.bindInput(Limits, "facts_import_count", "facts.import_count"),                    alloc_phase.capacity.bindInput(Limits, "facts_local_count", "facts.local_count"),                    alloc_phase.capacity.bindInput(Limits, "facts_nesting_depth", "facts.nesting_depth"),                    alloc_phase.capacity.bindInput(Limits, "facts_value_count", "facts.value_count"),                },                .type_selectors = &.{},                .nodes = &.{                    .{ .input = 0 },                    .{ .input = 1 },                    .{ .input = 2 },                    .{ .input = 3 },                    .{ .input = 4 },                    .{ .input = 5 },                    .{ .add = .{ .left = 0, .right = 1 } },                    .{ .add = .{ .left = 6, .right = 2 } },                    .{ .add = .{ .left = 7, .right = 3 } },                    .{ .add = .{ .left = 8, .right = 4 } },                    .{ .add = .{ .left = 9, .right = 5 } },                },                .assertions = &.{.{                    .scope = .closure_total,                    .measure = .retained,                    .relation = .upper_bound,                    .expression = 10,                }},            },            .overload = .{                .kind = .reject_before_seal,                .detail = "unsupported input, nesting, index, byte, arithmetic, or OOM failure occurs before activation",            },            .risks = .{                .transitive = .{                    .status = .open,                    .detail = "emit and take are source-reviewed simple roots, but the ledger does not fail closed over their complete call graph",                },                .foreign = .{                    .status = .open,                    .detail = "source review found no callback, indirect, policy, raw heap, or OS edge, but no machine witness excludes future foreign edges",                },            },            .obligations = &.{                .{ .key = "wasm_capacity", .role = .capacity_model },                .{ .key = "wasm_sealed_emit_transitive_risk", .role = .transitive_risk },                .{ .key = "wasm_sealed_emit_foreign_risk", .role = .foreign_risk },                .{ .key = "wasm_nesting_boundary", .role = .overload },                .{ .key = "wasm_snapshot_lifetime", .role = .custom },                .{ .key = "wasm_oom_retry", .role = .overload },            },        },        .bindings = .{            .owner = @This(),            .seal = .{                .family = alloc_phase.capacity.selector(@This().activate),                .premise = .{                    .class = .checked_semantic_fact,                    .authority = .checker,                },            },            .teardown = .{                .family = alloc_phase.capacity.selector(@This().deinit),                .premise = .{                    .class = .checked_semantic_fact,                    .authority = .checker,                },            },        },    };    phase: alloc_phase.capacity.Phase,    capacity: Capacity,    output_capacity: OutputCapacity,    output: []u8,    output_taken: bool,    pub const Limits = emission.Limits;    pub const Capacity = emission.Capacity;    pub const OutputCapacity = emission.OutputCapacity;    const Self = @This();    pub fn init(allocator: Allocator, limits: Limits) emission.Error!Self {        const capacity = try Capacity.derive(limits);        const functions = try allocator.alloc(            emission.FunctionPlan,            capacity.facts.function_count,        );        errdefer allocator.free(functions);        const function_index = try allocator.alloc(u32, capacity.function_index_slots);        errdefer allocator.free(function_index);        const values = try allocator.alloc(emission.ValuePlan, capacity.facts.value_count);        errdefer allocator.free(values);        const value_index = try allocator.alloc(u32, capacity.value_index_slots);        errdefer allocator.free(value_index);        const frames = try allocator.alloc(emission.function.Frame, capacity.frame_count);        errdefer allocator.free(frames);        var plan = try emission.plan.planning.fill(            limits.module,            functions,            function_index,            values,            value_index,            capacity.facts,        );        const measured = try emission.module_encoding.preparePlan(            &plan,            limits.module,            limits.options,            frames,        );        const output_capacity = try OutputCapacity.derive(capacity, measured);        const output = try allocator.alloc(u8, output_capacity.output_bytes);        errdefer allocator.free(output);        var out = wasm.binary.Fixed.init(output);        try emission.module_encoding.write(            &out,            &plan,            limits.module,            limits.options,            frames,        );        _ = try out.finish();        allocator.free(frames);        allocator.free(value_index);        allocator.free(values);        allocator.free(function_index);        allocator.free(functions);        return .{            .phase = .initialization,            .capacity = capacity,            .output_capacity = output_capacity,            .output = output,            .output_taken = false,        };    }    pub fn activate(self: *Self) emission.Error!void {        if (self.phase != .initialization) return error.AlreadyActive;        self.phase = .steady;    }    pub fn emit(self: *const Self) emission.Error![]const u8 {        if (self.phase != .steady) return error.NotActive;        if (self.output_taken) return error.AlreadyEmitted;        return self.output;    }    pub fn take(self: *Self) emission.Error!Module {        _ = try self.emit();        self.output_taken = true;        return .{ .bytes = self.output };    }    pub fn deinit(self: *Self, allocator: Allocator) void {        if (self.phase == .teardown) @panic("WASM module emitter teardown is terminal");        self.phase = .teardown;        if (!self.output_taken) allocator.free(self.output);        self.output = undefined;    }};
Called byCallstest sourcelib.choir.src.backends.wasm.emission.capacitytest: wasm capacity arithmetic reject...test sourcelib.choir.src.backends.wasm.emission.capacitytest: wasm index capacity preserves a...test sourcelib.choir.src.backends.wasm.emission.capacitytest: wasm zero capacity owns no inde...private sourcelib.choir.src.backends.wasm.emission.capacityaddprivate sourcelib.choir.src.backends.wasm.emission.capacitybytesForbackends.wasm.emission.Capacityderive
Static calls · unresolved targets: 0 · external targets: 1.
Called byCallsNo direct callersbackends.wasm.emission.inspectioninspectbackends.wasm.emission.Limitsinspect
Static calls · unresolved targets: 0 · external targets: 0.
Called byCallsNo direct callersprivate sourcelib.choir.src.backends.wasm.emission.capacityaddbackends.wasm.emission.OutputCapacityderive
Static calls · unresolved targets: 0 · external targets: 0.

Source: lib/choir/src/backends/wasm/emission/model.zig:20

zig
pub const max_nesting_depth: usize = 256;
Called byCallsNo direct callsprivate sourcelib.choir.src.backends.wasm.emission.owneremitTestModuletest sourcelib.choir.src.backends.wasm.emission.ownertest: WASM empty and declaration-only...test sourcelib.choir.src.backends.wasm.emission.ownertest: WASM module emitter captures sa...test sourcelib.choir.src.backends.wasm.emission.ownertest: WASM module emitter initializat...test sourcelib.choir.src.backends.wasm.emission.ownertest: WASM module emitter seals an in...test sourcelib.choir.src.backends.wasm.emission.ownertest: WASM module snapshot outlives i...backends.wasm.ModuleEmitteractivate
Static calls · unresolved targets: 0 · external targets: 0.
Called byCallsNo direct callsprivate sourcelib.choir.src.backends.wasm.emission.owneremitTestModuletest sourcelib.choir.src.backends.wasm.emission.ownertest: WASM empty and declaration-only...test sourcelib.choir.src.backends.wasm.emission.ownertest: WASM module emitter capacity ma...test sourcelib.choir.src.backends.wasm.emission.ownertest: WASM module emitter captures sa...test sourcelib.choir.src.backends.wasm.emission.ownertest: WASM module emitter initializat...+2 morebackends.wasm.ModuleEmitterdeinit
Static calls · unresolved targets: 0 · external targets: 1.
Called byCallsNo direct callsbackends.wasm.ModuleEmittertaketest sourcelib.choir.src.backends.wasm.emission.ownertest: WASM empty and declaration-only...test sourcelib.choir.src.backends.wasm.emission.ownertest: WASM module emitter captures sa...test sourcelib.choir.src.backends.wasm.emission.ownertest: WASM module emitter seals an in...backends.wasm.ModuleEmitteremit
Static calls · unresolved targets: 0 · external targets: 0.
Called byCallsprivate sourcelib.choir.src.backends.wasm.emission.owneremitTestModuletest sourcelib.choir.src.backends.wasm.emission.ownertest: WASM empty and declaration-only...test sourcelib.choir.src.backends.wasm.emission.ownertest: WASM module emitter capacity ma...test sourcelib.choir.src.backends.wasm.emission.ownertest: WASM module emitter captures sa...test sourcelib.choir.src.backends.wasm.emission.ownertest: WASM module emitter initializat...+4 morebackends.wasm.emission.plan.planningfillbackends.wasm.ModuleEmitterinit
Static calls · unresolved targets: 3 · external targets: 5.
Called byCallsprivate sourcelib.choir.src.backends.wasm.emission.owneremitTestModuletest sourcelib.choir.src.backends.wasm.emission.ownertest: WASM module emitter initializat...test sourcelib.choir.src.backends.wasm.emission.ownertest: WASM module emitter seals an in...test sourcelib.choir.src.backends.wasm.emission.ownertest: WASM module snapshot outlives i...backends.wasm.ModuleEmitteremitbackends.wasm.ModuleEmittertake
Static calls · unresolved targets: 0 · external targets: 0.

Source: lib/choir/src/backends/wasm/emission/model.zig:3

zig
pub const Options = backends.interface.EmitOptions;

Source: lib/choir/src/backends/wasm/emission/root.zig

zig
const capacity = @import("capacity.zig");const inspection_module = @import("inspection.zig");const model = @import("model.zig");const module = @import("module/root.zig");const owner = @import("owner.zig");pub const function = @import("function/root.zig");pub const inspection = inspection_module;pub const module_encoding = module;pub const plan = @import("plan/root.zig");pub const symbols = @import("symbols.zig");pub const types = @import("types.zig");pub const Capacity = capacity.Capacity;pub const OutputCapacity = capacity.OutputCapacity;pub const Error = model.Error;pub const Facts = model.Facts;pub const Limits = capacity.Limits;pub const Module = owner.Module;pub const ModuleEmitter = owner.ModuleEmitter;pub const Options = model.Options;pub const SectionSizes = model.SectionSizes;pub const max_nesting_depth = model.max_nesting_depth;pub const FunctionPlan = plan.FunctionPlan;pub const Plan = plan.Plan;pub const ValuePlan = plan.ValuePlan;

Source: lib/choir/src/backends/wasm/root.zig:3

zig
pub const emission = @import("emission/root.zig");

Complete caller list for backends.wasm.ModuleEmitter.deinit

7 direct callers.

Complete caller list for backends.wasm.ModuleEmitter.init

9 direct callers.

Audit

Definitions24
Public names37
Members47
Version26.7.0
Revisiondaab053ee433