JVM parity: unchecked-char -> char, pr of infinities -> ##Inf

Allowlist review found three addressable divergences:
- unchecked-char returned a number; the JVM returns a char.
- the readable printer (pr-str, coll elements, the -e/REPL printer) rendered
  infinities as Infinity/inf; Clojure's readable form is ##Inf/##-Inf/##NaN
  (str/print still gives Infinity). So (pr-str ##Inf) => ##Inf, (str [##Inf]) =>
  [##Inf], (str ##Inf) => Infinity.

Corpus 2695->2698; allowlist 43->40 (drop the 3 now-passing entries). Re-minted.
This commit is contained in:
Yogthos 2026-06-21 17:55:05 -04:00
parent 518683ccd6
commit 4d1ec44676
5 changed files with 19 additions and 20 deletions

View file

@ -28,11 +28,11 @@
(define (jolt-pr-readable x)
(cond
((string? x) (string-append "\"" (jolt-str-escape x) "\""))
;; pr renders the infinities / NaN long-form (Clojure .toString), at every
;; nesting level — unlike the -e printer's inf/-inf/nan.
((and (flonum? x) (fl= x +inf.0)) "Infinity")
((and (flonum? x) (fl= x -inf.0)) "-Infinity")
((and (flonum? x) (not (fl= x x))) "NaN")
;; pr renders the infinities / NaN in READABLE form (##Inf reads back), unlike
;; str's "Infinity"/"-Infinity"/"NaN". Applies at every nesting level.
((and (flonum? x) (fl= x +inf.0)) "##Inf")
((and (flonum? x) (fl= x -inf.0)) "##-Inf")
((and (flonum? x) (not (fl= x x))) "##NaN")
;; transients print as a cold tagged type (print-method routes this through a
;; multimethod; the readable fallback renders it directly).
;; forward refs to transients.ss (loaded later) — resolved at call time.

View file

@ -133,12 +133,12 @@
;; without a ".0" ((* 1.0 5) prints as "5", (/ 1 2) as "0.5").
(define (jolt-num->string x)
(cond
;; the -e / element printer renders the infinities and NaN as inf/-inf/nan
;; (Chez's number->string gives +inf.0 etc.); the str/print family uses the
;; long "Infinity"/"NaN" forms (see jolt-str-render-one in converters.ss).
((and (flonum? x) (fl= x +inf.0)) "inf")
((and (flonum? x) (fl= x -inf.0)) "-inf")
((and (flonum? x) (not (fl= x x))) "nan")
;; the -e / element printer renders the infinities and NaN in READABLE form
;; (##Inf reads back, like Clojure's REPL/pr); str/print uses "Infinity"/"NaN"
;; (see jolt-str-render-one in converters.ss).
((and (flonum? x) (fl= x +inf.0)) "##Inf")
((and (flonum? x) (fl= x -inf.0)) "##-Inf")
((and (flonum? x) (not (fl= x x))) "##NaN")
((and (rational? x) (integer? x)) (number->string (exact x)))
(else (number->string x))))

View file

@ -11,7 +11,7 @@
;; reset between cases so there is no leakage — same isolation a fresh process gives.
;;
;; chez --script host/chez/run-corpus.ss
;; JOLT_CHEZ_ZJ_FLOOR=N override the regression floor (default 2695)
;; JOLT_CHEZ_ZJ_FLOOR=N override the regression floor (default 2698)
;; JOLT_CORPUS_LIMIT=N every-Nth stride (fast iteration; floor drops to 0)
;; JOLT_DUMP_CRASH_LABELS=1 list crash + allowlisted labels
(import (chezscheme))
@ -93,11 +93,11 @@
"^Type tag on var" "symbol hint -> :tag"
"lists extended type" "seq of tags"
"close on throw" "macroexpand-1" "ns-imports empty user"
"bean is the map" "proxy resolves nil" "unchecked-char"
"bean is the map" "proxy resolves nil"
"*in* is bound" "*in* bound"
"bigdec" "bigdec int M" "bigdec suffix M"
"transient vector" "transient map"
"atom override fires nested" "inf inside coll" "pr-str Infinity"
"atom override fires nested"
"defmethod overrides a record, top level"
"defmethod fires nested in a map" "defmethod fires through prn"
"direct builtin override" "methods table inspectable"
@ -203,7 +203,7 @@
;; Regression floor: fail on any NEW divergence or if pass drops below the floor.
(define base-floor (let ((s (getenv "JOLT_CHEZ_ZJ_FLOOR")))
(if s (string->number s) 2695)))
(if s (string->number s) 2698)))
(define floor (if limit 0 base-floor))
(when (or (> (length diverged) 0) (< pass floor))
(printf "REGRESSION: pass ~a < floor ~a or ~a new divergence(s)\n"

View file

@ -561,7 +561,7 @@
(guard (e (#t #f))
(def-var! "clojure.core" "unchecked-short" (letrec ((unchecked-short (lambda (x) (let fnrec918 ((x x)) (jolt-invoke (var-deref "clojure.core" "bit-and") (jolt-invoke (var-deref "clojure.core" "int") x) 65535))))) unchecked-short)))
(guard (e (#t #f))
(def-var! "clojure.core" "unchecked-char" (letrec ((unchecked-char (lambda (x) (let fnrec919 ((x x)) (jolt-invoke (var-deref "clojure.core" "bit-and") (jolt-invoke (var-deref "clojure.core" "int") x) 65535))))) unchecked-char)))
(def-var! "clojure.core" "unchecked-char" (letrec ((unchecked-char (lambda (x) (let fnrec919 ((x x)) (jolt-invoke (var-deref "clojure.core" "char") (jolt-invoke (var-deref "clojure.core" "bit-and") (jolt-invoke (var-deref "clojure.core" "int") x) 65535)))))) unchecked-char)))
(guard (e (#t #f))
(def-var! "clojure.core" "unchecked-float" (letrec ((unchecked-float (lambda (x) (let fnrec920 ((x x)) (jolt-invoke (var-deref "clojure.core" "double") x))))) unchecked-float)))
(guard (e (#t #f))