pub struct VirtualMachine {
pub resource_usage: Option<ResourceUsage>,
pub metrics: Option<VmMetrics>,
/* private fields */
}Expand description
The Shape virtual machine
Fields§
§resource_usage: Option<ResourceUsage>Optional resource usage tracker for sandboxed execution.
When set, the dispatch loop calls tick_instruction() each cycle.
metrics: Option<VmMetrics>Optional VM metrics collector. None when VMConfig.metrics_enabled
is false (the default), giving zero per-instruction overhead.
Implementations§
Source§impl VirtualMachine
impl VirtualMachine
Sourcepub fn execute_function_by_name(
&mut self,
name: &str,
args: Vec<ValueWord>,
ctx: Option<&mut ExecutionContext>,
) -> Result<ValueWord, VMError>
pub fn execute_function_by_name( &mut self, name: &str, args: Vec<ValueWord>, ctx: Option<&mut ExecutionContext>, ) -> Result<ValueWord, VMError>
Execute a named function with arguments, returning its result.
If the program has module-level bindings, the top-level code is executed first (once) to initialize them before calling the target function.
Sourcepub fn execute_function_by_id(
&mut self,
func_id: u16,
args: Vec<ValueWord>,
ctx: Option<&mut ExecutionContext>,
) -> Result<ValueWord, VMError>
pub fn execute_function_by_id( &mut self, func_id: u16, args: Vec<ValueWord>, ctx: Option<&mut ExecutionContext>, ) -> Result<ValueWord, VMError>
Execute a function by its ID with positional arguments.
Used by the remote execution system when the caller already knows the
function index (e.g., from a RemoteCallRequest.function_id).
Sourcepub fn execute_closure(
&mut self,
function_id: u16,
upvalues: Vec<Upvalue>,
args: Vec<ValueWord>,
ctx: Option<&mut ExecutionContext>,
) -> Result<ValueWord, VMError>
pub fn execute_closure( &mut self, function_id: u16, upvalues: Vec<Upvalue>, args: Vec<ValueWord>, ctx: Option<&mut ExecutionContext>, ) -> Result<ValueWord, VMError>
Execute a closure with its captured upvalues and arguments.
Used by the remote execution system to run closures that were serialized with their captured values.
Sourcepub fn execute_function_fast(
&mut self,
func_id: u16,
ctx: Option<&mut ExecutionContext>,
) -> Result<ValueWord, VMError>
pub fn execute_function_fast( &mut self, func_id: u16, ctx: Option<&mut ExecutionContext>, ) -> Result<ValueWord, VMError>
Fast function execution for hot loops (backtesting)
- Uses pre-computed function ID (no name lookup)
- Uses reset_minimal() for minimum overhead
- Uses execute_fast() which skips debugging overhead
- Assumes function doesn’t create GC objects or use exceptions
Sourcepub fn execute_function_with_named_args(
&mut self,
func_id: u16,
named_args: &[(String, ValueWord)],
ctx: Option<&mut ExecutionContext>,
) -> Result<ValueWord, VMError>
pub fn execute_function_with_named_args( &mut self, func_id: u16, named_args: &[(String, ValueWord)], ctx: Option<&mut ExecutionContext>, ) -> Result<ValueWord, VMError>
Execute a function with named arguments Maps named args to positional based on function’s param_names
Sourcepub fn resume(
&mut self,
value: ValueWord,
ctx: Option<&mut ExecutionContext>,
) -> Result<ExecutionResult, VMError>
pub fn resume( &mut self, value: ValueWord, ctx: Option<&mut ExecutionContext>, ) -> Result<ExecutionResult, VMError>
Resume execution after a suspension.
The resolved value is pushed onto the stack, and execution continues from where it left off (the IP is already set to the resume point).
Sourcepub fn execute_with_async(
&mut self,
ctx: Option<&mut ExecutionContext>,
) -> Result<ValueWord, VMError>
pub fn execute_with_async( &mut self, ctx: Option<&mut ExecutionContext>, ) -> Result<ValueWord, VMError>
Execute with automatic async task resolution.
Runs execute_with_suspend in a loop. Each time the VM suspends on a
Future { id }, the host resolves the task via the TaskScheduler
(synchronously executing the spawned callable inline) and resumes the
VM with the result. This continues until execution completes or an
unresolvable suspension is encountered.
Source§impl VirtualMachine
impl VirtualMachine
Sourcepub fn execute(
&mut self,
ctx: Option<&mut ExecutionContext>,
) -> Result<ValueWord, VMError>
pub fn execute( &mut self, ctx: Option<&mut ExecutionContext>, ) -> Result<ValueWord, VMError>
Execute the loaded program
§Arguments
ctx- Optional ExecutionContext for trading operations (rows, indicators, etc.)
Sourcepub fn execute_with_suspend(
&mut self,
ctx: Option<&mut ExecutionContext>,
) -> Result<ExecutionResult, VMError>
pub fn execute_with_suspend( &mut self, ctx: Option<&mut ExecutionContext>, ) -> Result<ExecutionResult, VMError>
Execute the loaded program, returning either a completed value or suspension info.
Unlike execute(), this method distinguishes between completion and suspension,
allowing the host to resume execution after resolving a future.
Source§impl VirtualMachine
impl VirtualMachine
Sourcepub fn snapshot(&self, store: &SnapshotStore) -> Result<VmSnapshot, VMError>
pub fn snapshot(&self, store: &SnapshotStore) -> Result<VmSnapshot, VMError>
Create a serializable snapshot of VM state.
Sourcepub fn from_snapshot(
program: BytecodeProgram,
snapshot: &VmSnapshot,
store: &SnapshotStore,
) -> Result<Self, VMError>
pub fn from_snapshot( program: BytecodeProgram, snapshot: &VmSnapshot, store: &SnapshotStore, ) -> Result<Self, VMError>
Restore a VM from a snapshot and bytecode program.
Source§impl VirtualMachine
impl VirtualMachine
pub fn new(config: VMConfig) -> Self
Sourcepub fn with_resource_limits(self, limits: ResourceLimits) -> Self
pub fn with_resource_limits(self, limits: ResourceLimits) -> Self
Attach resource limits to this VM. The dispatch loop will enforce them.
Sourcepub fn set_interrupt(&mut self, flag: Arc<AtomicU8>)
pub fn set_interrupt(&mut self, flag: Arc<AtomicU8>)
Set the interrupt flag (shared with Ctrl+C handler).
Sourcepub fn enable_time_travel(&mut self, mode: CaptureMode, max_entries: usize)
pub fn enable_time_travel(&mut self, mode: CaptureMode, max_entries: usize)
Enable time-travel debugging with the given capture mode and history limit.
Sourcepub fn disable_time_travel(&mut self)
pub fn disable_time_travel(&mut self)
Disable time-travel debugging and discard history.
Sourcepub fn enable_tiered_compilation(
&mut self,
) -> (Receiver<CompilationRequest>, Sender<CompilationResult>)
pub fn enable_tiered_compilation( &mut self, ) -> (Receiver<CompilationRequest>, Sender<CompilationResult>)
Enable tiered compilation for this VM.
Must be called after load_program() so the function count is known.
The caller is responsible for spawning a background compilation thread
that reads from the request channel and sends results back.
Returns (request_rx, result_tx) that the background thread should use.
Sourcepub fn tier_manager(&self) -> Option<&TierManager>
pub fn tier_manager(&self) -> Option<&TierManager>
Get a reference to the tier manager, if tiered compilation is enabled.
Sourcepub fn feedback_vectors(&self) -> &[Option<FeedbackVector>]
pub fn feedback_vectors(&self) -> &[Option<FeedbackVector>]
Access the feedback vectors (for JIT compilation).
Sourcepub fn program(&self) -> &BytecodeProgram
pub fn program(&self) -> &BytecodeProgram
Get a reference to the loaded program (for external JIT compilation).
Sourcepub fn time_travel(&self) -> Option<&TimeTravel>
pub fn time_travel(&self) -> Option<&TimeTravel>
Get a reference to the time-travel debugger, if enabled.
Sourcepub fn time_travel_mut(&mut self) -> Option<&mut TimeTravel>
pub fn time_travel_mut(&mut self) -> Option<&mut TimeTravel>
Get a mutable reference to the time-travel debugger, if enabled.
Sourcepub fn module_registry(&self) -> &ModuleExportRegistry
pub fn module_registry(&self) -> &ModuleExportRegistry
Get a reference to the extension module registry.
Sourcepub fn register_extension(&mut self, module: ModuleExports)
pub fn register_extension(&mut self, module: ModuleExports)
Register an extension module into the VM’s module registry. Also merges any method intrinsics for fast Object dispatch.
Sourcepub fn register_module_fn(&mut self, f: ModuleFn) -> usize
pub fn register_module_fn(&mut self, f: ModuleFn) -> usize
Register a ModuleFn in the table and return its ID (for ValueWord::ModuleFunction).
Sourcepub fn populate_module_objects(&mut self)
pub fn populate_module_objects(&mut self)
Populate extension module objects as module_bindings (json, duckdb, etc.).
These are used by extension Shape code (e.g., duckdb.query(...)).
Call this after load_program().
Source§impl VirtualMachine
impl VirtualMachine
Sourcepub fn enable_output_capture(&mut self)
pub fn enable_output_capture(&mut self)
Enable output capture for testing When enabled, print output goes to an internal buffer instead of stdout
Sourcepub fn get_captured_output(&self) -> Vec<String>
pub fn get_captured_output(&self) -> Vec<String>
Get captured output (returns empty vec if capture not enabled)
Sourcepub fn clear_captured_output(&mut self)
pub fn clear_captured_output(&mut self)
Clear captured output
Sourcepub fn load_program(&mut self, program: BytecodeProgram)
pub fn load_program(&mut self, program: BytecodeProgram)
Load a program into the VM
Sourcepub fn load_linked_program(&mut self, linked: LinkedProgram)
pub fn load_linked_program(&mut self, linked: LinkedProgram)
Load a LinkedProgram into the VM, extracting content-addressed metadata
directly from the linked function table.
This converts the LinkedProgram into the flat BytecodeProgram layout that
the executor expects, then populates function_hashes and function_entry_points
from the linked function metadata.
Sourcepub fn patch_function(
&mut self,
fn_id: u16,
new_blob: FunctionBlob,
) -> Result<Option<FunctionHash>, String>
pub fn patch_function( &mut self, fn_id: u16, new_blob: FunctionBlob, ) -> Result<Option<FunctionHash>, String>
Hot-patch a single function in the loaded program with a new blob.
The new blob’s instructions, constants, and strings replace the existing function’s bytecode in-place. The function’s metadata (arity, param names, locals count, etc.) is also updated. The content hash is recorded so that in-flight frames referencing the old hash remain valid (they execute from their saved IP which is now stale, but callers that resolve by function ID will pick up the new code on the next call).
Returns Ok(old_hash) on success (the previous content hash, if any),
or Err(msg) if the function ID is out of range.
Sourcepub fn load_program_with_permissions(
&mut self,
program: Program,
granted: &PermissionSet,
) -> Result<(), PermissionError>
pub fn load_program_with_permissions( &mut self, program: Program, granted: &PermissionSet, ) -> Result<(), PermissionError>
Load a content-addressed Program with permission checking.
Links the program, checks that total_required_permissions is a subset of
granted, and loads normally if the check passes. Returns an error listing
the missing permissions if the check fails.
Sourcepub fn load_linked_program_with_permissions(
&mut self,
linked: LinkedProgram,
granted: &PermissionSet,
) -> Result<(), PermissionError>
pub fn load_linked_program_with_permissions( &mut self, linked: LinkedProgram, granted: &PermissionSet, ) -> Result<(), PermissionError>
Load a LinkedProgram with permission checking.
Checks that total_required_permissions is a subset of granted, then
loads normally. Returns an error listing the missing permissions if the
check fails.
Sourcepub fn reset_stack(&mut self)
pub fn reset_stack(&mut self)
Reset stack only (for reusing compiled program across iterations) Keeps program, module_bindings, and GC state intact - only clears execution state
Sourcepub fn reset_minimal(&mut self)
pub fn reset_minimal(&mut self)
Minimal reset for hot loops - only clears essential state Use this when you know the function doesn’t create GC objects or use exceptions
Sourcepub fn last_error_line(&self) -> Option<u32>
pub fn last_error_line(&self) -> Option<u32>
Get the line number of the last error (for LSP integration)
Sourcepub fn last_error_file(&self) -> Option<&str>
pub fn last_error_file(&self) -> Option<&str>
Get the file path of the last error (for LSP integration)
Sourcepub fn take_last_uncaught_exception(&mut self) -> Option<ValueWord>
pub fn take_last_uncaught_exception(&mut self) -> Option<ValueWord>
Take the last uncaught exception payload if present.
Sourcepub fn push_value(&mut self, value: ValueWord)
pub fn push_value(&mut self, value: ValueWord)
Push a value onto the stack (public, for testing and host integration)
Sourcepub fn get_function_id(&self, name: &str) -> Option<u16>
pub fn get_function_id(&self, name: &str) -> Option<u16>
Get function ID for fast repeated calls (avoids name lookup in hot loops)
Source§impl VirtualMachine
impl VirtualMachine
pub fn create_typed_enum( &self, enum_name: &str, variant_name: &str, payload: Vec<ValueWord>, ) -> Option<ValueWord>
Trait Implementations§
Source§impl DebuggerIntegration for VirtualMachine
impl DebuggerIntegration for VirtualMachine
Source§fn trace_state(&self)
fn trace_state(&self)
Source§fn debug_break(&self)
fn debug_break(&self)
Source§fn instruction_pointer(&self) -> usize
fn instruction_pointer(&self) -> usize
Source§fn stack_size(&self) -> usize
fn stack_size(&self) -> usize
Source§fn stack_top(&self) -> Option<ExternalValue>
fn stack_top(&self) -> Option<ExternalValue>
Source§fn stack_values_vec(&self) -> Vec<ExternalValue>
fn stack_values_vec(&self) -> Vec<ExternalValue>
Source§fn call_stack_depth(&self) -> usize
fn call_stack_depth(&self) -> usize
Source§fn call_frames(&self) -> &[CallFrame]
fn call_frames(&self) -> &[CallFrame]
Source§fn local_values_vec(&self) -> Vec<ExternalValue>
fn local_values_vec(&self) -> Vec<ExternalValue>
Source§fn module_binding_values(&self) -> Vec<ValueWord>
fn module_binding_values(&self) -> Vec<ValueWord>
Source§fn set_module_binding(&mut self, index: usize, value: ValueWord)
fn set_module_binding(&mut self, index: usize, value: ValueWord)
Source§fn set_trace_mode(&mut self, enabled: bool)
fn set_trace_mode(&mut self, enabled: bool)
Source§fn debugger_mut(&mut self) -> Option<&mut VMDebugger>
fn debugger_mut(&mut self) -> Option<&mut VMDebugger>
Source§fn has_debugger(&self) -> bool
fn has_debugger(&self) -> bool
Source§impl GCIntegration for VirtualMachine
Available on non-crate feature gc only.
impl GCIntegration for VirtualMachine
gc only.Source§fn maybe_collect_garbage(&mut self)
fn maybe_collect_garbage(&mut self)
Source§fn gc_heap_size(&self) -> usize
fn gc_heap_size(&self) -> usize
Source§fn gc_object_count(&self) -> usize
fn gc_object_count(&self) -> usize
Source§fn gc(&self) -> &GarbageCollector
fn gc(&self) -> &GarbageCollector
Source§fn gc_mut(&mut self) -> &mut GarbageCollector
fn gc_mut(&mut self) -> &mut GarbageCollector
Source§impl TypedObjectOps for VirtualMachine
impl TypedObjectOps for VirtualMachine
Source§fn op_get_field_typed(
&mut self,
instruction: &Instruction,
) -> Result<(), VMError>
fn op_get_field_typed( &mut self, instruction: &Instruction, ) -> Result<(), VMError>
Get field from typed object using precomputed field type tag.
Zero-cost field access: the compiler embeds type_id, field_idx, and
field_type_tag into the operand. At runtime we just read
slots[field_idx] and use heap_mask + field_type_tag to interpret it.
No schema lookup required.
Source§fn op_set_field_typed(
&mut self,
instruction: &Instruction,
) -> Result<(), VMError>
fn op_set_field_typed( &mut self, instruction: &Instruction, ) -> Result<(), VMError>
Set field on typed object using precomputed field type tag.
Auto Trait Implementations§
impl !Freeze for VirtualMachine
impl !RefUnwindSafe for VirtualMachine
impl !Send for VirtualMachine
impl !Sync for VirtualMachine
impl Unpin for VirtualMachine
impl UnsafeUnpin for VirtualMachine
impl !UnwindSafe for VirtualMachine
Blanket Implementations§
Source§impl<T> BorrowMut<T> for Twhere
T: ?Sized,
impl<T> BorrowMut<T> for Twhere
T: ?Sized,
Source§fn borrow_mut(&mut self) -> &mut T
fn borrow_mut(&mut self) -> &mut T
Source§impl<T> Instrument for T
impl<T> Instrument for T
Source§fn instrument(self, span: Span) -> Instrumented<Self>
fn instrument(self, span: Span) -> Instrumented<Self>
Source§fn in_current_span(self) -> Instrumented<Self>
fn in_current_span(self) -> Instrumented<Self>
Source§impl<T> IntoEither for T
impl<T> IntoEither for T
Source§fn into_either(self, into_left: bool) -> Either<Self, Self>
fn into_either(self, into_left: bool) -> Either<Self, Self>
self into a Left variant of Either<Self, Self>
if into_left is true.
Converts self into a Right variant of Either<Self, Self>
otherwise. Read moreSource§fn into_either_with<F>(self, into_left: F) -> Either<Self, Self>
fn into_either_with<F>(self, into_left: F) -> Either<Self, Self>
self into a Left variant of Either<Self, Self>
if into_left(&self) returns true.
Converts self into a Right variant of Either<Self, Self>
otherwise. Read more