Skip to content

Commit 6426f4f

Browse files
Merge pull request #29 from hyperpolymath/reinforce/vclut-25-phase5b-idris-decoder
vcl-ut #25 P5b (step 2): certified Idris wire decoder + cross-language Refl conformance
2 parents 8006c35 + 5ab86b0 commit 6426f4f

12 files changed

Lines changed: 1163 additions & 58 deletions

File tree

.github/workflows/proof-corpus.yml

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -64,7 +64,8 @@ jobs:
6464
src/core/Levels.idr src/core/Checker.idr \
6565
src/core/Composition.idr src/core/Epistemic.idr \
6666
src/interface/abi/Types.idr src/interface/abi/Layout.idr \
67-
src/interface/abi/LayoutProofs.idr"
67+
src/interface/abi/LayoutProofs.idr \
68+
src/interface/WireDecode.idr src/interface/WireConformance.idr"
6869
if grep -nE '\b(believe_me|really_believe_me|assert_total|assert_smaller|idris_crash|postulate|sorry)\b' \
6970
$files | grep -vE ':\s*(--|\|\|\|)' ; then
7071
echo "::error::proof-escape symbol found in the Phase-1 corpus"

CHANGELOG.md

Lines changed: 24 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -12,13 +12,14 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
1212

1313
### Verified
1414

15-
**VclTotal proof corpus — Phase 0→4 remediation** (2026-05-18/19,
16-
hyperpolymath/standards#124). The `src/core/**` Idris2 corpus, which at
15+
**VclTotal proof corpus — Phase 0→4 remediation + Phase 5 boundary
16+
reinforcement** (2026-05-18/19, hyperpolymath/standards#124,
17+
hyperpolymath/vcl-ut#25). The `src/core/**` Idris2 corpus, which at
1718
Phase 0 did not compile and had never been machine-checked, is now
1819
CI-gated and green:
1920

2021
- `verification/proofs/vclut-core.ipkg` builds clean under idris2 0.8.0
21-
(`idris2 --build`, exit 0, `%default total`) as **10 modules**, with
22+
(`idris2 --build`, exit 0, `%default total`) as **12 modules**, with
2223
**zero proof-escape symbols** (no `believe_me`/`postulate`/`assert_*`/
2324
`idris_crash`/`sorry`), enforced by `.github/workflows/proof-corpus.yml`.
2425
- Phase 1 (#21): corpus resurrection — `ABI.Types`/`Grammar` repaired,
@@ -33,6 +34,26 @@ CI-gated and green:
3334
bounds) + L6–L10 `composeJoin` closure (`l6..l9Compose`,
3435
`epiStructJoin`); L10 acyclicity carried by the explicit
3536
`JoinSideCondition` (provably non-closed, not faked).
37+
- Phase 5 / vcl-ut#25 (boundary reinforcement): trusted Rust/SPARK-grade
38+
parser (P5a, #26) + deterministic versioned wire codec (P5b step 1,
39+
#28); **P5b step 2 (this change)**`VclTotal.Interface.WireDecode`,
40+
a total (`%default total`, zero proof-escape) decoder of the v1 wire
41+
format into the certified `Statement`, recursion bounded by an
42+
input-length fuel `Nat`; `VclTotal.Interface.WireConformance` proves
43+
it byte-for-byte conformant with the Rust `to_wire` encoder by `Refl`
44+
on golden fixtures (regeneration oracle:
45+
`src/interface/parse/tests/conformance_emit.rs`). The C-ABI
46+
`Statement` marshalling *decode* side is now certified. Disclosed:
47+
the NaN *payload* is not preserved across the Idris `Double` boundary
48+
(finite + infinite values bit-exact; Rust proptest remains the
49+
exhaustive float witness). OWED: **P5c — typed-wasm PCC transport**
50+
(proof term + checker kernel the consumer re-runs; *re-checkable*,
51+
TCB = checker kernel; the estate-aligned objective — the `ffi/zig`
52+
fail-closed shim is retained only as the C-ABI attestation
53+
*fallback*, not the endpoint); **P5d** — the signed-attestation
54+
fallback contract for C-only consumers. Re-checkable transport is
55+
impossible only over a C ABI, not over typed-wasm (two-tier boundary
56+
model: `verification/proofs/VERIFICATION-STANCE.adoc`).
3657

3758
`verification/proofs/VERIFICATION-STANCE.adoc` is the authoritative,
3859
precisely-scoped catalogue (residual OWED items disclosed, not masked).

PROOF-NEEDS.md

Lines changed: 19 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -6,8 +6,8 @@
66
- **LOC**: ~8,000
77
- **Languages**: Rust, ReScript, Idris2, Zig
88
- **Existing ABI proofs**: `src/interface/abi/*.idr` + domain-specific Idris2: `src/core/Checker.idr`, `Grammar.idr`, `Levels.idr`, `Schema.idr`, `Composition.idr`
9-
- **Machine-verified**: the full `VclTotal` proof corpus — `verification/proofs/vclut-core.ipkg` builds clean under idris2 0.8.0 (`idris2 --build`, exit 0, `%default total`, **zero proof-escape symbols**, CI-gated by `.github/workflows/proof-corpus.yml`) as **10 modules** (`ABI.{Types,Layout,LayoutProofs}` + `Core.{Grammar,Schema,Decide,Levels,Checker,Composition,Epistemic}`), plus the self-contained `verification/proofs/SafetyL4Model.idr` (`--check`, exit 0). Phases 1–3 are on `origin/main` (PRs #21/#22/#23); Phase 4 (`LayoutProofs` + L6–L10 `composeJoin` closure) is **PR #24**, pending merge.
10-
- **Status (Phase 0 → 4 RESOLVED, honestly)**: the Phase-0 blockers are fixed, not faked — the corpus compiles and is machine-checked; `ABI.Types`/`Grammar` errors repaired; **L2/L3/L5 de-vacuized** (Phase 2, evidence-carrying predicates over `Core.Decide`); all ten levels carry `checkLevelNSound` and `Checker.certifyAt`/`certifyRequested` assemble a genuine dependent `SafetyCertificate` (Phase 3); the Zig FFI is no longer a fabricating stub — it is **fail-closed** with a proof-gated `Checker.certifiedLevel` mint (Phase 3d). Remaining honest gaps are precisely scoped (FFI proof-transport, string→`Statement` parser, L3 subquery/heuristic scoping, L9/L10 predicate depth, the additive↔ceil `alignUp` sliver). `verification/proofs/VERIFICATION-STANCE.adoc` is the authoritative, proof-backed catalogue and takes precedence over this file.
9+
- **Machine-verified**: the full `VclTotal` proof corpus — `verification/proofs/vclut-core.ipkg` builds clean under idris2 0.8.0 (`idris2 --build`, exit 0, `%default total`, **zero proof-escape symbols**, CI-gated by `.github/workflows/proof-corpus.yml`) as **12 modules** (`ABI.{Types,Layout,LayoutProofs}` + `Core.{Grammar,Schema,Decide,Levels,Checker,Composition,Epistemic}` + `Interface.{WireDecode,WireConformance}`), plus the self-contained `verification/proofs/SafetyL4Model.idr` (`--check`, exit 0). Phases 1–4 are on `origin/main` (PRs #21/#22/#23/#24); Phase 5 / vcl-ut#25 (trusted Rust parser P5a #26, wire codec P5b-step-1 #28, **certified Idris wire decoder + cross-language `Refl` conformance** P5b-step-2) reinforces the FFI boundary.
10+
- **Status (Phase 0 → 4 RESOLVED, honestly; Phase 5 boundary reinforcement in progress)**: the Phase-0 blockers are fixed, not faked — the corpus compiles and is machine-checked; `ABI.Types`/`Grammar` errors repaired; **L2/L3/L5 de-vacuized** (Phase 2, evidence-carrying predicates over `Core.Decide`); all ten levels carry `checkLevelNSound` and `Checker.certifyAt`/`certifyRequested` assemble a genuine dependent `SafetyCertificate` (Phase 3); the Zig FFI is no longer a fabricating stub — it is **fail-closed** with a proof-gated `Checker.certifiedLevel` mint (Phase 3d). **Phase 5 (vcl-ut#25)**: a trusted Rust/SPARK-grade parser + a deterministic versioned wire codec exist, and the *decode* side of the C-ABI `Statement` marshalling is now **certified** — `VclTotal.Interface.WireDecode` is a total (zero-escape) decoder proven byte-for-byte conformant with the Rust encoder by `Refl` (`WireConformance`). Remaining honest gaps are precisely scoped (P5c = typed-wasm PCC proof-transport — proof term + checker kernel the consumer re-runs, *re-checkable*, the estate-aligned objective; the C-ABI/Zig shim retained only as the fail-closed attestation fallback; P5d = signed-attestation *fallback* contract for C-only consumers; plus L3 subquery/heuristic scoping; L9/L10 predicate depth; the additive↔ceil `alignUp` sliver; the disclosed NaN-payload limitation of the Idris `Double` boundary). Re-checkable transport is impossible *only* over a C ABI, not over the estate's typed-wasm target. `verification/proofs/VERIFICATION-STANCE.adoc` is the authoritative, proof-backed catalogue and takes precedence over this file.
1111

1212
## What Needs Proving
1313

@@ -44,6 +44,23 @@
4444
- The *trusted* boundary parser is the Rust/SPARK-grade
4545
`src/interface/parse` crate (`vcltotal-parse`, P5a of vcl-ut#25),
4646
which mirrors `Grammar.idr` and feeds the certifier across the C-ABI.
47+
Its `wire.rs` codec (P5b step 1) serialises the parsed `Statement`
48+
to a deterministic versioned binary format
49+
(`src/interface/parse/WIRE-FORMAT.adoc`).
50+
- The *certified* receiver of that format is
51+
`VclTotal.Interface.WireDecode` (P5b step 2): a total, zero-escape
52+
Idris decoder into the certified `Statement`, proven byte-for-byte
53+
conformant with the Rust encoder by `Refl` in
54+
`VclTotal.Interface.WireConformance`. The marshalling seam's *decode*
55+
side is therefore now machine-verified. **P5c** (the estate-aligned
56+
objective): transport the certificate over the **typed-wasm** target
57+
as a proof term + a small checker kernel the consumer re-runs —
58+
proof-carrying code, *re-checkable*, TCB = checker kernel + typed-wasm
59+
verifier (re-checkable transport is impossible only over a C ABI; the
60+
`ffi/zig` fail-closed shim is retained only as the C-ABI attestation
61+
fallback). **P5d** (fallback tier): the signed-attestation contract
62+
for consumers reachable only over C. Both OWED; see the two-tier
63+
boundary model in `verification/proofs/VERIFICATION-STANCE.adoc`.
4764
- Optional future work: prove the ReScript frontend faithfully tracks
4865
the Idris2 grammar (low priority; it is a convenience frontend, not a
4966
trust anchor).

src/interface/WireConformance.idr

Lines changed: 101 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,101 @@
1+
-- SPDX-License-Identifier: PMPL-1.0-or-later
2+
-- Copyright (c) 2026 Jonathan D.A. Jewell <j.d.a.jewell@open.ac.uk>
3+
4+
||| VCL-total Interface — Cross-language Wire Conformance (P5b step 2)
5+
|||
6+
||| Machine-checked proof that the certified Idris decoder
7+
||| (`VclTotal.Interface.WireDecode.fromWire`) agrees, byte-for-byte,
8+
||| with the trusted Rust encoder (`src/interface/parse/src/wire.rs`
9+
||| `to_wire`) on shared golden fixtures.
10+
|||
11+
||| Each `goldenN` is the EXACT `to_wire` image emitted by the Rust
12+
||| regeneration oracle `src/interface/parse/tests/conformance_emit.rs`
13+
||| (run that test with `--nocapture` to re-derive these literals; the
14+
||| literals below are injected verbatim from its output, never
15+
||| hand-transcribed). The corresponding
16+
||| `conformN : fromWire goldenN = Right expectedN` is proved by `Refl`:
17+
||| the corpus build only succeeds if the total decoder, evaluated at
18+
||| compile time on the Rust bytes, reduces to exactly the expected
19+
||| certified `Statement`. This is WIRE-FORMAT.adoc's conformance
20+
||| contract discharged as a proof, not a runtime test — no
21+
||| proof-escape, %default total.
22+
|||
23+
||| Fixtures: F1 minimal; F2 exercises strings / ints / bools / agents /
24+
||| options / lists / a nested comparison expression and every extension
25+
||| clause; F3 the float path with the exactly-representable `2.5`
26+
||| (arbitrary-`f64` bit-exactness — incl. the NaN payload, which the
27+
||| Idris `Double` boundary does NOT preserve, by disclosure — is the
28+
||| Rust proptest's job: `wire.rs::golden_bit_exact_floats`).
29+
30+
module VclTotal.Interface.WireConformance
31+
32+
import VclTotal.ABI.Types
33+
import VclTotal.Core.Grammar
34+
import VclTotal.Interface.WireDecode
35+
36+
%default total
37+
38+
-- ── F1: minimal — SELECT * FROM STORE "main", level SchemaBound ──────
39+
40+
golden1 : List Bits8
41+
golden1 = [86,67,76,87,1,0,1,0,0,0,3,2,4,0,0,0,109,97,105,110,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1]
42+
43+
expected1 : Statement
44+
expected1 =
45+
MkStatement [SelStar] (SrcStore "main")
46+
Nothing [] Nothing [] Nothing Nothing
47+
Nothing Nothing Nothing Nothing Nothing
48+
SchemaBound
49+
50+
conform1 : fromWire WireConformance.golden1 = Right WireConformance.expected1
51+
conform1 = Refl
52+
53+
-- ── F2: strings/ints/bools/agents/options/lists/nested expr + every
54+
-- extension clause; level EpistemicSafe ─────────────────────────
55+
56+
golden2 : List Bits8
57+
golden2 = [86,67,76,87,1,0,2,0,0,0,0,0,2,0,0,0,105,100,3,0,6,0,0,0,117,117,105,100,45,49,1,2,0,0,1,1,0,0,0,120,1,1,7,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,5,1,0,0,0,116,1,1,10,0,0,0,0,0,0,0,0,1,1,1,0,0,0,119,1,2,1,1,3,0,0,0,0,0,0,0,1,1,1,2,0,0,0,0,1,5,0,0,0,108,101,97,110,52,1,0,0,0,0,0,1,3,1,10]
58+
59+
expected2 : Statement
60+
expected2 =
61+
MkStatement
62+
[SelField (MkFieldRef Graph "id"), SelStar]
63+
(SrcOctad "uuid-1")
64+
(Just (ECompare Eq
65+
(EField (MkFieldRef Vector "x") TAny)
66+
(ELiteral (LitInt 7) TAny)
67+
TAny))
68+
[]
69+
Nothing
70+
[(MkFieldRef Temporal "t", True)]
71+
(Just 10)
72+
Nothing
73+
(Just (ProofWitness "w"))
74+
(Just EffReadWrite)
75+
(Just (VerAtLeast 3))
76+
(Just LinUseOnce)
77+
(Just (EpClause
78+
[AgEngine, AgProver "lean4"]
79+
[EpReqKnows AgEngine (ELiteral (LitBool True) TAny)]))
80+
EpistemicSafe
81+
82+
conform2 : fromWire WireConformance.golden2 = Right WireConformance.expected2
83+
conform2 = Refl
84+
85+
-- ── F3: float path — WHERE 2.5 (exactly representable), level
86+
-- ParseSafe. Witnesses the IEEE-754 reconstruction reduces to
87+
-- the identical primitive `Double` under the evaluator. ─────────
88+
89+
golden3 : List Bits8
90+
golden3 = [86,67,76,87,1,0,1,0,0,0,3,2,1,0,0,0,115,1,1,2,0,0,0,0,0,0,4,64,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0]
91+
92+
expected3 : Statement
93+
expected3 =
94+
MkStatement [SelStar] (SrcStore "s")
95+
(Just (ELiteral (LitFloat 2.5) TAny))
96+
[] Nothing [] Nothing Nothing
97+
Nothing Nothing Nothing Nothing Nothing
98+
ParseSafe
99+
100+
conform3 : fromWire WireConformance.golden3 = Right WireConformance.expected3
101+
conform3 = Refl

0 commit comments

Comments
 (0)