/- MagicQ.Tests — cheap `decide` examples exercising the MagicQ checker on the library protocols. These are the first regression tests that the checker genuinely REJECTS malformed cultivation/distillation programs at the logical/type level, and ACCEPTS well-formed ones with the expected output/obligation summary. Mathlib-free; every lemma is a small `by decide`. -/ import MagicQ.Library.ReedMuller15 import MagicQ.Library.Cultivation namespace MagicQ.Tests open MagicQ TypeChecker -- the `by decide` protocol-checker tests reduce the full `checkProtocol` over the accumulated -- obligation list, which exceeds the default elaborator recursion depth (512). set_option maxRecDepth 4000 /-! ## §1. Standard 15-to-1 distillation (`rm15_to_1`). -/ -- (The old "fewer than 15 inputs is rejected" test was removed with the refactor: -- `measureSyndrome` is a GENERIC primitive that does NOT hardwire arity — "exactly 15" is now -- a property of the `rm15_to_1` LIBRARY protocol, not a primitive-level check. Input *basis* -- rejection (non-A-type) is still enforced — see §1·5 below.) /-- **RM15 resource arity (accept).** Exactly 15 compatible `T` resources check, producing exactly ONE output and consuming all 15 inputs (+ the output). -/ example : checks? ReedMuller15.rm15To1 = true := by decide /-- The accepted `rm15_to_1` produces exactly one output magic state. -/ example : ((checkProtocol ⟨[]⟩ ReedMuller15.rm15To1).toOption.map (·.outputs.length)) = some 1 := by decide /-- … and that output is a `T`-type state. -/ example : ((checkProtocol ⟨[]⟩ ReedMuller15.rm15To1).toOption.map (fun cp => cp.outputs.all (fun s => s.basis.tType))) = some true := by decide /-- … the 15 inputs are all consumed (16 consume-records: 15 inputs + the output). -/ example : ((checkProtocol ⟨[]⟩ ReedMuller15.rm15To1).toOption.map (·.consumed.length)) = some 16 := by decide /-- … and nothing leaks (every resource is consumed exactly once). -/ example : ((checkProtocol ⟨[]⟩ ReedMuller15.rm15To1).toOption.map (·.leaked)) = some [] := by decide /-- … the distillation threshold is recorded as a deferred quality claim (surfaced from the library protocol's output quality, not hardwired into the primitive). -/ example : ((checkProtocol ⟨[]⟩ ReedMuller15.rm15To1).toOption.map (fun cp => cp.deferred.contains (.qualityClaim "ε < 0.141"))) = some true := by decide /-- … the NON-Pauli Bravyi–Kitaev `A`-type syndrome (`η`) decoding is recorded as a deferred obligation by `measureSyndrome` — the binary CSS surrogate does NOT prove it. -/ example : ((checkProtocol ⟨[]⟩ ReedMuller15.rm15To1).toOption.map (fun cp => cp.deferred.contains (.syndromeDecoding "rm15.eta"))) = some true := by decide /-- … and the 15 consumed input carriers are RETIRED — `finalCarriers` has NO live carrier (every input carrier + the output carrier is retired by op-end). -/ example : ((checkProtocol ⟨[]⟩ ReedMuller15.rm15To1).toOption.map (fun cp => (cp.finalCarriers.filter (fun p => p.2.live)).length)) = some 0 := by decide /-! ## §1·5. 15-to-1 input basis: only standard `|A₀⟩ = T|+⟩` (`.T`/`.A0`). -/ /-- 15 inputs of a single `basis`, distilled to one `.T` output. -/ def distillWith (basis : MagicBasis) : Protocol := { name := "distill_with" ops := ((List.range 15).map (fun i => ProtocolOp.inject .supplied basis i (.external "noisy-T-input") i {})) ++ [ .measureSyndrome (List.range 15) 15 15 (.external "RM15") {} [] , .output 15 ] } /-- **Valid `.T` inputs are accepted.** -/ example : checks? (distillWith .T) = true := by decide /-- **Valid `.A0` inputs are accepted** (`|A₀⟩ = T|+⟩`, the canonical BK input). -/ example : checks? (distillWith .A0) = true := by decide /-- **`.Tdg` inputs are REJECTED** — the conjugate `T†` is not silently relabelled to `.T`. -/ example : checks? (distillWith .Tdg) = false := by decide /-- **`.Y` inputs are REJECTED** (wrong magic family). -/ example : checks? (distillWith .Y) = false := by decide /-! ## §2. Magic-state cultivation (`cultivate_T`). -/ /-- **Cultivation (accept).** The default cultivation protocol checks. -/ example : checks? Cultivation.defaultT = true := by decide /-- … producing exactly one output magic state. -/ example : ((checkProtocol ⟨[]⟩ Cultivation.defaultT).toOption.map (·.outputs.length)) = some 1 := by decide /-- … and recording the deferred GROWTH fault-distance obligation (d1 = 5). -/ example : ((checkProtocol ⟨[]⟩ Cultivation.defaultT).toOption.map (fun cp => cp.deferred.contains (.growthFaultDistance 0 5))) = some true := by decide /-- … and the deferred ESCAPE graft obligation (d2 = 15). -/ example : ((checkProtocol ⟨[]⟩ Cultivation.defaultT).toOption.map (fun cp => cp.deferred.contains (.escapeGraft 0 15))) = some true := by decide /-- … and the external-carrier obligations for the un-materialised color codes. -/ example : ((checkProtocol ⟨[]⟩ Cultivation.defaultT).toOption.map (fun cp => cp.deferred.contains (.externalCarrier "ColorCode(3)" "injection carrier not materialised in ChainQ"))) = some true := by decide /-- **Cultivation (reject): premature output.** Outputting BEFORE growth/escape establish the promised fault/code distances is rejected. -/ example : checks? (Cultivation.cultivateTPremature Cultivation.defaultSpec) = false := by decide /-- **Cultivation uses the NON-Pauli H_XY (T-basis) double-check, not `.Z`**, via the DEFERRED-assumption path (`assumeLogicalCheck`) — the AST carries the `hxy` axis (faithful to 2409.17595), never a Pauli letter, and never the validated path. -/ example : Cultivation.defaultT.ops.any (fun op => match op with | .assumeLogicalCheck _ obs _ _ => decide (obs.axis = .hxy) | _ => false) = true := by decide /-- … and the checker records the deferred-assumption check EXPLICITLY in `CheckedProtocol.deferred` with its FULL data (carrier, observable, detector, justification), not free-text only — ChainQ cannot yet prove the carrier admits a transversal H_XY, but the obligation is machine-readable. -/ example : ((checkProtocol ⟨[]⟩ Cultivation.defaultT).toOption.map (fun cp => cp.deferred.contains (.assumedLogicalCheck 0 { idx := 0, axis := .hxy } "cultivate.double-check" "transversal H_XY=(X+Y)/√2 double-check (GHZ-controlled), 2409.17595"))) = some true := by decide /-- … and a cultivation quality `deferred` claim is SURFACED into the checked summary (`MagicQuality.deferred` → `Obligation.qualityClaim`), not just left on the value. -/ example : ((checkProtocol ⟨[]⟩ Cultivation.defaultT).toOption.map (fun cp => cp.deferred.contains (.qualityClaim "fault distance d1 established by Bell-boundary growth"))) = some true := by decide /-! ## §2·5. `r1`/`r2` are OPERATIONAL ops, not just `params` metadata. -/ /-- A spec with distinct idling rounds `r1=7`, `r2=9`. -/ def spec79 : Cultivation.CultivationSpec := { Cultivation.defaultSpec with r1 := 7, r2 := 9 } /-- **`r1` drives the grafted-code idling `stabilize`** — `r1=7` ⇒ a `stabilizationRounds 0 7` obligation. -/ example : ((checkProtocol ⟨[]⟩ (Cultivation.cultivateT spec79)).toOption.map (fun cp => cp.deferred.contains (.stabilizationRounds 0 7))) = some true := by decide /-- **`r2` drives the final-matchable idling `stabilize`** — `r2=9` ⇒ a `stabilizationRounds 0 9` obligation. -/ example : ((checkProtocol ⟨[]⟩ (Cultivation.cultivateT spec79)).toOption.map (fun cp => cp.deferred.contains (.stabilizationRounds 0 9))) = some true := by decide /-- … and the default (`r1=r2=5`) does NOT record `r1=7` rounds — the parameter genuinely changes the op structure, it is not dead metadata. -/ example : ((checkProtocol ⟨[]⟩ Cultivation.defaultT).toOption.map (fun cp => cp.deferred.contains (.stabilizationRounds 0 7))) = some false := by decide /-- … and the explicit escape TRANSITION into the final matchable code (distance d2=15) is recorded as its own obligation, distinct from the initial `escapeGraft`. -/ example : ((checkProtocol ⟨[]⟩ Cultivation.defaultT).toOption.map (fun cp => cp.deferred.contains (.escapeTransition 0 15))) = some true := by decide /-! ## §3. Postselection scope. -/ /-- A standalone protocol postselecting on an UNKNOWN syndrome. -/ def badPostselect : Protocol := { name := "bad_postselect" ops := [ .postselect (.syndromeEq "no-such-syndrome" false) ] } /-- **Postselection scope (reject).** A postselection on an unproduced detector/syndrome is rejected. -/ example : checks? badPostselect = false := by decide /-- A protocol whose postselection DOES refer to a produced syndrome checks. -/ def goodPostselect : Protocol := { name := "good_postselect" ops := [ .inject .unitary .T 0 (.external "C") 0 {} , .checkLogical 0 { idx := 0, axis := .pauli .Z } "syn" , .postselect (.syndromeEq "syn" false) , .discard 0 ] } example : checks? goodPostselect = true := by decide /-- **External-carrier deferral is EXPLICIT, not silent.** A protocol on an `external` carrier checks, but ONLY with the external carrier recorded as a deferred obligation in `CheckedProtocol.deferred`. -/ example : ((checkProtocol ⟨[]⟩ goodPostselect).toOption.map (fun cp => cp.deferred.contains (.externalCarrier "C" "injection carrier not materialised in ChainQ"))) = some true := by decide /-! ## §4. Linearity and well-formedness corner cases. -/ /-- A logical check addressing a NON-exposed logical (idx ≥ k) is rejected. -/ def badObservable : Protocol := { name := "bad_observable" ops := [ .inject .unitary .T 0 (.external "C") 0 {} , .checkLogical 0 { idx := 3, axis := .pauli .Z } "syn" -- carrier exposes only idx 0 , .discard 0 ] } example : checks? badObservable = false := by decide /-- DOUBLE-output of the same resource is rejected (linearity: consumed twice). -/ def doubleOutput : Protocol := { name := "double_output" ops := [ .inject .unitary .T 0 (.external "C") 0 {} , .output 0 , .output 0 ] } example : checks? doubleOutput = false := by decide /-- A duplicate carrier id is rejected. -/ def dupCarrier : Protocol := { name := "dup_carrier" ops := [ .inject .unitary .T 0 (.external "C") 0 {} , .inject .unitary .T 0 (.external "C") 1 {} -- carrier 0 reused , .discard 0 ] } example : checks? dupCarrier = false := by decide /-- A distillation output claiming a code distance that NO op establishes is REJECTED — the output codeDistance gate is a genuine cross-check, not the tautology `d ≤ d` (distillation never self-stamps its own claimed distance). -/ def distillInflatedDistance : Protocol := { name := "distill_inflated_distance" ops := ReedMuller15.inputInjections ++ [ .measureSyndrome (List.range 15) 15 15 (.external "RM15") { codeDistance := some 9999 } [] , .output 15 ] } example : checks? distillInflatedDistance = false := by decide /-- **Linearity: leaks fail by default.** Two states injected, only one output — the un-disposed state is a `resourceLeak` ERROR, so the protocol is REJECTED. -/ def leaky : Protocol := { name := "leaky" ops := [ .inject .unitary .T 0 (.external "C") 0 {} , .inject .unitary .T 1 (.external "C2") 1 {} , .output 0 ] } -- resource 1 never consumed example : checks? leaky = false := by decide /-- … disposing BOTH live states (output one, discard the other) checks. -/ def notLeaky : Protocol := { leaky with name := "not_leaky", ops := leaky.ops ++ [ .discard 1 ] } example : checks? notLeaky = true := by decide /-! ## §4·4. Carrier lifecycle: output/discard RETIRES the carrier. -/ /-- **`inject; output; grow` is REJECTED** — once a state is returned, its carrier is no longer live, so the later `grow` fails (`carrierNotLive`). -/ def outputThenGrow : Protocol := { name := "output_then_grow" ops := [ .inject .unitary .T 0 (.external "C") 0 {} , .output 0 , .grow 0 (.external "D") 5 "g" ] } example : checks? outputThenGrow = false := by decide /-- **`inject; discard; checkLogical` is REJECTED** — `discard` also retires the carrier. -/ def discardThenCheck : Protocol := { name := "discard_then_check" ops := [ .inject .unitary .T 0 (.external "C") 0 {} , .discard 0 , .checkLogical 0 { idx := 0, axis := .pauli .Z } "c" ] } example : checks? discardThenCheck = false := by decide /-! ## §4·5. Ownership and aliasing: block-backed carriers must be live + owned. -/ /-- A minimal valid one-logical-qubit block (validity ignores ownership/liveness). -/ def bareQubit (o : Owned) : Block := { n := 1, stab := [], lx := [[true, false]], lz := [[false, true]], own := o } /-- Γ holding a single BORROWED block. -/ def borrowedEnv : TypedEnv := ⟨[⟨bareQubit .borrowed, by decide⟩]⟩ /-- Γ holding a single OWNED block. -/ def ownedEnv : TypedEnv := ⟨[⟨bareQubit .owned, by decide⟩]⟩ /-- Inject onto the (block 0) carrier, then dispose it. -/ def injectOntoBlock : Protocol := { name := "inject_onto_block" ops := [ .inject .unitary .T 0 (.block 0) 0 {}, .discard 0 ] } /-- **Block-backed op on a BORROWED block is REJECTED** (reuses `TypeError.notOwned`). -/ example : checksIn? borrowedEnv injectOntoBlock = false := by decide /-- … the SAME op on an OWNED block checks. -/ example : checksIn? ownedEnv injectOntoBlock = true := by decide /-- **Block aliasing is REJECTED.** Two LIVE MagicQ carriers must not reference the same underlying `.block id` (reuses `TypeError.clone`). -/ def aliasBlock : Protocol := { name := "alias_block" ops := [ .inject .unitary .T 0 (.block 0) 0 {} , .inject .unitary .T 1 (.block 0) 1 {} -- block 0 already held by a live carrier , .discard 0, .discard 1 ] } example : checksIn? ownedEnv aliasBlock = false := by decide /-- … but a block FREED by a prior `discard` may be re-claimed (liveness transfers). -/ def reuseBlock : Protocol := { name := "reuse_block" ops := [ .inject .unitary .T 0 (.block 0) 0 {} , .discard 0 -- retires carrier 0, freeing block 0 , .inject .unitary .T 1 (.block 0) 1 {} , .discard 1 ] } example : checksIn? ownedEnv reuseBlock = true := by decide /-- **`grow` into a `.block` TARGET is REJECTED** — the v1 AST carries no switch certificate, so a real block-backed switch cannot be validated; a `.block` target must not be silently treated as a code template / aliased in. -/ def growIntoBlock : Protocol := { name := "grow_into_block" ops := [ .inject .unitary .T 0 (.external "C") 0 {}, .grow 0 (.block 0) 5 "g", .discard 0 ] } /-- grow into a BORROWED `.block` → rejected. -/ example : checksIn? borrowedEnv growIntoBlock = false := by decide /-- grow into an OWNED `.block` → still rejected (no `SwitchCert` path implemented). -/ example : checksIn? ownedEnv growIntoBlock = false := by decide /-- **`graft` into a `.block` TARGET is REJECTED** too (borrowed shown). -/ def graftIntoBlock : Protocol := { name := "graft_into_block" ops := [ .inject .unitary .T 0 (.external "C") 0 {}, .graft 0 (.block 0) 5 "g", .discard 0 ] } example : checksIn? borrowedEnv graftIntoBlock = false := by decide /-- **A live carrier on `.block 0`, then ANOTHER carrier `grow`s into `.block 0`, is REJECTED** — no silent `.block` target aliasing. -/ def growAliasLiveBlock : Protocol := { name := "grow_alias_live_block" ops := [ .inject .unitary .T 0 (.block 0) 0 {} -- carrier 0 lives on (owned) block 0 , .inject .unitary .T 1 (.external "C") 1 {} , .grow 1 (.block 0) 5 "g" -- carrier 1 grows INTO block 0 → rejected , .discard 0, .discard 1 ] } example : checksIn? ownedEnv growAliasLiveBlock = false := by decide /-! ## §4·6. Non-Pauli `hxy` requires the explicit deferred-assumption path. -/ /-- **`.hxy` via the validated `checkLogical` path on a bare block is REJECTED** — the type system cannot prove a transversal H_XY; it must use `assumeLogicalCheck`. -/ def hxyOnBareBlock : Protocol := { name := "hxy_on_bare_block" ops := [ .inject .unitary .T 0 (.block 0) 0 {} , .checkLogical 0 { idx := 0, axis := .hxy } "c" , .discard 0 ] } example : checksIn? ownedEnv hxyOnBareBlock = false := by decide /-- … while the SAME `.hxy` check via `assumeLogicalCheck` is ACCEPTED and recorded as an explicit deferred obligation in `CheckedProtocol.deferred`. -/ def hxyViaAssume : Protocol := { name := "hxy_via_assume" ops := [ .inject .unitary .T 0 (.external "C") 0 {} , .assumeLogicalCheck 0 { idx := 0, axis := .hxy } "c" "assumed H_XY" , .discard 0 ] } example : checks? hxyViaAssume = true := by decide /-- … recording the obligation with FULL data: carrier `0`, observable `{idx 0, hxy}`, detector `"c"`, and justification — not free-text only. -/ example : ((checkProtocol ⟨[]⟩ hxyViaAssume).toOption.map (fun cp => cp.deferred.contains (.assumedLogicalCheck 0 { idx := 0, axis := .hxy } "c" "assumed H_XY"))) = some true := by decide /-! ## §5. Obligation discharge (pairing MagicQ outputs with compiler obligations). -/ /-- A produced `T` output DISCHARGES a mixed-IR `tGate` obligation — so either `cultivate_T` or `rm15_to_1` can supply a logical `T`-gate's magic state. -/ example : dischargesObligation { basis := .T, carrier := 0 } { kind := .tGate, target := ⟨0, 0⟩ } = true := by decide example : dischargesObligation { basis := .A0, carrier := 0 } { kind := .tGate, target := ⟨0, 0⟩ } = true := by decide /-- A non-`T`-type (`Y`) state does NOT discharge a `tGate` obligation. -/ example : dischargesObligation { basis := .Y, carrier := 0 } { kind := .tGate, target := ⟨0, 0⟩ } = false := by decide end MagicQ.Tests