Add umutex APIs.
This commit is contained in:
parent
3cac7b5ddb
commit
77e7cda2cf
@ -61,6 +61,52 @@ __thr_umtx_unlock(volatile umtx_t *mtx, long id)
|
||||
return (errno);
|
||||
}
|
||||
|
||||
int
|
||||
__thr_umutex_lock(struct umutex *mtx, uint32_t id)
|
||||
{
|
||||
if (_umtx_op(mtx, UMTX_OP_MUTEX_LOCK, 0, 0, 0) == 0)
|
||||
return 0;
|
||||
return (errno);
|
||||
}
|
||||
|
||||
int
|
||||
__thr_umutex_timedlock(struct umutex *mtx, uint32_t id,
|
||||
const struct timespec *timeout)
|
||||
{
|
||||
if (timeout && (timeout->tv_sec < 0 || (timeout->tv_sec == 0 &&
|
||||
timeout->tv_nsec <= 0)))
|
||||
return (ETIMEDOUT);
|
||||
if (_umtx_op(mtx, UMTX_OP_MUTEX_LOCK, 0, 0,
|
||||
__DECONST(void *, timeout)) == 0)
|
||||
return (0);
|
||||
return (errno);
|
||||
}
|
||||
|
||||
int
|
||||
__thr_umutex_unlock(struct umutex *mtx, uint32_t id)
|
||||
{
|
||||
if (_umtx_op(mtx, UMTX_OP_MUTEX_UNLOCK, 0, 0, 0) == 0)
|
||||
return (0);
|
||||
return (errno);
|
||||
}
|
||||
|
||||
int
|
||||
__thr_umutex_kern_trylock(struct umutex *mtx)
|
||||
{
|
||||
if (_umtx_op(mtx, UMTX_OP_MUTEX_TRYLOCK, 0, 0, 0) == 0)
|
||||
return (0);
|
||||
return (errno);
|
||||
}
|
||||
|
||||
int
|
||||
__thr_umutex_set_ceiling(struct umutex *mtx, uint32_t ceiling,
|
||||
uint32_t *oldceiling)
|
||||
{
|
||||
if (_umtx_op(mtx, UMTX_OP_SET_CEILING, ceiling, oldceiling, 0) == 0)
|
||||
return (0);
|
||||
return (errno);
|
||||
}
|
||||
|
||||
int
|
||||
_thr_umtx_wait(volatile umtx_t *mtx, long id, const struct timespec *timeout)
|
||||
{
|
||||
|
@ -33,11 +33,21 @@
|
||||
|
||||
typedef long umtx_t;
|
||||
|
||||
/* simple lock routines.*/
|
||||
int __thr_umtx_lock(volatile umtx_t *mtx, long id) __hidden;
|
||||
int __thr_umtx_timedlock(volatile umtx_t *mtx, long id,
|
||||
const struct timespec *timeout) __hidden;
|
||||
int __thr_umtx_unlock(volatile umtx_t *mtx, long id) __hidden;
|
||||
|
||||
/* POSIX semantic lock routines */
|
||||
int __thr_umutex_lock(struct umutex *mtx, uint32_t id) __hidden;
|
||||
int __thr_umutex_timedlock(struct umutex *mtx, uint32_t id,
|
||||
const struct timespec *timeout) __hidden;
|
||||
int __thr_umutex_unlock(struct umutex *mtx, uint32_t id) __hidden;
|
||||
int __thr_umutex_kern_trylock(struct umutex *mtx) __hidden;
|
||||
int __thr_umutex_set_ceiling(struct umutex *mtx, uint32_t ceiling,
|
||||
uint32_t *oldceiling) __hidden;
|
||||
|
||||
static inline void
|
||||
_thr_umtx_init(volatile umtx_t *mtx)
|
||||
{
|
||||
@ -84,4 +94,40 @@ _thr_umtx_unlock(volatile umtx_t *mtx, long id)
|
||||
int _thr_umtx_wait(volatile umtx_t *mtx, umtx_t exp,
|
||||
const struct timespec *timeout) __hidden;
|
||||
int _thr_umtx_wake(volatile umtx_t *mtx, int count) __hidden;
|
||||
|
||||
static inline int
|
||||
_thr_umutex_trylock(struct umutex *mtx, uint32_t id)
|
||||
{
|
||||
if (atomic_cmpset_acq_32(&mtx->m_owner, UMUTEX_UNOWNED, id))
|
||||
return (0);
|
||||
if ((mtx->m_flags & UMUTEX_PRIO_PROTECT) == 0)
|
||||
return (EBUSY);
|
||||
return (__thr_umutex_kern_trylock(mtx));
|
||||
}
|
||||
|
||||
static inline int
|
||||
_thr_umutex_lock(struct umutex *mtx, uint32_t id)
|
||||
{
|
||||
if (atomic_cmpset_acq_32(&mtx->m_owner, UMUTEX_UNOWNED, id))
|
||||
return (0);
|
||||
return (__thr_umutex_lock(mtx, id));
|
||||
}
|
||||
|
||||
static inline int
|
||||
_thr_umutex_timedlock(struct umutex *mtx, uint32_t id,
|
||||
const struct timespec *timeout)
|
||||
{
|
||||
if (atomic_cmpset_acq_32(&mtx->m_owner, UMUTEX_UNOWNED, id))
|
||||
return (0);
|
||||
return (__thr_umutex_timedlock(mtx, id, timeout));
|
||||
}
|
||||
|
||||
static inline int
|
||||
_thr_umutex_unlock(struct umutex *mtx, uint32_t id)
|
||||
{
|
||||
if (atomic_cmpset_rel_32(&mtx->m_owner, id, UMUTEX_UNOWNED))
|
||||
return (0);
|
||||
return (__thr_umutex_unlock(mtx, id));
|
||||
}
|
||||
|
||||
#endif
|
||||
|
Loading…
Reference in New Issue
Block a user