wai-quantum: QIR and jeff read and written on every surface, each conversion checked, bounded against hostile input #554
Merged
dcharlot
merged 10 commits from 2026-10-31 09:48:06 -04:00
wai/quantum-interchange into main 2026-10-31
wai-quantum: the tests that need the dyadic QIR writer or the receipts built only with them
All checks were successful
wai-quantum CPU vector units / member · vector unit, avx2 (x86_64 silicon) (pull_request) Successful in 20s
wai-quantum CPU vector units / member · vector unit, sve 2048-bit (aarch64, emulated) (pull_request) Successful in 31s
wai-quantum CPU vector units / member · vector unit, sve 512-bit (aarch64, emulated) (pull_request) Successful in 24s
WAI Studio / Studio in Chromium and Firefox · macos (pull_request) Successful in 15m49s
wai-quantum verdicts and repairs / the intent set and the verdict under wasm32-wasip2 (wasmtime) (pull_request) Successful in 1m19s
wai-quantum studio and desktop / desktop app · linux (pull_request) Successful in 5m41s
wai-quantum verdicts and repairs / verdicts, repairs and the intent set · linux (pull_request) Successful in 1m44s
wai-quantum WebGPU member / member · discrete GPU, Vulkan (jetson-hub) (pull_request) Successful in 28m19s
wai-quantum views in agent hosts / views · the page and its engine (pull_request) Successful in 3m5s
WAI conformance / cargo-class corpora · linux-arm64 (pull_request) Successful in 24m30s
wai-quantum views in agent hosts / views · a scripted host (pull_request) Successful in 3m28s
wai-quantum WebGPU member / member · software Vulkan (linux) (pull_request) Successful in 2m12s
WAI conformance / delivery telemetry · CMCD and CMSD against an independent library (pull_request) Successful in 10s
WAI Studio / the catalogue's actions, the unit tests and the core · linux (pull_request) Successful in 1m11s
WAI conformance / cross-arch byte-equality · linux-arm64 (pull_request) Successful in 44s
wai-quantum tensor-engine member / member · tensor engine, the kernel toolchain's simulator (linux) (pull_request) Successful in 8m48s
wai-quantum WebGPU member / shader checks · browser build · wasip2 inertness · MSRV (pull_request) Successful in 4m11s
WAI conformance / C2PA manifest emission · signed, read back, validated (pull_request) Successful in 2m21s
WAI conformance / each feature of the independent verifiers' steps compiles alone (pull_request) Successful in 18m19s
WAI mbt2018_mean integer decode (regenerated vectors) / regenerate mbt2018_mean integer vectors → Rust decode, required (pull_request) Successful in 6m16s
wai-web wasm32 / wai-web wasm32 build · corpus, menu and writers (pull_request) Successful in 6m56s
WAI examples / WAI examples · android-app · linux-arm64 (pull_request) Successful in 5m47s
wai-quantum HIP member / member · HIP absent (linux-arm64) (pull_request) Successful in 34s
wai-quantum npu-cores member / member · npu-cores absent (linux-arm64) (pull_request) Successful in 30s
WAI Studio / Studio in WebKit · linux (pull_request) Successful in 11m40s
wai-quantum pulse and dynamics / the same bits · linux-arm64 (pull_request) Successful in 1m40s
wai-quantum tensor-engine member / member · tensor engine absent (linux-arm64) (pull_request) Successful in 35s
WAI energy receipts / energy receipts · linux-arm64 (pull_request) Successful in 11m50s
wai-sink-android native sink library / the JNI layer and the platform-free half on the host JVM · linux-arm64 (pull_request) Successful in 2m50s
WAI conformance / independent verifiers · claims, JWP, key discovery and integer payloads (Python) (pull_request) Successful in 1h1m2s
Two of the other formats' tests write QIR 1 with crate::quantum_qir, which quantum_engine does not include, so the contract workflow's test build (quantum_engine with quantum_receipt, quantum_qec and quantum_noise) did not compile. They now carry #[cfg(feature = "quantum_qir")] and still run in the full build, where the formats workflow runs them. Two pulse tests seal their answers, so they carry #[cfg(feature = "quantum_receipt")], as error correction's sealing test does. Co-Authored-By: Claude Opus 5.5 <[email protected]>
wai-quantum-service smoke: paced within the client's window; the agent docs for pulse and other formats together
With the pulse and the other-format checks both in it, the smoke makes more submissions than a default window's 30, and the service refused the last with J030. Before each POST the script now reads where the client stands from GET /v1/health (RateLimit: r left, t seconds until one more is), and with none left it waits for one. Against production it takes longer and checks the same things. CI starts each instance it smokes with WAI_QSVC_CLIENT_BURST=60, so it never waits there. The agent docs (llms-full.txt, service-mcp.json) are blessed again from both branches' tools. Co-Authored-By: Claude Opus 5.5 <[email protected]>
wai-quantum views: the page rebuilt with the Studio's words for other formats, in the image CI rebuilds it in
The Studio's file open names QIR and jeff in locales/*/frame.json, which the views page is built from, so build-views --check refused the page. Rebuilt with wai/wai-quantum-views/build.sh in catthehacker/ubuntu:act-22.04 with Rust 1.98.0, as the views workflow rebuilds it. Co-Authored-By: Claude Opus 5.5 <[email protected]>
quantum-studio: open QIR and jeff files through the engine
"Open" takes .ll, .qir and .jeff beside .qasm: the engine reads the file to OpenQASM 3 in the page (engine_convert, in the worker), the program goes into the editor as a version from the file, and the line under it names the format and its version, the check (written back to its format and read again) and each of the reader's notes with its code. A module the reader refuses leaves the editor as it was, the refusal and its code in the status line. The desktop app answers the same request with a convert command. The Studio e2e opens a QIR module, a jeff module and a module its profile forbids; the desktop's test is pinned in CI. Co-Authored-By: Claude Opus 5.5 <[email protected]>
wai-quantum-cli: the stdio MCP run tools take a program's source
run_quantum_circuit, plan_quantum_circuit and run_on_target on the
command line's server take {"source": {"format", "program" |
"program_base64"}} in place of qasm, read to the job's qasm first, as the
job service's run tools now declare it too: one schema
(engine::formats::source_schema) and one refusal, the reader's code
before the job layer's. Reading a source is idempotent: a request whose
qasm is what its source reads to (one read already, or sealed) reads as
it is, and the service no longer refused its own expanded runs. The
tools-list tests call each with a source and with a refusal; the agent
docs are re-blessed.
Co-Authored-By: Claude Opus 5.5 <[email protected]>
wai-quantum: other formats bounded against hostile input, in CI
A jeff register's size reached Vec::with_capacity before the qubit cap, so one of 2^32 - 1 qubits asked for 34 GB: under wasm32-wasip2 the test written first trapped in qureg_op. It is now refused (Q111) before anything is made. The audit of every allocation and loop sized by the input: - the wire reader bounds every pointer, segment and list in 64 bits (a segment count of u32::MAX overflowed a 32-bit usize), and counts each list element against the words it may visit; - the jeff reader counts every register slot, array element (an array copied by setIndex included), call frame and condition term against one budget, caps arrays, values per function, operations run and gates written, shares conditions between copies, and no longer truncates a 64-bit size, index, selector or shift to fit; - the QIR reader no longer copies a block's lines on each visit, bounds the nesting of branches, the instructions run over every path and the state each path copies, and dedups a condition's reads; - a condition is at most 1 024 terms and 32 deep once written, a run of one operator written flat; - a conversion's check is not run past 262 144 gates applied or 4e9 amplitudes, and says so; both readers take modules of up to 16 MiB. tests/formats_mutation.rs mutates every QIR and jeff file of the conformance set from a fixed seed (45 153 inputs: bits flipped, files cut short and spliced, every length, count, offset and 32-bit field inflated) and holds each to converting or a refusal with a code of the table, within 20 s and 1 GiB measured by a counting allocator. wai-quantum-formats.yml runs it natively and under wasm32-wasip2 (a release build with overflow checks), the count pinned. Co-Authored-By: Claude Opus 5.5 <[email protected]>
wai-quantum: other formats documented, and a jeff module's gates capped
The engine, command line and service READMEs (and their translations) describe the readers and writers, convert, --from, convert_program, POST /v1/convert and a job's source; docs/formats.md, whose commands now run under the documentation check, says what each reader takes; the changelog has the section. A jeff module that unrolls to more gates than the reader holds is refused (Q210) instead of growing without bound. Co-Authored-By: Claude Opus 5.5 <[email protected]>
wai-quantum: other formats on every surface
The command line converts with `wai-quantum convert FILE --to
qasm|qir|jeff [--profile base|adaptive] [-o FILE] [--json]`, the
conversion checked and its notes on standard error, and every verb that
reads a program reads QIR (.ll, .qir) and jeff (.jeff) by its extension,
or by the global --from. Both MCP servers serve convert_program (the one
definition, from the engine), its answer the tools schema's new convert;
the job service answers POST /v1/convert within its bounds, and a job may
carry its program as {"source": {"format", "program" | "program_base64"}}
in place of qasm, read before anything else reads it. The Studio's engine
has engine_convert. The agent docs are regenerated; both smoke scripts
convert, run a QIR module and check a profile's refusal; the wasm32 and
native pins in wai-web-wasm.yml move to 19 and 27.
Co-Authored-By: Claude Opus 5.5 <[email protected]>
quantum-conformance: other formats, natively and under wasm32-wasip2
wai/quantum-conformance/formats/ holds a module for each construct, each with the program it must read to (a reference held by the equivalence ladder), the outcomes it gives, a round trip back to its format, the formats it writes to, and every refusal with its code and its place: the QIR specification's two example programs, every intrinsic, a QIR 1 module with typed pointers, the profiles' refusals; jeff modules built field by field from the schema; the jeff project's own structured benchmarks and examples, unchanged; and OpenQASM sources written to each format, the QIR written pinned by its BLAKE3. CI runs it in wai-quantum-formats.yml, with the readers' and writers' unit tests. The jeff reader now converts integers to floats and floats to integers, and a QIR conversion is checked against the type it gives. Co-Authored-By: Claude Opus 5.5 <[email protected]>
wai-quantum: QIR 2.x under its profiles, and jeff, read and written
engine::formats reads QIR (LLVM text, 1.x and 2.x) under the profile its entry point names: the base profile's rules and the adaptive profile's module flags are enforced, and what a profile forbids is refused with its code and line. Rotations at arbitrary angles are read at their exact doubles, with a note that the double-precision methods take them; a Clifford+T module stays on the bit-exact path. A program is written as QIR 2.0: the base profile, or the adaptive profile with forward branches for a program that measures in the middle or branches. jeff (format 0.3) is read and written through a small Cap'n Proto reader and writer of the crate's own: structured control flow decided or unrolled on reading, a switch on a measured bit written as a condition, Pauli-product rotations lowered exactly, custom gates read only by a standard name. Every refusal has a code (Q700 to Q721) and its place, and convert() checks each conversion with the equivalence ladder. Co-Authored-By: Claude Opus 5.5 <[email protected]>