Hint Resolve trace_erasure_cat trace_erasure_map : trace_erasure.
Hint Constructors trace_erasure event_erasure : trace_erasure.
End TraceErasure.
(** ** Memory Erasure*)
Module MemErasure.
(** The values of the erased memory may be more defined and its permissions are top.*)
(** In retrospect setting the permissions to top was a bad choice. It should have been that the permissions of the erased memory are above the permissions of the other memory. This would make it more reusable and it wouldn't need a second definition for free. *)
Local Notation "a # b" := (PMap.get b a) (at level 1).
Record mem_erasure (m m': mem) :=
{ perm_le:
forall b ofs k,
Mem.valid_block m' b ->
(Mem.mem_access m')#b ofs k = Some Freeable;
erased_contents: forall b ofs,
memval_erasure (ZMap.get ofs ((Mem.mem_contents m) # b))
(ZMap.get ofs ((Mem.mem_contents m') # b));
erased_nb: Mem.nextblock m = Mem.nextblock m'
}.

(* Specifications: *)
Lemma mem_erasure_restr:
forall m m' pmap (Hlt: permMapLt pmap (getMaxPerm m)),
mem_erasure m m' ->
mem_erasure (restrPermMap Hlt) m'.
Lemma mem_erasure_dilute_1:
forall m m',
mem_erasure m m' ->
mem_erasure (setMaxPerm m) m'.
Lemma getN_erasure:
forall m1 m2 b
(Herase: forall (b : positive) (ofs : ZIndexed.t),
memval_erasure (ZMap.get ofs (Mem.mem_contents m1) # b)
(ZMap.get ofs (Mem.mem_contents m2) # b)),
forall n ofs,
memval_erasure_list
(Mem.getN n ofs (m1.(Mem.mem_contents)#b))
(Mem.getN n ofs (m2.(Mem.mem_contents)#b)).
Lemma proj_bytes_erasure:
forall vl vl',
memval_erasure_list vl vl' ->
forall bl,
proj_bytes vl = Some bl ->
proj_bytes vl' = Some bl.
Lemma proj_bytes_not_erasure:
forall vl vl',
memval_erasure_list vl vl' ->
proj_bytes vl = None -> proj_bytes vl' <> None -> In Undef vl.
Lemma check_value_erasure:
forall vl vl',
memval_erasure_list vl vl' ->
forall v v' q n,
check_value n v q vl = true ->
val_erasure v v' -> v <> Vundef ->
check_value n v' q vl' = true.
Lemma proj_value_erasure:
forall q vl1 vl2,
memval_erasure_list vl1 vl2 ->
val_erasure (proj_value q vl1) (proj_value q vl2).
Lemma load_result_erasure:
forall chunk v1 v2,
val_erasure v1 v2 ->
val_erasure (Val.load_result chunk v1) (Val.load_result chunk v2).
Lemma decode_val_erasure:
forall vl1 vl2 chunk,
memval_erasure_list vl1 vl2 ->
val_erasure (decode_val chunk vl1) (decode_val chunk vl2).
Lemma mem_load_erased:
forall chunk m m' b ofs v
(Hload: Mem.load chunk m b ofs = Some v)
(Herased: mem_erasure m m'),
exists v',
Mem.load chunk m' b ofs = Some v' /\
val_erasure v v'.
Lemma setN_erasure :
forall (vl1 vl2 : seq.seq memval),
memval_erasure_list vl1 vl2 ->
forall (p : Z) (c1 c2 : ZMap.t memval),
(forall q : Z,
memval_erasure (ZMap.get q c1) (ZMap.get q c2)) ->
forall q : Z,
memval_erasure (ZMap.get q (Mem.setN vl1 p c1))
(ZMap.get q (Mem.setN vl2 p c2)).
Lemma mem_store_erased:
forall chunk m m' b ofs v v' m2
(Hstore: Mem.store chunk m b ofs v = Some m2)
(Herased: mem_erasure m m')
(Hval_erasure: val_erasure v v') ,
exists m2', Mem.store chunk m' b ofs v' = Some m2'
/\ mem_erasure m2 m2'.
Lemma mem_loadv_erased:
forall chunk m m' vptr v
(Hload: Mem.loadv chunk m vptr = Some v)
(Herased: mem_erasure m m'),
exists v',
Mem.loadv chunk m' vptr = Some v' /\
val_erasure v v'.
Lemma mem_storev_erased:
forall chunk m m' vptr v v' m2
(Hstore: Mem.storev chunk m vptr v = Some m2)
(Herased: mem_erasure m m')
(Hval_erasure: val_erasure v v') ,
exists m2', Mem.storev chunk m' vptr v' = Some m2'
/\ mem_erasure m2 m2'.
Lemma mem_erasure_valid_pointer:
forall m m' b ofs,
mem_erasure m m' ->
Mem.valid_pointer m b ofs ->
Mem.valid_pointer m' b ofs.
Lemma mem_erasure_valid_pointer_guard:
forall m m' b ofs ofs',
mem_erasure m m' ->
Mem.valid_pointer m' b ofs
|| Mem.valid_pointer m' b ofs' = false ->
Mem.valid_pointer m b ofs
|| Mem.valid_pointer m b ofs'= false.
Lemma val_erasure_cmpu:
forall v1 v2 v1' v2' m m' cmp
(Hval_erasure: val_erasure v1 v1')
(Hval_erasure2: val_erasure v2 v2')
(Hmem: mem_erasure m m'),
val_erasure (Val.cmpu (Mem.valid_pointer m) cmp v1 v2)
(Val.cmpu (Mem.valid_pointer m') cmp v1' v2').