Files
AILang/crates/ailang-check
Brummel b11a6d9883 fix(mono): thread declared return type into mono synth re-entry
GREEN for the series-step-1 base-tier RED (e035eff). A polymorphic fn
that allocates `(new RawBuf n)` with no explicit type-arg — element var
solved purely from the enclosing ctor-field type `(con RawBuf a)` —
checked clean but failed `ail build --alloc=rc` with the unregistered
`RawBuf_new__Unit`.

Root cause (verified, and it diverges from the handoff's diagnosis
pointer): the no-type-arg `(new RawBuf n)` desugars to an ordinary
`(app RawBuf.new n)` free-fn call, NOT a surviving `Term::New` — so the
`lower_to_mir.rs:501 elem: None` site the pointer named is never reached
for this case. The real gap is in mono's synth re-entry.
`RawBuf.new : forall a. (Int) -> RawBuf a` has a result-only forall var
`a` that no argument pins. `collect_mono_targets` and
`collect_residuals_ordered` re-`synth` the body but never unified the
synthesised body type against the declared return type, so `a`'s metavar
stayed unbound through the walk and the free-fn arm Unit-defaulted it.
This is the typed-MIR re-synth strictness family again: a mono synth
re-entry that did not replicate a step `check_fn` performs.

Fix (one file, mono.rs): both re-entries now call a shared
`unify_body_against_declared_ret` that mirrors `check_fn`'s closing
`unify(&ret_ty, &body_ty, …)` (lib.rs:2498), threading the return-type
solution into the same `subst` the FreeFnCall metas read. For
`mk : (Int) -> Box Float` this pins `a := Float` from the ctor-field
context `(con RawBuf a)`, so the buffer specialises to the registered
`RawBuf_new__Float`. Safe by construction: mono runs on already-checked
code, so this unify can only re-derive the solution check already
proved — it cannot introduce a new failure. The shared helper keeps the
two passes resolving identical `type_args`, so the minted symbol matches
the Phase-3 rewrite target.

Verification: full `cargo test --workspace` green (0 failed across all
suites); new pin green; `intercepts_bijection_with_intrinsic_markers`
green (no intercept/marker change — `RawBuf_new__Float` already
registered); `pre_desugar_validation.rs` untouched. Both CLAUDE.md
lockstep pairs intact. End-to-end: a polymorphic `Series a` over RawBuf
now builds and runs with the model-0007 `(new Series (con Float) n)`
caller surface — the precondition for Series as a pure library
extension.

refs #61
2026-06-02 12:44:51 +02:00
..