(* the inheritance from PCMs *)
Definition heapUMCMix :=
UMCMixin ftE tfE defE undefE emptyE updE domE dom_eqE freeE
findE unionE umfiltE empbE undefbE ptsE.
Canonical heapUMC := Eval hnf in UMC heap heapUMCMix.
Definition heapPCMMix := union_map_classPCMMix heapUMC.
Canonical heapPCM := Eval hnf in PCM heap heapPCMMix.
Definition heapCPCMMix := union_map_classCPCMMix heapUMC.
Canonical heapCPCM := Eval hnf in CPCM heap heapCPCMMix.
Definition heapTPCMMix := union_map_classTPCMMix heapUMC.
Canonical heapTPCM := Eval hnf in TPCM heap heapTPCMMix.
End Exports.
End Heap.
Export Heap.Exports.
Notation heap := Heap.heap.
Definition heap_pts A (x : ptr) (v : A) :=
@UMC.pts _ _ heapUMC x (idyn v).
Notation "x :-> v" := (@heap_pts _ x v) (at level 30).
(*****************************)
(* Specific points-to lemmas *)
(*****************************)
Section HeapPointsToLemmas.
Implicit Types (x : ptr) (h : heap).

(* Specifications: *)
Lemma hcancelPtT A1 A2 x (v1 : A1) (v2 : A2) :
valid (x :-> v1) -> x :-> v1 = x :-> v2 -> A1 = A2.
Lemma hcancelT A1 A2 x (v1 : A1) (v2 : A2) h1 h2 :
valid (x :-> v1 \+ h1) ->
x :-> v1 \+ h1 = x :-> v2 \+ h2 -> A1 = A2.
Lemma path_filter (A : ordType) (s : seq A) (p : pred A) x :
path ord x s -> path ord x (filter p s).
Lemma dom_fresh h n : (fresh h).+n \notin dom h.
Lemma fresh_null h : fresh h != null.
Lemma pickP h : valid h && ~~ empb h = (pick h \in dom h).
(***********************)
(* Some derived lemmas *)
(***********************)
Lemma domPtUnX A (v : A) x i : valid (x :-> v \+ i) -> x \in dom (x :-> v \+ i).
Lemma updi_cat x vs1 vs2 :
updi x (vs1 ++ vs2) = updi x vs1 \+ updi x.+(size vs1) vs2.
Lemma updi_catI x y vs1 vs2 :
y = x.+(size vs1) -> updi x vs1 \+ updi y vs2 = updi x (vs1 ++ vs2).
Lemma updiD x xs : valid (updi x xs) = (x != null) || (size xs == 0).
Lemma updiVm x m xs :
x \in dom (updi x.+m xs) = [&& x != null, m == 0 & size xs > 0].
Lemma updimV x m xs :
x.+m \in dom (updi x xs) = (x != null) && (m < size xs).
Lemma updiP x y xs :
reflect (y != null /\ exists m, x = y.+m /\ m < size xs)
(x \in dom (updi y xs)).
(* Invertibility *)
Lemma updi_inv x xs1 xs2 :
valid (updi x xs1) -> updi x xs1 = updi x xs2 -> xs1 = xs2.
Lemma updi_iinv x xs1 xs2 h1 h2 :
size xs1 = size xs2 -> valid (updi x xs1 \+ h1) ->
updi x xs1 \+ h1 = updi x xs2 \+ h2 -> xs1 = xs2 /\ h1 = h2.