123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107open!Baseopen!ImportmoduleCapsule=Capsule.PrimmoduletypeS=sig@@portable(** Condition variable for waiting for changes to state protected by a lock. *)type'klock(** ['k t] is the type of a condition variable associated with the capsule ['k]. This
condition may only be used with the matching ['k lock]. *)type'kt:valuemodcontendedforkablemanyportableunyieldingmoduleWait:sig(** A value of type ['k Condition.Wait.t] provides the local ability to wait on a
condition variable associated with the capsule ['k] *)type'kt:valuemodnon_floatportablewith'klock(** [release_temporarily cw key ~f] temporarily releases the lock associated with
[cw], runs [f] with the lock {i not} held, re-acquires the lock, and then returns
the result of [f] along with the key for the capsule.
If [f] raises an exception, the lock will {i not} be poisoned.
@raise Poisoned if [t] cannot be reacquired because it is otherwise poisoned.
@raise Frozen if [t] cannot be reacquired because it is frozen.
@raise Terminated if [w] is terminated before the lock is reacquired. *)val%templaterelease_temporarily:'kt@local->'kCapsule.Key.t@unique->f:(Await.t@local->'a@lonceunique)@localonce->#('a*'kCapsule.Key.t)@lonceunique[@@model=(global,local)]end(** [create ()] creates a new condition variable associated with the matching ['k lock]
and with a certain property {i P} that is protected by the lock.
The optional [padded] argument specifies whether to pad the data structure to avoid
false sharing. See {!Atomic.make} for a longer explanation. *)valcreate:?padded:bool@local->unit->'kt(** [wait w t key] atomically releases the lock associated with [cw] and blocks on the
condition variable [t]. To ensure exception safety, it takes hold of the ['k Key.t]
associated with the lock.
[wait] returns with the [lock] reacquired once the condition variable [t] has been
signaled via {!signal} or {!broadcast}. [wait] may also return for no reason -
callers cannot assume that the property {i P} associated with the condition variable
[c] holds when [wait] returns.
@raise Poisoned if [t] cannot be reacquired because it is poisoned.
@raise Frozen if [t] cannot be reacquired because it is frozen.
@raise Terminated if [w] is terminated before the lock is reacquired. *)valwait:'kWait.t@local->'kt@local->'kCapsule.Key.t@unique->'kCapsule.Key.t@unique(** [signal t] wakes up one waiter on the condition variable [t], if there is one. If
there is none, this call has no effect. It is recommended to call [signal t] after a
critical section - that is, after the lock associated with [t] has been acquired,
the condition for signaling has been confirmed, and the lock is released. *)valsignal:'kt@local->unit(** [broadcast t] wakes up all waiters on the condition variable [t]. If there are none,
this call has no effect. It is recommended to call [broadcast t] after a critical
section, that is, after the lock associated with [t] has been acquired, the
condition for broadcasting has been confirmed, and the lock released. *)valbroadcast:'kt@local->unitend(** The private interface to condition variables, used by implementations of locks. Not
exposed outside of this library. *)moduletypeS_private=sig@@portableincludeS(*_ These two functions might ostensibly be nicer to define in the Wait module, but
overriding submodules in module types is cumbersome, and it's an internal interface
so it doesn't matter as much *)(** This function must be called with the lock held, and takes the key to prove that *)val%templatewith_wait:('r:value_or_null).Await.t@local->'klock@local->'kCapsule.Key.t@unique->('kWait.t@local->'kCapsule.Key.t@unique->'r@lonceunique)@localonce->'r@lonceunique[@@model=(global,local)]vallock_is_held:'kWait.t@local->boolendmoduletypeArg=sig@@portabletype'ktvalunsafe_acquire:Await.t@local->'kt@local->unitvalunsafe_release:'kt@local->unitendmoduletypeCondition=sig@@portablemoduletypeS=SmoduleMake(Lock:Arg):S_privatewithtype'klock:='kLock.tend