Two fixes from the independent review of f043cd7.
RationalNs::checked_add cross-multiplied into u128 and then added without a check. Each
product fits, but their sum does not: two reduced fractions near the U64 maximum add to about
2^129, which panics in debug and wraps in release, after which the reduction returns a
confidently wrong rational. Every multiplication and the addition now go through a checked
path, as ipc-v1 section 2 requires, with a fixture row and a test that reaches the overflow
rather than the "does not fit U64" reduction limit.
The schema-set test checked fourteen hardcoded type names, so a new payload type could have
shipped outside contractDigest. It now iterates the readers own list, all fifty of them.
Also amends ipc-v1 section 5, dated: Worker.Acknowledge carries req-<U64> request ids, not
arbitrary Ids, because the serial watermark rule in that same section cannot reject reuse
after acknowledgment unless the acknowledged id carries its serial.
Two specifications CONTRACT-01 owes the slices that cannot be built without them.
seed-derivation-v1: the versioned derivation of independent per-agent seeds from a recorded
master seed and stable agent ids, the exact hashed material, the lane rule that keeps a seed
away from zero (the pinned kernel RNG is an xorshift, whose state must not be zero), the
properties a composition may rely on, and the test vectors both languages reproduce.
checkpoint-envelope-v1: the exact byte layout of the new envelope per state-media-v1 section
4, with the header, canonical-JSON manifest, 112-byte payload table entries, eight-byte
aligned payloads and the digest footer; the manifest field set; what a reader enforces and in
what order; and the durable commit sequence of section 6, whose commit point is the store
manifest rename. FLYSIM01 is unchanged, refused at the magic, and stays separately readable.
Both are specifications with fixtures, not the store: generations, rotation, the capture
queue and the restore flow remain STATE-01.
The rung-10 loop whole: which building the fly was in, why every candidate list
on that map emptied, the byte dump that named the battle menu's swapped entries,
the ROM-gated before and after, and the two arms of the trap hunt being identical
because a restore clears the ledgers the loop was built out of.
Section 13.1's tables follow: MENU off both overworld rows and off the narrow
counter row, the move list's conditional BACK, the start menu reachable only by
the raw START button, and two new rows in the pad-empty audit - the room whose
one door the ledger rests, and the map with no way out at all, which is the one
empty pad left and is asserted rather than covered.
The contract: no pair of buttons on any battle pad may undo each other with
nothing else changing, which is section 12.2's rule stated at the pad instead
of at one macro. Section 13.1's table takes NEXT off the own-turn main menu,
gives the bag a row of its own on the own turn, and records MOVE 1 as the
backstop that row keeps.
The audit carries the reproduction -- 71,673 frames in one battle, 73 of 73
windows flagged, BACK 739 starts on the move list against NEXT 739 on the main
menu -- the ROM-gated run before and after, the trap hunt before and after
(1 distinct tile to 260, 73 of 73 flagged windows to 68 of 73, 0 overworld
frames to 20,394), and the residuals: NEXT on a move list whose cursor the seam
cannot place is now the largest source of it, which is row 30b and wants a WRAM
reading rather than a pad change.
286 distinct tiles become 489 over twenty brain minutes from the rung-9
checkpoint, the median flagged window holds 55 tiles instead of 16, GO FRONTIER
runs 64 walks worth up to twelve net tiles instead of four worth one, and one
walk spends its cap where six did.
The cost is named rather than buried: flagged windows go 61 to 70 and windows
under four tiles 5 to 14, and every one of those is a window spent inside a
battle -- a fly that covers more ground walks into more grass, 48,756 battle
frames becoming 50,413 with the longest battle 9,549 frames becoming 13,411.
This is the first measurement in that file where more ground and fewer flags do
not both hold, and it is stated as such.
Section 15 is the contract for map-aware walks: what is decoded, the one ROM
read and why it is a read of the cartridge image, what the window fallback is
for and how it says so, and the proof. macros-wram.md section 9 is the bytes --
four addresses with their encodings, the bank-aware read on the seam, the corner
the cartridge settled, the two gates against a plausible-but-wrong decode, and
the survey of Pallet Town and Viridian Forest.
The rung-9 forest review: what was live, the mechanism of all three
observations, the audit rows, and the trap hunt before and after from the
release container's own checkpoint.
The hunt is brain-driven rather than stubbed, which is legitimate here and
was not for sections 13 and 14: this branch adds no macro type, so no
population is re-dealt and the two arms differ in the macro code alone.
Distinct tiles 216 to 286, windows flagged 70 of 73 to 61, windows under
four tiles 21 to 5, BACK starts with no list open 175 to 0, MOVE n starts
36 to 68.
Four residuals are named rather than buried: BACK is still 359 starts of
830 over open lists, which is row 34's contract; a NEXT/BACK two-cycle
closes the run inside one battle, from a move list whose cursor the seam
cannot place on its opening frames; a window spent in a battle is flagged
by the tile rule whatever happens in it; and the THROW BALL precondition
is inert in this run because the save carries a party of one.
Row 41 is the loop behind this one: in the before arm the fly answered the
nurse's box YES 474 times on one tile of a Pokemon Center for the last
eight brain minutes of the run. The after arm never enters it, so it is
neither reproduced nor fixed here. It is the next thing to measure.