Skip to content

Floor C1: fixture compiles render only the modules their reader reads - #13037

Merged
gunbai-bot[bot] merged 4 commits into
mainfrom
session/merry-koi-266
Oct 3, 2026
Merged

gunbai-bot[bot] merged 4 commits into
mainfrom
session/merry-koi-266

Conversation

@gunbai-bot

@gunbai-bot gunbai-bot Bot commented Oct 3, 2026

Copy link
Copy Markdown
Contributor

Floor repair C1 from #13030 (docs/plans/floor-time-attribution-2026-10-02.md), redirected by sharp-raven-357's ruling (option A).

Derivation (DESIGN §6b)

The brief proposed compiling each fixture against the prepared closure. Re-deriving the chain did not support that:

  • v1's compile (compile_to_resolved_with_options → emit_resolved_for_target) has no add-one-module seam.
  • The prepared closure is not the closure a fixture would build. Preparation does not arm with_type_ref_hit_ne_bind_measure, while the census does. And the prepared pool is the gate closure, not the fixture's own imports.

The earliest unjustified link is later: emit renders every closure module (RenderEveryModule), but the emit check reads one file, and the census reads only diagnostics. That is redundant demand (DESIGN §2), and the repair deletes it rather than caching it. Rendering through RenderSelectedMirrors is already a production route (required_regen_host).

Change

  • compile_fixture_rendering_only_what_is_read is now the single route for both instruments. Its render set comes from fixture_render_selection, which derives it from the compiled graph:

    • the modules spanned in FIXTURE_SOURCE_PATH;
    • plus, for the emit check, the closure module whose emitted path is the read path.

    The selection therefore cannot name a module outside the closure.

  • Refusals are typed (FixtureRenderRefusal):

    • NoFixtureModuleInClosure;
    • ReadPathNotEmitted: a clean compile that did not produce the path the check reads. Before this change, that case passed as a silent false.

    They surface as InterpError::FixtureRenderRefused / WitnessRuntimeCause::FixtureRenderRefused. Nothing widens to a full render.

  • The census still renders the fixture's modules. It reads their per-module emit refusals, so rendering nothing would drop them. Whole-graph emit checks (collisions, anonymous records, effectful recursion) run before selection and are unchanged.

  • Stated narrowing: a corpus module inside a fixture's closure is no longer rendered, so its own emit refusal no longer reaches the census rows or the emit check's hard gate. Corpus emission is the subject of the generated-artifact lanes.

Enrolled control (requirement 2; DESIGN §3 pairing, §4b(4))

render_selection_agreement_receipt runs over RENDER_SELECTION_AGREEMENT_FIXTURES on every required floor run, right after the module-path index warm. For each fixture it renders full and selected at one revision and requires three things: equal read-path bytes, equal diagnostics, and a strictly smaller selected file set exactly when the fixture says it narrows.

On mismatch it returns REQUIRED-FLOOR REFUSAL cause=RenderSelectionDisagreement receipt=… fixture=… read_path=…, naming the first differing byte offset or diagnostic index. It refuses the floor; it never warns. It prints [floor-receipt] receipt=render-selection-agreement … lines.

The fixtures:

  • reads_fixture_module and reads_imported_module: these import the leaf modules std.magnitude and std.error_primitives, and the read-path one reads src/std_magnitude.rs.
  • import_free_has_nothing_to_narrow: the red for the route.

Measured cost, by hand on a remote runner (index already warm): 18ms for all three fixtures (10/5/1ms).

Structural prediction (stated before the confirming run)

  • What collapses: the render work per fixture compile. In the probe below, a 5-module closure went from a full emit of 4,845ms to a selected emit of 24ms, with resolve at 179ms. On the floor, the ~539s of compile.emit inside the 14 v1-checker modules' fill_cpu_ms should shrink to the fixture module's own rendering.
  • What remains: frontend, resolve and reconcile over each fixture's closure (the remainder of the ~667s). That stays because the closure compile is the instrument's subject.
  • What stays equal: the same claims run, with the same verdicts; and the receipt holds.
  • What would falsify this:
    • a verdict flip;
    • a fixture-render-refused cause appearing on a claim, which would mean a witness was passing on an absent read path;
    • claim-evaluation-fold CPU not falling by roughly the emit share.

Evidence

  • Probe (fixture_render_selection_probe, run by hand with --ignored): bytes equal and diagnostics equal on the sample fixture; full emit 4,845ms against selected emit 24ms.
  • Clippy: cargo clippy --all-targets -D warnings is clean, run remotely.
  • Before/after floor: pending. Before = run 37070592712 at d8eebae; after = this PR's floor job. The comparison uses the floor's own carriers (floor-seam-cpu, [floor-shared-fill]) and will be added here. Option C, reading verdicts at claim grain from those two runs, is also pending.

Seed growth is recorded in gunbc.fixture_render_selection_seed_growth. No budget is raised.

🤖 Generated with Claude Code

compile_dag_rust_emit_check and compile_dag_diagnostic_census compiled a
fixture's live import closure and then rendered Rust for every module of it,
though the emit check reads one file and the census reads diagnostics (among
them the fixture module's own emit refusals). The render set is now derived
from the compiled graph: the fixture's own modules plus the closure module
whose emitted path is the read path. No fixture module, or a clean compile
that emitted no file at the read path, refuses with a typed
FixtureRenderRefusal; nothing falls back to rendering every module.

render_selection_agreement_receipt, run by the required floor on every run
over RENDER_SELECTION_AGREEMENT_FIXTURES, is the enrolled control: it renders
full and selected at the same revision and refuses the floor when the read
bytes, the diagnostics, or the narrowing route disagree. Its import-free
fixture is the red for the route.

Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
@gunbai-bot

gunbai-bot Bot commented Oct 3, 2026

Copy link
Copy Markdown
Contributor Author

Before/after evidence at one revision

Both runs are at main e3d6a814b6, with this PR's commit the only difference:

  • Before: the floor dispatched on session/merry-koi-266-baseline-e3d6, which points at e3d6a814b6 exactly: run 37081735809, floor job 111083532270.
  • After: this PR's floor on refs/pull/13037/merge, whose parents are e3d6a814b6 and f4305a6c41: run 37081593594, floor job 111083099479.

Read from the floor's own carriers ([floor-seam-cpu], [floor-shared-fill], the site-projection phase line, claims_failed):

before after
planned claims 664 664
claims_failed 0 0
claims with a [floor-shared-fill] line (same set in both) 197 197
claim-evaluation-fold thread CPU 756.5s 157.1s
fill CPU over those 197 claims 710.3s 111.4s
marginal CPU over those 197 claims 1.25s 1.21s
floor job wall time 39m47s 32m11s
[floor-receipt] render-selection-agreement (not present) held, 3 fixtures, 40ms CPU

Top modules by fill, before → after:

  • declared_type_inhabitance_direct_call_witness: 219.5s → 28.2s
  • infer_function_value_argument_arrow_witness_test: 113.1s → 9.0s
  • declared_type_expected_type_path_witness: 90.1s → 6.9s
  • infer_callable_type_argument_witness_test: 60.0s → 3.4s
  • infer_nullary_local_callable_witness_test: 50.6s → 2.1s

Prediction check

  • Held: the collapse. Fill fell by about 599s, roughly the predicted ~539s emit share plus the emit inside the census fills. Marginal CPU did not move.
  • Held: semantic outputs equal. The same 664 claims ran, there were no failures in either run, and no fixture-render-refused cause appeared. So no witness was relying on an absent read path.
  • Residue, as predicted: frontend, resolve and reconcile over each fixture closure, about 111s across the 197 claims. A few modules barely moved (match_exhaustiveness_coproduct_witness 21.9s → 19.8s, namespace_step0_subject_collector_witness 12.1s → 12.1s). Those are compile-dominated, not emit-dominated.
  • Not achieved: the brief's original postcondition, "fill collapses to the fixture module's own compile". The closure compile remains, per the ruling, and is not filed as a follow-up.

Verdict grain (option C). The floor logs refusals per claim and aggregates passes, so equality is read as: identical planned set (664), the same 197 fill claims, claims_failed=0 on both runs, and no new runtime cause.

… (review 74373)

Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
@gunbai-bot

gunbai-bot Bot commented Oct 3, 2026

Copy link
Copy Markdown
Contributor Author

Review 74373: fixed in a489ddb. FixtureRenderRefused and its two doc lines now sit above FillBudgetExceeded's doc block, so each variant carries only its own doc. Variant order is unchanged, so the derived Ord is unchanged. CI and re-review are pending on that head. — sent from merry-koi-266

@gunbai-bot
gunbai-bot Bot added this pull request to the merge queue Oct 3, 2026
@github-merge-queue
github-merge-queue Bot removed this pull request from the merge queue due to failed status checks Oct 3, 2026
@gunbai-bot
gunbai-bot Bot added this pull request to the merge queue Oct 3, 2026
@github-merge-queue
github-merge-queue Bot removed this pull request from the merge queue due to failed status checks Oct 3, 2026
@gunbai-bot

gunbai-bot Bot commented Oct 3, 2026

Copy link
Copy Markdown
Contributor Author

Correction to my evidence comment above. "The same 664 claims ran" overstates what I checked. Both runs report claims=664 on the site-projection line, and the 197 claims that carry [floor-shared-fill] rows are set-equal across the two runs. That is the population the fill and fold figures are computed over. I did not intersect the full 664 claim ids. Neither run had a failed claim, so any non-fill claim that was planned in only one run passed there, but identity of the full planned set is not established. — sent from merry-koi-266

gunbc-ci-auto-heal and others added 2 commits October 3, 2026 11:32
…me the read diagnostics

gunbc#12846 retired std.magnitude, so on main+#13037 the reads_fixture_module
fixture no longer compiled and render_selection_agreement_receipt refused the
merge-group floor (merge-group run 37094610954). The fixtures now import leaf modules
whose retirement would cascade visibly, the coupling is documented, and the
read-path refusal names the full render's diagnostics.

Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
@gunbai-bot
gunbai-bot Bot added this pull request to the merge queue Oct 3, 2026
Merged via the queue into main with commit 7938504 Oct 3, 2026
4 checks passed
@gunbai-bot
gunbai-bot Bot deleted the session/merry-koi-266 branch October 3, 2026 14:48
@briansrls
briansrls restored the session/merry-koi-266 branch October 3, 2026 14:49
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

0 participants