Illumos 5812 - assertion failed in zrl_tryenter(): zr_owner==NULL
5812 assertion failed in zrl_tryenter(): zr_owner==NULL Reviewed by: George Wilson <george@delphix.com> Reviewed by: Alex Reece <alex@delphix.com> Reviewed by: Will Andrews <will@freebsd.org> Approved by: Gordon Ross <gwr@nexenta.com> References: https://www.illumos.org/issues/5812 https://github.com/illumos/illumos-gate/commit/8df1730 Ported-by: DHE <git@dehacked.net> Signed-off-by: Brian Behlendorf <behlendorf1@llnl.gov> Closes #3357
This commit is contained in:
parent
6186e29753
commit
8dd86a10cf
|
@ -20,6 +20,7 @@
|
||||||
*/
|
*/
|
||||||
/*
|
/*
|
||||||
* Copyright (c) 2010, Oracle and/or its affiliates. All rights reserved.
|
* Copyright (c) 2010, Oracle and/or its affiliates. All rights reserved.
|
||||||
|
* Copyright (c) 2014 by Delphix. All rights reserved.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
@ -43,7 +44,7 @@
|
||||||
* A ZRL can be locked only while there are zero references, so ZRL_LOCKED is
|
* A ZRL can be locked only while there are zero references, so ZRL_LOCKED is
|
||||||
* treated as zero references.
|
* treated as zero references.
|
||||||
*/
|
*/
|
||||||
#define ZRL_LOCKED ((uint32_t)-1)
|
#define ZRL_LOCKED -1
|
||||||
#define ZRL_DESTROYED -2
|
#define ZRL_DESTROYED -2
|
||||||
|
|
||||||
void
|
void
|
||||||
|
@ -61,7 +62,7 @@ zrl_init(zrlock_t *zrl)
|
||||||
void
|
void
|
||||||
zrl_destroy(zrlock_t *zrl)
|
zrl_destroy(zrlock_t *zrl)
|
||||||
{
|
{
|
||||||
ASSERT(zrl->zr_refcount == 0);
|
ASSERT0(zrl->zr_refcount);
|
||||||
|
|
||||||
mutex_destroy(&zrl->zr_mtx);
|
mutex_destroy(&zrl->zr_mtx);
|
||||||
zrl->zr_refcount = ZRL_DESTROYED;
|
zrl->zr_refcount = ZRL_DESTROYED;
|
||||||
|
@ -81,7 +82,7 @@ zrl_add(zrlock_t *zrl)
|
||||||
uint32_t cas = atomic_cas_32(
|
uint32_t cas = atomic_cas_32(
|
||||||
(uint32_t *)&zrl->zr_refcount, n, n + 1);
|
(uint32_t *)&zrl->zr_refcount, n, n + 1);
|
||||||
if (cas == n) {
|
if (cas == n) {
|
||||||
ASSERT((int32_t)n >= 0);
|
ASSERT3S((int32_t)n, >=, 0);
|
||||||
#ifdef ZFS_DEBUG
|
#ifdef ZFS_DEBUG
|
||||||
if (zrl->zr_owner == curthread) {
|
if (zrl->zr_owner == curthread) {
|
||||||
DTRACE_PROBE2(zrlock__reentry,
|
DTRACE_PROBE2(zrlock__reentry,
|
||||||
|
@ -99,7 +100,7 @@ zrl_add(zrlock_t *zrl)
|
||||||
while (zrl->zr_refcount == ZRL_LOCKED) {
|
while (zrl->zr_refcount == ZRL_LOCKED) {
|
||||||
cv_wait(&zrl->zr_cv, &zrl->zr_mtx);
|
cv_wait(&zrl->zr_cv, &zrl->zr_mtx);
|
||||||
}
|
}
|
||||||
ASSERT(zrl->zr_refcount >= 0);
|
ASSERT3S(zrl->zr_refcount, >=, 0);
|
||||||
zrl->zr_refcount++;
|
zrl->zr_refcount++;
|
||||||
#ifdef ZFS_DEBUG
|
#ifdef ZFS_DEBUG
|
||||||
zrl->zr_owner = curthread;
|
zrl->zr_owner = curthread;
|
||||||
|
@ -113,14 +114,14 @@ zrl_remove(zrlock_t *zrl)
|
||||||
{
|
{
|
||||||
uint32_t n;
|
uint32_t n;
|
||||||
|
|
||||||
n = atomic_dec_32_nv((uint32_t *)&zrl->zr_refcount);
|
|
||||||
ASSERT((int32_t)n >= 0);
|
|
||||||
#ifdef ZFS_DEBUG
|
#ifdef ZFS_DEBUG
|
||||||
if (zrl->zr_owner == curthread) {
|
if (zrl->zr_owner == curthread) {
|
||||||
zrl->zr_owner = NULL;
|
zrl->zr_owner = NULL;
|
||||||
zrl->zr_caller = NULL;
|
zrl->zr_caller = NULL;
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
n = atomic_dec_32_nv((uint32_t *)&zrl->zr_refcount);
|
||||||
|
ASSERT3S((int32_t)n, >=, 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
int
|
int
|
||||||
|
@ -133,14 +134,14 @@ zrl_tryenter(zrlock_t *zrl)
|
||||||
(uint32_t *)&zrl->zr_refcount, 0, ZRL_LOCKED);
|
(uint32_t *)&zrl->zr_refcount, 0, ZRL_LOCKED);
|
||||||
if (cas == 0) {
|
if (cas == 0) {
|
||||||
#ifdef ZFS_DEBUG
|
#ifdef ZFS_DEBUG
|
||||||
ASSERT(zrl->zr_owner == NULL);
|
ASSERT3P(zrl->zr_owner, ==, NULL);
|
||||||
zrl->zr_owner = curthread;
|
zrl->zr_owner = curthread;
|
||||||
#endif
|
#endif
|
||||||
return (1);
|
return (1);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
ASSERT((int32_t)n > ZRL_DESTROYED);
|
ASSERT3S((int32_t)n, >, ZRL_DESTROYED);
|
||||||
|
|
||||||
return (0);
|
return (0);
|
||||||
}
|
}
|
||||||
|
@ -148,11 +149,11 @@ zrl_tryenter(zrlock_t *zrl)
|
||||||
void
|
void
|
||||||
zrl_exit(zrlock_t *zrl)
|
zrl_exit(zrlock_t *zrl)
|
||||||
{
|
{
|
||||||
ASSERT(zrl->zr_refcount == ZRL_LOCKED);
|
ASSERT3S(zrl->zr_refcount, ==, ZRL_LOCKED);
|
||||||
|
|
||||||
mutex_enter(&zrl->zr_mtx);
|
mutex_enter(&zrl->zr_mtx);
|
||||||
#ifdef ZFS_DEBUG
|
#ifdef ZFS_DEBUG
|
||||||
ASSERT(zrl->zr_owner == curthread);
|
ASSERT3P(zrl->zr_owner, ==, curthread);
|
||||||
zrl->zr_owner = NULL;
|
zrl->zr_owner = NULL;
|
||||||
membar_producer(); /* make sure the owner store happens first */
|
membar_producer(); /* make sure the owner store happens first */
|
||||||
#endif
|
#endif
|
||||||
|
@ -166,7 +167,7 @@ zrl_refcount(zrlock_t *zrl)
|
||||||
{
|
{
|
||||||
int n;
|
int n;
|
||||||
|
|
||||||
ASSERT(zrl->zr_refcount > ZRL_DESTROYED);
|
ASSERT3S(zrl->zr_refcount, >, ZRL_DESTROYED);
|
||||||
|
|
||||||
n = (int)zrl->zr_refcount;
|
n = (int)zrl->zr_refcount;
|
||||||
return (n <= 0 ? 0 : n);
|
return (n <= 0 ? 0 : n);
|
||||||
|
@ -175,7 +176,7 @@ zrl_refcount(zrlock_t *zrl)
|
||||||
int
|
int
|
||||||
zrl_is_zero(zrlock_t *zrl)
|
zrl_is_zero(zrlock_t *zrl)
|
||||||
{
|
{
|
||||||
ASSERT(zrl->zr_refcount > ZRL_DESTROYED);
|
ASSERT3S(zrl->zr_refcount, >, ZRL_DESTROYED);
|
||||||
|
|
||||||
return (zrl->zr_refcount <= 0);
|
return (zrl->zr_refcount <= 0);
|
||||||
}
|
}
|
||||||
|
@ -183,7 +184,7 @@ zrl_is_zero(zrlock_t *zrl)
|
||||||
int
|
int
|
||||||
zrl_is_locked(zrlock_t *zrl)
|
zrl_is_locked(zrlock_t *zrl)
|
||||||
{
|
{
|
||||||
ASSERT(zrl->zr_refcount > ZRL_DESTROYED);
|
ASSERT3S(zrl->zr_refcount, >, ZRL_DESTROYED);
|
||||||
|
|
||||||
return (zrl->zr_refcount == ZRL_LOCKED);
|
return (zrl->zr_refcount == ZRL_LOCKED);
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue