Grants — budget conservation: the fund cannot award money it does not have
COVID-era relief programs paid out past their appropriations because the "remaining budget" lived in a spreadsheet beside the disbursement system — GAO flagged billions in over- and duplicate disbursements. The bug class is always the same: the balance check and the payment are two systems. Here they are one write: an award debits the fund slot, and a negative balance is unrepresentable — the memory refuses the overdraft. Conservation (awards + remaining == appropriation) holds by construction, and a closed fund is terminal: soma verify proves no path re-opens it.
A Soma program from the civic part of the verified corpus: 107 lines, cells GrantFund, GrantFundTests. It passes soma check with soma 3.2.4.
How it is built
The cell GrantFund declares 7 signals in its face: appropriate(amount: Int) -> Map, award_grant(grantee: String, amount: Int) -> Map, close_fund() -> Map, remaining_balance() -> Int, total_awarded() -> Int, conserved() -> Bool and phase() -> String; keeps 2 memory slots: remaining (Map<String, Int>, persistent and consistent) under the invariant remaining >= 0 and awarded (Map<String, Int>, persistent and consistent) under the invariant awarded >= 0. Its state machine fund starts in proposed and allows 2 transitions: proposed -> disbursing and disbursing -> closed. closed is terminal. Handlers: phase (line 42), appropriate (line 44), award_grant (line 52), close_fund (line 68), remaining_balance (line 74), total_awarded (line 76) and conserved (line 83).
The file also holds 1 test cell (GrantFundTests) with 14 assertions, run by soma test.
The source
grants.cell
// ============================================================================
// GRANTS — budget conservation: the fund cannot award money it does not have
// ============================================================================
// COVID-era relief programs paid out past their appropriations because the
// "remaining budget" lived in a spreadsheet beside the disbursement system —
// GAO flagged billions in over- and duplicate disbursements. The bug class is
// always the same: the balance check and the payment are two systems. Here
// they are one write: an award debits the fund slot, and a negative balance
// is unrepresentable — the memory refuses the overdraft. Conservation
// (awards + remaining == appropriation) holds by construction, and a closed
// fund is terminal: soma verify proves no path re-opens it.
// ============================================================================
cell GrantFund {
face {
signal appropriate(amount: Int) -> Map
signal award_grant(grantee: String, amount: Int) -> Map
signal close_fund() -> Map
signal remaining_balance() -> Int
signal total_awarded() -> Int
signal conserved() -> Bool
signal phase() -> String
}
memory {
// The wall: a balance below zero is rejected at the write,
// no matter what arithmetic a handler believed.
remaining: Map<String, Int> [persistent, consistent]
invariant remaining >= 0
awarded: Map<String, Int> [persistent, consistent]
invariant awarded >= 0
}
// closed is terminal: a spent fund never disburses again.
state fund {
initial: proposed
proposed -> disbursing
disbursing -> closed
}
on phase() { return get_status("fund") }
on appropriate(amount: Int) {
let r = try { transition("fund", "disbursing") }
if r.error != () { return map("ok", false, "reason", "{r.error}") }
remaining.set("fund", amount)
remaining.set("appropriation", amount)
return map("ok", true, "fund", amount)
}
on award_grant(grantee: String, amount: Int) {
if phase() != "disbursing" {
return map("ok", false, "reason", "fund is {phase()}")
}
if amount <= 0 { return map("ok", false, "reason", "award must be positive") }
let bal = remaining.get("fund") ?? 0
// THE WALL: if amount > bal this write is an overdraft and refuses.
let w = try { remaining.set("fund", bal - amount) }
if w.error != () {
return map("ok", false, "reason", "insufficient fund: {bal} < {amount}")
}
let prior = awarded.get(grantee) ?? 0
awarded.set(grantee, prior + amount)
return map("ok", true, "grantee", grantee, "remaining", bal - amount)
}
on close_fund() {
let r = try { transition("fund", "closed") }
if r.error != () { return map("ok", false, "reason", "{r.error}") }
return map("ok", true, "unspent", remaining_balance())
}
on remaining_balance() { return remaining.get("fund") ?? 0 }
on total_awarded() {
let names = awarded.keys()
let n = 0
for g in names { n = n + (awarded.get(g) ?? 0) }
return n
}
on conserved() {
let appropriation = remaining.get("appropriation") ?? 0
return total_awarded() + remaining_balance() == appropriation
}
}
cell test GrantFundTests {
rules {
assert award_grant("arts-coop", 100).ok == false // nothing appropriated
assert appropriate(1000).ok == true
assert award_grant("arts-coop", 600).ok == true
assert award_grant("food-bank", 600).ok == false // would overdraft
assert remaining_balance() == 400
assert award_grant("food-bank", 400).ok == true
assert award_grant("library", 1).ok == false // fund is empty
assert_fails remaining.set("fund", -1) // overdraft unrepresentable
assert_fails awarded.set("ghost", -50) // no negative awards
assert total_awarded() == 1000
assert conserved() == true
assert close_fund().ok == true
assert award_grant("late", 1).ok == false // closed fund pays nobody
assert_fails transition("fund", "disbursing") // and stays closed
}
}What the toolchain says
$ soma check grants.cell
✓ All checks passed.$ soma test grants.cell
test GrantFundTests ...
✓ assert award_grant("arts-coop", 100).ok == false
✓ assert appropriate(1000).ok == true
✓ assert award_grant("arts-coop", 600).ok == true
✓ assert award_grant("food-bank", 600).ok == false
✓ assert remaining_balance() == 400
✓ assert award_grant("food-bank", 400).ok == true
✓ assert award_grant("library", 1).ok == false
✓ assert_fails remaining.set("fund", -1) — raised memory invariant violated on 'remaining': remaining >= 0 — rejected write of -1 (key "fund"); the slot is unchanged
✓ assert_fails awarded.set("ghost", -50) — raised memory invariant violated on 'awarded': awarded >= 0 — rejected write of -50 (key "ghost"); the slot is unchanged
✓ assert total_awarded() == 1000
✓ assert conserved() == true
✓ assert close_fund().ok == true
✓ assert award_grant("late", 1).ok == false
✓ assert_fails transition("fund", "disbursing") — raised invalid transition: closed → disbursing. Current state: 'closed'. Valid targets: []
14 tests: 14 passed, 0 failed$ soma verify grants.cell
Verifying grants.cell...
State machine 'fund': 3 states, initial 'proposed'
States: [closed, disbursing, proposed]
✓ 3 states, 2 transitions
✓ all states reachable from 'proposed'
✓ terminal states: [closed]
✓ no deadlocks
✓ liveness: every state can eventually reach a terminal state
✓ think-isolated: CTL safety properties hold regardless of LLM output (2 handlers, 2 literal transitions, 0 dynamic)
✓ termination: all 7 handlers structurally terminate
✓ refinement: handler `appropriate` ⟶ {disbursing}
✓ refinement: handler `close_fund` ⟶ {closed}
· transition sources: `appropriate`, `close_fund` call transition(id, target) without declaring the source — the runtime refuses a move the graph forbids, but the proof does not see where the handler starts; `transition(id, from, to)` names the edge (checked by `soma check`, refused at run time from any other state)
GrantFund/invariants:
⚠ invariant remaining >= 0 — runtime-checked (computed values): appropriate → remaining because `amount` is a parameter (narrow it: `require amount >= 0 else …`), award_grant → remaining
✓ invariant awarded >= 0 — writer 'award_grant' proven by induction (writes prior + amount)
10 passed, 1 warnings, 0 failures
Temporal properties for 'fund':
✓ deadlock_free — no deadlocks in any reachable state
Temporal: 1 passed, 0 failed
VERIFY OK