You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

52 lines
2.6 KiB

  1. #lang ivy1.7
  2. include tendermint
  3. include abstract_tendermint
  4. # Here we prove the second accountability property: no well-behaved node is
  5. # ever observed to violate the accountability properties.
  6. # The proof is done in two steps: first we prove the the abstract specification
  7. # satisfies the property, and then we show by refinement that this property
  8. # also holds in the concrete specification.
  9. # To see what is checked in the refinement proof, use `ivy_show isolate=accountable_safety_2 accountable_safety_2.ivy`
  10. # To see what is checked in the abstract correctness proof, use `ivy_show isolate=abstract_accountable_safety_2 accountable_safety_2.ivy`
  11. # To check the whole proof, use `ivy_check complete=fo accountable_safety_2.ivy`.
  12. # Proof that the property holds in the abstract specification
  13. # ============================================================
  14. isolate abstract_accountable_safety_2 = {
  15. instantiate abstract_tendermint
  16. # the main property:
  17. invariant [wb_never_punished] well_behaved(N) -> ~(observed_equivocation(N) | observed_unlawful_prevote(N))
  18. # the main invariant for proving wb_not_punished:
  19. invariant well_behaved(N) & precommitted(N,R,V) & ~locked(N,R,V) & V ~= value.nil -> exists R2,V2 . V2 ~= value.nil & R < R2 & precommitted(N,R2,V2) & locked(N,R2,V2)
  20. invariant (exists N . well_behaved(N) & precommitted(N,R,V) & V ~= value.nil) -> exists Q . nset.is_quorum(Q) & forall N . nset.member(N,Q) -> observed_prevoted(N,R,V)
  21. invariant well_behaved(N) -> (observed_prevoted(N,R,V) <-> prevoted(N,R,V))
  22. invariant well_behaved(N) -> (observed_precommitted(N,R,V) <-> precommitted(N,R,V))
  23. # nodes stop prevoting or precommitting in lower rounds when doing so in a higher round:
  24. invariant well_behaved(N) & prevoted(N,R2,V2) & R1 < R2 -> left_round(N,R1)
  25. invariant well_behaved(N) & locked(N,R2,V2) & R1 < R2 -> left_round(N,R1)
  26. invariant [precommit_unique_per_round] well_behaved(N) & precommitted(N,R,V1) & precommitted(N,R,V2) -> V1 = V2
  27. } with nset, round, abstract_accountable_safety_2.defs.observed_equivocation_def, abstract_accountable_safety_2.defs.observed_unlawful_prevote_def
  28. # Proof that the property holds in the concrete specification
  29. # ===========================================================
  30. isolate accountable_safety_2 = {
  31. instantiate tendermint(abstract_accountable_safety_2)
  32. invariant well_behaved(N) -> ~(abstract_accountable_safety_2.observed_equivocation(N) | abstract_accountable_safety_2.observed_unlawful_prevote(N))
  33. } with round, value, shim, abstract_accountable_safety_2, abstract_accountable_safety_2.defs.observed_equivocation_def, abstract_accountable_safety_2.defs.observed_unlawful_prevote_def