Chez numeric tower: exact ints / Ratio / double for JVM parity (jolt-n6al)
jolt was all-flonum (one :number type, inherited from Janet whose only number type is a double). The Chez runtime has a full numeric tower, so the zero-Janet path now carries it = JVM Clojure semantics: (/ 1 2) => 1/2 (exact Ratio, was 0.5) (integer? 3) => true (integer? 3.0) => false (float? 3.0) => true (ratio? (/ 1 2)) => true (= 3 3.0) => false (== 3 3.0) => true (+ 1 2) => 3 (exact) (/ 1.0 2) => 0.5 (double) jolt= was already exactness-aware (values.ss) and == is value-equality, so =/== match the JVM split. The reader preserves exactness (integer literals exact, a/b ratios exact rationals, decimals/exponents flonums); backend_scheme emit-const renders exact ints/ratios and flonums faithfully; the value-position arithmetic, count, int, compare, bit ops, parseLong, string .length/.indexOf, range, timestamps, and array bytes return exact integers (= JVM int/long) instead of coercing to flonum. double/parseDouble/clojure.math floor|ceil|signum stay double. Only the zero-Janet path carries the tower (the Janet reader loses exactness into a double before emit). The prelude/all-flonum path is unaffected for compiled code; the runtime reader is shared, so a couple of all-flonum reader assertions become value (==) assertions. ~16 numeric corpus cases now give the JVM tower value vs the Janet-era :expected and are allowlisted as tower divergences (Chez == reference JVM) pending the corpus flip to JVM (jolt-ecz0). No BigDecimal type (1M). Re-minted. zero-janet 2682 (floor 2698->2682, the reclassified tower cases), 0 new divergences; fixpoint 10/10, bootstrap 6/6, spine 35/35, cli 49/49; Janet gate 155 files 0 failed.
This commit is contained in:
parent
eb1c3298a4
commit
467ad75ff7
20 changed files with 291 additions and 210 deletions
|
|
@ -14,9 +14,12 @@
|
|||
[# --- scalars + collections (value equality, order-independent) ---
|
||||
["(= 42 (read-string \"42\"))" "true"]
|
||||
["(= 42 (read-string \"0x2A\"))" "true"]
|
||||
["(= 0.5 (read-string \"1/2\"))" "true"]
|
||||
# numeric tower (jolt-n6al): "1/2" reads as an exact Ratio (= JVM), so a
|
||||
# category-aware = against the double 0.5 is false; assert numeric value (==),
|
||||
# which holds in both the all-flonum and tower models.
|
||||
["(== 0.5 (read-string \"1/2\"))" "true"]
|
||||
["(= -3.5 (read-string \"-3.5\"))" "true"]
|
||||
["(= 1000.0 (read-string \"1e3\"))" "true"]
|
||||
["(== 1000.0 (read-string \"1e3\"))" "true"]
|
||||
["(= 1 (read-string \"1N\"))" "true"]
|
||||
["(integer? (read-string \"7\"))" "true"]
|
||||
["(= :foo (read-string \":foo\"))" "true"]
|
||||
|
|
|
|||
|
|
@ -110,7 +110,27 @@
|
|||
# unquoted value forms eval in hash order, not source order — a minor ordering
|
||||
# gap (pmap has no insertion order; the reader's source-order table doesn't cover
|
||||
# syntax-quote-built maps). 1 case; the non-syntax-quote map-order cases pass.
|
||||
"source order through syntax-quote" true})
|
||||
"source order through syntax-quote" true
|
||||
# numeric tower (jolt-n6al): the zero-Janet path now carries the Chez numeric
|
||||
# tower (exact ints / Ratio / double) = JVM parity, while the corpus :expected
|
||||
# is the all-flonum Janet value (the Janet host has only doubles). So Chez gives
|
||||
# the JVM value and the Janet-era corpus diverges — flipped to JVM at Phase 5
|
||||
# (jolt-ecz0), these stay allowlisted during the transition. Each verified
|
||||
# Chez == reference JVM Clojure.
|
||||
"divide to fraction" true # (/ 1 2) -> 1/2 (JVM Ratio), corpus 0.5
|
||||
"ratio 3/4" true # 3/4 literal -> Ratio
|
||||
"neg ratio" true # -1/2 -> Ratio
|
||||
"ratio -> double" true # ratio result, corpus double
|
||||
"/ ratio-as-double" true
|
||||
"native unary div" true # (/ 2) -> 1/2
|
||||
"double" true # (double 3) -> 3.0 (double != exact 3)
|
||||
"doubles" true "floats" true
|
||||
"unchecked-double" true "unchecked-float" true
|
||||
"floor" true # clojure.math/floor -> 2.0 (JVM double)
|
||||
"signum" true # clojure.math/signum -> -1.0 (JVM double)
|
||||
"Math/sqrt" true # -> 3.0 (double)
|
||||
"Math/pow" true # -> 8.0 (double)
|
||||
"bigdec int M" true}) # 1M: no BigDecimal type on Chez (documented gap)
|
||||
|
||||
# Cases that BLOCK forever on a shared-heap / JVM host (profile.edn :bucket
|
||||
# :timeout) — skip them, like :throws: a single hung case would stall the whole
|
||||
|
|
@ -226,7 +246,12 @@
|
|||
# date/time (Date/Timestamp/SimpleDateFormat/TimeZone) + clojure.edn/read over a
|
||||
# reader -> 2692; STM stub + portable line-seq -> 2696; realized? on a lazy-seq +
|
||||
# conj! 1-arity (transducer-completion identity) -> 2698.
|
||||
(def base-floor (scan-number (or (os/getenv "JOLT_CHEZ_ZJ_FLOOR") "2698")))
|
||||
# numeric tower (jolt-n6al): 2698 -> 2682. ~16 numeric cases that the all-flonum
|
||||
# model coincidentally passed (corpus :expected is the Janet double value) now give
|
||||
# the JVM tower value (1/2, 3.0, ...) and are reclassified as known tower
|
||||
# divergences (Chez == reference JVM). The floor rises back when the corpus flips
|
||||
# to JVM values (jolt-ecz0, Phase 5).
|
||||
(def base-floor (scan-number (or (os/getenv "JOLT_CHEZ_ZJ_FLOOR") "2682")))
|
||||
(def floor (if (os/getenv "JOLT_CORPUS_LIMIT") 0 base-floor))
|
||||
(when (or (> (length diverged) 0) (< pass floor))
|
||||
(printf "REGRESSION: pass %d < floor %d or %d new divergence(s)" pass floor (length diverged)))
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue