Skip to content

feat: numscript compiler, public compile/exec API and CLI - #200

Merged
ascandone merged 1 commit into
feat/register-vm-irfrom
feat/numscript-compiler
Sep 25, 2026
Merged

ascandone merged 1 commit into
feat/register-vm-irfrom
feat/numscript-compiler

Conversation

@ascandone

Copy link
Copy Markdown
Contributor

PR 3 of the VM series, stacked on #199 (retargets to main when it merges). Cut from feat/vm's final tree state by path checkout, like #199.

What this adds

  • internal/compiler — lowers parsed numscript to the IR of feat: compiler and register VM #199: sources/destinations to funds-queue instruction sequences, allotments to AssertLeftover + split, vars to typed registers with a VarsEncoder for runtime bindings. Fixture-driven tests run the whole interpreter spec corpus through compiler+VM (scripts_test.go), with a blacklist for the one feature the compiler doesn't lower yet (asset scaling), plus a corpus-wide verifier pass.
  • internal/typecheck — the compiler's checker: bidirectional base-type checking, fault-tolerant. Not a duplicate of analysis' checker, which is unification-based (asset-identity inference) and stays the LSP's.
  • internal/builtins — the builtin name constants, now shared: analysis' Fn* constants alias these instead of re-declaring the literals (one of the two cleanups noted in the series plan; the other is typecheck's package doc, which wrongly claimed analysis consumes it).
  • Public API (numscript.go): Compile/CompileWithFeatureFlags, CompiledProgram encode/decode, VarsEncoder/DecodeVars, NewVm/ExecVm, and opt-in VerifyCompiledProgram(WithVars) for bytecode from elsewhere. compiler-architecture.md documents the pipeline.
  • CLI wiring in internal/cmd.

24 files, +6.9k/−20.

Semantics

The compiler+VM matches the tree-walking interpreter on the whole spec corpus, including the recent main-side decisions: a negative destination max clamps to zero (was a hard error in an earlier cut of this code; aligned after merging main into feat/vm), and allotments past 100% next to remaining reject at run time (Op_AssertLeftover), which the interpreter now also does since #198.

Verification

Root suite (incl. the full fixture corpus through compiler+VM), internal/oracle and internal/difftest modules green; gofmt clean. Next in the series: the difftest VM leg, so generated programs run against oracle, interpreter and VM together.

The numscript-to-IR compiler (internal/compiler) with its own
bidirectional checker (internal/typecheck) and the shared builtin names
(internal/builtins); the public API in numscript.go (Compile,
VarsEncoder, NewVm, ExecVm, program/vars encode-decode, opt-in
verification) and the CLI wiring. Cut from feat/vm's final tree state.

Two cleanups called out in the series plan: internal/analysis' builtin
name constants now alias internal/builtins instead of re-declaring the
literals, and typecheck's package doc no longer claims analysis
consumes it (analysis keeps its own unification-based checker).
@NumaryBot NumaryBot added risk: medium NumaryBot classified this pull request as medium risk. bot-reviewed NumaryBot completed its review workflow for the current head. review-inconclusive labels Sep 25, 2026
@ascandone
ascandone merged commit 5790bef into feat/register-vm-ir Sep 25, 2026
12 of 16 checks passed
@ascandone
ascandone deleted the feat/numscript-compiler branch September 25, 2026 15:58
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

bot-reviewed NumaryBot completed its review workflow for the current head. review-inconclusive risk: medium NumaryBot classified this pull request as medium risk.

Development

Successfully merging this pull request may close these issues.

2 participants