Definition Ynode_add_spec :=
DECLARE _Ynode_add
WITH p: val, t: YTree
PRE  [ _p OF (tptr t_struct_Ynode) ]
PROP  ()
LOCAL (temp _p p)
SEP (ytree_rep t p)
POST [ Tvoid ]
PROP()
LOCAL()
SEP (ytree_rep (y_add1 t) p).
Definition YTree_add_spec :=
DECLARE _YTree_add
WITH p: val, t: tree (unit * YTree)
PRE  [ _p OF (tptr t_struct_Ytree) ]
PROP  ()
LOCAL (temp _p p)
SEP (t_ytree_rep t p)
POST [ Tvoid ]
PROP()
LOCAL()
SEP (t_ytree_rep (ty_add1 t) p).
Definition YList_add_spec :=
DECLARE _YList_add
WITH p: val, t: list (tree (unit * YTree) * unit)
PRE  [ _p OF (tptr t_struct_Ylist) ]
PROP  ()
LOCAL (temp _p p)
SEP (lt_ytree_rep t p)
POST [ Tvoid ]
PROP()
LOCAL()
SEP (lt_ytree_rep (lty_add1 t) p).
Definition main_spec :=
DECLARE _main
WITH gv : globals
PRE  [] main_pre prog nil gv
POST [ tint ]
PROP() LOCAL () SEP(TT).
Definition Gprog : funspecs :=
ltac:(with_library prog
[Xnode_add_spec; Xfoo_spec; Ynode_add_spec; YList_add_spec; YTree_add_spec; main_spec]).
Module GeneralLseg.
Section GeneralLseg.
Context {V: Type}.
Variable listrep: list V -> val -> mpred.
Definition lseg (contents: list V) (x z: val) : mpred :=
ALL tcontents: list V, listrep tcontents z -* listrep (contents ++ tcontents) x.

(* Specifications: *)
Lemma emp_lseg_nil: forall (x: val),
emp |-- lseg nil x x.
Lemma lseg_lseg: forall (s1 s2: list V) (x y z: val),
lseg s2 y z * lseg s1 x y |-- lseg (s1 ++ s2) x z.
Lemma list_lseg: forall (s1 s2: list V) (x y: val),
listrep s2 y * lseg s1 x y |-- listrep (s1 ++ s2) x.