S0 of the ratified Fork C plan (zero-legacy name-resolution redesign, S0→S6).
Pure setup/documentation: NO production code change, NO behavior change.
Single-author output byte-identical to wt-stdlib-base by construction.
Deliverables under docs/fork-c/ (docs/, not current/, because current/ is
gitignored and the contract must be committed):
S0.1 — byte-baseline + commit-discipline: the committed examples/expected/*
snapshots are the single-author byte-identity reference; the zero-diff repro is
`zig build && zig build test && bash tests/run_examples.sh`. Resolver-target set
explicitly excluded + listed. Commit-classification rule: mirror | consumer-cutover | deletion.
S0.2 — E6b disposition + two-corpus partition: transitional E6b src NOT merged
(grep-clean: no resolveRegistrationSigTypeInSource / sig_registration_mode /
e6br_gate.test.zig on baseline). Harvested 0811–0829 trees + goldens (never the
src), empirically partitioned by running each through the base compiler vs the
E6b target:
- baseline-green (mirror-equivalence): 0795–0798 (merged) + 0823, 0828 — given
examples/expected/ markers, locked into the S0 baseline.
- resolver-target (known-wrong old behavior): 0811–0822, 0824–0827, 0829 + the
re-filed E6BR-5 nested-pattern regression — a listed xfail harness under
tests/resolver-target/ (manifest + TARGET goldens, NO active marker), flips
active+green at S3.9. 0811/0829 noted as old-selector-wrong on the E6b-unmerged
base; E6BR-5 subsumed by the whole-AST resolver, NOT an E6b attempt-6.
S0.3 — A–E6 reuse/delete ledger: every load-bearing A–E6 artifact mapped REUSED
(Fork C home) or DELETED/TRANSITIONAL (S3/S6 phase); E6c/d/e dropped, F/H/I/K
absorbed/superseded.
Gate over the baseline-green corpus: zig build + zig build test (LSP corpus sweep
574 files, no crash) + bash tests/run_examples.sh (540 passed, 0 failed) all exit 0.
73 lines
7.3 KiB
Markdown
73 lines
7.3 KiB
Markdown
# S0.3 — A–E6 reuse / delete ledger
|
||
|
||
Authority: `runs/stdlib/design/fork-c-deepdive/reconciled.md` (§6 roadmap + per-phase
|
||
deletion lists, §8 fold-in) + `runs/stdlib/design/migration.md` ("what happens to
|
||
already-merged A–E6 work") + `planspec-r3.json` (S0.3). Base: `wt-stdlib-base @
|
||
1f75528`. Symbol/file refs are grounded against the base tree. This is documentation
|
||
only — no code change.
|
||
|
||
This ledger is the contract the later phases execute against: every load-bearing A–E6
|
||
artifact is mapped to **REUSED** (with its Fork C home) or **DELETED/TRANSITIONAL**
|
||
(with the S3/S6 phase that removes it). A–E6a stays merged; the transitional E6b src
|
||
is never merged (see `S0.2-…`).
|
||
|
||
## A. REUSED — A–E6 work that becomes Fork C infrastructure
|
||
|
||
| A–E6 artifact (base location) | Fork C home | phase |
|
||
|---|---|---|
|
||
| **Phase A import facts** — `RawDeclRef` / `RawAuthor` / `ModuleDecls` / `NamespaceEdges` (`src/imports.zig`), built in `resolveImports` (`core.zig`) | **seed `DeclId` construction** — `DeclTable` keys every `RawDeclRef` into a stable `DeclId` (source + name + AST ptr + `DeclKind`); namespace members get ids | S1 |
|
||
| **Phase B visibility** — `collectVisibleAuthors` / `collectNamespaceAuthors` (`src/ir/resolver.zig`), "the one graph iterator" over `flat_import_graph`/`namespace_edges` | **resolver internals** — become the resolver's visibility walk, with own-wins / single-flat-visible / ≥2-ambiguous **verdicts above them**, producing `ResolvedRef` | S2 |
|
||
| **Phase C callable selection** | **`ResolvedRef.function` / `.type_function`** keyed by `DeclId` | S2 (select) → S3 (consume) |
|
||
| **Phase D nominal identity** — `internNominal` / `updatePreservingKey` + the **`nominal_id == 0 ≡ structural intern` ordinal-0 byte-identity rule** (`src/ir/types.zig`, `lower.zig`) | **reused inside materialization** — `materializeType(ResolvedTypeNode)` interns in old scan order with ordinal 0 for non-colliding decls ⇒ byte-identical single-author output | S3 (+ green-lock every phase) |
|
||
| **E-series selection rules** — own-wins / not-visible / ambiguity / direct-flat (the E1–E6a behaviors) | **resolver behavior + regression tests** (the baseline-green corpus is the mirror oracle) | S2 behavior; regressions locked S0 |
|
||
| **CP rule** — body-author == layout-author | **keyed by `InstantiationId{template_decl, resolved_args}`** in the fact store | S4 |
|
||
| **E6BR routed-signature cases** (the E6BR-1…4 behavioral cells) | **resolver-signature regressions** — the resolver walks every signature reference position; cases live in the resolver-target corpus, flip at S3.9 | S3.9 |
|
||
| **FFI `foreign_class_map` consumers + 116-class corpus** | parallel `DeclId`s land at S1 (map still the consumer); foreign classes keyed by `DeclId` at S4; runtime names stay **payload strings on facts** | S1 → S4 |
|
||
|
||
## B. DELETED / TRANSITIONAL — removed in S3/S6
|
||
|
||
| artifact (base location) | why it goes | removal phase |
|
||
|---|---|---|
|
||
| **Stateless `type_bridge` leaves** — `resolveAstType` / `resolveTypeName` / `resolveInline{Enum,Union,Struct,ErrorSet}` / `resolveParameterizedType` / `resolveErrorType` (`src/ir/type_bridge.zig`); the whole `type_bridge.zig` (E6b renamed the entry leaf `resolveAstTypeNoAuthorSelection`) | no-author `findByName` leaves — replaced by `materializeType(ResolvedTypeNode)` which cannot take a name | selectors S3; file S6 |
|
||
| **`TypeResolver.resolveName` / `resolveNamed`** (`src/ir/type_resolver.zig`) (E6b: `resolveNamedGlobalNoAuthorSelection`) | name→global resolution; superseded by the resolver | S3 (name-selection) / S6 (`resolveName*`) |
|
||
| **Old name selectors** — `selectNominalLeaf`, `resolveNominalLeaf`, `moduleTypeAuthor`, `namedRefTid`, `flatTypeAuthorCount`, `nameAuthoredAsTypeAnywhere`, `selectModuleConst` (+ const-source pins), `selectGenericStructHead`, `headTypeGate`, `headFnLeak`, `flatFnAuthor*`, the name-selection in `resolveTypeCallWithBindings`/`resolveParameterizedWithBindings` (`src/ir/lower.zig`) | the duality leak — replaced by `ResolvedRef`/`ResolvedTypeNode` consumed in lowering | S3 |
|
||
| **`*_by_source` mirrors + source pins** (`src/ir/program_index.zig`) + their writers + the `lower.zig` unified writers | dual-write mirrors of the global maps — superseded by the `DeclId`-keyed fact store | S4 |
|
||
| **`type_decl_tids`** (`src/ir/types.zig`, `lower.zig`) | name→TypeId mirror — superseded by `DeclId` facts | S4/S6 |
|
||
| **`ShadowTypeDecl` / shadow-slot reservation helpers** (`src/ir/lower.zig`) + lower-side nominal selectors | shadow reservation is a name-keyed pre-pass artifact — subsumed by `DeclId` pre-pass | S3/S4 |
|
||
| **`TypeTable.findByName` / `findUniqueByName`** (`src/ir/types.zig`) | the global name table — deleted **last** (after the ~15 category-(b) stdlib lookups are re-homed to resolved-once `DeclId`s, per the §6 critical ordering constraint) | S6 |
|
||
| **the type-reference choke-point + route-all engine** (`resolveRegistrationSigTypeInSource` / `sig_registration_mode`) | **transitional E6b src — never merged**; destined for deletion under Fork C | S3/S6 (already off-baseline) |
|
||
| **the grep gate `e6br_gate.test.zig`** (+ its `ir.zig` import) | **transitional E6b src — never merged**; unnecessary once the leaf it polices is gone | S6 (already off-baseline) |
|
||
| **the S2→S3 assert-only Debug mirror** | a test oracle, not a code path — must be deleted in the **same S3.10 commit** that removes the last old selector | S3.10 |
|
||
|
||
## C. Dropped / absorbed / superseded plan items
|
||
|
||
- **E6c / E6d / E6e** (protocol / foreign / type-fn per-kind identity): **DROPPED as
|
||
steps.** They become resolver behavior + regression tests — a whole-AST resolver
|
||
walks every reference position (annotation, `size_of`, dispatch head, `Self`,
|
||
vtable), closing the protocol surface the per-kind patch structurally could not
|
||
(reconciled §4 T4).
|
||
- **F** (namespace resolver + 0104): **ABSORBED** into S2 as resolver internals
|
||
(`namespace_edges` → `ResolvedRef.namespace` / member).
|
||
- **H** (constructor heads): **ABSORBED** into S3 `materializeType` over resolved
|
||
generic/protocol/type-fn heads.
|
||
- **I** (protocol + foreign selection, loud-on-≥2): **ABSORBED** into S2 selection + S4
|
||
`DeclId` facts.
|
||
- **K** (delete dead readers): **SUPERSEDED** by the S4 `DeclId`-keyed fact store + the
|
||
S6 deletions — "just delete the maps" is upgraded to "replace with `DeclId` facts."
|
||
- **the per-kind taxonomy**: **REIFIED** as the `ResolvedRef` union itself; the
|
||
exhaustive `switch` is the live taxonomy check (the grep gate is gone because the leaf
|
||
it policed no longer exists).
|
||
|
||
## D. Acceptance (S0.3) — self-check
|
||
|
||
- ✅ Every load-bearing A–E6 artifact mapped to REUSED (with Fork C home) or
|
||
DELETED/TRANSITIONAL (with the S3/S6 phase that removes it) — tables A & B; covers
|
||
Phase A import facts → `DeclId` seed; B `collectVisibleAuthors` → resolver internals;
|
||
C callable selection → `ResolvedRef.function/type_function`; D `internNominal` +
|
||
ordinal-0 byte-identity → materialization; E-series rules → resolver behavior +
|
||
regressions; CP → `InstantiationId`; the stateless `type_bridge`/`type_resolver`
|
||
leaves, `*_by_source` mirrors + source pins, `type_decl_tids`/shadow helpers +
|
||
lower-side selectors, the choke-point + route-all + grep gate → S3/S6 deletion.
|
||
- ✅ States E6c/d/e dropped and F/H/I/K absorbed/superseded — table C.
|
||
- ✅ No code change.
|