Skip to content

gate brake: see the host seam, and stop counting retirement rows as documentation - #1105

Merged
youknowone merged 2 commits into
mainfrom
ec-wiring
Aug 7, 2026
Merged

gate brake: see the host seam, and stop counting retirement rows as documentation#1105
youknowone merged 2 commits into
mainfrom
ec-wiring

Conversation

@youknowone

Copy link
Copy Markdown
Owner

Follow-up to #1102, which merged while these were being written. Nine review
findings, all verified against the source before fixing; none turned out to be a
false positive.

e720509 — the u32 SnapshotFrame carries no -1 sentinel

There are two SnapshotFrame types. resume::SnapshotFrame and
resumedata::RebuiltFrame are i32-typed and -1 is a real value there.
recorder::SnapshotFrame is u32, and #1102 — in a commit titled correct the
SnapshotFrame pc and py_pc comments
— carried the i32 twin's sentinel wording
across to it. u32::MAX occurred nowhere else in that file: no writer stamps it,
no reader tests it. The comment now says so and points at where the sentinel does
live. The two i32 comments are correct and are left alone.

20537f2 — two holes in the brake #1102 added

Both were reported by Codex, and both are the brake failing to brake.

The scanner could not see the host seam. gates_read_by recognised only
env::var / env::var_os. pyre-interpreter/src/importing.rs reads
PYRE_STDLIB through host_os::var and through host_seam::ops::getenv,
which takes a byte string — invisible to a std::env search. That gate stayed
covered only by accident, because pyre-wasm-runner also reads it through
env::var; a wasm- or sandbox-only gate would have had no such cover and would
have bypassed the brake entirely. READ_FORMS now carries all three forms and
the scan accepts an optional b prefix.

Retirement rows counted as documentation. gates_documented_in accepted a
PYRE_* token anywhere in gate-triage.md, including §1/§1b/§1c/§2/§3 — the
sections that record gates which are gone. PYRE_SINGLE_PASS has no read site
and is named only in §1c, so re-introducing a reader for it would have landed
green on the strength of its own retirement row, with neither its new polarity
nor a retirement plan written down. Tokens now count only from sections whose
## heading does not say retired/dead/not-gates.

That exclusion is itself load-bearing, so it is anchored on both sides rather
than trusted: PYRE_SINGLE_PASS must not count as documented, and PYRE_JD1
(live in §6a) must. A heading reword now fails loudly instead of silently
widening what the test accepts.

Re-measured with the widened forms: 105 distinct names — unchanged, because
both seam reads are PYRE_STDLIB128 (file, name) pairs, up one because the
two seam reads share a file, and 0 undocumented under the stricter rule.

What the re-measurement did to F5

F5 claimed 51 names left to retire. Once §6 landed and the live/history split was
made explicit, the real number is 3. Of the 8 live-named gates with no *.rs
reader:

  • one is the PYRE_FBW_* fragment in §1d's heading, not a gate;
  • four are live gates the brake cannot seePYRE_CHECK_PYPY3,
    PYRE_CHECK_PYTHON3, PYRE_SHARED_BUILD and PYRE_SYNTH_PYPY are read from
    check.py, check_synthetic.py, the CI workflows and
    scripts/llbc_extract.py. A *.rs census reads them as retire targets and
    they are not;
  • three (PYRE_FBW_REC_UNROLL, PYRE_FBW_VABLE_SCALAR_CA, PYRE_P2_DRAIN) are
    read from nothing in the tree and are the actual debt.

So the brake is Rust-only, and a Python- or YAML-only gate can still enter
undocumented — which is the hole §6 was written to close. That limitation is now
stated in the test's own module doc and tracked as F5, rather than left for the
next reader to rediscover. Widening the scan is deliberately not in this PR.

Also in the documents

  • The deletion policy now names Settled as its one exception, instead of
    contradicting the section two screens below it.
  • F4/F3 parallel-safety no longer claims "different crates" — both touch
    pyre-jit. They share no file and no symbol, which is the real reason.
  • The F4 census is described as built, not pending.
  • Code fences in both documents carry a language.

Verification

cargo test -p pyrex --test gate_triage_complete 2 passed / 0 failed ·
cargo test -p majit-metainterp clean · cargo fmt --all -- --check rc=0.

The brake run finished in 6s, so its binary was checked against the source rather
than trusted: compiled 22:02:29, source last edited 21:51:05.

The base moved by #999 and #1097 (43 .rs files) plus #1102's own squash. The
gate population is unchanged at 105 — none added, none removed — so the brake's
green is a real green and not a moved goalpost.

🤖 Generated with Claude Code

`SnapshotFrame::pc` and `py_pc` are `u32` in this type, so the `-1` the comment
paired them with is not a value either can hold. `u32::MAX` occurred nowhere else
in the file: no writer stamps it and no reader tests it. The sentinel belongs to
the `i32`-typed `resume::SnapshotFrame` and `resumedata::RebuiltFrame`, whose
comments are unchanged.

Assisted-by: Claude
…ge entries

Two holes in the brake added earlier on this branch.

`gates_read_by` recognised only `env::var`/`env::var_os`, so the host seam was
invisible: `importing.rs` reads `PYRE_STDLIB` through `host_os::var` and through
`host_seam::ops::getenv`, which takes a byte string. That gate stayed visible
only because `pyre-wasm-runner` reads it through `env::var` as well; a wasm- or
sandbox-only gate would have had no such cover. `READ_FORMS` now carries all
three forms and the scan accepts an optional `b` prefix.

`gates_documented_in` accepted a `PYRE_*` token anywhere in `gate-triage.md`,
including the retirement tables. `PYRE_SINGLE_PASS` has no read site and is named
only in §1c, so re-introducing a reader for it would have landed green on the
strength of its own retirement row. Tokens now count only from sections whose
`##` heading does not say retired/dead/not-gates, with an assertion on each side
of the split so that a heading reword fails loudly rather than silently widening
what the test accepts.

Re-measured with the widened forms: 105 distinct names, unchanged, because both
seam reads are `PYRE_STDLIB`; 128 (file, name) pairs, up one because the two seam
reads share a file; 0 undocumented under the stricter rule.

F5 is rewritten to what the re-measurement shows. Of the 8 live-named gates with
no `*.rs` reader, one is the `PYRE_FBW_*` fragment in §1d's heading and four
(`PYRE_CHECK_PYPY3`, `PYRE_CHECK_PYTHON3`, `PYRE_SHARED_BUILD`,
`PYRE_SYNTH_PYPY`) are read from `check.py`, `check_synthetic.py`, the CI
workflows and `scripts/llbc_extract.py` — live, and outside this Rust-only scan.
Three remain as retire targets. The scan's scope is now stated in the test's own
module doc.

Also in `rework.md`: the deletion policy names the Settled section as its one
exception; F4/F3 parallel-safety no longer claims different crates, since both
touch `pyre-jit`; and the F4 census is described as built rather than pending.
Code fences in both documents carry a language.

Assisted-by: Claude
@coderabbitai

coderabbitai Bot commented Aug 7, 2026

Copy link
Copy Markdown

Warning

Review limit reached

@youknowone, you've reached your PR review limit, so we couldn't start this review.

Next review available in: 4 minutes

You've used all free OSS reviews for now. Wait for the free limit to reset to keep reviewing this public repository.

How can I continue?

After more reviews become available, a review can be triggered using the @coderabbitai review command as a PR comment. Alternatively, push new commits to this PR.

To avoid repeated limits, reduce automatic review volume by pausing incremental auto-reviews earlier, using label-based review opt-in, excluding WIP or generated PR titles, or requesting reviews manually when the PR is ready. If your team needs uninterrupted high-volume reviews, an organization admin can enable usage-based reviews.

How do review limits work?

CodeRabbit enforces per-developer PR review limits for each organization. Most developers receive the normal plan review availability.

For paid Pro and Pro+ PR reviews, CodeRabbit uses adaptive limits for sustained high-volume activity. When a developer's recent PR review activity reaches the 95th percentile or higher among CodeRabbit users, additional reviews become available more gradually as earlier reviews age out of the rolling window.

Please refer docs for additional details.

Review details
⚙️ Run configuration

Configuration used: Organization UI

Review profile: ASSERTIVE

Plan: Pro Plus

Run ID: d89312dc-73b7-4eaf-9c7c-a09a420f9950

📥 Commits

Reviewing files that changed from the base of the PR and between d936eb4 and 20537f2.

📒 Files selected for processing (4)
  • majit/majit-metainterp/src/recorder.rs
  • pyre/gate-triage.md
  • pyre/pyrex/tests/gate_triage_complete.rs
  • pyre/rework.md

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands.

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: 20537f27bc

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

let lower = heading.to_ascii_lowercase();
// "retired", not "retire": §4 is a *live* section whose heading says when
// its gates will go ("retire when the epic closes").
lower.contains("retired") || lower.contains("dead") || lower.contains("not gates")

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Badge Exclude the §1d retirement section

The keyword-based classification treats §1d as live because its heading says “Parity verdicts” rather than “retired,” even though its table explicitly marks PYRE_FBW_VABLE_SCALAR_CA as retired. If a reader for that retired gate is reintroduced, gates_documented_in includes the historical row and the brake passes without requiring new polarity or retirement documentation—the exact failure this change is intended to prevent. Classify §1d as history explicitly rather than relying only on these heading keywords.

Useful? React with 👍 / 👎.

@github-actions

github-actions Bot commented Aug 7, 2026

Copy link
Copy Markdown

🤖 Codex parity review

Static analysis of this diff vs the local RPython/PyPy sources (commit 20537f2).
Updated: 2026-08-07T13:42:23.927Z

Files in the reviewed diff
majit/majit-metainterp/src/recorder.rs
pyre/gate-triage.md
pyre/pyrex/tests/gate_triage_complete.rs
pyre/rework.md

1. Regressions to PyPy parity introduced by this patch

None.

2. Other mismatches introduced by this patch

None.

3. Pre-existing mismatches (already present before this patch)

None.

4. Structural adaptations

  • majit/majit-metainterp/src/recorder.rs:95 ↔ rpython/jit/metainterp/opencoder.py:750: Pyre’s snapshot frame carries an additional forward Python-PC field (py_pc); RPython serializes only (jitcode_index, pc, boxes). This pre-existing metadata is required by Pyre’s resume/traceback reconstruction path and the patch only corrects its sentinel documentation; it makes no executable change.

@youknowone
youknowone merged commit c72fa84 into main Aug 7, 2026
13 of 17 checks passed
@youknowone
youknowone deleted the ec-wiring branch August 7, 2026 16:19
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.

1 participant