(**************************************************************************)
(*                            Syntactic heaps                             *)
(* Pointers and heap variables are syntactified as indices in the context *)
(* Disjoint union is syntactified as concatenation of lists               *)
(**************************************************************************)
Definition synheap := seq elem.
(*****************************************************************************)
(* Validity of indices:                                                      *)
(*   valid i t  iif all the indices in t are in bounds of the contexts lists *)
(*****************************************************************************)
Fixpoint valid_ptrs i t :=
match t with
Pts sx _ :: s => (sx < size (ptr_ctx i)) && valid_ptrs i s
| Var _ :: s => valid_ptrs i s
| _ => true
end.
Fixpoint valid_heaps i t :=
match t with
Pts _ _ :: s => valid_heaps i s
| Var v :: s => (v < size (heap_ctx i)) && valid_heaps i s
| _ => true
end.
Definition valid i t := valid_ptrs i t && valid_heaps i t.

(* Specifications: *)
Lemma valid_cons i e t : valid i (e :: t) = valid i [:: e] && valid i t.
Lemma valid_ptrs_cat j t1 t2 :
valid_ptrs j (t1 ++ t2) = valid_ptrs j t1 && valid_ptrs j t2.
Lemma valid_heaps_cat j t1 t2 :
valid_heaps j (t1 ++ t2) = valid_heaps j t1 && valid_heaps j t2.
Lemma valid_cat j t1 t2 : valid j (t1 ++ t2) = valid j t1 && valid j t2.
Lemma valid_subctx i j t : subctx i j -> valid i t -> valid j t.
Definition hlook := [fun i => onth (heap_ctx i)].