wai: D2c M8 — WIV1 and WIR1 through wai-ops/1's stage operators, goldens unchanged #308

Merged
dcharlot merged 45 commits from wai/d2c-m8 into main 2026-10-18 07:19:04 -04:00
Owner

D2c M8: WIV1 (wai.video.int_motion, and the P-frames of wai.video.int_hyper) and WIR1 (wai.{image,video,audio,splat}.int_refine) decode through the integer operator set wai-ops/1, by its stage operators alone (integer-operators §13.5). No arithmetic changes, and every committed golden is unchanged.

Stacked on #298 (M7a): this branch starts from wai/d2c-m7a at 3bc90f02, and its diff against main includes #298's commits until #298 merges. #298's newer heads are merged in, with no conflict: a1e007b9 (origin/main with #296; CHANGELOG both sides) as 88e4735f, and the pushed a6cd06d7 (origin/main at ea84f7e2) as f01eb197, which changes no file under wai/, .github/ or scripts/.

What changes

  • Stage operators, no graph. A clip and a refinement layer run no network, so neither has a lowering or a bounds certificate. The decodes are:
    • WIV1: one E1 rans64_decode (t4097, lenient, canonical) over the clip's stream; the prediction 128 for frame 0 under keyframe 0, otherwise E10 mc_predict on the previous decoded frame; E9 residual_step on [0, 255].
    • WIR1: per unit, one E1 decode of its stream; the prediction from the element below (identity), E11 up2_predict or E12 rate_predict; E9 on [0, 255] or [−32768, 32767].
  • wai-ops. E1 decodes a symbol against a table in whatever width a payload's parser keeps it (Rans::symbol_in; table_ok reads its entries likewise). E10, E11 and E12 gain per-element forms (mc_predict_at, up2_at, rate_at) that read a frame, a picture or source samples in the driver's own layout, so a decode forms no copy: int_payload_cost's bound (a keyframe-0 clip holds its declared working bytes to within 4096) holds unchanged. mc_predict, up2_predict and rate_predict are those forms over a Tensor; their vectors are unchanged.
  • The drivers. int_video::ops and staged::wir1::ops, each with its stage form (stages: the operands each operator takes), its decode, and WIR1's stream check. A.4 step 1 (a unit's geometry) is shared with the direct decode.
  • The switch. int_video::{decode_typed, decode_pframes_typed}, staged::wir1::apply_unit and Wir1::check_streams decode through the drivers, so the integer-payload decode, the staged sink, the video receipts and the browser crate do. The direct decodes are int_video::legacy and staged::wir1::legacy, test-only (legacy_int).
  • The 32-bit form, behind a feature, for D3b. wai-ops' E9 32-bit form (stage::residual_step_i32, i32_form_fits, and residual_step_by_i32 for i64 operands) is behind the new i32_forms feature, and compiled for its own tests and for K29 under the model checker. wai-rs' i32_forms decodes both payloads through it (int_video::ops::{decode_typed_i32, decode_pframes_typed_i32}, staged::wir1::ops::apply_unit_i32). byte-exact-conformance turns it on by default, so the matrix holds the 32-bit form to the pinned digests on every leg.
  • Gate 7. The direct decodes' arithmetic (their own predictors, and wir1_arith's saturating step) runs only in the test-only decode. int_video::predict is E10 on an RGB8 frame, which the encoder predicts with; the WIR1 encoder predicts with the decode's E11 or E12 (ops::prediction) and steps with E9; the staged-measurement and staged-corpus tools call ops::{up2_prediction, rate_prediction}. staged::predict's up2_at, rate_at, rate_index and rdiv, and wir1_arith, are test-only (and cfg(kani)); rate_len, the rate predictor's geometry, stays. The predictors' proofs move to the operators a decode runs: e11_up2_between_its_neighbours, e12_rdiv_matches_its_definition and e12_rate_at_reads_only_source_samples, in the stage shard.
  • Registry. wai.video.int_motion and the four int_refine capabilities register an ops member with no graph, { "set": "wai-ops/1", "stage": { "rans64": { t4097, lenient, canonical } } }: with no parameter set there is no profile, subset or lowering. OpsMember's three are optional, and the schema requires set, the three together, and a lowering or a stage. registry/capabilities.json and its schema regenerated.
  • Text. integer-operators: §5E writes E10, E11 and E12 out; §11 the stage-only member; §13.5 the WIV1 and WIR1 drivers and their widths; the status note names the stage-only capabilities; §15.3 item 5 (none). integer-payloads §3 and §12 and staged-delivery A.4 cite the stage operators. SPEC §5 (the int_motion and int_hyper rows, the refinement table), §7 (StandardDefined) and §8 (no planned break). CHANGELOG.
  • CI. tests/int_video_ops.rs and tests/wir1_ops.rs in both fast-kernel steps of wai-conformance.yml, which carry i32_forms (appended, so gate.sh's grep still finds the steps); the differential's two new halves run there for a fixed count and nightly in wai-ops-differential.yml, whose features gain video_int,staged; the moved harnesses in wai-formal-verification.yml's stage shard.

Planned breaks

None. integer-operators §15.3 item 5 and SPEC §8 say so: the decodes through the stage operators give the output and the refusal of the decoders they replaced, on every input. The differential's oracle is equality, with no exemption.

Gates, each red once and restored

gate commits falsification red
1 stage forms 19c4f407, a0db84b9, 582a643c E1's t4097 length bound widened to 4098 int_video_ops and wir1_ops, e1s_table_rule_is_the_payloads: "4098 entries: the decode's checks and E1 disagree"; wai-verify vectors verify, stage/rans64_decode.jsonl line 433. (A first run left the WIV1 case green: its 4098-entry table was not strictly increasing, so it broke two rules; fixed in 582a643c and run red again.)
2 golden equality 840b7961, ac203e85, 768e8798 E10's half-pel rounding without its +1 int_video_ops: video_real differs (the whole-pel clips, the 65 staged bases and video_nk alike); byte-exact wiv1_through_the_stage_operators_is_golden, video_real frame 2; the file-based goldens stay green (pre-switch); stage/mc_predict.jsonl line 17
2 E12's rdiv rounding halves toward zero wir1_ops: audio_flac_rate_ladder L1 unit 0 (−272 against −273); byte-exact staged_sets_through_the_stage_operators_are_byte_exact, the audio set; stage/rate_predict.jsonl line 1
3 refusal parity, ops members ee2fc134, c00b656c, f0c2b4b9 E1's canonical end accepts an unread word int_video_ops: "wiv1_unread_word: through the stage operators None, directly Some(…does not end canonically…)"; wir1_ops: stream_noncanonical/L1.wai checked Ok; stage/rans64_decode.jsonl line 45
4 differential c84ca0ec, 11af3852 the driver's block grid taken as w / block (only a grid with a partial last column reaches it; every committed clip's sides are multiples of its block) gates 1 to 3 green; int_video_random_clips_decode_alike, "the two decodes differ", seed 3372 (h 5, w 3, block 4)
5 the 32-bit form 44686569 the 32-bit form's R one short ((hi − lo)/q) wai-ops residual_identity_holds; wir1_ops 32-bit test (image_up2_from_int_hyper L1, element 2966: 254 against 255); byte-exact staged_sets_through_the_32bit_form_are_byte_exact; both differential halves. The exact paths stay green, and so do the WIV1 32-bit golden and test: no committed clip has a residual past ⌊255/q⌋
6 the switch 9a377f9b E10 and E12's faults above, with the switch live now the file-based goldens: byte-exact wiv1_keyframe_0_payloads_are_byte_identical, int_video_real_footage_exercises_the_half_pel_predictor, staged_audio_rate_ladder_is_byte_exact; wai-rs int_video_halfpel; wai_int_payload_vectors verify (FAIL video_real) and wai_staged_vectors verify (the generator's encoder checks its reconstruction against the decode). staged_verify.py and int_payload_verify.py, which share no code with the decoder, stay green
6 memory the decode clones the previous frame for E10 int_payload_cost: "int_video: the decode held 42524 bytes, over the declared 35612"
7 the direct arithmetic leaves production f2513980, ca6c0544 the test-only direct decodes broken (legacy::predict without its +1, wir1_arith::step without its clamp) production green (int_video, int_video_halfpel, int_video_keyframe, int_payload, staged_resources, cli_stage, the lib tests, byte-exact 101, both corpora's verify); the comparisons red: int_video_ops, wir1_ops (attested_across_drop L1, element 24: 255 through the operator set, 7 directly; the refusal sweep), both differential halves

Every fault was restored with git, and the gate's tests run green again on the committed tree.

Goldens, unchanged

Every golden M8's row names, byte for byte:

  • int_video_golden: the synthetic clip (clip FNV 27573cdba1ad6628, SHA-256 5afd6477…) and the half-pel real footage (1ec1f0fa7da0d70f, e6724ca2…), every frame; through the stage operators, through the 32-bit form, and as the sink decodes (byte-exact on the matrix's legs; int_video, int_video_halfpel, int_video_keyframe in wai-rs).
  • The WIV1 payloads of int-payload-conformance (int_video, video_real, video_nk 4a81f0c9…) and every refusal fixture's code (wai_int_payload_vectors verify, tests/int_payload.rs, int_payload_verify.py).
  • The staged corpus: every case of staged-conformance (wai_staged_vectors verify, which regenerates every file and compares byte for byte), staged_verify.py, the wasm32 sink (69 of 69 cases, 146 unit stage hashes equal the native ones), and byte-exact's pinned stage digests of the video, image and audio sets, through the stage operators and the 32-bit form.
  • The operators' own vectors (ops-conformance/stage/), unchanged and reproduced by both certifiers.

Results

All on the build host, on the merged head 88e4735f; f01eb197 has the same wai/, .github/ and scripts/ trees.

  • gate.sh d2c-m8-merged: GREEN. The build, the lib tests, carriage, the corpus loop (21 of 21), the fast kernels, byte-exact, wai-web wasm32 and the neural gates. Also GREEN on the switched tree (d2c-m8-g6) and after gate 7 (d2c-m8-g7).
  • Also green on the merged head:
    • the release fast-kernel step (overflow checks off, i32_forms): 37 test binaries, 0 failures, int_payload_cost at the 2^30-byte clip among them;
    • wai registry export --check;
    • wai-ops cargo test --locked, debug and release;
    • the wai-verify build and its tests; wai-verify vectors verify (every file verifies); tools/wai_ops_check.py ops-conformance (every vector file, lowered graph and certificate rewritten byte for byte);
    • staged_verify.py (69 cases, 0 failures) and int_payload_verify.py;
    • the nightly differential's feature set builds (legacy_int,splat_int,audio_int,world_int,video_int,staged);
    • wai-web: the native tests (32), the wasm32 release build and wasm-bindgen 0.2.127; under Node, verify_int_payload_wasm (int_video 5afd6477…, video_real e6724ca2…, video_nk 4a81f0c9…) and verify_staged_wasm (69 of 69 cases, 146 unit stage hashes equal the native ones);
    • check-lockfiles.sh with 1.98.0 (38 lockfiles current), check-public-names.sh with the host's list, pr-touches-paths-selftest.sh;
    • locally: tests in CI, section refs, orphan sources, comparative prose, vanity metrics, workflow concurrency.
    • No build changed a tracked file; include/wai.h is as committed.
  • The differential (both new halves; outcomes by refusal):
    • per push, 3000 cases each, seed 3372, debug: clips decoded alike 2549 (the rest refused alike: stream exhausted 186, not canonical 89, a broken table 49, q 40, mv_precision 36, the vector count 26, a short stream 13, an I-frame a byte short 12); layers: units applied alike 5743, geometry_mismatch 188, stream_exhausted 15, stream_noncanonical 15, refused at parse 6, no layer drawn 21.
    • timed, 300 s, seed 20261017: debug 2,402,935 clips (2,007,594 decoded alike) and 408,439 layers (782,495 units alike); release 11,948,953 clips (9,983,805 alike) and 3,322,036 layers (6,361,634 units alike). Every refusal alike; no case panicked either way.
    • with i32_forms (the fast-kernel steps), every case also through the 32-bit form, alike.
  • Parity counts: 69 committed WIV1 payloads and 132 WIR1 layers (237 units) through the stage operators as directly; 4 committed decode fixtures, 21 per-rule fixtures and 682 changed streams of WIV1, and 25 geometry fixtures and 765 changed streams of WIR1, refused alike; 618 clips and 501 units through the 32-bit form as through the exact form.
  • Memory: int_payload_cost holds unchanged: a keyframe-0 clip holds its declared working bytes to within 4096, and staged_resources and int_video_enc_memory pass.

Kani

The moved harnesses, and those the change touches, under memguard at 48 GB and a 45-minute budget: 8 of 8 verified, 0 failures.

  • e12_rate_at_reads_only_source_samples 7.4 s, e12_rdiv_matches_its_definition 13.7 s, e11_up2_between_its_neighbours 2.8 s (new in wai-ops, in the stage shard);
  • k29_residual_step_32bit_identity_registered_ranges 137.9 s (its functions are now behind i32_forms, and compiled under cfg(kani));
  • the direct decode's own staged_predict::{rate_index_in_bounds, rdiv_matches_spec, up2_bounded} and staged_wir1_arith::step_in_range 64.8 s, which still compile under their new cfg.

k29_residual_step_32bit_identity_every_range (the stage-long shard) was not rerun: its code is unchanged, only gated. No harness is left kani_open by this PR.

Decisions

  • Gate 1 for a decode with no graph is its stage form. There is no lowering to write or certificate to compute, and Appendix C has no row for these payloads. What gate 1 commits is the mapping from each payload's fields to each operator's operands, checked on every committed payload (69 WIV1 payloads, 132 WIR1 layers), and that E1's t4097 rule is each payload's table rule, edit for edit. The operators' own vectors are ops-conformance/stage/, which both certifiers reproduce byte for byte.
  • Gate 5 for a decode with no fast kernel is the 32-bit form. The one faster arithmetic these decodes have is E9's 32-bit identity, which a 32-bit fabric runs; gate 5 holds it to the exact form on every committed payload, on the random cases of the differential and on every leg of the byte-equality matrix.
  • The ops member of a stage-only capability names no profile. A profile is what a parameter set's certificate meets; these capabilities have no set. Their widths are §7.4's per operator (E1 a 64-bit state, E12 64-bit arithmetic, E9 i32 by its identity), which §13.5 now states.
  • Parse rules stay the payloads'. int_video::check and WIR1's parser keep their table checks, codes and order; gate 1 shows E1's rule admits exactly the tables they admit.
  • The direct decodes' proofs stay (staged_predict::, staged_wir1_arith:: in the integer-core shard): they prove the reference the differential holds the operator set to.

Left for D3b, and for M7b/O8

  • D3b takes the i32_forms feature: E9's 32-bit form for the integer GPU legs, with its parity tests and byte-equality goldens. E10 and E11 fit i32 as they are; E1 needs a 64-bit state and E12 64-bit arithmetic on any fabric (§7.4), so a GPU leg for these payloads emulates both or leaves them to the CPU.
  • M7b still waits for O8 (the jpegai PTQ networks' topology); nothing here touches it.
  • Nothing is deployed.

Notes

  • Every cargo build, test and Kani run ran on the build host through rb, under memguard; logs are under $RB_ROOT/logs/d2c-m8/ and logs/land/d2c-m8-*.
  • No cargo fmt, no git stash, no cargo output piped into head or tail. No history rewritten; WIP-labelled commits were committed before their runs, and each gate's results are in its later commits' messages.
  • No write or command was refused by the permission system.

🤖 Generated with Claude Code

D2c M8: `WIV1` (`wai.video.int_motion`, and the P-frames of `wai.video.int_hyper`) and `WIR1` (`wai.{image,video,audio,splat}.int_refine`) decode through the integer operator set `wai-ops/1`, by its stage operators alone ([integer-operators](wai/extensions/integer-operators.md) §13.5). No arithmetic changes, and every committed golden is unchanged. **Stacked on #298** (M7a): this branch starts from `wai/d2c-m7a` at `3bc90f02`, and its diff against main includes #298's commits until #298 merges. #298's newer heads are merged in, with no conflict: `a1e007b9` (origin/main with #296; CHANGELOG both sides) as `88e4735f`, and the pushed `a6cd06d7` (origin/main at `ea84f7e2`) as `f01eb197`, which changes no file under `wai/`, `.github/` or `scripts/`. ## What changes - **Stage operators, no graph.** A clip and a refinement layer run no network, so neither has a lowering or a bounds certificate. The decodes are: - `WIV1`: one E1 `rans64_decode` (`t4097`, `lenient`, `canonical`) over the clip's stream; the prediction 128 for frame 0 under keyframe 0, otherwise E10 `mc_predict` on the previous decoded frame; E9 `residual_step` on `[0, 255]`. - `WIR1`: per unit, one E1 decode of its stream; the prediction from the element below (identity), E11 `up2_predict` or E12 `rate_predict`; E9 on `[0, 255]` or `[−32768, 32767]`. - **`wai-ops`.** E1 decodes a symbol against a table in whatever width a payload's parser keeps it (`Rans::symbol_in`; `table_ok` reads its entries likewise). E10, E11 and E12 gain per-element forms (`mc_predict_at`, `up2_at`, `rate_at`) that read a frame, a picture or source samples in the driver's own layout, so a decode forms no copy: `int_payload_cost`'s bound (a keyframe-0 clip holds its declared working bytes to within 4096) holds unchanged. `mc_predict`, `up2_predict` and `rate_predict` are those forms over a `Tensor`; their vectors are unchanged. - **The drivers.** `int_video::ops` and `staged::wir1::ops`, each with its stage form (`stages`: the operands each operator takes), its decode, and `WIR1`'s stream check. A.4 step 1 (a unit's geometry) is shared with the direct decode. - **The switch.** `int_video::{decode_typed, decode_pframes_typed}`, `staged::wir1::apply_unit` and `Wir1::check_streams` decode through the drivers, so the integer-payload decode, the staged sink, the video receipts and the browser crate do. The direct decodes are `int_video::legacy` and `staged::wir1::legacy`, test-only (`legacy_int`). - **The 32-bit form, behind a feature, for D3b.** `wai-ops`' E9 32-bit form (`stage::residual_step_i32`, `i32_form_fits`, and `residual_step_by_i32` for `i64` operands) is behind the new `i32_forms` feature, and compiled for its own tests and for K29 under the model checker. `wai-rs`' `i32_forms` decodes both payloads through it (`int_video::ops::{decode_typed_i32, decode_pframes_typed_i32}`, `staged::wir1::ops::apply_unit_i32`). byte-exact-conformance turns it on by default, so the matrix holds the 32-bit form to the pinned digests on every leg. - **Gate 7.** The direct decodes' arithmetic (their own predictors, and `wir1_arith`'s saturating step) runs only in the test-only decode. `int_video::predict` is E10 on an RGB8 frame, which the encoder predicts with; the `WIR1` encoder predicts with the decode's E11 or E12 (`ops::prediction`) and steps with E9; the staged-measurement and staged-corpus tools call `ops::{up2_prediction, rate_prediction}`. `staged::predict`'s `up2_at`, `rate_at`, `rate_index` and `rdiv`, and `wir1_arith`, are test-only (and `cfg(kani)`); `rate_len`, the rate predictor's geometry, stays. The predictors' proofs move to the operators a decode runs: `e11_up2_between_its_neighbours`, `e12_rdiv_matches_its_definition` and `e12_rate_at_reads_only_source_samples`, in the stage shard. - **Registry.** `wai.video.int_motion` and the four `int_refine` capabilities register an `ops` member with no graph, `{ "set": "wai-ops/1", "stage": { "rans64": { t4097, lenient, canonical } } }`: with no parameter set there is no profile, subset or lowering. `OpsMember`'s three are optional, and the schema requires `set`, the three together, and a lowering or a stage. `registry/capabilities.json` and its schema regenerated. - **Text.** integer-operators: §5E writes E10, E11 and E12 out; §11 the stage-only member; §13.5 the `WIV1` and `WIR1` drivers and their widths; the status note names the stage-only capabilities; §15.3 item 5 (none). integer-payloads §3 and §12 and staged-delivery A.4 cite the stage operators. SPEC §5 (the `int_motion` and `int_hyper` rows, the refinement table), §7 (`StandardDefined`) and §8 (no planned break). CHANGELOG. - **CI.** `tests/int_video_ops.rs` and `tests/wir1_ops.rs` in both fast-kernel steps of `wai-conformance.yml`, which carry `i32_forms` (appended, so `gate.sh`'s grep still finds the steps); the differential's two new halves run there for a fixed count and nightly in `wai-ops-differential.yml`, whose features gain `video_int,staged`; the moved harnesses in `wai-formal-verification.yml`'s stage shard. ## Planned breaks None. integer-operators §15.3 item 5 and SPEC §8 say so: the decodes through the stage operators give the output and the refusal of the decoders they replaced, on every input. The differential's oracle is equality, with no exemption. ## Gates, each red once and restored | gate | commits | falsification | red | |---|---|---|---| | 1 stage forms | `19c4f407`, `a0db84b9`, `582a643c` | E1's `t4097` length bound widened to 4098 | `int_video_ops` and `wir1_ops`, `e1s_table_rule_is_the_payloads`: "4098 entries: the decode's checks and E1 disagree"; `wai-verify vectors verify`, `stage/rans64_decode.jsonl` line 433. (A first run left the `WIV1` case green: its 4098-entry table was not strictly increasing, so it broke two rules; fixed in `582a643c` and run red again.) | | 2 golden equality | `840b7961`, `ac203e85`, `768e8798` | E10's half-pel rounding without its `+1` | `int_video_ops`: video_real differs (the whole-pel clips, the 65 staged bases and video_nk alike); byte-exact `wiv1_through_the_stage_operators_is_golden`, video_real frame 2; the file-based goldens stay green (pre-switch); `stage/mc_predict.jsonl` line 17 | | 2 | | E12's `rdiv` rounding halves toward zero | `wir1_ops`: `audio_flac_rate_ladder` L1 unit 0 (−272 against −273); byte-exact `staged_sets_through_the_stage_operators_are_byte_exact`, the audio set; `stage/rate_predict.jsonl` line 1 | | 3 refusal parity, `ops` members | `ee2fc134`, `c00b656c`, `f0c2b4b9` | E1's `canonical` end accepts an unread word | `int_video_ops`: "wiv1_unread_word: through the stage operators None, directly Some(…does not end canonically…)"; `wir1_ops`: `stream_noncanonical/L1.wai` checked Ok; `stage/rans64_decode.jsonl` line 45 | | 4 differential | `c84ca0ec`, `11af3852` | the driver's block grid taken as `w / block` (only a grid with a partial last column reaches it; every committed clip's sides are multiples of its block) | gates 1 to 3 green; `int_video_random_clips_decode_alike`, "the two decodes differ", seed 3372 (h 5, w 3, block 4) | | 5 the 32-bit form | `44686569` | the 32-bit form's `R` one short (`(hi − lo)/q`) | wai-ops `residual_identity_holds`; `wir1_ops` 32-bit test (`image_up2_from_int_hyper` L1, element 2966: 254 against 255); byte-exact `staged_sets_through_the_32bit_form_are_byte_exact`; both differential halves. The exact paths stay green, and so do the `WIV1` 32-bit golden and test: no committed clip has a residual past `⌊255/q⌋` | | 6 the switch | `9a377f9b` | E10 and E12's faults above, with the switch live | now the file-based goldens: byte-exact `wiv1_keyframe_0_payloads_are_byte_identical`, `int_video_real_footage_exercises_the_half_pel_predictor`, `staged_audio_rate_ladder_is_byte_exact`; wai-rs `int_video_halfpel`; `wai_int_payload_vectors verify` (FAIL video_real) and `wai_staged_vectors verify` (the generator's encoder checks its reconstruction against the decode). `staged_verify.py` and `int_payload_verify.py`, which share no code with the decoder, stay green | | 6 memory | | the decode clones the previous frame for E10 | `int_payload_cost`: "int_video: the decode held 42524 bytes, over the declared 35612" | | 7 the direct arithmetic leaves production | `f2513980`, `ca6c0544` | the test-only direct decodes broken (`legacy::predict` without its `+1`, `wir1_arith::step` without its clamp) | production green (int_video, int_video_halfpel, int_video_keyframe, int_payload, staged_resources, cli_stage, the lib tests, byte-exact 101, both corpora's verify); the comparisons red: `int_video_ops`, `wir1_ops` (attested_across_drop L1, element 24: 255 through the operator set, 7 directly; the refusal sweep), both differential halves | Every fault was restored with git, and the gate's tests run green again on the committed tree. ## Goldens, unchanged Every golden M8's row names, byte for byte: - `int_video_golden`: the synthetic clip (clip FNV `27573cdba1ad6628`, SHA-256 `5afd6477…`) and the half-pel real footage (`1ec1f0fa7da0d70f`, `e6724ca2…`), every frame; through the stage operators, through the 32-bit form, and as the sink decodes (byte-exact on the matrix's legs; `int_video`, `int_video_halfpel`, `int_video_keyframe` in wai-rs). - The `WIV1` payloads of int-payload-conformance (int_video, video_real, video_nk `4a81f0c9…`) and every refusal fixture's code (`wai_int_payload_vectors verify`, `tests/int_payload.rs`, `int_payload_verify.py`). - The staged corpus: every case of `staged-conformance` (`wai_staged_vectors verify`, which regenerates every file and compares byte for byte), `staged_verify.py`, the wasm32 sink (69 of 69 cases, 146 unit stage hashes equal the native ones), and byte-exact's pinned stage digests of the video, image and audio sets, through the stage operators and the 32-bit form. - The operators' own vectors (`ops-conformance/stage/`), unchanged and reproduced by both certifiers. ## Results All on the build host, on the merged head `88e4735f`; `f01eb197` has the same `wai/`, `.github/` and `scripts/` trees. - **`gate.sh d2c-m8-merged`: GREEN.** The build, the lib tests, carriage, the corpus loop (21 of 21), the fast kernels, byte-exact, wai-web wasm32 and the neural gates. Also GREEN on the switched tree (`d2c-m8-g6`) and after gate 7 (`d2c-m8-g7`). - **Also green on the merged head:** - the release fast-kernel step (overflow checks off, `i32_forms`): 37 test binaries, 0 failures, `int_payload_cost` at the 2^30-byte clip among them; - `wai registry export --check`; - wai-ops `cargo test --locked`, debug and release; - the wai-verify build and its tests; `wai-verify vectors verify` (every file verifies); `tools/wai_ops_check.py ops-conformance` (every vector file, lowered graph and certificate rewritten byte for byte); - `staged_verify.py` (69 cases, 0 failures) and `int_payload_verify.py`; - the nightly differential's feature set builds (`legacy_int,splat_int,audio_int,world_int,video_int,staged`); - wai-web: the native tests (32), the wasm32 release build and wasm-bindgen 0.2.127; under Node, `verify_int_payload_wasm` (int_video `5afd6477…`, video_real `e6724ca2…`, video_nk `4a81f0c9…`) and `verify_staged_wasm` (69 of 69 cases, 146 unit stage hashes equal the native ones); - `check-lockfiles.sh` with 1.98.0 (38 lockfiles current), `check-public-names.sh` with the host's list, `pr-touches-paths-selftest.sh`; - locally: tests in CI, section refs, orphan sources, comparative prose, vanity metrics, workflow concurrency. - No build changed a tracked file; `include/wai.h` is as committed. - **The differential** (both new halves; outcomes by refusal): - per push, 3000 cases each, seed 3372, debug: clips decoded alike 2549 (the rest refused alike: stream exhausted 186, not canonical 89, a broken table 49, `q` 40, `mv_precision` 36, the vector count 26, a short stream 13, an I-frame a byte short 12); layers: units applied alike 5743, `geometry_mismatch` 188, `stream_exhausted` 15, `stream_noncanonical` 15, refused at parse 6, no layer drawn 21. - timed, 300 s, seed 20261017: debug 2,402,935 clips (2,007,594 decoded alike) and 408,439 layers (782,495 units alike); release 11,948,953 clips (9,983,805 alike) and 3,322,036 layers (6,361,634 units alike). Every refusal alike; no case panicked either way. - with `i32_forms` (the fast-kernel steps), every case also through the 32-bit form, alike. - **Parity counts:** 69 committed `WIV1` payloads and 132 `WIR1` layers (237 units) through the stage operators as directly; 4 committed decode fixtures, 21 per-rule fixtures and 682 changed streams of `WIV1`, and 25 geometry fixtures and 765 changed streams of `WIR1`, refused alike; 618 clips and 501 units through the 32-bit form as through the exact form. - **Memory:** `int_payload_cost` holds unchanged: a keyframe-0 clip holds its declared working bytes to within 4096, and `staged_resources` and `int_video_enc_memory` pass. ## Kani The moved harnesses, and those the change touches, under memguard at 48 GB and a 45-minute budget: 8 of 8 verified, 0 failures. - `e12_rate_at_reads_only_source_samples` 7.4 s, `e12_rdiv_matches_its_definition` 13.7 s, `e11_up2_between_its_neighbours` 2.8 s (new in wai-ops, in the stage shard); - `k29_residual_step_32bit_identity_registered_ranges` 137.9 s (its functions are now behind `i32_forms`, and compiled under `cfg(kani)`); - the direct decode's own `staged_predict::{rate_index_in_bounds, rdiv_matches_spec, up2_bounded}` and `staged_wir1_arith::step_in_range` 64.8 s, which still compile under their new `cfg`. `k29_residual_step_32bit_identity_every_range` (the stage-long shard) was not rerun: its code is unchanged, only gated. No harness is left `kani_open` by this PR. ## Decisions - **Gate 1 for a decode with no graph is its stage form.** There is no lowering to write or certificate to compute, and Appendix C has no row for these payloads. What gate 1 commits is the mapping from each payload's fields to each operator's operands, checked on every committed payload (69 `WIV1` payloads, 132 `WIR1` layers), and that E1's `t4097` rule is each payload's table rule, edit for edit. The operators' own vectors are `ops-conformance/stage/`, which both certifiers reproduce byte for byte. - **Gate 5 for a decode with no fast kernel is the 32-bit form.** The one faster arithmetic these decodes have is E9's 32-bit identity, which a 32-bit fabric runs; gate 5 holds it to the exact form on every committed payload, on the random cases of the differential and on every leg of the byte-equality matrix. - **The `ops` member of a stage-only capability names no profile.** A profile is what a parameter set's certificate meets; these capabilities have no set. Their widths are §7.4's per operator (E1 a 64-bit state, E12 64-bit arithmetic, E9 `i32` by its identity), which §13.5 now states. - **Parse rules stay the payloads'.** `int_video::check` and `WIR1`'s parser keep their table checks, codes and order; gate 1 shows E1's rule admits exactly the tables they admit. - **The direct decodes' proofs stay** (`staged_predict::`, `staged_wir1_arith::` in the integer-core shard): they prove the reference the differential holds the operator set to. ## Left for D3b, and for M7b/O8 - **D3b** takes the `i32_forms` feature: E9's 32-bit form for the integer GPU legs, with its parity tests and byte-equality goldens. E10 and E11 fit `i32` as they are; E1 needs a 64-bit state and E12 64-bit arithmetic on any fabric (§7.4), so a GPU leg for these payloads emulates both or leaves them to the CPU. - **M7b** still waits for O8 (the jpegai PTQ networks' topology); nothing here touches it. - Nothing is deployed. ## Notes - Every cargo build, test and Kani run ran on the build host through `rb`, under memguard; logs are under `$RB_ROOT/logs/d2c-m8/` and `logs/land/d2c-m8-*`. - No `cargo fmt`, no `git stash`, no cargo output piped into `head` or `tail`. No history rewritten; WIP-labelled commits were committed before their runs, and each gate's results are in its later commits' messages. - No write or command was refused by the permission system. 🤖 Generated with [Claude Code](https://claude.com/claude-code)
The exact decoder (and integer-operators §13.6.1 step 3, transcribed from it) put a
block whose likely was exactly 1003, 1352 or 1937 in the next band, for its σ addition
and its dequantisation multiplier. The reference decoder's own residual-variance tables
(4352 entries per branch, indexed by likely; dumped from the reference decoder, and the
tables the float decode path reads) change value at 1004, 1353 and 1938. The edges are
now 1004, 1353 and 1938 in jpegai_pipeline and in §13.6.1; §15.3 item 4 records it.

tests/jpegai_mans_golden.rs gains jpegai_rvs_bands_are_the_reference_tables: for every
likely and both branches, the band the edges give selects the reference's σ addition and
dequant multiplier. On test256.bin no block's likely is within 2 of an edge (the
reference's likely, luma 0..1357 and chroma 0..908), so no output changes.

Co-Authored-By: Claude Opus 5.5 <[email protected]>
wai-ops: lower::jpegai is now parse_jpegai (the members of norm.json and Table 13.6-A,
typed) followed by the lowering, and gains lower::jpegai_net and jpegai_net_loaded, the
same lowering of a bundle already parsed, loaded under a profile without writing and
parsing the graphs again; stage::mans::decode_sgm_tables decodes with latent tables
built once. tests/goldens.rs holds the parsed path to the bytes path.

wai-rs: jpegai_ops (new) converts the bundle this crate parses (NormTables, IntNet) to
wai-ops' form and loads the scale path under acc32 (ScalePath: the two graphs, the latent
tables, the rows and the gains), and decodes one plane through §13.6.1 steps 1-4 (plane);
jpegai_ops::legacy is the front half as jpegai_decode computes it, test-only.
NormTables' bounds and CDF rows are i64, so the load checks see what the file says
rather than a value wrapped to a byte. tests/jpegai_ops.rs: the committed synthetic
bundle and the pinned jpegai/v1 bundle lower, from their bytes and from the parsed form,
to the committed certificates' graphs, and load under acc32. Named in wai-conformance's
fast-kernels steps and in wai-jpegai-e2e.yml (pinned bundle, missing input = failure).

Results (build host, release): wai-ops goldens 7 passed (the parsed lowering test on the
committed set and on the pinned jpegai/v1 bundle); tests/jpegai_ops.rs 2 passed, no skip,
jpegai/v1 at 3e243dc1 meeting acc32; jpegai_mans_golden 12 passed; the pinned whole
decode (jpegai_e2e_full, jpegai_reconstruction_binding, jpegai_cross_platform: 9 stage
hashes and WAI_JPEGAI_EXPECT_SHA256) unchanged; frontend and chroma stage tests green.

Falsified: the conversion reads the depthwise block's shifts from conv1's member.
Red: jpegai_ops EXIT=101, both tests at "the converted bundle is the one wai-ops parses
from the bytes". Restored with git: green above.

Co-Authored-By: Claude Opus 5.5 <[email protected]>
jpegai_decode: each plane's integers come from a front half, the direct computation
(jpegai_ops::legacy, still the production decode until the switch) or the integer
operator set (jpegai_ops::plane, from the bundle's loaded ScalePath). jpegai_decode::ops
decodes through the operator set: the codestream's scope, then the scale path lowered
and loaded under acc32, then the decode; it refuses with the operator set's codes
(Refusal::Ops). LEF's sigma is v + rvs, which is i_s + gain + rvs.

jpegai_ops: PlaneSetup and plane_with (one plane from its graph, rows, tables and
bounds); scale_net_of_blocks (the float path's bundle form of the same network);
load_scale and fac_rows for one plane. wai-ops: lower::jpegai::scale, one plane's graph.

Goldens through the lowering: tests/jpegai_ops.rs (the planes' integers and the whole
decode, stage by stage, against the direct decode, and the pinned RGB hash);
jpegai_hyperscale_calibration (the scale graph, max|Δ| = 0); jpegai_mans_golden (E8's
tables, the reference encoder's streams, the 258-call replay, the scale graph on both
planes, the sigma chain); byte-exact jpegai_golden (E8 on the reference stream);
jpegai_e2e_frontend and jpegai_e2e_chroma (steps 1-4, the chroma plane discarding the 160
luma rows).

Co-Authored-By: Claude Opus 5.5 <[email protected]>
The compile fix of the gate's WIP commit (a payload helper with two borrowed inputs
needs its lifetime named), and gate 2's results.

Results (build host, release; pinned jpegai/v1 inputs fetched and checked against
tools/jpegai-e2e-v1.sha256; the reference-decoder stage fixtures rebuilt from the local
assets' dumps and checked by the unchanged tests first):
- tests/jpegai_ops.rs 4 passed, no skip: both planes' z, v, mask, likely, rvs, σ_idx
  and y_q through the lowering equal the direct computation's; the whole decode through
  the operator set equals the direct decode at all 7 stages and matches
  WAI_JPEGAI_EXPECT_SHA256.
- jpegai_hyperscale_calibration, luma and chroma: the scale graph (acc32) vs the
  reference I_s, 40960/40960 and 24576/24576 exact, max|Δ| = 0.
- jpegai_mans_golden 12 passed: E8's tables (4 golden, 32 normative), the reference
  encoder's sgm and fac streams, codestream → E8, the 258-call replay, the scale graph on
  both planes, the sigma chain through the stage operators.
- byte-exact jpegai_golden 3 passed (E8 on the reference stream).
- jpegai_e2e_frontend and jpegai_e2e_chroma: y_q through the operator set 40960/40960
  and 24576/24576 exact; every later stage as before (U,V 3.377%, Y 1.398% at 1 LSB).
- The file-based goldens (jpegai_e2e_full, jpegai_reconstruction_binding,
  jpegai_cross_platform's 9 hashes) unchanged; wai-ops 35 + 7 + 3 + 4 + 2 + 1 + 1 tests.

Falsified (Part 3.5):
- Chroma's fac decode skips the 160 luma rows' reads (a fresh decoder over only its own
  96 rows). Red: jpegai_ops 2 of 4 (the planes test, Refusal { StreamExhausted,
  Symbol(711) }; the whole decode, Ops(StreamExhausted)), jpegai_e2e_chroma (the same
  refusal). The file-based goldens stay green: the switch is gate 6. Restored: green.
- B_y read as signed in E8. Every M7a golden stays green: no reference stream decodes an
  escape at a distribution whose bound is 128 or more, so the prediction that
  jpegai_mans_golden carries this row is corrected. Red: wai-verify vectors verify,
  stage/mans_decode.jsonl line 12 (a vector with a bound of 128). Restored: green.

Co-Authored-By: Claude Opus 5.5 <[email protected]>
The registry gains wai.image.jpegai's ops member: wai-ops/1, acc32, full, jpegai-int/1
(no stage modes: mANS and the scale path's stage operators have none). Its registry test
holds it, beside the NeuralIntegerExact capabilities' acc64 members. SPEC §5's row cites
integer-operators §13.6.1 and jpegai_ops.rs; SPEC §7's NeuralEntropyExact entry says
the stages its class covers decode through the operator set at acc32.

tests/jpegai_ops.rs: every load check of §13.6.1 broken one change at a time (and a sum
past i32 that meets acc64), refused model_mismatch from the members' bytes and from the
parsed bundle; the three entropy payloads cut at every length, on the committed bundle
and on the pinned one: decoded alike, or refused stream_exhausted where the direct decode
panics (with overflow checks; without them it may compute on, counted); a codestream
out of scope refused with check_scope's reason, before the bundle's checks.

Co-Authored-By: Claude Opus 5.5 <[email protected]>
registry/capabilities.json regenerated (wai registry export): wai.image.jpegai's ops
member. The stage constants (the coded threshold, the hyper-latent offset, the RVS edges
and additions) and the profile are crate-only, so cbindgen does not put them in
include/wai.h; jpegai_ops::stage_constants gives the first three to tests.

Co-Authored-By: Claude Opus 5.5 <[email protected]>
On the committed bundle every cut stream runs out (its tables are not the ones the test
codestream was coded with), so the test had no case decoded alike. Payloads lengthened at
their front (16, 256, 4096 bytes) decode further before they run out.

Co-Authored-By: Claude Opus 5.5 <[email protected]>
origin/main at a76522da: #274 (M6, this branch's base) merged as 80477972, and #262, #272,
#276 and #277, none of which touches wai/.

Co-Authored-By: Claude Opus 5.5 <[email protected]>
tests/int_ops_differential.rs gains the jpegai half: random bundles (pmf rows of widths 1
to 64, bounds among 0, 1, 2, 4, 30, 127, 128, 200 and 255, CDF rows, gains that put most,
some or no positions coded, scale networks of 1 to 3 channels between blocks, with
shifts up to 40 and, rarely, weights of 2^20, shifts of 64 to 128 or wrong dims) and
random or damaged payloads (the committed codestream's, cut, lengthened at the front,
bit-flipped, or random bytes). Outside the planned breaks, both planes' integers equal
the direct computation's, or the stream is refused (stream_exhausted) where the direct
computation panics with overflow checks on; a planned break (a load check, acc64 but
not acc32, or a shift of 64 to 127 that now has its exact meaning) is classified from
the members alone, and refused from the bytes and from the parsed bundle alike. The
nightly workflow's header names it.

Co-Authored-By: Claude Opus 5.5 <[email protected]>
Co-Authored-By: Claude Opus 5.5 <[email protected]>
The first per-push run reached no decodable case: a shift of 128 drawn per element
(1 in 64, over 2,560 elements) put nearly every bundle under a load check. One network
in about eight now has one shift of 31 to 40 per block, and one in 64 a shift of 64 to
127 or of 128.

Gate 5 (WIP, committed before running): int_ops' equivalence tests run the committed
bundle's scale graphs on the fast kernels under every fast policy (three convolutions
each, every value the interpreter's, z over [-31, 32]); tests/jpegai_ops.rs holds both
planes' integers to the reference policy under every fast policy, on the committed and
the pinned bundle, payloads whole and cut.

Co-Authored-By: Claude Opus 5.5 <[email protected]>
acc32 holds every shift to at most 63 (integer-operators §7.1), so a bundle with a shift
of 64 to 127 is refused at load under the capability's profile; the classifier's acc32
kind covers it. The first release run: 1,500 cases, planes decoded alike 226, refused
where the direct decode panicked 2,194, computed on 0; breaks acc32 55, bounds 27, cdfs
36, dims 51, gains 24, per_channel 16, pmf 34, shift (128) 47.

Co-Authored-By: Claude Opus 5.5 <[email protected]>
jpegai_decode::{decode, decode_with_stages} decode through the integer operator set and
return Result<Rgb, Refusal>; load and decode_loaded run a scale path loaded once. The
direct decode is jpegai_decode::legacy and jpegai_ops::legacy, test-only (legacy_int).

The neural sink's exact path lowers and loads the scale path from the members' bytes
through the store of loaded sets (int_set_cache, keyed by the listing of norm.json and
weights/hs_{y,uv}.json); a refusal of the exact decode (model_mismatch, stream_exhausted,
or set_incomplete for a member the set lacks) is the decode's result and does not fall
back to the float decode (O9). Only an absent bundle, or a target or floating-point
environment the float stages cannot run in, takes the float decode.

The float decode path (neural::jpegai) runs its scale path and entropy decodes through
the same driver (jpegai_ops::plane, O10), from its own bundle's members; one whose
hyper-latent offsets are not 31, or that fails a load check, is refused.

The browser crate's decodeJpegAiMans decodes through E8 (jpegai_ops::latent_span) and
throws on a refusal; decodeJpegAiFull reports the decode's refusal.

Co-Authored-By: Claude Opus 5.5 <[email protected]>
The byte-equality crate includes int_ops.rs without jpegai_ops, so the scale path's
fast-kernel test moves into jpegai_ops' own test module. tests/jpegai_memory.rs (own
binary, a live-bytes allocator, the pinned bundle): with the scale path loaded
beforehand, the decode through the operator set holds no more than the direct decode;
named in wai-jpegai-e2e.yml.

Co-Authored-By: Claude Opus 5.5 <[email protected]>
integer-operators: the status note names jpegai's scale path and entropy decodes;
§15.3 item 4 adds the acc32 refusal, the order (scope, bundle, streams) and that a
refusal is not replaced by the float path. determinism-tiers §5: both paths decode the
claim's stages through the operator set at acc32; the two codes; a sink holding the
bundle reports the exact decode's refusal and does not fall back (O9). SPEC §5's row and
§8's planned breaks; the capability constant's comment; CHANGELOG.

tests/jpegai_memory.rs also reports each plane's front half through the operator set
and directly. First run (before this): the direct decode held 175,465,380 bytes; with
the scale path loaded beforehand (14,083,663 bytes to load, 7,557,178 held) the decode
through the operator set held 175,465,380; loading and decoding in one call 183,012,574.

Co-Authored-By: Claude Opus 5.5 <[email protected]>
The front half held about 10% more than the direct computation (luma 2,445,680 bytes
against 2,218,884; chroma 1,489,776 against 1,357,586): every mask and σ_idx was held
twice while the latent decoded, once as the plane's and once in its span. They are now
formed into each channel's span and taken back after the decode.

Co-Authored-By: Claude Opus 5.5 <[email protected]>
Results (build host, release, pinned jpegai/v1 inputs, no skip):
- tests/jpegai_ops.rs 9 passed (the whole decode through the operator set equals the
  direct decode at all 7 stages and WAI_JPEGAI_EXPECT_SHA256; the stream parity on the
  committed bundle 4 alike / 326 refused where the direct decode panicked, on jpegai/v1
  39 / 291; every kernel policy alike).
- The file-based goldens, now through the operator set: jpegai_e2e_full,
  jpegai_reconstruction_binding (the pinned pixel hash), jpegai_cross_platform (all 9
  hashes), jpegai_e2e_frontend and jpegai_e2e_chroma, jpegai_hyperscale_calibration on
  both planes (max|Δ| = 0), jpegai_mans_golden 13, byte-exact jpegai_golden 3.
- The neural dispatch: the exact bundle decodes; an absent bundle takes the float path;
  a bound of 256 is reported as model_mismatch and does not fall back; a missing member
  is set_incomplete.
- The float path through the shared driver: jpegai_e2e and jpegai_live 5/196608 samples
  at 1 LSB, as before; jpegai_scope_ort green.
- Memory (reference kernels): the direct decode held 175,465,380 bytes; with the scale
  path loaded beforehand (14,083,663 bytes to load, 7,557,178 held) the decode through
  the operator set held 175,465,380. Each plane's front half alone: luma 2,114,160
  against 2,218,884 directly, chroma 1,290,864 against 1,357,586. The test now asserts
  both.

Co-Authored-By: Claude Opus 5.5 <[email protected]>
The duplicate ports neural/jpegai_hyper.rs and neural/jpegai_mans.rs, which the float
decode path ran its front half with, are deleted (O10): that path runs the shared
driver since the switch. The direct pieces of the exact decoder leave production,
test-only (legacy_int): the crate-root mANS port (jpegai_mans), the hyper-scale network
(jpegai_synthesis::decode_hyper_scale and its convolution) and the pipeline's
skip_mask, rvs_additive, rvs_likely and sigma_index. The calibration tests that read
them require legacy_int.

jpegai_mans_golden runs on E8 and the scale graph alone; jpegai_e2e (the float chain
against the reference PNG) takes its front half from the driver, still checking the
dumped RVS additions, masks and residuals; the byte-equality crate drops the neural
port and keeps E8 and the direct port.

Co-Authored-By: Claude Opus 5.5 <[email protected]>
Results (build host, release, pinned inputs, no skip): tests/jpegai_ops.rs 9 passed;
the CI trio (jpegai_e2e_full, jpegai_reconstruction_binding, jpegai_cross_platform:
all 9 hashes and WAI_JPEGAI_EXPECT_SHA256); jpegai_e2e_frontend and jpegai_e2e_chroma;
jpegai_hyperscale_calibration on both planes (max|Δ| = 0); jpegai_mans_golden 12 passed
on E8 alone; the neural dispatch 3; the float path (jpegai_e2e, jpegai_live 5/196608 at
1 LSB, jpegai_scope_ort); byte-exact jpegai_golden 2; wai-ops' bundle tests 2;
jpegai_memory (front half luma 2,114,160 against 2,218,884, chroma 1,290,864 against
1,357,586); the differential, 1,500 cases, no disagreement. Each build's cargo check
(neural_int; neural_int,legacy_int,provenance; neural; the differential's features;
the default features with neural; wai-web; the byte-equality crate) adds no warning.

Falsified: the test-only direct mANS port refills its window to 48 bits instead of 56.
Production green (the CI trio, byte-exact's E8 golden); the comparisons red:
jpegai_ops 4 of 9 (the planes, the whole decode, both stream-parity tests), byte-exact's
direct-port golden, the differential ("Luma: the two decodes differ", seed
10208061212434326836). Restored: green.

Co-Authored-By: Claude Opus 5.5 <[email protected]>
origin/main at f18ce9ac (#275, #278, #280, #281, #282, #283). CHANGELOG: both sections
kept, this branch's first.

Co-Authored-By: Claude Opus 5.5 <[email protected]>
Co-Authored-By: Claude Opus 5.5 <[email protected]>
The two K27 totality harnesses (16-byte streams, spans of up to 5) are kani_open: on the
build host each grew past a 48 GB memory guard (peak resident 76 and 91 GB) and was
stopped. k27_mans_is_total_small checks the same property on 10-byte streams, a latent
span of up to 3 positions and then a hyper-latent row of up to 3 symbols from the same
window; the stage shard's filter (proofs::stage::k27) runs it.

Co-Authored-By: Claude Opus 5.5 <[email protected]>
The harness over a 10-byte stream with a latent span and a hyper-latent row of 3 also
grew past its memory guard on the build host (40 GB; peak resident 57 GB) and was
stopped. It is replaced by two harnesses over 8-byte streams, a span of up to 2 and a
row of up to 2.

Co-Authored-By: Claude Opus 5.5 <[email protected]>
origin/main at bea79dc6 (the live-room, live-events and capture-binding extensions,
#284 to #288 among them). CHANGELOG: both sides kept, this branch's section first.

Co-Authored-By: Claude Opus 5.5 <[email protected]>
wai-ops: K27's narrower harnesses withdrawn; K27's totality stays kani_open
All checks were successful
wai-ops integer operators / linux-x86_64 (pull_request) Successful in 1m4s
WAI neural sink gates / model-free refusals of the neural sink (pull_request) Successful in 1m29s
wai-ops integer operators / wasm32 under Node (pull_request) Successful in 23s
wai-ops integer operators / wasm32-wasip2 (wasmtime) (pull_request) Successful in 30s
wai-ops integer operators / independent checker (Python) (pull_request) Successful in 12s
WAI conformance / delivery telemetry · CMCD and CMSD against an independent library (pull_request) Successful in 13s
WAI conformance / cross-arch byte-equality · linux-arm64 (pull_request) Successful in 26s
wai-quantum WebGPU member / member · software Vulkan (linux) (pull_request) Successful in 2m18s
WAI conformance / C2PA manifest emission · signed, read back, validated (pull_request) Successful in 1m14s
wai-quantum WebGPU member / shader checks · browser build · wasip2 inertness · MSRV (pull_request) Successful in 3m36s
wai-pack / wai-pack · linux (pull_request) Successful in 1m31s
WAI energy receipts / energy receipts · linux-arm64 (pull_request) Successful in 2m30s
wai-web wasm32 / wai-web wasm32 build · corpus, menu and writers (pull_request) Successful in 3m17s
WAI mbt2018_mean integer decode (regenerated vectors) / regenerate mbt2018_mean integer vectors → Rust decode, required (pull_request) Successful in 5m55s
WAI conformance / independent verifiers · claims, JWP, key discovery and integer payloads (Python) (pull_request) Successful in 14m24s
WAI conformance / cargo-class corpora · linux-arm64 (pull_request) Successful in 16m44s
WAI HTTP delivery / HTTP corpus · falsify mutations 0/3 (pull_request) Successful in 49m4s
WAI HTTP delivery / HTTP corpus · falsify patches 0/3 (pull_request) Successful in 6m11s
WAI HTTP delivery / HTTP corpus · falsify mutations 1/3 (pull_request) Successful in 48m16s
WAI HTTP delivery / HTTP corpus · falsify mutations 2/3 (pull_request) Successful in 48m25s
WAI HTTP delivery / HTTP corpus · every patch and mutation in exactly one shard (pull_request) Successful in 6s
WAI HTTP delivery / HTTP corpus · verified both ways, and the differential (pull_request) Successful in 2m54s
WAI HTTP delivery / HTTP corpus · falsify patches 1/3 (pull_request) Successful in 6m40s
WAI HTTP delivery / HTTP corpus · falsify patches 2/3 (pull_request) Successful in 6m13s
WAI HTTP delivery / cache rules · controls and labelled caches (pull_request) Successful in 1m42s
wai-ops integer operators / linux-aarch64 (pull_request) Successful in 1m5s
wai-pack / wai-pack · the floor through a media prober (pull_request) Successful in 27s
wai-pack / wai-pack · linux-arm64 (pull_request) Successful in 1m22s
wai-pack / wai-pack · dependency licences (pull_request) Successful in 1m24s
wai-pack / wai-pack · independent verifier (Python) (pull_request) Successful in 4m13s
3bc90f0297
None of the narrower windows fits a memory budget. On the build host, under memguard:
the existing kani_open harnesses (16-byte streams, a span or a row of up to 5) grew past
48 GB (peak resident 76 and 91 GB); one over a 10-byte stream with a span and a row of 3
past 40 GB (57 GB); and the latent and the hyper-latent harness over 8-byte streams with
2 positions each still ran past 25 minutes and 24 GB. Each was stopped. Run in the
stage shard, any of them would take its runner's memory, so they are withdrawn and K27's
totality harnesses stay kani_open as on main. The stage shard's k27 and k28 harnesses
that do fit (k27_mans_bounds_are_unsigned, k28_mans_entry_fields) verify.

Co-Authored-By: Claude Opus 5.5 <[email protected]>
A clip and a refinement layer run no network, so neither has a lowering or a
bounds certificate (integer-operators §13.5: graphs none). Gate 1 for them is
the stage form: the operands each decode hands each stage operator.

- int_video::ops::stages: E1 rans64_decode (t4097, lenient, canonical) on the
  clip's table and offset; E10 mc_predict at mv_precision; E9 residual_step
  with q on [0, 255].
- staged::wir1::ops::stages: E1 per unit; the prediction (identity, E11 up2,
  E12 rate); E9 with q on the unit kind's range.
- wai-ops: E1's table rule reads its entries as i64 from whatever width a
  parser keeps them in, so a driver checks its table without a copy.
- tests/int_video_ops.rs and tests/wir1_ops.rs: every committed WIV1 payload
  and WIR1 layer has its stage form; E1's t4097 rule is each payload's table
  rule; the stage vectors cover the modes and ranges used. Both run in the
  fast-kernel steps.

Co-Authored-By: Claude Opus 5.5 <[email protected]>
Co-Authored-By: Claude Opus 5.5 <[email protected]>
Its entries were not strictly increasing, so E1 refused it for that too, and
the case could not tell E1's length bound from the payload's. They now rise
by 15, and only the length is past the rule.

Co-Authored-By: Claude Opus 5.5 <[email protected]>
- wai-ops: E1's symbol decode takes its table in any width (Rans::symbol_in;
  symbol is it over a Table); E10, E11 and E12 gain their per-element forms,
  mc_predict_at, up2_at and rate_at, which read a frame, a picture or the
  source samples in whatever layout the driver holds them, so a decode forms
  no copy. mc_predict, up2_predict and rate_predict are them over a Tensor.
- int_video::ops::{decode_typed, decode_pframes_typed}: one E1 decode of the
  residual stream (t4097, lenient, canonical), GREY or E10 for the
  prediction, E9 on [0, 255]. The direct decode moves, unchanged, into
  int_video::legacy; decode_typed and decode_pframes_typed still call it
  (the switch is gate 6).
- staged::wir1::ops::{apply_unit, check_streams}: E1 per unit, identity, E11
  or E12 for the prediction, E9 on the kind's range. The direct decode moves,
  unchanged, into wir1::legacy; A.4 step 1 (the unit's geometry) is shared.
- Goldens: tests/int_video_ops.rs, every committed WIV1 payload (the staged
  bases among them) through the stage operators as directly, and the three
  vectors and the keyframe-0 JSON forms to every committed digest;
  tests/wir1_ops.rs, every committed WIR1 layer's every unit as directly, and
  each layer's stream check; byte-exact-conformance,
  wiv1_through_the_stage_operators_is_golden and
  staged_sets_through_the_stage_operators_are_byte_exact, with the pinned
  constants.

Co-Authored-By: Claude Opus 5.5 <[email protected]>
Co-Authored-By: Claude Opus 5.5 <[email protected]>
Gate 2's falsification (E12's rdiv rounding halves toward zero) printed both
units in full. Results, both falsified red and restored:

- E10's half-pel rounding without its +1: int_video_ops, video_real differs
  (the whole-pel clips, the 65 staged bases and video_nk alike); byte-exact
  wiv1_through_the_stage_operators_is_golden, video_real frame 2; the
  file-based goldens stay green (pre-switch); wai-verify vectors verify,
  stage/mc_predict.jsonl line 17.
- E12's rdiv rounding halves toward zero: wir1_ops, audio_flac_rate_ladder
  L1 unit 0 (-272 against -273); byte-exact
  staged_sets_through_the_stage_operators_are_byte_exact, the audio set;
  wai-verify vectors verify, stage/rate_predict.jsonl line 1.

Co-Authored-By: Claude Opus 5.5 <[email protected]>
- Refusal parity. tests/int_video_ops.rs: every committed WIV1 fixture the
  decode refuses (int-payload-conformance), refused alike by both decodes with
  its code and by the sink; one fixture per refusal of the decode in its
  order; the stream cut at every word, and bytes changed across it.
  tests/wir1_ops.rs: every committed layer's streams checked alike (the
  corpus's stream_exhausted and stream_noncanonical cases with their codes);
  A.4 step 1 broken once per rule for each predictor; a coded layer of each
  kind and predictor cut at every word, a word appended, every byte changed.
- Registry: wai.video.int_motion and the four int_refine capabilities carry
  an ops member with no graph, { wai-ops/1, stage: rans64 t4097 lenient
  canonical }. OpsMember's profile, subset and lowering are optional; the
  schema requires set, the three together, and a lowering or a stage.
- Text: integer-operators §11 (a member with no graph), SPEC §5 (the
  int_motion and int_hyper rows, the refinement table) and §7
  (StandardDefined), CHANGELOG.

Co-Authored-By: Claude Opus 5.5 <[email protected]>
Co-Authored-By: Claude Opus 5.5 <[email protected]>
The sweep cut the clip's stream at every word and changed every seventh byte,
6684 cases of two decodes each (64 s in a debug build). It now cuts at each of
the last 64 words and every 61st word before them, and changes every 31st
byte: 682 cases, 7.5 s.

Co-Authored-By: Claude Opus 5.5 <[email protected]>
tests/int_ops_differential.rs gains two halves, each behind its decoder's
feature (video_int, staged), which the fast-kernel steps and now the nightly
workflow carry:

- int_video_random_clips_decode_alike: random clips (partial block grids,
  both precisions, q to 65535, tables of 3 to 64 entries at offsets to the
  ends of i32, vectors anywhere in i16, keyframe 1 with its I-frame, escaped
  and extreme residuals, a broken field one clip in 64, damaged streams)
  through int_video::ops and int_video::legacy: the same frames or the same
  refusal, and no panic.
- wir1_random_layers_apply_alike: random layers of every kind and predictor
  (rates to 2^20, small tables so most residuals escape, q to 65535, one table
  or one per unit) coded by the reference encoder, a stream damaged one layer
  in eight, a unit applied to another shape or type one in sixteen: every
  unit and the streams' check alike, no panic.

There is no planned break: integer-operators §15.3 lists none for these
decoders, so the oracle is equality.

Co-Authored-By: Claude Opus 5.5 <[email protected]>
The damage can cut a one-word stream below 8 bytes, which the parse refuses
(stream_length) before either decode runs.

Co-Authored-By: Claude Opus 5.5 <[email protected]>
A stage-only decode has no fast kernel behind an interpreter. What a faster
fabric runs instead is E9's 32-bit form (§5E E9, Width): the form D3b's
integer GPU legs take. Gate 5 holds it to the exact form.

- wai-ops: residual_step_i32 and i32_form_fits behind the new i32_forms
  feature (and cfg(test), cfg(kani), so the unit tests and K29 keep them);
  residual_step_by_i32, E9 through its 32-bit form for a driver whose
  operands are i64. wai-verify declares the feature name its included
  sources test.
- wai-rs i32_forms: int_video::ops::{decode_typed_i32,
  decode_pframes_typed_i32} and staged::wir1::ops::apply_unit_i32, the
  drivers with E9 as a parameter.
- Parity: every committed clip and layer through the 32-bit form as through
  the exact form (tests/int_video_ops.rs, tests/wir1_ops.rs), changed
  streams too; the differential compares the 32-bit form on every random
  case; byte-exact-conformance (i32_forms on by default) decodes WIV1 and the
  staged sets through it to the pinned digests on every leg.
- CI: the fast-kernel steps carry i32_forms, appended so gate.sh's grep
  still finds them.

Gate 4's falsification, for the record: ops::frame's block grid taken as
w / block, which only a grid with a partial last column reaches (every
committed clip's sides are multiples of its block). Gates 1 to 3 stayed
green (int_video_ops 5, wir1_ops 5); int_video_random_clips_decode_alike
failed at seed 3372 (h 5, w 3, block 4). Timed 300 s, seed 20261017: debug
2,402,935 clips and 408,439 layers, release 11,948,953 and 3,322,036,
alike.

Co-Authored-By: Claude Opus 5.5 <[email protected]>
- int_video::{decode_typed, decode_pframes_typed} decode through
  int_video::ops (E1, E10, E9); staged::wir1::apply_unit and
  Wir1::check_streams through staged::wir1::ops (E1, E11 or E12, E9). The
  int_payload decode, the staged sink, the receipts and the browser crate
  reach them through these. The direct decodes, int_video::legacy and
  staged::wir1::legacy, are test-only (legacy_int).
- integer-operators: §5E writes E10, E11 and E12 out; §13.5 the WIV1 and
  WIR1 drivers (no graph, the step and the predictions, and their widths);
  the status note names the stage-only capabilities; §15.3 item 5: none.
- integer-payloads §3 and §12 and staged-delivery A.4 cite the stage
  operators; SPEC §8: no planned break; CHANGELOG.

Co-Authored-By: Claude Opus 5.5 <[email protected]>
The arithmetic guards of the direct decodes (their own predictors, and the
saturating step of wir1_arith) no longer run outside the test-only decode;
the stage operators carry them now.

- int_video::predict is E10 on an RGB8 frame (the encoder predicts with it,
  as the decode does); the direct predictor, verbatim, is
  int_video::legacy::predict, test-only.
- staged::wir1: the direct decode's pred_at and step are legacy's. The
  encoder predicts with the decode's E11, E12 or the element below
  (ops::prediction) and steps with E9; it refuses a stage below of the wrong
  shape or element type up front. ops::{up2_prediction, rate_prediction} are
  E11 and E12 on the interleaved layouts, which the staged-measurement and
  staged-corpus tools now call.
- staged::predict's up2_at, rate_at, rate_index and rdiv, and the
  wir1_arith module, are test-only (legacy_int; and cfg(kani), for the
  harnesses that still prove them); rate_len, the rate predictor's geometry,
  stays. wai-verify declares legacy_int.
- The predictors' proofs move to the operators a decode runs: wai-ops'
  e11_up2_between_its_neighbours, e12_rdiv_matches_its_definition and
  e12_rate_at_reads_only_source_samples, in the stage shard.

Gate 6's results, for the record (the switch at 9a377f9b): gate.sh GREEN;
the release fast-kernel step; staged_verify.py and int_payload_verify.py;
wai-web native 32 and wasm32, verify_int_payload_wasm and verify_staged_wasm
(69 of 69 cases, 146 unit stage hashes equal the native ones); include/wai.h
unchanged. Falsified with the switch live: E10's half-pel rounding without
its +1 and E12's rdiv halves toward zero turn the file-based goldens red
(byte-exact wiv1_keyframe_0_payloads_are_byte_identical, video_real frame 2;
int_video_real_footage_exercises_the_half_pel_predictor;
staged_audio_rate_ladder_is_byte_exact; wai-rs int_video_halfpel), and the
corpora (wai_int_payload_vectors verify, FAIL video_real; wai_staged_vectors
verify, the encoder's reconstruction differs from the decode); the Python
verifiers stay green. The decode cloning the previous frame for E10 turns
int_payload_cost red: int_video held 42524 bytes against 35612 declared.

Co-Authored-By: Claude Opus 5.5 <[email protected]>
Main gained wai.live.compose (#296). The only conflict was the CHANGELOG's top
insertion; both entries are kept, this one first.

Co-Authored-By: Claude Opus 5.5 <[email protected]>
On f2513980, all green: gate.sh d2c-m8-g7 GREEN (build, lib tests, carriage,
the corpus loop 21 of 21, the fast kernels, byte-exact, wai-web wasm32, the
neural gates); each integer feature alone (cargo check --lib); wai-verify's
build and lib tests; byte-exact 101.

Kani, under memguard at 48 GB and a 45-minute budget: 8 of 8 verified,
e11_up2_between_its_neighbours, e12_rdiv_matches_its_definition and
e12_rate_at_reads_only_source_samples (the predictors' proofs, moved to
the operators a decode runs), K29 on the registered ranges, and the direct
decode's own harnesses (staged_predict::, staged_wir1_arith::step_in_range),
which still compile under their new cfg.

Falsified: the test-only direct decodes broken (int_video::legacy::predict's
half-pel rounding without its +1, wir1_arith::step without its clamp). The
production decode stays green: int_video, int_video_halfpel,
int_video_keyframe, int_payload, staged_resources, cli_stage, the lib tests,
byte-exact 101, and both corpora's verify. The comparisons go red:
int_video_ops (video_real), wir1_ops (attested_across_drop L1, element 24:
255 through the operator set, 7 directly; and the refusal sweep), and both
halves of the differential. Restored.

Co-Authored-By: Claude Opus 5.5 <[email protected]>
Merge remote-tracking branch 'origin/main' into wai/d2c-m7a
Some checks failed
wai formal verification (integer core) / kani (plan) (pull_request) Has been cancelled
wai formal verification (integer core) / kani (sound) (pull_request) Has been cancelled
wai formal verification (integer core) / kani (stage) (pull_request) Has been cancelled
wai formal verification (integer core) / kani (rans64-t2) (pull_request) Has been cancelled
wai formal verification (integer core) / kani (stage-long) (pull_request) Has been cancelled
wai formal verification (integer core) / kani (integer-core) (pull_request) Has been cancelled
WAI energy receipts / does this change touch it (pull_request) Has been cancelled
WAI energy receipts / energy receipts · linux (pull_request) Has been cancelled
WAI energy receipts / energy receipts · linux-arm64 (pull_request) Has been cancelled
WAI energy receipts / energy receipts · macos (pull_request) Has been cancelled
WAI conformance / does this change touch it (pull_request) Has been cancelled
WAI conformance / cargo-class corpora · linux (pull_request) Has been cancelled
WAI conformance / cargo-class corpora · linux-arm64 (pull_request) Has been cancelled
WAI conformance / cargo-class corpora · macos (pull_request) Has been cancelled
WAI conformance / quantum core and corpus under wasm32-wasip2 (wasmtime) (pull_request) Has been cancelled
WAI conformance / v2 vocabulary · manifests validate as stated (pull_request) Has been cancelled
WAI conformance / independent verifiers · claims, JWP, key discovery and integer payloads (Python) (pull_request) Has been cancelled
WAI conformance / delivery telemetry · CMCD and CMSD against an independent library (pull_request) Has been cancelled
WAI conformance / cross-arch byte-equality · linux (pull_request) Has been cancelled
WAI conformance / cross-arch byte-equality · linux-arm64 (pull_request) Has been cancelled
WAI conformance / cross-arch byte-equality · macos (pull_request) Has been cancelled
WAI conformance / codec wrappers · fuzz smoke, text decode limits, C entry points, provenance, the semantic path (pull_request) Has been cancelled
WAI conformance / C2PA manifest emission · signed, read back, validated (pull_request) Has been cancelled
wai cross-architecture byte-equality / does this change touch it (pull_request) Has been cancelled
wai cross-architecture byte-equality / linux-aarch64 (pull_request) Has been cancelled
wai cross-architecture byte-equality / linux-x86_64 (pull_request) Has been cancelled
wai cross-architecture byte-equality / macos-arm64 (reference) (pull_request) Has been cancelled
standards workspaces build + test / which workspaces this change touches (pull_request) Has been cancelled
standards workspaces build + test / macOS energy backends (pull_request) Has been cancelled
repository checks / lockfiles, tests in CI, workflow hygiene, spec and section references, public text (pull_request) Has been cancelled
a6cd06d780
Merge remote-tracking branch 'origin/wai/d2c-m7a' into wai/d2c-m8
All checks were successful
WAI conformance / cargo-class corpora · linux-arm64 (pull_request) Successful in 13m58s
wai formal verification (integer core) / kani (isqrt512) (pull_request) Successful in 46m23s
wai formal verification (integer core) / kani (stage-long) (pull_request) Successful in 22m13s
wai formal verification (integer core) / kani (integer-core) (pull_request) Successful in 5m52s
WAI neural decoders end-to-end / synthetic fixtures → Rust decode → reference (±4) (pull_request) Successful in 1m16s
WAI JPEG-AI whole decode (pinned inputs, required) / fetch pinned JPEG-AI inputs → whole decode + pixel hash, required (pull_request) Successful in 2m43s
WAI neural sink gates / model-free refusals of the neural sink (pull_request) Successful in 1m23s
wai-ops integer operators / wasm32-wasip2 (wasmtime) (pull_request) Successful in 32s
wai-ops integer operators / linux-x86_64 (pull_request) Successful in 55s
wai-ops integer operators / wasm32 under Node (pull_request) Successful in 22s
wai-ops integer operators / independent checker (Python) (pull_request) Successful in 13s
wai-pack / wai-pack · linux (pull_request) Successful in 1m32s
wai-quantum WebGPU member / shader checks · browser build · wasip2 inertness · MSRV (pull_request) Successful in 3m15s
wai-quantum WebGPU member / member · software Vulkan (linux) (pull_request) Successful in 2m5s
wai-web wasm32 / wai-web wasm32 build · corpus, menu and writers (pull_request) Successful in 3m7s
WAI mbt2018_mean integer decode (regenerated vectors) / regenerate mbt2018_mean integer vectors → Rust decode, required (pull_request) Successful in 5m33s
WAI HTTP delivery / HTTP corpus · falsify mutations 0/3 (pull_request) Successful in 46m9s
WAI HTTP delivery / HTTP corpus · falsify patches 0/3 (pull_request) Successful in 4m42s
WAI HTTP delivery / HTTP corpus · falsify mutations 1/3 (pull_request) Successful in 45m16s
WAI HTTP delivery / HTTP corpus · falsify mutations 2/3 (pull_request) Successful in 45m30s
WAI HTTP delivery / HTTP corpus · every patch and mutation in exactly one shard (pull_request) Successful in 4s
WAI HTTP delivery / HTTP corpus · verified both ways, and the differential (pull_request) Successful in 2m36s
WAI HTTP delivery / HTTP corpus · falsify patches 1/3 (pull_request) Successful in 5m28s
wai-ops integer operators / linux-aarch64 (pull_request) Successful in 59s
WAI HTTP delivery / cache rules · controls and labelled caches (pull_request) Successful in 1m3s
WAI HTTP delivery / HTTP corpus · falsify patches 2/3 (pull_request) Successful in 5m10s
wai-pack / wai-pack · the floor through a media prober (pull_request) Successful in 16s
wai-pack / wai-pack · linux-arm64 (pull_request) Successful in 1m10s
wai-pack / wai-pack · dependency licences (pull_request) Successful in 1m9s
wai-pack / wai-pack · independent verifier (Python) (pull_request) Successful in 3m53s
f01eb197a0
Merge origin/main into wai/d2c-m8; CHANGELOG keeps every entry
All checks were successful
wai formal verification (integer core) / kani (stage) (pull_request) Successful in 2m40s
WAI HTTP delivery / HTTP corpus · falsify mutations 0/3 (pull_request) Successful in 46m28s
WAI HTTP delivery / HTTP corpus · falsify patches 0/3 (pull_request) Successful in 4m52s
WAI HTTP delivery / HTTP corpus · falsify mutations 1/3 (pull_request) Successful in 45m7s
WAI HTTP delivery / HTTP corpus · falsify mutations 2/3 (pull_request) Successful in 45m18s
WAI HTTP delivery / HTTP corpus · every patch and mutation in exactly one shard (pull_request) Successful in 4s
WAI HTTP delivery / HTTP corpus · falsify patches 1/3 (pull_request) Successful in 5m40s
WAI HTTP delivery / HTTP corpus · verified both ways, and the differential (pull_request) Successful in 2m40s
WAI HTTP delivery / cache rules · controls and labelled caches (pull_request) Successful in 1m6s
wai-ops integer operators / linux-aarch64 (pull_request) Successful in 59s
WAI HTTP delivery / HTTP corpus · falsify patches 2/3 (pull_request) Successful in 5m19s
wai-pack / wai-pack · the floor through a media prober (pull_request) Successful in 25s
wai-pack / wai-pack · linux-arm64 (pull_request) Successful in 1m15s
wai-pack / wai-pack · dependency licences (pull_request) Successful in 1m12s
wai formal verification (integer core) / kani (isqrt512) (pull_request) Successful in 43m34s
wai-pack / wai-pack · independent verifier (Python) (pull_request) Successful in 4m12s
wai formal verification (integer core) / kani (stage-long) (pull_request) Successful in 21m19s
wai formal verification (integer core) / kani (integer-core) (pull_request) Successful in 5m45s
WAI JPEG-AI whole decode (pinned inputs, required) / fetch pinned JPEG-AI inputs → whole decode + pixel hash, required (pull_request) Successful in 2m31s
WAI neural sink gates / model-free refusals of the neural sink (pull_request) Successful in 1m21s
WAI neural decoders end-to-end / synthetic fixtures → Rust decode → reference (±4) (pull_request) Successful in 1m28s
wai-ops integer operators / wasm32-wasip2 (wasmtime) (pull_request) Successful in 32s
wai-ops integer operators / linux-x86_64 (pull_request) Successful in 53s
wai-ops integer operators / wasm32 under Node (pull_request) Successful in 24s
wai-ops integer operators / independent checker (Python) (pull_request) Successful in 12s
wai-pack / wai-pack · linux (pull_request) Successful in 1m17s
wai-quantum WebGPU member / member · software Vulkan (linux) (pull_request) Successful in 2m8s
wai-quantum WebGPU member / shader checks · browser build · wasip2 inertness · MSRV (pull_request) Successful in 3m5s
wai-web wasm32 / wai-web wasm32 build · corpus, menu and writers (pull_request) Successful in 3m7s
WAI mbt2018_mean integer decode (regenerated vectors) / regenerate mbt2018_mean integer vectors → Rust decode, required (pull_request) Successful in 5m20s
9e563a65ce
Main gained wai.live.recording and wai.text.timed (#303, with #299) and a wai-quantum
change (#302). The only conflict was the CHANGELOG's top insertion; M7a's and M8's
entries stay first.

Co-Authored-By: Claude Opus 5.5 <[email protected]>
dcharlot referenced this pull request from a commit 2026-10-18 07:34:19 -04:00
Sign in to join this conversation.
No reviewers
No labels
No milestone
No project
No assignees
1 participant
Notifications
Due date
The due date is invalid or out of range. Please use the format "yyyy-mm-dd".

No due date set.

Dependencies

No dependencies set

Reference
Transaction-Science/open-standards!308
No description provided.