Section VotesCorrect.
Context {orig_base_params : BaseParams}.
Context {one_node_params : OneNodeParams orig_base_params}.
Context {raft_params : RaftParams orig_base_params}.
Context {rri : raft_refinement_interface}.
Context {vlcti : votes_le_current_term_interface}.
Ltac split_votes_correct :=
intros; subst;
intuition; [ unfold one_vote_per_term in *
| unfold votes_currentTerm_votedFor_correct in *
| unfold currentTerm_votedFor_votes_correct in * ];
cbn [nwState].
Ltac start_proof :=
intros;
match goal with H : forall _, ?f _ = _ |- _ => rewrite H in * end;
update_destruct; rewrite_update;
cbn [fst snd] in *; eauto.
Proof using.
unfold refined_raft_net_invariant_client_request, votes_correct.
split_votes_correct; start_proof;
rewrite @votes_update_elections_data_client_request in *;
find_apply_lem_hyp handleClientRequest_term_votedFor; break_and;
repeat find_rewrite; eauto.
Qed.
Ltac do_le_antisym :=
match goal with
| [ H : ?x <= ?y, H' : ?y <= ?x |- _ ] =>
assert (x = y) by auto using Nat.le_antisymm
end.
Proof using vlcti.
unfold refined_raft_net_invariant_timeout, votes_correct.
split_votes_correct; start_proof.
- find_eapply_lem_hyp votes_update_elections_data_timeout_votedFor; eauto.
find_eapply_lem_hyp votes_update_elections_data_timeout_votedFor; eauto.
intuition.
+ eauto.
+ find_apply_lem_hyp votes_le_current_term_invariant; auto; simpl in *; lia.
+ find_apply_lem_hyp votes_le_current_term_invariant; auto; simpl in *; lia.
+ congruence.
- find_eapply_lem_hyp votes_update_elections_data_timeout_votedFor; eauto.
intuition. subst.
find_copy_apply_lem_hyp votes_le_current_term_invariant; auto.
find_copy_apply_lem_hyp handleTimeout_currentTerm.
do_le_antisym.
erewrite handleTimeout_same_term_votedFor_preserved by eauto.
eauto.
- eapply update_elections_data_timeout_votes_intro_new; intuition eauto.
Qed.

Lemma votes_correct_append_entries :
refined_raft_net_invariant_append_entries votes_correct.