Keyboard shortcuts

Press or to navigate between chapters

Press S or / to search in the book

Press ? to show this help

Press Esc to hide this help

Lean による形式化

本プロジェクトでは Lean 4 を使い、Verified 表示の fail-closed 条件、journal count の整合性、input commitment の canonical encoding、LSB-first bitmap packing、抽象 guest tally model の不変条件を形式化しています。

Lean は実装を直接証明するのではなく、抽象モデル上で不変条件を証明し、そこから生成した generated vectors / formal report / formal audit を TypeScript・Rust のテストと CI に接続することで、モデルと実装の対応付けを継続的に検査します。Lean が扱わない範囲は末尾の 証明していないこと を参照してください。

Lean で定義しているもの

Lean module主な定義役割
Basic.leanCheckStatus, SummaryStatus, SummaryTone, CheckId, CheckCategory, CheckRole, Criticality検証チェックと summary model の基礎型
JournalCounts.leanmissingSlotsOf, invalidPresentedSlotsOf, excludedSlotsOfzkVM journal の count 分解を Nat モデルで表す
VerificationSummary.leancheckDefinitions, isRequiredCheck, canFullyVerify, deriveSummaryModel/verify の最終判定に関わる fail-closed model
InputCommitment.leanCommitmentVote, InputCommitmentCase, canonical order, u16LE, u32LE, preimage encodinginput commitment の byte layout と順序安定性をモデル化
Bitmap.leanpackedByteCount, packedAddress, byteValueAt, packBitsLSB-first bitmap packing と bit address をモデル化
GuestModel.leanRejectReason, GuestVote, CandidateTally, GuestState, classifyVote, processVotes, guest boundszkVM guest の抽象 tally / rejection state machine

GuestModel.leanzkvm/methods/guest/src/main.rs を行単位で翻訳したものではありません。外部的に重要な処理順序、つまりインデックス範囲、重複 index、選択肢、コミットメント、重複 commitment、包含証明、集計反映の順序を抽象 state machine として表します。

Lean で証明していること

領域代表 theorem主張
Journal countexcluded_zero_implies_no_slot_loss, slot_partition_totalexcludedSlots = 0 なら missing / invalid presented が 0 になり、slot loss がない
Verification summaryfully_verified_implies_all_required_success, fully_verified_implies_no_unknown_checks, fully_verified_implies_required_roles_successfully_verified は required check 成功、unknown check 不在、重要 role 成功を要求する
Input commitmentcanonical_vote_order_total, canonical_encoding_permutation_invariantvote の入力順序に依存しない canonical encoding が定義されている
Bitmappack_bits_length, pack_bits_get_bitLSB-first packing の byte 数と bit 取得がモデル通りになる
Guest modelaccepted_votes_count_tally, valid_votes_count_accepted, processVotes_fold_invariant抽象 guest fold が tally / validVotes / seen index の不変条件を保つ
Guest completenesszero_exclusion_guest_model_completeexcludedSlots = 0 が guest model 上で missing / invalid presented の不存在につながる
Bounded countsno_overflow_under_guest_bounds明示した guest bounds 内で seen / valid / rejected / tally bucket が Rust u32 に収まる

これらは抽象モデル上の主張です。実装との対応は、次の generated vectors とテストで検査します。

実装との接続

flowchart LR
  L["Lean models<br/>formal/StarkBallotFormal/*.lean"]
  T["Theorems<br/>形式的な不変条件"]
  R["formal-report.json<br/>主張と前提"]
  V["generated-vectors/*.json<br/>実装対応付けケース"]
  A["formal-audit.json<br/>theorem hash / dependency / hygiene"]
  TS["TypeScript tests<br/>Vitest"]
  RS["Rust vector tests<br/>cargo test"]
  FCI["formal CI<br/>pnpm formal:verify"]
  RCI["Rust tests workflow<br/>cargo test"]

  L --> T
  T --> R
  L --> V
  T --> A
  V --> TS
  V --> RS
  R --> FCI
  V --> FCI
  A --> FCI
  TS --> FCI
  RS --> RCI
generated vector消費先目的
verification-summary-cases.jsonTypeScript summary testsLean summary model と deriveVerificationSummary の対応
verification-display-cases.jsonverify page overall-status testsUI が verified を誤表示しないことの drift guard
check-definitions.jsonTypeScript check-definition testcheck ID / category / role / criticality / required 条件の drift guard
input-commitment-cases.jsonTypeScript / Rust testscanonical order と pre-hash bytes の対応
bitmap-cases.jsonTypeScript / Rust testsLSB-first packing と bitmap behavior の対応
guest-model-cases.jsonRust guest tests抽象 guest model と Rust guest inspection surface の対応

pnpm formal:verify は Lean build、formal report / generated vectors / audit の freshness、TypeScript の vector-consuming tests、生成 JSON の format check をまとめて実行します。Rust 側の vector-consuming tests は docs/current/formal/generated-vectors/** の変更で起動する Rust tests workflow の cargo test によって検査します。

この接続により、Lean model が変わったのに実装テストが追従していない場合、または実装側の encoding / summary / guest behavior が model から外れた場合に、CI 上で drift を検出できます。

対応付けを支える成果物

Lean の成果物を public documentation と実装テストに接続するため、次を組み込んでいます。

  • guest-model generated vectors
  • check-definition drift vector
  • theorem statement hash
  • generated-vector hash
  • #print axioms に基づく theorem dependency audit
  • proof hygiene scan
  • explicit guest bounds
  • TypeScript / Rust 側の vector-consuming tests
  • pnpm formal:verify による freshness gate

実行コマンド

コマンド目的
pnpm formal:buildLean workspace を build する
pnpm formal:reportformal-report.json を再生成する
pnpm formal:report:checkreport が最新か確認する
pnpm formal:vectorsLean から generated vectors を再生成する
pnpm formal:vectors:checkgenerated vectors が最新か確認する
pnpm formal:audittheorem statement / dependency / proof hygiene audit を生成する
pnpm formal:audit:checkaudit artifact が最新か確認する
pnpm formal:test:tsLean vector を消費する TypeScript tests を実行する
pnpm formal:verifybuild、report、vectors、audit、TS tests、format checks をまとめて検証する

証明していないこと

Lean は次を証明しません。

  • SHA-256 の衝突困難性
  • RISC Zero receipt soundness
  • Rust compiler / TypeScript runtime / browser runtime の完全な正しさ
  • AWS runtime behavior
  • React rendering 全体の正しさ
  • 本番選挙システムとしての安全性
  • zkVM guest Rust 実装全体の line-by-line verification

したがって、正確な主張は「投票システム全体を形式検証した」ではありません。正確には、選択した安全モデルを Lean で証明し、generated vectors と CI drift guard によって TypeScript / Rust 実装との対応を検査している、というものです。