Verification & evidence
On this page 5
This project's central rule is that a claim is only as good as the artifact
behind it. Conformance scores, ABI coverage, performance ratios, and platform
support are all backed by checked-in evidence under docs/.data/, regenerated by
tools, and gated in CI.
The evidence system
| Claim | Evidence artifact | Regenerated by |
|---|---|---|
| ECMAScript conformance | docs/.data/test262.json | bun run docs:data -- --from run.txt |
| WebAssembly conformance | per-profile inventories + wasm-conformance-matrix.json | home-tool run tools/wasm-conformance-matrix.ts |
| Thread corpus coverage | pr249-reference-inventory.json, pr249-execution-nogil.json | tools/threads-reference-audit.ts, tools/nogil-corpus-gate.ts |
| Public / private ABI | the JSON inventories under docs/c-api/, docs/objc-api/, docs/abi/ | the *-audit build steps |
| GC relocation coverage | gc-relocation-inventory.json | zig build gc-relocation-inventory-check |
| Performance | dated .md report plus its raw .tsv samples | benchmark-comparison, tools/benchmark-publication.ts |
| Platform support | docs/platforms.md | tools/platform-release-matrix.ts |
| Release readiness | release-compatibility-matrix.json | zig build release-compatibility-check |
Public prose in README.md and status pages is generated from these
artifacts between HTML markers. Editing the rendered text by hand is reverted
by the next generator run and can silently desync a release gate. See
the accuracy plan.
CI gate families
ci.yml
is authoritative. It runs on pull requests, pushes to main, manual dispatch,
and nightly. Each Required Check is its own matrix leg with fail-fast: false, so an unrelated failure cannot mask the threading gates.
- Unit suite, sharded — and the same suite under ThreadSanitizer.
- Thread corpus, sharded in serialized mode, plus a no-GIL witness case and an execution-inventory witness.
- No-GIL corpus gates — a TSan sweep requiring zero engine-state races, and a functional gate against the published baseline, in both Debug and ReleaseSafe.
threadfuzzacross six profiles (default, amplified, broad, mid-GC, lifecycle, verify) plus TSan variants. Seeded, so these are deterministic gates rather than flaky stress.- WebAssembly smokes across ten pinned upstream corpora, with converter binaries pinned by commit and SHA-256.
- ABI boundary fixtures across Debug / ReleaseSafe / TSan, plus the audits.
test262-parallel— parallel execution introduces no new failures.- Docs —
zig build docs-link-checkresolves every internal link and sidebar entry, thenbun run docs:buildmust succeed. The link check is separate because bunpress renders a link to a missing page without complaint.
A manual-only performance workflow runs the macOS/JSC matrix and retains raw samples plus a rendered report as a 90-day artifact. It never gates ordinary CI: hosted-runner timing is evidence to inspect, not an automatic comparison with the recorded reference host.
Promotion rules
Coverage grows by promotion, and promotion has an explicit bar.
- A PR-249 thread case is promoted only when it passes in its declared mode and finishes inside the no-GIL gate's budget. Several cases are ~20× slower with the GIL off, so passing in GIL mode is not promotion evidence — promoting such a case breaks CI.
- The no-GIL gate treats a case unknown to the baseline as must pass, so a newly promoted case earns its place rather than inheriting an exemption by being absent from the file.
- Every non-helper file outside the promoted allowlists must carry either an implementation blocker or a structured terminal disposition. A blocked case that happens to pass a probe is not thereby promoted.
- An ABI entry moves from
pendingtoimplementedonly when behaviour tests cover it, not when the declaration compiles.
Adding a gate
When you add a capability, add its gate in the same change:
- Produce a machine-readable inventory or report under
docs/.data/. - Add a verifier that fails on drift — the pattern used throughout is derive
the live set from source, require exact ordered coverage, and fail closed
(see
gc-relocation-inventory-check). - Wire it into
ci.ymlas its own leg. - If it affects a public claim, regenerate the marker-delimited README section rather than editing prose.
- If it closes a roadmap item, update
docs/.data/release-compatibility-matrix.jsonand re-runzig build release-compatibility-check.
Reading the release matrix
release-compatibility-matrix.json tracks the gates that stand between the
current state and a stable release — platform matrix, public C API, Objective-C
bridge, inspector, private ABI profiles, and the remaining engine gates
(automatic shared-realm compaction, a moving nursery for the multi-age GC, and
optimizing-JIT backend/differential evidence).
zig build release-compatibility-check # validate the matrix
home-tool run tools/release-compatibility.ts --release # fail unless every gate is green
home-tool run tools/release-compatibility.ts --update-readme
The README's "What Is Not Implemented" section is generated from that file, and its removal is itself gated. That is the point: the honest list of gaps is maintained by a tool, not by memory.