darwin-kernel-rwlocks-20081023

LICENSE IPL10

convert to kernel rwlocks on darwin
This commit is contained in:
Derrick Brashear 2008-10-24 22:07:01 +00:00
parent e73e2ff4b5
commit 069cd726c0
2 changed files with 114 additions and 49 deletions

View File

@ -35,6 +35,7 @@ RCSID
#endif /* defined(AFS_DARWIN70_ENV) */
lck_grp_t * openafs_lck_grp;
lck_grp_t * openafs_rw_grp;
static lck_grp_attr_t * openafs_lck_grp_attr;
void rx_kmutex_setup(void) {
openafs_lck_grp_attr= lck_grp_attr_alloc_init();
@ -43,10 +44,13 @@ void rx_kmutex_setup(void) {
openafs_lck_grp = lck_grp_alloc_init("openafs", openafs_lck_grp_attr);
lck_grp_attr_free(openafs_lck_grp_attr);
openafs_rw_grp = lck_grp_alloc_init("openafs-rw", openafs_lck_grp_attr);
lck_grp_attr_free(openafs_lck_grp_attr);
}
void rx_kmutex_finish(void) {
lck_grp_free(openafs_lck_grp);
lck_grp_free(openafs_rw_grp);
}
#endif

View File

@ -18,6 +18,9 @@
#ifdef AFS_DARWIN80_ENV
#include <kern/locks.h>
/* kernel private from osfmk/kern/locks.h ... sigh */
extern boolean_t lck_mtx_try_lock(lck_mtx_t *lck);
extern boolean_t lck_rw_try_lock(lck_rw_t *lck, lck_rw_type_t lck_rw_type);
#else
#include <sys/lock.h>
#endif
@ -52,9 +55,7 @@
if (isGlockOwner) AFS_GUNLOCK(); \
osi_Assert((lck)->owner == current_thread()); \
(lck)->owner = (thread_t)0; \
lck_mtx_lock((lck)->meta); \
(lck)->waiters--; \
lck_mtx_unlock((lck)->meta); \
OSAtomicDecrement32Barrier((lck)->waiters); \
msleep(cv, (lck)->lock, PDROP|PVFS, "afs_CV_WAIT", NULL); \
if (isGlockOwner) AFS_GLOCK(); \
MUTEX_ENTER(lck); \
@ -68,9 +69,7 @@
if (isGlockOwner) AFS_GUNLOCK(); \
osi_Assert((lck)->owner == current_thread()); \
(lck)->owner = (thread_t)0; \
lck_mtx_lock((lck)->meta); \
(lck)->waiters--; \
lck_mtx_unlock((lck)->meta); \
OSAtomicDecrement32Barrier((lck)->waiters); \
msleep(cv, (lck)->lock, PDROP|PVFS, "afs_CV_TIMEDWAIT", &ts); \
if (isGlockOwner) AFS_GLOCK(); \
MUTEX_ENTER(lck); \
@ -124,74 +123,136 @@
#ifdef AFS_DARWIN80_ENV
typedef struct {
lck_mtx_t *meta;
int waiters; /* also includes anyone holding the lock */
lck_mtx_t *lock;
thread_t owner;
} afs_kmutex_t;
typedef int afs_kcondvar_t;
typedef struct {
int readers;
lck_mtx_t *lock;
thread_t owner;
} afs_krwlock_t;
extern lck_grp_t * openafs_lck_grp;
extern lck_grp_t * openafs_rw_grp;
#define RWLOCK_UPLOCK(a) \
do { \
osi_Assert((a)->owner != current_thread()); \
lck_rw_lock_shared_to_exclusive((a)->lock); \
osi_Assert((a)->owner == (thread_t)0); \
(a)->owner = current_thread(); \
OSAtomicDecrement32Barrier((a)->readers); \
} while(0)
#define RWLOCK_INIT(a,b,c,d) \
do { \
lck_attr_t *openafs_lck_attr = lck_attr_alloc_init(); \
(a)->lock = lck_rw_alloc_init(openafs_rw_grp, openafs_lck_attr); \
lck_attr_free(openafs_lck_attr); \
(a)->readers = 0; \
(a)->owner = (thread_t)0; \
} while(0)
#define RWLOCK_DESTROY(a) \
do { \
lck_rw_destroy((a)->lock, openafs_rw_grp); \
(a)->owner = (thread_t)-1; \
} while(0)
#define RWLOCK_RDLOCK(a) \
do { \
OSAtomicIncrement32Barrier((a)->readers); \
lck_rw_lock_shared((a)->lock); \
} while(0)
#define RWLOCK_WRLOCK(a) \
do { \
osi_Assert((a)->owner != current_thread()); \
lck_rw_lock_exclusive((a)->lock); \
osi_Assert((a)->owner == (thread_t)0); \
(a)->owner = current_thread(); \
} while(0)
/* acquire main lock before releasing meta lock, so we don't race */
#define RWLOCK_TRYRDLOCK(a) ({ \
int _ret; \
_ret = lck_rw_try_lock((a)->lock, LCK_RW_TYPE_SHARED); \
if (_ret) { \
OSAtomicIncrement32Barrier((a)->readers); \
} \
_ret; \
})
/* acquire main lock before releasing meta lock, so we don't race */
#define RWLOCK_TRYWRLOCK(a) ({ \
int _ret; \
osi_Assert((a)->owner != current_thread()); \
_ret = lck_rw_try_lock((a)->lock, LCK_RW_TYPE_EXCLUSIVE); \
if (_ret) { \
osi_Assert((a)->owner == (thread_t)0); \
(a)->owner = current_thread(); \
} \
_ret; \
})
#define RWLOCK_UNLOCK(a) \
do { \
if ((a)->owner == current_thread()) { \
(a)->owner = (thread_t)0; \
lck_rw_unlock_exclusive((a)->lock); \
} else { \
lck_rw_unlock_shared((a)->lock); \
OSAtomicDecrement32Barrier((a)->readers); \
} \
} while(0)
#define MUTEX_SETUP() rx_kmutex_setup()
#define MUTEX_FINISH() rx_kmutex_finish()
#define LOCKINIT(a) \
do { \
lck_attr_t *openafs_lck_attr = lck_attr_alloc_init(); \
lck_attr_t *openafs_lck_attr = lck_attr_alloc_init(); \
(a) = lck_mtx_alloc_init(openafs_lck_grp, openafs_lck_attr); \
lck_attr_free(openafs_lck_attr); \
lck_attr_free(openafs_lck_attr); \
} while(0)
#define MUTEX_INIT(a,b,c,d) \
do { \
lck_attr_t *openafs_lck_attr = lck_attr_alloc_init(); \
(a)->meta = lck_mtx_alloc_init(openafs_lck_grp, openafs_lck_attr); \
do { \
lck_attr_t *openafs_lck_attr = lck_attr_alloc_init(); \
(a)->lock = lck_mtx_alloc_init(openafs_lck_grp, openafs_lck_attr); \
lck_attr_free(openafs_lck_attr); \
(a)->waiters = 0; \
(a)->owner = (thread_t)0; \
lck_attr_free(openafs_lck_attr); \
(a)->waiters = 0; \
(a)->owner = (thread_t)0; \
} while(0)
#define MUTEX_DESTROY(a) \
do { \
lck_mtx_destroy((a)->lock, openafs_lck_grp); \
lck_mtx_destroy((a)->meta, openafs_lck_grp); \
(a)->owner = (thread_t)-1; \
lck_mtx_destroy((a)->lock, openafs_lck_grp); \
(a)->owner = (thread_t)-1; \
} while(0)
#define MUTEX_ENTER(a) \
do { \
lck_mtx_lock((a)->meta); \
(a)->waiters++; \
lck_mtx_unlock((a)->meta); \
lck_mtx_lock((a)->lock); \
osi_Assert((a)->owner == (thread_t)0); \
(a)->owner = current_thread(); \
#define MUTEX_ENTER(a) \
do { \
OSAtomicIncrement32Barrier((a)->waiters); \
lck_mtx_lock((a)->lock); \
osi_Assert((a)->owner == (thread_t)0); \
(a)->owner = current_thread(); \
} while(0)
/* acquire main lock before releasing meta lock, so we don't race */
#define MUTEX_TRYENTER(a) ({ \
int _ret; \
lck_mtx_lock((a)->meta); \
if ((a)->waiters) { \
lck_mtx_unlock((a)->meta); \
_ret = 0; \
} else { \
(a)->waiters++; \
lck_mtx_lock((a)->lock); \
lck_mtx_unlock((a)->meta); \
osi_Assert((a)->owner == (thread_t)0); \
(a)->owner = current_thread(); \
_ret = 1; \
} \
_ret; \
})
#define MUTEX_TRYENTER(a) ({ \
int _ret; \
_ret = lck_mtx_try_lock((a)->lock); \
if (_ret) { \
OSAtomicIncrement32Barrier((a)->waiters); \
osi_Assert((a)->owner == (thread_t)0); \
(a)->owner = current_thread(); \
} \
_ret; \
})
#define MUTEX_EXIT(a) \
do { \
#define MUTEX_EXIT(a) \
do { \
osi_Assert((a)->owner == current_thread()); \
(a)->owner = (thread_t)0; \
lck_mtx_unlock((a)->lock); \
lck_mtx_lock((a)->meta); \
(a)->waiters--; \
lck_mtx_unlock((a)->meta); \
(a)->owner = (thread_t)0; \
lck_mtx_unlock((a)->lock); \
OSAtomicDecrement32Barrier((a)->waiters); \
} while(0)
#undef MUTEX_ISMINE