Lvc.Spilling.SpillUtil
Require Import List Map CSet Envs AllInRel Exp AppExpFree.
Require Import IL Annotation AutoIndTac Liveness.Liveness LabelsDefined.
Notation "'spilling'"
:= (ann (⦃var⦄ × ⦃var⦄ × list (⦃var⦄ × ⦃var⦄))).
Notation "'getSp' sl" := (fst (fst (getAnn sl))) (at level 40).
Notation "'getL' sl" := (snd (fst (getAnn sl))) (at level 40).
Notation "'getRm' sl" := (snd (getAnn sl)) (at level 40, only parsing).
Require Import IL Annotation AutoIndTac Liveness.Liveness LabelsDefined.
Notation "'spilling'"
:= (ann (⦃var⦄ × ⦃var⦄ × list (⦃var⦄ × ⦃var⦄))).
Notation "'getSp' sl" := (fst (fst (getAnn sl))) (at level 40).
Notation "'getL' sl" := (snd (fst (getAnn sl))) (at level 40).
Notation "'getRm' sl" := (snd (getAnn sl)) (at level 40, only parsing).
(* move somewhere *)
Lemma tl_list_incl (X : Type) `{OrderedType X} (L : list X)
: of_list (tl L) ⊆ of_list L.
Proof.
general induction L; simpl; eauto with cset.
Qed.
Lemma tl_set_incl (X : Type) `{OrderedType X} (s : set X)
: of_list (tl (elements s)) ⊆ s .
Proof.
rewrite tl_list_incl.
hnf. intros. eapply elements_iff. cset_tac.
Qed.
Definition sub_spill (sl' sl : spilling) :=
sl' = setTopAnn sl (getAnn sl') (*Note that rm=rm' *)
∧ fst (fst (getAnn sl')) ⊆ fst (fst (getAnn sl))
∧ snd (fst (getAnn sl')) ⊆ snd (fst (getAnn sl))
∧ snd (getAnn sl') = snd (getAnn sl).
Function count (sl : spilling)
:= cardinal (fst (fst (getAnn sl))) + cardinal (snd (fst (getAnn sl))).
(* TODO move somewhere *)
Lemma get_get_eq (X : Type) (L : list X) (n : nat) (x x' : X)
: get L n x → get L n x' → x = x' .
Proof.
intros get_x get_x'.
induction get_x; inversion get_x'.
- reflexivity.
- apply IHget_x. assumption.
Qed.
Lemma sub_spill_refl sl
: sub_spill sl sl .
Proof.
unfold sub_spill.
repeat split.
simpl; eauto.
- unfold setTopAnn.
destruct sl; destruct a; destruct p;
simpl; reflexivity.
- reflexivity.
- reflexivity.
Qed.
Lemma of_list_tl_hd (L : list var)
: L ≠ nil
→ of_list L [=] of_list (tl L) ∪ singleton (hd default_var L) .
Proof.
intro N.
induction L; simpl; eauto.
- isabsurd.
- cset_tac.
Qed.
Lemma tl_hd_set_incl (s t : ⦃var⦄)
: s \ of_list (tl (elements t)) ⊆ s \ t ∪ singleton (hd default_var (elements t)) .
Proof.
hnf.
intros a H.
apply diff_iff in H.
destruct H as [in_s not_in_tl_t].
apply union_iff.
decide (a ∈ t).
- right.
rewrite <- of_list_elements in i.
rewrite of_list_tl_hd in i.
+ apply union_iff in i.
destruct i.
× contradiction.
× eauto.
+ intro N.
apply elements_nil_eset in N.
rewrite of_list_elements in i.
rewrite N in i.
isabsurd.
- left.
cset_tac.
Qed.
Lemma nth_zip (X Y Z : Type) (L : list X) (L': list Y)
(x : X) (x' : Y) (d : Z) (f : X → Y → Z) n
: get L n x
→ get L' n x'
→ nth n (f ⊜ L L') d = f x x'.
Proof.
intros get_x get_x'.
general induction n;
simpl; eauto; isabsurd;
inv get_x;
inv get_x'.
- simpl. apply IHn; eauto.
Qed.
Lemma count_zero_Empty_Sp (sl : spilling)
: count sl = 0 → Empty (getSp sl) .
Proof.
intro count_zero.
apply cardinal_Empty.
unfold count in count_zero.
omega.
Qed.
Lemma count_zero_cardinal_Sp (sl : spilling)
: count sl = 0
→ cardinal (getSp sl) = 0 .
Proof.
intro count_zero.
unfold count in count_zero.
omega.
Qed.
Lemma count_zero_cardinal_L (sl : spilling)
: count sl = 0
→ cardinal (getL sl) = 0 .
Proof.
intro count_zero.
unfold count in count_zero.
omega.
Qed.
Lemma count_zero_Empty_L (sl : spilling)
: count sl = 0 → Empty (getL sl) .
Proof.
intro count_zero.
apply cardinal_Empty.
unfold count in count_zero.
omega.
Qed.
Lemma Empty_Sp_L_count_zero (sl : spilling)
: Empty (getSp sl)
→ Empty (getL sl)
→ count sl = 0 .
Proof.
intros Empty_Sp Empty_L.
apply cardinal_Empty in Empty_Sp.
apply cardinal_Empty in Empty_L.
unfold count.
omega.
Qed.
Definition clear_L (sl : spilling)
:= setTopAnn sl (getSp sl, ∅, getRm sl) .
Lemma count_clearL (sl : spilling)
: count (clear_L sl) = cardinal (getSp sl) .
Proof.
unfold count.
unfold clear_L.
rewrite getAnn_setTopAnn.
simpl.
rewrite empty_cardinal.
omega.
Qed.
Definition merge (RM : set var × set var) :=
fst RM ∪ snd RM.
Lemma getAnn_als_EQ_merge_rms
(Lv : 〔⦃var⦄〕)
(als : 〔ann ⦃var⦄〕)
(Λ : 〔⦃var⦄ × ⦃var⦄〕)
(pir2 : PIR2 Equal (merge ⊝ Λ) Lv)
(rms : 〔⦃var⦄ × ⦃var⦄〕)
(H23 : PIR2 Equal (merge ⊝ rms) (getAnn ⊝ als))
:
PIR2 Equal (merge ⊝ (rms ++ Λ)) (getAnn ⊝ als ++ Lv)
.
Proof.
rewrite List.map_app. apply PIR2_app; eauto.
Qed.
Lemma al_sub_RfMf
(als : list (ann ⦃var⦄))
(rms : list (⦃var⦄ × ⦃var⦄))
(al : ann ⦃var⦄)
(R M : ⦃var⦄)
(n : nat)
: get rms n (R,M)
→ get als n al
→ PIR2 Equal (merge ⊝ rms) (getAnn ⊝ als)
→ getAnn al ⊆ R ∪ M.
Proof.
intros get_rm get_al H16.
general induction get_rm;
try invc get_al; invc H16;
unfold merge in *; simpl in *; eauto.
rewrite pf; eauto.
Qed.
Lemma al_eq_RfMf
(als : list (ann ⦃var⦄))
(rms : list (⦃var⦄ × ⦃var⦄))
(al : ann ⦃var⦄)
(R M : ⦃var⦄)
(n : nat)
: get rms n (R,M)
→ get als n al
→ merge ⊝ rms = getAnn ⊝ als
→ getAnn al [=] R ∪ M .
Proof.
intros get_rm get_al H16.
general induction get_rm;
try invc get_al; invc H16;
simpl in *; eauto.
Qed.
Definition slot_merge
(slot : var → var)
(RM : set var × set var)
:= fst RM ∪ map slot (snd RM).
Lemma slot_merge_app
(L1 L2: list (set var × set var))
(slot : var → var)
:
slot_merge slot ⊝ L1 ++ slot_merge slot ⊝ L2
= slot_merge slot ⊝ (L1 ++ L2)
.
Proof.
intros.
unfold slot_merge.
rewrite List.map_app; eauto.
Qed.
Lemma nth_rfmf
(l : lab)
(Λ : 〔⦃var⦄ × ⦃var⦄〕)
(slot : var → var)
(R_f M_f : ⦃var⦄)
(H15 : get Λ (counted l) (R_f, M_f))
: nth (counted l) (slot_merge slot ⊝ Λ) ∅ [=] R_f ∪ map slot M_f .
Proof.
eapply get_nth with (d:=(∅,∅)) in H15 as H15'.
simpl in H15'.
assert ((fun RM
⇒ fst RM ∪ map slot (snd RM)) (nth l Λ (∅,∅))
= (fun RM
⇒ fst RM ∪ map slot (snd RM)) (R_f,M_f))
as H_sms. {
f_equal; simpl; [ | f_equal];
rewrite H15'; simpl; eauto.
}
unfold slot_merge.
rewrite <- map_nth in H_sms.
simpl in H_sms.
assert (l < length ((fun RM : ⦃var⦄ × ⦃var⦄
⇒ fst RM ∪ map slot (snd RM)) ⊝ Λ))
as l_len. {
apply get_length in H15.
clear - H15; eauto with len.
}
assert (nth l ((fun RM : ⦃var⦄ × ⦃var⦄
⇒ fst RM ∪ map slot (snd RM)) ⊝ Λ) ∅
= R_f ∪ map slot M_f)
as H_sms'. {
rewrite nth_indep with (d':=∅ ∪ map slot ∅).
× exact H_sms.
× eauto with len.
}
simpl.
rewrite H_sms'.
reflexivity.
Qed.
(* the following lemmata & definitions could be extracted *)
Definition clear_SpL (sl : spilling) := setTopAnn sl (∅,∅,snd (getAnn sl)).
Definition reduce_Sp (sl : spilling) :=
setTopAnn sl (of_list (tl (elements (getSp sl))), getL sl, snd (getAnn sl)).
Definition reduce_L (sl : spilling) :=
setTopAnn sl (getSp sl, of_list (tl (elements (getL sl))), snd (getAnn sl)).
Lemma count_clear_zero (sl : spilling)
: count (clear_SpL sl) = 0.
Proof.
unfold count.
unfold clear_SpL.
rewrite getAnn_setTopAnn.
simpl.
apply empty_cardinal.
Qed.
Definition clear_Sp (sl : spilling) :=
setTopAnn sl (∅,getL sl,getRm sl).
Lemma count_clearSp (sl : spilling)
: count (clear_Sp sl) = cardinal (getL sl).
Proof.
unfold count.
unfold clear_Sp.
rewrite getAnn_setTopAnn.
simpl.
rewrite empty_cardinal.
reflexivity.
Qed.
Lemma getSp_clearSp (sl : spilling)
: getSp clear_Sp sl = ∅.
Proof.
unfold clear_Sp.
rewrite getAnn_setTopAnn.
simpl.
reflexivity.
Qed.
Lemma getL_clearSp (sl : spilling)
: getL clear_Sp sl = getL sl.
Proof.
unfold clear_Sp.
rewrite getAnn_setTopAnn.
simpl.
reflexivity.
Qed.
Lemma getSp_clear (sl : spilling)
: getSp clear_SpL sl = ∅.
Proof.
unfold clear_SpL.
rewrite getAnn_setTopAnn.
simpl.
reflexivity.
Qed.
Lemma getL_clear (sl : spilling)
: getL clear_SpL sl = ∅.
Proof.
unfold clear_SpL.
rewrite getAnn_setTopAnn.
simpl.
reflexivity.
Qed.
Lemma getRm_clear (sl : spilling)
: getRm clear_SpL sl = getRm sl.
Proof.
unfold clear_SpL.
rewrite getAnn_setTopAnn.
simpl.
reflexivity.
Qed.
Lemma getRm_clearSp (sl : spilling)
: getRm clear_Sp sl = getRm sl.
Proof.
unfold clear_Sp.
rewrite getAnn_setTopAnn.
simpl.
reflexivity.
Qed.
Definition setSp (sl : spilling) (Sp : ⦃var⦄) : spilling :=
setTopAnn sl (Sp,getL sl,getRm sl) .
Lemma clear_clearSp (sl : spilling)
: clear_SpL (clear_Sp sl) = clear_SpL sl.
Proof.
unfold clear_SpL.
unfold clear_Sp.
rewrite setTopAnn_setTopAnn.
rewrite getAnn_setTopAnn.
simpl.
reflexivity.
Qed.
Lemma clearSp_clearSp (sl : spilling)
: clear_Sp (clear_Sp sl) = clear_Sp sl.
Proof.
unfold clear_Sp.
rewrite getAnn_setTopAnn.
rewrite setTopAnn_setTopAnn.
simpl.
reflexivity.
Qed.
Lemma setSp_getSp (sl : spilling)
: setSp sl (getSp sl) = sl.
Proof.
unfold setSp.
unfold setTopAnn.
destruct sl;
destruct a;
destruct p;
simpl;
reflexivity.
Qed.
Lemma getSp_setSp (sl : spilling) (Sp : ⦃var⦄)
: getSp (setSp sl Sp) = Sp.
Proof.
unfold setSp.
rewrite getAnn_setTopAnn.
simpl.
reflexivity.
Qed.