Skip to content

Commit 238f194

Browse files
hyperpolymathclaude
andcommitted
ambientops #127: rewrite stance to verified truth — SPARK is theatre
Adversarial re-verification (gnat/gnatprove + 2-agent static SPARK-RM swarm, dynamically spot-confirmed on origin/main) found PR#48's 'Strong' SPARK coverage matrix comprehensively FALSE: - snapshot_manager.adb:4 pragma SPARK_Mode(Off) — entire rollback body unanalysed; never compiled (call@:93 of fn declared@:145, no fwd decl); headline Post rests on reversibility_types.adb:31 System_State_Matches_Snapshot = hardcoded 'return True'. - safety_boundary.adb:6 SPARK_Mode(Off); safety_boundary.ads:78+ Safe_* are functions with in Out param (illegal SPARK), no escape; no privilege/scope/bound model exists (only Is_Valid(Token)). - safety_invariant.ads legal SPARK but tautologies over ghost state the real (SPARK_Mode Off) path never updates. Original 2026-05-18 audit ('SPARK theatre') was right; #48 was wrong. RUST-SPARK-STANCE.adoc: false coverage matrix flagged SUPERSEDED; added verified-correction section with file:line evidence, what this PR genuinely delivers, and the precisely-scoped OWED programme. Refs hyperpolymath/standards#124 Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
1 parent 9082980 commit 238f194

1 file changed

Lines changed: 80 additions & 19 deletions

File tree

RUST-SPARK-STANCE.adoc

Lines changed: 80 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -38,6 +38,11 @@ one deliberate `SPARK_Mode (Off)` are documented honestly under
3838

3939
== SPARK contract coverage (`total-update/ada/dnfinition/src`)
4040

41+
WARNING: ⚠️ The matrix in this section is **FALSE and SUPERSEDED** — see
42+
<<verified-correction>>. It was written from a source read that never
43+
compiled and was never `gnatprove`-checked. Retained only to show what
44+
was claimed vs. what verification found.
45+
4146
Contracts in SPARK live on the package *spec* (`.ads`), not the body
4247
(`.adb`); body files carrying zero `Pre/Post` is correct, not theatre.
4348
Spec-level coverage:
@@ -93,25 +98,81 @@ behaviour can destabilise the host. The proof-relevant surface, per
9398
The Rust crates sit on the application side of this seam; they are never
9499
the ABI/FFI boundary, satisfying §"Rust is never the ABI".
95100

96-
[#honest-gaps]
97-
== Honest gaps
98-
99-
* *`backend_interface.ads` (OWED).* This is a pure abstract interface
100-
(`type Package_Manager_Backend is interface;`, ~20 `is abstract`
101-
primitives: `Install`, `Remove`, `Upgrade`, `Search`, …). It carries
102-
no class-wide contracts, so `gnatprove` cannot propagate obligations
103-
to the `backend_guix`/`backend_nix` implementations. Adding
104-
`Pre'Class`/`Post'Class` to the safety-relevant primitives (notably
105-
`Install`/`Remove`/`Upgrade` result states and `Is_Available`
106-
preconditions) is the principal remaining SPARK proof obligation.
107-
Tracked under `standards#124` / `#127`.
108-
* *`plugin_registry.ads` (weak).* One contract only; strengthen
109-
registration post-state. Lower priority than the interface.
110-
* *`reversibility_types.ads` is deliberately `SPARK_Mode (Off)`.* The
111-
in-file comment documents the reason (a record-component / type-name
112-
clash on `Rollback_Result.Snapshot_ID`); SPARK is re-enabled once a
113-
genuine proof obligation justifies resolving the clash. This is an
114-
honest, documented deferral — explicitly *not* the "theatre" pattern.
101+
[#verified-correction]
102+
== ⚠️ Verified correction (standards#127, 2026-05-18) — supersedes the coverage matrix above
103+
104+
WARNING: An adversarial re-verification (gnat / gnatprove + 2-agent
105+
static SPARK-RM swarm, then dynamically spot-confirmed on `origin/main`)
106+
found that the "SPARK contract coverage" matrix and the "real,
107+
*non-theatrical* SPARK/Ada" claim earlier in this document are *false*.
108+
They were written from a source read that **never compiled and was never
109+
`gnatprove`-checked**. The original 2026-05-18 estate audit ("`SPARK_Mode
110+
On`, theatre") was *correct*; the PR#48 reframing was the inaccuracy.
111+
The whole `total-update/ada/dnfinition` SPARK story is *theatre*:
112+
113+
* *`backend_interface.ads` — never compiled; illegal SPARK.*
114+
`Transaction_Item.Package` used an Ada **reserved word** as a field
115+
name (no compiler accepts it). `Install`/`Remove`/`Upgrade`/
116+
`Upgrade_System`/`Autoremove` are *functions* with an `in out`
117+
controlling parameter — **illegal SPARK** (SPARK RM 4.5.2) — under
118+
`pragma SPARK_Mode (On)`. *This PR* fixes the reserved word (renamed
119+
`Pkg`, now compiles), honestly sets `SPARK_Mode (Off)` with rationale,
120+
and adds sound Ada 2022 `Pre'Class`/`Post'Class` on the SPARK-legal
121+
query ops + `plugin_registry` `Pre`s (runtime-checked; the spec for
122+
the OWED refactor).
123+
* *`snapshot_manager.adb:4` — `pragma SPARK_Mode (Off)`* over the entire
124+
safety-critical rollback body. gnatprove proves **nothing** about
125+
rollback. The body also *never compiled*: `:93` calls
126+
`Create_Btrfs_Snapshot`, first declared `:145`, no forward declaration
127+
(Ada visibility error). The headline `Rollback_To_Snapshot` `Post`
128+
rests on `reversibility_types.adb:26-32`
129+
`System_State_Matches_Snapshot` which is `pragma Unreferenced (ID);
130+
return True;` — a **hardcoded-`True` vacuous ghost oracle** — and is
131+
additionally fail-permissive (`or else Status in Failed |
132+
Requires_Reboot`). The "25 Strong" rating is false.
133+
* *`safety_boundary.adb:6` — `pragma SPARK_Mode (Off)`*; and
134+
`safety_boundary.ads:78-101` re-declares `Safe_Install`/`Safe_Remove`/
135+
`Safe_Upgrade`/… as *functions* with `in Out …'Class` (the same
136+
illegal-SPARK construct, *without* even the honesty escape). No
137+
privilege/scope/bound model exists anywhere; the only precondition is
138+
`Is_Valid (Token)` (recovery-point presence). The "15 Strong /
139+
privilege-containment" rating is false.
140+
* *`safety_invariant.ads` — legal SPARK but vacuous.* Contracts are
141+
definitional tautologies over `Ghost` state that the real (SPARK_Mode
142+
Off) enforcement path never updates; e.g. `Lemma_Recovery_Enables_
143+
Rollback` has `Post ≡ Pre` by definition. Proved-but-meaningless.
144+
* *`plugin_registry.ads`* is transitively non-SPARK (uses
145+
`Backend_Access` from the non-SPARK `backend_interface`); its `Pre`s
146+
(strengthened by this PR) cannot be `gnatprove`-discharged until the
147+
refactor below.
148+
149+
=== What this PR genuinely delivers (no theatre, no fake green)
150+
151+
. Real bug fix: `backend_interface.ads` now compiles (reserved word).
152+
. Honest SPARK boundary on `backend_interface.ads` + documented OWED.
153+
. Sound Ada 2022 contracts (query-op `Pre'Class`/`Post'Class`,
154+
`Register_Backend` `Pre`, six `plugin_registry` non-empty-ID `Pre`s),
155+
runtime-enforced and serving as the spec for the SPARK refactor.
156+
. This verified, honest stance — replacing the false matrix.
157+
158+
=== OWED — large genuine programme, tracked standards#127 (must NOT be faked)
159+
160+
. State-mutating `function` → `procedure (… ; Result : out …)` redesign
161+
across `backend_interface` + every backend (`backend_guix`,
162+
`backend_nix`) + `safety_boundary`, to make the modification path
163+
legal SPARK.
164+
. Bring `snapshot_manager.adb` / `safety_boundary.adb` into
165+
`SPARK_Mode (On)` (they are wholly `Off` today) and fix the
166+
`snapshot_manager.adb` elaboration-order error so it compiles.
167+
. Replace the `System_State_Matches_Snapshot` hardcoded-`True` ghost
168+
with a real state model; connect `safety_invariant` ghost state to the
169+
executing enforcement path so its lemmas are non-vacuous.
170+
. Only then can the safety-critical contracts be `gnatprove`-discharged.
171+
172+
NOTE: the `BUILD_MODE=spark` mode and `gnatprove` are real *tooling*, but
173+
no safety-critical body is analysed by them today. Do not cite ambientops
174+
as "formally verified" until the OWED programme lands.
175+
115176
* *`.claude/CLAUDE.md` language drift.* Any stale ReScript/Tauri/Deno
116177
table is superseded by the estate policy and this stance doc; reconcile
117178
separately.

0 commit comments

Comments
 (0)