From f66925d3a8a1ba3cd8147e0c9aaf6ff0cfa2883b Mon Sep 17 00:00:00 2001 From: Yogthos Date: Mon, 22 Jun 2026 23:07:04 -0400 Subject: [PATCH] jolt build: --opt mode turns on the inference passes (Phase 4 stage 4a) MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Wire the optimization gate to build mode. inline-enabled? (which gates the inference + flatten-lets + scalar-replace passes in jolt.passes/run-passes) was hardwired off, so those passes had never run on Chez at all. host-contract now exposes a settable hc-optimize? flag; `jolt build --opt` flips it on during app emission. Kept off for the default release build for now: the passes are sound by design (RFC 0005/0006) but unexercised on Chez, so release stays on the proven var-deref codegen until they're validated against the corpus. --opt is the opt-in fast path. buildsmoke checks both modes produce the same result. This does not yet deliver direct call binding — the backend has no direct-link emission path (every :var call still routes through jolt-invoke/var-deref) and the inline-ir host stash is still a stub. Those are the remaining stage-4 levers. --- host/chez/build-smoke.sh | 17 ++++++++++++++--- host/chez/build.ss | 7 ++++++- host/chez/host-contract.ss | 7 ++++++- 3 files changed, 26 insertions(+), 5 deletions(-) diff --git a/host/chez/build-smoke.sh b/host/chez/build-smoke.sh index 8cd75de..d058b96 100755 --- a/host/chez/build-smoke.sh +++ b/host/chez/build-smoke.sh @@ -22,11 +22,22 @@ want='HELLO FROM A BUILT BINARY! HELLO FROM A BUILT BINARY! args: [alpha bb ccc] sum: 10' -if [ "$got" = "$want" ]; then - echo "build smoke: passed" -else +if [ "$got" != "$want" ]; then echo " FAIL: binary output mismatch" echo "--- want ---"; echo "$want" echo "--- got ----"; echo "$got" exit 1 fi + +# Optimized mode (inference + flatten + scalar-replace) must produce the same +# result — a sanity check that the passes don't miscompile this app. +if ! JOLT_PWD="$app" bin/joltc build -m app.core -o "$out" --opt >/dev/null 2>&1; then + echo " FAIL: jolt build --opt exited non-zero"; exit 1 +fi +got_opt="$(cd / && "$out" alpha bb ccc 2>&1)" +if [ "$got_opt" != "$want" ]; then + echo " FAIL: --opt binary output mismatch" + echo "--- got ----"; echo "$got_opt" + exit 1 +fi +echo "build smoke: passed (release + optimized)" diff --git a/host/chez/build.ss b/host/chez/build.ss index a3bacdb..8eae388 100644 --- a/host/chez/build.ss +++ b/host/chez/build.ss @@ -179,10 +179,15 @@ (when (null? ordered) (error 'jolt-build (string-append "no source namespace loaded for " entry-ns " — is it on the source roots?"))) - ;; 2. emit each app namespace. + ;; 2. emit each app namespace. `optimized` turns on the inference + flatten + ;; + scalar-replace passes (closed world). release/dev stay on proven + ;; var-deref codegen until those passes are validated on Chez — they were + ;; dormant before `jolt build` (inline-enabled? was hardwired off). + (set-optimize! (string=? mode "optimized")) (let* ((app-strs (apply append (map (lambda (nf) (bld-emit-ns (car nf) (read-file-string (cdr nf)))) ordered))) + (_ (set-optimize! #f)) (builddir (string-append out-path ".build")) (flat-ss (string-append builddir "/flat.ss")) (flat-so (string-append builddir "/flat.so")) diff --git a/host/chez/host-contract.ss b/host/chez/host-contract.ss index fe7e2c6..4bf38c3 100644 --- a/host/chez/host-contract.ss +++ b/host/chez/host-contract.ss @@ -280,7 +280,12 @@ (define (hc-record-type? ctx name) #f) (define (hc-record-ctor-key ctx name) jolt-nil) (define (hc-record-shapes ctx) (jolt-hash-map)) -(define (hc-inline-enabled? ctx) #f) +;; Optimization gate. Off for ordinary runs (open world, redefinition); `jolt +;; build` flips it on during app emission for release/optimized modes (closed +;; world), turning on the inference + flatten + scalar-replace passes. +(define hc-optimize? #f) +(define (set-optimize! on) (set! hc-optimize? on)) +(define (hc-inline-enabled? ctx) hc-optimize?) (define (hc-inline-ir ctx ns-name nm) jolt-nil) ;; --- declare the hot clojure.core primitives so resolve-global sees them ------