intensional.examples.trace_helpers
From intensional.heap_lang Require Import lang notation.
From intensional.examples Require Import stdpp_extra tactics.
Set Default Proof Using "Type".
Implicit Types t : list val.
Definition check_tag (tag: string) (v: val) :=
match v with
| (# (LitTag tag'), _)%V => String.eqb tag tag'
| _ => false
end.
Lemma check_tag_in_tags tag v t :
check_tag tag v = true →
v ∈ t →
tag ∈ tags t.
Proof.
revert tag v. induction t as [|v' t].
{ intros ? ? ?. inversion 1. }
{ intros * H1 [->|H2]%elem_of_cons. cbn.
{ unfold check_tag in H1. repeat case_match; simplify_eq; eauto.
apply String.eqb_eq in H1. subst. constructor. }
{ cbn. apply elem_of_app. right. eapply IHt; eauto. } }
Qed.
Lemma fresh_tag_nocheck t tag :
tag ∉ tags t →
Forall (λ v, ¬ check_tag tag v) t.
Proof.
induction t as [|v t]. done.
cbn. repeat case_match; eauto; simplify_eq.
intros [? ?]%not_elem_of_cons. apply Forall_cons. split; eauto.
unfold check_tag. intros Heq%Is_true_eq_true.
by apply String.eqb_eq in Heq as ->.
Qed.
Lemma not_check_tag_iff (tag tag':string) v :
¬ check_tag tag (#tag', v)%V ↔ tag ≠ tag'.
Proof.
unfold check_tag. split; intros HH1 HH2; apply HH1.
{ subst. rewrite String.eqb_refl //. }
{ apply Is_true_eq_true, String.eqb_eq in HH2. auto. }
Qed.
Lemma check_tag_iff (tag tag':string) v :
check_tag tag (#tag', v)%V = true ↔ tag = tag'.
Proof.
unfold check_tag. split; intros HH.
{ apply String.eqb_eq in HH. auto. }
{ subst. rewrite String.eqb_refl //. }
Qed.
Lemma filter_check_single_tag_neq (tag tag':string) v :
tag ≠ tag' →
filter (λ v, check_tag tag v) [(#tag', v)%V] = [].
Proof.
intros. apply filter_is_nil. repeat constructor.
by apply not_check_tag_iff.
Qed.
Lemma filter_check_single_tag_eq (tag:string) v :
filter (λ v, check_tag tag v) [(#tag, v)%V] = [(#tag, v)%V].
Proof.
intros. apply filter_Forall_id. repeat constructor.
by apply Is_true_eq_left, check_tag_iff.
Qed.
Lemma tags_app t u : tags (t ++ u) = tags t ++ tags u.
Proof.
induction t as [|v t].
{ cbn [tags]. done. }
{ cbn. case_match. all: try rewrite IHt //. subst.
repeat case_match; auto. }
Qed.
From intensional.examples Require Import stdpp_extra tactics.
Set Default Proof Using "Type".
Implicit Types t : list val.
Definition check_tag (tag: string) (v: val) :=
match v with
| (# (LitTag tag'), _)%V => String.eqb tag tag'
| _ => false
end.
Lemma check_tag_in_tags tag v t :
check_tag tag v = true →
v ∈ t →
tag ∈ tags t.
Proof.
revert tag v. induction t as [|v' t].
{ intros ? ? ?. inversion 1. }
{ intros * H1 [->|H2]%elem_of_cons. cbn.
{ unfold check_tag in H1. repeat case_match; simplify_eq; eauto.
apply String.eqb_eq in H1. subst. constructor. }
{ cbn. apply elem_of_app. right. eapply IHt; eauto. } }
Qed.
Lemma fresh_tag_nocheck t tag :
tag ∉ tags t →
Forall (λ v, ¬ check_tag tag v) t.
Proof.
induction t as [|v t]. done.
cbn. repeat case_match; eauto; simplify_eq.
intros [? ?]%not_elem_of_cons. apply Forall_cons. split; eauto.
unfold check_tag. intros Heq%Is_true_eq_true.
by apply String.eqb_eq in Heq as ->.
Qed.
Lemma not_check_tag_iff (tag tag':string) v :
¬ check_tag tag (#tag', v)%V ↔ tag ≠ tag'.
Proof.
unfold check_tag. split; intros HH1 HH2; apply HH1.
{ subst. rewrite String.eqb_refl //. }
{ apply Is_true_eq_true, String.eqb_eq in HH2. auto. }
Qed.
Lemma check_tag_iff (tag tag':string) v :
check_tag tag (#tag', v)%V = true ↔ tag = tag'.
Proof.
unfold check_tag. split; intros HH.
{ apply String.eqb_eq in HH. auto. }
{ subst. rewrite String.eqb_refl //. }
Qed.
Lemma filter_check_single_tag_neq (tag tag':string) v :
tag ≠ tag' →
filter (λ v, check_tag tag v) [(#tag', v)%V] = [].
Proof.
intros. apply filter_is_nil. repeat constructor.
by apply not_check_tag_iff.
Qed.
Lemma filter_check_single_tag_eq (tag:string) v :
filter (λ v, check_tag tag v) [(#tag, v)%V] = [(#tag, v)%V].
Proof.
intros. apply filter_Forall_id. repeat constructor.
by apply Is_true_eq_left, check_tag_iff.
Qed.
Lemma tags_app t u : tags (t ++ u) = tags t ++ tags u.
Proof.
induction t as [|v t].
{ cbn [tags]. done. }
{ cbn. case_match. all: try rewrite IHt //. subst.
repeat case_match; auto. }
Qed.