Section MEMORY_CONSTRUCTION_II.
Variable j12 j23 j12' j23':meminj.
Variable m1 m1' m2 : mem.
Definition AccessMap_II_FUN (b2:block):
Z -> perm_kind -> option permission :=
if plt b2 (Mem.nextblock m2)
then (fun ofs2 k =>
match j23 b2 with
None => PMap.get b2 m2.(Mem.mem_access) ofs2 k
| Some (b3,d3) =>
match source j12 m1 b2 ofs2 with
Some(b1,ofs1) => PMap.get b1 m1'.(Mem.mem_access) ofs1 k
| None => PMap.get b2 m2.(Mem.mem_access) ofs2 k
end
end)
else (fun ofs2 k =>
match source j12' m1' b2 ofs2 with
Some(b1,ofs1) => PMap.get b1 m1'.(Mem.mem_access) ofs1 k
| None => None
end).
Definition ContentMap_II_ValidBlock_FUN b2 ofs2: memval :=
match source j12 m1 b2 ofs2 with
Some(b1,ofs1) =>
match j23' b2 with
None => ZMap.get ofs2 (PMap.get b2 m2.(Mem.mem_contents))
| Some(b3,ofs3) =>
inject_memval j12'
(ZMap.get ofs1 (PMap.get b1 m1'.(Mem.mem_contents)))
end
| None => ZMap.get ofs2 (PMap.get b2 m2.(Mem.mem_contents))
end.
Definition ContentMap_II_InvalidBlock_FUN b2 ofs2: memval :=
match source j12' m1' b2 ofs2 with
None => Undef
| Some(b1,ofs1) =>
inject_memval j12'
(ZMap.get ofs1 (PMap.get b1 m1'.(Mem.mem_contents)))
end.
Definition ContentMap_II_Block_FUN b ofs : memval:=
if plt b (Mem.nextblock m2)
then ContentMap_II_ValidBlock_FUN b ofs
else ContentMap_II_InvalidBlock_FUN b ofs.
Variable MINMAX_Offset: block -> option (Z * Z).
Hypothesis MINMAX: forall b2 ,
match MINMAX_Offset b2 with
Some(mn,mx) =>
(forall ofs, ofs < mn \/ ofs > mx ->
Plt b2 (Mem.nextblock m2) ->
ZMap.get ofs (Mem.mem_contents m2)!!b2 = Undef) /\
forall b1 delta, j12 b1 = Some(b2,delta) \/ j12' b1 = Some(b2,delta)->
forall z, z + delta < mn \/ z + delta > mx ->
ZMap.get z (Mem.mem_contents m1')!!b1 = Undef
| None =>
(Plt b2 (Mem.nextblock m2) ->
forall ofs, ZMap.get ofs (Mem.mem_contents m2)!!b2 = Undef)
/\
forall b1 delta, j12 b1 = Some(b2,delta) \/ j12' b1 = Some(b2,delta)->
forall z, ZMap.get z (Mem.mem_contents m1')!!b1 = Undef
end.
Definition ContentsMap_II_FUN
(NB2':block)
(b:block):
ZMap.t memval.
destruct (plt b NB2').
apply (CM_block_II_existsT b).
apply (ZMap.init Undef).
Defined.
Definition mkII
(NB2':block)
(Hyp1: (Mem.nextblock m2 <= NB2')%positive)
(Hyp2: forall (b1 b2 : block) (delta : Z),
j12' b1 = Some (b2, delta) -> (b2 < NB2')%positive)
: Mem.mem'.
destruct (mkAccessMap_II_existsT NB2' Hyp1 Hyp2) as [AM [ADefault PAM]].
destruct (ContentsMap_II_existsT NB2') as [CM [CDefault PCM]].
eapply Mem.mkmem with (nextblock:=NB2')
(mem_access:=AM)
(mem_contents:=CM).
(*access_max*)
intros. rewrite PAM. unfold AccessMap_II_FUN.
destruct (plt b (Mem.nextblock m2)).
(*valid_block m2 b*)
destruct (j23 b).
destruct p0.
remember (source j12 m1 b ofs) as src.
destruct src.
destruct p0. apply m1'.
apply m2.
apply m2.
(*invalid_block m2 b*)
remember (source j12' m1' b ofs) as src.
destruct src.
destruct p. apply m1'.
reflexivity.
(*nextblock_noaccess*)
intros. rewrite PAM.
unfold AccessMap_II_FUN.
destruct (plt b (Mem.nextblock m2)).
exfalso. apply H; clear - Hyp1 p. xomega.
remember (source j12' m1' b ofs) as src.
destruct src; trivial.
destruct p.
exfalso. apply H. clear - Heqsrc Hyp2.
apply source_SomeE in Heqsrc.
destruct Heqsrc as [b1 [delta [ofs1
[PBO [Bounds [J1 [P1 Off2]]]]]]]; subst.
apply (Hyp2 _ _ _ J1).
(*contents_default*)
intros.
rewrite PCM; clear PCM.
unfold ContentsMap_II_FUN.
destruct (plt b NB2').
remember (CM_block_II_existsT b).
destruct s. apply a.
reflexivity.
Defined.
End MEMORY_CONSTRUCTION_II.
Definition minmax_at (m:mem) (j:meminj) (b2 b1: block) : option(Z * Z) :=
match j b1
with Some (b,delta) =>
if peq b b2
then match (zmap_finite_c _ (PMap.get b1 m.(Mem.mem_contents)))
with (mn,mx) => Some(mn+delta,mx+delta)
end
else None
| None => None
end.
Definition minmaxN (n:block) (m:mem) (j:meminj) (b2:block) : option (Z * Z):=
Pos.peano_rect
(fun p => option(Z * Z))
(minmax_at m j b2 (1%positive))
(fun p Hp =>
match minmax_at m j b2 (Pos.succ p)
with Some(min1,max1) =>
match Hp with
Some(min2, max2) => Some (Zmin min1 min2, Zmax max1 max2)
| None => Some(min1,max1)
end
| None => Hp
end)
n.
Definition minmax m j (b2:block): option(Z * Z) :=
if plt 1%positive (Mem.nextblock m)
then minmaxN (Pos.pred (Mem.nextblock m)) m j b2
else None.

Lemma minmax_sound: forall m j b2,
match minmax m j b2
with Some(mn,mx) =>
forall b1 delta, (b1 < Mem.nextblock m)%positive ->
j b1 = Some(b2,delta) ->
forall z, z + delta < mn \/ z + delta > mx ->
ZMap.get z (Mem.mem_contents m)!!b1 = Undef
| None => forall b1 delta, (b1 < Mem.nextblock m)%positive ->
j b1 = Some(b2,delta) ->
forall z, ZMap.get z (Mem.mem_contents m)!!b1 = Undef
end.