wai packaging train: a title's whole ladder in one package, steps on the fabric with the least measured energy, decode-equivalence on GPUs (#426 #438 #452's GPU tier) #465

Merged
dcharlot merged 41 commits from train/pack-stack into main 2026-10-26 08:43:11 -04:00
392 changed files with 16884 additions and 737 deletions

View file

@ -5,20 +5,26 @@ name: wai-ops-gpu integer operators on GPUs
# (64- and 128-bit arithmetic built from 32-bit words), and the integer decoders with
# their graphs on the device (wai-rs `ops_gpu`).
#
# - metal (the `macos` runner, whose host has a GPU): the arithmetic probe on a
# - metal (the `macos` runner, whose host has a GPU): WGSL's integer semantics
# (wai/wgsl-conformance, determinism-tiers §5, Claiming the tier on a GPU), the
# committed vectors and SplitMix64 cases of every operation, with an edited kernel
# refused at discovery; the arithmetic probe on a
# million cases; every graph vector of wai/ops-conformance that the subset covers,
# at both widths, against the committed results and the interpreter; the shader
# mutants, every one of which the corpus must catch; every committed vector and
# refusal fixture of every capability that runs a wai-ops/1 graph, the jpegai/v1
# inputs included, against the decode on the CPU; and the corpus again in a
# headless browser's WebGPU, the kernels compiled by the browser's own WGSL
# compiler. WAI_OPS_GPU_EXPECT declares the one adapter the host must offer, and
# compiler, with the semantics suite there and its vectors held to the reference
# compiled to wasm32, in the page and under Node. WAI_OPS_GPU_EXPECT declares the one adapter the host must offer, and
# WAI_OPS_GPU_REQUIRE makes an absent adapter a failure, never a skip; each step
# then requires the report lines with their counts, so a filtered or empty run
# fails too. The splat renderer's compositing (extensions/splat-exact.md) runs there
# too: every view of the splat corpus equal to the CPU's frame, and its mutants caught.
# - checks (`linux`, a container with no GPU): the crate and its tests build, the
# device tests print SKIPPED and pass, and the same tests under
# - checks (`linux`, a container with no GPU): the crate and its tests build; the
# WGSL rules on naga's IR (tests/wgsl_rules.rs) and the committed semantics vectors
# against the reference, which need no adapter, pass; the device tests print SKIPPED
# and pass, and the same tests under
# WAI_OPS_GPU_REQUIRE=1 fail: an absent adapter is not a pass. The browser module
# builds for wasm32-unknown-unknown; the bench tool builds.
#
@ -37,6 +43,7 @@ on:
- 'wai/wai-ops-gpu/**'
- 'wai/wai-ops/**'
- 'wai/ops-conformance/**'
- 'wai/wgsl-conformance/**'
# The decoders whose graphs run on the device, and what they decode.
- 'wai/wai-rs/Cargo.toml'
- 'wai/wai-rs/Cargo.lock'
@ -130,7 +137,7 @@ jobs:
fi
else
grep -q '^ops-gpu corpus: SKIPPED' "$rep" || { echo "::error::the corpus test printed neither a result nor SKIPPED"; exit 1; }
if WAI_OPS_GPU_REQUIRE=1 cargo test --locked --release --test corpus --test arith --test mutants > "$RUNNER_TEMP/require.log" 2>&1; then
if WAI_OPS_GPU_REQUIRE=1 cargo test --locked --release --test corpus --test arith --test mutants --test semantics > "$RUNNER_TEMP/require.log" 2>&1; then
echo "::error::with no adapter, the device tests passed under WAI_OPS_GPU_REQUIRE=1"; exit 1
fi
grep -q 'WAI_OPS_GPU_REQUIRE is set' "$RUNNER_TEMP/require.log" \
@ -179,16 +186,21 @@ jobs:
: > "$WAI_OPS_GPU_REPORT"
nice -n 10 cargo test --locked --release -- --nocapture --test-threads=1 2>&1 | tee "$log"
k=gpu-metal-0
# Six tests in four binaries: the library's one, arith's two, corpus's two and
# mutants' one, none filtered, ignored or failed.
# Seventeen tests in six binaries: the library's four, arith's two, corpus's two,
# mutants' one, semantics' three and wgsl_rules' five, none filtered, ignored or
# failed.
ran=$(awk '/^test result: ok\. [0-9]+ passed; 0 failed; 0 ignored; 0 measured; 0 filtered out/ { n += $4 } END { print n + 0 }' "$log")
[ "$ran" = 6 ] || { echo "::error::$ran tests ran and passed, not 6"; exit 1; }
[ "$ran" = 17 ] || { echo "::error::$ran tests ran and passed, not 17"; exit 1; }
! grep -q '^test result: FAILED' "$log" || { echo "::error::a test failed"; exit 1; }
grep -qxF "ops-gpu adapters: as declared ($k)" "$WAI_OPS_GPU_REPORT" || { echo "::error::the adapters found are not $k"; exit 1; }
grep -qE "^ops-gpu arith: key=$k .* cases=[0-9]+ words=[0-9]+ equal$" "$WAI_OPS_GPU_REPORT" || { echo "::error::no probe result for $k"; exit 1; }
grep -qE "^ops-gpu corpus: key=$k .* acc32 vectors=[1-9][0-9]* decodes=[1-9][0-9]*; acc64 vectors=[1-9][0-9]* decodes=[1-9][0-9]*; .* mismatches=0 errors=0 " "$WAI_OPS_GPU_REPORT" \
|| { echo "::error::no equal corpus run for $k"; exit 1; }
grep -qxF "ops-gpu mutants: key=$k killed 18 of 18" "$WAI_OPS_GPU_REPORT" || { echo "::error::a mutant survived on $k, or the mutant test did not run"; exit 1; }
grep -qE "^ops-gpu semantics: key=$k .* committed=[1-9][0-9]* cases=[1-9][0-9]* guarded=[1-9][0-9]* differ=0 " "$WAI_OPS_GPU_REPORT" \
|| { echo "::error::no run of WGSL's integer semantics on $k with every guarded case equal"; exit 1; }
grep -qE "^ops-gpu semantics mutant: key=$k refused: the WGSL semantics suite: rem_i32 " "$WAI_OPS_GPU_REPORT" \
|| { echo "::error::the edited semantics kernel was not refused on $k"; exit 1; }
- name: The jpegai/v1 inputs
shell: bash
run: bash wai/tools/wai_jpegai_fetch_e2e_inputs.sh "$RUNNER_TEMP/jpegai"
@ -288,7 +300,14 @@ jobs:
nice -n 10 cargo build --locked --release --target wasm32-unknown-unknown
t="${CARGO_TARGET_DIR:-target}"
wasm-bindgen --target web --out-dir pkg --out-name wai_ops_gpu_browser "$t/wasm32-unknown-unknown/release/wai_ops_gpu_browser.wasm"
# The committed semantics vectors against the reference compiled to wasm32,
# under Node, with no GPU.
node semantics_reference.mjs
log="$RUNNER_TEMP/browser.log"
nice -n 10 node run.mjs 2>&1 | tee "$log"
grep -qE '^browser webgpu: key=gpu-webgpu-[0-9a-f]+ .* acc32 vectors=[1-9][0-9]* decodes=[1-9][0-9]*; acc64 vectors=[1-9][0-9]* decodes=[1-9][0-9]*; .* mismatches=0 errors=0$' "$log" \
|| { echo "::error::no equal corpus run on a GPU adapter in the browser"; exit 1; }
grep -qE '^wasm reference: target=wasm32 .* cases=[1-9][0-9]* equal$' "$log" \
|| { echo "::error::the semantics vectors are not the wasm32 reference's in the page"; exit 1; }
grep -qE '^browser webgpu semantics: key=gpu-webgpu-[0-9a-f]+ .* guarded=[1-9][0-9]* differ=0 ' "$log" \
|| { echo "::error::no run of WGSL's integer semantics on a GPU adapter in the browser with every guarded case equal"; exit 1; }

View file

@ -6,7 +6,11 @@ name: wai-pack
# - legs: on each architecture of the fleet, clippy with float arithmetic denied (no
# float decides anything in a package), the tests in release with a floor on how many
# each target lists, and the corpus recomputed by the crate: the golden packages
# packed again byte for byte and verified, every mutation's reason.
# packed again byte for byte and verified, every mutation's reason. On the macOS leg,
# whose host has a GPU, the steps a GPU runs (packaging §11.6): wai-pack-gpu's kernels
# against their references and every edited kernel caught, and wai-pack's fabric
# differential (every golden packed on the GPU byte for byte, every verdict the CPU's),
# an absent adapter a failure there (WAI_PACK_GPU_REQUIRE), never a skip.
# - independent: the corpus recomputed by its second implementation, written in Python
# from the extension text and sharing no code with wai-pack, the golden packages
# verified and re-derived from their sources among it (every refinement layer and
@ -20,7 +24,8 @@ name: wai-pack
#
# Push filters match the push's delta, so every path a build or a verifier reads is
# listed: the crate, the wai crate it builds on, the corpus, the BLAKE3, integer payload,
# staged-delivery and staged-measurement verifiers and the registry export pack_verify.py
# staged-delivery and staged-measurement verifiers, the claim verifier (a metered
# package's claim) and the OER verifier it imports, the registry export pack_verify.py
# reads, and this file.
concurrency:
@ -31,10 +36,13 @@ on:
pull_request:
paths:
- 'wai/wai-pack/**'
- 'wai/wai-pack-gpu/**'
- 'wai/wai-rs/**'
- 'wai/pack-conformance/**'
- 'wai/claim-conformance/_blake3.py'
- 'wai/claim-conformance/_ed25519.py'
- 'wai/claim-conformance/claim_verify.py'
- 'wai/oer-conformance/oer2_verify.py'
- 'wai/int-payload-conformance/int_payload_verify.py'
- 'wai/staged-conformance/staged_verify.py'
- 'wai/staged-measure-conformance/sim_verify.py'
@ -126,11 +134,17 @@ jobs:
echo "$target: $n tests (floor $floor)"
[ "$n" -ge "$floor" ] || { echo "::error::$target lists $n tests, under its floor of $floor"; fail=1; }
done <<'EOF'
--lib 34
--lib 39
--test=cmaf 4
--test=conformance 1
--test=packs 7
--test=fabric 3
--test=floor_only 2
--test=ladder 3
--test=pack_alloc 1
--test=packs 8
--test=review 9
--test=refusals 5
--test=refusals 6
--test=repack 3
--test=scenecut 3
--test=source_alloc 1
--test=staged 10
@ -141,6 +155,36 @@ jobs:
working-directory: wai/wai-pack
run: cargo run --release --locked --bin wai-pack -- conformance check ../pack-conformance
# The steps a GPU runs (packaging §11.6), on the one leg whose host has a GPU. Each
# test prints the adapter it ran on; the step requires those lines, so a run that
# found no adapter, or filtered the tests away, fails.
- name: wai-pack-gpu, clippy and its kernels against their references (Metal)
if: matrix.os == 'macos'
shell: bash
working-directory: wai/wai-pack-gpu
env:
WAI_PACK_GPU_REQUIRE: '1'
run: |
set -euo pipefail
cargo clippy --locked --all-targets -- -D warnings
cargo test --release --locked -- --nocapture 2>&1 | tee "$RUNNER_TEMP/gpu.txt"
grep -q 'motion search, 54 frames, every vector the text' "$RUNNER_TEMP/gpu.txt"
grep -q 'every hash the reference crate' "$RUNNER_TEMP/gpu.txt"
[ "$(grep -c '^caught: ' "$RUNNER_TEMP/gpu.txt")" -ge 12 ]
- name: wai-pack's fabric differential on the GPU (Metal)
if: matrix.os == 'macos'
shell: bash
working-directory: wai/wai-pack
env:
WAI_PACK_GPU_REQUIRE: '1'
run: |
set -euo pipefail
cargo clippy --locked --all-targets --features gpu,fabric-meter -- -D warnings
cargo test --release --locked --features gpu --test fabric -- --nocapture 2>&1 | tee "$RUNNER_TEMP/fabric.txt"
grep -q 'the search on the GPU: ' "$RUNNER_TEMP/fabric.txt"
grep -q 'verdicts, each the CPU' "$RUNNER_TEMP/fabric.txt"
grep -q 'test result: ok. 7 passed' "$RUNNER_TEMP/fabric.txt"
independent:
name: wai-pack · independent verifier (Python)
needs: relevant
@ -163,6 +207,12 @@ jobs:
working-directory: wai
shell: bash
run: python3 pack-conformance/pack_verify.py pack-conformance
# The same checks with the hashes and decodes run ahead in worker processes
# (--jobs): every check and its reason are the serial run's.
- name: pack_verify.py --jobs 2
working-directory: wai
shell: bash
run: python3 pack-conformance/pack_verify.py --jobs 2 pack-conformance
- name: Install Rust 1.98.0
shell: bash
run: |
@ -207,6 +257,13 @@ jobs:
set -euo pipefail
python3 ../pack-conformance/stage_diff.py target/debug/wai-pack 1 1000
python3 ../pack-conformance/stage_diff.py target/release/wai-pack 2 3000
# The supplied CMAF reader differentially (packaging §7.7): seeded alterations of a
# media muxer's segments and of §7.6's writer's, every verdict and accepted segment's
# samples of wai-pack's reader equal to pack_verify.py's.
- name: cmaf_diff.py, wai-pack against pack_verify.py
shell: bash
working-directory: wai/wai-pack
run: python3 ../pack-conformance/cmaf_diff.py target/release/wai-pack 1 3000
# A still's reader differentially: the zlib library's own streams, dynamic blocks
# built on each of RFC 1951's and zlib's code-set rules, and their alterations, every
# verdict of wai-pack's reader equal to pack_verify.py's, which inflates with
@ -232,27 +289,52 @@ jobs:
SUDO=""; [ "$(id -u)" -ne 0 ] && SUDO="sudo"
$SUDO apt-get update -qq
$SUDO apt-get install -y -qq ffmpeg
# Test 14: the golden's init.mp4 and its fragments, in its floor playlist's order,
# read as one AV1 track of every frame of the source, with a key frame at each piece
# start of the plan and nowhere else, and decode without an error.
# Test 14: each golden floor's init.mp4 and its fragments, in its floor playlist's
# order, read as one AV1 track of every frame of the source, with a key frame at each
# piece start of the plan and nowhere else, and decode without an error; a ladder
# golden has one floor playlist per floor rung (packaging §7.1), each read so.
- name: The goldens' floors read and decode
shell: bash
working-directory: wai/pack-conformance/packs
run: |
set -euo pipefail
for g in video-base-01 video-staged-01; do
for g in video-base-01 video-staged-01 video-ladder-01 video-cmaf-01 video-floor-only-02; do
( cd "$g/package"
tmp=$(mktemp -d)
cat floor/v/init.mp4 $(grep -v '^#' hls/classic/floor-v.m3u8 | sed 's#^\.\./\.\./##') > "$tmp/floor.mp4"
ffprobe -v error -count_frames -select_streams v:0 -show_entries stream=codec_name,width,height,nb_read_frames -of default=nw=1 "$tmp/floor.mp4" | tee "$tmp/probe.txt"
grep -qx 'codec_name=av1' "$tmp/probe.txt"
grep -qx 'nb_read_frames=200' "$tmp/probe.txt"
keys=$(ffprobe -v error -select_streams v:0 -show_entries packet=pts,flags -of csv=p=0 "$tmp/floor.mp4" | awk -F, '$2 ~ /K/ {print $1}' | tr '\n' ' ')
want=$(tr '\n' ' ' < plan-v.txt)
echo "$g key frames: $keys"
[ "$keys" = "$want" ] || { echo "::error::$g: key frames at $keys; the plan says $want"; exit 1; }
ffmpeg -v error -xerror -i "$tmp/floor.mp4" -f null -
echo "$g: the floor reads as one AV1 track of 200 frames, a key frame at each piece start" )
for pl in hls/classic/floor-*.m3u8; do
f=$(basename "$pl" .m3u8); f=${f#floor-}
tmp=$(mktemp -d)
cat "floor/$f/init.mp4" $(grep -v '^#' "$pl" | sed 's#^\.\./\.\./##') > "$tmp/floor.mp4"
ffprobe -v error -count_frames -select_streams v:0 -show_entries stream=codec_name,width,height,nb_read_frames -of default=nw=1 "$tmp/floor.mp4" | tee "$tmp/probe.txt"
grep -qx 'codec_name=av1' "$tmp/probe.txt"
grep -qx 'nb_read_frames=200' "$tmp/probe.txt"
# A sample's pts is in the track's timescale, not in frames: the packager's
# own floors tick once per frame, a muxer's CMAF floor (video-cmaf-01) 48000
# times. The sample spacing is the second sample's pts less the first's (some
# ffprobe versions report no duration for the first fMP4 sample), every sample
# must sit on that grid, and a duration ffprobe does report must equal it: a gap,
# an uneven duration or a sample out of order is refused here rather than read
# as a moved key frame. A key frame's index is its place on the grid.
keys=$(ffprobe -v error -select_streams v:0 -show_entries packet=pts,duration,flags -of compact=p=0 "$tmp/floor.mp4" \
| awk -F'|' -v what="$g $f" '
{ delete v; for (i = 1; i <= NF; i++) { j = index($i, "="); v[substr($i, 1, j - 1)] = substr($i, j + 1) }
if (v["pts"] !~ /^-?[0-9]+$/) { printf "::error::%s: sample %d has no pts (%s)\n", what, NR - 1, v["pts"] > "/dev/stderr"; bad = 1; exit 1 }
pts[NR - 1] = v["pts"]; dur[NR - 1] = v["duration"]; key[NR - 1] = (v["flags"] ~ /K/) }
END { if (bad) exit 1
n = NR
if (n < 2) { printf "::error::%s: fewer than two samples\n", what > "/dev/stderr"; exit 1 }
p0 = pts[0]; d = pts[1] - p0
if (d <= 0) { printf "::error::%s: the second sample is not after the first (%s, %s)\n", what, p0, pts[1] > "/dev/stderr"; exit 1 }
for (i = 0; i < n; i++) {
if (pts[i] - p0 != i * d) { printf "::error::%s: sample %d is at pts %s, not %d samples of %d ticks after %s\n", what, i, pts[i], i, d, p0 > "/dev/stderr"; exit 1 }
if (dur[i] ~ /^[0-9]+$/ && dur[i] != d) { printf "::error::%s: sample %d lasts %s ticks, not %d\n", what, i, dur[i], d > "/dev/stderr"; exit 1 }
if (key[i]) printf "%d ", i
} }')
want=$(tr '\n' ' ' < plan-v.txt)
echo "$g $f key frames: $keys"
[ "$keys" = "$want" ] || { echo "::error::$g $f: key frames at $keys; the plan says $want"; exit 1; }
ffmpeg -v error -xerror -i "$tmp/floor.mp4" -f null -
echo "$g $f: the floor reads as one AV1 track of 200 frames, a key frame at each piece start"
done )
done
licences:

View file

@ -6,6 +6,179 @@ wire format may change and such changes are recorded here.
## v0.4.0 — current
### GPUs: when `decode-equivalence` may be claimed, and WGSL's integer semantics on every adapter
- **Claiming the tier on a GPU** ([determinism-tiers](extensions/determinism-tiers.md)
§5). A decoder claims `decode-equivalence` for output whose graphs ran on a GPU only
when every shader module that ran them is integer only (no floating-point type, so no
reassociation or fusion can change a result), uses no subgroup or quad operation and
enables no extension, has no result that depends on scheduling (one atomic kind per
word, its result unused, no atomic load or store; no out-of-bounds access), and is
translated with the translator's integer
guards on: signed arithmetic through unsigned, guarded division and remainder, `abs` and
negation of the most negative value. Where the translator does not produce WGSL's
result, the module does not reach the operation: naga 30.0.1 passes shift amounts to
MSL, HLSL and SPIR-V unreduced, a signed left shift as it is, and integer `clamp` as
MSL's and HLSL's `clamp`, so every shift amount is masked below 32, no left shift is of
a signed value, and every `clamp` has literal bounds in order. Before an adapter runs a
graph it passes WGSL's integer semantics vectors and the implementation's probe; the
claim names the adapter and the translator (or, where the backend reports no PCI
identity, the adapter's name and the system's build). The conditions open with a general
form for any accelerator, of which these are the GPU's.
- **WGSL's integer semantics vectors** (`wgsl-conformance/`). Every integer operation a
kernel may use, on `i32`, `u32` and their two-component vectors, at the cases WGSL defines at run
time and MSL, HLSL and SPIR-V leave open, each result written from the WGSL text
(Candidate Recommendation Draft, 21 October 2026). Cases the kernels never reach are
marked `unguarded`: reported, not deciding.
- **`wai-ops-gpu`.** Discovery runs the semantics suite on each adapter after the
arithmetic probe, and refuses an adapter that differs on a guarded case. Every run-time
shift amount in the kernels is now masked (`& 31u`) and the two run-time clamps are
`min(max(…))`; WGSL gives the same result either way, and the translated code is then
defined on every backend. `tests/wgsl_rules.rs` holds every shipped module to the
conditions on naga's IR and in its MSL and HLSL translations (signed arithmetic found by
naga's wrapping, atomic loads and stores refused), with planted violations refused; the
browser page runs the suite through the browser's WGSL compiler and checks the vectors
against the reference compiled to wasm32. Shown in the forge's run of `wai-ops-gpu.yml` on
Metal and on a browser's WebGPU on that GPU: every guarded case equal, every unguarded one
too, and the capability corpora decoding with their graphs on the device to the CPU
decode's bytes; and on Vulkan with an integrated GPU of PCI vendor 0x1002 and llvmpipe on
Linux, the crate's tests with none differing. The tier is claimed on those, each run's
report lines committed in `wai/research/ops-gpu-runs.txt`; adapters run by hand with no
record, and those G1 showed on the kernel text before the masks, are not claimed until a
recorded run.
### Packaging: each step on the fabric that does it with the least energy
- **Steps and fabrics** ([packaging](extensions/packaging.md) §11.6). The computations of
a pack and a verify are named steps (`source-read`, `segment`, `base-search`,
`base-code`, `refine-code`, `sse`, `object-hash`, `digest`, `floor-read`,
`floor-decode`, `index`, `io`, and `source-decode` before a pack), and each may run on a
CPU, a GPU, a media engine or a neural processor (`npu`). Every step is defined in integers (and
AV1 decoding by its decoding process), so where it runs changes no byte of a package
and no verdict: §11.2 holds across fabrics. A packager runs a step on a backend only
after it has given the reference's output on qualifying inputs; a verifier computes a
check on another fabric only where the package states the value it compares with, and
decides any mismatch again on the reference. No hardware encoder computes a WAI step; a
floor encoded on one is a §7.5 floor. A floor states no decoded-output digest, so a
hardware decode never decides a floor verdict.
- **The fabric record** ([jwp-receipts](extensions/jwp-receipts.md) §2.4.8,
[energy-measurement](extensions/energy-measurement.md) §6.3). A measurement claim may
carry `fabrics`: each step with every fabric that ran it and its backend, and the
figure divided into one share per fabric, attributed `task` (the operating system's
account of the work's own energy) or `rail` (the fabric's whole rail, the work its sole
user, read by sampling every user's busy time through the span). A rail shared with
other work is never divided by busy time, and a fabric that ran a step has a share of
more than 0. `fabrics` is the one claim member that is absent rather than null, so every
existing claim and package keeps its bytes; a verifier before this revision refuses a
claim that carries it (`unknown_member`). New reasons: `measurement_fabric_unknown`, `measurement_fabric_order`,
`measurement_fabric_unmetered`, `measurement_fabric_unused`, `measurement_fabric_sum`.
- **wai-pack** places each call of a step on the fabric whose measured cost for its size
is least (`--fabric cpu|gpu|auto:<costs.json>`, `wai-pack fabric list|calibrate`), the
CPU on a tie, where unmeasured, and for every call another fabric does not take. With
feature `gpu`, the motion search, SSE and the object hashes run on a GPU through
**wai-pack-gpu**, integer WGSL kernels through wgpu, shown exact on Metal (Vulkan and
DX12 are built and not run, and nothing is claimed for them). With feature
`fabric-meter` on macOS, `--meter fabric` meters a pack per fabric without privileges
(the task's own and billed CPU energy, and the GPU's whole rail where the pack was its
sole user) and seals an `OnChipCounter` figure with a declared uncertainty and the
claim's fabric record. `wai-pack floor-decode` decodes a
package's floors with libdav1d or the media engine and prints each piece's digest, for
comparing decoders. The Python verifiers stay on the CPU and share no code with wai-rs;
`claim_verify.py` and `pack_verify.py` read the fabric record.
- **Conformance.** Claim vectors of the fabric record appended after the existing ones, which a test
pins by digest. wai-pack-gpu's kernels are held to references transcribed from the text
and every edited kernel is caught; wai-pack's fabric differential packs every golden on
a GPU byte for byte and gives every package and staged mutation the CPU's verdict.
### Packaging: a title's whole ladder in one package
- **Several floor rungs per package** ([packaging](extensions/packaging.md) §7.1). A
component may have any number of floor rungs; each piece then has one floor object per
floor rung, in ladder order, all over one base, so the base of a ladder is coded once.
Each floor rung has a **floor name**: the component's id when it has one floor rung (so
existing packages are unchanged, byte for byte), the rung's id when it has several. The
name names the supplied stream (`<name>.obu`, §7.3), the CMAF files (`floor/<name>/`,
§7.6), the floor playlist (`hls/classic/floor-<name>.m3u8`), the DASH representation
(`<name>-floor`) and the MoQ track (`<name>/floor`); a floor name that cannot be one path
segment, or two equal in any case, is refused (`pack-id`). The classical master lists one
variant per floor rung; with several, `dash/classic.mpd` carries each representation's
codecs and size on the representation. The verifier holds the *k*-th floor entry of each
piece to the *k*-th floor rung.
- **A re-pack from a parent** (§11.5). A packer may take every piece's base and
refinements from an earlier package instead of coding them (`wai-pack pack
--base-from <package>`), so a title's integer base is coded once and taken by every
package made from the same source after it. It refuses a parent that does not verify
(`repack-parent-invalid`), one whose pieces, kinds, rungs, parameters or deadlines are
not this pack's (`repack-parent-mismatch`), and one whose prefixes do not reconstruct
this source with the SSE their entries state (`repack-source-mismatch`). Its receipt
names the parent with parent kind `re-pack`, and its other files are those of a pack
that codes. A verifier holding the parent checks the re-pack against it (`wai-pack
verify --parent`).
- **A floor that is the ladder's own CMAF segments** (§7.7). With
`floor.supplied_form = "cmaf"` (absent, the OBU form; existing policy digests are
unchanged), a supplied floor is an existing ladder's `init.mp4` and media segments, one
segment per piece, read box by box: the floor's temporal units are the samples, each
with a temporal delimiter before it. The package's floor files are the ladder's files,
byte for byte, named by their SHA-256, and the package carries the supplied floor's
listing (`floor.listing`), whose SHA-256 the policy pins, so the receipt binds every
byte of the ladder. A server can hold those files once for the classic site and the
package. New refusals: `floor-cmaf-malformed`, `floor-cmaf-timing`, `floor-cmaf-pieces`.
`wai-pack pack --link-supplied` writes them as hard links to the supplied files.
- **A floor-only profile** (§7.8). A component of `profile = "floor-only"` is its floor
rungs alone: no integer base, no refinement, no source (`policy-floor-only`
otherwise). Its pieces are its first floor rung's media segments (the CMAF form) or
shown key frames (the OBU form), each at most `max_ms` (`floor-piece-length`); each piece
is its floor objects, which present no base and so carry no `derived_from`, and its kind
is `none` (stage index kind 6). It attests delivery: the receipt binds every floor
object and the supplied floor's bytes, and the verifier holds them to the AV1 stream's
structure and the CMAF files; it states no decoded output, no fidelity to a source and
no primary. The stage index now requires a floor's `derived_from` exactly when its piece
has a base (`floor-derived-from`).
- **The independent verifier at scale** (`pack_verify.py`). Each object is hashed once,
and `http_verify.resolve_uri` finds an object by its content id rather than by hashing
every object for every URI. `--jobs N` runs every object's hash and every base's decode
and layers in N worker processes, piece by piece, ahead of checks that are unchanged in
order and reason. `--native-blake3` takes BLAKE3 from the `blake3` module after it
agrees with the pure implementation on the published vectors (opt-in: that module is
the implementation wai-rs links). `--package <dir>` verifies one package without its
sources or its key. **The measurement claim is checked** (§9.4): the claim corpus's
verifier reads it, and it is held to the receipt's figure, class, evidence and signer, so
a correctly metered package passes; `package-mutations/` gains a metered package (`ok`),
a claim about another figure (`measurement-claim-invalid`) and none
(`measurement-claim-missing`).
- **§7.3: key-frame sequence headers** (an informative note). A floor taken from an
existing ladder needs a sequence header in every key-frame unit; a producer that puts
one back must put back the stream's own first sequence header, byte for byte, not the
sample entry's `av1C` header, which can differ in its tool flags and is refused
(`floor-av1-malformed`). `tests/refusals.rs` holds the rule.
- **The DASH renderer** (`wai::http_binding::dash`) writes a representation's own
`@codecs`, `@width` and `@height` when given, and an adaptation set's `@codecs` only when
every representation shares it.
- **A streaming on-demand packer** (§11.4). The packer reads the source twice, a frame
at a time, once to cut it and once to code it, and each floor stream a temporal unit at
a time, and `wai-pack pack` writes each file into its directory as it is made, reading
objects back for the catalogs. What it holds no longer grows with the title, but for a
record per piece and per entry and a byte per frame per floor; a refusal removes what it
wrote. `--jobs <n>` codes n pieces at once, each alone, so the package is the same for
any n. A source that does not read the same twice is refused (`pack-source-changed`).
`tests/pack_alloc.rs` packs a source eight times as long in the same peak memory.
- **Conformance.** `packs/video-ladder-01/` (two floors, one at half size, over
`video-base-01`'s bases, which are the same objects), `ladder-mutations/`,
`packs/video-repack-01/` (the ladder re-packed from `video-base-01`),
`packs/video-cmaf-01/` and `cmaf-mutations/` (the ladder's streams as a muxer's fMP4
segments), `packs/video-floor-only-01/` and `-02/` (both forms, no base), index cases of
a piece of floors alone, `tests/ladder.rs`, `tests/repack.rs`, `tests/cmaf.rs`,
`tests/floor_only.rs`, and the independent
verifier `pack_verify.py`, with a box reader of its own, which re-derives every golden
from its sources and checks the re-pack against its parent. `supplied_floor.py` writes
one stream per floor rung; `supplied_cmaf.py` the CMAF form.
- **What a metered pack's figure brackets, and what a CMAF floor must agree with.** The
meter starts once the policy's own refusals have passed, before the source's first
read, so the figure covers the whole pack: both reads, the floor checks and a parent's
verification (§9.4). A CMAF floor's `av1C` and sample entry must be its sequence
header's, and every sample is a sync sample exactly when its unit starts at a shown key
frame (§7.7, §11.3). A re-pack's verification holds its parent whole (§11.4).
### Hybrid signatures: receipts that stay verifiable after Ed25519 can be forged
- **One suite** ([pq-signatures](extensions/pq-signatures.md) §2): ML-DSA-65 (FIPS 204) beside

View file

@ -146,6 +146,14 @@ the figure with its class. The vectors cover:
- **The labelled delivery leaf:** an `energy` claim against an object whose leaf carries
a class, agreeing, and disagreeing in figure, class or evidence; an `OnChipCounter`
label with no filtering state reads as `Unknown`.
- **The fabric record (§2.4.8 rule 6, energy-measurement §6.3),** appended after every
earlier vector, which a test pins by digest: accepted, a figure divided between the CPU
(`task`) and a GPU (`rail`) over steps that ran on each; at step 2, a record written
`null` (a report without one has no member), a step with a member it does not define,
an empty backend and a share written as a string; at step 4, a fabric and an
attribution outside §6.3, a share divided by GPU time (which names no attribution),
steps out of order, a fabric twice, no step, a step on an unmetered fabric, a share on
a fabric no step ran on, and shares that do not sum to the figure.
## What a party observed of a stage set: `stage` and `delivery-gap`

View file

@ -222,6 +222,13 @@ GAP_REASONS = ("delivery-timeout", "discretion", "not-received") # §2.4.11
BRACKET = ["idle", "busy", "window_us", "completions", "in_flight", "opening"]
SUMMARY = ["n", "mean_uw", "sd_uw", "live_intervals", "longest_live_run"]
BUILD = ["profile", "toolchain", "target"]
# §2.4.8's fabric record (energy-measurement §6.3): the one member of a claim that is absent
# rather than null, so a report sealed before it existed keeps its bytes.
FABRIC_RECORD = ["steps", "shares"]
FABRIC_STEP = ["step", "fabric", "backend"]
FABRIC_SHARE = ["fabric", "joules_micro", "attribution"]
FABRICS = ["cpu", "gpu", "media", "npu"]
ATTRIBUTIONS = ["rail", "task"]
PREDICTION = ["predictor", "descriptor_hash", "predicted_joules_micro"]
# energy-measurement §6.1: profile -> (subject_type, carries several figures, an Ed25519
# key signs the figure, names a group).
@ -404,7 +411,7 @@ def check_body(cls, b):
else:
raise Reject(2, "field_type")
return
members(b, BODY[cls], 2)
members(b, BODY[cls] + (["fabrics"] if cls == "measurement" and "fabrics" in b else []), 2)
if cls == "reconstruct-session":
check_session_body(b)
return
@ -494,6 +501,8 @@ def check_body(cls, b):
need(bd["toolchain"] is None or isinstance(bd["toolchain"], str), 2)
need(bd["target"] is None or is_token(bd["target"]), 2)
need(b["power_reader"] is None or isinstance(b["power_reader"], str), 2)
if "fabrics" in b:
check_fabric_shape(b["fabrics"])
else:
need(is_uri(b["vocabulary"]), 2)
for k in ("op_requested", "op_committed", "op_delivered"):
@ -1421,6 +1430,46 @@ def acquisition(b):
need(u is None and f is None and ref is None, 4, ev)
def check_fabric_shape(f):
"""§2.4.8's fabric record at step 2: an object of `steps` and `shares`, every row of
one an object of its members before any row's values, the terms tokens, a backend a
non-empty string, a share's figure an integer. Never null."""
need(isinstance(f, dict), 2)
members(f, FABRIC_RECORD, 2)
for key, cols in (("steps", FABRIC_STEP), ("shares", FABRIC_SHARE)):
rows = f[key]
need(isinstance(rows, list), 2)
for row in rows:
need(isinstance(row, dict), 2)
members(row, cols, 2)
for row in rows:
if key == "steps":
need(all(isinstance(row[k], str) for k in cols), 2)
need(is_token(row["step"]) and is_token(row["fabric"]) and row["backend"] != "", 2)
else:
need(isinstance(row["fabric"], str) and isinstance(row["attribution"], str), 2)
need(is_token(row["fabric"]) and is_token(row["attribution"]) and is_int(row["joules_micro"]), 2)
def fabric_rules(f, joules):
"""§2.4.8 rule 6: the vocabularies of energy-measurement §6.3, the order (steps by
term then fabric, shares by fabric, each once, neither empty), every fabric a step
names metered (a share of more than 0: 0 J is no reading of work), every share's fabric
running a step, and the shares summing to the figure."""
st, sh = f["steps"], f["shares"]
need(all(s["fabric"] in FABRICS for s in st) and all(s["fabric"] in FABRICS and s["attribution"] in ATTRIBUTIONS for s in sh),
4, "measurement_fabric_unknown")
keys = [(s["step"].encode(), FABRICS.index(s["fabric"])) for s in st]
ranks = [FABRICS.index(s["fabric"]) for s in sh]
need(st and sh and all(a < b for a, b in zip(keys, keys[1:])) and all(a < b for a, b in zip(ranks, ranks[1:])),
4, "measurement_fabric_order")
metered = {s["fabric"] for s in sh if s["joules_micro"] > 0}
ran = {s["fabric"] for s in st}
need(ran <= metered, 4, "measurement_fabric_unmetered")
need({s["fabric"] for s in sh} <= ran, 4, "measurement_fabric_unused")
need(sum(s["joules_micro"] for s in sh) == joules, 4, "measurement_fabric_sum")
def class_rules(c):
"""§3.1 step 4 — §2.4.5-§2.4.7 and §2.6."""
cls, b = c["class"], c["body"]
@ -1446,6 +1495,8 @@ def class_rules(c):
4, "measurement_no_power_reader")
if b["bracket"] is not None:
bracket_rules(b["bracket"], b["joules_micro"], b["energy_provenance"], b["energy_uncertainty"])
if "fabrics" in b:
fabric_rules(b["fabrics"], b["joules_micro"])
elif cls == "operating-point":
figure_rules(c)
pts = [b[k] for k in ("op_requested", "op_committed", "op_delivered")]

View file

@ -24416,6 +24416,241 @@
"step": 6,
"reason": "context_mismatch"
}
},
{
"name": "measurement_fabrics_accept",
"about": "an OnChipCounter figure of 9,000 uJ, declared 5 % over 1.2 s, divided by fabric: the motion search ran on the CPU and on a GPU, the base's coding on the CPU, the object hashes on the GPU; the CPU's share is the task's own and the GPU's its whole rail, the work its sole user, and the shares sum to the figure",
"procedure": "claim",
"receipt": "{\"body\":{\"bracket\":null,\"build\":{\"profile\":\"release\",\"target\":\"x86_64-unknown-linux-gnu\",\"toolchain\":\"rustc 1.98.0 (example)\"},\"energy_calibration_ref\":null,\"energy_counter_filtering\":\"Unknown\",\"energy_provenance\":\"OnChipCounter\",\"energy_uncertainty\":{\"relative_ppm\":50000,\"window_us\":1200000},\"fabrics\":{\"shares\":[{\"attribution\":\"task\",\"fabric\":\"cpu\",\"joules_micro\":6500},{\"attribution\":\"rail\",\"fabric\":\"gpu\",\"joules_micro\":2500}],\"steps\":[{\"backend\":\"claim-conformance: a cpu backend\",\"fabric\":\"cpu\",\"step\":\"base-code\"},{\"backend\":\"claim-conformance: a cpu backend\",\"fabric\":\"cpu\",\"step\":\"base-search\"},{\"backend\":\"claim-conformance: a gpu backend\",\"fabric\":\"gpu\",\"step\":\"base-search\"},{\"backend\":\"claim-conformance: a gpu backend\",\"fabric\":\"gpu\",\"step\":\"object-hash\"}]},\"figure_index\":null,\"figure_profile\":\"moq-jwp:claim-link\",\"group\":null,\"joules_micro\":9000,\"power_reader\":\"reader:example\"},\"class\":\"measurement\",\"issued_at\":\"2026-09-27T12:00:00Z\",\"kind\":\"claim\",\"parent_receipt_hash\":null,\"seq\":1,\"sig\":\"d563add9d03cf635943255656c0a19d0dc0a7763997ae7bdd654721086166254aefeb13a238cde962e52af288534bb1f3ba73e87431fd2b64c384371c1240201\",\"signer_id\":\"did:example:meter\",\"signer_pubkey\":\"a09aa5f47a6759802ff955f8dc2d2a14a5c99d23be97f864127ff9383455a4f0\",\"subject\":\"c75b47e8b64ba4138d15c07e59dc1e7a710397dc5100392ec351641ae96835dd\",\"subject_type\":\"receipt\"}",
"context": {
"figure": {
"claim": "{\"body\":{\"coverage\":\"Whole\",\"energy_calibration_ref\":null,\"energy_counter_filtering\":\"Unknown\",\"energy_provenance\":\"OnChipCounter\",\"energy_uncertainty\":{\"relative_ppm\":50000,\"window_us\":1200000},\"grade\":\"measured\",\"joules_micro\":9000,\"method\":\"https://transaction.science/wai/extensions/energy-measurement\",\"oer_receipt\":null,\"work_unit\":\"subpixel\",\"work_units\":49152},\"class\":\"energy\",\"issued_at\":\"2026-09-27T12:00:00Z\",\"kind\":\"claim\",\"parent_receipt_hash\":null,\"seq\":0,\"sig\":\"c0056b86a1e042b82ea6172315eb864f9cfb84ff0be9862f160042271046aaa77809515ca814e6ece9d8ba74337aa3d16dc11c9341b1532d4ad653cc7018220a\",\"signer_id\":\"did:example:meter\",\"signer_pubkey\":\"a09aa5f47a6759802ff955f8dc2d2a14a5c99d23be97f864127ff9383455a4f0\",\"subject\":\"5bb20a10b980be8c6d95915394f6e89cd49c16d0f5e94cd87c0ec6ce37bcfc5e\",\"subject_type\":\"object\"}"
}
},
"expected": {
"outcome": "accept",
"link_hash": "1fd781c0116f36c64e0f262e481c563394eee79ba9bf7db66ba8d8b401ab811f"
}
},
{
"name": "measurement_fabrics_null",
"about": "a fabric record written null: a report without one has no member, so it has one canonical form",
"procedure": "claim",
"receipt": "{\"body\":{\"bracket\":null,\"build\":{\"profile\":\"release\",\"target\":\"x86_64-unknown-linux-gnu\",\"toolchain\":\"rustc 1.98.0 (example)\"},\"energy_calibration_ref\":null,\"energy_counter_filtering\":\"Unknown\",\"energy_provenance\":\"OnChipCounter\",\"energy_uncertainty\":{\"relative_ppm\":50000,\"window_us\":1200000},\"fabrics\":null,\"figure_index\":null,\"figure_profile\":\"moq-jwp:claim-link\",\"group\":null,\"joules_micro\":9000,\"power_reader\":\"reader:example\"},\"class\":\"measurement\",\"issued_at\":\"2026-09-27T12:00:00Z\",\"kind\":\"claim\",\"parent_receipt_hash\":null,\"seq\":1,\"sig\":\"00c2f4afe0fc0c8431b7e4e1cdccd836731ff4cb4a331ff2405e4208a11e3d01af168dce67d42acbd14cd2995894488f29ed35a659fdf77df756e088bcbbe60a\",\"signer_id\":\"did:example:meter\",\"signer_pubkey\":\"a09aa5f47a6759802ff955f8dc2d2a14a5c99d23be97f864127ff9383455a4f0\",\"subject\":\"c75b47e8b64ba4138d15c07e59dc1e7a710397dc5100392ec351641ae96835dd\",\"subject_type\":\"receipt\"}",
"expected": {
"outcome": "reject",
"step": 2,
"reason": "field_type"
}
},
{
"name": "measurement_fabric_step_unknown_member",
"about": "a step carrying its work count: a step is its term, fabric and backend",
"procedure": "claim",
"receipt": "{\"body\":{\"bracket\":null,\"build\":{\"profile\":\"release\",\"target\":\"x86_64-unknown-linux-gnu\",\"toolchain\":\"rustc 1.98.0 (example)\"},\"energy_calibration_ref\":null,\"energy_counter_filtering\":\"Unknown\",\"energy_provenance\":\"OnChipCounter\",\"energy_uncertainty\":{\"relative_ppm\":50000,\"window_us\":1200000},\"fabrics\":{\"shares\":[{\"attribution\":\"task\",\"fabric\":\"cpu\",\"joules_micro\":6500},{\"attribution\":\"rail\",\"fabric\":\"gpu\",\"joules_micro\":2500}],\"steps\":[{\"backend\":\"claim-conformance: a cpu backend\",\"fabric\":\"cpu\",\"step\":\"base-code\",\"units\":48},{\"backend\":\"claim-conformance: a cpu backend\",\"fabric\":\"cpu\",\"step\":\"base-search\"},{\"backend\":\"claim-conformance: a gpu backend\",\"fabric\":\"gpu\",\"step\":\"base-search\"},{\"backend\":\"claim-conformance: a gpu backend\",\"fabric\":\"gpu\",\"step\":\"object-hash\"}]},\"figure_index\":null,\"figure_profile\":\"moq-jwp:claim-link\",\"group\":null,\"joules_micro\":9000,\"power_reader\":\"reader:example\"},\"class\":\"measurement\",\"issued_at\":\"2026-09-27T12:00:00Z\",\"kind\":\"claim\",\"parent_receipt_hash\":null,\"seq\":1,\"sig\":\"483cb47a9ac2d5a10e98c5bbefed416e08f00b4f1db0fdc61bbc7159d1342a1d75ebdac91ecd67433c9388845694289b3fdccb0e6e230a68abf98377181b0e0d\",\"signer_id\":\"did:example:meter\",\"signer_pubkey\":\"a09aa5f47a6759802ff955f8dc2d2a14a5c99d23be97f864127ff9383455a4f0\",\"subject\":\"c75b47e8b64ba4138d15c07e59dc1e7a710397dc5100392ec351641ae96835dd\",\"subject_type\":\"receipt\"}",
"expected": {
"outcome": "reject",
"step": 2,
"reason": "unknown_member"
}
},
{
"name": "measurement_fabric_backend_empty",
"about": "a step whose backend is the empty string",
"procedure": "claim",
"receipt": "{\"body\":{\"bracket\":null,\"build\":{\"profile\":\"release\",\"target\":\"x86_64-unknown-linux-gnu\",\"toolchain\":\"rustc 1.98.0 (example)\"},\"energy_calibration_ref\":null,\"energy_counter_filtering\":\"Unknown\",\"energy_provenance\":\"OnChipCounter\",\"energy_uncertainty\":{\"relative_ppm\":50000,\"window_us\":1200000},\"fabrics\":{\"shares\":[{\"attribution\":\"task\",\"fabric\":\"cpu\",\"joules_micro\":6500},{\"attribution\":\"rail\",\"fabric\":\"gpu\",\"joules_micro\":2500}],\"steps\":[{\"backend\":\"claim-conformance: a cpu backend\",\"fabric\":\"cpu\",\"step\":\"base-code\"},{\"backend\":\"\",\"fabric\":\"cpu\",\"step\":\"base-search\"},{\"backend\":\"claim-conformance: a gpu backend\",\"fabric\":\"gpu\",\"step\":\"base-search\"},{\"backend\":\"claim-conformance: a gpu backend\",\"fabric\":\"gpu\",\"step\":\"object-hash\"}]},\"figure_index\":null,\"figure_profile\":\"moq-jwp:claim-link\",\"group\":null,\"joules_micro\":9000,\"power_reader\":\"reader:example\"},\"class\":\"measurement\",\"issued_at\":\"2026-09-27T12:00:00Z\",\"kind\":\"claim\",\"parent_receipt_hash\":null,\"seq\":1,\"sig\":\"0a7b70e0b6f4296e25f6a820cc80e185bc042223065900d2a7ba693682af9a6c0ea3ca240e7b6e8d26bad4e91dc3e66b21d05127e1964e71cbc1c4519920b301\",\"signer_id\":\"did:example:meter\",\"signer_pubkey\":\"a09aa5f47a6759802ff955f8dc2d2a14a5c99d23be97f864127ff9383455a4f0\",\"subject\":\"c75b47e8b64ba4138d15c07e59dc1e7a710397dc5100392ec351641ae96835dd\",\"subject_type\":\"receipt\"}",
"expected": {
"outcome": "reject",
"step": 2,
"reason": "field_type"
}
},
{
"name": "measurement_fabric_share_not_integer",
"about": "a share written as a string",
"procedure": "claim",
"receipt": "{\"body\":{\"bracket\":null,\"build\":{\"profile\":\"release\",\"target\":\"x86_64-unknown-linux-gnu\",\"toolchain\":\"rustc 1.98.0 (example)\"},\"energy_calibration_ref\":null,\"energy_counter_filtering\":\"Unknown\",\"energy_provenance\":\"OnChipCounter\",\"energy_uncertainty\":{\"relative_ppm\":50000,\"window_us\":1200000},\"fabrics\":{\"shares\":[{\"attribution\":\"task\",\"fabric\":\"cpu\",\"joules_micro\":\"6500\"},{\"attribution\":\"rail\",\"fabric\":\"gpu\",\"joules_micro\":2500}],\"steps\":[{\"backend\":\"claim-conformance: a cpu backend\",\"fabric\":\"cpu\",\"step\":\"base-code\"},{\"backend\":\"claim-conformance: a cpu backend\",\"fabric\":\"cpu\",\"step\":\"base-search\"},{\"backend\":\"claim-conformance: a gpu backend\",\"fabric\":\"gpu\",\"step\":\"base-search\"},{\"backend\":\"claim-conformance: a gpu backend\",\"fabric\":\"gpu\",\"step\":\"object-hash\"}]},\"figure_index\":null,\"figure_profile\":\"moq-jwp:claim-link\",\"group\":null,\"joules_micro\":9000,\"power_reader\":\"reader:example\"},\"class\":\"measurement\",\"issued_at\":\"2026-09-27T12:00:00Z\",\"kind\":\"claim\",\"parent_receipt_hash\":null,\"seq\":1,\"sig\":\"35e8050b3113c9afb459d8becf89cc6d45a542d11e98ea3a3bd345edcc3cc84f24cdefe007287bb2e4c0bc611d107ad9d370240fc52fb488311c43173b06c800\",\"signer_id\":\"did:example:meter\",\"signer_pubkey\":\"a09aa5f47a6759802ff955f8dc2d2a14a5c99d23be97f864127ff9383455a4f0\",\"subject\":\"c75b47e8b64ba4138d15c07e59dc1e7a710397dc5100392ec351641ae96835dd\",\"subject_type\":\"receipt\"}",
"expected": {
"outcome": "reject",
"step": 2,
"reason": "field_type"
}
},
{
"name": "measurement_fabric_unknown",
"about": "a share on a fabric energy-measurement 6.3 does not name",
"procedure": "claim",
"receipt": "{\"body\":{\"bracket\":null,\"build\":{\"profile\":\"release\",\"target\":\"x86_64-unknown-linux-gnu\",\"toolchain\":\"rustc 1.98.0 (example)\"},\"energy_calibration_ref\":null,\"energy_counter_filtering\":\"Unknown\",\"energy_provenance\":\"OnChipCounter\",\"energy_uncertainty\":{\"relative_ppm\":50000,\"window_us\":1200000},\"fabrics\":{\"shares\":[{\"attribution\":\"task\",\"fabric\":\"cpu\",\"joules_micro\":6500},{\"attribution\":\"rail\",\"fabric\":\"fpga\",\"joules_micro\":2500}],\"steps\":[{\"backend\":\"claim-conformance: a cpu backend\",\"fabric\":\"cpu\",\"step\":\"base-code\"},{\"backend\":\"claim-conformance: a cpu backend\",\"fabric\":\"cpu\",\"step\":\"base-search\"},{\"backend\":\"claim-conformance: a gpu backend\",\"fabric\":\"gpu\",\"step\":\"base-search\"},{\"backend\":\"claim-conformance: a gpu backend\",\"fabric\":\"gpu\",\"step\":\"object-hash\"}]},\"figure_index\":null,\"figure_profile\":\"moq-jwp:claim-link\",\"group\":null,\"joules_micro\":9000,\"power_reader\":\"reader:example\"},\"class\":\"measurement\",\"issued_at\":\"2026-09-27T12:00:00Z\",\"kind\":\"claim\",\"parent_receipt_hash\":null,\"seq\":1,\"sig\":\"2fb83853cfa5029129afc3fc28841a4087604634388f0aa9984041d063040d51ef2b037e7ed4921b9664aea2cf49b5d18585c91a92a6237355a5841f1240b306\",\"signer_id\":\"did:example:meter\",\"signer_pubkey\":\"a09aa5f47a6759802ff955f8dc2d2a14a5c99d23be97f864127ff9383455a4f0\",\"subject\":\"c75b47e8b64ba4138d15c07e59dc1e7a710397dc5100392ec351641ae96835dd\",\"subject_type\":\"receipt\"}",
"expected": {
"outcome": "reject",
"step": 4,
"reason": "measurement_fabric_unknown"
}
},
{
"name": "measurement_fabric_attribution_unknown",
"about": "a share attributed by a method energy-measurement 6.3 does not name",
"procedure": "claim",
"receipt": "{\"body\":{\"bracket\":null,\"build\":{\"profile\":\"release\",\"target\":\"x86_64-unknown-linux-gnu\",\"toolchain\":\"rustc 1.98.0 (example)\"},\"energy_calibration_ref\":null,\"energy_counter_filtering\":\"Unknown\",\"energy_provenance\":\"OnChipCounter\",\"energy_uncertainty\":{\"relative_ppm\":50000,\"window_us\":1200000},\"fabrics\":{\"shares\":[{\"attribution\":\"task\",\"fabric\":\"cpu\",\"joules_micro\":6500},{\"attribution\":\"estimate\",\"fabric\":\"gpu\",\"joules_micro\":2500}],\"steps\":[{\"backend\":\"claim-conformance: a cpu backend\",\"fabric\":\"cpu\",\"step\":\"base-code\"},{\"backend\":\"claim-conformance: a cpu backend\",\"fabric\":\"cpu\",\"step\":\"base-search\"},{\"backend\":\"claim-conformance: a gpu backend\",\"fabric\":\"gpu\",\"step\":\"base-search\"},{\"backend\":\"claim-conformance: a gpu backend\",\"fabric\":\"gpu\",\"step\":\"object-hash\"}]},\"figure_index\":null,\"figure_profile\":\"moq-jwp:claim-link\",\"group\":null,\"joules_micro\":9000,\"power_reader\":\"reader:example\"},\"class\":\"measurement\",\"issued_at\":\"2026-09-27T12:00:00Z\",\"kind\":\"claim\",\"parent_receipt_hash\":null,\"seq\":1,\"sig\":\"1423300528ef4fc9dae5cec7259f49bfa5c0a12e9732598038b62d0e2f25795bdc5d97c1f199a5ffe9b9b3eba3968722db6a3fdc8064e9b2371812ed37ed2c08\",\"signer_id\":\"did:example:meter\",\"signer_pubkey\":\"a09aa5f47a6759802ff955f8dc2d2a14a5c99d23be97f864127ff9383455a4f0\",\"subject\":\"c75b47e8b64ba4138d15c07e59dc1e7a710397dc5100392ec351641ae96835dd\",\"subject_type\":\"receipt\"}",
"expected": {
"outcome": "reject",
"step": 4,
"reason": "measurement_fabric_unknown"
}
},
{
"name": "measurement_fabric_time_share",
"about": "a shared GPU rail divided by its users' GPU time: busy time does not apportion energy, so energy-measurement 6.3 names no such attribution",
"procedure": "claim",
"receipt": "{\"body\":{\"bracket\":null,\"build\":{\"profile\":\"release\",\"target\":\"x86_64-unknown-linux-gnu\",\"toolchain\":\"rustc 1.98.0 (example)\"},\"energy_calibration_ref\":null,\"energy_counter_filtering\":\"Unknown\",\"energy_provenance\":\"OnChipCounter\",\"energy_uncertainty\":{\"relative_ppm\":50000,\"window_us\":1200000},\"fabrics\":{\"shares\":[{\"attribution\":\"task\",\"fabric\":\"cpu\",\"joules_micro\":6500},{\"attribution\":\"time-share\",\"fabric\":\"gpu\",\"joules_micro\":2500}],\"steps\":[{\"backend\":\"claim-conformance: a cpu backend\",\"fabric\":\"cpu\",\"step\":\"base-code\"},{\"backend\":\"claim-conformance: a cpu backend\",\"fabric\":\"cpu\",\"step\":\"base-search\"},{\"backend\":\"claim-conformance: a gpu backend\",\"fabric\":\"gpu\",\"step\":\"base-search\"},{\"backend\":\"claim-conformance: a gpu backend\",\"fabric\":\"gpu\",\"step\":\"object-hash\"}]},\"figure_index\":null,\"figure_profile\":\"moq-jwp:claim-link\",\"group\":null,\"joules_micro\":9000,\"power_reader\":\"reader:example\"},\"class\":\"measurement\",\"issued_at\":\"2026-09-27T12:00:00Z\",\"kind\":\"claim\",\"parent_receipt_hash\":null,\"seq\":1,\"sig\":\"9a7cb5dab16431b800c127c9d705a4adb7aac0de8c8c2f8a8d48e6263e2b20141bb8b66e0f18d8c0a010044d53ef0abd9772f97fae398ee9fbfb747688a44304\",\"signer_id\":\"did:example:meter\",\"signer_pubkey\":\"a09aa5f47a6759802ff955f8dc2d2a14a5c99d23be97f864127ff9383455a4f0\",\"subject\":\"c75b47e8b64ba4138d15c07e59dc1e7a710397dc5100392ec351641ae96835dd\",\"subject_type\":\"receipt\"}",
"expected": {
"outcome": "reject",
"step": 4,
"reason": "measurement_fabric_unknown"
}
},
{
"name": "measurement_fabric_steps_out_of_order",
"about": "the motion search listed before the base's coding: steps are in byte order of their terms",
"procedure": "claim",
"receipt": "{\"body\":{\"bracket\":null,\"build\":{\"profile\":\"release\",\"target\":\"x86_64-unknown-linux-gnu\",\"toolchain\":\"rustc 1.98.0 (example)\"},\"energy_calibration_ref\":null,\"energy_counter_filtering\":\"Unknown\",\"energy_provenance\":\"OnChipCounter\",\"energy_uncertainty\":{\"relative_ppm\":50000,\"window_us\":1200000},\"fabrics\":{\"shares\":[{\"attribution\":\"task\",\"fabric\":\"cpu\",\"joules_micro\":6500},{\"attribution\":\"rail\",\"fabric\":\"gpu\",\"joules_micro\":2500}],\"steps\":[{\"backend\":\"claim-conformance: a cpu backend\",\"fabric\":\"cpu\",\"step\":\"base-search\"},{\"backend\":\"claim-conformance: a cpu backend\",\"fabric\":\"cpu\",\"step\":\"base-code\"},{\"backend\":\"claim-conformance: a gpu backend\",\"fabric\":\"gpu\",\"step\":\"base-search\"},{\"backend\":\"claim-conformance: a gpu backend\",\"fabric\":\"gpu\",\"step\":\"object-hash\"}]},\"figure_index\":null,\"figure_profile\":\"moq-jwp:claim-link\",\"group\":null,\"joules_micro\":9000,\"power_reader\":\"reader:example\"},\"class\":\"measurement\",\"issued_at\":\"2026-09-27T12:00:00Z\",\"kind\":\"claim\",\"parent_receipt_hash\":null,\"seq\":1,\"sig\":\"20f9687c74c6d1c5dc09606d2b4b55934d396645ce4087ccd630d3d13f3d6793b86ba10ee3b8647589991f666863dfb65f99d429a8be512d3e08a8a4c213a10f\",\"signer_id\":\"did:example:meter\",\"signer_pubkey\":\"a09aa5f47a6759802ff955f8dc2d2a14a5c99d23be97f864127ff9383455a4f0\",\"subject\":\"c75b47e8b64ba4138d15c07e59dc1e7a710397dc5100392ec351641ae96835dd\",\"subject_type\":\"receipt\"}",
"expected": {
"outcome": "reject",
"step": 4,
"reason": "measurement_fabric_order"
}
},
{
"name": "measurement_fabric_share_twice",
"about": "two shares on the CPU: a fabric has one share",
"procedure": "claim",
"receipt": "{\"body\":{\"bracket\":null,\"build\":{\"profile\":\"release\",\"target\":\"x86_64-unknown-linux-gnu\",\"toolchain\":\"rustc 1.98.0 (example)\"},\"energy_calibration_ref\":null,\"energy_counter_filtering\":\"Unknown\",\"energy_provenance\":\"OnChipCounter\",\"energy_uncertainty\":{\"relative_ppm\":50000,\"window_us\":1200000},\"fabrics\":{\"shares\":[{\"attribution\":\"task\",\"fabric\":\"cpu\",\"joules_micro\":6500},{\"attribution\":\"task\",\"fabric\":\"cpu\",\"joules_micro\":2500}],\"steps\":[{\"backend\":\"claim-conformance: a cpu backend\",\"fabric\":\"cpu\",\"step\":\"base-code\"}]},\"figure_index\":null,\"figure_profile\":\"moq-jwp:claim-link\",\"group\":null,\"joules_micro\":9000,\"power_reader\":\"reader:example\"},\"class\":\"measurement\",\"issued_at\":\"2026-09-27T12:00:00Z\",\"kind\":\"claim\",\"parent_receipt_hash\":null,\"seq\":1,\"sig\":\"1f7fe306ff1e650138a7ee6fb054b73d4fb9f2c85094eaf73b75df56407c065b0be43d210b3f70b12cef7da6ef9c3b5288045ac040ba982b05b308fada97a40e\",\"signer_id\":\"did:example:meter\",\"signer_pubkey\":\"a09aa5f47a6759802ff955f8dc2d2a14a5c99d23be97f864127ff9383455a4f0\",\"subject\":\"c75b47e8b64ba4138d15c07e59dc1e7a710397dc5100392ec351641ae96835dd\",\"subject_type\":\"receipt\"}",
"expected": {
"outcome": "reject",
"step": 4,
"reason": "measurement_fabric_order"
}
},
{
"name": "measurement_fabric_no_step",
"about": "shares with no step: a record says where the work ran",
"procedure": "claim",
"receipt": "{\"body\":{\"bracket\":null,\"build\":{\"profile\":\"release\",\"target\":\"x86_64-unknown-linux-gnu\",\"toolchain\":\"rustc 1.98.0 (example)\"},\"energy_calibration_ref\":null,\"energy_counter_filtering\":\"Unknown\",\"energy_provenance\":\"OnChipCounter\",\"energy_uncertainty\":{\"relative_ppm\":50000,\"window_us\":1200000},\"fabrics\":{\"shares\":[{\"attribution\":\"task\",\"fabric\":\"cpu\",\"joules_micro\":6500},{\"attribution\":\"rail\",\"fabric\":\"gpu\",\"joules_micro\":2500}],\"steps\":[]},\"figure_index\":null,\"figure_profile\":\"moq-jwp:claim-link\",\"group\":null,\"joules_micro\":9000,\"power_reader\":\"reader:example\"},\"class\":\"measurement\",\"issued_at\":\"2026-09-27T12:00:00Z\",\"kind\":\"claim\",\"parent_receipt_hash\":null,\"seq\":1,\"sig\":\"fcbfa43728338659ae17f72f6504a7c66beb0f7a16ded7d54cdae225dc5bf60ad8fdeed0d68e1b5bc54b9f87b806b466397be042cf2e99acf8b72fe955716101\",\"signer_id\":\"did:example:meter\",\"signer_pubkey\":\"a09aa5f47a6759802ff955f8dc2d2a14a5c99d23be97f864127ff9383455a4f0\",\"subject\":\"c75b47e8b64ba4138d15c07e59dc1e7a710397dc5100392ec351641ae96835dd\",\"subject_type\":\"receipt\"}",
"expected": {
"outcome": "reject",
"step": 4,
"reason": "measurement_fabric_order"
}
},
{
"name": "measurement_fabric_unmetered",
"about": "a step on the GPU with a share on the CPU alone: a fabric that ran work has a share",
"procedure": "claim",
"receipt": "{\"body\":{\"bracket\":null,\"build\":{\"profile\":\"release\",\"target\":\"x86_64-unknown-linux-gnu\",\"toolchain\":\"rustc 1.98.0 (example)\"},\"energy_calibration_ref\":null,\"energy_counter_filtering\":\"Unknown\",\"energy_provenance\":\"OnChipCounter\",\"energy_uncertainty\":{\"relative_ppm\":50000,\"window_us\":1200000},\"fabrics\":{\"shares\":[{\"attribution\":\"task\",\"fabric\":\"cpu\",\"joules_micro\":9000}],\"steps\":[{\"backend\":\"claim-conformance: a cpu backend\",\"fabric\":\"cpu\",\"step\":\"base-code\"},{\"backend\":\"claim-conformance: a cpu backend\",\"fabric\":\"cpu\",\"step\":\"base-search\"},{\"backend\":\"claim-conformance: a gpu backend\",\"fabric\":\"gpu\",\"step\":\"base-search\"},{\"backend\":\"claim-conformance: a gpu backend\",\"fabric\":\"gpu\",\"step\":\"object-hash\"}]},\"figure_index\":null,\"figure_profile\":\"moq-jwp:claim-link\",\"group\":null,\"joules_micro\":9000,\"power_reader\":\"reader:example\"},\"class\":\"measurement\",\"issued_at\":\"2026-09-27T12:00:00Z\",\"kind\":\"claim\",\"parent_receipt_hash\":null,\"seq\":1,\"sig\":\"e80d06b9530fabbc029511d67d81fa6ae40b0efbc4fa2cab10f3dae10c44b61a854d8bf31de038524c52f27c91d80ed4aed177b15af4786ee022b3e3183be202\",\"signer_id\":\"did:example:meter\",\"signer_pubkey\":\"a09aa5f47a6759802ff955f8dc2d2a14a5c99d23be97f864127ff9383455a4f0\",\"subject\":\"c75b47e8b64ba4138d15c07e59dc1e7a710397dc5100392ec351641ae96835dd\",\"subject_type\":\"receipt\"}",
"expected": {
"outcome": "reject",
"step": 4,
"reason": "measurement_fabric_unmetered"
}
},
{
"name": "measurement_fabric_unused",
"about": "a share on the GPU while every step ran on the CPU",
"procedure": "claim",
"receipt": "{\"body\":{\"bracket\":null,\"build\":{\"profile\":\"release\",\"target\":\"x86_64-unknown-linux-gnu\",\"toolchain\":\"rustc 1.98.0 (example)\"},\"energy_calibration_ref\":null,\"energy_counter_filtering\":\"Unknown\",\"energy_provenance\":\"OnChipCounter\",\"energy_uncertainty\":{\"relative_ppm\":50000,\"window_us\":1200000},\"fabrics\":{\"shares\":[{\"attribution\":\"task\",\"fabric\":\"cpu\",\"joules_micro\":6500},{\"attribution\":\"rail\",\"fabric\":\"gpu\",\"joules_micro\":2500}],\"steps\":[{\"backend\":\"claim-conformance: a cpu backend\",\"fabric\":\"cpu\",\"step\":\"base-code\"},{\"backend\":\"claim-conformance: a cpu backend\",\"fabric\":\"cpu\",\"step\":\"base-search\"}]},\"figure_index\":null,\"figure_profile\":\"moq-jwp:claim-link\",\"group\":null,\"joules_micro\":9000,\"power_reader\":\"reader:example\"},\"class\":\"measurement\",\"issued_at\":\"2026-09-27T12:00:00Z\",\"kind\":\"claim\",\"parent_receipt_hash\":null,\"seq\":1,\"sig\":\"840f781fc3e916ca96f69d70622b44042aac6e12d5f249fc7180a450d0407a677d0bdff29ffdd5a8ed2de7958cbc602b381193e4c37a472df2c0da691a800c0a\",\"signer_id\":\"did:example:meter\",\"signer_pubkey\":\"a09aa5f47a6759802ff955f8dc2d2a14a5c99d23be97f864127ff9383455a4f0\",\"subject\":\"c75b47e8b64ba4138d15c07e59dc1e7a710397dc5100392ec351641ae96835dd\",\"subject_type\":\"receipt\"}",
"expected": {
"outcome": "reject",
"step": 4,
"reason": "measurement_fabric_unused"
}
},
{
"name": "measurement_fabric_sum",
"about": "shares of 6,500 and 2,499 uJ under a figure of 9,000: the shares divide the figure",
"procedure": "claim",
"receipt": "{\"body\":{\"bracket\":null,\"build\":{\"profile\":\"release\",\"target\":\"x86_64-unknown-linux-gnu\",\"toolchain\":\"rustc 1.98.0 (example)\"},\"energy_calibration_ref\":null,\"energy_counter_filtering\":\"Unknown\",\"energy_provenance\":\"OnChipCounter\",\"energy_uncertainty\":{\"relative_ppm\":50000,\"window_us\":1200000},\"fabrics\":{\"shares\":[{\"attribution\":\"task\",\"fabric\":\"cpu\",\"joules_micro\":6500},{\"attribution\":\"rail\",\"fabric\":\"gpu\",\"joules_micro\":2499}],\"steps\":[{\"backend\":\"claim-conformance: a cpu backend\",\"fabric\":\"cpu\",\"step\":\"base-code\"},{\"backend\":\"claim-conformance: a cpu backend\",\"fabric\":\"cpu\",\"step\":\"base-search\"},{\"backend\":\"claim-conformance: a gpu backend\",\"fabric\":\"gpu\",\"step\":\"base-search\"},{\"backend\":\"claim-conformance: a gpu backend\",\"fabric\":\"gpu\",\"step\":\"object-hash\"}]},\"figure_index\":null,\"figure_profile\":\"moq-jwp:claim-link\",\"group\":null,\"joules_micro\":9000,\"power_reader\":\"reader:example\"},\"class\":\"measurement\",\"issued_at\":\"2026-09-27T12:00:00Z\",\"kind\":\"claim\",\"parent_receipt_hash\":null,\"seq\":1,\"sig\":\"021a0adfef8e0c31ed5bb725de1b9468a96e55a469971ebcb874d1691b194b7c8f8d2781567ec247187d682f2dc40a2b8cbd2a8eefe8a5ea42b61da5977d4a03\",\"signer_id\":\"did:example:meter\",\"signer_pubkey\":\"a09aa5f47a6759802ff955f8dc2d2a14a5c99d23be97f864127ff9383455a4f0\",\"subject\":\"c75b47e8b64ba4138d15c07e59dc1e7a710397dc5100392ec351641ae96835dd\",\"subject_type\":\"receipt\"}",
"expected": {
"outcome": "reject",
"step": 4,
"reason": "measurement_fabric_sum"
}
},
{
"name": "measurement_fabric_share_zero",
"about": "steps on the GPU with a GPU share of 0 and the CPU's the whole figure: 0 J is no reading of work, so the GPU is unmetered",
"procedure": "claim",
"receipt": "{\"body\":{\"bracket\":null,\"build\":{\"profile\":\"release\",\"target\":\"x86_64-unknown-linux-gnu\",\"toolchain\":\"rustc 1.98.0 (example)\"},\"energy_calibration_ref\":null,\"energy_counter_filtering\":\"Unknown\",\"energy_provenance\":\"OnChipCounter\",\"energy_uncertainty\":{\"relative_ppm\":50000,\"window_us\":1200000},\"fabrics\":{\"shares\":[{\"attribution\":\"task\",\"fabric\":\"cpu\",\"joules_micro\":9000},{\"attribution\":\"rail\",\"fabric\":\"gpu\",\"joules_micro\":0}],\"steps\":[{\"backend\":\"claim-conformance: a cpu backend\",\"fabric\":\"cpu\",\"step\":\"base-code\"},{\"backend\":\"claim-conformance: a cpu backend\",\"fabric\":\"cpu\",\"step\":\"base-search\"},{\"backend\":\"claim-conformance: a gpu backend\",\"fabric\":\"gpu\",\"step\":\"base-search\"},{\"backend\":\"claim-conformance: a gpu backend\",\"fabric\":\"gpu\",\"step\":\"object-hash\"}]},\"figure_index\":null,\"figure_profile\":\"moq-jwp:claim-link\",\"group\":null,\"joules_micro\":9000,\"power_reader\":\"reader:example\"},\"class\":\"measurement\",\"issued_at\":\"2026-09-27T12:00:00Z\",\"kind\":\"claim\",\"parent_receipt_hash\":null,\"seq\":1,\"sig\":\"40c183a89a5c1c779452f91941c70398b2d247507be988deec6f44449366667d77f0866dab12bc7a31b3c59a75aad8accec26dd69be7bbeb9d2f04a9b6792b0a\",\"signer_id\":\"did:example:meter\",\"signer_pubkey\":\"a09aa5f47a6759802ff955f8dc2d2a14a5c99d23be97f864127ff9383455a4f0\",\"subject\":\"c75b47e8b64ba4138d15c07e59dc1e7a710397dc5100392ec351641ae96835dd\",\"subject_type\":\"receipt\"}",
"expected": {
"outcome": "reject",
"step": 4,
"reason": "measurement_fabric_unmetered"
}
},
{
"name": "measurement_fabric_step_fabric_unknown",
"about": "a step on a fabric energy-measurement 6.3 does not name",
"procedure": "claim",
"receipt": "{\"body\":{\"bracket\":null,\"build\":{\"profile\":\"release\",\"target\":\"x86_64-unknown-linux-gnu\",\"toolchain\":\"rustc 1.98.0 (example)\"},\"energy_calibration_ref\":null,\"energy_counter_filtering\":\"Unknown\",\"energy_provenance\":\"OnChipCounter\",\"energy_uncertainty\":{\"relative_ppm\":50000,\"window_us\":1200000},\"fabrics\":{\"shares\":[{\"attribution\":\"task\",\"fabric\":\"cpu\",\"joules_micro\":9000}],\"steps\":[{\"backend\":\"claim-conformance: a cpu backend\",\"fabric\":\"cpu\",\"step\":\"base-code\"},{\"backend\":\"claim-conformance: a fpga backend\",\"fabric\":\"fpga\",\"step\":\"base-search\"}]},\"figure_index\":null,\"figure_profile\":\"moq-jwp:claim-link\",\"group\":null,\"joules_micro\":9000,\"power_reader\":\"reader:example\"},\"class\":\"measurement\",\"issued_at\":\"2026-09-27T12:00:00Z\",\"kind\":\"claim\",\"parent_receipt_hash\":null,\"seq\":1,\"sig\":\"a345442a98a79bba3e6775a0fa0a33f977d2429fbf283bc650e6582d1efc402d0420441b6798f96dda35cc46477358c1485a5069111b769474e0ecd48e193e02\",\"signer_id\":\"did:example:meter\",\"signer_pubkey\":\"a09aa5f47a6759802ff955f8dc2d2a14a5c99d23be97f864127ff9383455a4f0\",\"subject\":\"c75b47e8b64ba4138d15c07e59dc1e7a710397dc5100392ec351641ae96835dd\",\"subject_type\":\"receipt\"}",
"expected": {
"outcome": "reject",
"step": 4,
"reason": "measurement_fabric_unknown"
}
},
{
"name": "measurement_fabric_step_twice",
"about": "the same step on the same fabric twice: each pair once",
"procedure": "claim",
"receipt": "{\"body\":{\"bracket\":null,\"build\":{\"profile\":\"release\",\"target\":\"x86_64-unknown-linux-gnu\",\"toolchain\":\"rustc 1.98.0 (example)\"},\"energy_calibration_ref\":null,\"energy_counter_filtering\":\"Unknown\",\"energy_provenance\":\"OnChipCounter\",\"energy_uncertainty\":{\"relative_ppm\":50000,\"window_us\":1200000},\"fabrics\":{\"shares\":[{\"attribution\":\"task\",\"fabric\":\"cpu\",\"joules_micro\":9000}],\"steps\":[{\"backend\":\"claim-conformance: a cpu backend\",\"fabric\":\"cpu\",\"step\":\"base-code\"},{\"backend\":\"claim-conformance: a cpu backend\",\"fabric\":\"cpu\",\"step\":\"base-code\"}]},\"figure_index\":null,\"figure_profile\":\"moq-jwp:claim-link\",\"group\":null,\"joules_micro\":9000,\"power_reader\":\"reader:example\"},\"class\":\"measurement\",\"issued_at\":\"2026-09-27T12:00:00Z\",\"kind\":\"claim\",\"parent_receipt_hash\":null,\"seq\":1,\"sig\":\"009d90b44d017c9157dff50ea14276c0d5fafa8bb60242b9e62b586c58e83f20f395c780996c10027211006330d29b7d852b43613ed1ffc838fdb79eac9c6602\",\"signer_id\":\"did:example:meter\",\"signer_pubkey\":\"a09aa5f47a6759802ff955f8dc2d2a14a5c99d23be97f864127ff9383455a4f0\",\"subject\":\"c75b47e8b64ba4138d15c07e59dc1e7a710397dc5100392ec351641ae96835dd\",\"subject_type\":\"receipt\"}",
"expected": {
"outcome": "reject",
"step": 4,
"reason": "measurement_fabric_order"
}
},
{
"name": "measurement_fabric_step_fabrics_out_of_order",
"about": "one step on the GPU listed before the same step on the CPU: within a step, fabrics are in their order",
"procedure": "claim",
"receipt": "{\"body\":{\"bracket\":null,\"build\":{\"profile\":\"release\",\"target\":\"x86_64-unknown-linux-gnu\",\"toolchain\":\"rustc 1.98.0 (example)\"},\"energy_calibration_ref\":null,\"energy_counter_filtering\":\"Unknown\",\"energy_provenance\":\"OnChipCounter\",\"energy_uncertainty\":{\"relative_ppm\":50000,\"window_us\":1200000},\"fabrics\":{\"shares\":[{\"attribution\":\"task\",\"fabric\":\"cpu\",\"joules_micro\":6500},{\"attribution\":\"rail\",\"fabric\":\"gpu\",\"joules_micro\":2500}],\"steps\":[{\"backend\":\"claim-conformance: a gpu backend\",\"fabric\":\"gpu\",\"step\":\"base-search\"},{\"backend\":\"claim-conformance: a cpu backend\",\"fabric\":\"cpu\",\"step\":\"base-search\"}]},\"figure_index\":null,\"figure_profile\":\"moq-jwp:claim-link\",\"group\":null,\"joules_micro\":9000,\"power_reader\":\"reader:example\"},\"class\":\"measurement\",\"issued_at\":\"2026-09-27T12:00:00Z\",\"kind\":\"claim\",\"parent_receipt_hash\":null,\"seq\":1,\"sig\":\"a3c62b1c9da7257015292be987dd37e405f6343ee90d5a976ab0c60960f294c7635319c1f7befc5fe55b395c725528256e7219d11d1a7964b5460b9d94b63608\",\"signer_id\":\"did:example:meter\",\"signer_pubkey\":\"a09aa5f47a6759802ff955f8dc2d2a14a5c99d23be97f864127ff9383455a4f0\",\"subject\":\"c75b47e8b64ba4138d15c07e59dc1e7a710397dc5100392ec351641ae96835dd\",\"subject_type\":\"receipt\"}",
"expected": {
"outcome": "reject",
"step": 4,
"reason": "measurement_fabric_order"
}
},
{
"name": "measurement_fabric_no_share",
"about": "steps with no share: a record divides the figure",
"procedure": "claim",
"receipt": "{\"body\":{\"bracket\":null,\"build\":{\"profile\":\"release\",\"target\":\"x86_64-unknown-linux-gnu\",\"toolchain\":\"rustc 1.98.0 (example)\"},\"energy_calibration_ref\":null,\"energy_counter_filtering\":\"Unknown\",\"energy_provenance\":\"OnChipCounter\",\"energy_uncertainty\":{\"relative_ppm\":50000,\"window_us\":1200000},\"fabrics\":{\"shares\":[],\"steps\":[{\"backend\":\"claim-conformance: a cpu backend\",\"fabric\":\"cpu\",\"step\":\"base-code\"},{\"backend\":\"claim-conformance: a cpu backend\",\"fabric\":\"cpu\",\"step\":\"base-search\"},{\"backend\":\"claim-conformance: a gpu backend\",\"fabric\":\"gpu\",\"step\":\"base-search\"},{\"backend\":\"claim-conformance: a gpu backend\",\"fabric\":\"gpu\",\"step\":\"object-hash\"}]},\"figure_index\":null,\"figure_profile\":\"moq-jwp:claim-link\",\"group\":null,\"joules_micro\":9000,\"power_reader\":\"reader:example\"},\"class\":\"measurement\",\"issued_at\":\"2026-09-27T12:00:00Z\",\"kind\":\"claim\",\"parent_receipt_hash\":null,\"seq\":1,\"sig\":\"3f0736d61f9e45784e60116a289d0aaa5c073807daf1c4b429f2056e4811da7d4f24084cc620aaca4057357239033cea1e51e0f61662a4bb2ccf36b2373de209\",\"signer_id\":\"did:example:meter\",\"signer_pubkey\":\"a09aa5f47a6759802ff955f8dc2d2a14a5c99d23be97f864127ff9383455a4f0\",\"subject\":\"c75b47e8b64ba4138d15c07e59dc1e7a710397dc5100392ec351641ae96835dd\",\"subject_type\":\"receipt\"}",
"expected": {
"outcome": "reject",
"step": 4,
"reason": "measurement_fabric_order"
}
},
{
"name": "measurement_fabric_step_missing_member",
"about": "a step with no backend: a step is its term, fabric and backend",
"procedure": "claim",
"receipt": "{\"body\":{\"bracket\":null,\"build\":{\"profile\":\"release\",\"target\":\"x86_64-unknown-linux-gnu\",\"toolchain\":\"rustc 1.98.0 (example)\"},\"energy_calibration_ref\":null,\"energy_counter_filtering\":\"Unknown\",\"energy_provenance\":\"OnChipCounter\",\"energy_uncertainty\":{\"relative_ppm\":50000,\"window_us\":1200000},\"fabrics\":{\"shares\":[{\"attribution\":\"task\",\"fabric\":\"cpu\",\"joules_micro\":6500},{\"attribution\":\"rail\",\"fabric\":\"gpu\",\"joules_micro\":2500}],\"steps\":[{\"fabric\":\"cpu\",\"step\":\"base-code\"},{\"backend\":\"claim-conformance: a cpu backend\",\"fabric\":\"cpu\",\"step\":\"base-search\"},{\"backend\":\"claim-conformance: a gpu backend\",\"fabric\":\"gpu\",\"step\":\"base-search\"},{\"backend\":\"claim-conformance: a gpu backend\",\"fabric\":\"gpu\",\"step\":\"object-hash\"}]},\"figure_index\":null,\"figure_profile\":\"moq-jwp:claim-link\",\"group\":null,\"joules_micro\":9000,\"power_reader\":\"reader:example\"},\"class\":\"measurement\",\"issued_at\":\"2026-09-27T12:00:00Z\",\"kind\":\"claim\",\"parent_receipt_hash\":null,\"seq\":1,\"sig\":\"f2e25d0f2a427e3d79b806e79094d4ab8ff471f98184b6f72566d425b1c68477e9691255239176d4d17d56c276768cc4c9703e9a5374a14d01c8c01c437b3106\",\"signer_id\":\"did:example:meter\",\"signer_pubkey\":\"a09aa5f47a6759802ff955f8dc2d2a14a5c99d23be97f864127ff9383455a4f0\",\"subject\":\"c75b47e8b64ba4138d15c07e59dc1e7a710397dc5100392ec351641ae96835dd\",\"subject_type\":\"receipt\"}",
"expected": {
"outcome": "reject",
"step": 2,
"reason": "missing_required_field"
}
},
{
"name": "measurement_fabric_record_unknown_member",
"about": "a record carrying the span's window beside its steps and shares: a record is its steps and shares",
"procedure": "claim",
"receipt": "{\"body\":{\"bracket\":null,\"build\":{\"profile\":\"release\",\"target\":\"x86_64-unknown-linux-gnu\",\"toolchain\":\"rustc 1.98.0 (example)\"},\"energy_calibration_ref\":null,\"energy_counter_filtering\":\"Unknown\",\"energy_provenance\":\"OnChipCounter\",\"energy_uncertainty\":{\"relative_ppm\":50000,\"window_us\":1200000},\"fabrics\":{\"shares\":[{\"attribution\":\"task\",\"fabric\":\"cpu\",\"joules_micro\":6500},{\"attribution\":\"rail\",\"fabric\":\"gpu\",\"joules_micro\":2500}],\"steps\":[{\"backend\":\"claim-conformance: a cpu backend\",\"fabric\":\"cpu\",\"step\":\"base-code\"},{\"backend\":\"claim-conformance: a cpu backend\",\"fabric\":\"cpu\",\"step\":\"base-search\"},{\"backend\":\"claim-conformance: a gpu backend\",\"fabric\":\"gpu\",\"step\":\"base-search\"},{\"backend\":\"claim-conformance: a gpu backend\",\"fabric\":\"gpu\",\"step\":\"object-hash\"}],\"window_us\":1200000},\"figure_index\":null,\"figure_profile\":\"moq-jwp:claim-link\",\"group\":null,\"joules_micro\":9000,\"power_reader\":\"reader:example\"},\"class\":\"measurement\",\"issued_at\":\"2026-09-27T12:00:00Z\",\"kind\":\"claim\",\"parent_receipt_hash\":null,\"seq\":1,\"sig\":\"8cfe28bd7cdd09663b2cdddf3de730ae1b5bddfd7a7da57522f14a58c3fedf18ce041988ec3f71d5fab1d1bff73513c0339a6ec7702f52641aafd4eb814e0905\",\"signer_id\":\"did:example:meter\",\"signer_pubkey\":\"a09aa5f47a6759802ff955f8dc2d2a14a5c99d23be97f864127ff9383455a4f0\",\"subject\":\"c75b47e8b64ba4138d15c07e59dc1e7a710397dc5100392ec351641ae96835dd\",\"subject_type\":\"receipt\"}",
"expected": {
"outcome": "reject",
"step": 2,
"reason": "unknown_member"
}
}
]
}

View file

@ -541,31 +541,38 @@ shows, by fabric:
(integer-operators §7.3). The host makes the interpreter's run-time checks before the
device runs anything, and a `check` tensor that leaves its range refuses the decode at
its operator. The driver's stage operators stay on the CPU, and so does a graph with an
operator outside `wai-ops/1-i32`. The tier is met for those graphs on each adapter and
backend below, where a run reproduced, at both widths, every graph vector of
integer-operators §14.1 and §14.2 that `wai-ops/1-i32` covers (§6):
- Metal, on the integrated GPU of an arm64 desktop (macOS 27.0.1);
operator outside `wai-ops/1-i32`. The tier is claimed for those graphs only under the
conditions of *Claiming the tier on a GPU* (below), which the crate meets, and only on
an adapter where a run, on the kernel text of this revision, gave WGSL's result for
every guarded case of the integer semantics suite, the host's result for every word of
the arithmetic probe, and the interpreter's outputs, at both widths, for every graph
vector of integer-operators §14.1 and §14.2 that `wai-ops/1-i32` covers (§6), with the
run's report committed (`wai/research/ops-gpu-runs.txt`). That is each adapter and backend
below:
- Metal, on the integrated GPU of an arm64 desktop (macOS 27.0.1), in the forge's run
10236 (job 46928) of `wai-ops-gpu.yml`;
- a browser's WebGPU on that same GPU, the kernels compiled by the browser's own WGSL
compiler (Chromium 148 and a Chromium-based browser at 155, headless);
- Vulkan, on a discrete GPU of PCI vendor 0x10de, device 0x28e1 (driver 595.84), and
on an integrated GPU of PCI vendor 0x8086, device 0xa7a0 (Mesa 25.2.8), in one Linux
x86_64 host;
- Vulkan, on an integrated GPU of PCI vendor 0x1002, device 0x1586 (Mesa 26.0.8),
Linux x86_64.
compiler (Chromium 148, headless), in the same job;
- Vulkan, on an integrated GPU of PCI vendor 0x1002, device 0x1586 (Mesa 26.0.8), Linux
x86_64, and a software Vulkan driver (llvmpipe, Mesa 26.0.8) on that host, which runs on
the CPU.
On each of these but the browser, the capability corpora (integer-operators §14.4)
also decoded with their graphs on the device: every committed vector and refusal
fixture of `wai.neural.int_hyper`, `wai.video.int_hyper`, `wai.audio.int_codec`,
`wai.splat.int_codec`, `wai.neural.int_synth` and `wai.neural.int_mlicpp` gave the
bytes, or the refusal code, of the decode on the CPU, and every graph the device ran
gave the interpreter's outputs. A software Vulkan driver (llvmpipe, on both Linux hosts)
gave the same results; it runs on the CPU. Nothing is claimed for an adapter, a backend
or a driver version that is not listed; DX12 was not run. `wai.image.jpegai`'s scale
graphs (`hs_y`, `hs_uv`, at `acc32`) and hyper decoders and context stages (`rec_y`,
`rec_uv`, at `acc64`) ran on each of these devices but the browser with the
interpreter's outputs, so its `entropy-consistency` claim (§5) holds with its scale
path there. Its synthesis graphs use operators outside `wai-ops/1-i32` and ran on the
CPU.
On Metal, the capability corpora (integer-operators §14.4) also decoded with their
graphs on the device, as §6 records: every committed vector and refusal fixture of
`wai.neural.int_hyper`, `wai.video.int_hyper`, `wai.audio.int_codec`,
`wai.splat.int_codec`, `wai.neural.int_synth` and `wai.neural.int_mlicpp` gave the bytes,
or the refusal code, of the decode on the CPU, and every graph the device ran gave the
interpreter's outputs. `wai.image.jpegai`'s scale graphs (`hs_y`, `hs_uv`, at `acc32`)
and hyper decoders and context stages (`rec_y`, `rec_uv`, at `acc64`) ran there with the
interpreter's outputs, so its `entropy-consistency` claim (§5) holds with its scale path
there. Its synthesis graphs use operators outside `wai-ops/1-i32` and ran on the CPU. On
the Vulkan adapters the capability corpora have not run on this revision's kernels. The
adapters G1 showed on the kernel text before this revision (Vulkan on Linux x86_64 with
PCI vendors 0x10de and 0x8086), and those a hand run showed on this revision's kernels
with no record committed (Vulkan and DX12 on a Windows x86_64 host, and its software DX12
adapter), are not claimed until a run of this revision's kernels is recorded there. The kernel text differs from G1's only in the
shift masks and the two clamps that *Claiming the tier on a GPU* requires. Nothing is
claimed for an adapter, a backend or a driver version that is not listed.
- **NPU.** No decoder of these capabilities runs on one in this revision, and the tier is
not claimed there. A network evaluated in floating point on a GPU or NPU does not meet
it (§1).
@ -578,6 +585,137 @@ digest, a reconstruction or an energy figure to it. Content that the application
decrypts itself, as in Lane B of SPEC §6.5, is decoded like any plaintext, and the
tier holds for it as it does for plaintext.
### Claiming the tier on a GPU, and on another accelerator
`decode-equivalence` holds on an accelerator (a GPU, a neural processor, any device other
than the CPU that runs a decoder's graphs) only where three things keep the integer
arithmetic the capability's registration fixes: the program the device runs, the
toolchain's translation of that program into the device's own code, and the device. In
general form, a decoder claims the tier for output an accelerator computed only when, for
every program that ran it: the program computes in integers only, so no reassociation or
fusion can change a result; it uses no operation whose result depends on a grouping the
device chooses; no result depends on scheduling (item 3 below, as written); the
translation gives the program language's result for every operation it uses, and the
program does not reach an operation on operands where the translation does not; the
device passes a conformance suite of the operations' edge cases, and the implementation's
probe of the wider arithmetic it builds, before it runs a graph; and the claim names the
device and the toolchain that ran. The items below are those conditions for a GPU, whose
programs are WGSL modules; another accelerator's text states its own program language,
translator, suite and probe in their place.
The texts read for a GPU are WGSL, W3C Candidate Recommendation Draft, 21 October 2026,
and naga 30.0.1, the translator wgpu 30.0.1 compiles WGSL with.
WGSL defines each integer operation at run time, the cases that are errors when the
operands are known before the shader runs included (WGSL §8.8, §8.10, §17.5): addition,
subtraction, multiplication and negation of a concrete integer type are modulo 2^32;
`e1 / 0` is `e1`, and `e1 % 0` is 0; the most negative `i32` divided by −1 is itself, and
its remainder 0; a shift amount is taken modulo 32; an integer `clamp(e, low, high)` is
`min(max(e, low), high)`; a bit field's offset and count are clamped to the word. The
languages a WGSL module is translated into leave some of these open: MSL and HLSL leave
signed overflow undefined; MSL leaves a left shift of a negative or overflowing signed
value undefined, and a right shift of a negative value to the implementation; and MSL,
HLSL and SPIR-V leave a zero divisor, the most
negative value divided by −1, a shift by the width or more, and a `clamp` whose bounds are
out of order undefined or to the implementation. Floating point is open even in WGSL: an
implementation may reassociate operations, and may fuse them where the result is at least
as accurate (WGSL §15.7.5). A subgroup operation's result depends on its subgroup, whose
size is a power of two from 4 to 128 that the device compiler chooses, whose invocations
have no defined relationship to `local_invocation_index`, and of whose invocations only
the active ones take part (WGSL §15.5, §15.6.3). An out-of-bounds access has several
permitted outcomes (WGSL §6.5.7).
So a decoder **MAY** claim `decode-equivalence` for output whose graphs ran on a GPU only
when every condition below holds for every shader module that ran them, on that adapter,
in that process. Otherwise the output is the GPU's, and no tier is claimed for it.
1. **Integer only.** Every scalar type in the module, of every declaration and of every
expression, is `bool`, `i32` or `u32`; every literal is of one of them; every
conversion is between them. No floating-point type appears for any purpose, an index
or a loop bound included. With no floating-point operation, no reassociation or fusion
an implementation may make changes a result: integer addition and multiplication
modulo 2^32 give the same value in any order.
2. **No subgroup or quad operation, and no extension.** The module enables nothing
(`enable`) and calls no subgroup or quad built-in.
3. **No result depends on scheduling.** Each output word is written by one invocation and
read by no other invocation of the same dispatch. Every atomic operation on a given
memory word is of one kind: `atomicOr`, `atomicAnd`, `atomicMin` or `atomicMax`, or
`atomicAdd` and `atomicSub` together; no `atomicLoad`, `atomicStore`, `atomicExchange`
or `atomicCompareExchangeWeak` reaches it in the dispatch; and the value an atomic
returns is not used. Each of those kinds alone is order-free; two on one word are not
(an `atomicOr` then an `atomicAnd` differs from the reverse). No access is out of
bounds.
4. **The translation gives WGSL's results.** A translation into a language that leaves an
integer result open produces WGSL's result for each operation the module uses: signed
addition, subtraction, multiplication and negation evaluated in unsigned arithmetic
and reinterpreted; division and remainder through a guard that substitutes the divisor
1 where WGSL's result is the dividend, and remainder 0; the absolute value of the most
negative value, itself. naga 30.0.1 does all of these in MSL and HLSL (its `naga_div`,
`naga_mod`, `naga_neg` and `naga_abs`, and signed arithmetic through unsigned); in
SPIR-V, whose integer addition, subtraction, multiplication and negation wrap, it
guards division and remainder. In MSL the division and remainder guards, and in SPIR-V
the division and unsigned-remainder guards, are written only while its integer-division
checks are on; SPIR-V's signed remainder is guarded even with them off, and HLSL's
guards are always written (DX12's translation goes through FXC, shader model 5.1). A
host
**MUST NOT** turn a translator's guards off: in wgpu, a module created unchecked, or
`ShaderRuntimeChecks::int_div_checks` false. Where a translator does not produce
WGSL's result for an operation, the module **MUST NOT** reach that operation on the
operands concerned. naga 30.0.1 passes a shift amount to MSL, HLSL and SPIR-V without
reducing it modulo 32, writes a signed left shift as it is, and writes an integer
`clamp` as MSL's and HLSL's `clamp`; so every shift amount in the module is a literal below 32 or
masked below 32 (`e & 31u`), no left shift has a signed left operand (the module
shifts the `u32` and bitcasts), and every `clamp` has literal bounds in order, another
bound being written `min(max(e, low), high)`. A right shift of a negative value, which
MSL leaves to the implementation, is held by item 5: the suite runs it on the adapter.
5. **The adapter passes the conformance suite first.** Before an adapter runs any graph of
the decode, in the same process, it gives WGSL's result for every case of the integer
semantics vectors (`wai/wgsl-conformance/integer.jsonl`) that the file marks guarded,
and for further cases of each operation that the implementation draws, and the host's
result for every word of the implementation's probe of the wider arithmetic it builds
from 32-bit words. And the implementation has reproduced, on that adapter, backend and
driver, every graph vector of integer-operators §14.1 and §14.2 its subset covers, at
each width it runs (integer-operators §12, *Evidence for a fabric*). An adapter that
differs on any guarded case or probe word runs no graph.
6. **The claim names what ran.** A receipt or report of a GPU decode at this tier names
the adapter (backend, PCI vendor and device, driver) and the translator and its
release. Where the backend reports no PCI identity and no driver (Metal and a browser's
WebGPU give vendor and device 0x0 and an empty driver), it names in their place the
adapter name the backend gives and the operating system's build, or the browser and
its version.
The semantics vectors cover every integer operation a kernel may use (rule 7 of
`tests/wgsl_rules.rs` keeps the kernels inside them), on `i32`, `u32` and two-component
vectors of them where a kernel uses those, with the edge cases above: every pair of a set of values
at and near the edges of both types for the arithmetic, division and remainder, every
shift amount from 0 to 40 and the extremes past it, and bit fields at and past the word.
They mark as unguarded the cases item 4 keeps a module from, a shift amount of 32 or more
and `clamp` bounds out of order, whose result is the hardware's through naga 30.0.1. A run
reports what each adapter gives on them; a difference there does not refuse the adapter,
since no module at this tier reaches one. The file is written from WGSL's definitions by
`wai_ops_gpu::semantics::reference` and checked against it natively, and against the same
reference compiled to wasm32, under Node and in a browser page.
`wai/wai-ops-gpu` meets these conditions. `tests/wgsl_rules.rs` holds every shipped module,
on naga's IR, to items 1, 2 and 4 and to item 3's atomic and barrier parts: the types and
literals; a closed list of expressions and built-in functions; the one atomic operation,
`atomicOr`, its result unused, and no atomic load or store; the bindings, with no workgroup
or private memory and no barrier; the shift masks, no signed left shift, and `clamp`
bounds; that every integer operation a kernel uses is one the semantics suite runs; and
naga's wrapping of signed arithmetic and its guard helpers in each module's MSL and HLSL
translations, which disappear from the MSL with its division checks turned off. Item 3's
other parts, each output word written by one invocation and read by no other, and no
access out of bounds, rest on the host's indexing of the dispatch and on wgpu's bounds
checks, which the checked module-creation call keeps on; the rules check does not decide
them. It also holds the crate to the checked module-creation call, and shows each planted
violation (a floating-point value, `f16`, a subgroup reduction, an `atomicAdd`, an
atomic's result read, an atomic load, an atomic store, workgroup memory and a barrier, a
storage barrier alone, an unmasked shift, a signed left shift, a `clamp` with run-time
bounds) refused by the rule it breaks. Discovery runs item 5's suite and probe on each adapter before it runs a graph;
`tests/semantics.rs` shows every adapter refused when the suite's remainder is written by
hand, `a - (a / b) * b`, which gives `a` where WGSL gives 0. In a browser,
`wai-ops-gpu/browser` runs the same suite through the browser's own WGSL compiler.
## 6. Evidence status
What the repository demonstrates, claim by claim, as of 2026-09-27 (main at
@ -614,7 +752,7 @@ task list has no Windows task after that day. The Windows results below are hist
| `wai.audio.opus.dred.int`: the profile's features are an exact integer function of the payload and the pinned weights, the same on the CPU and on a GPU, and within the draft's tolerance of its reference features | the corpus `live-conformance/dred/` regenerates byte for byte, and its second implementation (`dred_verify.py`, standard-library Python written from the extension) recomputes every digest and row; the two graphs on the GPU at `acc64` give the interpreter's integers graph by graph and the CPU decode's bytes; on the draft's eight test vectors the features pass the draft's feature test and lie at `total` 0.0021 from the network in floating point (opus-dred §6) | measured 2026-10-22 with rustc 1.98.0 on macOS arm64 (the build host: the wai-rs tests in release, the GPU test on its Metal adapter `gpu-metal-0`) and the Python verifier on a second macOS arm64 host. Not measured: x86_64, Linux, Windows, wasm. CI runs the corpus, the measurement and the verifier on the forge's Linux arm64 runner (`wai-conformance.yml`) and the GPU test on the `macos` runner (`wai-ops-gpu.yml`), with no forge run recorded yet. The weights are fetched by digest, not committed | `wai-rs/tests/dred_exact.rs`, `wai-rs/tests/dred_exact_measure.rs`, `wai-rs/tests/dred_exact_gpu.rs`, `live-conformance/dred_verify.py` |
| `wai.audio.int_codec`, `wai.splat.int_codec` | committed vectors that never skip. Their frozen hashes are the output of an independent Python integer reference, computed when the vectors were exported (`tools/wai_int_audio_export.py`, `tools/wai_int_splat_export.py`); no Python runs in CI. The conformance workflow's fast-kernel steps enable `audio_int` and `splat_int` and, in debug and release builds, decode both vectors against those hashes under the reference kernels and every fast-kernel policy (`tests/int_kernels_vectors.rs`); that passed on the forge's Linux x86_64, Linux arm64 and macOS arm64 runners for the landing chain's head `7cfcecfa` (run 745, 2026-09-30). The same steps also name `tests/int_audio.rs` and `tests/int_splat.rs`, which check each vector against the same hash and against its own metadata (sample count; attribute count, tensor size and grid side); Cargo declares each with its feature as a required feature, so a step that names it without that feature fails instead of running nothing. This row records no forge run of those two | `wai-rs/tests/int_audio.rs`, `int_splat.rs`, `int_kernels_vectors.rs`; `.github/workflows/wai-conformance.yml` |
| `wai.neural.int_mlicpp` on its committed vector (synthetic seeded weights; a 64×64 image, 8 latent channels in 4 slices): the decode reproduces the export tool's independent integer reference byte for byte — the RGB, and every scale bucket and symbol of the latent stream in coding order (512 symbols over all 16 buckets of the scale table, 47 of the symbols coded by the rANS escape) — under the reference kernels and under the fast kernels on 1, 2, 3, 5 and all available threads; one integer unit changed in each of four chosen parameters, one on each path that feeds a value (a hyper-decoder weight, an entropy-network weight, a mean-head bias, a synthesis weight), changes the image; a header whose shapes the model cannot produce, or on which a network would form a buffer over the cap, is refused before anything is allocated (`tests/int_mlicpp_preflight.rs`, which counts allocations); damaged payloads are refused or decode, and never panic in an overflow-checked build | measured 2026-09-29 with rustc 1.98.0 on the source of the change that added this row: macOS arm64 native (the wai-rs tests, with overflow checks on and off; the `byte-exact-conformance` golden, release) and wasm32-wasip2 under wasmtime 49.0.1 (the same tests and golden, release; on wasm the fast kernels run single-threaded as portable scalar code, and `usize` is 32-bit). All pinned hashes matched on both. Not measured: x86_64 — the development machine has no x86_64 translation layer installed, and an x86_64-apple-darwin build of the golden compiles but cannot execute there — nor Linux or Windows. The golden runs on every leg of the byte-exact matrix (`wai-conformance.yml`, `wai-byte-equality.yml`) and `tests/int_mlicpp.rs` on every leg of `wai-conformance.yml` in both profiles. Both passed on the forge's Linux x86_64, Linux arm64 and macOS arm64 runners for the landing chain's head `7cfcecfa` (run 745, 2026-09-30); there is no Windows leg. The dispatch through `decode_envelope_strict` (the prior pinning the one-file model bundle, the strict gate) runs in `wai-neural-gates.yml`. The weights are synthetic, so nothing here measures compression quality | `wai-rs/tests/int_mlicpp.rs`, `wai-rs/tests/int_mlicpp_preflight.rs`, `byte-exact-conformance/src/int_mlicpp_golden.rs`, `wai-rs/tests/neural_native_decode.rs`; `tools/wai_int_mlicpp_export.py` |
| `wai-ops/1-i32` graphs on GPUs (`wai/wai-ops-gpu`, §5): each device's arithmetic agrees with 128-bit host arithmetic on every probe case; every graph vector of `ops-conformance/` that the subset covers gives the interpreter's outputs or refusal code, at `acc32` and at `acc64`; the integer decoders, with their graphs on the device, give the CPU decode's bytes or refusal codes on every committed vector and refusal fixture, and every graph the device runs gives the interpreter's outputs | measured 2026-10-20 and 2026-10-21 with rustc 1.98.0 and wgpu 30.0.1, release builds, on the source of the change that added this row, on the adapters §5 lists: Metal on macOS 27.0.1 (arm64); headless Chromium 148, and a Chromium-based browser at 155, on that GPU; Vulkan on Linux x86_64 with the 0x10de and 0x8086 adapters (driver 595.84, Mesa 25.2.8) and, on another host, with the 0x1002 adapter (Mesa 26.0.8); and llvmpipe on both Linux hosts. On each, the probe (`tests/arith.rs`) agreed on every word of 1,051,757 cases, and the corpus (`tests/corpus.rs`) ran 813 vectors (1,104 decodes) on the 32-bit kernels and 1,426 (1,921 decodes) on the 64-bit ones, 212 of the decodes refusals, with no difference; 209 graphs use an operator outside the subset and ran on the CPU, and 95 vectors are refused at load. Run on the 32-bit kernels, 330 of the 613 graphs whose certificate does not meet `acc32` gave other results, so the width a graph runs at is the certificate's. Eighteen edits of one kernel expression each (a rounding shift or its addend off by one, a tie rule, a clamp bound moved by one, a dropped carry or cross term, a sign rule, a post bias, an index rule; `tests/mutants.rs`) were each caught by the corpus on every adapter, and an edited product by the probe. `wai-rs/tests/ops_gpu.rs` decoded the committed vectors and refusal fixtures of the six capabilities §5 names, the world renderer's two vectors and `wai.image.jpegai`'s `jpegai/v1` codestream, comparing every graph the device ran with the interpreter as well as each decode's bytes; none differed. The browser leg ran the corpus, not the decoders. `wai-ops-gpu.yml` runs the Metal and browser legs on the `macos` runner, where an absent adapter fails; this row records no forge run of it yet. No other workflow runs a GPU leg of these tests | `wai-ops-gpu/tests/`, `wai-ops-gpu/browser/`, `wai-rs/tests/ops_gpu.rs`; `.github/workflows/wai-ops-gpu.yml` |
| `wai-ops/1-i32` graphs on GPUs (`wai/wai-ops-gpu`, §5, *Claiming the tier on a GPU*): every shipped module meets items 1, 2 and 4 and item 3's atomic and barrier parts on naga's IR; each device gives WGSL's result for every guarded case of the integer semantics suite and agrees with 128-bit host arithmetic on every probe case; every graph vector of `ops-conformance/` that the subset covers gives the interpreter's outputs or refusal code, at `acc32` and at `acc64`; the integer decoders, with their graphs on the device, give the CPU decode's bytes or refusal codes on every committed vector and refusal fixture, and every graph the device runs gives the interpreter's outputs | the forge's run 10236 (job 46928) of `wai-ops-gpu.yml`, 2026-10-22, rustc 1.98.0 and wgpu 30.0.1 (naga 30.0.1), release builds, on the kernel text of the change that added *Claiming the tier on a GPU*, on the adapters §5 lists: Metal on macOS 27.0.1 (arm64), and headless Chromium 148 on that GPU; and, on 2026-10-24 at the commit that added `wai/research/ops-gpu-runs.txt` (which holds both runs' report lines), Vulkan on Linux x86_64 with the 0x1002 adapter (Mesa 26.0.8) and llvmpipe, where every test of the crate ran and passed with `WAI_OPS_GPU_REQUIRE=1` and the semantics suite, the probe, the corpus and the mutants gave the figures below with none differing. `tests/wgsl_rules.rs` passed, each planted violation refused by the rule named. On Metal the semantics suite (`tests/semantics.rs`) gave WGSL's result for every one of 254,464 cases, the 25,088 committed and 4,096 SplitMix64 cases of each operation: 231,690 guarded, and the 22,774 unguarded too (a shift amount of 32 or more, `clamp` bounds out of order); the browser leg ran 82,432 cases with none differing, and the committed file reproduced under the reference compiled to wasm32, in the page and under Node 26. The probe (`tests/arith.rs`) agreed on every word of 1,051,757 cases; the corpus (`tests/corpus.rs`) ran 813 vectors (1,104 decodes) on the 32-bit kernels and 1,426 (1,921 decodes) on the 64-bit ones, 212 of the decodes refusals, with no difference; 209 graphs use an operator outside the subset and ran on the CPU, and 95 vectors are refused at load. Eighteen edits of one kernel expression each (`tests/mutants.rs`) were each caught by the corpus, an edited product by the probe, and a remainder written by hand by the semantics suite at discovery. `wai-rs/tests/ops_gpu.rs` decoded the committed vectors and refusal fixtures of the six capabilities §5 names, the world renderer's two vectors and `wai.image.jpegai`'s `jpegai/v1` codestream on Metal, in the forge run, comparing every graph the device ran with the interpreter as well as each decode's bytes; none differed. The browser leg ran the corpus and the semantics suite, not the decoders. Hand runs of this kernel text on Vulkan on Linux x86_64 (PCI vendors 0x10de and 0x8086, and llvmpipe) and on Windows x86_64 (Vulkan and DX12, PCI vendors 0x10de and 0x8086, and the software DX12 adapter) committed no record, and G1's runs of the 0x10de and 0x8086 adapters were of the kernel text before it; none of those is claimed. `wai-rs/tests/ops_gpu.rs` has not run on the Vulkan adapters on this kernel text. `wai-ops-gpu.yml` runs the Metal and browser legs on the `macos` runner, where an absent adapter fails. No other workflow runs a GPU leg of these tests | `wai-ops-gpu/tests/`, `wai-ops-gpu/browser/`, `wai-rs/tests/ops_gpu.rs`, `wgsl-conformance/`; `.github/workflows/wai-ops-gpu.yml` |
So at `entropy-consistency`, WAI's JPEG AI symbol decode is demonstrated across
architectures (x86_64 against arm64) once the distribution indices are given; the
@ -634,9 +772,9 @@ arm64 and on wasm32-wasip2 (a 32-bit target), measured on the development machin
it also passed on the byte-exact matrix's Linux x86_64, Linux arm64 and macOS arm64
legs in run 745. On GPUs, the committed vectors of `int_hyper` (and its video keyframe),
`int_codec` audio and splat, `int_synth` and `int_mlicpp` decode with their graphs on
the device to the CPU decode's bytes on each adapter §5 lists, measured by hand on small
vectors; the `wai-ops-gpu` workflow repeats it on one of them, with no forge run
recorded yet.
the device to the CPU decode's bytes on Metal, the adapter §5 lists that runs them, after
it gave WGSL's integer semantics on every guarded case, in the `wai-ops-gpu` workflow's
forge run 10236 (job 46928).
For the JPEG AI exact decoder's pinned reconstruction (§5), identity across
machines rests on construction, and on one comparison: a single codestream on the

View file

@ -1026,6 +1026,75 @@ and, under a hardware class, that the rail was live and the ratio is at least 1
(jwp-receipts §2.4.8). It does not check the values, which cannot be re-measured
(§5).
### 6.3 A figure divided by fabric
Work can run on more than one kind of processor, a **fabric**: `cpu`, `gpu`,
`media` (a hardware video engine) or `npu` (a neural processor). A
`measurement` report MAY carry a **fabric record** (jwp-receipts §2.4.8,
`fabrics`): the steps of the work, each with every fabric that ran it and the
backend that did, and the figure divided into one **share** per fabric that ran
a step. The figure is the sum of its shares, and its class (§2) is the class of
the whole: a share is no measurement of its own. A figure divided by fabric is
sealed under the class of its weakest share's reading, with that class's evidence
over the span; the reference meter's shares are both `OnChipCounter` readings
(§2.9), filtering `Unknown`, with a declared relative standard uncertainty of 5 %
(the counters' read granularity, not a measured spread) and the span as its window,
so its figure is an `OnChipCounter` figure. A fabric that ran a step has a share of
more than 0: 0 J is no reading of work.
Each share states how its energy was attributed to the work:
- `task`: the operating system's account of the work's own energy on that
fabric, as it accounts a task's use of the processors, which other work on the
host does not enter. On the reference hosts it is the kernel's per-task CPU
energy read with `proc_pid_rusage` at `RUSAGE_INFO_V6`, `ri_energy_nj +
ri_billed_energy − ri_serviced_energy`: the task's own energy, and the energy
system services spent for it and the kernel billed to it, less what it spent
servicing others. The kernel folds a thread's energy in only when the thread
leaves its core, and a process's read of itself does not fold the thread that
reads, so each end's read is taken only once the reading thread's own energy
count is seen to move across a sleep; a read that does not fold is no reading.
- `rail`: the fabric's whole rail over the span, its idle and static draw over the
span included, in which the work was the fabric's sole user: at least 99% of
the busy time every user of the fabric accrued over it. The users are read at
least every 200 ms through the span, each user's busy time differenced between
consecutive reads by an identity it keeps for its life, the first read before
the rail's start and the last after its end, so that the busy window encloses
the rail's. A user of the work's own that vanishes, a difference that is
negative, or a read that fails, gives no share; another user that vanishes is
counted busy for the whole interval it vanished in, and nothing is clamped. The
rail is read through the span, and must be live over it (§3.1). A user created
and destroyed between two reads is not seen; that is the attribution's residual.
The window of a `rail` share runs from the rail's republish before the span to
its republish after it, so it can exceed the span by up to one republish
period on each side; the figure's declared window is the span's.
A span that gives a figure divided by fabric lasts at least 1 s and five reading
intervals. No attribution divides a rail that other work shared by its users' busy
time, and a `rail` share is never a part of a rail: it is the whole rail, or there
is none.
Busy time does not apportion energy: a GPU kernel that keeps the GPU busy at a
low clock and one that keeps it busy at a high clock accrue the same time and
draw very differently, and a division by GPU time has been measured to charge
a decode three to fifteen times the GPU energy it drew alone
(`jouleclaw-energy`, `process_gpu`). Where a fabric that ran a step was shared
and its rail cannot be attributed, the span has no fabric record: the producer
meters it otherwise (§3's bracket, over the whole figure), or seals it
unmetered. So does a span that ran a step on a fabric with no live counter: on
the reference hosts (macOS 27 on arm64) the media engine and the neural processor
have none an unprivileged process can read.
A figure profile defines the vocabulary of its record's steps. A `measurement`
report about a figure whose profile defines no step vocabulary **MUST NOT** carry a
fabric record; in this revision only `wai:video-package-receipt-id` defines one
([packaging](packaging.md) §11, its steps and fabrics).
The record says where the work ran and what each fabric drew; it changes
nothing a figure's verifier checks of the figure itself (§6.2). Which fabric
ran a step changes no output of a step whose output its specification fixes
([packaging](packaging.md) §11, its steps and fabrics), so a record is a statement about energy, not
about what was produced.
## 7. Worked example
`wai.video.int_motion`, real-footage vector, 8 frames of 96×96 RGB, release

View file

@ -325,10 +325,13 @@ signed by someone other than the publisher. A `claim` receipt carries
one such statement — a class-scoped `body` under a `class`
discriminator — on one envelope.
Required members. A claim has no optional members but the three hybrid members of
[pq-signatures](pq-signatures.md) §3.1 (`pq_suite`, `pq_key`, `pq_sig`), carried all or none;
a verifier that does not implement that extension refuses them as `unknown_member`. A nullable member
is present and `null`, so one claim has one canonical form.
Required members. A claim has no optional members but two. The three hybrid
members of [pq-signatures](pq-signatures.md) §3.1 (`pq_suite`, `pq_key`, `pq_sig`)
are carried all or none; a verifier that does not implement that extension refuses
them as `unknown_member`. A `measurement` claim's `fabrics` (§2.4.8) is absent when
the claim does not divide its figure by fabric and is never `null`, so a claim
sealed before the member existed keeps its bytes and its link hash. Every other
nullable member is present and `null`, so one claim has one canonical form.
| field | type | meaning |
|---|---|---|
@ -692,6 +695,7 @@ receipt's identity for every other profile.
| `bracket` | object or `null` | For a figure obtained under energy-measurement §3: `{ "idle": summary, "busy": summary, "window_us": integer, "completions": integer, "in_flight": integer, "opening": "from-rest" or "running" }`, a summary being `{ "n": integer, "mean_uw": integer, "sd_uw": integer, "live_intervals": integer, "longest_live_run": integer }` as energy-measurement §6.2 defines them. `null` otherwise. |
| `build` | object | `{ "profile": "release" or "debug", "toolchain": string or null, "target": term or null }`: the build of the code measured (energy-measurement §5, §8). `release` is an optimised build (for a Rust build, `opt-level` 2, 3, `s` or `z`, whatever its profile is named); any other build is `debug`. A finer vocabulary is a new registration. |
| `power_reader` | string or `null` | The reader of the power interface (energy-measurement §8). Required under a hardware class (rule 4). |
| `fabrics` | object, or absent | Where the work the figure covers ran, and the figure divided by fabric (energy-measurement §6.3): `{ "steps": [step, ...], "shares": [share, ...] }`. A step is `{ "step": term, "fabric": term, "backend": string }`: a step of the work, in the vocabulary of the document that defines the figure's receipt (for `wai:video-package-receipt-id`, the steps of [packaging](packaging.md) §11), a fabric that ran it, and the implementation and device that did, a non-empty string. A share is `{ "fabric": term, "joules_micro": integer, "attribution": term }`. Absent, the claim does not divide its figure; never `null` (§2.4). |
A report carries none of what follows from its values: neither the §4 ratio nor
its verdict, which every reader derives (energy-measurement §6.2). A bracket
@ -737,6 +741,19 @@ Rules, checked at §3.1 step 4 in this order:
**MUST** be the bracket's (`measurement_window_mismatch`), and the declared
`relative_ppm` **MUST** be at least the least `p` the bracket supports
(energy-measurement §6.2) (`measurement_declaration_below_bracket`).
6. Where `fabrics` is present, in this order:
- every fabric is `cpu`, `gpu`, `media` or `npu`, and every attribution `task`
or `rail` (energy-measurement §6.3) (`measurement_fabric_unknown`);
- there is at least one step and one share; the steps are in the order of their
`step`, in byte order, and then of their fabric, in the order just given, each pair
once; and the shares are in the order of their fabric, each fabric once
(`measurement_fabric_order`);
- every fabric a step names has a share of more than 0
(`measurement_fabric_unmetered`): a fabric that ran work is metered, and 0 J is
no reading of it;
- every share's fabric runs a step (`measurement_fabric_unused`);
- the shares sum to `joules_micro` (`measurement_fabric_sum`): the record divides
the figure, and the figure's class covers every share.
**Against the figure** (§3.1 step 6). The context is the receipt the claim
names, verified under its own profile's rules; for `moq-jwp:object`, that is
@ -2055,9 +2072,14 @@ order listed.
2. **Body.** A `body` that is not an object is `field_type`. Otherwise
it is checked against the class's member table (for a lawful-basis
body, the table of the record that `record`, read first, names; see
§2.4.6): a member absent is `missing_required_field`, an additional
§2.4.6): a member absent is `missing_required_field` (but a
`measurement` body's `fabrics`, which may be absent, §2.4), an additional
member is `unknown_member`, and then, in the table's order, a member
that is not of the type the table gives it is `field_type`. That is
that is not of the type the table gives it is `field_type`; a `fabrics`
that is `null` is `field_type`, and within it, as in a bracket, a member
absent is `missing_required_field` and an additional one `unknown_member`
(`steps` before `shares`, each array's rows read for their members before
its rows' values). That is
a wrong JSON type; an integer that is not one of §2.4.3; a byte
string that is not lowercase hex, two digits a byte, or a hash that
is not 64 of them; a value outside an enumeration this extension
@ -2216,6 +2238,11 @@ and never folds it in: confirmation changes the outcome of no step here.
| 4 | `measurement_figure_mismatch` | `joules_micro` is not the figure the bracket gives |
| 4 | `measurement_window_mismatch` | under a hardware class, the declared window is not the bracket's |
| 4 | `measurement_declaration_below_bracket` | under a hardware class, `relative_ppm` is below the least the bracket supports |
| 4 | `measurement_fabric_unknown` | a fabric record names a fabric other than `cpu`, `gpu`, `media` and `npu`, or an attribution other than `task` and `rail` |
| 4 | `measurement_fabric_order` | a fabric record with no step or no share, its steps not in the order of their step and fabric, or its shares not in the order of their fabric, or a pair or a fabric twice |
| 4 | `measurement_fabric_unmetered` | a fabric record's step runs on a fabric the record gives no share, or a share of 0 |
| 4 | `measurement_fabric_unused` | a fabric record's share is on a fabric no step of it runs on |
| 4 | `measurement_fabric_sum` | a fabric record's shares do not sum to `joules_micro` |
| 4 | `operating_point_empty_point` | a point is present with no member |
| 4 | `operating_point_delivered_alone` | `op_delivered` is present without `op_committed` |
| 4 | `operating_point_incomplete` | `op_requested` or `op_committed` is present without `op_delivered` |

View file

@ -4,11 +4,16 @@
> this extension fixes what a verifier recomputes. This revision defines the policy,
> its digest and what it may ask a packager to emit (§3), how a source is cut into
> pieces (§4), the objects a packager writes, refinements and stills among them, and a
> piece's ladder (§5), the stage index (§6), the floor (§7), what each class is offered
> piece's ladder (§5), the stage index (§6), the floor, one or several, supplied as OBU
> streams or as an existing ladder's CMAF files (§7), what each class is offered
> over HTTP and MoQ and how its delivery is simulated (§8), the package receipt and live
> windows (§9), and the package and its verification (§11). Reference impl: `wai-pack` —
> windows (§9), the package, its verification and a re-pack from a parent (§11), and
> where each step of a pack or a verify may run (§11.6).
> Reference impl: `wai-pack` —
> `policy`, `capcheck`, `source`, `scenecut`, `classify`, `plan`, `encode`, `png`,
> `floor`, `cmaf`, `catalog`, `pack`, `live`, `delivery`, `verify`; in `wai-rs`, the
> `floor`, `cmaf`, `cmaf_read`, `catalog`, `files`, `pack`, `live`, `delivery`, `verify`,
> `fabric`, `fabric_meter`, `floor_decode`, and `wai-pack-gpu` for the steps a GPU runs;
> in `wai-rs`, the
> encoder `int_video_enc`, the refinement encoder `staged::wir1`, the stage index
> `stage_index`, the receipt `package` and the delivery simulator `stage_measure::sim`;
> the corpus [`pack-conformance/`](../pack-conformance/). Keywords **MUST**, **MUST NOT**,
@ -32,8 +37,15 @@ where it names them.
- **Class**: a delivery profile the policy names.
- **Moment**: a declared span of presentation time with tags.
- **Floor**: a rendition in a standard codec, for sinks that lack the primary.
- **Floor name**: the name a floor rung's files and catalog entries carry (§7.1): its
component's id when the component has one floor rung, the rung's id when it has
several.
- **Timebase** of a component: `num / den` units per second. For video one unit is
one frame; for audio, one sample.
- **Step**: one of the computations of a pack or a verify (§11.6), such as the base's
motion search or an object's content hash.
- **Fabric**: the kind of processor a step runs on: `cpu`, `gpu`, `media` (a hardware
video engine) or `npu` (a neural processor) (§11.6).
## 3. Policy
@ -81,6 +93,7 @@ absent table reads as empty.
| `component.media` | string | required | `video`, `image`, `audio`, `world`, `feed`, `avatar`, `film` |
| `component.source` | string | absent | |
| `component.timebase` | table | required | members `num`, `den`, each 1 to `2^32 − 1`, required |
| `component.profile` | string | absent | `floor-only` (§7.8); absent, the standard profile |
| `segmentation.target_ms` | integer | 2000 | |
| `segmentation.min_ms` | integer | 1000 | |
| `segmentation.max_ms` | integer | 4000 | |
@ -99,6 +112,7 @@ absent table reads as empty.
| `ladder.params` | table | empty | by capability, below |
| `floor.supplied_listing` | string | absent | 64 lowercase hexadecimal digits |
| `floor.extra_keyframes` | boolean | `false` | |
| `floor.supplied_form` | string | absent | `cmaf` (§7.7); absent, the OBU form (§7.3) |
| `live.layer_lag_ms` | array of integers | one 0 per layer | §3.4 |
| `class` | array of tables | empty | |
| `class.id` | string | required | 1 to 255 bytes |
@ -157,15 +171,17 @@ first that fails is the refusal:
chain of `refines` returns to a rung it passed (`policy-refines-cycle`); every
chain stays in its component and ends at a base (`policy-refines-base`); no rung is
refined twice (`policy-refines-branch`).
8. Every component has a base rung (`policy-no-base`).
8. Every component has a base rung (`policy-no-base`), but a floor-only one (§7.8), which
has no base and no refinement rung, no `source`, and at least one floor rung
(`policy-floor-only`).
9. A rung's **layer** is 0 for a base or a floor, and one more than the rung it
refines for a refinement; the policy has one more layer than its highest rung
layer. No class's and no rule's `max_layer` exceeds the highest
(`policy-class-layer`).
10. A rule's `then.ladder` names known rungs, all of one component, each once:
exactly one base, every refinement over a rung it names (so its layers are a chain
from that base), and every floor rung of the component (every piece has a floor,
§7.1) (`policy-rule-ladder`).
exactly one base (none, for a floor-only component), every refinement over a rung it
names (so its layers are a chain from that base), and every floor rung of the
component (every piece has a floor, §7.1) (`policy-rule-ladder`).
11. `live.layer_lag_ms` has one entry per layer, the first 0, the entries
non-decreasing (`policy-layer-lag`).
12. The deadline values (`defaults.deadline_ms` and every rule's `then.deadline_ms`)
@ -205,8 +221,9 @@ no reference outside the piece, and no later object of the package references in
it.
**4.2** Piece boundaries are a pure function of the source frames and the effective
policy. Where the policy names `wai.pack.scenecut/1`, the boundaries **MUST** be those
§4.3 computes. The list of piece starts, in timebase units, is the **plan**, and its
policy; a floor-only component's, which has no source, of its first floor rung (§7.8).
Where the policy names `wai.pack.scenecut/1`, the boundaries of a component with a
source **MUST** be those §4.3 computes. The list of piece starts, in timebase units, is the **plan**, and its
digest is
BLAKE3("wai:pack-plan\x01" ‖ u64 LE n ‖ n × u64 LE start)
@ -475,7 +492,7 @@ bytes are zero.
| 8 | 4 | `duration`, in timebase units |
| 12 | 4 | `first_entry`, window-relative |
| 16 | 2 | `n_entries` |
| 18 | 1 | `kind`: 0 natural, 1 static, 2 synthetic, 3 motion_high (§4.6), 4 world segment, 5 audio |
| 18 | 1 | `kind`: 0 natural, 1 static, 2 synthetic, 3 motion_high (§4.6), 4 world segment, 5 audio, 6 none (a floor-only component's piece, which no source classifies, §7.8) |
| 19 | 1 | flags: bit 0 scene cut, bit 1 forced at `max` (§4.3), bit 2 started by a cue, bit 3 aligned to the lead (§4.5) |
| 20 | 4 | `rules`: bit *i* set when rule *i* matched the piece (§8.1) |
| 24 | 4 | `moments`: bit *i* set when the piece lies in moment *i* (§8.1) |
@ -562,7 +579,9 @@ of these, checked in this order:
(`layer-gap`); its tier (§6.4: `tier-entropy-passthrough`, `tier-weakest`, then
`tier-mismatch`); a non-zero `prefix_digest` with a tier other than
decode-equivalence (`digest-without-tier`); a deadline on an entry that is not a
refinement (`deadline-role`); a floor without flag bit 2 (`floor-derived-from`); a
refinement (`deadline-role`); a floor whose flag bit 2 is not set exactly when its
piece has a base, so a floor presents its piece's base and a piece of floors alone
presents none (`floor-derived-from`); a
content hash an earlier entry has at another length (`dup-length`); the duplicate
flag other than set exactly when an earlier entry has the content hash (`dup-flag`).
3. Class by class: a flag with no meaning (`class-flags`); a plan value other than
@ -615,12 +634,18 @@ and one without the source cannot. A floor's `sse` is `2^64 − 1`.
**7.1** Every piece of a video, image or audio component **MUST** have a floor rendition
in a capability of SPEC §5's mandatory floor or recommended set; a packager refuses a
video component with no floor rung (`floor-missing`). A film or world package SHOULD
have one. This revision packs a supplied AV1 floor (`wai.video.av1` or
`wai.video.av1.lossless`, `source = "supplied"`).
have one. A component may have several floor rungs: each piece then has one floor object
per floor rung, in ladder order (§5.7), so one package carries a ladder of standard-codec
renditions over one base, which is coded once. Each floor rung has a floor name (§2): the
component's id when the component has one floor rung, the rung's id when it has several.
A floor name names files (§7.3, §7.6, §8.3), so one that cannot be one path segment of a
listing, or two floor names of a package equal once `A`–`Z` are mapped to `a`–`z`, are
refused (`pack-id`, §11.1). This revision packs supplied AV1 floors (`wai.video.av1` or
`wai.video.av1.lossless`, `source = "supplied"`), one stream per floor rung.
**7.2** *Floor objects.* Each piece's floor is one object of the floor rung's capability
(§5.2), whose manifest carries `derived_from` (SPEC §7.1, *Derived renditions*) naming
the piece's base: `motif` the base's content hash, `motif_capability` its capability,
(§5.2), whose manifest, except in a floor-only component (§7.8), carries `derived_from`
(SPEC §7.1, *Derived renditions*) naming the piece's base: `motif` the base's content hash, `motif_capability` its capability,
`renderer` the floor's maker, and `settings` `BLAKE3("wai:render-settings\x01" ‖
JCS(settings))` (§3.6). For a supplied floor, `renderer` is `supplied@<the supplied
listing's SHA-256>` and the settings are `{"source": "supplied", "supplied_listing":
@ -633,13 +658,15 @@ sequence header's maximum frame height and width, the component's timebase `num`
`den`), then each temporal unit as a `u32` little-endian length and its bytes as the
stream holds them.
**7.3** *A supplied floor* is a directory holding, per video component, `<id>.obu`: an
AV1 stream in the low-overhead OBU format (every OBU with its size field), one temporal
unit per source frame. Its listing (SPEC §3.1) of every file is pinned by the policy's
`floor.supplied_listing`. A packager **MUST** refuse, before it writes anything:
**7.3** *A supplied floor* is a directory holding, per floor rung of a video component,
`<floor name>.obu` (§7.1): an AV1 stream in the low-overhead OBU format (every OBU with
its size field), one temporal unit per source frame. Its listing (SPEC §3.1) of every
file is pinned by the policy's `floor.supplied_listing`. A packager **MUST** refuse,
before it writes anything, the directory and then each floor rung's stream in ladder
order:
- a directory whose listing does not hash to `floor.supplied_listing`
(`floor-listing-mismatch`), and a component with no stream in it
(`floor-listing-mismatch`), and a floor rung with no stream in it
(`floor-stream-missing`);
- a stream that does not split into temporal units each holding a frame, whose first
unit holds no sequence header, with a sequence header whose bytes differ from the
@ -652,21 +679,36 @@ unit per source frame. Its listing (SPEC §3.1) of every file is pinned by the p
`KEY_FRAME` and `show_frame` 1, or the sequence uses the reduced still-picture header;
a unit that shows an existing frame does not.
*Key-frame sequence headers (informative).* A floor taken from an existing ladder without
re-encoding (its CMAF samples demuxed to this form, each with its temporal delimiter put
back) needs a sequence header in every unit that starts at a shown key frame. Where a
ladder's key-frame samples lack one, a producer that puts one back must put back the
stream's own first sequence header OBU, byte for byte, after each such unit's temporal
delimiter: §7.3 refuses any other bytes (`floor-av1-malformed`). The sequence header in
the ladder's sample entry (`av1C`) is not always the stream's: an encoder may write it
before it settles its coding tools, so that it differs from the in-band one in its tool
flags, and a stream with that header put back is refused. The packager writes its own
`av1C` from the in-band header (§7.6). A ladder whose key frames carry no in-band header
cannot be taken in the CMAF form (§7.7), whose units are its samples as they are.
The plan a supplied floor is made against is the **keyframe plan**, the file
`plan-<id>.txt`: each piece's first frame in decimal, one per line, each line ended by a
line feed. Its pieces' starts are the plan of §4.2, and `wai-pack plan` writes it from the
source and the policy before any floor is encoded.
**7.4** The floor is presentation. Its output is never compared with the primary's, and
no tier or `replicate` claim covers it.
**7.4** The floor is presentation. Its output is never compared with the primary's. A
floor object's manifest writes `intent: "replicate"`, which promises only what its
capability's decoder conformance promises (SPEC §7: `wai.video.av1` is registered
`standard-tolerance`); no tier and no claim against a primary or a source covers it.
**7.5** A floor produced by an encoder that is not a pure function of its input (§11)
**MUST** name that encoder and its version in `derived_from.renderer`.
**MUST** name that encoder and its version in `derived_from.renderer`, and, where the
encoder is hardware, the device and the driver that ran it.
**7.6** *CMAF.* The floor of a video component is also written as CMAF files, which no
stage index lists: `floor/<id>/init.mp4`, and one fragment per piece,
`floor/<id>/<SHA-256 of the fragment>.m4s`. Box layouts are ISO/IEC 14496-12's, with the
AV1 binding's sample entry; every integer is big-endian and every time 0:
**7.6** *CMAF.* Each floor rung's floor is also written as CMAF files, which no stage
index lists: `floor/<floor name>/init.mp4`, and one fragment per piece,
`floor/<floor name>/<SHA-256 of the fragment>.m4s`. Box layouts are ISO/IEC 14496-12's,
with the AV1 binding's sample entry; every integer is big-endian and every time 0:
- `init.mp4`: `ftyp` (major brand `cmfc`, minor version 0, compatible `cmfc`, `iso6`,
`av01`), then `moov` holding `mvhd` (version 0, timescale `tb_num`, rate 1, volume 1,
@ -692,6 +734,112 @@ AV1 binding's sample entry; every integer is big-endian and every time 0:
The codecs string of the floor is the AV1 binding's short form,
`av01.<profile>.<level, two digits><M or H>.<bit depth, two digits>`.
**7.7** *A supplied CMAF floor.* With `floor.supplied_form = "cmaf"`, a supplied floor is
an existing ladder's CMAF files rather than OBU streams: per floor rung of floor name *f*
(§7.1), a directory `<f>/` holding `init.mp4` and the floor's media segments, which are
every other file of `<f>/`, each named `*.m4s` and in no directory below it, in byte order
of their names, at least one. The floor's temporal units are the segments' samples, in
order, each a temporal unit without its temporal delimiter: a unit is the two bytes
`0x12 0x00` (a temporal delimiter OBU with its size field and no extension) followed by the
sample. Boxes are ISO/IEC 14496-12's; a box's 32-bit size is at least 8, a size of 1 is the
64-bit size that follows its type (at least 16), and a size of 0 is refused; a box's
children tile its body:
- `init.mp4`: its top-level boxes tile the file; one `moov`, holding one `trak` and one
`mvex`; the `trak`'s `tkhd` names the track, its `mdia`'s `mdhd` gives the timescale
*T*, its `hdlr` is of handler type `vide`, and its `stsd` holds one sample entry, of type
`av01`; an `edts`, where the `trak` has one, holds an `elst` of one entry, at media
time 0 and rate 1; and the `mvex` holds one `trex`, of the track, whose defaults a
sample takes.
- a media segment: its top-level boxes tile the file: boxes of the types `styp`, `sidx`,
`prft`, `emsg`, `free` and `skip`, then one or more `moof`, each followed by an `mdat`,
and nothing else. A `moof` holds an `mfhd` and one `traf`, and nothing else; the `traf`
holds one `tfhd` of the track, one `tfdt` and one or more `trun`, and nothing else; the
`tfhd`'s flags are among `0x2`, `0x8`, `0x10`, `0x20` and `0x20000` (no base data
offset, no empty duration); each `trun`'s are among `0x1`, `0x4`, `0x100`, `0x200`,
`0x400` and `0x800`, `0x1` (its data offset) among them. A sample's duration, size and
flags are its `trun`'s (the first sample's flags its first-sample flags where the `trun`
gives them), else the `tfhd`'s defaults, else the `trex`'s; its bytes start at the
`moof`'s first byte plus its `trun`'s data offset, a run's samples one after another,
and lie in the `mdat` after the `moof`.
A packager **MUST** refuse, before it writes anything, after the directory's listing
(§7.3), floor rung by floor rung in ladder order and segment by segment in order:
1. a floor rung with no `<f>/init.mp4` (`floor-stream-missing`); another file of `<f>/`
that is not a media segment, or no media segment (`floor-cmaf-malformed`);
2. an `init.mp4` that is not the above (`floor-cmaf-malformed`), or whose timescale is 0
or whose edit list is another (`floor-cmaf-timing`);
3. a media segment that is not the above, or that holds a sample of no bytes
(`floor-cmaf-malformed`), or a sample with a composition offset other than 0 or a
`moof` whose decode time is not where the one before it ended (`floor-cmaf-timing`),
each where it is read; then one whose first sample is not a sync sample
(`sample_is_non_sync_sample` set) (`floor-cmaf-malformed`); then a sample that does
not last one frame (`duration · num = T · den`), or a segment whose first decode time
is not the frame where the segment before it ended, the first at frame 0
(`dts · num = frame · T · den`) (`floor-cmaf-timing`); then its units, as §7.3 reads a
stream's (`floor-av1-malformed`, a unit's own faults held to the end);
4. then, as §7.3: a unit count other than the source's frames (`floor-frame-count`), and
the faults held back (`floor-av1-malformed`); then an `init.mp4` whose `av01` entry has
no `av1C`, or whose `av1C` profile, level, tier, bit depth, monochrome and chroma fields,
or whose sample entry's width and height, are not the sequence header's and its
maximum frame size (`floor-cmaf-malformed`): a player configures its decoder from them,
and §8.3's playlists name the sequence header's; then a sample that is a sync sample where
its unit does not start at a shown key frame, or that is not one where its unit does
(`floor-cmaf-malformed`): the ladder's sample flags reach players unchanged, and
players seek by them;
5. other than one media segment per piece of the plan, each holding exactly its piece's
frames (`floor-cmaf-pieces`);
6. a key frame §7.3 refuses (`floor-keyframe-mismatch`).
The floor's CMAF files are then the supplied ones, byte for byte: `floor/<f>/init.mp4`
the supplied `init.mp4`, and per piece `floor/<f>/<SHA-256>.m4s` its media segment (§7.6's
writer is not used), which §8.3's playlists and MPDs list. The package also carries the
supplied floor's listing as `floor.listing`: its SHA-256 is `floor.supplied_listing`, which
the policy digest, and so the receipt, binds, and it names each of the ladder's files by
its SHA-256, so the receipt binds the ladder's bytes. A server may hold those files once,
for the ladder and the package alike (by a hard link, or by their content address): they
are the same bytes. The floor objects carry the units as §7.2 frames them, as in the OBU
form.
**7.8** *The floor-only profile.* A component of `profile = "floor-only"` is its floor
rungs alone: no base, no refinement and no source (§3.4 item 8). It is for a library that
delivers its standard-codec renditions as WAI objects, each named by its content hash,
listed in a signed stage index and bound to a signed receipt, without the integer lane.
- *Its pieces* are its first floor rung's: in the CMAF form (§7.7), one piece per media
segment; in the OBU form (§7.3), one piece from each of the stream's shown key frames
to the next, the stream's first unit one (`floor-keyframe-mismatch` otherwise), and the
first floor rung's unit count is the component's frame count. A piece of more than
`max_ms` (§4.4) is refused (`floor-piece-length`); `min_ms` and `target_ms` do not
apply, and the scene-cut segmenter does not run. Every other floor rung is held to those
pieces as §7.3 and §7.7 hold a floor to a plan. A piece's kind is `none` (§6.2), its
flags 0; a rule that states `when.piece_kind` matches none of them, and its moments are
§8.1's.
- *Its objects*: each piece has one floor object per floor rung (§7.1) and nothing else.
A floor object presents no base, so its manifest is §5.2's for its capability with no
`derived_from`, and its entry's flag bit 2 is clear (§6.3); everything else is §7.2's.
Every class lists the floor only (§8.1): no catalog lists a WAI object, the MoQ catalog
is the floors' tracks, and the package has no WAI playlist or MPD.
- *What it attests*: the receipt signs the policy, so the supplied floor's listing, and
the stage index, so every floor object's content hash, length and capability; a
verifier recomputes the dedup counts, holds every object to its hash and to §7.2's
framing, its units to the AV1 stream's structure (temporal units, one per frame,
sequence headers, shown key frames at the piece starts), and the CMAF files to the
units (§7.6) or, in the CMAF form, to the ladder's bytes through `floor.listing`
(§7.7). A floor-only package's catalogs list no WAI object: a sink receives the floor's
CMAF files through HLS or DASH, or the floor's MoQ track. In the CMAF form it can check
each segment's SHA-256 name against `floor.listing`, which the policy pins and the
receipt signs; in the OBU form a segment's name is bound only through a verifier that
rebuilds it from the objects (§7.6). So a sink's binding of a frame to a receipted
object (browser-sink §7) does not apply to a floor-only package.
- *What it does not attest*: a floor states no tier (§7.4): no decoded-output digest is
stated or checked, so nothing says what a decoder makes of the units; there is no
source, so no `sse` and no fidelity to anything; there is no primary, so no claim
against one, and the floor objects' `intent: "replicate"` promises their capability's
decoder conformance and nothing more (§7.4); and the pieces are not classified. It attests delivery, not
pictures.
## 8. Classes, catalogs and delivery
**8.1** *What a class lists.* The stages listed for a class are a pure function of the
@ -704,7 +852,8 @@ catalog bytes.
`e_ms > from_ms`. Rule *i* matches it when each condition the rule states holds: its
kind is in `when.piece_kind`, and a tag of a moment it lies in is in
`when.moment_tag`. Matching rules fold in document order (§3.4).
- A floor-only class lists the floor (`0xFF`). Otherwise the class lists
- A floor-only class lists the floor (`0xFF`), and every class lists only the floor of a
piece with no base, a floor-only component's (§7.8). Otherwise the class lists
`min(max_layer, the rules' then.max_layer, the piece's highest layer)`; under
`max_kbps`, while the listed prefix needs more than `max_kbps`, that is
`ceil(8 · bytes · num / (1000 · duration · den))` kilobits per second over the bytes of
@ -737,18 +886,20 @@ second; a variant's `BANDWIDTH` is the largest over the pieces it lists and
`AVERAGE-BANDWIDTH` the rate of all their bytes over all their durations. A floor
variant's bytes per piece are its fragment's; a WAI variant's are the listed bases' and
refinements', over the pieces its HTTP view lists (above). Every playlist
line ends with a line feed. For component *c*, of frame size `W×H`, whose floor has
codecs string *F* and maximum frame size `FW×FH`:
line ends with a line feed. For component *c*, of frame size `W×H`, and each of its
floor rungs, in ladder order, of floor name *f* (§7.1), codecs string *F* and maximum
frame size `FW×FH`:
- `hls/classic/master.m3u8`: `#EXTM3U`, `#EXT-X-VERSION:7`,
`#EXT-X-INDEPENDENT-SEGMENTS`, `#EXT-X-STREAM-INF:BANDWIDTH=<b>,AVERAGE-BANDWIDTH=<a>,CODECS="F",RESOLUTION=FWxFH`,
`../classic/floor-<c>.m3u8`: a URI that names the same playlist from every class's
`#EXT-X-INDEPENDENT-SEGMENTS`, then per floor rung
`#EXT-X-STREAM-INF:BANDWIDTH=<b>,AVERAGE-BANDWIDTH=<a>,CODECS="F",RESOLUTION=FWxFH` and
`../classic/floor-<f>.m3u8`: a URI that names the same playlist from every class's
directory, so each class's master differs from this one only by the session-data
line, as [http-delivery](http-delivery.md) §11.1 and §11.8 require.
- `hls/classic/floor-<c>.m3u8`: `#EXTM3U`, `#EXT-X-VERSION:7`,
- `hls/classic/floor-<f>.m3u8`, per floor rung: `#EXTM3U`, `#EXT-X-VERSION:7`,
`#EXT-X-TARGETDURATION:<t>`, `#EXT-X-MEDIA-SEQUENCE:0`, `#EXT-X-PLAYLIST-TYPE:VOD`,
`#EXT-X-INDEPENDENT-SEGMENTS`, `#EXT-X-MAP:URI="../../floor/<c>/init.mp4"`, then per
piece `#EXTINF:<S.mmm>,` and `../../floor/<c>/<sha256>.m4s`, then `#EXT-X-ENDLIST`.
`#EXT-X-INDEPENDENT-SEGMENTS`, `#EXT-X-MAP:URI="../../floor/<f>/init.mp4"`, then per
piece `#EXTINF:<S.mmm>,` and `../../floor/<f>/<sha256>.m4s`, then `#EXT-X-ENDLIST`.
- `hls/<class>/master.m3u8`: the classical master, byte for byte, with, when the class
lists a WAI object over HTTP, `#EXT-X-SESSION-DATA:DATA-ID="science.transaction.wai.multivariant",VALUE="wai.m3u8"`
after `#EXT-X-INDEPENDENT-SEGMENTS`, and no other change.
@ -759,8 +910,9 @@ codecs string *F* and maximum frame size `FW×FH`:
`#EXT-X-STREAM-INF:BANDWIDTH=<b>,AVERAGE-BANDWIDTH=<a>,CODECS="<union>",X-WAI-FLOOR="<floor>",RESOLUTION=WxH`,
`wai-<c>.m3u8`. The union and the floor are [http-delivery](http-delivery.md) §4.2's
over the objects the class lists.
- `hls/<class>/wai-<c>.m3u8`: the floor playlist's lines without `#EXT-X-MAP`, adjacent
to it ([http-delivery](http-delivery.md) §11.2); per piece, `#EXT-X-GAP` when the
- `hls/<class>/wai-<c>.m3u8`: the first floor rung's playlist's lines without
`#EXT-X-MAP`, adjacent to it ([http-delivery](http-delivery.md) §11.2) and so to every
floor rung's, which list the same pieces; per piece, `#EXT-X-GAP` when the
class's HTTP view lists nothing of it (a floor-only piece, or one whose base is not of
the default base capability), `#EXTINF:<S.mmm>,`, each refinement the class lists,
in entry order, as `#WAI-LAYER:N=<layer>,URI="../../objects/<hash>.wai#n=<byte_len>"`,
@ -778,10 +930,13 @@ over the component's whole duration and its target duration, `<Period id="p0" st
one `AdaptationSet`, `</Period>` and `</MPD>`, indented by two spaces a level:
- `dash/classic.mpd`: `<AdaptationSet id="1" contentType="video" mimeType="video/mp4" codecs="F" width="FW" height="FH" segmentAlignment="true" startWithSAP="1">`
holding `<Representation id="<c>-floor" bandwidth="<b>">` with
`<SegmentList timescale="<num>">`: `<Initialization sourceURL="../floor/<c>/init.mp4"/>`,
holding, per floor rung, `<Representation id="<f>-floor" bandwidth="<b>">` with
`<SegmentList timescale="<num>">`: `<Initialization sourceURL="../floor/<f>/init.mp4"/>`,
a `SegmentTimeline` of one `<S t="<(start − first start)·den>" d="<d·den>"/>` per
piece, and one `<SegmentURL media="../floor/<c>/<sha256>.m4s"/>` per piece.
piece, and one `<SegmentURL media="../floor/<f>/<sha256>.m4s"/>` per piece. With
several floor rungs, the `AdaptationSet` carries no `codecs`, `width` or `height`, and
each `Representation` carries its own after `bandwidth`:
`<Representation id="<f>-floor" bandwidth="<b>" codecs="F" width="FW" height="FH">`.
- `dash/<class>.mpd`, when the class's HTTP view lists a WAI object:
`<AdaptationSet id="1" contentType="video" mimeType="application/wai" codecs="<union>" width="W" height="H">`
holding `<EssentialProperty schemeIdUri="tag:transaction.science,2026:wai/http-delivery"/>`,
@ -819,9 +974,10 @@ does not hold. A sink receives every track a track depends on (moq-streaming-for
§4.1), so a dependency is all of them. A refinement track carries
`wai_delivery_timeout_ms` (§8.6), a catalog field this extension defines under the `wai_`
prefix of moq-streaming-format §4. The base track has `altGroup` 1 when the component has
a floor: the floor is a track `<c>/floor` of `packaging` `"cmaf"`, in the same namespace,
with `altGroup` 1, `renderGroup` 1, `codec`, `width` and `height`, and a sink that
selects the floor subscribes to no layer track. The receipts tracks follow, one per media
a floor: each floor rung's floor, in ladder order, is a track `<f>/floor` for its floor
name *f* (§7.1), of `packaging` `"cmaf"`, in the same namespace, with `altGroup` 1,
`renderGroup` 1, `codec`, `width` and `height`, and a sink that selects a floor
subscribes to no layer track. The receipts tracks follow, one per media
track in its order, each `{"isLive": false, "name": "<name>/receipts", "namespace",
"packaging": "wai-receipts"}`. The catalog passes moq-streaming-format §4.1's check, and a
packager writes no other. A package holds no receipt: the publisher signs each track's
@ -956,7 +1112,8 @@ figure and class that do not cohere, or a legacy label (`receipt-energy`); a sig
that does not verify (`receipt-signature`).
**9.2** Live windows chain by the parent link with parent kind `live-window`. A re-pack
of an earlier package **MAY** name it with parent kind `re-pack`.
of an earlier package **MAY** name it with parent kind `re-pack`, and one that takes its
bases and refinements from it **MUST** (§11.5).
The reference live packer (`wai-pack live`, `wai_pack::live`) takes a source a frame at a
time, cuts it with the segmenter of §4.3, which decides a frame once `lookahead_frames`
@ -1024,7 +1181,11 @@ a `measurement` claim about it ([jwp-receipts](jwp-receipts.md) §2.4.8,
`wai:video-package-receipt-id`, signed with the package key and checked against the
receipt before it is written. A verifier refuses a metered package without it
(`measurement-claim-missing`) or with one that does not verify and check against the
receipt (`measurement-claim-invalid`).
receipt (`measurement-claim-invalid`). The figure brackets the whole pack: it starts once
the policy's own refusals (§3.4, §11.1) have passed, before the source's first read, and
covers both reads of the source, the supplied floor's checks (§7.3, §7.7), a parent's
verification (§11.5), every piece's coding and every file written, and stops before the
receipt is sealed. A packager **MUST NOT** leave any of that work outside it.
## 10. Royalty-free packaging
@ -1041,23 +1202,30 @@ royalty-free by its standards body"; it is not a freedom-to-operate opinion.
policy.toml policy.json plan-<c>.txt index-<c>.wsix package.receipt.json
objects/<content hash>.wai …
floor/<c>/init.mp4 floor/<c>/<sha256>.m4s …
floor/<f>/init.mp4 floor/<f>/<sha256>.m4s … (per floor rung, of floor name f)
floor.listing (a supplied CMAF floor's listing, §7.7)
hls/classic/… hls/<class>/… dash/… moq/catalog.json stages/<class>.json
claims/<receipt_hash>.measurement.json (a metered package)
LISTING
`policy.toml` is the policy as given; `policy.json` its effective canonical JSON
(§3.2). `LISTING` is the listing (SPEC §3.1) of every other file, and its SHA-256 is the
**pack digest**. A component or class id that cannot be one path segment of a listing,
two class ids equal once `A`–`Z` are mapped to `a`–`z`, and a class named `classic` in
any case (ids name paths, and paths fold case) are refused (`pack-id`).
**pack digest**. A component or class id or a floor name (§7.1) that cannot be one path
segment of a listing, two class ids or two floor names equal once `A`–`Z` are mapped to
`a`–`z`, and a class named `classic` in any case (ids name paths, and paths fold case)
are refused (`pack-id`).
**11.2** *Re-pack equivalence.* Given the same source bytes, effective policy, supplied
floor, signing key and packager identity, a conforming reference packager **MUST**
produce byte-identical package files on every machine, except the energy figure and
measurement claim of a metered package and floor objects §7.5 covers. A verifier
produce byte-identical package files on every machine and whichever fabric runs each
step (§11.6), except the energy figure and measurement claim of a metered package and
floor objects §7.5 covers. A verifier
**MAY** pack again and compare listings. A packager whose identity differs is not held
to this.
to this. A re-pack from a parent (§11.5) is held to it with the parent among its inputs;
and where the parent was packed by a conforming packager of the same identity, from the
same source, under base
and refinement rungs of the same capabilities and parameters, its files are those of a
pack that codes every piece, but for its receipt's parent and so `LISTING`.
**11.3** *Verification.* A verifier of a package, without its sources, applies these
checks in this order and refuses at the first that fails; a check that reads files a
@ -1077,7 +1245,7 @@ failed check names is not applied:
effective canonical JSON, `royalty_free_only` forced on where `policy.json` says
`true` (`policy-json-mismatch`; an override never turns it off, §3.2, so a
`policy.json` that says `false` over a `policy.toml` that says `true` is refused
here); its ids can name files (`pack-id`, §11.1); and under that effective policy it
here); its ids and floor names can name files (`pack-id`, §11.1); and under that effective policy it
asks for nothing a packager may not emit (§3.6's reason; under `royalty_free_only`, a
patent-pool floor is `license-refused`).
5. The receipt's components are the policy's, by id, in order, each of the policy's
@ -1089,18 +1257,20 @@ failed check names is not applied:
class are the component's; its string table is the component's id, the class ids
in policy order, then each capability at its first use; its class records are the
policy's classes, in order, with their `max_layer`, floor-only flag and `max_kbps`;
every piece's kind is one a video piece has; its rules and moments are §8.1's from
every piece's kind is one a video piece has, `none` exactly in a floor-only
component (§7.8); its rules and moments are §8.1's from
its kind and span; its entries are the rungs of its ladder (§5.7), by role,
capability and layer: its base, each refinement in layer order, each floor; each
capability and layer: its base, each refinement in layer order, each floor (a
floor-only component's, its floors alone); each
refinement's deadline is its plan's (§8.6); and its class plan is §8.1's from its
entries;
- the plan file holds the index's starts and its digest is the header's
(`plan-mismatch`);
- every entry's object is present (`object-missing`) and keeps the object rules of
§6.3, its counted bytes included;
- before any frame is decoded, each piece's floor object, where the policy has a floor
rung and the object's payload reads as §7.2's framing, holds one unit per frame of
its piece (`floor-object-mismatch`);
- before any frame is decoded, each piece's floor objects, where the policy has floor
rungs and an object's payload reads as §7.2's framing, hold one unit per frame of
their piece (`floor-object-mismatch`);
- every base and refinement, in entry order: a base decodes by its capability (a
still is a PNG §5.7 reads, its one frame held for the piece), or it is
`prefix-digest`; its manifest is the one §5.2 states for its piece's frames and its
@ -1111,61 +1281,198 @@ failed check names is not applied:
does not apply, ends the check;
- then every decode-equivalent prefix decodes to its `prefix_digest`
(`prefix-digest`);
- when all of that holds, the floor: per piece, one floor object of the floor rung's
capability whose renderer, settings, framing header, unit count and target are
§7.2's (`floor-object-mismatch`) and which presents the piece's base
(`floor-motif-mismatch`); its units each one temporal unit holding a frame, the
first of the first piece carrying a sequence header, every sequence header the
first's bytes, every shown key frame carrying one (`floor-av1-malformed`); each
piece opening on a shown key frame, and no other unit being one unless the policy
allows extra key frames (`floor-keyframe-mismatch`); and the CMAF files are the
ones its temporal units give (§7.6, `floor-cmaf-mismatch`);
- when all of that holds, the floors, floor rung by floor rung in ladder order: per
piece, one floor object per floor rung, the rung's the *k*-th floor entry for the
*k*-th floor rung, of the rung's capability, whose renderer, settings, framing
header, unit count and target are §7.2's (`floor-object-mismatch`) and which
presents the piece's base (`floor-motif-mismatch`), or, in a floor-only component,
which carries no `derived_from` (`floor-object-mismatch`); its units each one temporal unit
holding a frame, the first of the rung's first piece carrying a sequence header,
every sequence header the first's bytes, every shown key frame carrying one
(`floor-av1-malformed`); each piece opening on a shown key frame, and no other unit
being one unless the policy allows extra key frames (`floor-keyframe-mismatch`); and
the rung's CMAF files are the ones its temporal units give (§7.6,
`floor-cmaf-mismatch`); or, for a supplied floor in the CMAF form (§7.7), `floor.listing`
is a listing that hashes to `floor.supplied_listing`, `floor/<f>/init.mp4` is the file
of its line `<f>/init.mp4` and reads as §7.7's initialization segment, its `av1C` and
sample entry size the floor's sequence header's, and the
listing's media segments of `<f>/`, in its order, are one per piece, piece *k*'s
`floor/<f>/<its SHA-256>.m4s`, reading as §7.7's media segment, opening on a sync
sample, each sample one frame and the first at the piece's start, its samples the
piece's floor units without their temporal delimiters, each a sync sample exactly
when its unit starts at a shown key frame (`floor-cmaf-mismatch`);
- then the catalogs are the ones the index, the objects and the floor give, and an
index no catalog can be written for (a start past `2^53 − 1`) is refused
(`catalog-mismatch`).
7. A metered package's measurement claim (§9.4: `measurement-claim-missing`,
`measurement-claim-invalid`); an object file no entry names (`object-unlisted`); a
`measurement-claim-invalid`, a fabric record naming a step this extension does not
define, §11.6, among the latter); an object file no entry names (`object-unlisted`); a
catalog file past the ones given (`catalog-unexpected`); any other file
(`unexpected-file`).
**11.4** *What this revision packs.* The reference packager packs one video component:
bases of `wai.video.int_motion` (§5.5, §5.6) and stills of `wai.image.png` (§5.7);
refinements of `wai.video.int_refine` over an `int_motion` base (§5.4); each piece by its
ladder, a rule's ladder subset included (§5.7); and a supplied AV1 floor (§7.3). Its live
packer packs the same pieces in windows, without a floor (§9.2). It refuses by name,
ladder, a rule's ladder subset included (§5.7); and a supplied AV1 floor per floor rung,
one or several (§7.1), in the OBU form (§7.3) or the CMAF form (§7.7); and floor-only
components (§7.8). Its live
packer packs the same pieces in windows, without a floor (§9.2). It runs `base-search`,
`sse` and `object-hash` on a GPU that qualifies, where it is built to and asked to, and
every other step on the CPU (§11.6). It refuses by name,
before writing anything, what it does not pack yet: another medium
(`pack-media-unsupported`), a floor to encode (`pack-floor-encode-unsupported`), and a rung
of a capability it does not encode, or a refinement over a base it does not refine
(`pack-capability-unsupported:<cap>`, every one naming the capability of the rung it does
not pack); and a component with no source (`pack-source-missing`) or whose source's frame
rate is not its timebase (`pack-source-rate`). Where its own work fails it
refuses by name too, and writes nothing: an encode the encoder refuses, such as a piece
not pack); and a component of the standard profile with no source (`pack-source-missing`;
a floor-only component has none, §7.8) or whose source's frame rate is not its timebase
(`pack-source-rate`). Where its own work fails it
refuses by name too, and leaves nothing written (a file it wrote before the refusal is
removed): an encode the encoder refuses, such as a piece
past the samples it holds, or an object it wrote that does not count (`pack-encode`); a
piece past `2^32 − 1` units (`pack-piece-length`); catalogs it cannot write, the case
§11.3 refuses as `catalog-mismatch` (`pack-catalog`); a meter that was asked for and
gives no figure, a span too short to reach a microjoule or a figure past `2^64 − 1`
(`pack-meter`, never an unmetered package in its place); a measurement claim it cannot
write (`pack-measurement-claim`); and a listing it cannot write (`pack-listing`). It
write (`pack-measurement-claim`); a listing it cannot write (`pack-listing`); and a source
that does not read the same twice (`pack-source-changed`) or a supplied floor stream that
does not (`floor-listing-mismatch`): it reads each a frame or a temporal unit at a time,
once to cut and check it and once to code it, and holds neither whole. What it holds is
not a function of the source's length but for a record per piece and per entry and a byte
per frame of each floor (whether it starts at a key frame): the frames of the pieces it
codes at once, which it chooses, each piece coded alone (§4.1), so the package is the same
for any number; one piece of each floor; and, for the catalogs, one object at a time,
read back from where it wrote it; except a re-pack, which holds its parent whole while it
verifies it (§11.5), so its memory grows with the parent. Each file is written whole as it
is made. It
writes a package only into a directory that is new or holds nothing, and refuses any
other before it packs (`pack-out-not-empty`): written among another package's files, it
would leave behind the ones it does not write.
**11.5** *Re-pack from a parent.* A packager **MAY** take every piece's base and
refinements from an earlier package, its **parent**, instead of coding them, so a
component's integer base is coded once and taken by every package made from the same
source after it. It reads the source as for a pack that codes (§4: its pieces and their
kinds, §4.3, §4.6, are this source's), and **MUST** refuse, checks 1 and 2 before it
writes anything and check 3 as it reads each piece, leaving nothing written (§11.4):
1. a parent that does not verify as §11.3 verifies a package (`repack-parent-invalid`,
with the reason the parent fails for);
2. a parent with no component of the component's id, media and timebase, or whose pieces
are not this source's, piece by piece: another number of pieces, or a piece of
another start, duration, flags or kind, or whose ladder (§5.7, under the parent's
policy) codes its base and refinements in rungs of other capabilities or other
parameters (§3.3) than this policy's ladder for the piece, in layer order, or with
another deadline (§8.6) (`repack-parent-mismatch`);
3. a piece whose prefixes, each the parent's base decoded and its refinements applied in
layer order by a staged-delivery §4 sink, do not reconstruct this source with the
`sse` the parent's entry states (§6.6) (`repack-source-mismatch`): a parent packed
from another source.
It then writes, for each piece, the parent's base and refinement objects and their
entries' fields (§6.2: content hash, lengths, capability, role, layer, tier, prefix
digest, `sse`, deadline) in place of coding them, and the floors as it would; its
receipt names the parent's receipt with parent kind `re-pack` (§9.1). A verifier holding
the parent **MAY** check a re-pack against it: the parent verifies
(`repack-parent-invalid`), the re-pack's receipt names the parent's receipt with parent
kind `re-pack`, and each component's pieces are the parent's, piece by piece, of the same
start, duration, kind and flags, whose base and refinement entries are the parent's
entries, every field the same but the entry's place in its index: the entry it refines
counted from its piece's first entry, and the duplicate flag, which an index's own
entries decide (`repack-parent-mismatch`). A re-pack holds no source of its parent's
bases; what binds a reused base to this source is the third check, and what binds it to
the parent is the receipt.
**11.6** *Steps and fabrics.* The steps of a pack and a verify are named by these terms:
| Step | What it computes |
|---|---|
| `source-decode` | a source's frames from a coded rendition, before a pack, by a producer's tool (§4.7 reads the result) |
| `source-read` | a source's frames or samples (§4.7) |
| `segment` | the pieces (§4.3) and their kinds (§4.6) |
| `base-search` | the integer base's motion search (§5.5) |
| `base-code` | the rest of the integer base (§5.5), its step (§5.6) and a still (§5.7) |
| `refine-code` | refinement layers, each applied by the reference sink (§5.4) |
| `sse` | an entry's `sse` (§6.6) |
| `object-hash` | an object's content hash (§5.3) |
| `digest` | the SHA-256 digests: decoded-output digests (§6.5), listings, file names |
| `floor-read` | a supplied floor's units, CMAF boxes and listing (§7.3, §7.7) |
| `floor-decode` | a floor's units decoded to pictures (item 4 below) |
| `index` | the stage indexes, catalogs, receipt and claim (§6, §8, §9) |
| `io` | reading and writing files |
Every step is a function of its inputs, defined in integers (and `floor-decode` by the
AV1 decoding process), and none names a fabric:
1. *Packages.* A packager **MAY** run a step on any fabric whose output is the step's
for every input. It **MUST NOT** run a step on a backend that has not, on each device
it opens and before it is used, given the step's output for every input of a
qualifying set, nor at all on one that computes otherwise than the step's
definition, such as in floating
point where the step is defined in integers, or with a learned approximation. A
backend that cannot take a call (a size, a lost device) leaves it to the CPU, with the
same output. So §11.2 holds across fabrics: the package files are the same bytes
whichever fabric ran each step, and only a metered package's measurement claim says
where they ran. A qualifying set holds, at the least:
- for the motion search (§5.5), frame pairs of noise, of a smooth field, of a flat
field (every candidate ties in cost) and of alternating columns (two vectors tie
in cost and in length), at sizes that are not a whole number of blocks, at three
block sizes or more, at full-pel and half-pel precision, and with search ranges
that reach the frame's edge;
- for SSE, inputs of at least three lengths, among them one byte and one past
4096 bytes;
- for BLAKE3, messages of 0 and 1 bytes, of 1023, 1024 and 1025 bytes around a chunk,
and longer than four chunks.
(Informative: the reference packager's set is `wai_pack::fabric::qualifying_frames`
and the inputs of `wai_pack::fabric::qualify`.)
2. *Verdicts.* A verifier's verdict and its reason are functions of the package
(§11.3). A verifier **MAY** compute a check on another fabric where the package states
the value the check compares with, such as an object's content hash: a match shows
that the fabric computed the check, and a mismatch **MUST** be computed again on the
reference implementation before it is reported. Every other check runs on a backend
held to the reference's output as item 1 holds a packager's. A verdict that changes
with the fabric is the verifier's fault, never the package's.
3. *Hardware encoders.* A hardware encoder's output depends on the chip, its firmware
and driver, and its settings, and no rule fixes it, so no step of this extension is
computed by one. A floor a packager is given is an input, whatever made it (§7.3,
§7.7); a floor a packager encodes on such hardware is one §7.5 covers, whose
`derived_from.renderer` names what §7.5 requires, and §11.2 does not hold its bytes.
4. *Decoding a floor.* The AV1 decoding process fixes every output sample of a stream
whose sequence header has `film_grain_params_present` 0, and of every stream before
film grain is applied (AV1 §7.2), so conformant decoders on any fabric give the same
pictures of a floor's units. A floor states no decoded-output digest (§7.4), so a
decode of it has no stated value to compare with: a verifier that decodes floors
**MUST NOT** refuse a package for what a decoder other than the reference gives, nor
read a hardware decoder's error or concealment as a verdict. A hardware decoder's
frames may be held in a wider format than the stream's bit depth (a 10-bit sample
shifted into the high bits of a 16-bit word); a reader of them recovers each sample
exactly or refuses the frame, and never rounds. (Informative: `wai-pack floor-decode`
reports each piece's digest from either decoder, for comparing them.)
5. *The fabric record.* A metered package's measurement claim **MAY** carry a fabric
record (jwp-receipts §2.4.8, energy-measurement §6.3): each step the metered span ran,
with every fabric that ran it and its backend, and the figure's share on each. Its
steps are this section's terms (§11.3 step 7). An unmetered package carries no claim,
so no record: which fabric ran a step is not part of the package, and two packages
that differ only in where their steps ran are the same files.
## 12. Reasons
| Reason | Where |
|---|---|
| `policy-toml` (not UTF-8, a byte-order mark, not TOML 1.0, nesting past 32), `policy-float`, `policy-datetime`, `policy-negative`, `policy-integer-range` | §3.2 |
| `policy-unknown-key`, `policy-missing-key`, `policy-type`, `policy-value`, `policy-schema` | §3.3 |
| `policy-too-many-components`, `policy-too-many-rungs`, `policy-too-many-classes`, `policy-too-many-rules`, `policy-too-many-moments`, `policy-duplicate-id`, `policy-lead`, `policy-open-gop`, `policy-piece-bounds`, `policy-ladder-component`, `policy-refines-role`, `policy-dangling-refines`, `policy-refines-cycle`, `policy-refines-base`, `policy-refines-branch`, `policy-no-base`, `policy-class-layer`, `policy-rule-ladder`, `policy-layer-lag`, `policy-too-many-deadlines`, `policy-deadline-unreachable` | §3.4 |
| `policy-too-many-components`, `policy-too-many-rungs`, `policy-too-many-classes`, `policy-too-many-rules`, `policy-too-many-moments`, `policy-duplicate-id`, `policy-lead`, `policy-open-gop`, `policy-piece-bounds`, `policy-ladder-component`, `policy-refines-role`, `policy-dangling-refines`, `policy-refines-cycle`, `policy-refines-base`, `policy-refines-branch`, `policy-no-base`, `policy-floor-only`, `policy-class-layer`, `policy-rule-ladder`, `policy-layer-lag`, `policy-too-many-deadlines`, `policy-deadline-unreachable` | §3.4 |
| `capability-unknown`, `capability-not-payload`, `capability-candidate`, `capability-role`, `license-unclassified`, `license-refused`, each naming the capability (and the licence label) | §3.6 |
| `y4m-header`, `y4m-interlaced`, `y4m-colorspace`, `y4m-size-change`, `y4m-truncated`, `wav-format`, `wav-truncated` | §4.7 |
| `index-magic`, `index-version`, `index-truncated`, `index-reserved`, `index-media-class`, `index-role`, `index-tier`, `index-string`, `index-trailing` | §6.2 |
| `index-timebase`, `window-start`, `piece-order`, `piece-entries`, `piece-kind`, `entry-flags`, `entry-order`, `layer-role`, `refines-outside-window`, `refines-mismatch`, `layer-gap`, `tier-entropy-passthrough`, `tier-weakest`, `tier-mismatch`, `digest-without-tier`, `deadline-role`, `floor-derived-from`, `dup-length`, `dup-flag`, `class-plan`, `class-flags` | §6.3, §6.4 |
| `object-length`, `object-hash`, `non-envelope-entry`, `object-lengths`, `object-capability`, `object-refines`, `object-derived-from` | §6.3 |
| `floor-missing`, `floor-listing-mismatch`, `floor-stream-missing`, `floor-av1-malformed`, `floor-frame-count`, `floor-keyframe-mismatch` | §7.1, §7.3 |
| `floor-stream-missing`, `floor-cmaf-malformed`, `floor-cmaf-timing`, `floor-cmaf-pieces` | §7.7 |
| `floor-keyframe-mismatch`, `floor-piece-length` | §7.8 |
| `floor-object-mismatch`, `floor-motif-mismatch`, `floor-av1-malformed`, `floor-keyframe-mismatch`, `floor-cmaf-mismatch`, against a package | §11.3 |
| `receipt-json`, `receipt-version`, `receipt-index-count`, `receipt-index-digest`, `receipt-stage-root`, `receipt-component`, `receipt-policy-digest`, `receipt-counts`, `receipt-parent-kind`, `receipt-energy`, `receipt-signature` | §9.1 |
| `measurement-claim-missing`, `measurement-claim-invalid` | §9.4 |
| `unexpected-file`, `listing-missing`, `listing-mismatch`, `policy-digest-mismatch`, `policy-json-mismatch`, `policy-component-mismatch`, `index-missing`, `index-policy-mismatch`, `plan-mismatch`, `object-missing`, `object-manifest`, `prefix-digest`, `catalog-mismatch`, `catalog-unexpected`, `object-unlisted` | §11.3 |
| `pack-id`, `pack-source-missing`, `pack-source-rate`, `pack-media-unsupported`, `pack-floor-encode-unsupported`, `pack-capability-unsupported` (naming the capability) | §11.1, §11.4 |
| `pack-encode`, `pack-piece-length`, `pack-catalog`, `pack-meter`, `pack-measurement-claim`, `pack-listing`, `pack-out-not-empty` | §11.4 |
| `pack-encode`, `pack-piece-length`, `pack-catalog`, `pack-meter`, `pack-measurement-claim`, `pack-listing`, `pack-source-changed`, `pack-out-not-empty` | §11.4 |
| `repack-parent-invalid`, `repack-parent-mismatch`, `repack-source-mismatch` | §11.5 |

View file

@ -70,8 +70,26 @@ def blake3(b):
return B3.blake3(b)
# Each object's content hash, computed once: an object resolved many times (resolve_uri,
# once per URI that names it) is hashed once. A caller that has checked an object's hash
# against its own record may seed it (seed_content_hash).
_CONTENT_HASH = {}
def content_hash(env):
return blake3(DOMAIN + env)
h = _CONTENT_HASH.get(env)
if h is None:
h = _CONTENT_HASH[env] = blake3(DOMAIN + env)
return h
def seed_content_hash(env, h):
"""Record an object's content hash that the caller has computed and checked."""
_CONTENT_HASH[env] = h
def forget_content_hashes():
_CONTENT_HASH.clear()
# ------------------------------------------------------------------ the registry
@ -3035,7 +3053,11 @@ def resolve_uri(objs, uri):
name = base.rsplit("/", 1)[-1]
if name.endswith(".wai") and re.fullmatch(r"[0-9a-f]{64}", name[:-4]):
cid = name[:-4]
b = next((b for b in objs.values() if cid is not None and content_hash(b).hex() == cid), None)
# An object held under its own content id is found by name, its hash checked; any
# other by its content hash, each object hashed once (content_hash).
b = objs.get(f"{cid}.wai") if cid is not None else None
if b is None or content_hash(b).hex() != cid:
b = next((b for b in objs.values() if cid is not None and content_hash(b).hex() == cid), None)
if b is None:
raise SystemExit("http_verify: %s names no corpus object" % uri)
return b

View file

@ -57,6 +57,44 @@ packages (§6–§11), and their delivery over a simulated link (§8.9).
written by `supplied_floor.py`. The bumper's base, layers and floor are one object
each; the still's piece is carried over HTTP by the floor (§8.3) and over MoQ on the
base track.
- `packs/video-ladder-01/` — a golden package of two floor rungs over one base (§7.1):
the fixture and base rung of `video-base-01`, so its bases are that package's objects,
and two supplied AV1 streams, `floor/hi.obu` at the fixture's size and `floor/lo.obu`
at half its width and height, each written by `supplied_floor.py` (`--scale lo=2`).
Each piece has its base and one floor object per floor rung; each floor has its own
CMAF files under its floor name (`floor/hi/`, `floor/lo/`), its own floor playlist and
MoQ track, and the classical master, every class's master and `dash/classic.mpd` list
both.
- `packs/video-repack-01/` — a re-pack golden (§11.5): `video-ladder-01`'s policy under
another asset id and its supplied floor, packed with every piece's base taken from the
parent its file `parent` names, `video-base-01`, rather than coded. Its objects are
`video-ladder-01`'s; its receipt names `video-base-01`'s receipt as the package it
re-packs (parent kind `re-pack`); and each piece's base entry is the parent's, field for
field. Both verifiers check it against its parent.
- `packs/video-cmaf-01/` — a golden whose supplied floor is in the CMAF form (§7.7):
`video-ladder-01`'s policy with `floor.supplied_form = "cmaf"`, and its two streams as a
media muxer wrote them, `floor/<name>/init.mp4` and `floor/<name>/seg_<k>.m4s`, one
segment per piece, by `supplied_cmaf.py` (ffmpeg's HLS muxer, `-c copy`). The package's
floor files are those files, byte for byte, under their SHA-256; `floor.listing` is the
supplied floor's listing; and each floor object holds its piece's samples, which are the
OBU form's temporal units of the same streams.
- `cmaf-mutations/` — the CMAF golden altered, in `package-mutations/`'s layout: itself
(`ok`); a segment replaced by one of the same samples, a `free` box before it, under its
own SHA-256, which the catalogs name, so its one fault is its binding to `floor.listing`;
`floor.listing` altered; and without it (each `floor-cmaf-mismatch`).
- `packs/video-floor-only-01/` and `packs/video-floor-only-02/` — floor-only goldens
(§7.8): a component of `profile = "floor-only"` with the ladder's two floor rungs and no
base or source, the floor in the CMAF form (`video-cmaf-01`'s files) and in the OBU form
(`video-ladder-01`'s streams). Their pieces are the first floor's segments or shown key
frames, the ladder golden's plan; each piece is its two floor objects, which carry no
`derived_from` and hold the ladder golden's units, of kind `none`; no class lists a WAI
object.
- `ladder-mutations/` — packages a verifier must refuse or accept (§11.3), each the
ladder golden altered (re-sealed with its key where the receipt or `LISTING` alone
would catch it), in `package-mutations/`'s layout: the golden itself (`ok`); piece 2's
two floor objects swapped (`floor-object-mismatch`); the second floor's CMAF files
under the component's name (`floor-cmaf-mismatch`); and a classical master listing one
floor of two (`catalog-mismatch`).
- `mutations/` — stage indexes, objects and version-2 receipts, and `expected.json`:
each case's reason (§6.2–§6.4, §9.1), a well-formed case of each kind among them,
and three receipts carrying a signature only a verifier that checks the equation
@ -86,7 +124,9 @@ packages (§6–§11), and their delivery over a simulated link (§8.9).
window past 32 KiB, bytes after the zlib stream, and its Adler-32. And one dynamic
block of literals twice: with a lone distance code of one bit, read (the one
incomplete code set the zlib library takes), and of two bits, refused.
- `staged-mutations/` — the staged golden altered and re-sealed with its key, in the
- `staged-mutations/` — the staged golden itself (`ok`: verified without its sources,
every layer's prefix digest held to it), and the staged golden altered and re-sealed
with its key, in the
layout of `package-mutations/`: a refinement on another deadline than its plan's, a
piece missing its top layer, a still where the policy's rule now gives the piece the
default ladder (each `index-policy-mismatch`), a top layer coded again at another step
@ -115,7 +155,10 @@ packages (§6–§11), and their delivery over a simulated link (§8.9).
off among them), a missing or corrupted object, a live window no catalog can be
written for, floor objects that do not open on a key frame or are not §7.2's, files
and directories a strict read finds, and a receipt file that is not its canonical
form; and one the verifier must accept (an extra key frame the policy allows).
form; and those the verifier must accept (an extra key frame the policy allows, and a
metered package, §9.4: the golden re-sealed with a 500 mW model meter over one second
and its measurement claim, every member fixed), with a claim about another figure
(`measurement-claim-invalid`) and none (`measurement-claim-missing`).
The fixtures are not committed. `wai-pack fixture gen <name>` writes each from its
definition (`wai-pack/src/fixture.rs`), every byte an integer function of the frame

View file

@ -0,0 +1,29 @@
{
"pack": "video-cmaf-01",
"cases": [
{
"name": "ok",
"reason": "ok",
"remove": []
},
{
"name": "segment-not-the-supplied-one",
"reason": "floor-cmaf-mismatch",
"remove": [
"floor/hi/14cdbe56c8f57b1427ab9c2a9ebf6669ce8edec06fd7cd0961a01d2aaf720889.m4s"
]
},
{
"name": "floor-listing-altered",
"reason": "floor-cmaf-mismatch",
"remove": []
},
{
"name": "floor-listing-missing",
"reason": "floor-cmaf-mismatch",
"remove": [
"floor.listing"
]
}
]
}

View file

@ -0,0 +1,47 @@
688cb303ccb16fcdd21c8cb681f936ba813829e71fbf15df0ccb28b04c134447 dash/classic.mpd
a3aa7658db9b85a9d9a1fed977825189f75c5adad0f5fdfcd70ebd604824c138 dash/mobile.mpd
3f520749a6d2f231cddfd17804ee3629439f3678515e424c44e36cff54d89de9 dash/tv.mpd
4e4d6d55b352c17da028bcbf8d314cdd1f9bb1406367008710788665727dcffa floor.listing
14cdbe56c8f57b1427ab9c2a9ebf6669ce8edec06fd7cd0961a01d2aaf720889 floor/hi/14cdbe56c8f57b1427ab9c2a9ebf6669ce8edec06fd7cd0961a01d2aaf720889.m4s
759f476ce9e9b003d7d797060f9c039141d261dd65212035e96bb157783423c1 floor/hi/759f476ce9e9b003d7d797060f9c039141d261dd65212035e96bb157783423c1.m4s
d3616b6368fc800ce421a492fbd0f6263b9e06ee0af1e8269ce4f20d5cb3653d floor/hi/d3616b6368fc800ce421a492fbd0f6263b9e06ee0af1e8269ce4f20d5cb3653d.m4s
e5583297b1456e46366fe3317784fadf8c165c5e16e864629b194dc46290387e floor/hi/e5583297b1456e46366fe3317784fadf8c165c5e16e864629b194dc46290387e.m4s
eb559df9571de1869981ca82672abbabad528b294b15a1d7bf9b635761c584f8 floor/hi/eb559df9571de1869981ca82672abbabad528b294b15a1d7bf9b635761c584f8.m4s
a8a19ef9cd4d540037ef298097bbc5317de6a99690c8c4a745cc867c034208d6 floor/hi/init.mp4
0e0407f5a552e405846a411627df17537e5c31accca37390c391a7c1d27353af floor/lo/0e0407f5a552e405846a411627df17537e5c31accca37390c391a7c1d27353af.m4s
10b19654062fa37b83c082c922f54529725c36a4ead953b1fbfbbee14d4e79a8 floor/lo/10b19654062fa37b83c082c922f54529725c36a4ead953b1fbfbbee14d4e79a8.m4s
2c484c9bead2b261ac1a18c2aedec11761813f995d11dc9779c5f9b039d59b73 floor/lo/2c484c9bead2b261ac1a18c2aedec11761813f995d11dc9779c5f9b039d59b73.m4s
a855b2701af4e7c8c912448be9fc023f911b4e9e94b65770393c4df6d705b5e8 floor/lo/a855b2701af4e7c8c912448be9fc023f911b4e9e94b65770393c4df6d705b5e8.m4s
c29687008dafdf251b2ca962c3e830f785b38a56c81aee1f4c86f2e8f9115fcc floor/lo/c29687008dafdf251b2ca962c3e830f785b38a56c81aee1f4c86f2e8f9115fcc.m4s
6dd501e27365ce9ef90576771aad73de4d200362e6974551847afc3c90604344 floor/lo/init.mp4
ebdc7e40aecbe8b61124ac78f233b0dfaf2a8c5674d3fc9bb023935de1d9b6cb hls/classic/floor-hi.m3u8
66f5eb8b89b80e7da839b23f39665eb85480c6a725fa29d93556efee673c1b9e hls/classic/floor-lo.m3u8
d793737b69231eface4951001e65b3c52cba864f231246a41e64d49c77ebdc97 hls/classic/master.m3u8
d793737b69231eface4951001e65b3c52cba864f231246a41e64d49c77ebdc97 hls/legacy/master.m3u8
8c3b5e2b18192b383c8df8675acd435b861a2585bc6eaf0c09292754f44a8cef hls/mobile/master.m3u8
c4044eca76959c9f87230484a2b207fb12c0bcaedb8d921eab806014fca53cb8 hls/mobile/wai-v.m3u8
60a6378f46afc9308dc4ac4d138602b16568577616ea0bf4526b142d86899151 hls/mobile/wai.m3u8
8c3b5e2b18192b383c8df8675acd435b861a2585bc6eaf0c09292754f44a8cef hls/tv/master.m3u8
ff4edf2929e380d205c1c74156621185feec53d593ffa968b8dfaf0d05448bcd hls/tv/wai-v.m3u8
5d42147b308330913c3d9c8a868ca83ce4d3f3e460da8d84c84014eb24aaf9d7 hls/tv/wai.m3u8
649330bcfaaee54f802f6b4ddf6e459daca8bb0e8df86c87a9d6bd0d65cd09ea index-v.wsix
68f00abff5ef19f074d510f8cce4592afc2a1d4981a87663965a46dc8bcbe1d3 moq/catalog.json
9f381e2ab764b5e14770b00503c1c90b9c22ba22f87464b2869a70644af11939 objects/08797901ff55d0bb4afba5cffe95df64b7e216f3a0c9ba82006133bb9b6d7f16.wai
07e98fb9ef9ff3fa6bf04f9078da2a3d2423e586feea1061256131a1d1fbb943 objects/24761a434c91c627f11abd6265371966b50573602a200dd7bb04e0d90889326d.wai
d5f9cdd996920e07339b79093b9e4e5cb4237f1780f268220cc6f89c79aea90a objects/399048a078b0f2983149266a44eaf207cfa63f490212b69389fba4d72f62c60f.wai
cfb71256ef44758ea279846a8938823994d321abce83ef73afd2ed269a8e0259 objects/618e0a89be8c7e556b380326b219c2f6fbfc5a0cb97754e871c1c23a99bdb481.wai
f3eedf9eb2870c0160801397412e7a4c3aca4a6e16f1a69a276e1356d38c9220 objects/61c7c3b7ccab07ed01df5b0d7ca0240598b914dbf2cabe545aa001e8de12d365.wai
d03f0813c266294f84483cfe4db177d094c06b95ab3a8471d6b2ec53401f05a7 objects/a236e9070d10fd09342cafdbf6973edd35e5266cf850fe2f38f77536ac803912.wai
2316616549f7f92dc29e34fe656c332c9f4a1e20f4be26396976407acc792ba4 objects/a3ae43406f9966487b6c5f5a4d56e9dca50c327423fcfd2a98f4c342d1dbfaf9.wai
b2a40a9a8cec3dcaf6c92a07d6765203c412c57ec879b7e33a52eabb2e74609d objects/c2ce1907255a041c388afd06ccd007436368e8d20467fdec2a1eebbb84b03bf2.wai
6d665f1bef3784cbb428abc28724f74fa83c8f2bc812828621c93c5514b6dc0e objects/c5253efe2949669bb9df01d9f60c01f2570ba4be1c0af26105e092dfccf90d30.wai
0acecba00acc28e313805189fd826ad3a9fab1fe69727ef2d5999fc543426289 objects/c81171fa53998cfe94207ad66ab9b53cfbd4b3f058730e62512ca9f0f6ef2ea3.wai
f3bd9cbe3c2518c997a4d1d3a32145a04f55ef53e0b5760a6ce6aa5e14fe06a7 objects/dea0f6415f639fca99d91a0341aba164078a1bd4780e21d72cbf2234928272ec.wai
d22c4f8ac8a5de43bbec6be04ea8b6da72f2bd133f8f57a31607362670178c68 objects/f467872fe8d3cd1f60f832c997cc14fd00abbf601c61286a612089b4a53a195a.wai
f1f4e32ba9f76e36431d97e0fd52b9025075f553bf6b9f63c484d60573c8ea90 package.receipt.json
517630d9bee1f5559baff3bb3e642f6aa7b5276226f6e3bdba4f3f9724794859 plan-v.txt
428e24f9e1c62fc5590ce3d3a6239a5c274dcfc1391a2ea2abe8dc0562da7d20 policy.json
9d2b4c15ac17ee074f646d0b1ed11ef56557f633ff67a3e6a6d0eb4dd1596548 policy.toml
2f5807b891b8eb0a44b76c4303487be1dcf19e111f06f6c642e14b81c85d7c4d stages/legacy.json
8695fff48ca86321c5198e3a8cf660ccba208df4f40fd1907e76c64a52674cf5 stages/mobile.json
6ae56077cfc368a59489233eeee6ee7fd97437821822637ac62096ab93c85286 stages/tv.json

View file

@ -0,0 +1,12 @@
a8a19ef9cd4d540037ef298097bbc5317de6a99690c8c4a745cc867c034208d6 hi/init.mp4
14cdbe56c8f57b1427ab9c2a9ebf6669ce8edec06fd7cd0961a01d2aaf720889 hi/seg_0000.m4s
e5583297b1456e46366fe3317784fadf8c165c5e16e864629b194dc46290387e hi/seg_0001.m4s
d3616b6368fc800ce421a492fbd0f6263b9e06ee0af1e8269ce4f20d5cb3653d hi/seg_0002.m4s
eb559df9571de1869981ca82672abbabad528b294b15a1d7bf9b635761c584f8 hi/seg_0003.m4s
759f476ce9e9b003d7d797060f9c039141d261dd65212035e96bb157783423c1 hi/seg_0004.m4s
6dd501e27365ce9ef90576771aad73de4d200362e6974551847afc3c90604344 lo/init.mp4
0e0407f5a552e405846a411627df17537e5c31accca37390c391a7c1d27353af lo/seg_0000.m4s
c29687008dafdf251b2ca962c3e830f785b38a56c81aee1f4c86f2e8f9115fcc lo/seg_0001.m4s
10b19654062fa37b83c082c922f54529725c36a4ead953b1fbfbbee14d4e79a8 lo/seg_0002.m4s
a855b2701af4e7c8c912448be9fc023f911b4e9e94b65770393c4df6d705b5e8 lo/seg_0003.m4s
20484c9bead2b261ac1a18c2aedec11761813f995d11dc9779c5f9b039d59b73 lo/seg_0004.m4s

View file

@ -0,0 +1,46 @@
688cb303ccb16fcdd21c8cb681f936ba813829e71fbf15df0ccb28b04c134447 dash/classic.mpd
a3aa7658db9b85a9d9a1fed977825189f75c5adad0f5fdfcd70ebd604824c138 dash/mobile.mpd
3f520749a6d2f231cddfd17804ee3629439f3678515e424c44e36cff54d89de9 dash/tv.mpd
14cdbe56c8f57b1427ab9c2a9ebf6669ce8edec06fd7cd0961a01d2aaf720889 floor/hi/14cdbe56c8f57b1427ab9c2a9ebf6669ce8edec06fd7cd0961a01d2aaf720889.m4s
759f476ce9e9b003d7d797060f9c039141d261dd65212035e96bb157783423c1 floor/hi/759f476ce9e9b003d7d797060f9c039141d261dd65212035e96bb157783423c1.m4s
d3616b6368fc800ce421a492fbd0f6263b9e06ee0af1e8269ce4f20d5cb3653d floor/hi/d3616b6368fc800ce421a492fbd0f6263b9e06ee0af1e8269ce4f20d5cb3653d.m4s
e5583297b1456e46366fe3317784fadf8c165c5e16e864629b194dc46290387e floor/hi/e5583297b1456e46366fe3317784fadf8c165c5e16e864629b194dc46290387e.m4s
eb559df9571de1869981ca82672abbabad528b294b15a1d7bf9b635761c584f8 floor/hi/eb559df9571de1869981ca82672abbabad528b294b15a1d7bf9b635761c584f8.m4s
a8a19ef9cd4d540037ef298097bbc5317de6a99690c8c4a745cc867c034208d6 floor/hi/init.mp4
0e0407f5a552e405846a411627df17537e5c31accca37390c391a7c1d27353af floor/lo/0e0407f5a552e405846a411627df17537e5c31accca37390c391a7c1d27353af.m4s
10b19654062fa37b83c082c922f54529725c36a4ead953b1fbfbbee14d4e79a8 floor/lo/10b19654062fa37b83c082c922f54529725c36a4ead953b1fbfbbee14d4e79a8.m4s
2c484c9bead2b261ac1a18c2aedec11761813f995d11dc9779c5f9b039d59b73 floor/lo/2c484c9bead2b261ac1a18c2aedec11761813f995d11dc9779c5f9b039d59b73.m4s
a855b2701af4e7c8c912448be9fc023f911b4e9e94b65770393c4df6d705b5e8 floor/lo/a855b2701af4e7c8c912448be9fc023f911b4e9e94b65770393c4df6d705b5e8.m4s
c29687008dafdf251b2ca962c3e830f785b38a56c81aee1f4c86f2e8f9115fcc floor/lo/c29687008dafdf251b2ca962c3e830f785b38a56c81aee1f4c86f2e8f9115fcc.m4s
6dd501e27365ce9ef90576771aad73de4d200362e6974551847afc3c90604344 floor/lo/init.mp4
ebdc7e40aecbe8b61124ac78f233b0dfaf2a8c5674d3fc9bb023935de1d9b6cb hls/classic/floor-hi.m3u8
66f5eb8b89b80e7da839b23f39665eb85480c6a725fa29d93556efee673c1b9e hls/classic/floor-lo.m3u8
d793737b69231eface4951001e65b3c52cba864f231246a41e64d49c77ebdc97 hls/classic/master.m3u8
d793737b69231eface4951001e65b3c52cba864f231246a41e64d49c77ebdc97 hls/legacy/master.m3u8
8c3b5e2b18192b383c8df8675acd435b861a2585bc6eaf0c09292754f44a8cef hls/mobile/master.m3u8
c4044eca76959c9f87230484a2b207fb12c0bcaedb8d921eab806014fca53cb8 hls/mobile/wai-v.m3u8
60a6378f46afc9308dc4ac4d138602b16568577616ea0bf4526b142d86899151 hls/mobile/wai.m3u8
8c3b5e2b18192b383c8df8675acd435b861a2585bc6eaf0c09292754f44a8cef hls/tv/master.m3u8
ff4edf2929e380d205c1c74156621185feec53d593ffa968b8dfaf0d05448bcd hls/tv/wai-v.m3u8
5d42147b308330913c3d9c8a868ca83ce4d3f3e460da8d84c84014eb24aaf9d7 hls/tv/wai.m3u8
649330bcfaaee54f802f6b4ddf6e459daca8bb0e8df86c87a9d6bd0d65cd09ea index-v.wsix
68f00abff5ef19f074d510f8cce4592afc2a1d4981a87663965a46dc8bcbe1d3 moq/catalog.json
9f381e2ab764b5e14770b00503c1c90b9c22ba22f87464b2869a70644af11939 objects/08797901ff55d0bb4afba5cffe95df64b7e216f3a0c9ba82006133bb9b6d7f16.wai
07e98fb9ef9ff3fa6bf04f9078da2a3d2423e586feea1061256131a1d1fbb943 objects/24761a434c91c627f11abd6265371966b50573602a200dd7bb04e0d90889326d.wai
d5f9cdd996920e07339b79093b9e4e5cb4237f1780f268220cc6f89c79aea90a objects/399048a078b0f2983149266a44eaf207cfa63f490212b69389fba4d72f62c60f.wai
cfb71256ef44758ea279846a8938823994d321abce83ef73afd2ed269a8e0259 objects/618e0a89be8c7e556b380326b219c2f6fbfc5a0cb97754e871c1c23a99bdb481.wai
f3eedf9eb2870c0160801397412e7a4c3aca4a6e16f1a69a276e1356d38c9220 objects/61c7c3b7ccab07ed01df5b0d7ca0240598b914dbf2cabe545aa001e8de12d365.wai
d03f0813c266294f84483cfe4db177d094c06b95ab3a8471d6b2ec53401f05a7 objects/a236e9070d10fd09342cafdbf6973edd35e5266cf850fe2f38f77536ac803912.wai
2316616549f7f92dc29e34fe656c332c9f4a1e20f4be26396976407acc792ba4 objects/a3ae43406f9966487b6c5f5a4d56e9dca50c327423fcfd2a98f4c342d1dbfaf9.wai
b2a40a9a8cec3dcaf6c92a07d6765203c412c57ec879b7e33a52eabb2e74609d objects/c2ce1907255a041c388afd06ccd007436368e8d20467fdec2a1eebbb84b03bf2.wai
6d665f1bef3784cbb428abc28724f74fa83c8f2bc812828621c93c5514b6dc0e objects/c5253efe2949669bb9df01d9f60c01f2570ba4be1c0af26105e092dfccf90d30.wai
0acecba00acc28e313805189fd826ad3a9fab1fe69727ef2d5999fc543426289 objects/c81171fa53998cfe94207ad66ab9b53cfbd4b3f058730e62512ca9f0f6ef2ea3.wai
f3bd9cbe3c2518c997a4d1d3a32145a04f55ef53e0b5760a6ce6aa5e14fe06a7 objects/dea0f6415f639fca99d91a0341aba164078a1bd4780e21d72cbf2234928272ec.wai
d22c4f8ac8a5de43bbec6be04ea8b6da72f2bd133f8f57a31607362670178c68 objects/f467872fe8d3cd1f60f832c997cc14fd00abbf601c61286a612089b4a53a195a.wai
f1f4e32ba9f76e36431d97e0fd52b9025075f553bf6b9f63c484d60573c8ea90 package.receipt.json
517630d9bee1f5559baff3bb3e642f6aa7b5276226f6e3bdba4f3f9724794859 plan-v.txt
428e24f9e1c62fc5590ce3d3a6239a5c274dcfc1391a2ea2abe8dc0562da7d20 policy.json
9d2b4c15ac17ee074f646d0b1ed11ef56557f633ff67a3e6a6d0eb4dd1596548 policy.toml
2f5807b891b8eb0a44b76c4303487be1dcf19e111f06f6c642e14b81c85d7c4d stages/legacy.json
8695fff48ca86321c5198e3a8cf660ccba208df4f40fd1907e76c64a52674cf5 stages/mobile.json
6ae56077cfc368a59489233eeee6ee7fd97437821822637ac62096ab93c85286 stages/tv.json

View file

@ -0,0 +1,47 @@
9c94223b39aee3a51b88d5b9876bcb034a7b83d7c3ad63d4a821a23067311fa4 dash/classic.mpd
a3aa7658db9b85a9d9a1fed977825189f75c5adad0f5fdfcd70ebd604824c138 dash/mobile.mpd
3f520749a6d2f231cddfd17804ee3629439f3678515e424c44e36cff54d89de9 dash/tv.mpd
03ab06e026880875581952f91232405077be9a522dbf739b6a9d093458369710 floor.listing
103573aca98afc526a45518dc6b93d0fcd58511bb34550b2f4d7b29431df9ad9 floor/hi/103573aca98afc526a45518dc6b93d0fcd58511bb34550b2f4d7b29431df9ad9.m4s
759f476ce9e9b003d7d797060f9c039141d261dd65212035e96bb157783423c1 floor/hi/759f476ce9e9b003d7d797060f9c039141d261dd65212035e96bb157783423c1.m4s
d3616b6368fc800ce421a492fbd0f6263b9e06ee0af1e8269ce4f20d5cb3653d floor/hi/d3616b6368fc800ce421a492fbd0f6263b9e06ee0af1e8269ce4f20d5cb3653d.m4s
e5583297b1456e46366fe3317784fadf8c165c5e16e864629b194dc46290387e floor/hi/e5583297b1456e46366fe3317784fadf8c165c5e16e864629b194dc46290387e.m4s
eb559df9571de1869981ca82672abbabad528b294b15a1d7bf9b635761c584f8 floor/hi/eb559df9571de1869981ca82672abbabad528b294b15a1d7bf9b635761c584f8.m4s
a8a19ef9cd4d540037ef298097bbc5317de6a99690c8c4a745cc867c034208d6 floor/hi/init.mp4
0e0407f5a552e405846a411627df17537e5c31accca37390c391a7c1d27353af floor/lo/0e0407f5a552e405846a411627df17537e5c31accca37390c391a7c1d27353af.m4s
10b19654062fa37b83c082c922f54529725c36a4ead953b1fbfbbee14d4e79a8 floor/lo/10b19654062fa37b83c082c922f54529725c36a4ead953b1fbfbbee14d4e79a8.m4s
2c484c9bead2b261ac1a18c2aedec11761813f995d11dc9779c5f9b039d59b73 floor/lo/2c484c9bead2b261ac1a18c2aedec11761813f995d11dc9779c5f9b039d59b73.m4s
a855b2701af4e7c8c912448be9fc023f911b4e9e94b65770393c4df6d705b5e8 floor/lo/a855b2701af4e7c8c912448be9fc023f911b4e9e94b65770393c4df6d705b5e8.m4s
c29687008dafdf251b2ca962c3e830f785b38a56c81aee1f4c86f2e8f9115fcc floor/lo/c29687008dafdf251b2ca962c3e830f785b38a56c81aee1f4c86f2e8f9115fcc.m4s
6dd501e27365ce9ef90576771aad73de4d200362e6974551847afc3c90604344 floor/lo/init.mp4
e2d4aee2f0c71cbe27d878bb1e01a4002a19b916d32c52dc728945eb4ff00968 hls/classic/floor-hi.m3u8
66f5eb8b89b80e7da839b23f39665eb85480c6a725fa29d93556efee673c1b9e hls/classic/floor-lo.m3u8
62229b01a8527c96ec8ab0f0fba8fc58eb26726e639b30b48f883d7d113dcfb7 hls/classic/master.m3u8
62229b01a8527c96ec8ab0f0fba8fc58eb26726e639b30b48f883d7d113dcfb7 hls/legacy/master.m3u8
ed2d3c068e96d0779acc488d18327aa83d379bb55986fe1948c2cddd4a11756b hls/mobile/master.m3u8
c4044eca76959c9f87230484a2b207fb12c0bcaedb8d921eab806014fca53cb8 hls/mobile/wai-v.m3u8
60a6378f46afc9308dc4ac4d138602b16568577616ea0bf4526b142d86899151 hls/mobile/wai.m3u8
ed2d3c068e96d0779acc488d18327aa83d379bb55986fe1948c2cddd4a11756b hls/tv/master.m3u8
ff4edf2929e380d205c1c74156621185feec53d593ffa968b8dfaf0d05448bcd hls/tv/wai-v.m3u8
5d42147b308330913c3d9c8a868ca83ce4d3f3e460da8d84c84014eb24aaf9d7 hls/tv/wai.m3u8
649330bcfaaee54f802f6b4ddf6e459daca8bb0e8df86c87a9d6bd0d65cd09ea index-v.wsix
68f00abff5ef19f074d510f8cce4592afc2a1d4981a87663965a46dc8bcbe1d3 moq/catalog.json
9f381e2ab764b5e14770b00503c1c90b9c22ba22f87464b2869a70644af11939 objects/08797901ff55d0bb4afba5cffe95df64b7e216f3a0c9ba82006133bb9b6d7f16.wai
07e98fb9ef9ff3fa6bf04f9078da2a3d2423e586feea1061256131a1d1fbb943 objects/24761a434c91c627f11abd6265371966b50573602a200dd7bb04e0d90889326d.wai
d5f9cdd996920e07339b79093b9e4e5cb4237f1780f268220cc6f89c79aea90a objects/399048a078b0f2983149266a44eaf207cfa63f490212b69389fba4d72f62c60f.wai
cfb71256ef44758ea279846a8938823994d321abce83ef73afd2ed269a8e0259 objects/618e0a89be8c7e556b380326b219c2f6fbfc5a0cb97754e871c1c23a99bdb481.wai
f3eedf9eb2870c0160801397412e7a4c3aca4a6e16f1a69a276e1356d38c9220 objects/61c7c3b7ccab07ed01df5b0d7ca0240598b914dbf2cabe545aa001e8de12d365.wai
d03f0813c266294f84483cfe4db177d094c06b95ab3a8471d6b2ec53401f05a7 objects/a236e9070d10fd09342cafdbf6973edd35e5266cf850fe2f38f77536ac803912.wai
2316616549f7f92dc29e34fe656c332c9f4a1e20f4be26396976407acc792ba4 objects/a3ae43406f9966487b6c5f5a4d56e9dca50c327423fcfd2a98f4c342d1dbfaf9.wai
b2a40a9a8cec3dcaf6c92a07d6765203c412c57ec879b7e33a52eabb2e74609d objects/c2ce1907255a041c388afd06ccd007436368e8d20467fdec2a1eebbb84b03bf2.wai
6d665f1bef3784cbb428abc28724f74fa83c8f2bc812828621c93c5514b6dc0e objects/c5253efe2949669bb9df01d9f60c01f2570ba4be1c0af26105e092dfccf90d30.wai
0acecba00acc28e313805189fd826ad3a9fab1fe69727ef2d5999fc543426289 objects/c81171fa53998cfe94207ad66ab9b53cfbd4b3f058730e62512ca9f0f6ef2ea3.wai
f3bd9cbe3c2518c997a4d1d3a32145a04f55ef53e0b5760a6ce6aa5e14fe06a7 objects/dea0f6415f639fca99d91a0341aba164078a1bd4780e21d72cbf2234928272ec.wai
d22c4f8ac8a5de43bbec6be04ea8b6da72f2bd133f8f57a31607362670178c68 objects/f467872fe8d3cd1f60f832c997cc14fd00abbf601c61286a612089b4a53a195a.wai
f1f4e32ba9f76e36431d97e0fd52b9025075f553bf6b9f63c484d60573c8ea90 package.receipt.json
517630d9bee1f5559baff3bb3e642f6aa7b5276226f6e3bdba4f3f9724794859 plan-v.txt
428e24f9e1c62fc5590ce3d3a6239a5c274dcfc1391a2ea2abe8dc0562da7d20 policy.json
9d2b4c15ac17ee074f646d0b1ed11ef56557f633ff67a3e6a6d0eb4dd1596548 policy.toml
2f5807b891b8eb0a44b76c4303487be1dcf19e111f06f6c642e14b81c85d7c4d stages/legacy.json
8695fff48ca86321c5198e3a8cf660ccba208df4f40fd1907e76c64a52674cf5 stages/mobile.json
6ae56077cfc368a59489233eeee6ee7fd97437821822637ac62096ab93c85286 stages/tv.json

View file

@ -0,0 +1,41 @@
<?xml version="1.0" encoding="UTF-8"?>
<MPD xmlns="urn:mpeg:dash:schema:mpd:2011" profiles="urn:mpeg:dash:profile:full:2011" type="static" mediaPresentationDuration="PT8.000S" minBufferTime="PT3S">
<Period id="p0" start="PT0S">
<AdaptationSet id="1" contentType="video" mimeType="video/mp4" segmentAlignment="true" startWithSAP="1">
<Representation id="hi-floor" bandwidth="9300" codecs="av01.0.00M.08" width="64" height="36">
<SegmentList timescale="25">
<Initialization sourceURL="../floor/hi/init.mp4"/>
<SegmentTimeline>
<S t="0" d="60"/>
<S t="60" d="25"/>
<S t="85" d="50"/>
<S t="135" d="25"/>
<S t="160" d="40"/>
</SegmentTimeline>
<SegmentURL media="../floor/hi/103573aca98afc526a45518dc6b93d0fcd58511bb34550b2f4d7b29431df9ad9.m4s"/>
<SegmentURL media="../floor/hi/e5583297b1456e46366fe3317784fadf8c165c5e16e864629b194dc46290387e.m4s"/>
<SegmentURL media="../floor/hi/d3616b6368fc800ce421a492fbd0f6263b9e06ee0af1e8269ce4f20d5cb3653d.m4s"/>
<SegmentURL media="../floor/hi/eb559df9571de1869981ca82672abbabad528b294b15a1d7bf9b635761c584f8.m4s"/>
<SegmentURL media="../floor/hi/759f476ce9e9b003d7d797060f9c039141d261dd65212035e96bb157783423c1.m4s"/>
</SegmentList>
</Representation>
<Representation id="lo-floor" bandwidth="8152" codecs="av01.0.00M.08" width="32" height="18">
<SegmentList timescale="25">
<Initialization sourceURL="../floor/lo/init.mp4"/>
<SegmentTimeline>
<S t="0" d="60"/>
<S t="60" d="25"/>
<S t="85" d="50"/>
<S t="135" d="25"/>
<S t="160" d="40"/>
</SegmentTimeline>
<SegmentURL media="../floor/lo/0e0407f5a552e405846a411627df17537e5c31accca37390c391a7c1d27353af.m4s"/>
<SegmentURL media="../floor/lo/c29687008dafdf251b2ca962c3e830f785b38a56c81aee1f4c86f2e8f9115fcc.m4s"/>
<SegmentURL media="../floor/lo/10b19654062fa37b83c082c922f54529725c36a4ead953b1fbfbbee14d4e79a8.m4s"/>
<SegmentURL media="../floor/lo/a855b2701af4e7c8c912448be9fc023f911b4e9e94b65770393c4df6d705b5e8.m4s"/>
<SegmentURL media="../floor/lo/2c484c9bead2b261ac1a18c2aedec11761813f995d11dc9779c5f9b039d59b73.m4s"/>
</SegmentList>
</Representation>
</AdaptationSet>
</Period>
</MPD>

View file

@ -0,0 +1,18 @@
#EXTM3U
#EXT-X-VERSION:7
#EXT-X-TARGETDURATION:3
#EXT-X-MEDIA-SEQUENCE:0
#EXT-X-PLAYLIST-TYPE:VOD
#EXT-X-INDEPENDENT-SEGMENTS
#EXT-X-MAP:URI="../../floor/hi/init.mp4"
#EXTINF:2.400,
../../floor/hi/103573aca98afc526a45518dc6b93d0fcd58511bb34550b2f4d7b29431df9ad9.m4s
#EXTINF:1.000,
../../floor/hi/e5583297b1456e46366fe3317784fadf8c165c5e16e864629b194dc46290387e.m4s
#EXTINF:2.000,
../../floor/hi/d3616b6368fc800ce421a492fbd0f6263b9e06ee0af1e8269ce4f20d5cb3653d.m4s
#EXTINF:1.000,
../../floor/hi/eb559df9571de1869981ca82672abbabad528b294b15a1d7bf9b635761c584f8.m4s
#EXTINF:1.600,
../../floor/hi/759f476ce9e9b003d7d797060f9c039141d261dd65212035e96bb157783423c1.m4s
#EXT-X-ENDLIST

View file

@ -0,0 +1,7 @@
#EXTM3U
#EXT-X-VERSION:7
#EXT-X-INDEPENDENT-SEGMENTS
#EXT-X-STREAM-INF:BANDWIDTH=9300,AVERAGE-BANDWIDTH=7923,CODECS="av01.0.00M.08",RESOLUTION=64x36
../classic/floor-hi.m3u8
#EXT-X-STREAM-INF:BANDWIDTH=8152,AVERAGE-BANDWIDTH=7583,CODECS="av01.0.00M.08",RESOLUTION=32x18
../classic/floor-lo.m3u8

View file

@ -0,0 +1,7 @@
#EXTM3U
#EXT-X-VERSION:7
#EXT-X-INDEPENDENT-SEGMENTS
#EXT-X-STREAM-INF:BANDWIDTH=9300,AVERAGE-BANDWIDTH=7923,CODECS="av01.0.00M.08",RESOLUTION=64x36
../classic/floor-hi.m3u8
#EXT-X-STREAM-INF:BANDWIDTH=8152,AVERAGE-BANDWIDTH=7583,CODECS="av01.0.00M.08",RESOLUTION=32x18
../classic/floor-lo.m3u8

View file

@ -0,0 +1,8 @@
#EXTM3U
#EXT-X-VERSION:7
#EXT-X-INDEPENDENT-SEGMENTS
#EXT-X-SESSION-DATA:DATA-ID="science.transaction.wai.multivariant",VALUE="wai.m3u8"
#EXT-X-STREAM-INF:BANDWIDTH=9300,AVERAGE-BANDWIDTH=7923,CODECS="av01.0.00M.08",RESOLUTION=64x36
../classic/floor-hi.m3u8
#EXT-X-STREAM-INF:BANDWIDTH=8152,AVERAGE-BANDWIDTH=7583,CODECS="av01.0.00M.08",RESOLUTION=32x18
../classic/floor-lo.m3u8

View file

@ -0,0 +1,8 @@
#EXTM3U
#EXT-X-VERSION:7
#EXT-X-INDEPENDENT-SEGMENTS
#EXT-X-SESSION-DATA:DATA-ID="science.transaction.wai.multivariant",VALUE="wai.m3u8"
#EXT-X-STREAM-INF:BANDWIDTH=9300,AVERAGE-BANDWIDTH=7923,CODECS="av01.0.00M.08",RESOLUTION=64x36
../classic/floor-hi.m3u8
#EXT-X-STREAM-INF:BANDWIDTH=8152,AVERAGE-BANDWIDTH=7583,CODECS="av01.0.00M.08",RESOLUTION=32x18
../classic/floor-lo.m3u8

View file

@ -0,0 +1,152 @@
#!/usr/bin/env python3
"""The supplied CMAF reader differentially (extensions/packaging.md §7.7): wai-pack's
(`wai-pack cmaf-verdict`) against pack_verify.py's, which shares no code with it, on
seeded alterations of real files. The files are the CMAF golden's floor (a media muxer's
initialization and media segments, packs/video-cmaf-01/floor/) and §7.6's writer's (the
ladder golden's package, packs/video-ladder-01/package/floor/). Each case alters the
initialization segment or one media segment: a byte flipped in its first boxes, a 32-bit
field overwritten at a box boundary, the file cut short, a box's size changed, a box
inserted at the top level or in a moof, the init's timescale or edit list altered, or a
segment's moof and mdat repeated. Every verdict (ok, floor-cmaf-malformed or
floor-cmaf-timing), and for an accepted segment its samples (offset, length, duration,
flags, decode time), must agree, and no reader may panic.
python3 cmaf_diff.py <wai-pack binary> <seed> <cases>
"""
import hashlib
import os
import random
import subprocess
import sys
import tempfile
HERE = os.path.dirname(os.path.abspath(__file__))
sys.path.insert(0, HERE)
import pack_verify as PV # noqa: E402
def py_init(b):
try:
return "ok", PV.cmaf_init(b)
except PV.CmafFault as x:
return x.code, None
except Exception as x: # a reader must refuse, never fail otherwise
return f"CRASH {type(x).__name__}", None
def py_segment(b, init):
try:
s = PV.cmaf_segment(b, init)
except PV.CmafFault as x:
return (x.code, 0, "-")
except Exception as x:
return (f"CRASH {type(x).__name__}", 0, "-")
text = "".join(f"{a},{n},{d},{f},{t};" for a, n, d, f, t in s)
return ("ok", len(s), hashlib.sha256(text.encode()).hexdigest())
def boxes(b, start, end):
try:
return PV.bmff_boxes(b, start, end)
except PV.CmafFault:
return []
def alter(rng, b):
b = bytearray(b)
top = boxes(b, 0, len(b))
k = rng.randrange(8)
if k == 6:
# The times: an init's timescale or its edit list's media time, at their offsets
# from the box type. `mdhd`'s timescale follows its version and flags and its two
# times, 4 bytes each in version 0 and 8 in version 1.
for kind, off in ((b"mdhd", None), (b"elst", 20), (b"elst", 16)):
at = bytes(b).find(kind)
if at >= 0 and off is None:
off = 16 if at + 4 < len(b) and b[at + 4] == 0 else 24
if at >= 0 and rng.random() < 0.5 and at + off + 4 <= len(b):
b[at + off:at + off + 4] = rng.choice([0, 1, 2, rng.randrange(1 << 32)]).to_bytes(4, "big")
return bytes(b)
k = 0
if k == 7:
# A media segment's moof and mdat repeated: the second's decode time is the first's.
pairs = [i for i, x in enumerate(top) if x[0] == b"moof" and i + 1 < len(top) and top[i + 1][0] == b"mdat"]
if pairs:
i = rng.choice(pairs)
b += b[top[i][1]:top[i + 1][3]]
return bytes(b)
k = 0
if k == 0 and b:
b[rng.randrange(min(len(b), 400))] ^= 1 << rng.randrange(8)
elif k == 1 and top:
x = rng.choice(top)
inner = boxes(b, x[2], x[3]) if x[0] in (b"moov", b"moof", b"trak", b"traf", b"mdia", b"minf", b"stbl", b"mvex") else []
y = rng.choice(inner) if inner and rng.random() < 0.7 else x
at = y[1] + rng.choice([8, 12, 16, 20, 24])
if at + 4 <= len(b):
b[at:at + 4] = rng.choice([0, 1, 7, 0xFFFFFFFF, rng.randrange(1 << 32)]).to_bytes(4, "big")
elif k == 2 and len(b) > 8:
del b[rng.randrange(8, len(b)):]
elif k == 3 and top:
x = rng.choice(top)
b[x[1]:x[1] + 4] = max(0, (x[3] - x[1]) + rng.choice([-9, -1, 1, 4, 8, -(x[3] - x[1])])).to_bytes(4, "big")
elif k == 4 and top:
kind = rng.choice([b"free", b"skip", b"uuid", b"styp", b"mdat", b"moof"])
box = (8 + 4).to_bytes(4, "big") + kind + bytes(4)
at = rng.choice([x[1] for x in top] + [len(b)])
b[at:at] = box
elif top:
moofs = [x for x in top if x[0] == b"moof"]
if moofs:
x = rng.choice(moofs)
inner = boxes(b, x[2], x[3])
at = rng.choice([y[1] for y in inner] + [x[3]])
kind = rng.choice([b"sbgp", b"free", b"tfdt", b"trun"])
box = (8 + 8).to_bytes(4, "big") + kind + bytes(8)
b[at:at] = box
b[x[1]:x[1] + 4] = (x[3] - x[1] + len(box)).to_bytes(4, "big")
return bytes(b)
def main(argv):
if len(argv) != 4:
print(__doc__)
return 2
wai_pack, seed, n = argv[1], int(argv[2]), int(argv[3])
rng = random.Random(seed)
root = os.path.join(HERE, "packs")
sets = []
for d in (os.path.join(root, "video-cmaf-01", "floor", "hi"), os.path.join(root, "video-cmaf-01", "floor", "lo"),
os.path.join(root, "video-ladder-01", "package", "floor", "hi")):
names = sorted(os.listdir(d))
sets.append((PV.load(os.path.join(d, "init.mp4")), [PV.load(os.path.join(d, x)) for x in names if x.endswith(".m4s")]))
bad, seen = 0, {}
with tempfile.TemporaryDirectory() as tmp:
for c in range(n):
init, segs = rng.choice(sets)
seg = rng.choice(segs)
if rng.random() < 0.25:
init = alter(rng, init)
else:
seg = alter(rng, seg)
ip, sp = os.path.join(tmp, "init.mp4"), os.path.join(tmp, "seg.m4s")
open(ip, "wb").write(init)
open(sp, "wb").write(seg)
out = subprocess.run([wai_pack, "cmaf-verdict", ip, sp], capture_output=True, text=True).stdout.splitlines()
iv, pi = py_init(init)
want = [f"init\t{iv}"]
if iv == "ok":
v = py_segment(seg, pi)
want.append(f"{sp}\t{v[0]}\t{v[1]}\t{v[2]}")
verdict = want[-1].split("\t")[1]
seen[verdict] = seen.get(verdict, 0) + 1
if out != want or any("PANIC" in x or "CRASH" in x for x in out + want):
bad += 1
if bad <= 10:
print(f"case {c}: wai-pack {out}, pack_verify {want}")
print(f"cmaf_diff: {n - bad}/{n} cases agree; verdicts {dict(sorted(seen.items()))}")
return 0 if bad == 0 else 1
if __name__ == "__main__":
sys.exit(main(sys.argv))

View file

@ -0,0 +1,35 @@
{
"pack": "video-ladder-01",
"cases": [
{
"name": "ok",
"reason": "ok",
"remove": []
},
{
"name": "floors-swapped",
"reason": "floor-object-mismatch",
"remove": [
"floor/hi/2f93f0ad449f9cc881b7816c6ab33fd445037d6538b445bcc76431f9c9f91c5b.m4s",
"floor/lo/acd166807d05fe4f512407f717659d88613f6d0d360485effe3751504cefbb74.m4s"
]
},
{
"name": "floor-under-the-component-s-name",
"reason": "floor-cmaf-mismatch",
"remove": [
"floor/lo/589ad79210bff258db68916876846a2b0d530ea2e44260af66ddc51ad14ce07f.m4s",
"floor/lo/6bba50408f894d0e9d5516a53992fdd2aa86db43ccdc684b69c51a688856a0db.m4s",
"floor/lo/acd166807d05fe4f512407f717659d88613f6d0d360485effe3751504cefbb74.m4s",
"floor/lo/d0f68eb18af5b67736ddccd97ed45c4c0274b0460f6abc8f54940ac378165833.m4s",
"floor/lo/d550ebb204adf0b5a7f310c7d07189e7bed63e12e34e9ed4d9bf96a101d864a9.m4s",
"floor/lo/init.mp4"
]
},
{
"name": "master-lists-one-floor",
"reason": "catalog-mismatch",
"remove": []
}
]
}

View file

@ -0,0 +1,46 @@
c5203585fea0962de941d258789157a0590e18b62a2e5d1facbd11e1cfd1ddb9 dash/classic.mpd
a3aa7658db9b85a9d9a1fed977825189f75c5adad0f5fdfcd70ebd604824c138 dash/mobile.mpd
3f520749a6d2f231cddfd17804ee3629439f3678515e424c44e36cff54d89de9 dash/tv.mpd
04c948608aaa7b5d78ad5355042a2ff65b0f75d9d4b1ad78f3ebffb886a74be6 floor/hi/04c948608aaa7b5d78ad5355042a2ff65b0f75d9d4b1ad78f3ebffb886a74be6.m4s
06d5cd79ba3860cccdc252fe915de0902f941a3c6a000295714f7cab193aa6cf floor/hi/06d5cd79ba3860cccdc252fe915de0902f941a3c6a000295714f7cab193aa6cf.m4s
2f93f0ad449f9cc881b7816c6ab33fd445037d6538b445bcc76431f9c9f91c5b floor/hi/2f93f0ad449f9cc881b7816c6ab33fd445037d6538b445bcc76431f9c9f91c5b.m4s
420ae4c941bba6e12a6c7fdb7d01dc69170ecb4240dffd2e86808ddf87baa12a floor/hi/420ae4c941bba6e12a6c7fdb7d01dc69170ecb4240dffd2e86808ddf87baa12a.m4s
576b7d2156c2b595bf48bf34f67996d7f89e75d105f0dc71c9841bb96e6cd0fc floor/hi/576b7d2156c2b595bf48bf34f67996d7f89e75d105f0dc71c9841bb96e6cd0fc.m4s
58c598174eed554cd0d1bc8abedca8c9d51d992c8e3b963bcb7574da4983ed9f floor/hi/init.mp4
589ad79210bff258db68916876846a2b0d530ea2e44260af66ddc51ad14ce07f floor/v/589ad79210bff258db68916876846a2b0d530ea2e44260af66ddc51ad14ce07f.m4s
6bba50408f894d0e9d5516a53992fdd2aa86db43ccdc684b69c51a688856a0db floor/v/6bba50408f894d0e9d5516a53992fdd2aa86db43ccdc684b69c51a688856a0db.m4s
acd166807d05fe4f512407f717659d88613f6d0d360485effe3751504cefbb74 floor/v/acd166807d05fe4f512407f717659d88613f6d0d360485effe3751504cefbb74.m4s
d0f68eb18af5b67736ddccd97ed45c4c0274b0460f6abc8f54940ac378165833 floor/v/d0f68eb18af5b67736ddccd97ed45c4c0274b0460f6abc8f54940ac378165833.m4s
d550ebb204adf0b5a7f310c7d07189e7bed63e12e34e9ed4d9bf96a101d864a9 floor/v/d550ebb204adf0b5a7f310c7d07189e7bed63e12e34e9ed4d9bf96a101d864a9.m4s
640cd81c83baefbe13e8ccc2bf577395c6602885cc73e201ca34dc267e7f0a48 floor/v/init.mp4
bfa98255d682517f58df4073bc71fdb3fcca120fc33d16e4aca873392476c586 hls/classic/floor-hi.m3u8
ad81674ac359096ebed255a26a40e82858e53e9754702429e59d72898df33812 hls/classic/floor-lo.m3u8
3fd88f9dcf835edf0fcca8dff8371d2b4e897ac097fc85901477c950c0da7996 hls/classic/master.m3u8
3fd88f9dcf835edf0fcca8dff8371d2b4e897ac097fc85901477c950c0da7996 hls/legacy/master.m3u8
09e75f55cb7ea829a4e630404d2ab540e8be0dbb1c4365dc30802359b658aed9 hls/mobile/master.m3u8
c4044eca76959c9f87230484a2b207fb12c0bcaedb8d921eab806014fca53cb8 hls/mobile/wai-v.m3u8
60a6378f46afc9308dc4ac4d138602b16568577616ea0bf4526b142d86899151 hls/mobile/wai.m3u8
09e75f55cb7ea829a4e630404d2ab540e8be0dbb1c4365dc30802359b658aed9 hls/tv/master.m3u8
ff4edf2929e380d205c1c74156621185feec53d593ffa968b8dfaf0d05448bcd hls/tv/wai-v.m3u8
5d42147b308330913c3d9c8a868ca83ce4d3f3e460da8d84c84014eb24aaf9d7 hls/tv/wai.m3u8
a5140df0bf1f82b88335c13789502298a952b350ad45dfcfcd249b2b9a263a71 index-v.wsix
c310c5a4ae14df691a1a37a6c34e90243ed72be1e8f725d38f1babe1f6866b21 moq/catalog.json
07e98fb9ef9ff3fa6bf04f9078da2a3d2423e586feea1061256131a1d1fbb943 objects/24761a434c91c627f11abd6265371966b50573602a200dd7bb04e0d90889326d.wai
2f5bd830d841eb122c63ae57a15442075478fd522ce55b6f9bcbe41acd51d8ae objects/482fbbb9b39bdb9cbf00515f94269ea591df681ced90b05d97e0df106b49b08e.wai
0057633252a2c2ed5f71fe14ca78075c8e89fc6675a08335ac90f0e56032b825 objects/4ab8f747d181632f342a4887b0a8bb86c174409cb625157784e18c5e5559a381.wai
cfb71256ef44758ea279846a8938823994d321abce83ef73afd2ed269a8e0259 objects/618e0a89be8c7e556b380326b219c2f6fbfc5a0cb97754e871c1c23a99bdb481.wai
f3eedf9eb2870c0160801397412e7a4c3aca4a6e16f1a69a276e1356d38c9220 objects/61c7c3b7ccab07ed01df5b0d7ca0240598b914dbf2cabe545aa001e8de12d365.wai
1a6f30fdc000f258c948470386d84beef2ba5a84e922c355093837ae21fd573c objects/6ce13c9ef6872caeb7fbe71661ca88bcc463ceac47f109c8c155e34bb1a6f37d.wai
b773dac63c9d2d9980d0d249ea956e03065c1ae40d17c512df29b690c0c820ef objects/b7bf0717e968d7b6be473785c9f66cbb814cde679bceb1ae37f0765308ddee72.wai
b2a40a9a8cec3dcaf6c92a07d6765203c412c57ec879b7e33a52eabb2e74609d objects/c2ce1907255a041c388afd06ccd007436368e8d20467fdec2a1eebbb84b03bf2.wai
cc8a6fc59be29bd33d96fb30ea9e5a30a5aa367a82da9c5784cbadce63396f62 objects/cf842ef3058d3c54d56c0ea3e075efdc77163602b4a1dabcff080e5ea28b9946.wai
01b596b672de3352adb3e01b34fcddfeff975f4ee1d0b88dde160ac10c9bf929 objects/d382ba093b0595c44a43dc3aad22fc0bed42baeb3488f00dfe3567056a7009c5.wai
9d9ae296558ce7f7d644ad0ca3af65eb4fc98d03b0bd6d7a8fc821fc952e86c1 objects/f525b4450c29153dde0b43e4d143dfb76fcc3884c607b744c8a53fa6a1728580.wai
3d573ee482f8187b0e3bc839aeea0f51a67144588d6d207e8466fea91a0c5b34 objects/f7f7f4d6af777bfcce09cdda5ecb754ce6bd8dcd2e03ecfc41359cad989b15f7.wai
bd6086051d0452449da8a90f426f454fee368b4794f7c294218a410ded8d9088 package.receipt.json
517630d9bee1f5559baff3bb3e642f6aa7b5276226f6e3bdba4f3f9724794859 plan-v.txt
d1cf1bd28a06f3a9d695dd64331cb56cf793818e9e9e6cec620183d9dce37b2d policy.json
4ba48d04e5c8e72336e32307b27b4371c96f20f7abf959ac1c1d344ccb9a8106 policy.toml
813329d5521ab5891bb86d29b362e448fae4247c949384b0687d66966546c4fe stages/legacy.json
ca8e0059a23311d7690a0519f85dfb48883721c817cd8fe1cd481cabe14b0032 stages/mobile.json
8bc9c9da674b4765ead0e41d54852ac105161e9638e7ae705e3982847b069e4c stages/tv.json

View file

@ -0,0 +1,46 @@
00ebf8e21ba74af068445c05138d2523c801d9d27d364e1377b518540bc8b34d dash/classic.mpd
a3aa7658db9b85a9d9a1fed977825189f75c5adad0f5fdfcd70ebd604824c138 dash/mobile.mpd
3f520749a6d2f231cddfd17804ee3629439f3678515e424c44e36cff54d89de9 dash/tv.mpd
04c948608aaa7b5d78ad5355042a2ff65b0f75d9d4b1ad78f3ebffb886a74be6 floor/hi/04c948608aaa7b5d78ad5355042a2ff65b0f75d9d4b1ad78f3ebffb886a74be6.m4s
06d5cd79ba3860cccdc252fe915de0902f941a3c6a000295714f7cab193aa6cf floor/hi/06d5cd79ba3860cccdc252fe915de0902f941a3c6a000295714f7cab193aa6cf.m4s
420ae4c941bba6e12a6c7fdb7d01dc69170ecb4240dffd2e86808ddf87baa12a floor/hi/420ae4c941bba6e12a6c7fdb7d01dc69170ecb4240dffd2e86808ddf87baa12a.m4s
576b7d2156c2b595bf48bf34f67996d7f89e75d105f0dc71c9841bb96e6cd0fc floor/hi/576b7d2156c2b595bf48bf34f67996d7f89e75d105f0dc71c9841bb96e6cd0fc.m4s
acd166807d05fe4f512407f717659d88613f6d0d360485effe3751504cefbb74 floor/hi/acd166807d05fe4f512407f717659d88613f6d0d360485effe3751504cefbb74.m4s
58c598174eed554cd0d1bc8abedca8c9d51d992c8e3b963bcb7574da4983ed9f floor/hi/init.mp4
2f93f0ad449f9cc881b7816c6ab33fd445037d6538b445bcc76431f9c9f91c5b floor/lo/2f93f0ad449f9cc881b7816c6ab33fd445037d6538b445bcc76431f9c9f91c5b.m4s
589ad79210bff258db68916876846a2b0d530ea2e44260af66ddc51ad14ce07f floor/lo/589ad79210bff258db68916876846a2b0d530ea2e44260af66ddc51ad14ce07f.m4s
6bba50408f894d0e9d5516a53992fdd2aa86db43ccdc684b69c51a688856a0db floor/lo/6bba50408f894d0e9d5516a53992fdd2aa86db43ccdc684b69c51a688856a0db.m4s
d0f68eb18af5b67736ddccd97ed45c4c0274b0460f6abc8f54940ac378165833 floor/lo/d0f68eb18af5b67736ddccd97ed45c4c0274b0460f6abc8f54940ac378165833.m4s
d550ebb204adf0b5a7f310c7d07189e7bed63e12e34e9ed4d9bf96a101d864a9 floor/lo/d550ebb204adf0b5a7f310c7d07189e7bed63e12e34e9ed4d9bf96a101d864a9.m4s
640cd81c83baefbe13e8ccc2bf577395c6602885cc73e201ca34dc267e7f0a48 floor/lo/init.mp4
49c1a6c22b80524c40e9509fd3c93ab4a7c1a470f4ff6df188aefe656a940a88 hls/classic/floor-hi.m3u8
cdb43220dbeebd408a3a221829c819ca5fb7c38682f3e63ebe2039648d4ce34d hls/classic/floor-lo.m3u8
cf34fb5f72042d09e651c8f21b68affb966bdbe55422e70c0d9d66d1a228a0af hls/classic/master.m3u8
cf34fb5f72042d09e651c8f21b68affb966bdbe55422e70c0d9d66d1a228a0af hls/legacy/master.m3u8
d40a6303c71682889899b2044f2d321dfd1f42b268abed0671109c61e0a67ad1 hls/mobile/master.m3u8
c4044eca76959c9f87230484a2b207fb12c0bcaedb8d921eab806014fca53cb8 hls/mobile/wai-v.m3u8
60a6378f46afc9308dc4ac4d138602b16568577616ea0bf4526b142d86899151 hls/mobile/wai.m3u8
d40a6303c71682889899b2044f2d321dfd1f42b268abed0671109c61e0a67ad1 hls/tv/master.m3u8
ff4edf2929e380d205c1c74156621185feec53d593ffa968b8dfaf0d05448bcd hls/tv/wai-v.m3u8
5d42147b308330913c3d9c8a868ca83ce4d3f3e460da8d84c84014eb24aaf9d7 hls/tv/wai.m3u8
555648a512bc2da29e24dd6c2c4c2c245fb65d05a1228a8185dbb36d94299b46 index-v.wsix
c310c5a4ae14df691a1a37a6c34e90243ed72be1e8f725d38f1babe1f6866b21 moq/catalog.json
07e98fb9ef9ff3fa6bf04f9078da2a3d2423e586feea1061256131a1d1fbb943 objects/24761a434c91c627f11abd6265371966b50573602a200dd7bb04e0d90889326d.wai
2f5bd830d841eb122c63ae57a15442075478fd522ce55b6f9bcbe41acd51d8ae objects/482fbbb9b39bdb9cbf00515f94269ea591df681ced90b05d97e0df106b49b08e.wai
0057633252a2c2ed5f71fe14ca78075c8e89fc6675a08335ac90f0e56032b825 objects/4ab8f747d181632f342a4887b0a8bb86c174409cb625157784e18c5e5559a381.wai
cfb71256ef44758ea279846a8938823994d321abce83ef73afd2ed269a8e0259 objects/618e0a89be8c7e556b380326b219c2f6fbfc5a0cb97754e871c1c23a99bdb481.wai
f3eedf9eb2870c0160801397412e7a4c3aca4a6e16f1a69a276e1356d38c9220 objects/61c7c3b7ccab07ed01df5b0d7ca0240598b914dbf2cabe545aa001e8de12d365.wai
1a6f30fdc000f258c948470386d84beef2ba5a84e922c355093837ae21fd573c objects/6ce13c9ef6872caeb7fbe71661ca88bcc463ceac47f109c8c155e34bb1a6f37d.wai
b773dac63c9d2d9980d0d249ea956e03065c1ae40d17c512df29b690c0c820ef objects/b7bf0717e968d7b6be473785c9f66cbb814cde679bceb1ae37f0765308ddee72.wai
b2a40a9a8cec3dcaf6c92a07d6765203c412c57ec879b7e33a52eabb2e74609d objects/c2ce1907255a041c388afd06ccd007436368e8d20467fdec2a1eebbb84b03bf2.wai
cc8a6fc59be29bd33d96fb30ea9e5a30a5aa367a82da9c5784cbadce63396f62 objects/cf842ef3058d3c54d56c0ea3e075efdc77163602b4a1dabcff080e5ea28b9946.wai
01b596b672de3352adb3e01b34fcddfeff975f4ee1d0b88dde160ac10c9bf929 objects/d382ba093b0595c44a43dc3aad22fc0bed42baeb3488f00dfe3567056a7009c5.wai
9d9ae296558ce7f7d644ad0ca3af65eb4fc98d03b0bd6d7a8fc821fc952e86c1 objects/f525b4450c29153dde0b43e4d143dfb76fcc3884c607b744c8a53fa6a1728580.wai
3d573ee482f8187b0e3bc839aeea0f51a67144588d6d207e8466fea91a0c5b34 objects/f7f7f4d6af777bfcce09cdda5ecb754ce6bd8dcd2e03ecfc41359cad989b15f7.wai
96b7f835515e95018d614ac326d03538b055a9ac2d3a52fac97e9f2dc29dc63b package.receipt.json
517630d9bee1f5559baff3bb3e642f6aa7b5276226f6e3bdba4f3f9724794859 plan-v.txt
d1cf1bd28a06f3a9d695dd64331cb56cf793818e9e9e6cec620183d9dce37b2d policy.json
4ba48d04e5c8e72336e32307b27b4371c96f20f7abf959ac1c1d344ccb9a8106 policy.toml
813329d5521ab5891bb86d29b362e448fae4247c949384b0687d66966546c4fe stages/legacy.json
ca8e0059a23311d7690a0519f85dfb48883721c817cd8fe1cd481cabe14b0032 stages/mobile.json
8bc9c9da674b4765ead0e41d54852ac105161e9638e7ae705e3982847b069e4c stages/tv.json

View file

@ -0,0 +1,41 @@
<?xml version="1.0" encoding="UTF-8"?>
<MPD xmlns="urn:mpeg:dash:schema:mpd:2011" profiles="urn:mpeg:dash:profile:full:2011" type="static" mediaPresentationDuration="PT8.000S" minBufferTime="PT3S">
<Period id="p0" start="PT0S">
<AdaptationSet id="1" contentType="video" mimeType="video/mp4" segmentAlignment="true" startWithSAP="1">
<Representation id="hi-floor" bandwidth="10440" codecs="av01.0.00M.08" width="64" height="36">
<SegmentList timescale="25">
<Initialization sourceURL="../floor/hi/init.mp4"/>
<SegmentTimeline>
<S t="0" d="60"/>
<S t="60" d="25"/>
<S t="85" d="50"/>
<S t="135" d="25"/>
<S t="160" d="40"/>
</SegmentTimeline>
<SegmentURL media="../floor/hi/420ae4c941bba6e12a6c7fdb7d01dc69170ecb4240dffd2e86808ddf87baa12a.m4s"/>
<SegmentURL media="../floor/hi/04c948608aaa7b5d78ad5355042a2ff65b0f75d9d4b1ad78f3ebffb886a74be6.m4s"/>
<SegmentURL media="../floor/hi/acd166807d05fe4f512407f717659d88613f6d0d360485effe3751504cefbb74.m4s"/>
<SegmentURL media="../floor/hi/06d5cd79ba3860cccdc252fe915de0902f941a3c6a000295714f7cab193aa6cf.m4s"/>
<SegmentURL media="../floor/hi/576b7d2156c2b595bf48bf34f67996d7f89e75d105f0dc71c9841bb96e6cd0fc.m4s"/>
</SegmentList>
</Representation>
<Representation id="lo-floor" bandwidth="9600" codecs="av01.0.00M.08" width="32" height="18">
<SegmentList timescale="25">
<Initialization sourceURL="../floor/lo/init.mp4"/>
<SegmentTimeline>
<S t="0" d="60"/>
<S t="60" d="25"/>
<S t="85" d="50"/>
<S t="135" d="25"/>
<S t="160" d="40"/>
</SegmentTimeline>
<SegmentURL media="../floor/lo/d0f68eb18af5b67736ddccd97ed45c4c0274b0460f6abc8f54940ac378165833.m4s"/>
<SegmentURL media="../floor/lo/6bba50408f894d0e9d5516a53992fdd2aa86db43ccdc684b69c51a688856a0db.m4s"/>
<SegmentURL media="../floor/lo/2f93f0ad449f9cc881b7816c6ab33fd445037d6538b445bcc76431f9c9f91c5b.m4s"/>
<SegmentURL media="../floor/lo/589ad79210bff258db68916876846a2b0d530ea2e44260af66ddc51ad14ce07f.m4s"/>
<SegmentURL media="../floor/lo/d550ebb204adf0b5a7f310c7d07189e7bed63e12e34e9ed4d9bf96a101d864a9.m4s"/>
</SegmentList>
</Representation>
</AdaptationSet>
</Period>
</MPD>

View file

@ -0,0 +1,18 @@
#EXTM3U
#EXT-X-VERSION:7
#EXT-X-TARGETDURATION:3
#EXT-X-MEDIA-SEQUENCE:0
#EXT-X-PLAYLIST-TYPE:VOD
#EXT-X-INDEPENDENT-SEGMENTS
#EXT-X-MAP:URI="../../floor/hi/init.mp4"
#EXTINF:2.400,
../../floor/hi/420ae4c941bba6e12a6c7fdb7d01dc69170ecb4240dffd2e86808ddf87baa12a.m4s
#EXTINF:1.000,
../../floor/hi/04c948608aaa7b5d78ad5355042a2ff65b0f75d9d4b1ad78f3ebffb886a74be6.m4s
#EXTINF:2.000,
../../floor/hi/acd166807d05fe4f512407f717659d88613f6d0d360485effe3751504cefbb74.m4s
#EXTINF:1.000,
../../floor/hi/06d5cd79ba3860cccdc252fe915de0902f941a3c6a000295714f7cab193aa6cf.m4s
#EXTINF:1.600,
../../floor/hi/576b7d2156c2b595bf48bf34f67996d7f89e75d105f0dc71c9841bb96e6cd0fc.m4s
#EXT-X-ENDLIST

View file

@ -0,0 +1,18 @@
#EXTM3U
#EXT-X-VERSION:7
#EXT-X-TARGETDURATION:3
#EXT-X-MEDIA-SEQUENCE:0
#EXT-X-PLAYLIST-TYPE:VOD
#EXT-X-INDEPENDENT-SEGMENTS
#EXT-X-MAP:URI="../../floor/lo/init.mp4"
#EXTINF:2.400,
../../floor/lo/d0f68eb18af5b67736ddccd97ed45c4c0274b0460f6abc8f54940ac378165833.m4s
#EXTINF:1.000,
../../floor/lo/6bba50408f894d0e9d5516a53992fdd2aa86db43ccdc684b69c51a688856a0db.m4s
#EXTINF:2.000,
../../floor/lo/2f93f0ad449f9cc881b7816c6ab33fd445037d6538b445bcc76431f9c9f91c5b.m4s
#EXTINF:1.000,
../../floor/lo/589ad79210bff258db68916876846a2b0d530ea2e44260af66ddc51ad14ce07f.m4s
#EXTINF:1.600,
../../floor/lo/d550ebb204adf0b5a7f310c7d07189e7bed63e12e34e9ed4d9bf96a101d864a9.m4s
#EXT-X-ENDLIST

View file

@ -0,0 +1,7 @@
#EXTM3U
#EXT-X-VERSION:7
#EXT-X-INDEPENDENT-SEGMENTS
#EXT-X-STREAM-INF:BANDWIDTH=10440,AVERAGE-BANDWIDTH=8903,CODECS="av01.0.00M.08",RESOLUTION=64x36
../classic/floor-hi.m3u8
#EXT-X-STREAM-INF:BANDWIDTH=9600,AVERAGE-BANDWIDTH=8875,CODECS="av01.0.00M.08",RESOLUTION=32x18
../classic/floor-lo.m3u8

View file

@ -0,0 +1,7 @@
#EXTM3U
#EXT-X-VERSION:7
#EXT-X-INDEPENDENT-SEGMENTS
#EXT-X-STREAM-INF:BANDWIDTH=10440,AVERAGE-BANDWIDTH=8903,CODECS="av01.0.00M.08",RESOLUTION=64x36
../classic/floor-hi.m3u8
#EXT-X-STREAM-INF:BANDWIDTH=9600,AVERAGE-BANDWIDTH=8875,CODECS="av01.0.00M.08",RESOLUTION=32x18
../classic/floor-lo.m3u8

View file

@ -0,0 +1,8 @@
#EXTM3U
#EXT-X-VERSION:7
#EXT-X-INDEPENDENT-SEGMENTS
#EXT-X-SESSION-DATA:DATA-ID="science.transaction.wai.multivariant",VALUE="wai.m3u8"
#EXT-X-STREAM-INF:BANDWIDTH=10440,AVERAGE-BANDWIDTH=8903,CODECS="av01.0.00M.08",RESOLUTION=64x36
../classic/floor-hi.m3u8
#EXT-X-STREAM-INF:BANDWIDTH=9600,AVERAGE-BANDWIDTH=8875,CODECS="av01.0.00M.08",RESOLUTION=32x18
../classic/floor-lo.m3u8

View file

@ -0,0 +1,8 @@
#EXTM3U
#EXT-X-VERSION:7
#EXT-X-INDEPENDENT-SEGMENTS
#EXT-X-SESSION-DATA:DATA-ID="science.transaction.wai.multivariant",VALUE="wai.m3u8"
#EXT-X-STREAM-INF:BANDWIDTH=10440,AVERAGE-BANDWIDTH=8903,CODECS="av01.0.00M.08",RESOLUTION=64x36
../classic/floor-hi.m3u8
#EXT-X-STREAM-INF:BANDWIDTH=9600,AVERAGE-BANDWIDTH=8875,CODECS="av01.0.00M.08",RESOLUTION=32x18
../classic/floor-lo.m3u8

View file

@ -0,0 +1 @@
{"asset_id":"video-ladder-01","components":[{"id":"v","index":"index-v.wsix","index_digest":"fc97f47085f5d79c5ac12f3ce965a6523929b3161091256f545bf6b520cb3017","media_class":"video","stage_root":"c9825fa6105cd5a41a142e11be3d6bf85421ca1547f580315cb5542f1a2de268"}],"energy_provenance":null,"grant":{"capability":"wai.video.package","funds_ceiling":null,"grant_hash":"0000000000000000000000000000000000000000000000000000000000000000","joule_ceiling_micro":null},"joules_micro":0,"kind":"package","packager":"builtin:[email protected]","parent_kind":"none","parent_receipt_hash":null,"policy_digest":"6938df61d1274e43680652af682498bd5c7f1505c5f51b08c770143643c6388e","receipt_hash":"42c2905ad0aabfe3c1d00caa9ecc73a089e289cd01f356ed5c60ce38395663e6","sig":"2f39ed2b68c18fce1278711711bc0cde4634403ae38b2c65dd1f64944acbbdcdd723490f017376c8c017871ef64b6c7a4d6e394851fe4ebed38dd2c84309a602","signer_id":"did:key:z6MkqahniHbtvRDna9jmc9dSMo88FCuKnuujLKxbWyK4682w","signer_pubkey":"a558bae731bbba29b0b2308493514f6ec8a51ab40409cce9e3afafecca787224","stored_bytes":127966,"total_bytes":140530,"total_entries":15,"unique_objects":12,"version":2,"work_units":15}

View file

@ -0,0 +1,46 @@
c5203585fea0962de941d258789157a0590e18b62a2e5d1facbd11e1cfd1ddb9 dash/classic.mpd
a3aa7658db9b85a9d9a1fed977825189f75c5adad0f5fdfcd70ebd604824c138 dash/mobile.mpd
3f520749a6d2f231cddfd17804ee3629439f3678515e424c44e36cff54d89de9 dash/tv.mpd
04c948608aaa7b5d78ad5355042a2ff65b0f75d9d4b1ad78f3ebffb886a74be6 floor/hi/04c948608aaa7b5d78ad5355042a2ff65b0f75d9d4b1ad78f3ebffb886a74be6.m4s
06d5cd79ba3860cccdc252fe915de0902f941a3c6a000295714f7cab193aa6cf floor/hi/06d5cd79ba3860cccdc252fe915de0902f941a3c6a000295714f7cab193aa6cf.m4s
2f93f0ad449f9cc881b7816c6ab33fd445037d6538b445bcc76431f9c9f91c5b floor/hi/2f93f0ad449f9cc881b7816c6ab33fd445037d6538b445bcc76431f9c9f91c5b.m4s
420ae4c941bba6e12a6c7fdb7d01dc69170ecb4240dffd2e86808ddf87baa12a floor/hi/420ae4c941bba6e12a6c7fdb7d01dc69170ecb4240dffd2e86808ddf87baa12a.m4s
576b7d2156c2b595bf48bf34f67996d7f89e75d105f0dc71c9841bb96e6cd0fc floor/hi/576b7d2156c2b595bf48bf34f67996d7f89e75d105f0dc71c9841bb96e6cd0fc.m4s
58c598174eed554cd0d1bc8abedca8c9d51d992c8e3b963bcb7574da4983ed9f floor/hi/init.mp4
589ad79210bff258db68916876846a2b0d530ea2e44260af66ddc51ad14ce07f floor/lo/589ad79210bff258db68916876846a2b0d530ea2e44260af66ddc51ad14ce07f.m4s
6bba50408f894d0e9d5516a53992fdd2aa86db43ccdc684b69c51a688856a0db floor/lo/6bba50408f894d0e9d5516a53992fdd2aa86db43ccdc684b69c51a688856a0db.m4s
acd166807d05fe4f512407f717659d88613f6d0d360485effe3751504cefbb74 floor/lo/acd166807d05fe4f512407f717659d88613f6d0d360485effe3751504cefbb74.m4s
d0f68eb18af5b67736ddccd97ed45c4c0274b0460f6abc8f54940ac378165833 floor/lo/d0f68eb18af5b67736ddccd97ed45c4c0274b0460f6abc8f54940ac378165833.m4s
d550ebb204adf0b5a7f310c7d07189e7bed63e12e34e9ed4d9bf96a101d864a9 floor/lo/d550ebb204adf0b5a7f310c7d07189e7bed63e12e34e9ed4d9bf96a101d864a9.m4s
640cd81c83baefbe13e8ccc2bf577395c6602885cc73e201ca34dc267e7f0a48 floor/lo/init.mp4
bfa98255d682517f58df4073bc71fdb3fcca120fc33d16e4aca873392476c586 hls/classic/floor-hi.m3u8
ad81674ac359096ebed255a26a40e82858e53e9754702429e59d72898df33812 hls/classic/floor-lo.m3u8
3d8ca6988d54790388e062f4ed37b3f73fd6904aefa5ed88014125e51aaf5429 hls/classic/master.m3u8
3fd88f9dcf835edf0fcca8dff8371d2b4e897ac097fc85901477c950c0da7996 hls/legacy/master.m3u8
09e75f55cb7ea829a4e630404d2ab540e8be0dbb1c4365dc30802359b658aed9 hls/mobile/master.m3u8
c4044eca76959c9f87230484a2b207fb12c0bcaedb8d921eab806014fca53cb8 hls/mobile/wai-v.m3u8
60a6378f46afc9308dc4ac4d138602b16568577616ea0bf4526b142d86899151 hls/mobile/wai.m3u8
09e75f55cb7ea829a4e630404d2ab540e8be0dbb1c4365dc30802359b658aed9 hls/tv/master.m3u8
ff4edf2929e380d205c1c74156621185feec53d593ffa968b8dfaf0d05448bcd hls/tv/wai-v.m3u8
5d42147b308330913c3d9c8a868ca83ce4d3f3e460da8d84c84014eb24aaf9d7 hls/tv/wai.m3u8
a5140df0bf1f82b88335c13789502298a952b350ad45dfcfcd249b2b9a263a71 index-v.wsix
c310c5a4ae14df691a1a37a6c34e90243ed72be1e8f725d38f1babe1f6866b21 moq/catalog.json
07e98fb9ef9ff3fa6bf04f9078da2a3d2423e586feea1061256131a1d1fbb943 objects/24761a434c91c627f11abd6265371966b50573602a200dd7bb04e0d90889326d.wai
2f5bd830d841eb122c63ae57a15442075478fd522ce55b6f9bcbe41acd51d8ae objects/482fbbb9b39bdb9cbf00515f94269ea591df681ced90b05d97e0df106b49b08e.wai
0057633252a2c2ed5f71fe14ca78075c8e89fc6675a08335ac90f0e56032b825 objects/4ab8f747d181632f342a4887b0a8bb86c174409cb625157784e18c5e5559a381.wai
cfb71256ef44758ea279846a8938823994d321abce83ef73afd2ed269a8e0259 objects/618e0a89be8c7e556b380326b219c2f6fbfc5a0cb97754e871c1c23a99bdb481.wai
f3eedf9eb2870c0160801397412e7a4c3aca4a6e16f1a69a276e1356d38c9220 objects/61c7c3b7ccab07ed01df5b0d7ca0240598b914dbf2cabe545aa001e8de12d365.wai
1a6f30fdc000f258c948470386d84beef2ba5a84e922c355093837ae21fd573c objects/6ce13c9ef6872caeb7fbe71661ca88bcc463ceac47f109c8c155e34bb1a6f37d.wai
b773dac63c9d2d9980d0d249ea956e03065c1ae40d17c512df29b690c0c820ef objects/b7bf0717e968d7b6be473785c9f66cbb814cde679bceb1ae37f0765308ddee72.wai
b2a40a9a8cec3dcaf6c92a07d6765203c412c57ec879b7e33a52eabb2e74609d objects/c2ce1907255a041c388afd06ccd007436368e8d20467fdec2a1eebbb84b03bf2.wai
cc8a6fc59be29bd33d96fb30ea9e5a30a5aa367a82da9c5784cbadce63396f62 objects/cf842ef3058d3c54d56c0ea3e075efdc77163602b4a1dabcff080e5ea28b9946.wai
01b596b672de3352adb3e01b34fcddfeff975f4ee1d0b88dde160ac10c9bf929 objects/d382ba093b0595c44a43dc3aad22fc0bed42baeb3488f00dfe3567056a7009c5.wai
9d9ae296558ce7f7d644ad0ca3af65eb4fc98d03b0bd6d7a8fc821fc952e86c1 objects/f525b4450c29153dde0b43e4d143dfb76fcc3884c607b744c8a53fa6a1728580.wai
3d573ee482f8187b0e3bc839aeea0f51a67144588d6d207e8466fea91a0c5b34 objects/f7f7f4d6af777bfcce09cdda5ecb754ce6bd8dcd2e03ecfc41359cad989b15f7.wai
bd6086051d0452449da8a90f426f454fee368b4794f7c294218a410ded8d9088 package.receipt.json
517630d9bee1f5559baff3bb3e642f6aa7b5276226f6e3bdba4f3f9724794859 plan-v.txt
d1cf1bd28a06f3a9d695dd64331cb56cf793818e9e9e6cec620183d9dce37b2d policy.json
4ba48d04e5c8e72336e32307b27b4371c96f20f7abf959ac1c1d344ccb9a8106 policy.toml
813329d5521ab5891bb86d29b362e448fae4247c949384b0687d66966546c4fe stages/legacy.json
ca8e0059a23311d7690a0519f85dfb48883721c817cd8fe1cd481cabe14b0032 stages/mobile.json
8bc9c9da674b4765ead0e41d54852ac105161e9638e7ae705e3982847b069e4c stages/tv.json

View file

@ -0,0 +1,5 @@
#EXTM3U
#EXT-X-VERSION:7
#EXT-X-INDEPENDENT-SEGMENTS
#EXT-X-STREAM-INF:BANDWIDTH=10440,AVERAGE-BANDWIDTH=9055,CODECS="av01.0.00M.08",RESOLUTION=64x36
../classic/floor-hi.m3u8

View file

@ -96,6 +96,24 @@
"index": "index/floor-without-derived-from.wsix",
"reason": "floor-derived-from"
},
{
"name": "floor-only-piece",
"kind": "index",
"index": "index/floor-only-piece.wsix",
"reason": "ok"
},
{
"name": "floor-only-piece-with-derived-from",
"kind": "index",
"index": "index/floor-only-piece-with-derived-from.wsix",
"reason": "floor-derived-from"
},
{
"name": "piece-kind-none",
"kind": "index",
"index": "index/piece-kind-none.wsix",
"reason": "ok"
},
{
"name": "entry-flag-unknown",
"kind": "index",

File diff suppressed because it is too large Load diff

View file

@ -282,6 +282,31 @@
"reason": "receipt-json",
"remove": []
},
{
"name": "metered",
"reason": "ok",
"remove": []
},
{
"name": "metered-claim-another-figure",
"reason": "measurement-claim-invalid",
"remove": []
},
{
"name": "metered-claim-missing",
"reason": "measurement-claim-missing",
"remove": []
},
{
"name": "metered-fabrics",
"reason": "ok",
"remove": []
},
{
"name": "metered-fabrics-unknown-step",
"reason": "measurement-claim-invalid",
"remove": []
},
{
"name": "empty-directory",
"reason": "unexpected-file",

View file

@ -0,0 +1,36 @@
9414f625ee38f54eb010a003c262ec5ed1ffc95b82510dc032da065846ff4b9b claims/01d891a6690096d3de7c8e7cec802cb95f82deb84b5d45994dd713e7576673f2.measurement.json
91b8aba2292191f2046eb841fe6fcb7b214826cecd9e06a3c193a68e7089e144 dash/classic.mpd
a3aa7658db9b85a9d9a1fed977825189f75c5adad0f5fdfcd70ebd604824c138 dash/mobile.mpd
3f520749a6d2f231cddfd17804ee3629439f3678515e424c44e36cff54d89de9 dash/tv.mpd
04c948608aaa7b5d78ad5355042a2ff65b0f75d9d4b1ad78f3ebffb886a74be6 floor/v/04c948608aaa7b5d78ad5355042a2ff65b0f75d9d4b1ad78f3ebffb886a74be6.m4s
06d5cd79ba3860cccdc252fe915de0902f941a3c6a000295714f7cab193aa6cf floor/v/06d5cd79ba3860cccdc252fe915de0902f941a3c6a000295714f7cab193aa6cf.m4s
2f93f0ad449f9cc881b7816c6ab33fd445037d6538b445bcc76431f9c9f91c5b floor/v/2f93f0ad449f9cc881b7816c6ab33fd445037d6538b445bcc76431f9c9f91c5b.m4s
420ae4c941bba6e12a6c7fdb7d01dc69170ecb4240dffd2e86808ddf87baa12a floor/v/420ae4c941bba6e12a6c7fdb7d01dc69170ecb4240dffd2e86808ddf87baa12a.m4s
99a24de04f7be9fc21097e69d2d61b222e458b1f93b8082026a9874aeb9f4c15 floor/v/99a24de04f7be9fc21097e69d2d61b222e458b1f93b8082026a9874aeb9f4c15.m4s
58c598174eed554cd0d1bc8abedca8c9d51d992c8e3b963bcb7574da4983ed9f floor/v/init.mp4
289bfcb09eb25124ac19597bc624371c34bea00aa1011ced9372d96b5e14b2bd hls/classic/floor-v.m3u8
3026d7f11005e34ff66298175777ee6806d649cf9d5c1467aaa4fb00ac5987e6 hls/classic/master.m3u8
3026d7f11005e34ff66298175777ee6806d649cf9d5c1467aaa4fb00ac5987e6 hls/legacy/master.m3u8
c5902f61ffaf77f940c4d3dc6e850340aaaeb3f433e4541f935c32443c50b341 hls/mobile/master.m3u8
c4044eca76959c9f87230484a2b207fb12c0bcaedb8d921eab806014fca53cb8 hls/mobile/wai-v.m3u8
60a6378f46afc9308dc4ac4d138602b16568577616ea0bf4526b142d86899151 hls/mobile/wai.m3u8
c5902f61ffaf77f940c4d3dc6e850340aaaeb3f433e4541f935c32443c50b341 hls/tv/master.m3u8
ff4edf2929e380d205c1c74156621185feec53d593ffa968b8dfaf0d05448bcd hls/tv/wai-v.m3u8
5d42147b308330913c3d9c8a868ca83ce4d3f3e460da8d84c84014eb24aaf9d7 hls/tv/wai.m3u8
0b65400d0bbde57ed6a2c19d90cb72ec753de0e76165e4f286acfd5a7bda14d2 index-v.wsix
115e8e1e7ee0765de9bd2f71576cae01ce6576a5ce2a24f3374879eb74d9a6af moq/catalog.json
07e98fb9ef9ff3fa6bf04f9078da2a3d2423e586feea1061256131a1d1fbb943 objects/24761a434c91c627f11abd6265371966b50573602a200dd7bb04e0d90889326d.wai
4d583d03292b77f9d46b02f2c80a774b1cda1b07df38243d18fe586b82eaca60 objects/35c7a45323b7afe979c123fa885f35cc55fabd2a1954759aebe4b95dbc76361f.wai
cfb71256ef44758ea279846a8938823994d321abce83ef73afd2ed269a8e0259 objects/618e0a89be8c7e556b380326b219c2f6fbfc5a0cb97754e871c1c23a99bdb481.wai
f3eedf9eb2870c0160801397412e7a4c3aca4a6e16f1a69a276e1356d38c9220 objects/61c7c3b7ccab07ed01df5b0d7ca0240598b914dbf2cabe545aa001e8de12d365.wai
9fdf29f5c9536d1f7701c791328d656ef725ba9b8cb3760bdb00f5a503c69338 objects/761c4649427c51796a2b699568775765b209ee80d2f4fc1cf040838c6724aa2d.wai
a3135205d3139b39409d4e4e2aafed2c042797d293a9f9fc8664467165336e25 objects/7cc2b824ad6105abfccae27093190311b6a2348842e571684b021a213341b94a.wai
3c66c0b25b759cd1fe6245d282ba928441b873d62e4ac62c95260e45a80fff77 objects/8f748dc64787b5c5ece081270c8559277f926322dd6ddc345306b8231f2d1752.wai
b2a40a9a8cec3dcaf6c92a07d6765203c412c57ec879b7e33a52eabb2e74609d objects/c2ce1907255a041c388afd06ccd007436368e8d20467fdec2a1eebbb84b03bf2.wai
4a2370c37281e64f30cb66a4bd7125854d6280855e90f00229b177bd70af3d8c package.receipt.json
517630d9bee1f5559baff3bb3e642f6aa7b5276226f6e3bdba4f3f9724794859 plan-v.txt
a497fdf29528c4744ce8548e3b430d6311f15c10ca2a4cb548fb9958d3d98f07 policy.json
d667cfa0c1e4e52f254f3a89a80cb0d3b6be0d833c40c8b44f60be33765859b0 policy.toml
59b343802800c815390b840da3ee6981367b495a30d8a1952f6484d04271caf9 stages/legacy.json
b7514cb869338126e4785943a4624e9dbfa44464fa450c55341b7931bd9c19f9 stages/mobile.json
33898452413a8fe209fb6b158bfd1e9b06a74fc3ab7639810522a586a4aa6ac6 stages/tv.json

View file

@ -0,0 +1 @@
{"body":{"bracket":null,"build":{"profile":"release","target":null,"toolchain":null},"energy_calibration_ref":null,"energy_counter_filtering":null,"energy_provenance":"ModelBased","energy_uncertainty":null,"figure_index":null,"figure_profile":"wai:video-package-receipt-id","group":null,"joules_micro":500001,"power_reader":"model:500mW"},"class":"measurement","issued_at":"2026-10-21T00:00:00Z","kind":"claim","parent_receipt_hash":null,"seq":0,"sig":"d6935698b54a44f0ff253340fe62334f30a2e8de5d4ab277496e67e666e621b87fdbd558867a7d64f5be637c9388f0cd5696d7629ad87fe89bf09194e0a35500","signer_id":"did:key:z6MkfMo6gxqdBhaHMNnmfhgZFBjpCDTkmJMJLoypsBZS9PwD","signer_pubkey":"0d7550754e0800a5d237eef5826035766b9b3e5a15868a940ab289958788e3b0","subject":"01d891a6690096d3de7c8e7cec802cb95f82deb84b5d45994dd713e7576673f2","subject_type":"receipt"}

View file

@ -0,0 +1 @@
{"asset_id":"video-base-01","components":[{"id":"v","index":"index-v.wsix","index_digest":"5ffc2be3f21af79078a1158e3d669e4268a35b0ca61a6e73ff252fdf38f346d0","media_class":"video","stage_root":"bd0c7799633b108cf9ccb0c7a4cedbdf6173a83470d3d96b94d075c03e0db7b6"}],"energy_provenance":"ModelBased","grant":{"capability":"wai.video.package","funds_ceiling":null,"grant_hash":"0000000000000000000000000000000000000000000000000000000000000000","joule_ceiling_micro":null},"joules_micro":500000,"kind":"package","packager":"builtin:[email protected]","parent_kind":"none","parent_receipt_hash":null,"policy_digest":"e1c131d56798eb840e22736076d74908bca2b7585aeae7e4bb1698218c01a35e","receipt_hash":"01d891a6690096d3de7c8e7cec802cb95f82deb84b5d45994dd713e7576673f2","sig":"eb052a53c735830304a6c74230dcc348ca6d0c8110497e916407062da83e627db36ba165167ed217e451a26dfa1f5b5e21cf766725063c4532df82ff9d949604","signer_id":"did:key:z6MkfMo6gxqdBhaHMNnmfhgZFBjpCDTkmJMJLoypsBZS9PwD","signer_pubkey":"0d7550754e0800a5d237eef5826035766b9b3e5a15868a940ab289958788e3b0","stored_bytes":119779,"total_bytes":130963,"total_entries":10,"unique_objects":8,"version":2,"work_units":10}

View file

@ -0,0 +1,35 @@
91b8aba2292191f2046eb841fe6fcb7b214826cecd9e06a3c193a68e7089e144 dash/classic.mpd
a3aa7658db9b85a9d9a1fed977825189f75c5adad0f5fdfcd70ebd604824c138 dash/mobile.mpd
3f520749a6d2f231cddfd17804ee3629439f3678515e424c44e36cff54d89de9 dash/tv.mpd
04c948608aaa7b5d78ad5355042a2ff65b0f75d9d4b1ad78f3ebffb886a74be6 floor/v/04c948608aaa7b5d78ad5355042a2ff65b0f75d9d4b1ad78f3ebffb886a74be6.m4s
06d5cd79ba3860cccdc252fe915de0902f941a3c6a000295714f7cab193aa6cf floor/v/06d5cd79ba3860cccdc252fe915de0902f941a3c6a000295714f7cab193aa6cf.m4s
2f93f0ad449f9cc881b7816c6ab33fd445037d6538b445bcc76431f9c9f91c5b floor/v/2f93f0ad449f9cc881b7816c6ab33fd445037d6538b445bcc76431f9c9f91c5b.m4s
420ae4c941bba6e12a6c7fdb7d01dc69170ecb4240dffd2e86808ddf87baa12a floor/v/420ae4c941bba6e12a6c7fdb7d01dc69170ecb4240dffd2e86808ddf87baa12a.m4s
99a24de04f7be9fc21097e69d2d61b222e458b1f93b8082026a9874aeb9f4c15 floor/v/99a24de04f7be9fc21097e69d2d61b222e458b1f93b8082026a9874aeb9f4c15.m4s
58c598174eed554cd0d1bc8abedca8c9d51d992c8e3b963bcb7574da4983ed9f floor/v/init.mp4
289bfcb09eb25124ac19597bc624371c34bea00aa1011ced9372d96b5e14b2bd hls/classic/floor-v.m3u8
3026d7f11005e34ff66298175777ee6806d649cf9d5c1467aaa4fb00ac5987e6 hls/classic/master.m3u8
3026d7f11005e34ff66298175777ee6806d649cf9d5c1467aaa4fb00ac5987e6 hls/legacy/master.m3u8
c5902f61ffaf77f940c4d3dc6e850340aaaeb3f433e4541f935c32443c50b341 hls/mobile/master.m3u8
c4044eca76959c9f87230484a2b207fb12c0bcaedb8d921eab806014fca53cb8 hls/mobile/wai-v.m3u8
60a6378f46afc9308dc4ac4d138602b16568577616ea0bf4526b142d86899151 hls/mobile/wai.m3u8
c5902f61ffaf77f940c4d3dc6e850340aaaeb3f433e4541f935c32443c50b341 hls/tv/master.m3u8
ff4edf2929e380d205c1c74156621185feec53d593ffa968b8dfaf0d05448bcd hls/tv/wai-v.m3u8
5d42147b308330913c3d9c8a868ca83ce4d3f3e460da8d84c84014eb24aaf9d7 hls/tv/wai.m3u8
0b65400d0bbde57ed6a2c19d90cb72ec753de0e76165e4f286acfd5a7bda14d2 index-v.wsix
115e8e1e7ee0765de9bd2f71576cae01ce6576a5ce2a24f3374879eb74d9a6af moq/catalog.json
07e98fb9ef9ff3fa6bf04f9078da2a3d2423e586feea1061256131a1d1fbb943 objects/24761a434c91c627f11abd6265371966b50573602a200dd7bb04e0d90889326d.wai
4d583d03292b77f9d46b02f2c80a774b1cda1b07df38243d18fe586b82eaca60 objects/35c7a45323b7afe979c123fa885f35cc55fabd2a1954759aebe4b95dbc76361f.wai
cfb71256ef44758ea279846a8938823994d321abce83ef73afd2ed269a8e0259 objects/618e0a89be8c7e556b380326b219c2f6fbfc5a0cb97754e871c1c23a99bdb481.wai
f3eedf9eb2870c0160801397412e7a4c3aca4a6e16f1a69a276e1356d38c9220 objects/61c7c3b7ccab07ed01df5b0d7ca0240598b914dbf2cabe545aa001e8de12d365.wai
9fdf29f5c9536d1f7701c791328d656ef725ba9b8cb3760bdb00f5a503c69338 objects/761c4649427c51796a2b699568775765b209ee80d2f4fc1cf040838c6724aa2d.wai
a3135205d3139b39409d4e4e2aafed2c042797d293a9f9fc8664467165336e25 objects/7cc2b824ad6105abfccae27093190311b6a2348842e571684b021a213341b94a.wai
3c66c0b25b759cd1fe6245d282ba928441b873d62e4ac62c95260e45a80fff77 objects/8f748dc64787b5c5ece081270c8559277f926322dd6ddc345306b8231f2d1752.wai
b2a40a9a8cec3dcaf6c92a07d6765203c412c57ec879b7e33a52eabb2e74609d objects/c2ce1907255a041c388afd06ccd007436368e8d20467fdec2a1eebbb84b03bf2.wai
4a2370c37281e64f30cb66a4bd7125854d6280855e90f00229b177bd70af3d8c package.receipt.json
517630d9bee1f5559baff3bb3e642f6aa7b5276226f6e3bdba4f3f9724794859 plan-v.txt
a497fdf29528c4744ce8548e3b430d6311f15c10ca2a4cb548fb9958d3d98f07 policy.json
d667cfa0c1e4e52f254f3a89a80cb0d3b6be0d833c40c8b44f60be33765859b0 policy.toml
59b343802800c815390b840da3ee6981367b495a30d8a1952f6484d04271caf9 stages/legacy.json
b7514cb869338126e4785943a4624e9dbfa44464fa450c55341b7931bd9c19f9 stages/mobile.json
33898452413a8fe209fb6b158bfd1e9b06a74fc3ab7639810522a586a4aa6ac6 stages/tv.json

View file

@ -0,0 +1 @@
{"asset_id":"video-base-01","components":[{"id":"v","index":"index-v.wsix","index_digest":"5ffc2be3f21af79078a1158e3d669e4268a35b0ca61a6e73ff252fdf38f346d0","media_class":"video","stage_root":"bd0c7799633b108cf9ccb0c7a4cedbdf6173a83470d3d96b94d075c03e0db7b6"}],"energy_provenance":"ModelBased","grant":{"capability":"wai.video.package","funds_ceiling":null,"grant_hash":"0000000000000000000000000000000000000000000000000000000000000000","joule_ceiling_micro":null},"joules_micro":500000,"kind":"package","packager":"builtin:[email protected]","parent_kind":"none","parent_receipt_hash":null,"policy_digest":"e1c131d56798eb840e22736076d74908bca2b7585aeae7e4bb1698218c01a35e","receipt_hash":"01d891a6690096d3de7c8e7cec802cb95f82deb84b5d45994dd713e7576673f2","sig":"eb052a53c735830304a6c74230dcc348ca6d0c8110497e916407062da83e627db36ba165167ed217e451a26dfa1f5b5e21cf766725063c4532df82ff9d949604","signer_id":"did:key:z6MkfMo6gxqdBhaHMNnmfhgZFBjpCDTkmJMJLoypsBZS9PwD","signer_pubkey":"0d7550754e0800a5d237eef5826035766b9b3e5a15868a940ab289958788e3b0","stored_bytes":119779,"total_bytes":130963,"total_entries":10,"unique_objects":8,"version":2,"work_units":10}

View file

@ -0,0 +1,36 @@
6b414a7fc1d9ee44a40aa79b9c3338d04ec00dbfbf88d39f5965ce65a6804890 claims/01d891a6690096d3de7c8e7cec802cb95f82deb84b5d45994dd713e7576673f2.measurement.json
91b8aba2292191f2046eb841fe6fcb7b214826cecd9e06a3c193a68e7089e144 dash/classic.mpd
a3aa7658db9b85a9d9a1fed977825189f75c5adad0f5fdfcd70ebd604824c138 dash/mobile.mpd
3f520749a6d2f231cddfd17804ee3629439f3678515e424c44e36cff54d89de9 dash/tv.mpd
04c948608aaa7b5d78ad5355042a2ff65b0f75d9d4b1ad78f3ebffb886a74be6 floor/v/04c948608aaa7b5d78ad5355042a2ff65b0f75d9d4b1ad78f3ebffb886a74be6.m4s
06d5cd79ba3860cccdc252fe915de0902f941a3c6a000295714f7cab193aa6cf floor/v/06d5cd79ba3860cccdc252fe915de0902f941a3c6a000295714f7cab193aa6cf.m4s
2f93f0ad449f9cc881b7816c6ab33fd445037d6538b445bcc76431f9c9f91c5b floor/v/2f93f0ad449f9cc881b7816c6ab33fd445037d6538b445bcc76431f9c9f91c5b.m4s
420ae4c941bba6e12a6c7fdb7d01dc69170ecb4240dffd2e86808ddf87baa12a floor/v/420ae4c941bba6e12a6c7fdb7d01dc69170ecb4240dffd2e86808ddf87baa12a.m4s
99a24de04f7be9fc21097e69d2d61b222e458b1f93b8082026a9874aeb9f4c15 floor/v/99a24de04f7be9fc21097e69d2d61b222e458b1f93b8082026a9874aeb9f4c15.m4s
58c598174eed554cd0d1bc8abedca8c9d51d992c8e3b963bcb7574da4983ed9f floor/v/init.mp4
289bfcb09eb25124ac19597bc624371c34bea00aa1011ced9372d96b5e14b2bd hls/classic/floor-v.m3u8
3026d7f11005e34ff66298175777ee6806d649cf9d5c1467aaa4fb00ac5987e6 hls/classic/master.m3u8
3026d7f11005e34ff66298175777ee6806d649cf9d5c1467aaa4fb00ac5987e6 hls/legacy/master.m3u8
c5902f61ffaf77f940c4d3dc6e850340aaaeb3f433e4541f935c32443c50b341 hls/mobile/master.m3u8
c4044eca76959c9f87230484a2b207fb12c0bcaedb8d921eab806014fca53cb8 hls/mobile/wai-v.m3u8
60a6378f46afc9308dc4ac4d138602b16568577616ea0bf4526b142d86899151 hls/mobile/wai.m3u8
c5902f61ffaf77f940c4d3dc6e850340aaaeb3f433e4541f935c32443c50b341 hls/tv/master.m3u8
ff4edf2929e380d205c1c74156621185feec53d593ffa968b8dfaf0d05448bcd hls/tv/wai-v.m3u8
5d42147b308330913c3d9c8a868ca83ce4d3f3e460da8d84c84014eb24aaf9d7 hls/tv/wai.m3u8
0b65400d0bbde57ed6a2c19d90cb72ec753de0e76165e4f286acfd5a7bda14d2 index-v.wsix
115e8e1e7ee0765de9bd2f71576cae01ce6576a5ce2a24f3374879eb74d9a6af moq/catalog.json
07e98fb9ef9ff3fa6bf04f9078da2a3d2423e586feea1061256131a1d1fbb943 objects/24761a434c91c627f11abd6265371966b50573602a200dd7bb04e0d90889326d.wai
4d583d03292b77f9d46b02f2c80a774b1cda1b07df38243d18fe586b82eaca60 objects/35c7a45323b7afe979c123fa885f35cc55fabd2a1954759aebe4b95dbc76361f.wai
cfb71256ef44758ea279846a8938823994d321abce83ef73afd2ed269a8e0259 objects/618e0a89be8c7e556b380326b219c2f6fbfc5a0cb97754e871c1c23a99bdb481.wai
f3eedf9eb2870c0160801397412e7a4c3aca4a6e16f1a69a276e1356d38c9220 objects/61c7c3b7ccab07ed01df5b0d7ca0240598b914dbf2cabe545aa001e8de12d365.wai
9fdf29f5c9536d1f7701c791328d656ef725ba9b8cb3760bdb00f5a503c69338 objects/761c4649427c51796a2b699568775765b209ee80d2f4fc1cf040838c6724aa2d.wai
a3135205d3139b39409d4e4e2aafed2c042797d293a9f9fc8664467165336e25 objects/7cc2b824ad6105abfccae27093190311b6a2348842e571684b021a213341b94a.wai
3c66c0b25b759cd1fe6245d282ba928441b873d62e4ac62c95260e45a80fff77 objects/8f748dc64787b5c5ece081270c8559277f926322dd6ddc345306b8231f2d1752.wai
b2a40a9a8cec3dcaf6c92a07d6765203c412c57ec879b7e33a52eabb2e74609d objects/c2ce1907255a041c388afd06ccd007436368e8d20467fdec2a1eebbb84b03bf2.wai
4a2370c37281e64f30cb66a4bd7125854d6280855e90f00229b177bd70af3d8c package.receipt.json
517630d9bee1f5559baff3bb3e642f6aa7b5276226f6e3bdba4f3f9724794859 plan-v.txt
a497fdf29528c4744ce8548e3b430d6311f15c10ca2a4cb548fb9958d3d98f07 policy.json
d667cfa0c1e4e52f254f3a89a80cb0d3b6be0d833c40c8b44f60be33765859b0 policy.toml
59b343802800c815390b840da3ee6981367b495a30d8a1952f6484d04271caf9 stages/legacy.json
b7514cb869338126e4785943a4624e9dbfa44464fa450c55341b7931bd9c19f9 stages/mobile.json
33898452413a8fe209fb6b158bfd1e9b06a74fc3ab7639810522a586a4aa6ac6 stages/tv.json

View file

@ -0,0 +1 @@
{"body":{"bracket":null,"build":{"profile":"release","target":null,"toolchain":null},"energy_calibration_ref":null,"energy_counter_filtering":null,"energy_provenance":"ModelBased","energy_uncertainty":null,"fabrics":{"shares":[{"attribution":"task","fabric":"cpu","joules_micro":500000}],"steps":[{"backend":"cpu: the reference implementation","fabric":"cpu","step":"base-code"},{"backend":"cpu: the reference implementation","fabric":"cpu","step":"lunch"}]},"figure_index":null,"figure_profile":"wai:video-package-receipt-id","group":null,"joules_micro":500000,"power_reader":"model:500mW"},"class":"measurement","issued_at":"2026-10-21T00:00:00Z","kind":"claim","parent_receipt_hash":null,"seq":0,"sig":"3d1c9daf255ffd4eded9a09f2ed4d9376ff7a94a28e179e2961aa354255aa3bcca287ac7d201a610fa5f87a527fb31718729fddd5982cb3fe2398a4b1e884806","signer_id":"did:key:z6MkfMo6gxqdBhaHMNnmfhgZFBjpCDTkmJMJLoypsBZS9PwD","signer_pubkey":"0d7550754e0800a5d237eef5826035766b9b3e5a15868a940ab289958788e3b0","subject":"01d891a6690096d3de7c8e7cec802cb95f82deb84b5d45994dd713e7576673f2","subject_type":"receipt"}

View file

@ -0,0 +1 @@
{"asset_id":"video-base-01","components":[{"id":"v","index":"index-v.wsix","index_digest":"5ffc2be3f21af79078a1158e3d669e4268a35b0ca61a6e73ff252fdf38f346d0","media_class":"video","stage_root":"bd0c7799633b108cf9ccb0c7a4cedbdf6173a83470d3d96b94d075c03e0db7b6"}],"energy_provenance":"ModelBased","grant":{"capability":"wai.video.package","funds_ceiling":null,"grant_hash":"0000000000000000000000000000000000000000000000000000000000000000","joule_ceiling_micro":null},"joules_micro":500000,"kind":"package","packager":"builtin:[email protected]","parent_kind":"none","parent_receipt_hash":null,"policy_digest":"e1c131d56798eb840e22736076d74908bca2b7585aeae7e4bb1698218c01a35e","receipt_hash":"01d891a6690096d3de7c8e7cec802cb95f82deb84b5d45994dd713e7576673f2","sig":"eb052a53c735830304a6c74230dcc348ca6d0c8110497e916407062da83e627db36ba165167ed217e451a26dfa1f5b5e21cf766725063c4532df82ff9d949604","signer_id":"did:key:z6MkfMo6gxqdBhaHMNnmfhgZFBjpCDTkmJMJLoypsBZS9PwD","signer_pubkey":"0d7550754e0800a5d237eef5826035766b9b3e5a15868a940ab289958788e3b0","stored_bytes":119779,"total_bytes":130963,"total_entries":10,"unique_objects":8,"version":2,"work_units":10}

View file

@ -0,0 +1,36 @@
4c26bc6aa2694b67430cf49ce8632588c97927c6c776d62295704036a3049d38 claims/01d891a6690096d3de7c8e7cec802cb95f82deb84b5d45994dd713e7576673f2.measurement.json
91b8aba2292191f2046eb841fe6fcb7b214826cecd9e06a3c193a68e7089e144 dash/classic.mpd
a3aa7658db9b85a9d9a1fed977825189f75c5adad0f5fdfcd70ebd604824c138 dash/mobile.mpd
3f520749a6d2f231cddfd17804ee3629439f3678515e424c44e36cff54d89de9 dash/tv.mpd
04c948608aaa7b5d78ad5355042a2ff65b0f75d9d4b1ad78f3ebffb886a74be6 floor/v/04c948608aaa7b5d78ad5355042a2ff65b0f75d9d4b1ad78f3ebffb886a74be6.m4s
06d5cd79ba3860cccdc252fe915de0902f941a3c6a000295714f7cab193aa6cf floor/v/06d5cd79ba3860cccdc252fe915de0902f941a3c6a000295714f7cab193aa6cf.m4s
2f93f0ad449f9cc881b7816c6ab33fd445037d6538b445bcc76431f9c9f91c5b floor/v/2f93f0ad449f9cc881b7816c6ab33fd445037d6538b445bcc76431f9c9f91c5b.m4s
420ae4c941bba6e12a6c7fdb7d01dc69170ecb4240dffd2e86808ddf87baa12a floor/v/420ae4c941bba6e12a6c7fdb7d01dc69170ecb4240dffd2e86808ddf87baa12a.m4s
99a24de04f7be9fc21097e69d2d61b222e458b1f93b8082026a9874aeb9f4c15 floor/v/99a24de04f7be9fc21097e69d2d61b222e458b1f93b8082026a9874aeb9f4c15.m4s
58c598174eed554cd0d1bc8abedca8c9d51d992c8e3b963bcb7574da4983ed9f floor/v/init.mp4
289bfcb09eb25124ac19597bc624371c34bea00aa1011ced9372d96b5e14b2bd hls/classic/floor-v.m3u8
3026d7f11005e34ff66298175777ee6806d649cf9d5c1467aaa4fb00ac5987e6 hls/classic/master.m3u8
3026d7f11005e34ff66298175777ee6806d649cf9d5c1467aaa4fb00ac5987e6 hls/legacy/master.m3u8
c5902f61ffaf77f940c4d3dc6e850340aaaeb3f433e4541f935c32443c50b341 hls/mobile/master.m3u8
c4044eca76959c9f87230484a2b207fb12c0bcaedb8d921eab806014fca53cb8 hls/mobile/wai-v.m3u8
60a6378f46afc9308dc4ac4d138602b16568577616ea0bf4526b142d86899151 hls/mobile/wai.m3u8
c5902f61ffaf77f940c4d3dc6e850340aaaeb3f433e4541f935c32443c50b341 hls/tv/master.m3u8
ff4edf2929e380d205c1c74156621185feec53d593ffa968b8dfaf0d05448bcd hls/tv/wai-v.m3u8
5d42147b308330913c3d9c8a868ca83ce4d3f3e460da8d84c84014eb24aaf9d7 hls/tv/wai.m3u8
0b65400d0bbde57ed6a2c19d90cb72ec753de0e76165e4f286acfd5a7bda14d2 index-v.wsix
115e8e1e7ee0765de9bd2f71576cae01ce6576a5ce2a24f3374879eb74d9a6af moq/catalog.json
07e98fb9ef9ff3fa6bf04f9078da2a3d2423e586feea1061256131a1d1fbb943 objects/24761a434c91c627f11abd6265371966b50573602a200dd7bb04e0d90889326d.wai
4d583d03292b77f9d46b02f2c80a774b1cda1b07df38243d18fe586b82eaca60 objects/35c7a45323b7afe979c123fa885f35cc55fabd2a1954759aebe4b95dbc76361f.wai
cfb71256ef44758ea279846a8938823994d321abce83ef73afd2ed269a8e0259 objects/618e0a89be8c7e556b380326b219c2f6fbfc5a0cb97754e871c1c23a99bdb481.wai
f3eedf9eb2870c0160801397412e7a4c3aca4a6e16f1a69a276e1356d38c9220 objects/61c7c3b7ccab07ed01df5b0d7ca0240598b914dbf2cabe545aa001e8de12d365.wai
9fdf29f5c9536d1f7701c791328d656ef725ba9b8cb3760bdb00f5a503c69338 objects/761c4649427c51796a2b699568775765b209ee80d2f4fc1cf040838c6724aa2d.wai
a3135205d3139b39409d4e4e2aafed2c042797d293a9f9fc8664467165336e25 objects/7cc2b824ad6105abfccae27093190311b6a2348842e571684b021a213341b94a.wai
3c66c0b25b759cd1fe6245d282ba928441b873d62e4ac62c95260e45a80fff77 objects/8f748dc64787b5c5ece081270c8559277f926322dd6ddc345306b8231f2d1752.wai
b2a40a9a8cec3dcaf6c92a07d6765203c412c57ec879b7e33a52eabb2e74609d objects/c2ce1907255a041c388afd06ccd007436368e8d20467fdec2a1eebbb84b03bf2.wai
4a2370c37281e64f30cb66a4bd7125854d6280855e90f00229b177bd70af3d8c package.receipt.json
517630d9bee1f5559baff3bb3e642f6aa7b5276226f6e3bdba4f3f9724794859 plan-v.txt
a497fdf29528c4744ce8548e3b430d6311f15c10ca2a4cb548fb9958d3d98f07 policy.json
d667cfa0c1e4e52f254f3a89a80cb0d3b6be0d833c40c8b44f60be33765859b0 policy.toml
59b343802800c815390b840da3ee6981367b495a30d8a1952f6484d04271caf9 stages/legacy.json
b7514cb869338126e4785943a4624e9dbfa44464fa450c55341b7931bd9c19f9 stages/mobile.json
33898452413a8fe209fb6b158bfd1e9b06a74fc3ab7639810522a586a4aa6ac6 stages/tv.json

View file

@ -0,0 +1 @@
{"body":{"bracket":null,"build":{"profile":"release","target":null,"toolchain":null},"energy_calibration_ref":null,"energy_counter_filtering":null,"energy_provenance":"ModelBased","energy_uncertainty":null,"fabrics":{"shares":[{"attribution":"task","fabric":"cpu","joules_micro":500000}],"steps":[{"backend":"cpu: the reference implementation","fabric":"cpu","step":"base-code"},{"backend":"cpu: the reference implementation","fabric":"cpu","step":"object-hash"}]},"figure_index":null,"figure_profile":"wai:video-package-receipt-id","group":null,"joules_micro":500000,"power_reader":"model:500mW"},"class":"measurement","issued_at":"2026-10-21T00:00:00Z","kind":"claim","parent_receipt_hash":null,"seq":0,"sig":"9888011d5eee7d70fe6f5671e2ad170c05d503b0977bfeacbd23bfb80bd27b95d54ba165c6b4066ce677217b949c5b4da10e251e6c857457c1743f122b9da90f","signer_id":"did:key:z6MkfMo6gxqdBhaHMNnmfhgZFBjpCDTkmJMJLoypsBZS9PwD","signer_pubkey":"0d7550754e0800a5d237eef5826035766b9b3e5a15868a940ab289958788e3b0","subject":"01d891a6690096d3de7c8e7cec802cb95f82deb84b5d45994dd713e7576673f2","subject_type":"receipt"}

View file

@ -0,0 +1 @@
{"asset_id":"video-base-01","components":[{"id":"v","index":"index-v.wsix","index_digest":"5ffc2be3f21af79078a1158e3d669e4268a35b0ca61a6e73ff252fdf38f346d0","media_class":"video","stage_root":"bd0c7799633b108cf9ccb0c7a4cedbdf6173a83470d3d96b94d075c03e0db7b6"}],"energy_provenance":"ModelBased","grant":{"capability":"wai.video.package","funds_ceiling":null,"grant_hash":"0000000000000000000000000000000000000000000000000000000000000000","joule_ceiling_micro":null},"joules_micro":500000,"kind":"package","packager":"builtin:[email protected]","parent_kind":"none","parent_receipt_hash":null,"policy_digest":"e1c131d56798eb840e22736076d74908bca2b7585aeae7e4bb1698218c01a35e","receipt_hash":"01d891a6690096d3de7c8e7cec802cb95f82deb84b5d45994dd713e7576673f2","sig":"eb052a53c735830304a6c74230dcc348ca6d0c8110497e916407062da83e627db36ba165167ed217e451a26dfa1f5b5e21cf766725063c4532df82ff9d949604","signer_id":"did:key:z6MkfMo6gxqdBhaHMNnmfhgZFBjpCDTkmJMJLoypsBZS9PwD","signer_pubkey":"0d7550754e0800a5d237eef5826035766b9b3e5a15868a940ab289958788e3b0","stored_bytes":119779,"total_bytes":130963,"total_entries":10,"unique_objects":8,"version":2,"work_units":10}

View file

@ -0,0 +1,36 @@
a2ef584d432d2a1a1af10cb9d342c0fecbb2c05d72fc054d3792a7ab4bacdce6 claims/01d891a6690096d3de7c8e7cec802cb95f82deb84b5d45994dd713e7576673f2.measurement.json
91b8aba2292191f2046eb841fe6fcb7b214826cecd9e06a3c193a68e7089e144 dash/classic.mpd
a3aa7658db9b85a9d9a1fed977825189f75c5adad0f5fdfcd70ebd604824c138 dash/mobile.mpd
3f520749a6d2f231cddfd17804ee3629439f3678515e424c44e36cff54d89de9 dash/tv.mpd
04c948608aaa7b5d78ad5355042a2ff65b0f75d9d4b1ad78f3ebffb886a74be6 floor/v/04c948608aaa7b5d78ad5355042a2ff65b0f75d9d4b1ad78f3ebffb886a74be6.m4s
06d5cd79ba3860cccdc252fe915de0902f941a3c6a000295714f7cab193aa6cf floor/v/06d5cd79ba3860cccdc252fe915de0902f941a3c6a000295714f7cab193aa6cf.m4s
2f93f0ad449f9cc881b7816c6ab33fd445037d6538b445bcc76431f9c9f91c5b floor/v/2f93f0ad449f9cc881b7816c6ab33fd445037d6538b445bcc76431f9c9f91c5b.m4s
420ae4c941bba6e12a6c7fdb7d01dc69170ecb4240dffd2e86808ddf87baa12a floor/v/420ae4c941bba6e12a6c7fdb7d01dc69170ecb4240dffd2e86808ddf87baa12a.m4s
99a24de04f7be9fc21097e69d2d61b222e458b1f93b8082026a9874aeb9f4c15 floor/v/99a24de04f7be9fc21097e69d2d61b222e458b1f93b8082026a9874aeb9f4c15.m4s
58c598174eed554cd0d1bc8abedca8c9d51d992c8e3b963bcb7574da4983ed9f floor/v/init.mp4
289bfcb09eb25124ac19597bc624371c34bea00aa1011ced9372d96b5e14b2bd hls/classic/floor-v.m3u8
3026d7f11005e34ff66298175777ee6806d649cf9d5c1467aaa4fb00ac5987e6 hls/classic/master.m3u8
3026d7f11005e34ff66298175777ee6806d649cf9d5c1467aaa4fb00ac5987e6 hls/legacy/master.m3u8
c5902f61ffaf77f940c4d3dc6e850340aaaeb3f433e4541f935c32443c50b341 hls/mobile/master.m3u8
c4044eca76959c9f87230484a2b207fb12c0bcaedb8d921eab806014fca53cb8 hls/mobile/wai-v.m3u8
60a6378f46afc9308dc4ac4d138602b16568577616ea0bf4526b142d86899151 hls/mobile/wai.m3u8
c5902f61ffaf77f940c4d3dc6e850340aaaeb3f433e4541f935c32443c50b341 hls/tv/master.m3u8
ff4edf2929e380d205c1c74156621185feec53d593ffa968b8dfaf0d05448bcd hls/tv/wai-v.m3u8
5d42147b308330913c3d9c8a868ca83ce4d3f3e460da8d84c84014eb24aaf9d7 hls/tv/wai.m3u8
0b65400d0bbde57ed6a2c19d90cb72ec753de0e76165e4f286acfd5a7bda14d2 index-v.wsix
115e8e1e7ee0765de9bd2f71576cae01ce6576a5ce2a24f3374879eb74d9a6af moq/catalog.json
07e98fb9ef9ff3fa6bf04f9078da2a3d2423e586feea1061256131a1d1fbb943 objects/24761a434c91c627f11abd6265371966b50573602a200dd7bb04e0d90889326d.wai
4d583d03292b77f9d46b02f2c80a774b1cda1b07df38243d18fe586b82eaca60 objects/35c7a45323b7afe979c123fa885f35cc55fabd2a1954759aebe4b95dbc76361f.wai
cfb71256ef44758ea279846a8938823994d321abce83ef73afd2ed269a8e0259 objects/618e0a89be8c7e556b380326b219c2f6fbfc5a0cb97754e871c1c23a99bdb481.wai
f3eedf9eb2870c0160801397412e7a4c3aca4a6e16f1a69a276e1356d38c9220 objects/61c7c3b7ccab07ed01df5b0d7ca0240598b914dbf2cabe545aa001e8de12d365.wai
9fdf29f5c9536d1f7701c791328d656ef725ba9b8cb3760bdb00f5a503c69338 objects/761c4649427c51796a2b699568775765b209ee80d2f4fc1cf040838c6724aa2d.wai
a3135205d3139b39409d4e4e2aafed2c042797d293a9f9fc8664467165336e25 objects/7cc2b824ad6105abfccae27093190311b6a2348842e571684b021a213341b94a.wai
3c66c0b25b759cd1fe6245d282ba928441b873d62e4ac62c95260e45a80fff77 objects/8f748dc64787b5c5ece081270c8559277f926322dd6ddc345306b8231f2d1752.wai
b2a40a9a8cec3dcaf6c92a07d6765203c412c57ec879b7e33a52eabb2e74609d objects/c2ce1907255a041c388afd06ccd007436368e8d20467fdec2a1eebbb84b03bf2.wai
4a2370c37281e64f30cb66a4bd7125854d6280855e90f00229b177bd70af3d8c package.receipt.json
517630d9bee1f5559baff3bb3e642f6aa7b5276226f6e3bdba4f3f9724794859 plan-v.txt
a497fdf29528c4744ce8548e3b430d6311f15c10ca2a4cb548fb9958d3d98f07 policy.json
d667cfa0c1e4e52f254f3a89a80cb0d3b6be0d833c40c8b44f60be33765859b0 policy.toml
59b343802800c815390b840da3ee6981367b495a30d8a1952f6484d04271caf9 stages/legacy.json
b7514cb869338126e4785943a4624e9dbfa44464fa450c55341b7931bd9c19f9 stages/mobile.json
33898452413a8fe209fb6b158bfd1e9b06a74fc3ab7639810522a586a4aa6ac6 stages/tv.json

View file

@ -0,0 +1 @@
{"body":{"bracket":null,"build":{"profile":"release","target":null,"toolchain":null},"energy_calibration_ref":null,"energy_counter_filtering":null,"energy_provenance":"ModelBased","energy_uncertainty":null,"figure_index":null,"figure_profile":"wai:video-package-receipt-id","group":null,"joules_micro":500000,"power_reader":"model:500mW"},"class":"measurement","issued_at":"2026-10-21T00:00:00Z","kind":"claim","parent_receipt_hash":null,"seq":0,"sig":"8e4df4a0568d61e153cd7eca9e8664dc69b11202d8999138b639ffa77f7ade7de212a2b31d3a7977861ab176286a77633257a17d0919c5e04a9d2741b85fc807","signer_id":"did:key:z6MkfMo6gxqdBhaHMNnmfhgZFBjpCDTkmJMJLoypsBZS9PwD","signer_pubkey":"0d7550754e0800a5d237eef5826035766b9b3e5a15868a940ab289958788e3b0","subject":"01d891a6690096d3de7c8e7cec802cb95f82deb84b5d45994dd713e7576673f2","subject_type":"receipt"}

View file

@ -0,0 +1 @@
{"asset_id":"video-base-01","components":[{"id":"v","index":"index-v.wsix","index_digest":"5ffc2be3f21af79078a1158e3d669e4268a35b0ca61a6e73ff252fdf38f346d0","media_class":"video","stage_root":"bd0c7799633b108cf9ccb0c7a4cedbdf6173a83470d3d96b94d075c03e0db7b6"}],"energy_provenance":"ModelBased","grant":{"capability":"wai.video.package","funds_ceiling":null,"grant_hash":"0000000000000000000000000000000000000000000000000000000000000000","joule_ceiling_micro":null},"joules_micro":500000,"kind":"package","packager":"builtin:[email protected]","parent_kind":"none","parent_receipt_hash":null,"policy_digest":"e1c131d56798eb840e22736076d74908bca2b7585aeae7e4bb1698218c01a35e","receipt_hash":"01d891a6690096d3de7c8e7cec802cb95f82deb84b5d45994dd713e7576673f2","sig":"eb052a53c735830304a6c74230dcc348ca6d0c8110497e916407062da83e627db36ba165167ed217e451a26dfa1f5b5e21cf766725063c4532df82ff9d949604","signer_id":"did:key:z6MkfMo6gxqdBhaHMNnmfhgZFBjpCDTkmJMJLoypsBZS9PwD","signer_pubkey":"0d7550754e0800a5d237eef5826035766b9b3e5a15868a940ab289958788e3b0","stored_bytes":119779,"total_bytes":130963,"total_entries":10,"unique_objects":8,"version":2,"work_units":10}

View file

@ -0,0 +1 @@
dd0a68c39958d90953634b6c1070e75dc5a5900d134e53f6b0dd35f0cec7abaa

View file

@ -0,0 +1,47 @@
688cb303ccb16fcdd21c8cb681f936ba813829e71fbf15df0ccb28b04c134447 dash/classic.mpd
a3aa7658db9b85a9d9a1fed977825189f75c5adad0f5fdfcd70ebd604824c138 dash/mobile.mpd
3f520749a6d2f231cddfd17804ee3629439f3678515e424c44e36cff54d89de9 dash/tv.mpd
03ab06e026880875581952f91232405077be9a522dbf739b6a9d093458369710 floor.listing
14cdbe56c8f57b1427ab9c2a9ebf6669ce8edec06fd7cd0961a01d2aaf720889 floor/hi/14cdbe56c8f57b1427ab9c2a9ebf6669ce8edec06fd7cd0961a01d2aaf720889.m4s
759f476ce9e9b003d7d797060f9c039141d261dd65212035e96bb157783423c1 floor/hi/759f476ce9e9b003d7d797060f9c039141d261dd65212035e96bb157783423c1.m4s
d3616b6368fc800ce421a492fbd0f6263b9e06ee0af1e8269ce4f20d5cb3653d floor/hi/d3616b6368fc800ce421a492fbd0f6263b9e06ee0af1e8269ce4f20d5cb3653d.m4s
e5583297b1456e46366fe3317784fadf8c165c5e16e864629b194dc46290387e floor/hi/e5583297b1456e46366fe3317784fadf8c165c5e16e864629b194dc46290387e.m4s
eb559df9571de1869981ca82672abbabad528b294b15a1d7bf9b635761c584f8 floor/hi/eb559df9571de1869981ca82672abbabad528b294b15a1d7bf9b635761c584f8.m4s
a8a19ef9cd4d540037ef298097bbc5317de6a99690c8c4a745cc867c034208d6 floor/hi/init.mp4
0e0407f5a552e405846a411627df17537e5c31accca37390c391a7c1d27353af floor/lo/0e0407f5a552e405846a411627df17537e5c31accca37390c391a7c1d27353af.m4s
10b19654062fa37b83c082c922f54529725c36a4ead953b1fbfbbee14d4e79a8 floor/lo/10b19654062fa37b83c082c922f54529725c36a4ead953b1fbfbbee14d4e79a8.m4s
2c484c9bead2b261ac1a18c2aedec11761813f995d11dc9779c5f9b039d59b73 floor/lo/2c484c9bead2b261ac1a18c2aedec11761813f995d11dc9779c5f9b039d59b73.m4s
a855b2701af4e7c8c912448be9fc023f911b4e9e94b65770393c4df6d705b5e8 floor/lo/a855b2701af4e7c8c912448be9fc023f911b4e9e94b65770393c4df6d705b5e8.m4s
c29687008dafdf251b2ca962c3e830f785b38a56c81aee1f4c86f2e8f9115fcc floor/lo/c29687008dafdf251b2ca962c3e830f785b38a56c81aee1f4c86f2e8f9115fcc.m4s
6dd501e27365ce9ef90576771aad73de4d200362e6974551847afc3c90604344 floor/lo/init.mp4
ebdc7e40aecbe8b61124ac78f233b0dfaf2a8c5674d3fc9bb023935de1d9b6cb hls/classic/floor-hi.m3u8
66f5eb8b89b80e7da839b23f39665eb85480c6a725fa29d93556efee673c1b9e hls/classic/floor-lo.m3u8
d793737b69231eface4951001e65b3c52cba864f231246a41e64d49c77ebdc97 hls/classic/master.m3u8
d793737b69231eface4951001e65b3c52cba864f231246a41e64d49c77ebdc97 hls/legacy/master.m3u8
8c3b5e2b18192b383c8df8675acd435b861a2585bc6eaf0c09292754f44a8cef hls/mobile/master.m3u8
c4044eca76959c9f87230484a2b207fb12c0bcaedb8d921eab806014fca53cb8 hls/mobile/wai-v.m3u8
60a6378f46afc9308dc4ac4d138602b16568577616ea0bf4526b142d86899151 hls/mobile/wai.m3u8
8c3b5e2b18192b383c8df8675acd435b861a2585bc6eaf0c09292754f44a8cef hls/tv/master.m3u8
ff4edf2929e380d205c1c74156621185feec53d593ffa968b8dfaf0d05448bcd hls/tv/wai-v.m3u8
5d42147b308330913c3d9c8a868ca83ce4d3f3e460da8d84c84014eb24aaf9d7 hls/tv/wai.m3u8
649330bcfaaee54f802f6b4ddf6e459daca8bb0e8df86c87a9d6bd0d65cd09ea index-v.wsix
68f00abff5ef19f074d510f8cce4592afc2a1d4981a87663965a46dc8bcbe1d3 moq/catalog.json
9f381e2ab764b5e14770b00503c1c90b9c22ba22f87464b2869a70644af11939 objects/08797901ff55d0bb4afba5cffe95df64b7e216f3a0c9ba82006133bb9b6d7f16.wai
07e98fb9ef9ff3fa6bf04f9078da2a3d2423e586feea1061256131a1d1fbb943 objects/24761a434c91c627f11abd6265371966b50573602a200dd7bb04e0d90889326d.wai
d5f9cdd996920e07339b79093b9e4e5cb4237f1780f268220cc6f89c79aea90a objects/399048a078b0f2983149266a44eaf207cfa63f490212b69389fba4d72f62c60f.wai
cfb71256ef44758ea279846a8938823994d321abce83ef73afd2ed269a8e0259 objects/618e0a89be8c7e556b380326b219c2f6fbfc5a0cb97754e871c1c23a99bdb481.wai
f3eedf9eb2870c0160801397412e7a4c3aca4a6e16f1a69a276e1356d38c9220 objects/61c7c3b7ccab07ed01df5b0d7ca0240598b914dbf2cabe545aa001e8de12d365.wai
d03f0813c266294f84483cfe4db177d094c06b95ab3a8471d6b2ec53401f05a7 objects/a236e9070d10fd09342cafdbf6973edd35e5266cf850fe2f38f77536ac803912.wai
2316616549f7f92dc29e34fe656c332c9f4a1e20f4be26396976407acc792ba4 objects/a3ae43406f9966487b6c5f5a4d56e9dca50c327423fcfd2a98f4c342d1dbfaf9.wai
b2a40a9a8cec3dcaf6c92a07d6765203c412c57ec879b7e33a52eabb2e74609d objects/c2ce1907255a041c388afd06ccd007436368e8d20467fdec2a1eebbb84b03bf2.wai
6d665f1bef3784cbb428abc28724f74fa83c8f2bc812828621c93c5514b6dc0e objects/c5253efe2949669bb9df01d9f60c01f2570ba4be1c0af26105e092dfccf90d30.wai
0acecba00acc28e313805189fd826ad3a9fab1fe69727ef2d5999fc543426289 objects/c81171fa53998cfe94207ad66ab9b53cfbd4b3f058730e62512ca9f0f6ef2ea3.wai
f3bd9cbe3c2518c997a4d1d3a32145a04f55ef53e0b5760a6ce6aa5e14fe06a7 objects/dea0f6415f639fca99d91a0341aba164078a1bd4780e21d72cbf2234928272ec.wai
d22c4f8ac8a5de43bbec6be04ea8b6da72f2bd133f8f57a31607362670178c68 objects/f467872fe8d3cd1f60f832c997cc14fd00abbf601c61286a612089b4a53a195a.wai
f1f4e32ba9f76e36431d97e0fd52b9025075f553bf6b9f63c484d60573c8ea90 package.receipt.json
517630d9bee1f5559baff3bb3e642f6aa7b5276226f6e3bdba4f3f9724794859 plan-v.txt
428e24f9e1c62fc5590ce3d3a6239a5c274dcfc1391a2ea2abe8dc0562da7d20 policy.json
9d2b4c15ac17ee074f646d0b1ed11ef56557f633ff67a3e6a6d0eb4dd1596548 policy.toml
2f5807b891b8eb0a44b76c4303487be1dcf19e111f06f6c642e14b81c85d7c4d stages/legacy.json
8695fff48ca86321c5198e3a8cf660ccba208df4f40fd1907e76c64a52674cf5 stages/mobile.json
6ae56077cfc368a59489233eeee6ee7fd97437821822637ac62096ab93c85286 stages/tv.json

View file

@ -0,0 +1,41 @@
<?xml version="1.0" encoding="UTF-8"?>
<MPD xmlns="urn:mpeg:dash:schema:mpd:2011" profiles="urn:mpeg:dash:profile:full:2011" type="static" mediaPresentationDuration="PT8.000S" minBufferTime="PT3S">
<Period id="p0" start="PT0S">
<AdaptationSet id="1" contentType="video" mimeType="video/mp4" segmentAlignment="true" startWithSAP="1">
<Representation id="hi-floor" bandwidth="9300" codecs="av01.0.00M.08" width="64" height="36">
<SegmentList timescale="25">
<Initialization sourceURL="../floor/hi/init.mp4"/>
<SegmentTimeline>
<S t="0" d="60"/>
<S t="60" d="25"/>
<S t="85" d="50"/>
<S t="135" d="25"/>
<S t="160" d="40"/>
</SegmentTimeline>
<SegmentURL media="../floor/hi/14cdbe56c8f57b1427ab9c2a9ebf6669ce8edec06fd7cd0961a01d2aaf720889.m4s"/>
<SegmentURL media="../floor/hi/e5583297b1456e46366fe3317784fadf8c165c5e16e864629b194dc46290387e.m4s"/>
<SegmentURL media="../floor/hi/d3616b6368fc800ce421a492fbd0f6263b9e06ee0af1e8269ce4f20d5cb3653d.m4s"/>
<SegmentURL media="../floor/hi/eb559df9571de1869981ca82672abbabad528b294b15a1d7bf9b635761c584f8.m4s"/>
<SegmentURL media="../floor/hi/759f476ce9e9b003d7d797060f9c039141d261dd65212035e96bb157783423c1.m4s"/>
</SegmentList>
</Representation>
<Representation id="lo-floor" bandwidth="8152" codecs="av01.0.00M.08" width="32" height="18">
<SegmentList timescale="25">
<Initialization sourceURL="../floor/lo/init.mp4"/>
<SegmentTimeline>
<S t="0" d="60"/>
<S t="60" d="25"/>
<S t="85" d="50"/>
<S t="135" d="25"/>
<S t="160" d="40"/>
</SegmentTimeline>
<SegmentURL media="../floor/lo/0e0407f5a552e405846a411627df17537e5c31accca37390c391a7c1d27353af.m4s"/>
<SegmentURL media="../floor/lo/c29687008dafdf251b2ca962c3e830f785b38a56c81aee1f4c86f2e8f9115fcc.m4s"/>
<SegmentURL media="../floor/lo/10b19654062fa37b83c082c922f54529725c36a4ead953b1fbfbbee14d4e79a8.m4s"/>
<SegmentURL media="../floor/lo/a855b2701af4e7c8c912448be9fc023f911b4e9e94b65770393c4df6d705b5e8.m4s"/>
<SegmentURL media="../floor/lo/2c484c9bead2b261ac1a18c2aedec11761813f995d11dc9779c5f9b039d59b73.m4s"/>
</SegmentList>
</Representation>
</AdaptationSet>
</Period>
</MPD>

View file

@ -0,0 +1,21 @@
<?xml version="1.0" encoding="UTF-8"?>
<MPD xmlns="urn:mpeg:dash:schema:mpd:2011" profiles="urn:mpeg:dash:profile:full:2011" type="static" mediaPresentationDuration="PT8.000S" minBufferTime="PT3S">
<Period id="p0" start="PT0S">
<AdaptationSet id="1" contentType="video" mimeType="application/wai" codecs="wai1.video.int_motion" width="64" height="36">
<EssentialProperty schemeIdUri="tag:transaction.science,2026:wai/http-delivery"/>
<SupplementalProperty schemeIdUri="tag:transaction.science,2026:wai/floor" value="wai1.video.int_motion"/>
<SupplementalProperty schemeIdUri="tag:transaction.science,2026:wai/class" value="mobile"/>
<SupplementalProperty schemeIdUri="tag:transaction.science,2026:wai/stages" value="../stages/mobile.json"/>
<Representation id="v-l0" bandwidth="79600">
<SegmentList timescale="25">
<SegmentTimeline>
<S t="60" d="25"/>
<S t="135" d="25"/>
</SegmentTimeline>
<SegmentURL media="../objects/61c7c3b7ccab07ed01df5b0d7ca0240598b914dbf2cabe545aa001e8de12d365.wai"/>
<SegmentURL media="../objects/61c7c3b7ccab07ed01df5b0d7ca0240598b914dbf2cabe545aa001e8de12d365.wai"/>
</SegmentList>
</Representation>
</AdaptationSet>
</Period>
</MPD>

View file

@ -0,0 +1,27 @@
<?xml version="1.0" encoding="UTF-8"?>
<MPD xmlns="urn:mpeg:dash:schema:mpd:2011" profiles="urn:mpeg:dash:profile:full:2011" type="static" mediaPresentationDuration="PT8.000S" minBufferTime="PT3S">
<Period id="p0" start="PT0S">
<AdaptationSet id="1" contentType="video" mimeType="application/wai" codecs="wai1.video.int_motion" width="64" height="36">
<EssentialProperty schemeIdUri="tag:transaction.science,2026:wai/http-delivery"/>
<SupplementalProperty schemeIdUri="tag:transaction.science,2026:wai/floor" value="wai1.video.int_motion"/>
<SupplementalProperty schemeIdUri="tag:transaction.science,2026:wai/class" value="tv"/>
<SupplementalProperty schemeIdUri="tag:transaction.science,2026:wai/stages" value="../stages/tv.json"/>
<Representation id="v-l0" bandwidth="143528">
<SegmentList timescale="25">
<SegmentTimeline>
<S t="0" d="60"/>
<S t="60" d="25"/>
<S t="85" d="50"/>
<S t="135" d="25"/>
<S t="160" d="40"/>
</SegmentTimeline>
<SegmentURL media="../objects/24761a434c91c627f11abd6265371966b50573602a200dd7bb04e0d90889326d.wai"/>
<SegmentURL media="../objects/61c7c3b7ccab07ed01df5b0d7ca0240598b914dbf2cabe545aa001e8de12d365.wai"/>
<SegmentURL media="../objects/c2ce1907255a041c388afd06ccd007436368e8d20467fdec2a1eebbb84b03bf2.wai"/>
<SegmentURL media="../objects/61c7c3b7ccab07ed01df5b0d7ca0240598b914dbf2cabe545aa001e8de12d365.wai"/>
<SegmentURL media="../objects/618e0a89be8c7e556b380326b219c2f6fbfc5a0cb97754e871c1c23a99bdb481.wai"/>
</SegmentList>
</Representation>
</AdaptationSet>
</Period>
</MPD>

View file

@ -0,0 +1,12 @@
a8a19ef9cd4d540037ef298097bbc5317de6a99690c8c4a745cc867c034208d6 hi/init.mp4
14cdbe56c8f57b1427ab9c2a9ebf6669ce8edec06fd7cd0961a01d2aaf720889 hi/seg_0000.m4s
e5583297b1456e46366fe3317784fadf8c165c5e16e864629b194dc46290387e hi/seg_0001.m4s
d3616b6368fc800ce421a492fbd0f6263b9e06ee0af1e8269ce4f20d5cb3653d hi/seg_0002.m4s
eb559df9571de1869981ca82672abbabad528b294b15a1d7bf9b635761c584f8 hi/seg_0003.m4s
759f476ce9e9b003d7d797060f9c039141d261dd65212035e96bb157783423c1 hi/seg_0004.m4s
6dd501e27365ce9ef90576771aad73de4d200362e6974551847afc3c90604344 lo/init.mp4
0e0407f5a552e405846a411627df17537e5c31accca37390c391a7c1d27353af lo/seg_0000.m4s
c29687008dafdf251b2ca962c3e830f785b38a56c81aee1f4c86f2e8f9115fcc lo/seg_0001.m4s
10b19654062fa37b83c082c922f54529725c36a4ead953b1fbfbbee14d4e79a8 lo/seg_0002.m4s
a855b2701af4e7c8c912448be9fc023f911b4e9e94b65770393c4df6d705b5e8 lo/seg_0003.m4s
2c484c9bead2b261ac1a18c2aedec11761813f995d11dc9779c5f9b039d59b73 lo/seg_0004.m4s

View file

@ -0,0 +1,18 @@
#EXTM3U
#EXT-X-VERSION:7
#EXT-X-TARGETDURATION:3
#EXT-X-MEDIA-SEQUENCE:0
#EXT-X-PLAYLIST-TYPE:VOD
#EXT-X-INDEPENDENT-SEGMENTS
#EXT-X-MAP:URI="../../floor/hi/init.mp4"
#EXTINF:2.400,
../../floor/hi/14cdbe56c8f57b1427ab9c2a9ebf6669ce8edec06fd7cd0961a01d2aaf720889.m4s
#EXTINF:1.000,
../../floor/hi/e5583297b1456e46366fe3317784fadf8c165c5e16e864629b194dc46290387e.m4s
#EXTINF:2.000,
../../floor/hi/d3616b6368fc800ce421a492fbd0f6263b9e06ee0af1e8269ce4f20d5cb3653d.m4s
#EXTINF:1.000,
../../floor/hi/eb559df9571de1869981ca82672abbabad528b294b15a1d7bf9b635761c584f8.m4s
#EXTINF:1.600,
../../floor/hi/759f476ce9e9b003d7d797060f9c039141d261dd65212035e96bb157783423c1.m4s
#EXT-X-ENDLIST

View file

@ -0,0 +1,18 @@
#EXTM3U
#EXT-X-VERSION:7
#EXT-X-TARGETDURATION:3
#EXT-X-MEDIA-SEQUENCE:0
#EXT-X-PLAYLIST-TYPE:VOD
#EXT-X-INDEPENDENT-SEGMENTS
#EXT-X-MAP:URI="../../floor/lo/init.mp4"
#EXTINF:2.400,
../../floor/lo/0e0407f5a552e405846a411627df17537e5c31accca37390c391a7c1d27353af.m4s
#EXTINF:1.000,
../../floor/lo/c29687008dafdf251b2ca962c3e830f785b38a56c81aee1f4c86f2e8f9115fcc.m4s
#EXTINF:2.000,
../../floor/lo/10b19654062fa37b83c082c922f54529725c36a4ead953b1fbfbbee14d4e79a8.m4s
#EXTINF:1.000,
../../floor/lo/a855b2701af4e7c8c912448be9fc023f911b4e9e94b65770393c4df6d705b5e8.m4s
#EXTINF:1.600,
../../floor/lo/2c484c9bead2b261ac1a18c2aedec11761813f995d11dc9779c5f9b039d59b73.m4s
#EXT-X-ENDLIST

View file

@ -0,0 +1,7 @@
#EXTM3U
#EXT-X-VERSION:7
#EXT-X-INDEPENDENT-SEGMENTS
#EXT-X-STREAM-INF:BANDWIDTH=9300,AVERAGE-BANDWIDTH=7915,CODECS="av01.0.00M.08",RESOLUTION=64x36
../classic/floor-hi.m3u8
#EXT-X-STREAM-INF:BANDWIDTH=8152,AVERAGE-BANDWIDTH=7583,CODECS="av01.0.00M.08",RESOLUTION=32x18
../classic/floor-lo.m3u8

Some files were not shown because too many files have changed in this diff Show more