(*Some (ThreadPool.getThreadR Htid, virtue1)*)
(*Some virtue2*)

Lemma free_step_diagram:
forall (U : list nat) (tr1 tr2 : HybridMachineSig.event_trace)
(st1 : ThreadPool (Some hb)) (m1' : mem)
(tid : nat) (cd : option compiler_index)
(st2 : ThreadPool (Some (S hb))) (mu : meminj)
(m2 : mem) (Htid : ThreadPool.containsThread st1 tid)
(c : semC) (b : block) (ofs : Integers.Ptrofs.int)
(pmap_tid' : access_map * access_map)
(pdata : nat -> option permission) (rmap : lock_info),
concur_match cd mu st1 m1' st2 m2 ->
List.Forall2 (inject_mevent mu) tr1 tr2 ->
forall Hcmpt : mem_compatible st1 m1',
HybridMachineSig.schedPeek U = Some tid ->
bounded_maps.bounded_nat_func' pdata LKSIZE_nat ->
invariant st1 ->
ThreadPool.getThreadC Htid = Kblocked c ->
semantics.at_external
(semantics.csem (event_semantics.msem semSem)) c
(restrPermMap (fst (ssrfun.pair_of_and (Hcmpt tid Htid)))) =
Some (FREE_LOCK, (Vptr b ofs :: nil)%list) ->
ThreadPool.lockRes st1 (b, Integers.Ptrofs.intval ofs) =
Some rmap ->
(forall (b0 : BinNums.positive) (ofs0 : BinNums.Z),
(fst rmap) !! b0 ofs0 = None /\ (snd rmap) !! b0 ofs0 = None) ->
Mem.range_perm
(restrPermMap (snd (ssrfun.pair_of_and (Hcmpt tid Htid)))) b
(Integers.Ptrofs.intval ofs)
(BinInt.Z.add (Integers.Ptrofs.intval ofs) LKSIZE) Cur Writable ->
setPermBlock None b (Integers.Ptrofs.intval ofs)
(snd (ThreadPool.getThreadR Htid)) LKSIZE_nat =
snd pmap_tid' ->
(forall i : nat,
BinInt.Z.le 0 (BinInt.Z.of_nat i) /\
BinInt.Z.lt (BinInt.Z.of_nat i) LKSIZE ->
Mem.perm_order'' (pdata (S i)) (Some Writable)) ->
setPermBlock_var pdata b (Integers.Ptrofs.intval ofs)
(fst (ThreadPool.getThreadR Htid)) LKSIZE_nat =
fst pmap_tid' ->
exists
e' (st2' : t) (m2' : mem) (cd' : option compiler_index)
(mu' : meminj),
concur_match cd' mu'
(ThreadPool.remLockSet
(ThreadPool.updThread Htid (Kresume c Vundef) pmap_tid')
(b, Integers.Ptrofs.intval ofs)) m1' st2' m2' /\
List.Forall2 (inject_mevent mu') (seq.cat tr1 (Events.external tid (Events.freelock (b, Integers.Ptrofs.intval ofs)) :: nil))
(seq.cat tr2 (Events.external tid e' :: nil)) /\
HybridMachineSig.external_step
(scheduler:=HybridMachineSig.HybridCoarseMachine.scheduler)
U tr2 st2 m2
(HybridMachineSig.schedSkip U)
(seq.cat tr2 (Events.external tid e' :: nil)) st2' m2'.