Proof using.
induction l; intros; simpl in *; intuition.
- find_inversion. simpl in *. intuition.
- unfold cacheApplyEntry, applyEntry in *.
repeat break_match; repeat find_inversion; simpl in *; intuition; eauto;
try solve
[find_inversion; find_rewrite; find_inversion; do_bool; omega];
try solve [find_inversion; repeat find_rewrite; congruence].
+ do_bool. destruct (clientId_eq_dec (eClient a) client).
* subst. find_rewrite. find_inversion.
eapply IHl; [eapply lt_le_trans; eauto|idtac|idtac|]; eauto.
unfold getLastId.
simpl. eauto using get_set_same.
* eapply IHl; eauto.
unfold getLastId in *.
simpl. rewrite get_set_diff; eauto.
+ do_bool. destruct (clientId_eq_dec (eClient a) client).
* repeat find_rewrite. congruence.
* eapply IHl; eauto.
unfold getLastId in *.
simpl. rewrite get_set_diff; eauto.
+ do_bool. destruct (clientId_eq_dec (eClient a) client).
* repeat find_rewrite. find_inversion.
eapply IHl; [eapply lt_le_trans; eauto|idtac|idtac|]; eauto.
unfold getLastId.
simpl. eauto using get_set_same.
* eapply IHl; eauto.
unfold getLastId in *.
simpl. rewrite get_set_diff; eauto.
+ do_bool. destruct (clientId_eq_dec (eClient a) client).
* repeat find_rewrite. congruence.
* eapply IHl; eauto.
unfold getLastId in *.
simpl. rewrite get_set_diff; eauto.
Qed.

Lemma applyEntries_before :
forall l h st os st' o client id id',
id < id' ->
applyEntries h st l = (os, st') ->
In (ClientResponse client id o) os ->
before_func (has_key client id) (has_key client id') l.