Definition sourceN (n:block) (j:meminj) (m:mem)
(b2:block) (ofs2:Z): option(block * Z) :=
Pos.peano_rect
(fun p => option(block * Z))
(match isSource j m b2 ofs2 1%positive
with Some ofs1 => Some(1%positive, ofs1)
| None => None
end)
(fun p Hp => match isSource j m b2 ofs2 (Pos.succ p)
with Some ofs1 => Some (Pos.succ p, ofs1)
| None => Hp
end)
n.

(* Specifications: *)
Lemma sourceN_SomeE: forall j m b2 ofs2 n b1 ofs1,
sourceN n j m b2 ofs2 = Some(b1,ofs1) ->
exists delta, (b1 <= n)%positive /\ j b1 = Some(b2,delta) /\
Mem.perm m b1 ofs1 Max Nonempty /\ ofs2=ofs1+delta.
Lemma sourceN_NoneE: forall j m b2 ofs2 n,
sourceN n j m b2 ofs2 = None ->
forall b1 delta, (b1 <= n)%positive -> j b1 = Some(b2,delta) ->
~ Mem.perm m b1 (ofs2-delta) Max Nonempty.
Lemma sourceN_SomeI: forall n j m b2 b1 ofs1 delta (OV:Mem.meminj_no_overlap j m),
j b1 = Some(b2,delta) -> Mem.perm m b1 ofs1 Max Nonempty ->
(b1 <= n)%positive ->
sourceN n j m b2 (ofs1+delta) = Some(b1,ofs1).
Lemma sourceN_SomeE: forall j m b2 ofs2 n b1 ofs1,
sourceN n j m b2 ofs2 = Some(b1,ofs1) ->
exists delta, (b1 <= n)%positive /\ j b1 = Some(b2,delta) /\
Mem.perm m b1 ofs1 Max Nonempty /\ ofs2=ofs1+delta.
Lemma sourceN_NoneE: forall j m b2 ofs2 n,
sourceN n j m b2 ofs2 = None ->
forall b1 delta, (b1 <= n)%positive -> j b1 = Some(b2,delta) ->
~ Mem.perm m b1 (ofs2-delta) Max Nonempty.
Lemma sourceN_SomeI: forall n j m b2 b1 ofs1 delta (OV:Mem.meminj_no_overlap j m),
j b1 = Some(b2,delta) -> Mem.perm m b1 ofs1 Max Nonempty ->
(b1 <= n)%positive ->
sourceN n j m b2 (ofs1+delta) = Some(b1,ofs1).