plan(reify): re-architect onto declare/define as the only compiler primitive

User-directed redirection. The compiler should expose ONLY declare() and
define(handle, info) as comptime type-table primitives; reify / make_enum /
RecvResult / TryResult all become plain sx in meta.sx (reify ==
{ h := declare(); define(h, info); return h; }). The AST-walking reifyType
and every syntactic reify recognition (decl.zig E :: reify hook, generic.zig
findReturnReifyCall routing) are to be DELETED, replaced by generic comptime
evaluation of a Type-returning expression.

PLAN-REIFY gains a RE-ARCHITECTURE section: the irreducible compiler floor
(declare = empty nominal slot; define = decode a TypeInfo VALUE + fill via
updatePreservingKey; comptime-eval a Type-returning ::-RHS/type-fn body),
the resolved naming/identity story (declare mints anonymous, the binding site
names it; identity via the existing instantiation cache), and an F1-F5 phase
table that re-greens 0614/0615/0617 on the floor.

No code change in this commit — the in-session Phase 3.2 attempt (make_enum +
eval-decode reader) was reverted (reset to 9306ad5) so the floor is built
first. Checkpoint records the revert + sets next step = F1.
This commit is contained in:
agra
2026-06-16 20:08:17 +03:00
parent 9306ad570d
commit e5d1d0de39
2 changed files with 82 additions and 17 deletions

View File

@@ -55,7 +55,57 @@ Examples: `06xx` (comptime, deterministic), `11xx` (diagnostics for loud failure
---
## Phases
## RE-ARCHITECTURE (user-directed, 2026-06-16) — `declare`/`define` are the ONLY compiler primitives
**Decision:** the compiler must expose **only** the two comptime type-table
primitives `declare()` and `define(handle, info)`. **`reify`, `make_enum`,
`RecvResult`, `TryResult` all become plain sx** in `meta.sx``reify` is literally
`{ h := declare(); define(h, info); return h; }`. The AST-walking `reifyType` and
every *syntactic* recognition of `reify` (`decl.zig`'s `E :: reify(...)` hook,
`generic.zig`'s `findReturnReifyCall` type-fn routing) are **deleted** — replaced by
generic **comptime evaluation of a Type-returning expression**.
This supersedes the old builtin-`reify` approach of Phases 0/1/3 below (which are
GREEN today but compiler-coupled). Phase 3.2 (`make_enum` + the eval-decode reader)
was implemented then **reverted** (commit reset to 9306ad5) to rebuild on this floor.
### The irreducible compiler floor (cannot be sx — mints `TypeId`s / evaluates types)
1. **`declare() -> Type`** — intern a fresh EMPTY forward nominal slot (unique
`nominal_id`, anonymous name), return it as a first-class `Type` value. Reuses the
`reserveShadowEnumSlot` shape (`nominal.zig:98`).
2. **`define(handle: Type, info: TypeInfo)`** — decode the `TypeInfo` **value** (the
reverted `reifyEnumFromVariantsValue` decode logic moves here: interp `Value`
names + payload `Type`-tags → `tagged_union` byte-identical to `buildEnumInfo`),
fill the slot via `updatePreservingKey` (`types.zig:442`). Loud on bad input.
3. **Comptime-evaluate a Type-returning `::` RHS / type-fn body** through the
interpreter to a `type_tag`, then bind / rename / identity-cache. This is the new
general capability that REPLACES the `reify`-name pattern-matching.
### Naming + identity (resolved)
- `declare()` mints ANONYMOUS; the **binding site** names it: a direct `X :: <expr>`
renames the handle to `X`; a type-fn instantiation renames to the mangled name.
- **Identity (Contract 1)** still rides the existing `instantiateTypeFunction`
mangled-name cache — `RecvResult(i64)` memoizes, body (hence `declare`) runs once.
### Floor phases (REPLACES old Phases 0/1/3; re-greens 0614/0615/0617)
| Step | Commit | What | Files |
|---|---|---|---|
| F1.0 | xfail | `examples/06xx` mints a **recursive** enum directly: `List :: declare();` + `define(List, .enum(.{ variants = .[ … payload = *List … ] }))`; construct + match a cons/nil list. Red (declare/define undefined). | `examples/06xx-*` |
| F1.1 | green | `declare`/`define` as comptime builtins + the `X :: declare()` decl hook + scan-time `define(...)` side-effect + the value-decode (from the reverted 3.2). Self-ref works because the handle predates the body. | `src/ir/lower/{decl,nominal}.zig`, `src/ir/interp.zig`, `meta.sx` |
| F2.0 | xfail | Reimplement `reify` in `meta.sx` as `declare`+`define`+return; switch `E :: reify(...)` to the **general comptime-Type-expr** decl path; delete the `E :: reify` AST special-case + `reifyType` literal walk. Red until the general path lands. | `meta.sx`, `src/ir/lower/decl.zig` |
| F2.1 | green | General comptime evaluation of a Type-returning `::` RHS (run interp → `type_tag` → rename/bind). `examples/0614` green again with ZERO `reify` knowledge in the compiler. | `src/ir/lower/decl.zig`, `src/ir/interp.zig` |
| F3.0 | xfail | Delete `findReturnReifyCall` routing; make `instantiateTypeFunction` run a Type-returning body through the interp generally. Red for 0615/0617 until it lands. | `src/ir/lower/generic.zig` |
| F3.1 | green | General type-fn body comptime-eval + rename to mangled name + identity cache. `examples/0615` (cross-site identity) + `0617` (RecvResult/TryResult) green on the floor. | `src/ir/lower/generic.zig` |
| F4 | xfail→green | `make_enum(variants)` in `meta.sx` — now TRIVIAL (reify is sx, type-fns eval generally). New `examples/06xx` (inline + computed variants). | `meta.sx`, `examples/06xx-*` |
| F5 | xfail→green | Validation + loud diagnostics: dup variant names, by-VALUE self-ref (`payload = List` not `*List` → "infinite size"), a `declare()` never `define()`d (hard error at end of comptime). | `src/ir/interp.zig` / `src/ir/types.zig`, `examples/11xx-*` |
> `type_info($T) -> TypeInfo` (old Phase 2.2 — reflect a type INTO a value) is
> orthogonal to this floor and still pending; it CONSTRUCTS a `TypeInfo` value
> (inverse of `define`'s decode). Round-trips through the floor once it lands.
---
## (SUPERSEDED by the re-architecture above) Original builtin-`reify` phases
### Phase 0 — `reify` of a flat enum (the core)
| Step | Commit | What | Files |