open-standards/wai/wai-rs/tests/neural_native_decode.rs
Transaction Science fbde9b2131
Some checks failed
no-vanity-metrics / Scan committed Markdown for vanity metrics (pull_request) Successful in 3s
no-vanity-metrics / WAI public text names no comparison (pull_request) Successful in 3s
no-vanity-metrics / WAI public text names no company or product (pull_request) Successful in 3s
standards workspaces build + test / eoc-rs (pull_request) Successful in 1m49s
standards workspaces build + test / jcp-rs (pull_request) Successful in 1m23s
standards workspaces build + test / proof-rs (pull_request) Successful in 1m16s
standards workspaces build + test / aac-rs (pull_request) Failing after 29s
standards workspaces build + test / sandbox-rs (pull_request) Successful in 2m10s
standards workspaces build + test / joule-code-rs (pull_request) Failing after 24s
standards workspaces build + test / joulecontract-rs (pull_request) Failing after 6s
standards workspaces build + test / map-rs (pull_request) Failing after 23s
standards workspaces build + test / mesh-rs (pull_request) Successful in 1m36s
standards workspaces build + test / smart-byte-rs (pull_request) Successful in 3m38s
wai cross-architecture byte-equality / linux-x86_64 (pull_request) Successful in 23s
standards workspaces build + test / openpay (pull_request) Failing after 3m10s
wai cross-architecture byte-equality / linux-aarch64 (pull_request) Successful in 51s
WAI conformance / cargo-class corpora · linux (pull_request) Successful in 3m55s
WAI conformance / v2 vocabulary · manifests validate as stated (pull_request) Successful in 38s
standards workspaces build + test / jouleclaw-rs (pull_request) Failing after 15m48s
WAI conformance / independent verifiers · claims, JWP, key discovery and integer payloads (Python) (pull_request) Successful in 2m9s
WAI conformance / cross-arch byte-equality · linux (pull_request) Successful in 24s
WAI conformance / C2PA manifest emission · signed, read back, validated (pull_request) Successful in 45s
WAI conformance / cargo-class corpora · linux-arm64 (pull_request) Successful in 5m59s
WAI conformance / cross-arch byte-equality · linux-arm64 (pull_request) Successful in 30s
WAI energy receipts / energy receipts · linux (pull_request) Successful in 1m4s
WAI energy receipts / energy receipts · linux-arm64 (pull_request) Successful in 1m8s
wai formal verification (integer core) / kani (pull_request) Successful in 4m22s
WAI JPEG-AI whole decode (pinned inputs, required) / fetch pinned JPEG-AI inputs → whole decode + pixel hash, required (pull_request) Successful in 57s
WAI neural decoders end-to-end / synthetic fixtures → Rust decode → reference (±4) (pull_request) Successful in 1m12s
WAI neural sink gates / model-free refusals of the neural sink (pull_request) Successful in 1m0s
WAI section references / cited sections exist (pull_request) Successful in 11s
WAI mbt2018_mean integer decode (regenerated vectors) / regenerate mbt2018_mean integer vectors → Rust decode, required (pull_request) Successful in 3m53s
wai-web wasm32 / wai-web wasm32 build · corpus, menu and writers (pull_request) Successful in 1m43s
standards workspaces build + test / arl-rs (pull_request) Successful in 2m33s
standards workspaces build + test / joule-ui-rs (pull_request) Successful in 2m59s
standards workspaces build + test / jouledesk-rs (pull_request) Successful in 3m1s
standards workspaces build + test / joulehook-rs (pull_request) Successful in 2m42s
standards workspaces build + test / sense-rs (pull_request) Successful in 2m42s
standards workspaces build + test / macOS energy backend (jcp-energy) (pull_request) Successful in 3m23s
wai cross-architecture byte-equality / macos-arm64 (reference) (pull_request) Successful in 30s
WAI conformance / cargo-class corpora · macos (pull_request) Successful in 6m9s
WAI conformance / cross-arch byte-equality · macos (pull_request) Successful in 31s
WAI energy receipts / energy receipts · macos (pull_request) Successful in 1m35s
wai: an unpinned decode reads its set once and is checked by every identity
Outside the integer path, a sink whose key log only revokes ran check 5
over the registered file's digest and any listing found beside it, then
decoded from the path. With no listing beside them, a revoked several-
file set decoded, and a file changed after the check was what the decode
read.

At a registry with a key log, the neural sink now reads once what the
decode can read: the registered file of a one-file set; otherwise every
file below the directory the decoder reads from (the registered
directory, or the registered file's), as pin::listing_of_dir lists it
(pin::read_dir_set, which listing_of_dir now uses). Check 5 runs over
every digest a pin over it could name: the file's, or the directory's
derived listing and each member's, and each listing beside them that
matches what was read. The decode then reads only those bytes
(neural::ParamSource::Checked, which replaces Authorised and records the
registered file within a set), never the path; where the key log holds
the capability's sets to jwp-receipts §7.9, only the part §7.9
authorised. The decoders outside the integer path read files by name
from that directory, some chosen by the payload, so the set is the
directory rather than a fixed list. With no key log the decode reads the
path, as before.

SPEC §4 (Module authorisation) and jwp-receipts §7.9 state the reference
behaviour.

Test: neural_native_decode::a_revoke_only_key_log_checks_and_reads_the_set_once
(a revoked set beside its listing; with no listing, the decoder and the
directory registered; a member's own digest revoked; the tables swapped
on disk after the check; no key log).

Co-Authored-By: Claude Opus 5.5 <[email protected]>
2026-10-01 23:08:03 -04:00

1630 lines
88 KiB
Rust
Raw Permalink Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

//! Native-sink E2E: decode every shipped `.wai` neural sample through
//! the Rust `ort`-backed runtime. Asserts the decoder produces sane
//! output (right sample count for audio, right pixel grid for image,
//! right frame count for video, and a non-trivial signal in each).
//!
//! Models are expected at `wai-web/demo/models/<name>/decoder.onnx` —
//! built via the corresponding `tools/wai_<name>_export_onnx.py` once
//! per machine (see wai-web/demo/models/README.md).
//!
//! Skipped (printed, not failed) when a given .onnx isn't present yet,
//! so a fresh clone with only some models built still runs the tests
//! that can run.
#![cfg(feature = "neural")]
use std::path::{Path, PathBuf};
use wai::container::{Conditioning, Manifest, ModelRequirement, Prior, Wai};
use wai::neural::{
decode_envelope, decode_envelope_strict, model_sha256, DecodeError, Decoded, ModelRegistry,
};
/// The reason a pinned decode was refused with, or a description of what happened.
fn refusal(r: Result<Decoded, DecodeError>) -> String {
match r {
Err(DecodeError::PriorMismatch(why)) => why.code().to_string(),
Err(e) => format!("other error: {e}"),
Ok(_) => "decoded".into(),
}
}
fn repo_root() -> PathBuf {
Path::new(env!("CARGO_MANIFEST_DIR")).join("..").canonicalize().unwrap()
}
fn model_path(name: &str) -> PathBuf {
repo_root().join(format!("wai-web/demo/models/{name}/decoder.onnx"))
}
fn sample_path(name: &str) -> PathBuf {
repo_root().join(format!("wai-web/demo/samples/{name}"))
}
fn load_envelope(name: &str) -> Wai {
let bytes = std::fs::read(sample_path(name))
.unwrap_or_else(|e| panic!("read {name}: {e}"));
Wai::from_bytes(&bytes).unwrap_or_else(|e| panic!("parse {name}: {e}"))
}
fn registry() -> ModelRegistry {
ModelRegistry::new()
.register("wai.neural.encodec32", model_path("encodec_32khz"))
.register("wai.neural.dac", model_path("dac_44khz"))
.register("wai.neural.mimi", model_path("mimi"))
.register("wai.neural.wavtokenizer", model_path("wavtokenizer"))
.register("wai.neural.bmshj2018", model_path("bmshj2018"))
.register("wai.neural.video_bmshj2018", model_path("bmshj2018")) // shares the image decoder
}
fn assert_audio_sane(cap: &str, sample_file: &str, expected_sr: u32, min_samples: usize) {
let onnx = model_path(match cap {
"wai.neural.encodec32" => "encodec_32khz",
"wai.neural.dac" => "dac_44khz",
"wai.neural.mimi" => "mimi",
"wai.neural.wavtokenizer" => "wavtokenizer",
_ => unreachable!(),
});
if !onnx.exists() {
eprintln!("skipping {cap}: {} not built (see tools/wai_<name>_export_onnx.py)",
onnx.display());
return;
}
let env = load_envelope(sample_file);
assert_eq!(env.manifest.model_requirement.capability, cap,
"{sample_file} declares wrong capability");
let dec = decode_envelope(&env, &registry())
.unwrap_or_else(|e| panic!("decode {sample_file}: {e}"));
match dec {
Decoded::Audio(audio) => {
assert_eq!(audio.sample_rate, expected_sr,
"{cap}: wrong sample rate");
assert!(audio.samples.len() >= min_samples,
"{cap}: only {} samples, expected ≥ {}",
audio.samples.len(), min_samples);
// Non-trivial signal: peak amplitude well above 0.
let peak = audio.samples.iter().fold(0f32, |a, &b| a.max(b.abs()));
assert!(peak > 0.01, "{cap}: peak={peak:.4} (silent decode?)");
// No NaNs.
assert!(audio.samples.iter().all(|s| s.is_finite()),
"{cap}: NaN/Inf in output");
println!(" {cap}: {} samples @ {} Hz, peak {:.3}",
audio.samples.len(), audio.sample_rate, peak);
}
_ => panic!("{cap}: expected Decoded::Audio"),
}
}
#[test] fn encodec32_decodes_natively() {
assert_audio_sane("wai.neural.encodec32", "glass.encodec.wai", 32_000, 16_000);
}
#[test] fn dac_decodes_natively() {
assert_audio_sane("wai.neural.dac", "glass.dac.wai", 44_100, 22_000);
}
#[test] fn mimi_decodes_natively() {
assert_audio_sane("wai.neural.mimi", "glass.mimi.wai", 24_000, 12_000);
}
#[test] fn wavtokenizer_decodes_natively() {
assert_audio_sane("wai.neural.wavtokenizer", "glass.wavtokenizer.wai", 24_000, 12_000);
}
#[test]
fn bmshj2018_decodes_natively() {
let onnx = model_path("bmshj2018");
if !onnx.exists() {
eprintln!("skipping bmshj2018: {} not built", onnx.display());
return;
}
let env = load_envelope("kodim23.bmshj2018.wai");
let dec = decode_envelope(&env, &registry()).expect("bmshj2018 decode");
match dec {
Decoded::Image(img) => {
assert_eq!(img.width, 256);
assert_eq!(img.height, 256);
assert_eq!(img.rgb.len(), 256 * 256 * 3);
// Variance: a real image has lots of pixel variation. A blank
// decode would be near-constant.
let mean = img.rgb.iter().map(|&v| v as f64).sum::<f64>() / img.rgb.len() as f64;
let var = img.rgb.iter()
.map(|&v| (v as f64 - mean).powi(2)).sum::<f64>() / img.rgb.len() as f64;
assert!(var > 100.0, "bmshj2018: variance {var:.0} suspiciously low");
println!(" bmshj2018: 256x256 RGB, mean={mean:.1}, var={var:.0}");
}
_ => panic!("bmshj2018: expected Decoded::Image"),
}
}
/// Determinism is half the `Prior.determinism` contract: a "replicate" claim
/// is only meaningful if the same envelope decodes to the same bytes every
/// time. Decode twice through the pinned single-thread runtime and require
/// bit-identical output.
#[test]
fn bmshj2018_decode_is_deterministic() {
let onnx = model_path("bmshj2018");
if !onnx.exists() {
eprintln!("skipping determinism: {} not built", onnx.display());
return;
}
let env = load_envelope("kodim23.bmshj2018.wai");
let reg = registry();
let rgb = |w: &Wai| match decode_envelope(w, &reg).expect("decode") {
Decoded::Image(i) => i.rgb,
_ => panic!("expected image"),
};
let first = rgb(&env);
let second = rgb(&env);
assert_eq!(first, second, "bmshj2018 decode is not bit-reproducible across runs");
println!(" bmshj2018: byte-identical across two decodes ({} bytes)", first.len());
}
/// The pin is enforced over the whole parameter set. `wai.neural.bmshj2018` reads
/// `decoder.onnx` and `cdfs_q<q>.json`, so it is registered with several files: a
/// form-less pin over the decoder alone is refused (`form_required`) before anything
/// is read, and a pin over the listing of the set (`wai.prior.set`) decodes; a pin
/// over another listing is refused (`prior_not_held`), never a silent wrong image.
#[test]
fn pinned_prior_is_enforced() {
let onnx = model_path("bmshj2018");
if !onnx.exists() {
eprintln!("skipping prior-pin: {} not built", onnx.display());
return;
}
let base = load_envelope("kodim23.bmshj2018.wai");
let pin = |p: Prior| -> Wai {
let mut m = base.manifest.clone();
m.conditioning.prior = Some(p);
Wai::new(m, base.payload.clone())
};
let det = "int-rans/p16+onnx-cpu-f32/1thread";
// Form-less over a several-file capability: refused before anything is read.
let decoder_only = Prior::new("bmshj2018-factorized/q3", model_sha256(&onnx).unwrap(), det);
assert_eq!(refusal(decode_envelope(&pin(decoder_only), &registry())), "form_required");
// The listing of decoder.onnx and every cdfs_q*.json, in a scratch copy of the set.
let dir = std::env::temp_dir().join(format!("wai-bmshj-set-{}", std::process::id()));
std::fs::create_dir_all(&dir).unwrap();
let mut names = vec!["decoder.onnx".to_string()];
for e in std::fs::read_dir(onnx.parent().unwrap()).unwrap().flatten() {
let n = e.file_name().to_string_lossy().into_owned();
if n.starts_with("cdfs_q") && n.ends_with(".json") {
names.push(n);
}
}
for n in &names {
std::fs::copy(onnx.parent().unwrap().join(n), dir.join(n)).unwrap();
}
let listing = wai::pin::write_listing(&dir, &names).unwrap();
std::fs::write(dir.join("set.sha256"), &listing).unwrap();
let reg = ModelRegistry::new().register("wai.neural.bmshj2018", dir.join("decoder.onnx"));
let set_pin = Prior::new("bmshj2018-factorized/q3", wai::pin::sha256_hex(&listing), det)
.with_form(wai::codecs::CAP_PRIOR_SET);
assert!(matches!(decode_envelope(&pin(set_pin.clone()), &reg), Ok(Decoded::Image(_))),
"the set pin over decoder.onnx and its CDF tables decodes");
let mut other = set_pin;
other.sha256 = "00".repeat(32);
assert_eq!(refusal(decode_envelope(&pin(other), &reg)), "prior_not_held");
std::fs::remove_dir_all(&dir).ok();
println!(" pin: form-less refused (form_required), set pin decodes, other set refused");
}
/// The pin check is pure hashing and runs with no ONNX model present, so this
/// exercises SPEC §3.1's verification on every machine. A stand-in file plays the
/// one-file parameter set of `wai.neural.encodec32`; the registry must accept the
/// true digest and an absent pin, and refuse every other pin with its reason.
#[test]
fn resolve_checked_verifies_prior_hash() {
let path = std::env::temp_dir().join(format!("wai_prior_check_model_{}.bin", std::process::id()));
std::fs::write(&path, b"pretend onnx decoder weights v1").unwrap();
let real = model_sha256(&path).expect("hash stand-in model");
const ENCODEC: &str = "wai.neural.encodec32";
let reg = ModelRegistry::new()
.register(ENCODEC, path.clone())
.register("wai.neural.bmshj2018", path.clone());
let code = |cap: &str, p: Option<&Prior>| match reg.resolve_verified(cap, p) {
Ok(_) => "ok".to_string(),
Err(DecodeError::PriorMismatch(r)) => r.code().to_string(),
Err(e) => format!("{e:?}"),
};
// No pin → unverified pass (the honest meaning of an unpinned decode).
assert_eq!(code(ENCODEC, None), "ok");
// The true digest → pass; the verified bytes are the file's.
let good = Prior::new("m/q3", real.clone(), "x");
assert_eq!(code(ENCODEC, Some(&good)), "ok");
// Another digest → refused, loudly.
assert_eq!(code(ENCODEC, Some(&Prior::new("m/q3", "00".repeat(32), "x"))), "prior_not_held");
// The true digest uppercased is not 64 lowercase hex: malformed, not compared.
assert_eq!(code(ENCODEC, Some(&Prior::new("m/q3", real.to_ascii_uppercase(), "x"))), "pin_malformed");
// A form this sink cannot read → refused as unreadable, not as a mismatch.
match reg.resolve_verified(ENCODEC, Some(&good.clone().with_form(wai::codecs::CAP_PRIOR_NNC))) {
Err(DecodeError::PriorMismatch(why)) => {
assert_eq!(why.code(), "form_unreadable");
assert!(why.to_string().contains("wai.prior.nnc") && why.to_string().contains("cannot be read by this sink"), "{why}");
}
other => panic!("an unreadable declared form must be refused, got {other:?}"),
}
// A declared form that is not a registered prior form.
match reg.resolve_verified(ENCODEC, Some(&good.clone().with_form("wai.image.png"))) {
Err(DecodeError::PriorMismatch(why)) => {
assert_eq!(why.code(), "form_not_registered");
assert!(why.to_string().contains("is not a registered prior form"), "{why}");
}
other => panic!("a non-form declared as a form must be refused, got {other:?}"),
}
// The same stand-in under a several-file capability: form-less is refused.
assert_eq!(code("wai.neural.bmshj2018", Some(&good)), "form_required");
// Unknown capability → unregistered, regardless of pin.
assert!(matches!(reg.resolve_verified("wai.neural.nope", None), Err(DecodeError::ModelNotRegistered(_))));
let _ = std::fs::remove_file(&path);
println!(" resolve_verified: none=ok, true=ok, wrong/upper/forms/several-files refused with their reasons");
}
#[test]
fn video_bmshj2018_decodes_natively() {
let onnx = model_path("bmshj2018");
if !onnx.exists() {
eprintln!("skipping video_bmshj2018: {} not built", onnx.display());
return;
}
let env = load_envelope("test.video.wai");
let dec = decode_envelope(&env, &registry()).expect("video decode");
match dec {
Decoded::Video(v) => {
assert!(v.frames_rgb.len() > 0, "no frames decoded");
assert_eq!(v.width, 256);
assert_eq!(v.height, 256);
assert!((v.fps - 12.0).abs() < 0.01, "fps {} != 12", v.fps);
// First frame should have non-trivial variance.
let f0 = &v.frames_rgb[0];
let mean = f0.iter().map(|&v| v as f64).sum::<f64>() / f0.len() as f64;
let var = f0.iter().map(|&v| (v as f64 - mean).powi(2)).sum::<f64>() / f0.len() as f64;
assert!(var > 100.0, "video frame 0 variance {var:.0} suspiciously low");
println!(" video_bmshj2018: {} frames {}x{} @ {} fps",
v.frames_rgb.len(), v.width, v.height, v.fps);
}
_ => panic!("video_bmshj2018: expected Decoded::Video"),
}
}
/// The replicate-soundness gate runs BEFORE any model is touched, so this is
/// model-independent. `replicate` promises decode-equivalence (SPEC §7), so the
/// capability's registry class decides first: only an integer-exact capability
/// can back it, and then only with a pinned integer-exact prior. A prior that
/// *declares* an integer contract over a float codec or over JPEG AI (integer
/// entropy decode, float later stages) is refused. Non-`replicate` intents are
/// unconstrained.
#[test]
fn strict_decode_gates_unsound_replicate() {
fn env(cap: &str, prior: Option<Prior>, intent: &str) -> Wai {
let mut conditioning = Conditioning::new("k");
conditioning.prior = prior;
let manifest = Manifest::new("image", intent, ModelRequirement::new(cap), conditioning)
.with_target(serde_json::json!({"w": 256, "h": 256}));
Wai::new(manifest, vec![])
}
let p = |det: &str| Prior::new("m", "ab".repeat(32), det);
// An integer-exact network read out of a form not established exact: refused
// before any model is touched, and the reason names the form. The envelope is
// built here, over an integer-exact capability, so neither the capability nor
// the contract can be what refuses it; the same prior without a form passes.
{
let over_int_synth = |prior: Prior| {
Wai::new(
Manifest::new("image", "replicate", ModelRequirement::new("wai.neural.int_synth"),
Conditioning::new("int_synth").with_prior(prior))
.with_target(serde_json::json!({"w": 256, "h": 256})),
vec![],
)
};
let exact = p("int-rans/p16+onnx-int8-integerized");
let nnc = exact.clone().with_form(wai::codecs::CAP_PRIOR_NNC);
let reg = ModelRegistry::new();
assert!(matches!(
decode_envelope_strict(&over_int_synth(exact), &reg),
Err(DecodeError::ModelNotRegistered(_))
));
match decode_envelope_strict(&over_int_synth(nnc), &reg) {
Err(DecodeError::UnsoundReplicate(why)) => {
assert!(why.contains("wai.prior.nnc"), "the refusal must name the form: {why}");
assert!(!why.contains("not integer-exact"), "the contract is integer-exact: {why}");
}
Err(e) => panic!("expected UnsoundReplicate, got {e:?}"),
Ok(_) => panic!("expected UnsoundReplicate, got a decode"),
}
}
let integer = p("int-rans/p16+onnx-int8-integerized");
let floaty = p("int-rans/p16+onnx-cpu-f32/1thread");
const FLOAT_CODEC: &str = "wai.neural.bmshj2018";
const INT_CODEC: &str = "wai.neural.int_synth";
const JPEGAI: &str = "wai.image.jpegai";
let reg = ModelRegistry::new(); // empty: the gate fires before model resolution
// replicate over a float codec → rejected, whatever the prior declares.
for prior in [Some(floaty.clone()), Some(integer.clone()), None] {
assert!(matches!(
decode_envelope_strict(&env(FLOAT_CODEC, prior, "replicate"), &reg),
Err(DecodeError::UnsoundReplicate(_))
));
}
// replicate over JPEG AI → rejected even with an integer-declared prior: its
// registry class is entropy-consistency only.
match decode_envelope_strict(&env(JPEGAI, Some(integer.clone()), "replicate"), &reg) {
Err(DecodeError::UnsoundReplicate(why)) => assert!(why.contains("entropy-consistency"), "{why}"),
other => panic!("jpegai replicate must be refused, got {:?}", other.map(|_| ())),
}
// replicate over the integer-exact codec: float or absent prior → rejected …
for prior in [Some(floaty.clone()), None] {
assert!(matches!(
decode_envelope_strict(&env(INT_CODEC, prior, "replicate"), &reg),
Err(DecodeError::UnsoundReplicate(_))
));
}
// … integer-exact prior → gate PASSES, falls through to model resolution
// (ModelNotRegistered proves the gate let it past).
assert!(matches!(
decode_envelope_strict(&env(INT_CODEC, Some(integer.clone()), "replicate"), &reg),
Err(DecodeError::ModelNotRegistered(_))
));
// Non-replicate intents aren't constrained by the gate.
for cap in [FLOAT_CODEC, JPEGAI] {
assert!(matches!(
decode_envelope_strict(&env(cap, Some(floaty.clone()), "improve"), &reg),
Err(DecodeError::ModelNotRegistered(_))
));
}
// An unregistered capability is reported as such.
assert!(matches!(
decode_envelope_strict(&env("wai.image.nope", Some(integer), "replicate"), &reg),
Err(DecodeError::UnknownCapability(_))
));
println!(" strict gate: class first (float, entropy-only refused), then prior; non-replicate passes");
}
/// `wai.neural.int_mlicpp` through the neural dispatch and the strict `replicate`
/// gate, on the committed conformance vector (`tests/vectors/int_mlicpp/`, no model
/// to fetch, so this never skips). The registered model is the one-file bundle the
/// envelope's prior pins: the decode must reproduce the pinned image, a bundle that
/// differs by one byte must be refused before anything is decoded, and `replicate`
/// with the prior removed must be refused by the gate. The vector's weights are
/// synthetic, so this checks the dispatch and the pin, not compression quality.
#[test]
fn int_mlicpp_decodes_through_the_strict_dispatch() {
let d = Path::new(env!("CARGO_MANIFEST_DIR")).join("tests/vectors/int_mlicpp");
let bundle = d.join("model.wmb");
let env = Wai::from_bytes(&std::fs::read(d.join("stream.wai")).unwrap()).unwrap();
let expected: serde_json::Value = serde_json::from_slice(&std::fs::read(d.join("expected.json")).unwrap()).unwrap();
let reg = ModelRegistry::new().register("wai.neural.int_mlicpp", &bundle);
assert_eq!(model_sha256(&bundle).unwrap(), env.prior().expect("pinned prior").sha256);
match decode_envelope_strict(&env, &reg) {
Ok(Decoded::Image(img)) => {
assert_eq!((img.width, img.height), (64, 64));
assert_eq!(format!("{:016x}", wai::int_hyper_synth::fnv1a(&img.rgb)),
expected["rgb_fnv1a"].as_str().unwrap(), "the pinned image");
}
Ok(_) => panic!("int_mlicpp must decode to an image"),
Err(e) => panic!("int_mlicpp strict decode failed: {e}"),
}
let tampered = std::env::temp_dir().join(format!("wai-int-mlicpp-{}.wmb", std::process::id()));
let mut bytes = std::fs::read(&bundle).unwrap();
let at = bytes.len() - 2;
bytes[at] ^= 1;
std::fs::write(&tampered, &bytes).unwrap();
let refused = decode_envelope_strict(&env, &ModelRegistry::new().register("wai.neural.int_mlicpp", &tampered));
std::fs::remove_file(&tampered).ok();
assert!(matches!(refused, Err(DecodeError::PriorMismatch(_))), "a one-byte-different bundle must be refused");
let mut manifest = env.manifest.clone();
manifest.conditioning.prior = None;
let unpinned = Wai::new(manifest, env.payload.clone());
assert!(matches!(decode_envelope_strict(&unpinned, &reg), Err(DecodeError::UnsoundReplicate(_))),
"replicate without a pinned prior must be refused");
println!(" int_mlicpp: strict dispatch decodes the pinned image; tampered bundle and unpinned replicate refused");
}
fn int_mlicpp_dir() -> PathBuf {
Path::new(env!("CARGO_MANIFEST_DIR")).join("tests/vectors/int_mlicpp")
}
fn image_fnv(r: Result<Decoded, DecodeError>) -> String {
match r {
Ok(Decoded::Image(img)) => format!("{:016x}", wai::int_hyper_synth::fnv1a(&img.rgb)),
Ok(_) => "not an image".into(),
Err(e) => format!("error: {e}"),
}
}
/// `stream_set.wai` pins the same bundle through its listing (`wai.prior.set`,
/// `decode-equivalence`). With `model.wmb` registered, the registry finds the
/// listing beside it, verifies it and the bundle, and the strict dispatch decodes the
/// pinned image from the verified bytes.
#[test]
fn int_mlicpp_set_pin_through_the_strict_dispatch() {
let d = int_mlicpp_dir();
let env = Wai::from_bytes(&std::fs::read(d.join("stream_set.wai")).unwrap()).unwrap();
let reg = ModelRegistry::new().register("wai.neural.int_mlicpp", d.join("model.wmb"));
assert_eq!(image_fnv(decode_envelope_strict(&env, &reg)), "7c0b9a4b3423d775");
}
/// SPEC §3.1 check 5 at the neural sink: a registry given a key log that holds
/// `wai.neural.int_mlicpp`'s pinned sets to jwp-receipts §7.9 refuses the committed set
/// once a key log revocation names its digest (`prior_revoked`), refuses it offline
/// (`prior_not_authorised`), and decodes it while a current grant holds it. A key log
/// that does not hold the capability to §7.9 still refuses the revoked set. The same
/// envelope with its pin removed decodes the registered set unpinned, and check 5 runs
/// over that set too (SPEC §4, *Module authorisation*).
#[cfg(feature = "key_discovery")]
#[test]
fn int_mlicpp_revoked_set_is_refused_through_the_key_log() {
use ed25519_dalek::SigningKey;
use wai::key_log::{commitment, Anchor, KeyEntry, KeyStatus, ModuleForm, ModuleGrant, Revision, SinkKeyLog};
const P: &str = "https://publisher.example";
const MLIC: &str = "wai.neural.int_mlicpp";
let key = |s: u8| SigningKey::from_bytes(&[s; 32]);
let d = int_mlicpp_dir();
let env = Wai::from_bytes(&std::fs::read(d.join("stream_set.wai")).unwrap()).unwrap();
let digest = wai::pin::sha256(&std::fs::read(d.join("model.sha256")).unwrap());
let sink_held = |revoked: Vec<[u8; 32]>, statuses: bool, held_to: bool| {
let unsigned = Revision {
origin: P.into(),
seq: 0,
prev: None,
issued_at: "2026-09-01T00:00:00Z".into(),
root: [0; 32],
next_root: commitment(&key(0x62).verifying_key().to_bytes()),
keys: vec![KeyEntry::active("modd", key(0x6b).verifying_key().to_bytes(), &["module/decoder"])],
revoked_modules: vec![],
grant_max_s: 3_600,
status_max_age_s: 600,
sig: [0; 64],
};
let r0 = Revision::seal(&key(0x61), unsigned.clone()).unwrap();
let r1 = Revision::seal(
&key(0x61),
Revision { seq: 1, prev: Some(r0.revision_hash()), issued_at: "2026-09-10T00:00:00Z".into(), revoked_modules: revoked, ..unsigned },
)
.unwrap();
let grant = ModuleGrant::seal(&key(0x6b), "did:web:publisher.example#modd", P, digest, ModuleForm::Decoder, &[MLIC],
"2026-09-20T05:30:00Z", "2026-09-20T06:30:00Z").unwrap().to_json();
let st = if statuses { vec![KeyStatus::seal(&key(0x61), &r1, "2026-09-20T05:55:00Z").to_json()] } else { vec![] };
let k = SinkKeyLog::new(vec![r0.clone(), r1], vec![Anchor::pinned(P, r0.revision_hash())])
.with_statuses(st)
.with_grants(vec![grant])
.at("2026-09-20T06:00:00Z");
if held_to { k.hold_pinned_sets(MLIC, &[P]) } else { k }
};
let sink = |revoked: Vec<[u8; 32]>, statuses: bool| sink_held(revoked, statuses, true);
let reg = |k: SinkKeyLog| ModelRegistry::new().register(MLIC, d.join("model.wmb")).with_key_log(k);
assert_eq!(refusal(decode_envelope(&env, &reg(sink(vec![digest], true)))), "prior_revoked");
assert_eq!(refusal(decode_envelope(&env, &reg(sink(vec![], false)))), "prior_not_authorised");
assert_eq!(image_fnv(decode_envelope_strict(&env, &reg(sink(vec![], true)))), "7c0b9a4b3423d775");
assert_eq!(refusal(decode_envelope(&env, &reg(sink_held(vec![digest], true, false)))), "prior_revoked");
assert_eq!(image_fnv(decode_envelope(&env, &reg(sink_held(vec![], false, false)))), "7c0b9a4b3423d775");
let mut manifest = env.manifest.clone();
manifest.conditioning.prior = None;
let unpinned = Wai::new(manifest, env.payload.clone());
let plain = ModelRegistry::new().register(MLIC, d.join("model.wmb"));
assert_eq!(image_fnv(decode_envelope(&unpinned, &plain)), "7c0b9a4b3423d775", "no key log: unpinned decodes");
assert_eq!(refusal(decode_envelope(&unpinned, &reg(sink(vec![digest], true)))), "prior_revoked");
assert_eq!(refusal(decode_envelope(&unpinned, &reg(sink_held(vec![digest], true, false)))), "prior_revoked");
assert_eq!(refusal(decode_envelope(&unpinned, &reg(sink(vec![], false)))), "prior_not_authorised");
assert_eq!(image_fnv(decode_envelope(&unpinned, &reg(sink(vec![], true)))), "7c0b9a4b3423d775");
assert_eq!(image_fnv(decode_envelope(&unpinned, &reg(sink_held(vec![], false, false)))), "7c0b9a4b3423d775");
// The bundle's own digest, which a form-less pin names, is checked too.
let bundle = wai::pin::sha256(&std::fs::read(d.join("model.wmb")).unwrap());
assert_eq!(refusal(decode_envelope(&unpinned, &reg(sink_held(vec![bundle], true, false)))), "prior_revoked");
let refused = reg(sink(vec![digest], true)).resolve_verified(MLIC, None);
assert!(matches!(refused, Err(DecodeError::PriorMismatch(ref r)) if r.code() == "prior_revoked"), "resolve_verified checks an unpinned set too");
}
/// The int_synth decode reads `int_synth.json` beside the registered path, so that
/// one file is its parameter set and what a form-less pin covers (SPEC §5). The
/// gradient corpus vector, pinned by the digest of its spec, decodes to the corpus
/// hash; a pin over another spec is refused.
#[test]
fn int_synth_pin_covers_the_spec_it_reads() {
let src = Path::new(env!("CARGO_MANIFEST_DIR")).join("../neural-conformance/vectors/gradient");
let spec = std::fs::read(src.join("int_synth.json")).unwrap();
let digest = wai::pin::sha256_hex(&spec);
assert_eq!(digest, "1c4705d17c01f865b20d785191c7f63b5c18dcc8fce77e15852cf8240b7368be");
let latent = std::fs::read(src.join("latent.bin")).unwrap();
let env = |sha: &str| Wai::new(
Manifest::new("image", "replicate", ModelRequirement::new("wai.neural.int_synth"),
Conditioning::new("int_synth").with_prior(Prior::new("gradient", sha, "int-synth/i64"))),
latent.clone());
// The registered path is the `model` stub the corpus convention uses.
let reg = ModelRegistry::new().register("wai.neural.int_synth", src.join("model"));
match decode_envelope_strict(&env(&digest), &reg) {
Ok(Decoded::Image(img)) => {
let mut h = blake3::Hasher::new();
h.update(b"wai:int-synth-rgb\x01");
h.update(&img.rgb);
assert_eq!(h.finalize().to_hex().as_str(),
"1282839b699ad3e79fc810a92ef4220fec7a57a573bb6c844709af4c1fb3f638");
}
other => panic!("the spec pin must decode, got {}", image_fnv(other)),
}
assert_eq!(refusal(decode_envelope(&env(&"ab".repeat(32)), &reg)), "prior_not_held");
}
/// A key log stand-in that revokes the digests it holds.
#[derive(Debug)]
struct Revokes(Vec<String>);
impl wai::pin::PinAuthority for Revokes {
fn check(&self, cap: &str, prior: &Prior) -> Result<(), wai::container::PinRefusal> {
self.check_unpinned(cap, std::slice::from_ref(&prior.sha256))
}
fn check_unpinned(&self, cap: &str, digests: &[String]) -> Result<(), wai::container::PinRefusal> {
if digests.iter().any(|d| self.0.contains(d)) {
return Err(wai::container::PinRefusal::Revoked { capability: cap.into(), revoked_by: None });
}
Ok(())
}
}
/// `wai.neural.int_synth` registered as a model directory, or as the `int_synth.json`
/// inside it: the decode reads that one file, a form-less pin covers it, and check 5
/// runs over it, so a key log that revokes the spec refuses the unpinned decode either
/// way (`prior_revoked`). Without the key log both registrations decode to the corpus
/// hash. The unpinned decode reads the bytes check 5 ran over: the spec replaced on
/// disk after the registry read it does not change the image.
#[test]
fn int_synth_check_5_covers_the_spec_a_model_directory_holds() {
let cap = "wai.neural.int_synth";
let src = Path::new(env!("CARGO_MANIFEST_DIR")).join("../neural-conformance/vectors/gradient");
let spec = std::fs::read(src.join("int_synth.json")).unwrap();
let latent = std::fs::read(src.join("latent.bin")).unwrap();
let digest = wai::pin::sha256_hex(&spec);
let dir = std::env::temp_dir().join(format!("wai-int-synth-dir-{}", std::process::id()));
std::fs::create_dir_all(&dir).unwrap();
std::fs::write(dir.join("int_synth.json"), &spec).unwrap();
let env = |prior: Option<Prior>| {
let mut cond = Conditioning::new("int_synth");
if let Some(p) = prior {
cond = cond.with_prior(p);
}
Wai::new(Manifest::new("image", "improve", ModelRequirement::new(cap), cond), latent.clone())
};
let rgb_hash = |r: Result<Decoded, DecodeError>| match r {
Ok(Decoded::Image(img)) => {
let mut h = blake3::Hasher::new();
h.update(b"wai:int-synth-rgb\x01");
h.update(&img.rgb);
h.finalize().to_hex().to_string()
}
other => refusal(other),
};
let want = "1282839b699ad3e79fc810a92ef4220fec7a57a573bb6c844709af4c1fb3f638";
for path in [dir.clone(), dir.join("int_synth.json")] {
let revoking = ModelRegistry::new().register(cap, path.clone()).with_key_log(Revokes(vec![digest.clone()]));
assert_eq!(refusal(decode_envelope(&env(None), &revoking)), "prior_revoked", "{}", path.display());
let plain = ModelRegistry::new().register(cap, path.clone());
assert_eq!(rgb_hash(decode_envelope(&env(None), &plain)), want, "{}", path.display());
let pin = Prior::new("gradient", digest.clone(), "int-synth/i64");
assert_eq!(rgb_hash(decode_envelope(&env(Some(pin)), &plain)), want, "{}: a form-less pin", path.display());
}
let reg = ModelRegistry::new().register(cap, dir.clone()).with_key_log(Revokes(vec![]));
let params = reg.resolve_verified(cap, None).expect("the unrevoked spec resolves");
std::fs::copy(src.join("../bloom/int_synth.json"), dir.join("int_synth.json")).unwrap();
assert_eq!(rgb_hash(wai::neural::decode_payload(cap, &latent, &params)), want, "the decode read what check 5 ran over");
std::fs::remove_dir_all(&dir).ok();
}
/// For every several-file capability the reference sink dispatches, a form-less pin
/// is refused with `form_required` before any file is read — even when its digest is
/// the stand-in's own, and even for a capability registered as a directory.
#[test]
fn several_file_capabilities_need_the_set_form() {
let stand_in = std::env::temp_dir().join(format!("wai-several-{}.bin", std::process::id()));
std::fs::write(&stand_in, b"stand-in").unwrap();
let digest = model_sha256(&stand_in).unwrap();
let mut n = 0;
for &cap in wai::codecs::known_capabilities() {
if wai::codecs::parameter_set_shape(cap) != Some(wai::codecs::ParameterSetShape::SeveralFiles) {
continue;
}
let path = if cap == "wai.image.jpegai" { std::env::temp_dir() } else { stand_in.clone() };
let reg = ModelRegistry::new().register(cap, path);
let env = Wai::new(
Manifest::new("image", "improve", ModelRequirement::new(cap),
Conditioning::new("k").with_prior(Prior::new("m", digest.clone(), "x"))),
vec![]);
assert_eq!(refusal(decode_envelope(&env, &reg)), "form_required", "{cap}");
n += 1;
}
assert!(n > 0);
std::fs::remove_file(&stand_in).ok();
}
/// A pinned decode reads its parameters only from the bytes it verified: the spec
/// file is overwritten after verification, and the decode still gives the image of
/// the verified spec.
#[test]
fn pinned_decode_reads_only_verified_bytes() {
let src = Path::new(env!("CARGO_MANIFEST_DIR")).join("../neural-conformance/vectors/gradient");
let dir = std::env::temp_dir().join(format!("wai-verified-bytes-{}", std::process::id()));
std::fs::create_dir_all(&dir).unwrap();
std::fs::copy(src.join("int_synth.json"), dir.join("int_synth.json")).unwrap();
let spec = std::fs::read(dir.join("int_synth.json")).unwrap();
let latent = std::fs::read(src.join("latent.bin")).unwrap();
let reg = ModelRegistry::new().register("wai.neural.int_synth", dir.join("model"));
let pin = Prior::new("gradient", wai::pin::sha256_hex(&spec), "int-synth/i64");
let params = reg.resolve_verified("wai.neural.int_synth", Some(&pin)).expect("verified");
let before = wai::neural::decode_payload("wai.neural.int_synth", &latent, &params);
// Replace the spec on disk with another one (the bloom vector's).
std::fs::copy(src.join("../bloom/int_synth.json"), dir.join("int_synth.json")).unwrap();
let after = wai::neural::decode_payload("wai.neural.int_synth", &latent, &params);
assert_eq!(image_fnv(before), image_fnv(after), "the decode read the bytes it verified");
// An unpinned decode reads the file as it is now, and so differs (or fails).
let unpinned = wai::neural::decode_payload("wai.neural.int_synth", &latent,
&reg.resolve_verified("wai.neural.int_synth", None).unwrap());
assert_ne!(image_fnv(unpinned), image_fnv(wai::neural::decode_payload("wai.neural.int_synth", &latent, &params)));
std::fs::remove_dir_all(&dir).ok();
}
/// SPEC §7: the replicate rule reads the capability the envelope decodes through.
/// The primary, `wai.image.jpegai`, cannot back `replicate`; the fallback,
/// `wai.neural.int_mlicpp`, can, and the pin is the committed bundle's. With only
/// the fallback held, and with both held (the primary's form-less pin is then
/// refused, `form_required`), the strict decode goes through the fallback and gives
/// the pinned image. With only the primary held it is refused before any file is read.
#[test]
fn strict_gate_reads_the_capability_it_decodes_through() {
let d = int_mlicpp_dir();
let committed = Wai::from_bytes(&std::fs::read(d.join("stream.wai")).unwrap()).unwrap();
let mut manifest = committed.manifest.clone();
manifest.model_requirement = ModelRequirement::new("wai.image.jpegai").with_fallback("wai.neural.int_mlicpp");
let env = Wai::new(manifest, committed.payload.clone());
assert_eq!(env.intent(), "replicate");
let only_fallback = ModelRegistry::new().register("wai.neural.int_mlicpp", d.join("model.wmb"));
assert_eq!(image_fnv(decode_envelope_strict(&env, &only_fallback)), "7c0b9a4b3423d775");
let both = ModelRegistry::new()
.register("wai.image.jpegai", std::env::temp_dir())
.register("wai.neural.int_mlicpp", d.join("model.wmb"));
assert_eq!(image_fnv(decode_envelope_strict(&env, &both)), "7c0b9a4b3423d775");
let only_primary = ModelRegistry::new().register("wai.image.jpegai", std::env::temp_dir());
assert!(matches!(decode_envelope_strict(&env, &only_primary), Err(DecodeError::UnsoundReplicate(_))));
}
/// SPEC §4 steps 3 and 5 take only a dispatchable capability, so a string the
/// sink's registry happens to hold but no dispatch could take (a record, a
/// candidate) is not one the strict decode could go through: the strict path's
/// early refusal does not read it, and the envelope gets the reason it gets from a
/// registry that holds nothing (step 6's missing model), the same reason the
/// non-strict path gives. A record has no replicate class, so a gate that read it
/// would refuse the envelope as naming an unknown capability.
#[test]
fn strict_gate_ignores_a_held_capability_it_cannot_dispatch() {
use wai::codecs::{capability_kind, is_candidate, registry::CAP_VIDEO_MANIFEST, Kind, CAP_TENSOR_NNC};
let d = int_mlicpp_dir();
let committed = Wai::from_bytes(&std::fs::read(d.join("stream.wai")).unwrap()).unwrap();
assert_eq!(capability_kind(CAP_VIDEO_MANIFEST), Some(Kind::Record));
assert!(is_candidate(CAP_TENSOR_NNC));
for held in [CAP_VIDEO_MANIFEST, CAP_TENSOR_NNC] {
let mut manifest = committed.manifest.clone();
manifest.model_requirement = ModelRequirement::new("wai.neural.int_mlicpp").with_fallback(held);
let env = Wai::new(manifest, committed.payload.clone());
assert_eq!(env.intent(), "replicate");
let holds = ModelRegistry::new().register(held, std::env::temp_dir());
for (path, got) in [
("strict, held", decode_envelope_strict(&env, &holds)),
("strict, empty registry", decode_envelope_strict(&env, &ModelRegistry::new())),
("non-strict, held", decode_envelope(&env, &holds)),
] {
assert!(matches!(got, Err(DecodeError::ModelNotRegistered(_))),
"{held}, {path}: expected ModelNotRegistered, got {:?}", got.map(|_| ()));
}
}
}
/// SPEC §4 step 6: when the capability's pinned decode is refused with
/// `set_incomplete` (step 3) and the fallback's pin is then refused (step 5), the
/// error is step 3's reason. The pin is a `wai.prior.set` listing whose one file is
/// not the `int_synth.json` the int_synth decode reads; the fallback holds another set.
#[test]
fn set_incomplete_at_step_3_outranks_the_fallback_refusal() {
let dir = std::env::temp_dir().join(format!("wai-step6-{}", std::process::id()));
std::fs::create_dir_all(&dir).unwrap();
std::fs::write(dir.join("other.bin"), b"not the spec").unwrap();
let listing = format!("{} other.bin\n", wai::pin::sha256_hex(b"not the spec"));
std::fs::write(dir.join("set.sha256"), &listing).unwrap();
let pin = Prior::new("set", wai::pin::sha256_hex(listing.as_bytes()), "int-synth/i64")
.with_form(wai::codecs::CAP_PRIOR_SET);
let latent = std::fs::read(Path::new(env!("CARGO_MANIFEST_DIR"))
.join("../neural-conformance/vectors/gradient/latent.bin")).unwrap();
let env = Wai::new(
Manifest::new("image", "improve",
ModelRequirement::new("wai.neural.int_synth").with_fallback("wai.neural.int_mlicpp"),
Conditioning::new("int_synth").with_prior(pin)),
latent);
let reg = ModelRegistry::new()
.register("wai.neural.int_synth", dir.join("model"))
.register("wai.neural.int_mlicpp", int_mlicpp_dir().join("model.wmb"));
let got = refusal(decode_envelope(&env, &reg));
std::fs::remove_dir_all(&dir).ok();
assert_eq!(got, "set_incomplete");
}
/// SPEC §7.1 step 5 under the strict policy: an entry the replicate rule leaves out
/// is reported with its `replicate_*` reason, not as a capability the sink lacks.
#[test]
fn decode_multi_strict_reports_replicate_reasons() {
use wai::container::{Rendition, WaiMulti};
use wai::neural::decode_multi_strict;
let d = int_mlicpp_dir();
let pl = Wai::from_bytes(&std::fs::read(d.join("stream.wai")).unwrap()).unwrap().payload;
let m = WaiMulti::new("image", "replicate", serde_json::Value::Null, vec![
Rendition::media("wai.image.jpegai", "jpegai", vec![0; 4]),
Rendition::media("wai.neural.int_mlicpp", "int_mlicpp", pl)
.with_prior(Prior::new("next", "5c".repeat(32), "int-rans/p16+int-mlicpp/i64")),
]);
let reg = ModelRegistry::new()
.register("wai.image.jpegai", std::env::temp_dir())
.register("wai.neural.int_mlicpp", d.join("model.wmb"));
match decode_multi_strict(&m, &reg) {
Err(DecodeError::NoRendition(r)) => {
let codes: Vec<(usize, &str)> = r.iter().map(|(i, why)| (*i, why.split(':').next().unwrap())).collect();
assert_eq!(codes, [(0, "replicate_class"), (1, "prior_not_held")], "{r:?}");
}
other => panic!("expected NoRendition, got {:?}", other.map(|(i, _)| i)),
}
}
/// SPEC §7.1 through the neural sink: a `WAI2` envelope carrying the committed
/// int_mlicpp payload twice, pinned to a successor set (which names the committed
/// bundle in `supersedes`) and to the committed bundle. `decode_multi_strict` skips
/// the first, picks the second and decodes the pinned image; without the bundle the
/// envelope is inert, with a reason per entry.
#[test]
fn wai2_decode_multi_picks_the_verified_rendition() {
use wai::codecs::DeclaredTier;
use wai::container::{Rendition, Supersedes, WaiMulti};
use wai::neural::{decode_multi, decode_multi_strict};
let d = int_mlicpp_dir();
let pl = Wai::from_bytes(&std::fs::read(d.join("stream.wai")).unwrap()).unwrap().payload;
let committed = model_sha256(&d.join("model.wmb")).unwrap();
let det = "int-rans/p16+int-mlicpp/i64";
let m = WaiMulti::new("image", "replicate", serde_json::Value::Null, vec![
Rendition::media("wai.neural.int_mlicpp", "int_mlicpp", pl.clone())
.with_prior(Prior::new("next", "5c".repeat(32), det).with_tier(DeclaredTier::DecodeEquivalence)
.with_supersedes(Supersedes::new(committed.clone()))),
Rendition::media("wai.neural.int_mlicpp", "int_mlicpp", pl)
.with_prior(Prior::new("committed", committed, det).with_tier(DeclaredTier::DecodeEquivalence)),
]);
let reg = ModelRegistry::new().register("wai.neural.int_mlicpp", d.join("model.wmb"));
match decode_multi_strict(&m, &reg) {
Ok((i, d)) => {
assert_eq!(i, 1);
assert_eq!(image_fnv(Ok(d)), "7c0b9a4b3423d775");
}
Err(e) => panic!("decode_multi_strict: {e}"),
}
match decode_multi(&m, &ModelRegistry::new()) {
Err(DecodeError::NoRendition(r)) => assert_eq!(r.len(), 2),
other => panic!("expected NoRendition, got {:?}", other.map(|(i, _)| i)),
}
let tampered = std::env::temp_dir().join(format!("wai-multi-{}.wmb", std::process::id()));
let mut b = std::fs::read(d.join("model.wmb")).unwrap();
b[10] ^= 1;
std::fs::write(&tampered, &b).unwrap();
match decode_multi(&m, &ModelRegistry::new().register("wai.neural.int_mlicpp", &tampered)) {
Err(DecodeError::NoRendition(r)) => {
assert!(r[0].1.starts_with("prior_not_held") && r[1].1.starts_with("prior_not_held"), "{r:?}");
}
other => panic!("expected NoRendition, got {:?}", other.map(|(i, _)| i)),
}
std::fs::remove_file(&tampered).ok();
}
/// END-TO-END validation against the real CompressAI mbt2018-mean model:
/// decode the SAME envelope in Rust and compare to CompressAI's own decode.
/// The Gaussian-conditional entropy decode must be EXACT (same rANS bytes →
/// same latents); only `g_s` (ONNX vs torch float) may differ by a hair. A
/// large divergence means the entropy decode is wrong. Artifacts produced by
/// the export/encode tools + a CompressAI reference decode; skipped if absent.
#[test]
fn mbt2018_mean_matches_compressai_reference() {
let wai = Path::new("/tmp/test.mbt.wai");
let ref_rgb = Path::new("/tmp/ref.rgb");
let model_dir = Path::new("/tmp/wai_mbt");
if !wai.exists() || !ref_rgb.exists() || !model_dir.join("hyper_synthesis.onnx").exists() {
eprintln!("skipping mbt reference match: /tmp artifacts not present");
return;
}
let env = Wai::read(wai).unwrap();
let reg = ModelRegistry::new().register("wai.neural.mbt2018_mean", model_dir.join("model"));
let img = match decode_envelope(&env, &reg).expect("rust decode") {
Decoded::Image(i) => i,
_ => panic!("expected image"),
};
assert_eq!((img.width, img.height), (256, 256));
let reference = std::fs::read(ref_rgb).unwrap();
assert_eq!(img.rgb.len(), reference.len());
let diffs = || img.rgb.iter().zip(&reference).map(|(a, b)| (*a as i32 - *b as i32).abs());
let maxd = diffs().max().unwrap();
let meand = diffs().map(|d| d as f64).sum::<f64>() / reference.len() as f64;
println!(" mbt2018_mean vs CompressAI: max|Δ|={maxd} mean|Δ|={meand:.3}");
assert!(maxd <= 4, "Rust decode diverges from CompressAI (max {maxd}) — entropy decode wrong");
}
/// END-TO-END validation of the EXISTING factorized `image.rs` decoder against
/// the real CompressAI bmshj2018-factorized. Factorized = static CDFs (no
/// scale-from-network), so it shouldn't have the hyperprior's bucket-flip
/// hazard. Skipped without /tmp artifacts.
#[test]
fn bmshj2018_matches_compressai_reference() {
let wai = Path::new("/tmp/test.bmshj.wai");
let ref_rgb = Path::new("/tmp/ref_bmshj.rgb");
let model = Path::new("/tmp/wai_bmshj/decoder.onnx");
if !wai.exists() || !ref_rgb.exists() || !model.exists() {
eprintln!("skipping bmshj reference match: /tmp artifacts not present");
return;
}
let env = Wai::read(wai).unwrap();
let reg = ModelRegistry::new().register("wai.neural.bmshj2018", model);
let img = match decode_envelope(&env, &reg).expect("rust decode") {
Decoded::Image(i) => i,
_ => panic!("expected image"),
};
let reference = std::fs::read(ref_rgb).unwrap();
assert_eq!(img.rgb.len(), reference.len());
let diffs = || img.rgb.iter().zip(&reference).map(|(a, b)| (*a as i32 - *b as i32).abs());
let maxd = diffs().max().unwrap();
let meand = diffs().map(|d| d as f64).sum::<f64>() / reference.len() as f64;
println!(" bmshj2018 vs CompressAI: max|Δ|={maxd} mean|Δ|={meand:.3}");
assert!(maxd <= 4, "bmshj2018 Rust decode diverges from CompressAI (max {maxd})");
}
/// END-TO-END validation of the checkerboard CONTEXT decoder (`context.rs`)
/// against a minimal CompressAI-compatible elic model run through the actual
/// export/encode logic. Validates the 2-pass anchor→context→non-anchor
/// orchestration + single-stream symbol order. Skipped without /tmp artifacts.
#[test]
fn elic_matches_reference() {
let wai = Path::new("/tmp/test.elic.wai");
let ref_rgb = Path::new("/tmp/ref_elic.rgb");
let model = Path::new("/tmp/wai_elic/decoder.onnx");
let dir = Path::new("/tmp/wai_elic");
if !wai.exists() || !ref_rgb.exists() || !dir.join("context.onnx").exists() {
eprintln!("skipping elic reference match: /tmp artifacts not present");
return;
}
let env = Wai::read(wai).unwrap();
let reg = ModelRegistry::new().register("wai.neural.elic", model);
let img = match decode_envelope(&env, &reg).expect("rust elic decode") {
Decoded::Image(i) => i,
_ => panic!("expected image"),
};
let reference = std::fs::read(ref_rgb).unwrap();
assert_eq!(img.rgb.len(), reference.len());
let diffs = || img.rgb.iter().zip(&reference).map(|(a, b)| (*a as i32 - *b as i32).abs());
let maxd = diffs().max().unwrap();
let meand = diffs().map(|d| d as f64).sum::<f64>() / reference.len() as f64;
println!(" elic vs reference: max|Δ|={maxd} mean|Δ|={meand:.3}");
assert!(maxd <= 4, "elic Rust decode diverges (max {maxd}) — checkerboard orchestration wrong");
}
/// END-TO-END validation of the MLIC++ channel-autoregressive decoder
/// (`mlicpp.rs`) against a minimal CompressAI-compatible model: K channel
/// slices × checkerboard, the entropy net re-run on concat[y_so_far, hyper] as
/// context grows. Validates the slice-loop ordering. Skipped without artifacts.
#[test]
fn mlicpp_matches_reference() {
let wai = Path::new("/tmp/test.mlic.wai");
let ref_rgb = Path::new("/tmp/ref_mlic.rgb");
let model = Path::new("/tmp/wai_mlic/decoder.onnx");
let dir = Path::new("/tmp/wai_mlic");
if !wai.exists() || !ref_rgb.exists() || !dir.join("entropy.onnx").exists() {
eprintln!("skipping mlicpp reference match: /tmp artifacts not present");
return;
}
let env = Wai::read(wai).unwrap();
let reg = ModelRegistry::new().register("wai.neural.mlicpp", model);
let img = match decode_envelope(&env, &reg).expect("rust mlicpp decode") {
Decoded::Image(i) => i,
_ => panic!("expected image"),
};
let reference = std::fs::read(ref_rgb).unwrap();
assert_eq!(img.rgb.len(), reference.len());
let diffs = || img.rgb.iter().zip(&reference).map(|(a, b)| (*a as i32 - *b as i32).abs());
let maxd = diffs().max().unwrap();
let meand = diffs().map(|d| d as f64).sum::<f64>() / reference.len() as f64;
println!(" mlicpp vs reference: max|Δ|={maxd} mean|Δ|={meand:.3}");
assert!(maxd <= 4, "mlicpp Rust decode diverges (max {maxd}) — slice orchestration wrong");
}
/// MLICv2 shares MLIC++'s multi-reference
/// channel-autoregressive decode — its gains live in the sink nets. Prove the
/// route is LIVE (not just registered): an mlicpp-format envelope relabeled
/// `wai.neural.mlicv2` decodes identically through `mlicpp::decode`.
#[test]
fn mlicv2_routes_through_mlicpp_decoder() {
let wai = Path::new("/tmp/test.mlic.wai");
let ref_rgb = Path::new("/tmp/ref_mlic.rgb");
let model = Path::new("/tmp/wai_mlic/decoder.onnx");
let dir = Path::new("/tmp/wai_mlic");
if !wai.exists() || !ref_rgb.exists() || !dir.join("entropy.onnx").exists() {
eprintln!("skipping mlicv2 route: /tmp artifacts not present");
return;
}
let base = Wai::read(wai).unwrap();
let mut m = base.manifest.clone();
m.model_requirement.capability = "wai.neural.mlicv2".into();
let env = Wai::new(m, base.payload.clone());
let reg = ModelRegistry::new().register("wai.neural.mlicv2", model);
let img = match decode_envelope(&env, &reg).expect("mlicv2 decode") {
Decoded::Image(i) => i,
_ => panic!("expected image"),
};
let reference = std::fs::read(ref_rgb).unwrap();
let maxd = img.rgb.iter().zip(&reference)
.map(|(a, b)| (*a as i32 - *b as i32).abs()).max().unwrap();
println!(" mlicv2 (via mlicpp route) vs reference: max|Δ|={maxd}");
assert!(maxd <= 4, "mlicv2 route diverges (max {maxd}) — dispatch not wired");
}
/// END-TO-END validation of the SNAC multi-resolution decoder (`snac.rs`):
/// N variable-length code levels → dynamic-input ONNX (codes_0..codes_{N-1}) →
/// waveform. Validates the multi-level wire parse + dynamic dispatch against a
/// clean synthetic decoder of SNAC's interface (the real SNAC model has known
/// ONNX-export issues — noise/attention reshapes — which is a sink-side concern,
/// not this decoder's). Skipped without /tmp artifacts.
#[test]
fn snac_matches_reference() {
let wai = Path::new("/tmp/test.snac.wai");
let ref_f = Path::new("/tmp/ref_snac.f32");
let model = Path::new("/tmp/wai_snac/decoder.onnx");
if !wai.exists() || !ref_f.exists() || !model.exists() {
eprintln!("skipping snac reference match: /tmp artifacts not present");
return;
}
let env = Wai::read(wai).unwrap();
let reg = ModelRegistry::new().register("wai.neural.snac", model);
let audio = match decode_envelope(&env, &reg).expect("snac decode") {
Decoded::Audio(a) => a,
_ => panic!("expected audio"),
};
assert_eq!(audio.sample_rate, 24_000);
let ref_bytes = std::fs::read(ref_f).unwrap();
let reference: Vec<f32> = ref_bytes.chunks_exact(4)
.map(|c| f32::from_le_bytes(c.try_into().unwrap())).collect();
assert_eq!(audio.samples.len(), reference.len(), "sample count mismatch");
let maxd = audio.samples.iter().zip(&reference)
.map(|(a, b)| (a - b).abs()).fold(0f32, f32::max);
println!(" snac vs reference: max|Δ|={maxd:.2e} ({} samples, 3 levels)", audio.samples.len());
assert!(maxd < 1e-4, "snac decode diverges (max {maxd}) — multi-level dispatch wrong");
}
/// CMIC (ICLR 2026, −15.91% vs VTM) uses the SCCTX entropy model (space-channel
/// context = channel slices + checkerboard) — the mlicpp orchestration; its
/// Mamba is in the sink transform. Prove the route is live: an mlicpp-format
/// envelope relabeled `wai.neural.cmic` decodes identically.
#[test]
fn cmic_routes_through_mlicpp_decoder() {
let wai = Path::new("/tmp/test.mlic.wai");
let ref_rgb = Path::new("/tmp/ref_mlic.rgb");
let model = Path::new("/tmp/wai_mlic/decoder.onnx");
let dir = Path::new("/tmp/wai_mlic");
if !wai.exists() || !ref_rgb.exists() || !dir.join("entropy.onnx").exists() {
eprintln!("skipping cmic route: /tmp artifacts not present");
return;
}
let base = Wai::read(wai).unwrap();
let mut m = base.manifest.clone();
m.model_requirement.capability = "wai.neural.cmic".into();
let env = Wai::new(m, base.payload.clone());
let reg = ModelRegistry::new().register("wai.neural.cmic", model);
let img = match decode_envelope(&env, &reg).expect("cmic decode") {
Decoded::Image(i) => i,
_ => panic!("expected image"),
};
let reference = std::fs::read(ref_rgb).unwrap();
let maxd = img.rgb.iter().zip(&reference)
.map(|(a, b)| (*a as i32 - *b as i32).abs()).max().unwrap();
println!(" cmic (via mlicpp route) vs reference: max|Δ|={maxd}");
assert!(maxd <= 4, "cmic route diverges (max {maxd}) — dispatch not wired");
}
/// END-TO-END validation of the DCVC INTER-frame video decoder
/// (`video_dcvc.rs`): a frame loop that propagates a reference feature, decoded
/// on CPU via ort (no GPU required). 3 moving frames through a
/// minimal hyperprior + temporal-decoder model; the reference feature threads
/// frame→frame so frames differ even from similar latents. Skipped w/o artifacts.
#[test]
fn dcvc_matches_reference() {
let wai = Path::new("/tmp/test.dcvc.wai");
let ref_rgb = Path::new("/tmp/ref_dcvc.rgb");
let dir = Path::new("/tmp/wai_dcvc");
if !wai.exists() || !ref_rgb.exists() || !dir.join("temporal_decoder.onnx").exists() {
eprintln!("skipping dcvc reference match: /tmp artifacts not present");
return;
}
let env = Wai::read(wai).unwrap();
let reg = ModelRegistry::new().register("wai.neural.dcvc_rt", dir.join("decoder.onnx"));
let video = match decode_envelope(&env, &reg).expect("dcvc decode") {
Decoded::Video(v) => v,
_ => panic!("expected video"),
};
assert_eq!(video.frames_rgb.len(), 3, "frame count");
let reference = std::fs::read(ref_rgb).unwrap();
let flat: Vec<u8> = video.frames_rgb.concat();
assert_eq!(flat.len(), reference.len(), "total byte count");
let maxd = flat.iter().zip(&reference)
.map(|(a, b)| (*a as i32 - *b as i32).abs()).max().unwrap();
// also confirm frames actually differ (temporal propagation did something)
let f0_eq_f1 = video.frames_rgb[0] == video.frames_rgb[1];
println!(" dcvc (3 frames, temporal propagation) vs reference: max|Δ|={maxd} frames-differ={}", !f0_eq_f1);
assert!(maxd <= 4, "dcvc decode diverges (max {maxd}) — temporal propagation wrong");
}
/// END-TO-END validation of the GLC CATEGORICAL decoder (`glc.rs`): codebook
/// indices via per-position softmax → CompressAI-exact pmf_to_quantized_cdf →
/// bypass-free categorical rANS, over a checkerboard. A minimal VQ model + a
/// matching categorical rANS encoder; reference = synthesis(true indices).
/// Skipped without /tmp artifacts.
#[test]
fn glc_matches_reference() {
let wai = Path::new("/tmp/test.glc.wai");
let ref_rgb = Path::new("/tmp/ref_glc.rgb");
let dir = Path::new("/tmp/wai_glc");
if !wai.exists() || !ref_rgb.exists() || !dir.join("hyper_entropy.onnx").exists() {
eprintln!("skipping glc reference match: /tmp artifacts not present");
return;
}
let env = Wai::read(wai).unwrap();
let reg = ModelRegistry::new().register("wai.neural.glc", dir.join("decoder.onnx"));
let img = match decode_envelope(&env, &reg).expect("glc decode") {
Decoded::Image(i) => i,
_ => panic!("expected image"),
};
let reference = std::fs::read(ref_rgb).unwrap();
assert_eq!(img.rgb.len(), reference.len());
let maxd = img.rgb.iter().zip(&reference)
.map(|(a, b)| (*a as i32 - *b as i32).abs()).max().unwrap();
println!(" glc (categorical/VQ, 256 indices) vs reference: max|Δ|={maxd}");
assert!(maxd <= 4, "glc decode diverges (max {maxd}) — categorical entropy wrong");
}
/// SNAC against the REAL pretrained snac_24khz model (not synthetic): exported
/// after model surgery — zero-noise (NoiseBlock's torch.randn made decode
/// stochastic; WAI needs determinism) + an export-clean snake. Validates the
/// multi-level decoder on the genuine 3-codebook hierarchy. Skipped w/o files.
#[test]
fn snac_real_model_matches_reference() {
let wai = Path::new("/tmp/test.snac_real.wai");
let ref_f = Path::new("/tmp/ref_snac_real.f32");
let model = Path::new("/tmp/wai_snac_real/decoder.onnx");
if !wai.exists() || !ref_f.exists() || !model.exists() {
eprintln!("skipping real-snac match: /tmp artifacts not present");
return;
}
let env = Wai::read(wai).unwrap();
let reg = ModelRegistry::new().register("wai.neural.snac", model);
let audio = match decode_envelope(&env, &reg).expect("snac decode") {
Decoded::Audio(a) => a,
_ => panic!("expected audio"),
};
assert_eq!(audio.sample_rate, 24_000);
let reference: Vec<f32> = std::fs::read(ref_f).unwrap()
.chunks_exact(4).map(|c| f32::from_le_bytes(c.try_into().unwrap())).collect();
assert_eq!(audio.samples.len(), reference.len());
let maxd = audio.samples.iter().zip(&reference)
.map(|(a, b)| (a - b).abs()).fold(0f32, f32::max);
println!(" REAL snac_24khz vs torch(deterministic): max|Δ|={maxd:.2e} ({} samples)", audio.samples.len());
assert!(maxd < 1e-3, "real snac decode diverges (max {maxd})");
}
/// int_synth against a REAL QAT/PTQ-trained model (not the constructed unit
/// test): a float autoencoder trained on synthetic images, then quantized to
/// the integer spec with per-layer activation-calibrated shifts. Confirms the
/// Rust integer decode is BIT-IDENTICAL to the numpy integer-forward reference
/// on a trained model (the determinism guarantee, on real weights). Skipped
/// without /tmp artifacts.
#[test]
fn int_synth_trained_model_matches_integer_forward() {
let wai = Path::new("/tmp/test.intsynth.wai");
let ref_rgb = Path::new("/tmp/ref_intsynth.rgb");
let dir = Path::new("/tmp/wai_intsynth");
if !wai.exists() || !ref_rgb.exists() || !dir.join("int_synth.json").exists() {
eprintln!("skipping trained int_synth: /tmp artifacts not present");
return;
}
let env = Wai::read(wai).unwrap();
let reg = ModelRegistry::new().register("wai.neural.int_synth", dir.join("model"));
let img = match decode_envelope(&env, &reg).expect("int_synth decode") {
Decoded::Image(i) => i,
_ => panic!("expected image"),
};
let reference = std::fs::read(ref_rgb).unwrap();
assert_eq!(img.rgb.len(), reference.len());
let maxd = img.rgb.iter().zip(&reference)
.map(|(a, b)| (*a as i32 - *b as i32).abs()).max().unwrap();
println!(" trained int_synth: Rust vs numpy integer-forward max|Δ|={maxd} (must be 0 — integer-exact)");
assert_eq!(maxd, 0, "Rust integer decode must be bit-identical to the reference");
}
/// A temporary directory holding the tiny conditional codec's set under its member
/// names (`g_s.whm`, `h_s.whm`, `entropy.json`) and a listing, `set.sha256`, of the
/// members `listed`. Returns the directory and the listing's SHA-256.
fn int_hyper_set_dir(tag: &str, listed: &[&str]) -> (PathBuf, String) {
let v = Path::new(env!("CARGO_MANIFEST_DIR")).join("tests/vectors/int_hyper");
let dir = std::env::temp_dir().join(format!("wai-int-hyper-{tag}-{}", std::process::id()));
std::fs::create_dir_all(&dir).unwrap();
let mut files = std::collections::BTreeMap::new();
for (member, src) in [("entropy.json", "tiny_entropy.json"), ("g_s.whm", "tiny_g_s.bin"), ("h_s.whm", "tiny_h_s.bin")] {
let b = std::fs::read(v.join(src)).unwrap();
std::fs::write(dir.join(member), &b).unwrap();
if listed.contains(&member) {
files.insert(member.to_string(), b);
}
}
let view: std::collections::BTreeMap<String, &[u8]> = files.iter().map(|(k, v)| (k.clone(), v.as_slice())).collect();
let listing = wai::pin::listing_from(&view).unwrap();
std::fs::write(dir.join("set.sha256"), &listing).unwrap();
(dir, wai::pin::sha256_hex(&listing))
}
/// `wai.neural.int_hyper` through the neural dispatch, which delegates it to
/// `int_payload::decode_int`: its `WIH1` payload decodes from the three-file set, pinned
/// through the set's listing (under the strict `replicate` gate) and unpinned, to the
/// committed image. A pinned set whose listing leaves out `h_s.whm` is refused with
/// `set_incomplete` naming it. The tool's JSON output carried as the payload is refused
/// (`bad_magic`), and the refusal is final: the fallback the envelope names is not tried.
/// An unpinned set without `h_s.whm` refuses a JSON form as `bad_magic` too, the payload
/// being checked before any member is read, and a `WIH1` as `set_incomplete`.
#[test]
fn int_hyper_decodes_through_the_neural_dispatch() {
use wai::codecs::{DeclaredTier, CAP_NEURAL_INT_HYPER as HYP, CAP_NEURAL_INT_SYNTH, CAP_PRIOR_SET};
let v = Path::new(env!("CARGO_MANIFEST_DIR")).join("tests/vectors/int_hyper");
let payload = std::fs::read(v.join("tiny_bitstream.wih1")).unwrap();
let rgb_sha = "dce7282d46f88f03d5dc0fd42f325756d310fe1fc982b6e1792a1fbfbeb482cf";
let env = |intent: &str, prior: Option<Prior>, fallback: Option<&str>, payload: Vec<u8>| {
let mut req = ModelRequirement::new(HYP);
if let Some(f) = fallback {
req = req.with_fallback(f);
}
let mut cond = Conditioning::new("int_hyper");
if let Some(p) = prior {
cond = cond.with_prior(p);
}
Wai::new(Manifest::new("image", intent, req, cond), payload)
};
let sha = |r: Result<Decoded, DecodeError>| match r {
Ok(Decoded::Image(img)) => wai::pin::sha256_hex(&img.rgb),
other => refusal(other),
};
let (dir, digest) = int_hyper_set_dir("all", &["entropy.json", "g_s.whm", "h_s.whm"]);
let reg = ModelRegistry::new().register(HYP, dir.join("g_s.whm"));
let pin = Prior::new("tiny", digest, "decode-equivalence").with_form(CAP_PRIOR_SET).with_tier(DeclaredTier::DecodeEquivalence);
assert_eq!(sha(decode_envelope_strict(&env("replicate", Some(pin), None, payload.clone()), &reg)), rgb_sha);
assert_eq!(sha(decode_envelope(&env("improve", None, None, payload.clone()), &reg)), rgb_sha);
let (part, digest) = int_hyper_set_dir("part", &["entropy.json", "g_s.whm"]);
let pin = Prior::new("tiny", digest, "decode-equivalence").with_form(CAP_PRIOR_SET);
let r = decode_envelope(&env("improve", Some(pin), None, payload.clone()), &ModelRegistry::new().register(HYP, part.join("g_s.whm")));
assert!(matches!(r, Err(DecodeError::PriorMismatch(wai::container::PinRefusal::SetIncomplete { ref path })) if path == "h_s.whm"), "{}", refusal(r));
let json = std::fs::read(v.join("tiny_bitstream.json")).unwrap();
let spec = Path::new(env!("CARGO_MANIFEST_DIR")).join("../neural-conformance/vectors/gradient/model");
let both = ModelRegistry::new().register(HYP, dir.join("g_s.whm")).register(CAP_NEURAL_INT_SYNTH, spec);
for fallback in [None, Some(CAP_NEURAL_INT_SYNTH)] {
match decode_envelope(&env("improve", None, fallback, json.clone()), &both) {
Err(DecodeError::InvalidPayload(why)) => assert!(why.contains("bad_magic") && why.contains(HYP), "{why}"),
other => panic!("a JSON form must be refused as bad_magic, got {}", refusal(other)),
}
}
// An unpinned set that lacks a member: the payload is checked first, so a JSON form
// is still bad_magic, and a WIH1 is set_incomplete, naming the member, so dispatch
// moves on as it does for any decoder.
let (lack, _) = int_hyper_set_dir("lack", &["entropy.json", "g_s.whm", "h_s.whm"]);
std::fs::remove_file(lack.join("h_s.whm")).unwrap();
let reg = ModelRegistry::new().register(HYP, lack.join("g_s.whm"));
match decode_envelope(&env("improve", None, None, json.clone()), &reg) {
Err(DecodeError::InvalidPayload(why)) => assert!(why.contains("bad_magic"), "{why}"),
other => panic!("a JSON form must be refused as bad_magic, got {}", refusal(other)),
}
let r = decode_envelope(&env("improve", None, None, payload.clone()), &reg);
assert!(matches!(r, Err(DecodeError::PriorMismatch(wai::container::PinRefusal::SetIncomplete { ref path })) if path == "h_s.whm"), "{}", refusal(r));
std::fs::remove_dir_all(&dir).ok();
std::fs::remove_dir_all(&part).ok();
std::fs::remove_dir_all(&lack).ok();
}
/// The integer video, audio and splat capabilities through the neural dispatch:
/// `wai.video.int_motion`, which reads no parameter set, advertised with
/// `ModelRegistry::builtin`; `wai.audio.int_codec` and `wai.splat.int_codec`, each
/// registered as its one file, unpinned and under a form-less pin over that file. Each
/// decodes to `Decoded::Int` in the integer form its digest is taken over, with the
/// committed SHA-256. `builtin` does not advertise a capability that reads a set.
#[cfg(all(feature = "video_int", feature = "audio_int", feature = "splat_int"))]
#[test]
fn integer_media_decode_through_the_neural_dispatch() {
use wai::codecs::{CAP_AUDIO_INT_CODEC as AUD, CAP_NEURAL_INT_HYPER, CAP_SPLAT_INT_CODEC as SPL, CAP_VIDEO_INT_MOTION as MOT};
use wai::int_payload::IntDecoded;
let v = Path::new(env!("CARGO_MANIFEST_DIR")).join("tests/vectors");
let rd = |rel: &str| std::fs::read(v.join(rel)).unwrap();
let side = |rel: &str, key: &str, field: &str| -> String {
let j: serde_json::Value = serde_json::from_slice(&rd(rel)).unwrap();
j[key][field].as_str().unwrap().to_string()
};
let env = |cap: &str, prior: Option<Prior>, payload: Vec<u8>| {
let mut cond = Conditioning::new("bytes");
if let Some(p) = prior {
cond = cond.with_prior(p);
}
Wai::new(Manifest::new("binary", "improve", ModelRequirement::new(cap), cond), payload)
};
let reg = ModelRegistry::new()
.builtin(MOT)
.register(AUD, v.join("int_audio/audio_model.bin"))
.register(SPL, v.join("int_splat/splat_gs.bin"));
assert!(reg.advertises(MOT));
assert!(!ModelRegistry::new().builtin(CAP_NEURAL_INT_HYPER).advertises(CAP_NEURAL_INT_HYPER));
match decode_envelope(&env(MOT, None, rd("int_video/int_video_bitstream.wiv1")), &reg) {
Ok(Decoded::Int(IntDecoded::Video { frames, width: 48, height: 48 })) => {
let per: Vec<u8> = frames.iter().flat_map(|f| wai::pin::sha256(f)).collect();
assert_eq!(wai::pin::sha256_hex(&per), side("int_video/sha256.json", "int_video", "clip_sha256"));
}
other => panic!("int_motion: {}", refusal(other)),
}
let model = rd("int_audio/audio_model.bin");
for prior in [None, Some(Prior::new("audio", wai::pin::sha256_hex(&model), "decode-equivalence"))] {
match decode_envelope(&env(AUD, prior, rd("int_audio/audio_bitstream.wia1")), &reg) {
Ok(Decoded::Int(IntDecoded::Pcm { samples, sample_rate: 16_000, channels: 1 })) => {
let le: Vec<u8> = samples.iter().flat_map(|s| s.to_le_bytes()).collect();
assert_eq!(wai::pin::sha256_hex(&le), side("int_audio/sha256.json", "audio", "sha256"));
}
other => panic!("int_codec: {}", refusal(other)),
}
}
let gs = rd("int_splat/splat_gs.bin");
for prior in [None, Some(Prior::new("splat", wai::pin::sha256_hex(&gs), "decode-equivalence"))] {
match decode_envelope(&env(SPL, prior, rd("int_splat/splat.wis1")), &reg) {
Ok(Decoded::Int(IntDecoded::Attr { bytes, n_attr: 14, s: 32, .. })) => {
assert_eq!(wai::pin::sha256_hex(&bytes), side("int_splat/sha256.json", "splat", "sha256"));
}
other => panic!("splat: {}", refusal(other)),
}
}
}
/// An integer capability this build has no decoder for (here `wai.video.int_motion`,
/// without `video_int`) is refused with `unsupported_capability`, which is not final:
/// SPEC §4 does not take step 3 with a capability the sink cannot decode, so dispatch
/// moves on to the fallback, which decodes the payload. Without a fallback the
/// capability is reported as unknown.
#[cfg(not(feature = "video_int"))]
#[test]
fn an_integer_capability_without_a_decoder_moves_on_to_the_fallback() {
let src = Path::new(env!("CARGO_MANIFEST_DIR")).join("../neural-conformance/vectors/gradient");
let latent = std::fs::read(src.join("latent.bin")).unwrap();
let (mot, synth) = ("wai.video.int_motion", "wai.neural.int_synth");
let reg = ModelRegistry::new().builtin(mot).register(synth, src.join("model"));
let env = |fallback: Option<&str>| {
let mut req = ModelRequirement::new(mot);
if let Some(f) = fallback {
req = req.with_fallback(f);
}
Wai::new(Manifest::new("image", "improve", req, Conditioning::new("int_synth")), latent.clone())
};
match decode_envelope(&env(Some(synth)), &reg) {
Ok(Decoded::Image(img)) => assert_eq!((img.width, img.height), (38, 38)),
other => panic!("the fallback must decode, got {}", refusal(other)),
}
assert!(matches!(decode_envelope(&env(None), &reg), Err(DecodeError::UnknownCapability(ref c)) if c == mot));
}
/// A key log stand-in that holds the capability's sets to §7.9 and grants only the
/// digests it holds: an unpinned set is authorised only under one of them.
#[derive(Debug)]
struct Grants(Vec<String>);
impl wai::pin::PinAuthority for Grants {
fn check(&self, cap: &str, prior: &Prior) -> Result<(), wai::container::PinRefusal> {
self.check_unpinned(cap, std::slice::from_ref(&prior.sha256))
}
fn check_unpinned(&self, cap: &str, digests: &[String]) -> Result<(), wai::container::PinRefusal> {
if digests.iter().any(|d| self.0.contains(d)) {
return Ok(());
}
Err(wai::container::PinRefusal::NotAuthorised { capability: cap.into(), check: None, reason: None })
}
}
/// A listing beside the registered path identifies a set only when it matches the
/// files the decode reads. A key log that grants only the publisher's listing refuses
/// an unpinned decode of other files (`prior_not_authorised`), with a copy of that
/// listing beside them or not; the publisher's own files beside the same listing
/// decode. The same holds for a one-file capability registered as its file, and for a
/// capability outside the integer path (resolved, not decoded: no model is needed).
#[test]
fn a_listing_that_does_not_match_the_files_read_authorises_nothing() {
use wai::codecs::{CAP_AUDIO_INT_CODEC as AUD, CAP_NEURAL_INT_HYPER as HYP};
let code = |r: Result<Decoded, DecodeError>| match r {
Ok(_) => "decoded".to_string(),
Err(e) => refusal(Err(e)),
};
let v = Path::new(env!("CARGO_MANIFEST_DIR")).join("tests/vectors");
let root = std::env::temp_dir().join(format!("wai-stale-listing-{}", std::process::id()));
let set: std::collections::BTreeMap<String, Vec<u8>> = [("entropy.json", "int_hyper/tiny_entropy.json"), ("g_s.whm", "int_hyper/tiny_g_s.bin"), ("h_s.whm", "int_hyper/tiny_h_s.bin")]
.into_iter().map(|(k, f)| (k.to_string(), std::fs::read(v.join(f)).unwrap())).collect();
let view: std::collections::BTreeMap<String, &[u8]> = set.iter().map(|(k, b)| (k.clone(), b.as_slice())).collect();
let granted = wai::pin::listing_from(&view).unwrap();
let write = |dir: &Path, files: &std::collections::BTreeMap<String, Vec<u8>>, listing: bool| {
std::fs::create_dir_all(dir).unwrap();
for (k, b) in files {
std::fs::write(dir.join(k), b).unwrap();
}
if listing {
std::fs::write(dir.join("publisher.sha256"), &granted).unwrap();
}
};
let mut other = set.clone();
other.get_mut("entropy.json").unwrap().push(b' ');
let env = Wai::new(Manifest::new("image", "improve", ModelRequirement::new(HYP), Conditioning::new("bytes")),
std::fs::read(v.join("int_hyper/tiny_bitstream.wih1")).unwrap());
let reg = |dir: &Path| ModelRegistry::new().register(HYP, dir.to_path_buf()).with_key_log(Grants(vec![wai::pin::sha256_hex(&granted)]));
for (name, files, listing, want) in [
("other files", &other, false, "prior_not_authorised"),
("other files beside the granted listing", &other, true, "prior_not_authorised"),
("the granted files beside their listing", &set, true, "decoded"),
] {
let dir = root.join(name.replace(' ', "-"));
write(&dir, files, listing);
assert_eq!(code(decode_envelope(&env, &reg(&dir))), want, "{name}");
}
// One file: the publisher's model.wam is granted under its listing; the sink's file
// differs in its last byte.
let model = std::fs::read(v.join("int_audio/audio_model.bin")).unwrap();
let one: std::collections::BTreeMap<String, &[u8]> = [("model.wam".to_string(), model.as_slice())].into_iter().collect();
let pub_listing = wai::pin::listing_from(&one).unwrap();
let mut tampered = model.clone();
*tampered.last_mut().unwrap() ^= 1;
let dir = root.join("audio");
std::fs::create_dir_all(&dir).unwrap();
std::fs::write(dir.join("model.wam"), &tampered).unwrap();
std::fs::write(dir.join("publisher.sha256"), &pub_listing).unwrap();
let envw = Wai::new(Manifest::new("audio", "improve", ModelRequirement::new(AUD), Conditioning::new("bytes")),
std::fs::read(v.join("int_audio/audio_bitstream.wia1")).unwrap());
let reg = ModelRegistry::new().register(AUD, dir.join("model.wam")).with_key_log(Grants(vec![wai::pin::sha256_hex(&pub_listing)]));
assert_eq!(code(decode_envelope(&envw, &reg)), "prior_not_authorised", "a one-file set beside a stale listing");
// A capability outside the integer path: the listing must match the files beside it
// and name the registered file.
let cap = "wai.neural.bmshj2018";
let dir = root.join("onnx");
std::fs::create_dir_all(&dir).unwrap();
std::fs::write(dir.join("decoder.onnx"), b"publisher").unwrap();
let onnx: std::collections::BTreeMap<String, &[u8]> = [("decoder.onnx".to_string(), &b"publisher"[..])].into_iter().collect();
let l = wai::pin::listing_from(&onnx).unwrap();
std::fs::write(dir.join("publisher.sha256"), &l).unwrap();
let reg = || ModelRegistry::new().register(cap, dir.join("decoder.onnx")).with_key_log(Grants(vec![wai::pin::sha256_hex(&l)]));
assert!(reg().resolve_verified(cap, None).is_ok(), "the granted file beside its listing resolves");
std::fs::write(dir.join("decoder.onnx"), b"other").unwrap();
assert!(matches!(reg().resolve_verified(cap, None), Err(DecodeError::PriorMismatch(ref r)) if r.code() == "prior_not_authorised"),
"another file beside the granted listing is not authorised");
std::fs::remove_dir_all(&root).ok();
}
/// Outside the integer path, a granted listing authorises the files it names and
/// nothing else: at a sink whose key log holds the capability's sets to §7.9, the
/// unpinned decode reads only the part §7.9 authorised of what it read once
/// (`ParamSource::Checked`), and a file the decode needs that the part does not name
/// is `set_incomplete`, never read from disk. A `wai.neural.bmshj2018` payload reads
/// its CDF tables (`cdfs_q3.json`) before it loads the decoder, so a decode that read
/// the unauthorised tables beside the decoder would fail parsing them instead.
///
/// - the decoder registered as its file, beside a granted listing that names only
/// `decoder.onnx` and an unauthorised `cdfs_q3.json`: `set_incomplete`;
/// - the directory registered, beside a granted listing that names only `notes.txt`:
/// `set_incomplete`;
/// - a granted listing of both files: the decode reads the tables from the set;
/// - a one-file capability granted under its file's digest: that file alone;
/// - a key log that only revokes: every file of the decoder's directory, read once.
#[test]
fn a_granted_listing_authorises_only_the_files_it_names() {
use wai::neural::ParamSource;
use wai::pin::Verified;
let bm = "wai.neural.bmshj2018";
let dir = std::env::temp_dir().join(format!("wai-granted-listing-{}", std::process::id()));
std::fs::create_dir_all(&dir).unwrap();
let files: [(&str, &[u8]); 3] = [("decoder.onnx", b"the publisher's decoder"), ("cdfs_q3.json", b"{\"unauthorised\": true}"), ("notes.txt", b"an unrelated file")];
for (n, b) in files {
std::fs::write(dir.join(n), b).unwrap();
}
let listing = |names: &[&str]| {
let set: std::collections::BTreeMap<String, &[u8]> =
files.iter().filter(|(n, _)| names.contains(n)).map(|(n, b)| (n.to_string(), *b)).collect();
let l = wai::pin::listing_from(&set).unwrap();
std::fs::write(dir.join("granted.sha256"), &l).unwrap();
wai::pin::sha256_hex(&l)
};
// h 1, w 1, an empty stream, quality 3, one channel, a 1 × 1 latent.
let mut payload = Vec::new();
for v in [1u32, 1, 0, 3] {
payload.extend_from_slice(&v.to_le_bytes());
}
payload.extend_from_slice(&[1, 0]);
let env = Wai::new(Manifest::new("image", "improve", ModelRequirement::new(bm), Conditioning::new("bytes")), payload);
let names = |p: &ParamSource| match p {
ParamSource::Checked { set: Verified::Set { files, .. }, .. } => files.keys().cloned().collect::<Vec<_>>().join(","),
ParamSource::Checked { set: Verified::File(_), .. } => "one file".into(),
ParamSource::Unpinned(_) => "the path".into(),
other => format!("{other:?}"),
};
let case = |path: PathBuf, granted: &[&str]| {
let reg = ModelRegistry::new().register(bm, path).with_key_log(Grants(vec![listing(granted)]));
(names(&reg.resolve_verified(bm, None).unwrap()), refusal(decode_envelope(&env, &reg)))
};
let incomplete = |r: &str| r == "set_incomplete";
let (set, r) = case(dir.join("decoder.onnx"), &["decoder.onnx"]);
assert_eq!(set, "decoder.onnx");
assert!(incomplete(&r), "a listing of the decoder alone does not authorise the tables beside it: {r}");
let (set, r) = case(dir.clone(), &["notes.txt"]);
assert_eq!(set, "notes.txt");
assert!(incomplete(&r), "a listing of another file does not authorise the directory: {r}");
let (set, r) = case(dir.join("decoder.onnx"), &["cdfs_q3.json", "decoder.onnx"]);
assert_eq!(set, "cdfs_q3.json,decoder.onnx");
assert!(r.contains("cdf parse cdfs_q3.json"), "the listed tables are read from the set: {r}");
// A one-file capability granted under its file's digest decodes from that file alone.
std::fs::remove_file(dir.join("granted.sha256")).unwrap();
let enc = "wai.neural.encodec32";
let digest = wai::pin::sha256_hex(files[0].1);
let reg = ModelRegistry::new().register(enc, dir.join("decoder.onnx")).with_key_log(Grants(vec![digest.clone()]));
match reg.resolve_verified(enc, None).unwrap() {
ParamSource::Checked { set: Verified::File(b), .. } => assert_eq!(b, files[0].1),
other => panic!("expected the authorised file, got {other:?}"),
}
// A key log that only revokes holds nothing to §7.9: the decode reads every file of
// the decoder's directory, read once.
let reg = ModelRegistry::new().register(bm, dir.join("decoder.onnx")).with_key_log(Revokes(vec!["00".repeat(32)]));
assert_eq!(names(&reg.resolve_verified(bm, None).unwrap()), "cdfs_q3.json,decoder.onnx,notes.txt");
std::fs::remove_dir_all(&dir).ok();
}
/// At a sink whose key log only revokes, an unpinned decode outside the integer path
/// is checked over every digest a pin over what it reads could name, and reads those
/// bytes alone (SPEC §4, *Module authorisation*). With no listing beside the files, a
/// key log that revokes the listing of `{decoder.onnx, cdfs_q3.json}` still refuses
/// them (`prior_revoked`) through the listing derived from the directory, whether the
/// decoder or the directory is registered; one that revokes a member's own digest
/// refuses them too. The bytes were read once: tables swapped on disk after the check
/// are not the tables the decode reads. With no key log, the decode reads the path.
#[test]
fn a_revoke_only_key_log_checks_and_reads_the_set_once() {
use wai::neural::{decode_payload, ParamSource};
use wai::pin::Verified;
let bm = "wai.neural.bmshj2018";
let root = std::env::temp_dir().join(format!("wai-revoke-only-{}", std::process::id()));
let (decoder, cdfs_a, cdfs_b): (&[u8], &[u8], &[u8]) = (b"the publisher's decoder bytes", b"cdfs A: not JSON", b"{\"channels\": 1}");
let mk = |name: &str| {
let d = root.join(name);
std::fs::create_dir_all(&d).unwrap();
std::fs::write(d.join("decoder.onnx"), decoder).unwrap();
std::fs::write(d.join("cdfs_q3.json"), cdfs_a).unwrap();
d
};
let set: std::collections::BTreeMap<String, &[u8]> =
[("decoder.onnx".to_string(), decoder), ("cdfs_q3.json".to_string(), cdfs_a)].into_iter().collect();
let listing = wai::pin::listing_from(&set).unwrap();
let revoked = wai::pin::sha256_hex(&listing);
let mut payload = Vec::new();
for v in [1u32, 1, 0, 3] {
payload.extend_from_slice(&v.to_le_bytes());
}
payload.extend_from_slice(&[1, 0]);
let env = Wai::new(Manifest::new("image", "improve", ModelRequirement::new(bm), Conditioning::new("bytes")), payload.clone());
let r = mk("revoked");
std::fs::write(r.join("set.sha256"), &listing).unwrap();
let file_reg = || ModelRegistry::new().register(bm, r.join("decoder.onnx"));
assert_eq!(refusal(decode_envelope(&env, &file_reg().with_key_log(Revokes(vec![revoked.clone()])))), "prior_revoked",
"the revoked set beside its listing");
std::fs::remove_file(r.join("set.sha256")).unwrap();
assert_eq!(refusal(decode_envelope(&env, &file_reg().with_key_log(Revokes(vec![revoked.clone()])))), "prior_revoked",
"the decoder registered, no listing beside it");
let dir_reg = ModelRegistry::new().register(bm, r.clone()).with_key_log(Revokes(vec![revoked.clone()]));
assert_eq!(refusal(decode_envelope(&env, &dir_reg)), "prior_revoked", "the directory registered, no listing beside it");
let member = Revokes(vec![wai::pin::sha256_hex(cdfs_a)]);
assert_eq!(refusal(decode_envelope(&env, &file_reg().with_key_log(member))), "prior_revoked", "a member's own digest revoked");
// Read once: the tables swapped after the check are not read. The decode reads A
// (not JSON: "expected value"); B would parse and lack a field.
let t = mk("toctou");
let reg = ModelRegistry::new().register(bm, t.join("decoder.onnx")).with_key_log(Revokes(vec![]));
let params = reg.resolve_verified(bm, None).unwrap();
std::fs::write(t.join("cdfs_q3.json"), cdfs_b).unwrap();
std::fs::write(t.join("cdfs_q4.json"), cdfs_b).unwrap();
let got = refusal(decode_payload(bm, &payload, &params));
assert!(got.contains("cdf parse cdfs_q3.json: expected value"), "the decode read the tables checked: {got}");
match &params {
ParamSource::Checked { set: Verified::Set { files, .. }, model } => {
assert_eq!(files.keys().collect::<Vec<_>>(), ["cdfs_q3.json", "decoder.onnx"]);
assert_eq!(model.as_deref(), Some("decoder.onnx"));
}
other => panic!("expected the files read once, got {other:?}"),
}
// No key log: no check 5, and the decode reads the path, as it always has.
assert!(matches!(ModelRegistry::new().register(bm, t.join("decoder.onnx")).resolve_verified(bm, None), Ok(ParamSource::Unpinned(_))));
std::fs::remove_dir_all(&root).ok();
}
/// The reference sink opens no encryption scheme, so an envelope whose manifest
/// declares one is inert at it (SPEC §6.4 step 2, `unsupported_encryption`): a
/// payload sent in the clear under a claim of encryption is not decoded as plaintext,
/// and a tool's JSON form under that claim is not read as a payload either. The same
/// payload without the claim decodes; a `WAI2` gives every entry the reason, also when
/// its `security` member is not a security object.
#[test]
fn an_encrypted_envelope_is_inert_at_the_reference_sink() {
use wai::codecs::CAP_NEURAL_INT_HYPER as HYP;
use wai::container::{Rendition, Security, WaiMulti};
use wai::neural::decode_multi;
let v = Path::new(env!("CARGO_MANIFEST_DIR")).join("tests/vectors");
let dir = std::env::temp_dir().join(format!("wai-encrypted-{}", std::process::id()));
std::fs::create_dir_all(&dir).unwrap();
for (k, f) in [("entropy.json", "int_hyper/tiny_entropy.json"), ("g_s.whm", "int_hyper/tiny_g_s.bin"), ("h_s.whm", "int_hyper/tiny_h_s.bin")] {
std::fs::copy(v.join(f), dir.join(k)).unwrap();
}
let reg = ModelRegistry::new().register(HYP, dir.clone());
let (wih1, json) = (std::fs::read(v.join("int_hyper/tiny_bitstream.wih1")).unwrap(), std::fs::read(v.join("int_hyper/tiny_bitstream.json")).unwrap());
let env = |payload: &[u8], security: Option<Security>| {
let mut m = Manifest::new("image", "improve", ModelRequirement::new(HYP), Conditioning::new("bytes"));
m.security = security;
Wai::from_bytes(&Wai::new(m, payload.to_vec()).to_emit_bytes().unwrap()).unwrap()
};
assert!(matches!(decode_envelope(&env(&wih1, None), &reg), Ok(Decoded::Image(_))), "in the clear, it decodes");
for payload in [&wih1, &json] {
match decode_envelope(&env(payload, Some(Security::new("aes-256-gcm", 7))), &reg) {
Err(DecodeError::Encrypted(why)) => assert!(why.starts_with("unsupported_encryption: "), "{why}"),
other => panic!("an encrypted envelope must be inert, got {}", refusal(other)),
}
}
let multi = |security: Option<serde_json::Value>| {
let mut m = WaiMulti::new("image", "improve", serde_json::Value::Null, vec![Rendition::media(HYP, "bytes", wih1.clone())]);
if let Some(s) = security {
m.manifest.extra.insert("security".into(), s);
}
WaiMulti::from_bytes(&m.to_bytes().unwrap()).unwrap()
};
assert!(matches!(decode_multi(&multi(None), &reg), Ok((0, Decoded::Image(_)))));
for s in [serde_json::json!({"encryption": "mls-sframe", "kid": 0}), serde_json::json!(true)] {
match decode_multi(&multi(Some(s.clone())), &reg) {
Err(DecodeError::NoRendition(skips)) => assert_eq!(skips, vec![(0, "unsupported_encryption".to_string())], "{s}"),
other => panic!("{s}: expected every entry inert, got {:?}", other.map(|(i, _)| i)),
}
}
std::fs::remove_dir_all(&dir).ok();
}
/// The neural registry's pinned path runs check 5 over every identity of the bytes it
/// verified: a one-file set whose file digest a key log revokes is refused through a
/// set-form pin over a listing of that file.
#[test]
fn a_pinned_set_revoked_under_its_file_digest_is_refused_through_a_listing_pin() {
use wai::codecs::{CAP_AUDIO_INT_CODEC as AUD, CAP_PRIOR_SET};
let v = Path::new(env!("CARGO_MANIFEST_DIR")).join("tests/vectors");
let model = std::fs::read(v.join("int_audio/audio_model.bin")).unwrap();
let dir = std::env::temp_dir().join(format!("wai-listing-pin-{}", std::process::id()));
std::fs::create_dir_all(&dir).unwrap();
std::fs::write(dir.join("model.wam"), &model).unwrap();
let one: std::collections::BTreeMap<String, &[u8]> = [("model.wam".to_string(), model.as_slice())].into_iter().collect();
let listing = wai::pin::listing_from(&one).unwrap();
std::fs::write(dir.join("model.sha256"), &listing).unwrap();
let pin = Prior::new("m", wai::pin::sha256_hex(&listing), "decode-equivalence").with_form(CAP_PRIOR_SET);
let plain = ModelRegistry::new().register(AUD, dir.join("model.wam"));
assert!(plain.verify(AUD, &pin).is_ok(), "the pin verifies");
let revoking = ModelRegistry::new().register(AUD, dir.join("model.wam")).with_key_log(Revokes(vec![wai::pin::sha256_hex(&model)]));
assert_eq!(revoking.verify(AUD, &pin).map(|_| ()).map_err(|r| r.code()), Err("prior_revoked"));
std::fs::remove_dir_all(&dir).ok();
}