core: enforce fn arity in both modes (jolt-6xn); canonical seq-to-map-for-destructuring
Fixed arities now throw Clojure's ArityException shape — 'Wrong number of
args (N) passed to: name' — on any count mismatch; variadic arities on fewer
than their fixed params. The compiled path already enforced fixed arities via
janet's native fn check and multi-arity dispatch; this adds the check to the
interpreter's single-arity closures (the oracle was silently dropping extra
args and giving a raw tuple-index error for missing ones) and guards the
compiled single-variadic wrapper's minimum. Messages carry the fn name when
there is one. 16 spec rows; the update.cljc suite row flipped green (4703 ->
4704).
Enforcement exposed that seq-to-map-for-destructuring had drifted: the spec
row called the 1-arity fn with two args, and the body silently dropped a
trailing unpaired element. Replaced with the canonical Clojure 1.11 version
(even pairs build the map, a single trailing element passes through — so
(f {:b 2}) kwargs calls work — and an unpaired key throws).
Also: transients RFC notes tuple support from the seed-shrink rounds.
This commit is contained in:
parent
501c6bf9c9
commit
9e9fd19450
6 changed files with 66 additions and 12 deletions
|
|
@ -183,10 +183,18 @@
|
|||
(and (not multi) (not ((first arities) :rest)))
|
||||
(emit-arity-fn ctx (first arities))
|
||||
# Single variadic arity: a thin wrapper collects the call's args so the rest
|
||||
# seq can be built, then hands off to the arity fn.
|
||||
# seq can be built, then hands off to the arity fn. Fewer args than the
|
||||
# fixed params is an arity error (jolt-6xn) — without the guard the fixed
|
||||
# binds fell off the end of the args tuple with a raw index error.
|
||||
(not multi)
|
||||
(let [jargs (gsym)]
|
||||
['fn ['& jargs] (emit-arity-invoke ctx (first arities) jargs)])
|
||||
(let [jargs (gsym)
|
||||
ar (first arities)
|
||||
nfixed (length (vview (ar :params)))]
|
||||
['fn ['& jargs]
|
||||
['if ['< ['length jargs] nfixed]
|
||||
['error ['string "Wrong number of args (" ['length jargs] ") passed to: "
|
||||
(or (node :name) "fn")]]
|
||||
(emit-arity-invoke ctx ar jargs)]])
|
||||
# Multi-arity: dispatch on arg count. Fixed arities match exactly; the (one)
|
||||
# variadic arity matches >= its fixed count.
|
||||
(let [jargs (gsym)
|
||||
|
|
@ -196,7 +204,8 @@
|
|||
(def nfixed (length (vview (ar :params))))
|
||||
(array/push cf (if (ar :rest) [>= nsym nfixed] [= nsym nfixed]))
|
||||
(array/push cf (emit-arity-invoke ctx ar jargs)))
|
||||
(array/push cf ['error "wrong number of args passed to fn"])
|
||||
(array/push cf ['error ['string "Wrong number of args (" nsym ") passed to: "
|
||||
(or (node :name) "fn")]])
|
||||
['fn ['& jargs]
|
||||
['do ['def nsym ['length jargs]] (tuple/slice cf)]])))
|
||||
|
||||
|
|
|
|||
|
|
@ -1730,7 +1730,8 @@
|
|||
(cond
|
||||
f (apply f fn-args)
|
||||
(and variadic-fn (>= n variadic-min)) (apply variadic-fn fn-args)
|
||||
(error (string "Wrong number of args (" n ") passed to fn"))))))
|
||||
(error (string "Wrong number of args (" n ") passed to: "
|
||||
(or fn-name "fn")))))))
|
||||
self)
|
||||
# Single-arity: (fn* [args] body...)
|
||||
(let [args-form (in form 1)
|
||||
|
|
@ -1757,7 +1758,16 @@
|
|||
(set result (eval-form ctx fn-bindings body-form)))
|
||||
(ctx-set-current-ns ctx saved-ns)
|
||||
result))
|
||||
(def n-fixed (length fixed-pats))
|
||||
(set self (fn [& fn-args]
|
||||
# ArityException semantics (jolt-6xn): a fixed arity takes
|
||||
# exactly its params, a variadic one at least its fixed params.
|
||||
# The compiled path enforces this natively (janet fn arity);
|
||||
# this keeps the interpreter oracle in agreement.
|
||||
(def n (length fn-args))
|
||||
(when (if rest-pat (< n n-fixed) (not= n n-fixed))
|
||||
(error (string "Wrong number of args (" n ") passed to: "
|
||||
(or fn-name "fn"))))
|
||||
(var fn-bindings @{})
|
||||
(table/setproto fn-bindings bindings)
|
||||
(var i 0)
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue