mirror of
https://github.com/vercel-labs/scriptc.git
synced 2026-11-09 10:22:28 +08:00
An owned local's or parameter's read in the last statement of its extent retained the value, and the scope released the binding's own reference later. When that statement reads the binding exactly once, outside any loop or try statement nested in it, assigns it nowhere and mentions no binding derived from it (which could borrow from the moved reference), the read now takes over the reference: it loads the slot and clears it, and the scope's NULL-tolerant release does nothing. The read node must occur once in the function, since lowering can share varRef nodes. Parameters also count locals rebound from them as derived, and bodies with walk borrows keep their parameters. (Ported from the unmerged rc-round3 branch and extended to parameters.) A parameter whose last use stores it (a field, record or element store, a record literal field, a push) now takes the owned convention instead of the borrowed one, unless it is only projected: `new Node(build(), build())` hands the temporaries straight into the fields instead of retaining a stored copy in the constructor and releasing the temporaries in the caller. Callers that still use their argument retain it, as for any owned parameter. Executed RC operations (with the private-array change): alloc-trees 8.10M -> 1.83M, optional-fields 18.76M -> 2.68M, region-builds 7.94M -> 5.89M, cyclic-graphs 6.93M -> 5.28M, intern-table-map 17.9M -> 16.0M; no workload increased. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>