12 KiB
Source8 S2b independent source review
2026-09-13. Reviewer: Codex-956atf /root/source8_s2a_review. Reviewed frozen clean 6de3b53103 atop b2c970b467 in .local/as2-20260913. HEAD and clean status were checked before and after inspection. No source edits, compiler, executable tests, GUI, Gitea or integration actions were performed. This report is outside the reviewed worktree.
Outcome and finding
One confirmed authored-test defect blocks a passing thirteen-test S2b gate. No additional blocking lowerer correctness finding was identified by source inspection. Compilation and all executable behavior on this pin remain unverified.
F1 — Medium: repeated-call test uses unsupported block comments
crates/oa-core/src/language/analysis_source/lower/tests.rs:352 substitutes the source fragment:
@combine(a: @receive_time, /* first */ b: @dispatch_time)
+ @combine(/* second */ b: @dispatch_time, a: @receive_time)
The settled scanner recognizes only // comments. In unchanged language/raw_tokens.rs, the slash/star characters here are punctuation. At the first /*, the borrowed expression parser expects a call argument name and rejects the slash; the test helper unit() unwraps declaration parsing at lower/tests.rs:35, before lower() or the occurrence/scoped-ID assertions execute. This defect therefore prevents the test from exercising its intended discriminator.
Repair: use accepted line comments with actual newlines between argument tokens, retaining distinct first/second comments, four original label spans and reversed authored argument order in the second call. Do not expand the grammar to satisfy this fixture. Strengthen the fixture setup with a replacement assertion if useful, but keep its semantic assertions.
Falsifier: run language::analysis_source::lower::tests::call_sites_and_parameter_scopes_preserve_distinct_original_occurrences on this exact pin. Source inspection predicts a parsing unwrap failure before lowering. On the corrected pin it must reach and pass the four-label/two-call-site, caller/callee scope and whole-admission assertions. No executable failure is claimed by this review.
The finding was sent to root immediately when identified. Root owns any unfreeze/correction and its replacement source identity.
Inputs and scope
Read the accepted r2 design and S2 implementation contract from the earlier review context, the new .local/analysis-source8-s2b-handoff-20260913.md, all nine changed files and complete base diff, unchanged scanner/cursor/declaration interfaces, existing Project identity helpers, and relevant analysis admission/typechecking paths. The diff has 2,196 insertions/1 deletion, including939 lines of lowering and1,138 lines of tests/oracle plus four fixtures.
The accepted boundary is explicit: a caller supplies an ordinary Project skeleton and already parsed typed Units under one Budget. The lowerer returns additions and source metadata; the caller merges and runs the existing complete semantic admission. This is not a whole-document/include parser, writer, public source8 adapter or source update implementation. The production header/DeclKind, scanner, source_project, model, persistence, analysis semantics and source3 bridge files are unchanged. The new module remains behind the existing test-only staging registration.
Correctness paths inspected
- Complete collection precedes resolution.
Tables::ordinaryat lower.rs:183 includes project, actual element kind/layer, relations, diagrams, node placements, artifacts, traces and existing definitions.Tables::typedat:236 adds every typed header and calculation signature before the body-resolution loop inlower()at:269. IDs and aliases are globally unique, while parameter names/IDs are unique only inside one calculation. This supports later-unit references and forward calls without domain fallback. - Identity stability. Missing header/input IDs return a located stabilization-required error. Collection and lowering never generate UUIDs or mutate source syntax. Global ID and ParameterId equality does not create a collision; targets preserve their identity domain explicitly. Existing catalog calculation signatures are collected under their actual global owner.
- Required typed bodies. Definitions and analysis Elements are built directly from the settled parsed syntax into existing model types. Exact scale/offset/magnitudes are cloned without float/JSON conversion. Quantity dimensions use
Dimension::new; parameters keep their authored Vec order; case overrides are keyed by resolved property IDs with explicit duplicate protection. Headers retain name, alias and description; analysis parents are set to None after the declaration parser's root/parent restrictions. - Reference domains. Kind, unit, calculation, property and constraint references have explicit category predicates. Unknown aliases and wrong enum domains report the original reference token and caller file.
$nameuses only the owning calculation's signature; call labels use the called calculation's signature, while argument expressions retain caller scope. Missing arguments and semantic type compatibility deliberately remain in existing admission; unknown or duplicate labels do not silently fall through. - All thirteen Expr variants. The iterative Visit/Build machine at:733 traverses source children in their authored order, schedules Build after children and reconstructs the exact existing model variant. Binary sides, conditional branches, list order, sum operands and unary/power/as-kind children remain distinct. Calls zip their authored child sequence with the corresponding resolved ParameterIds, then construct the model map; reversed source label order does not exchange argument values. Logical shape is preserved without constant folding.
- Occurrence identity. Each expression receives a file/owner/field/site with a parent edge to a previously created site. Child edges identify list position, binary side, conditional branch and resolved call ParameterId rather than argument source order. Labels point to the call site; Target retains the callee and parameter owner. Override targets and their body expressions share
Field::Override(property_id). This supplies the requested qualified path identity with linear metadata, while original syntax retains literal/header/field spans. Arena positions are explicitly ephemeral. - Failure handling. Typed collection/resolution attaches the current Unit file; ordinary skeleton failures use None rather than inventing source offsets. Partial output is discarded on error. Lowering reads the inherited latched Budget state first. The private caller contract requires parsed/stabilized syntax from the same live Budget and abandonment of a failed candidate; this review does not treat deliberately forged private structs as public parser inputs.
Budget and admission boundaries
Budget::lowering_entries and lowering_occurrences at budget.rs:139/146 are read-only allocation ceilings, not new syntax/numeric event charges. Tables use one aggregate reservation count across ordinary globals, typed globals and scoped parameter rows. Output expression sites and occurrence vectors are aggregate across all declarations/units. File keys, active work/value buffers, call parameters, declaration parameters and override maps are checked against bounded phase sizes. Local buffers are recreated as temporary structures; they do not reset the inherited source or Exact budget.
The iterative work machine checks queued child slots before reserving the child vector and extending pending work. Output record counts are bounded by their earlier global-table collection; parameter totals by signature collection; expression output by its site reservation. Stored expressions are assumed to come from the depth/list-bounded syntax parser, so the later owned-tree cleanup remains bounded by that accepted input contract. No scanner, Exact parser or reference-admission recharge is invoked in the lowerer. Resource ceilings remain experimental pending root's measured transport gate; source-only inspection is not a peak-memory or timing measurement.
Two scope details must remain precise in downstream descriptions:
Resolver::subjectat lower.rs:428 establishes Element-versus-Relation identity but does not itself exclude analysis Elements or check layers. Existinganalysis/admission.rs:395–427rejects analysis subjects and wrong-layer subjects after the merge. This does not admit an invalid Project under the stated caller contract; descriptions of a fully valid architectural subject must refer to the combined admission result, not lower() alone.- Phase-bound errors are returned by read-only checks; they do not newly latch the parse Budget. This is consistent with discarding the candidate after a lowering failure and with tests of unchanged syntax work. It is not a reusable postfailure recovery protocol. S4 still must enforce its complete candidate lifetime and combine ordinary source/bundle limits before allocation.
The test helper admit() at lower/tests.rs:44 invokes the existing complete admission on the merged candidate. The lowerer does not call semantic admission itself. Ordinary fixture parsing follows its existing source7 path; it cannot establish exactly-once full source8 include parsing or admission. No separate static typechecker or alternate model semantics were introduced.
Oracle and test review
The OA fixture/oracle use the settled17 UUIDs (15 global records plus two scoped parameters) and fourteen explicit display names. oracle.rs constructs a real Project directly from model types, fixed dimensions, integer Exact values and an independent rational wire value. It does not parse expected source or call a writer. The SA twin flips a fixed global UUID bit while preserving scoped ParameterIds, constructs SA functions/layers directly and retains neutral definitions. Both hand-authored fixtures match that identity mapping; definition order is reversed relative to use to exercise forward resolution.
The principal test asserts all fourteen names before whole-Project comparison. Other authored tests independently specify thirteen real Expr results, distinct repeated-call site metadata, same-ID/different-scope behavior, duplicates/missing IDs, wrong-domain and unknown references with token spans, and semantic rejection after structural lowering. The semantic negative mutations target Boolean-versus-quantity type, calculation property capture, missing call argument, a layer mismatch and a self-dependency cycle. Existing admission owns those failures rather than a second checker.
The phase-budget test independently expects17 table entries, with16 rejection and17 success, and includes0 rejection. The depth/width test authors128 logical depth and1,024 list members and traverses the returned model; it is not public JSON-depth acceptance. Affine/list/optional/unbound tests construct additional valid model bodies and retain provenance. None has run on this reviewed pin. F1 currently prevents the repeated-call case from testing the properties its assertions describe.
Required next checkpoint
Repair only the unsupported comment fixture on a new immutable pin, then review the bounded diff and compile/list/run the thirteen new tests with retained affected tests and strict checks under root's lease. Preserve any actual failures and source identity. Full public source8 support remains blocked on the explicitly outstanding canonical writer, source index/update/stabilization and production parser/bundle composition, followed by the existing root-owned gates. The previous b2 executable passes do not validate6de3b5.
Bounded correction followup — 472fe7a
Subsequently verified clean 472fe7a433 atop6de3b5 and read its complete one-line diff plus updated handoff. Only the repeated-call test fixture changes: both unsupported block comments become // first / // second followed by actual newline characters in the constructed source. Distinct comments, four labels, reversed second-call argument order and every existing path/span/scoped-ID assertion are preserved. No production implementation or other test changes occur.
F1 resolved in source. No remaining blocking source-review finding was identified within the reviewed S2b scope. The thirteen new tests and combined strict/executable gates remain unrun by this reviewer; no execution pass is inferred. Original6de3b5 findings above remain historical evidence at their original pin.