SageVM is a high-performance, pure SageLang implementation of the Sage Virtual Machine. It provides a portable execution substrate for SageOS, supporting both a traditional stack-based architecture (SVM) and a modern RISC-V register-based architecture (SRVM).
| Component | Compile | Execute | Self-Host | Coverage Suite |
|---|---|---|---|---|
SVM (Stack VM / .sgvm) |
✅ | ✅ | ✅ | 143 passed, 0 failed, 1 skipped |
SRVM (RISC-V Register VM / .sgrv) |
✅ | — | Not green; see TESTING.md |
- SVM is fully self-hosting and verified:
sagevm_standalone.sagecompiles to a.sgvmbinary (~96 KB) and executes on the Stack VM. The modern coverage suite passes with 143 tests, 0 failures, and 1 documented skip. - SRVM compilation and execution pipeline: Full SageLang source → SVM bytecode → RISC-V 32-bit instructions →
.sgrvbinary (~199 KB) execution with RV64I register file semantics. The current full SRVM suite still has broad backend compatibility failures in this checkout; targeted security and compilation checks remain required.
- Dual-Architecture Engine: Seamlessly switch between Stack VM (SVM) and RISC-V Register VM (SRVM) targets.
- Self-Hosted Compilation: The SageVM compiler is written in SageLang and compiles itself via the Stack VM — a true bootstrap.
- Coverage: The modern SVM suite covers 143 passing cases with one documented skip; legacy opcode and backend gaps are tracked in
TESTING.md. - Native Generator Yield Engine: Native SVM state preservation for
OP_YIELD,OP_CREATE_GENERATOR, andOP_GENERATOR_NEXT/next(). - RISC-V Translation: Full
StackToRiscVTranslatorpipeline converts SVM bytecode to RV64I-compatible 32-bit fixed-width instructions. - OOP & Exceptions: Native support for classes, inheritance, and
try/catch/finallyacross both architectures. - Delegation Bridge: Guest-to-host delegation for GPU, I/O, FFI, and native modules.
- Matrix Visualization: Native
math.printmsupport for formatted matrix output. - Security Sandboxing:
--safe,--no-exec, and--no-ffiflags for restricting guest execution. - Unified CLI: A single
sagevmtool to compile, run, disassemble, and hexdump both.sgvmand.sgrvbinaries with ANSI color feedback and automatic architecture detection.
SageVM requires SageLang v4.2.7 or higher. To build and install:
./sagemake --installThis produces the sagevm binary (and symlinks for sgvm/sgvmc).
To build without installing:
./sagemake buildsagevm run <file.sgvm|.sgrv> [--debug] [--safe] [--no-exec] [--no-ffi] [--riscv] [--jit]
sagevm compile <file.sage> [output] [--shebang] [--riscv]
sagevm dis <file.sgvm|.sgrv> [--sage | --svm] [--riscv]
sagevm hex <file.sgvm|.sgrv> [--riscv]
sagevm repl [--riscv | --svm] [--debug] [--safe] [--jit]
sagevm version
- run: Execute a compiled binary. Auto-detects architecture via magic headers (
SGVM/SGRV). - compile: Compile SageLang source to binary. Use
--riscvfor register-based.sgrvoutput. - dis: Disassemble binary into readable instructions. Auto-detects architecture.
- hex: Low-level binary hexdump. Auto-detects architecture.
- repl: Launch interactive REPL executing input lines directly on SRVM (RISC-V) or SVM (Stack VM) substrates.
The core SGVM architecture. Uses variable-length bytecode and a 65,536-entry operand stack. Optimized for code density and simple compiler targets.
- Opcode count: 92 (including locals, generators, GPU hot-paths)
- Call depth: 1,024 frames
- Handler depth: 1,024 levels
- Performance: Fully inlined hot-loop dispatch with state caching, single/two-scope global fast-paths, stack slot re-use, and in-place stack modification
A modern, register-based architecture based on the RV64I specification.
- 32 × 64-bit registers: Standard RISC-V register file mapping (x0–x31)
- Fixed-width encoding: 32-bit instructions for simplified decoding
- Custom VMSYS extensions:
OP_VMSYSfor SageVM system calls, object operations, and GPU delegation - Type profiling:
TypeProfilerfor register-level type hint analysis - Performance: Up to 30–40% faster interpretation for arithmetic-heavy code
Full detail in docs/CHANGELOG.md.
sys.exitis refused in safe mode, in both the SVM and the SRVM. It was reachable there.- Module host functions called through method dispatch are refused in safe mode, in both VMs.
- Generator chunk indices are bounds-checked before indexing
self.chunks. - Module reflection (
dir/keys/values) yields only values typedmoduleor prefixed__host_, instead of any string value -- which is how internal state was observable from a module wrapper. dict_keys/dict_values/dict_itemsreject a non-dict argument rather than indexing into it, in both VMs.
- 16-bit big-endian operands are decoded inline in
MetalVM.execute_opinstead of through aread_be16call, on the operand-fetch and jump paths. OP_GET_GLOBALcache hits short-circuit on booleantrue, and the constant-pool name lookup is deferred into thesafe_modebranch rather than paid on every global read.
- Seven new edge-case suites, each verified passing before merge. Suite is now 153 passed, 0 failed, 1 skipped, up from 140 passed / 6 failed.
security_builtins_hardeninghad an expectation asserting that an internal value leaks in safe mode, contradicting the comment beside it. Corrected.
- The version banner reported v1.1.0 while
VERSIONsaid v1.2.1; both now report 1.2.2.
- SRVM equality and uncallable handling: Added explicit nil-aware equality and a defined nil result for uncallable return paths.
- SVM constant-pool bounds: Replaced raw constant reads in fallback opcode handlers with checked accessors.
- SRVM safe-mode documentation: Synchronized architecture and specification notes for builtin and method protections.
- Global dispatch ordering: Deferred constant lookups behind cache-hit checks and moved startup-only opcode handling out of the hot loop path.
- Added nested-loop and loop/exception coverage fixtures; the SVM suite now passes 143 tests with one documented skip.
sys.systemdispatch fix (SVM):OP_IMPORTnow mapssys.systemto__builtin_sys_system; restricted runs reportError: sys.system is restrictedand return-1instead of silently routing through thesys.exechandler.- SRVM execution hardening:
sys.exec/sys.systemmap to functional builtin handlers enforcingsafe_mode/exec_enabled; added missingVMO_EXEC_AST,OBJ_METHOD_BIND, andVMO_CALL(instance-call) implementations plusOP_EXEC_AST_STMTtranslation in the SRVM compiler.
- Stack slot re-use: Replaced host
push()/pop()calls in the interpreter hot loop with logical stack-length management and slot re-use (~5.4% faster on 1M-iteration loops). - Index/property fast paths: Lazy
type()evaluation and safe-mode short-circuiting inOP_GET_INDEX/OP_SET_INDEX/OP_SET_PROPERTYcut GC pressure on index-heavy workloads by over 56%. - Dispatch streamlining: Bypassed redundant
dict_haspre-checks, skipped argument-array allocation for zero-arg calls, and inlined BE16 decoding in method dispatch (~13.6% faster on OOP benchmarks).
- Coverage suite expanded to 113 tests: New edge-case coverage for string builtins (
startswith/endswith), tuples,type(), andmem/structmodules; expectations aligned with the current SageLang host toolchain. - sagemake: Submodule synchronization now recurses into nested submodules for reliable reproducible builds.
| Benchmark | SVM (ms) | SRVM (ms) | Improvement |
|---|---|---|---|
fibonacci(22) |
2256 | 1580 | 30% |
loop_sum |
4513 | 3120 | 31% |
exception_handling |
417 | 290 | 30% |
Benchmarks reflect interpretation overhead in a pure SageLang environment.
- Architecture — Technical details of SVM and SRVM execution substrates
- Specification — Formal specification of binary formats and execution
- RISC-V Design — Deep dive into the SRVM register-based design
- Changelog — Full version history
- Roadmap — Outstanding features and known gaps
This project is licensed under the same terms as SageLang.
