Proof using.
intros.
unfold handleInput in *.
break_match; repeat break_let; repeat find_inversion;
[eapply_prop raft_net_invariant_timeout|
eapply_prop raft_net_invariant_client_request]; eauto;
unfold send_packets in *; simpl in *; intros; find_apply_hyp_hyp; intuition.
Qed.
Definition raft_net_invariant_state_same_packet_subset (P : network -> Prop) :=
forall net net',
(forall h, nwState net h = nwState net' h) ->
(forall p, In p (nwPackets net') -> In p (nwPackets net)) ->
P net ->
raft_intermediate_reachable net ->
P net'.
Definition raft_net_invariant_reboot (P : network -> Prop) :=
forall net net' d h d',
reboot d = d' ->
P net ->
raft_intermediate_reachable net ->
nwState net h = d ->
(forall h', nwState net' h' = update name_eq_dec (nwState net) h d' h') ->
nwPackets net = nwPackets net' ->
P net'.
Definition raft_net_invariant_init (P : network -> Prop) :=
P step_async_init.

(* Specifications: *)
Theorem raft_net_invariant :
forall P net,
raft_net_invariant_init P ->
raft_net_invariant_client_request P ->
raft_net_invariant_timeout P ->
raft_net_invariant_append_entries P ->
raft_net_invariant_append_entries_reply P ->
raft_net_invariant_request_vote P ->
raft_net_invariant_request_vote_reply P ->
raft_net_invariant_do_leader P ->
raft_net_invariant_do_generic_server P ->
raft_net_invariant_state_same_packet_subset P ->
raft_net_invariant_reboot P ->
raft_intermediate_reachable net ->
P net.