Definition pred2p (p: preds) : fpreds (pred rmap) :=
match p with SomeP A P => existT _ A P end.
Definition p2pred (p: fpreds (pred rmap)) : preds :=
match p with existT A P => SomeP A P end.
Definition ghost2g (r: ghost): SM.ghost (pred rmap) :=
map (option_map (fun '(a, b) => (a, pred2p b))) r.
Definition g2ghost (r: SM.ghost (pred rmap)) : ghost :=
map (option_map (fun '(a, b) => (a, p2pred b))) r.

(* Specifications: *)
Lemma g2ghost2g: forall x, ghost2g (g2ghost x) = x.
Lemma ghost2g2ghost: forall x, g2ghost (ghost2g x) = x.
Inductive res_join : resource -> resource -> resource -> Prop :=
| res_join_NO1 : forall sh1 nsh1 sh2 nsh2 sh3 nsh3
(RJ: join sh1 sh2 sh3),
res_join (NO sh1 nsh1) (NO sh2 nsh2) (NO sh3 nsh3)
| res_join_NO2 : forall sh1 rsh1 sh2 nsh2 sh3 rsh3 k p
(RJ: join sh1 sh2 sh3),
res_join (YES sh1 rsh1 k p) (NO sh2 nsh2) (YES sh3 rsh3 k p)
| res_join_NO3 : forall sh1 nsh1 sh2 rsh2 sh3 rsh3 k p
(RJ: join sh1 sh2 sh3),
res_join (NO sh1 nsh1) (YES sh2 rsh2 k p) (YES sh3 rsh3 k p)
| res_join_YES : forall sh1 rsh1 sh2 rsh2 sh3 rsh3 k p
(RJ: join sh1 sh2 sh3),
res_join (YES sh1 rsh1 k p) (YES sh2 rsh2 k p) (YES sh3 rsh3 k p)
| res_join_PURE : forall k p, res_join (PURE k p) (PURE k p) (PURE k p).