receipt-ledger: version 5 holds a decode to the frames it delivered, its codestream what it read #559
Loading…
Reference in a new issue
No description provided.
Delete branch "wai/decode-output"
Deleting a branch is permanent. Although the deleted branch may continue to exist for a short time before it actually gets removed, it CANNOT be undone in most cases. Continue?
The flaw. The receipt ledger gives every
int_motionjob output as its decode receipt and its codestream, and since #556 holds the codestream to what the served hop delivered. That is true of an encode. A decode delivers its reconstruction, and the codestream is what it read. A conforming router therefore had to state the decode's input as what it delivered, and commit the hop's OER/2 receipt to an object the hop never produced: the binding #552 exists to forbid.The rule (
extensions/receipt-ledger.md§4.8, tariff and invoice version 5). Version 5 is version 4's layout, rules and prices with one rule more:A decode's output gives
receipt,codestreamandframes. The receipt is still re-derived from the codestream, which is the decode's input.framesis one animated PNG (PNG's third edition:acTL,fcTL,fdAT) of 8-bit RGB. It is read whole first, by a still's chunk rules plus the animation's:acTLcounts the frames it holds.It must have the receipt's size and frame count. Then each frame is read as a still's image data, and its samples must hash (integer-payloads §15.1) to the receipt's frame at its index.
The served hop states exactly that animation, by content hash, and nothing else.
Why one object, not one PNG per frame. An earlier head of this PR held each frame as its own PNG, and that cannot work. A route record states a hop's outputs once each and at most 1024 (route-record §5.2). A decode of more than 34 s at 30 fps could not be recorded, and a still scene, which repeats a frame, could not be stated at all. An animated PNG is lossless, one file that every browser plays and any tool splits into stills, and a still reader reads its first frame. The frame hash binds the samples, not the PNG's bytes, so any writer's animation of the right samples holds.
Reason for a new version. A version-4 reader would refuse a decode's
frames, and no version-4 verdict may change. Versions 1 to 4 read, verify and bill exactly as before. A decode bills its receipts' subpixels as before, and an encode and every other job are held as in version 4.Animated PNG in wai-rs (
png_still):encode_animation: every byte is a function of the frames and the delay.animation: reads the whole structure, then each frame's samples only when asked, so a long clip is never held decoded in memory.Corpus. 89 → 108 vectors. One is accepted: a decode held to its animation, beside an encode. Eighteen are controls:
Every other vector and source is unchanged byte for byte, except the acknowledged
invoice_versioncontrol (now version 6).Checked.
wai-rs on Linux, with
receipt_ledger's features:--lib png_still::: 6 passed, including a round trip with a repeated frame and every animation rule refused alone;--lib receipt_ledger::: 13 passed;wai_receipt_ledger_vectors genregenerates the file byte for byte, andverifygives every vector its outcome.receipt_ledger_verify.py, written from the text and sharing no code, with its own animation reader:decode-framesamong them, are caught when dropped.Dependent verifiers: those of the corpora that read the ledger's (revenue share, opportunity report, route record) all pass.
Rust falsification: each rule was mutated alone in the reference (16 mutations), each run against a passing baseline:
The corpus caught every one, and the restored tree passes. Two reader rules have no corpus control that only they refuse: an fcTL's sequence number, and image data only as the first frame's (the default-image-apart control breaks other rules too). The unit tests refuse each of them alone.
🤖 Generated with Claude Code