ReviewOS

zig-utils/zig-js

Compiler: lower strict arguments objects into VM frames

#728
Closed chris opened this 9 days ago ·
9 days ago

Parents: #465, #498 Related: #555

Problem

The parser already records exact uses_arguments ownership across ordinary functions and nested arrows, and the runtime already constructs spec-shaped strict arguments exotic objects. Plain-function admission nevertheless rejects every arguments-using function before compiler admission, while Compiler.emitLoad rejects the identifier in every frame scope. Strict ordinary functions therefore remain on the tree walker despite needing no mapped parameter aliasing.

Scope

  • Give strict non-arrow function chunks one explicit frame slot for their own unmapped arguments object when the parser marks it observable.
  • Materialize that object during activation setup with exact length, indexed values, iterator, poison-pill callee, realm prototype, and moving-GC roots.
  • Let nested arrows resolve the owning ordinary function slot and let nested strict ordinary functions shadow it with their own object.
  • Preserve parameter-first frame layout, debugger local names, recursion, constructors, methods, tail calls, activation recycling, side exits, and JIT fail-closed behavior.
  • Keep direct eval and sloppy mapped arguments behind their existing exact barriers until frame-visible dynamic environments and parameter aliasing are implemented.

No-workaround rules

  • No Array substitute, copied plain object, eager object for functions that cannot observe arguments, disabled mapping, lost poison pill, environment-name fallback, source rewriting, or tree-walker callback from bytecode.
  • No stacks, queues, jobs, Promise, Worker, or Map/Set iterator changes.

Acceptance

  • Compiler tests prove a dedicated local slot and native load for strict function, method, constructor, nested-arrow, and nested-owner shapes.
  • Tree-walker and required-bytecode differentials cover indexing, length, iteration, callee poisoning, mutation isolation, nested ownership, recursion, this, and RHS/throw identity.
  • Moving-GC and focused TSan coverage pass with no leaks or races.
  • Full units and exact relevant Test262 arguments/function subtrees have nonzero parent to candidate accounting with zero regressions.
  • Commit, issue, and parent roadmaps carry exact links and measured evidence.
9 days ago

Landed in feat(compiler): lower strict arguments objects (#728).

Strict ordinary functions now materialize their unmapped arguments exotic object in a precise VM frame slot. Nested arrows capture the owner slot, nested ordinary functions shadow it, activation recycling and moving-GC rooting stay exact, and both native tiers fail closed. The implementation also separates direct-eval ownership from explicit arguments references, preserving the dynamic-environment barrier while avoiding false arguments slots.

Measured evidence:

  • final units: 1,856 passed, 1 skipped, 0 failed, 0 leaked across 10 shards
  • focused TSan: 1 passed, 0 failed, 0 leaked
  • frontend: 13/13 passed
  • docs: 50 pages built and manifest-verified
  • exact Test262 parent -> candidate: 1,323 -> 1,323 passes, 0 failures, byte-identical output, 0 regressions across arguments-object, class arguments, function expressions, function statements, and arrow functions

This advances #465 and #498; sloppy mapped arguments and direct eval retain their exact barriers.

9 days ago

Follow-on #729 now tracks the intentionally remaining sloppy mapped-arguments boundary. #728 stays complete for strict unmapped objects; #729 owns live parameter aliases, duplicate formals, severing, escaped frame-slot lifetime, and GC/no-GIL proof without weakening this issue's strict-only claim.

9 days ago

Follow-up #729 landed in 26b8c248. The activation-slot model introduced here now covers sloppy mapped arguments via object-owned atomic cells; strict unmapped behavior remains unchanged, and both native tiers continue to reject activation-initialized arguments slots.

Sign in to comment on this issue.