diff options
| author | oster <oster@NetBSD.org> | 2004-03-18 16:54:54 +0000 |
|---|---|---|
| committer | oster <oster@NetBSD.org> | 2004-03-18 16:54:54 +0000 |
| commit | 1051cc745f4ff7f45dca12591577b98787e6e6ce (patch) | |
| tree | 54a9d65ead202cc82de76f7a360e96e278c22093 /sys/dev/raidframe | |
| parent | bbf6758e005a69cf12c105de6ee355538b31ada0 (diff) | |
Re-work the locking mechanisms for reconstruct and PSS structures
such that we don't actually hold a simplelock while we are doing
a pool_get(), but that we still effectively protecting critical code.
This should fix all of the outstanding LOCKDEBUG warnings related to
rebuilding RAID sets.
Diffstat (limited to 'sys/dev/raidframe')
| -rw-r--r-- | sys/dev/raidframe/rf_psstatus.c | 13 | ||||
| -rw-r--r-- | sys/dev/raidframe/rf_psstatus.h | 24 | ||||
| -rw-r--r-- | sys/dev/raidframe/rf_raid1.c | 12 | ||||
| -rw-r--r-- | sys/dev/raidframe/rf_reconbuffer.c | 23 | ||||
| -rw-r--r-- | sys/dev/raidframe/rf_reconmap.c | 13 | ||||
| -rw-r--r-- | sys/dev/raidframe/rf_reconmap.h | 4 | ||||
| -rw-r--r-- | sys/dev/raidframe/rf_reconstruct.c | 31 | ||||
| -rw-r--r-- | sys/dev/raidframe/rf_reconstruct.h | 7 | ||||
| -rw-r--r-- | sys/dev/raidframe/rf_reconutil.c | 5 |
9 files changed, 111 insertions, 21 deletions
diff --git a/sys/dev/raidframe/rf_psstatus.c b/sys/dev/raidframe/rf_psstatus.c index b54c550e12e..4b26edc99f7 100644 --- a/sys/dev/raidframe/rf_psstatus.c +++ b/sys/dev/raidframe/rf_psstatus.c @@ -1,4 +1,4 @@ -/* $NetBSD: rf_psstatus.c,v 1.27 2004/03/08 02:25:27 oster Exp $ */ +/* $NetBSD: rf_psstatus.c,v 1.28 2004/03/18 16:54:54 oster Exp $ */ /* * Copyright (c) 1995 Carnegie-Mellon University. * All rights reserved. @@ -37,7 +37,7 @@ *****************************************************************************/ #include <sys/cdefs.h> -__KERNEL_RCSID(0, "$NetBSD: rf_psstatus.c,v 1.27 2004/03/08 02:25:27 oster Exp $"); +__KERNEL_RCSID(0, "$NetBSD: rf_psstatus.c,v 1.28 2004/03/18 16:54:54 oster Exp $"); #include <dev/raidframe/raidframevar.h> @@ -214,6 +214,11 @@ rf_RemoveFromActiveReconTable(RF_Raid_t *raidPtr, RF_StripeNum_t psid, RF_CallbackDesc_t *cb, *cb1; RF_LOCK_MUTEX(hdr->mutex); + while(hdr->lock) { + ltsleep(&hdr->lock, PRIBIO, "rf_racrecon", 0, &hdr->mutex); + } + hdr->lock = 1; + RF_UNLOCK_MUTEX(hdr->mutex); for (pt = NULL, p = hdr->chain; p; pt = p, p = p->next) { if ((p->parityStripeID == psid) && (p->which_ru == which_ru)) break; @@ -231,7 +236,9 @@ rf_RemoveFromActiveReconTable(RF_Raid_t *raidPtr, RF_StripeNum_t psid, else hdr->chain = p->next; p->next = NULL; - + + RF_LOCK_MUTEX(hdr->mutex); + hdr->lock = 0; RF_UNLOCK_MUTEX(hdr->mutex); /* wakup anyone waiting on the parity stripe ID */ diff --git a/sys/dev/raidframe/rf_psstatus.h b/sys/dev/raidframe/rf_psstatus.h index 40c5f6bb0f9..49e26983001 100644 --- a/sys/dev/raidframe/rf_psstatus.h +++ b/sys/dev/raidframe/rf_psstatus.h @@ -1,4 +1,4 @@ -/* $NetBSD: rf_psstatus.h,v 1.8 2004/03/08 02:25:27 oster Exp $ */ +/* $NetBSD: rf_psstatus.h,v 1.9 2004/03/18 16:54:54 oster Exp $ */ /* * Copyright (c) 1995 Carnegie-Mellon University. * All rights reserved. @@ -54,10 +54,22 @@ * descriptor. Note that we use just one lock for the whole hash chain. */ #define RF_HASH_PSID(_raid_,_psid_) ( (_psid_) % ((_raid_)->pssTableSize) ) /* simple hash function */ -#define RF_LOCK_PSS_MUTEX(_raidPtr, _psid) \ - RF_LOCK_MUTEX((_raidPtr)->reconControl->pssTable[ RF_HASH_PSID(_raidPtr,_psid) ].mutex) -#define RF_UNLOCK_PSS_MUTEX(_raidPtr, _psid) \ - RF_UNLOCK_MUTEX((_raidPtr)->reconControl->pssTable[ RF_HASH_PSID(_raidPtr,_psid) ].mutex) +#define RF_LOCK_PSS_MUTEX(_raidPtr, _psid) \ + do { \ + RF_LOCK_MUTEX((_raidPtr)->reconControl->pssTable[ RF_HASH_PSID(_raidPtr,_psid) ].mutex); \ + while((_raidPtr)->reconControl->pssTable[ RF_HASH_PSID(_raidPtr,_psid) ].lock) { \ + ltsleep(&(_raidPtr)->reconControl->pssTable[ RF_HASH_PSID(_raidPtr,_psid) ].lock, \ + PRIBIO, "rflockpss", 0, \ + &(_raidPtr)->reconControl->pssTable[ RF_HASH_PSID(_raidPtr,_psid) ].mutex); \ + } \ + (_raidPtr)->reconControl->pssTable[ RF_HASH_PSID(_raidPtr,_psid) ].lock = 1; \ + RF_UNLOCK_MUTEX((_raidPtr)->reconControl->pssTable[ RF_HASH_PSID(_raidPtr,_psid) ].mutex); \ + } while (0); + +#define RF_UNLOCK_PSS_MUTEX(_raidPtr, _psid) \ + RF_LOCK_MUTEX((_raidPtr)->reconControl->pssTable[ RF_HASH_PSID(_raidPtr,_psid) ].mutex); \ + (_raidPtr)->reconControl->pssTable[ RF_HASH_PSID(_raidPtr,_psid) ].lock = 0; \ + RF_UNLOCK_MUTEX((_raidPtr)->reconControl->pssTable[ RF_HASH_PSID(_raidPtr,_psid) ].mutex); struct RF_ReconParityStripeStatus_s { RF_StripeNum_t parityStripeID; /* the parity stripe ID */ @@ -87,6 +99,8 @@ struct RF_ReconParityStripeStatus_s { struct RF_PSStatusHeader_s { RF_DECLARE_MUTEX(mutex) /* mutex for this hash chain */ + int lock; /* 1 if this hash chain is locked, + 0 otherwise */ RF_ReconParityStripeStatus_t *chain; /* the hash chain */ }; /* masks for the "flags" field above */ diff --git a/sys/dev/raidframe/rf_raid1.c b/sys/dev/raidframe/rf_raid1.c index 363a0a07140..2e63393c703 100644 --- a/sys/dev/raidframe/rf_raid1.c +++ b/sys/dev/raidframe/rf_raid1.c @@ -1,4 +1,4 @@ -/* $NetBSD: rf_raid1.c,v 1.23 2004/03/05 03:22:05 oster Exp $ */ +/* $NetBSD: rf_raid1.c,v 1.24 2004/03/18 16:54:54 oster Exp $ */ /* * Copyright (c) 1995 Carnegie-Mellon University. * All rights reserved. @@ -33,7 +33,7 @@ *****************************************************************************/ #include <sys/cdefs.h> -__KERNEL_RCSID(0, "$NetBSD: rf_raid1.c,v 1.23 2004/03/05 03:22:05 oster Exp $"); +__KERNEL_RCSID(0, "$NetBSD: rf_raid1.c,v 1.24 2004/03/18 16:54:54 oster Exp $"); #include "rf_raid.h" #include "rf_raid1.h" @@ -580,6 +580,11 @@ rf_SubmitReconBufferRAID1(RF_ReconBuffer_t *rbuf, int keep_it, RF_LOCK_PSS_MUTEX(raidPtr, rbuf->parityStripeID); RF_LOCK_MUTEX(reconCtrlPtr->rb_mutex); + while(reconCtrlPtr->rb_lock) { + ltsleep(&reconCtrlPtr->rb_lock, PRIBIO, "reconctlcnmhs", 0, &reconCtrlPtr->rb_mutex); + } + reconCtrlPtr->rb_lock = 1; + RF_UNLOCK_MUTEX(reconCtrlPtr->rb_mutex); pssPtr = rf_LookupRUStatus(raidPtr, reconCtrlPtr->pssTable, rbuf->parityStripeID, rbuf->which_ru, RF_PSS_NONE, NULL); @@ -681,6 +686,9 @@ rf_SubmitReconBufferRAID1(RF_ReconBuffer_t *rbuf, int keep_it, out: RF_UNLOCK_PSS_MUTEX(raidPtr, rbuf->parityStripeID); + RF_LOCK_MUTEX(reconCtrlPtr->rb_mutex); + reconCtrlPtr->rb_lock = 0; + wakeup(&reconCtrlPtr->rb_lock); RF_UNLOCK_MUTEX(reconCtrlPtr->rb_mutex); #if RF_DEBUG_RECON if (rf_reconbufferDebug) { diff --git a/sys/dev/raidframe/rf_reconbuffer.c b/sys/dev/raidframe/rf_reconbuffer.c index ce1d2e1294b..79539eb5c0f 100644 --- a/sys/dev/raidframe/rf_reconbuffer.c +++ b/sys/dev/raidframe/rf_reconbuffer.c @@ -1,4 +1,4 @@ -/* $NetBSD: rf_reconbuffer.c,v 1.20 2004/03/03 13:29:00 oster Exp $ */ +/* $NetBSD: rf_reconbuffer.c,v 1.21 2004/03/18 16:54:54 oster Exp $ */ /* * Copyright (c) 1995 Carnegie-Mellon University. * All rights reserved. @@ -33,7 +33,7 @@ ***************************************************/ #include <sys/cdefs.h> -__KERNEL_RCSID(0, "$NetBSD: rf_reconbuffer.c,v 1.20 2004/03/03 13:29:00 oster Exp $"); +__KERNEL_RCSID(0, "$NetBSD: rf_reconbuffer.c,v 1.21 2004/03/18 16:54:54 oster Exp $"); #include "rf_raid.h" #include "rf_reconbuffer.h" @@ -141,6 +141,11 @@ rf_SubmitReconBufferBasic(RF_ReconBuffer_t *rbuf, int keep_it, RF_LOCK_PSS_MUTEX(raidPtr, rbuf->parityStripeID); RF_LOCK_MUTEX(reconCtrlPtr->rb_mutex); + while(reconCtrlPtr->rb_lock) { + ltsleep(&reconCtrlPtr->rb_lock, PRIBIO, "reconctlcnmhs", 0, &reconCtrlPtr->rb_mutex); + } + reconCtrlPtr->rb_lock = 1; + RF_UNLOCK_MUTEX(reconCtrlPtr->rb_mutex); pssPtr = rf_LookupRUStatus(raidPtr, reconCtrlPtr->pssTable, rbuf->parityStripeID, rbuf->which_ru, RF_PSS_NONE, NULL); RF_ASSERT(pssPtr); /* if it didn't exist, we wouldn't have gotten @@ -188,6 +193,9 @@ rf_SubmitReconBufferBasic(RF_ReconBuffer_t *rbuf, int keep_it, } if (keep_it) { RF_UNLOCK_PSS_MUTEX(raidPtr, rbuf->parityStripeID); + RF_LOCK_MUTEX(reconCtrlPtr->rb_mutex); + reconCtrlPtr->rb_lock = 0; + wakeup(&reconCtrlPtr->rb_lock); RF_UNLOCK_MUTEX(reconCtrlPtr->rb_mutex); rf_FreeReconBuffer(rbuf); return (retcode); @@ -278,6 +286,9 @@ rf_SubmitReconBufferBasic(RF_ReconBuffer_t *rbuf, int keep_it, out: RF_UNLOCK_PSS_MUTEX(raidPtr, rbuf->parityStripeID); + RF_LOCK_MUTEX(reconCtrlPtr->rb_mutex); + reconCtrlPtr->rb_lock = 0; + wakeup(&reconCtrlPtr->rb_lock); RF_UNLOCK_MUTEX(reconCtrlPtr->rb_mutex); return (retcode); } @@ -329,11 +340,19 @@ rf_GetFullReconBuffer(RF_ReconCtrl_t *reconCtrlPtr) RF_ReconBuffer_t *p; RF_LOCK_MUTEX(reconCtrlPtr->rb_mutex); + while(reconCtrlPtr->rb_lock) { + ltsleep(&reconCtrlPtr->rb_lock, PRIBIO, "reconctlcnmhs", 0, &reconCtrlPtr->rb_mutex); + } + reconCtrlPtr->rb_lock = 1; + RF_UNLOCK_MUTEX(reconCtrlPtr->rb_mutex); if ((p = reconCtrlPtr->fullBufferList) != NULL) { reconCtrlPtr->fullBufferList = p->next; p->next = NULL; } + RF_LOCK_MUTEX(reconCtrlPtr->rb_mutex); + reconCtrlPtr->rb_lock = 0; + wakeup(&reconCtrlPtr->rb_lock); RF_UNLOCK_MUTEX(reconCtrlPtr->rb_mutex); return (p); } diff --git a/sys/dev/raidframe/rf_reconmap.c b/sys/dev/raidframe/rf_reconmap.c index 61b8661842e..97d74e6662b 100644 --- a/sys/dev/raidframe/rf_reconmap.c +++ b/sys/dev/raidframe/rf_reconmap.c @@ -1,4 +1,4 @@ -/* $NetBSD: rf_reconmap.c,v 1.23 2004/03/01 01:12:22 oster Exp $ */ +/* $NetBSD: rf_reconmap.c,v 1.24 2004/03/18 16:54:54 oster Exp $ */ /* * Copyright (c) 1995 Carnegie-Mellon University. * All rights reserved. @@ -34,7 +34,7 @@ *************************************************************************/ #include <sys/cdefs.h> -__KERNEL_RCSID(0, "$NetBSD: rf_reconmap.c,v 1.23 2004/03/01 01:12:22 oster Exp $"); +__KERNEL_RCSID(0, "$NetBSD: rf_reconmap.c,v 1.24 2004/03/18 16:54:54 oster Exp $"); #include "rf_raid.h" #include <sys/time.h> @@ -142,6 +142,12 @@ rf_ReconMapUpdate(RF_Raid_t *raidPtr, RF_ReconMap_t *mapPtr, RF_ReconMapListElem_t *p, *pt; RF_LOCK_MUTEX(mapPtr->mutex); + while(mapPtr->lock) { + printf("napping...\n"); + ltsleep(&mapPtr->lock, PRIBIO, "reconupdate", 0, &mapPtr->mutex); + } + mapPtr->lock = 1; + RF_UNLOCK_MUTEX(mapPtr->mutex); RF_ASSERT(startSector >= 0 && stopSector < mapPtr->sectorsInDisk && stopSector >= startSector); @@ -168,6 +174,9 @@ rf_ReconMapUpdate(RF_Raid_t *raidPtr, RF_ReconMap_t *mapPtr, } startSector = RF_MIN(stopSector, last_in_RU) + 1; } + RF_LOCK_MUTEX(mapPtr->mutex); + mapPtr->lock = 0; + wakeup(&mapPtr->lock); RF_UNLOCK_MUTEX(mapPtr->mutex); } diff --git a/sys/dev/raidframe/rf_reconmap.h b/sys/dev/raidframe/rf_reconmap.h index 5983ef4ee8b..b03d812bf9e 100644 --- a/sys/dev/raidframe/rf_reconmap.h +++ b/sys/dev/raidframe/rf_reconmap.h @@ -1,4 +1,4 @@ -/* $NetBSD: rf_reconmap.h,v 1.8 2004/03/04 03:14:02 oster Exp $ */ +/* $NetBSD: rf_reconmap.h,v 1.9 2004/03/18 16:54:54 oster Exp $ */ /* * Copyright (c) 1995 Carnegie-Mellon University. * All rights reserved. @@ -54,6 +54,8 @@ struct RF_ReconMap_s { RF_ReconMapListElem_t **status; /* array of ptrs to list elements */ struct pool elem_pool; /* pool of RF_ReconMapListElem_t's */ RF_DECLARE_MUTEX(mutex) + int lock; /* 1 if someone has the recon map + locked, 0 otherwise */ }; /* a list element */ struct RF_ReconMapListElem_s { diff --git a/sys/dev/raidframe/rf_reconstruct.c b/sys/dev/raidframe/rf_reconstruct.c index ac09af7bf4d..a7b7fe9f273 100644 --- a/sys/dev/raidframe/rf_reconstruct.c +++ b/sys/dev/raidframe/rf_reconstruct.c @@ -1,4 +1,4 @@ -/* $NetBSD: rf_reconstruct.c,v 1.75 2004/03/13 02:00:15 oster Exp $ */ +/* $NetBSD: rf_reconstruct.c,v 1.76 2004/03/18 16:54:54 oster Exp $ */ /* * Copyright (c) 1995 Carnegie-Mellon University. * All rights reserved. @@ -33,7 +33,7 @@ ************************************************************/ #include <sys/cdefs.h> -__KERNEL_RCSID(0, "$NetBSD: rf_reconstruct.c,v 1.75 2004/03/13 02:00:15 oster Exp $"); +__KERNEL_RCSID(0, "$NetBSD: rf_reconstruct.c,v 1.76 2004/03/18 16:54:54 oster Exp $"); #include <sys/time.h> #include <sys/buf.h> @@ -792,8 +792,19 @@ ProcessReconEvent(RF_Raid_t *raidPtr, RF_ReconEvent_t *event) if (rbuf->type == RF_RBUF_TYPE_FLOATING) { RF_LOCK_MUTEX(raidPtr->reconControl->rb_mutex); + while(raidPtr->reconControl->rb_lock) { + ltsleep(&raidPtr->reconControl->rb_lock, PRIBIO, "reconctrlpre1", 0, + &raidPtr->reconControl->rb_mutex); + } + raidPtr->reconControl->rb_lock = 1; + RF_UNLOCK_MUTEX(raidPtr->reconControl->rb_mutex); + raidPtr->numFullReconBuffers--; rf_ReleaseFloatingReconBuffer(raidPtr, rbuf); + + RF_LOCK_MUTEX(raidPtr->reconControl->rb_mutex); + raidPtr->reconControl->rb_lock = 0; + wakeup(&raidPtr->reconControl->rb_lock); RF_UNLOCK_MUTEX(raidPtr->reconControl->rb_mutex); } else if (rbuf->type == RF_RBUF_TYPE_FORCED) @@ -1307,6 +1318,11 @@ CheckForNewMinHeadSep(RF_Raid_t *raidPtr, RF_HeadSepLimit_t hsCtr) RF_LOCK_MUTEX(reconCtrlPtr->rb_mutex); + while(reconCtrlPtr->rb_lock) { + ltsleep(&reconCtrlPtr->rb_lock, PRIBIO, "reconctlcnmhs", 0, &reconCtrlPtr->rb_mutex); + } + reconCtrlPtr->rb_lock = 1; + RF_UNLOCK_MUTEX(reconCtrlPtr->rb_mutex); new_min = ~(1L << (8 * sizeof(long) - 1)); /* 0x7FFF....FFF */ for (i = 0; i < raidPtr->numCol; i++) @@ -1329,6 +1345,9 @@ CheckForNewMinHeadSep(RF_Raid_t *raidPtr, RF_HeadSepLimit_t hsCtr) } } + RF_LOCK_MUTEX(reconCtrlPtr->rb_mutex); + reconCtrlPtr->rb_lock = 0; + wakeup(&reconCtrlPtr->rb_lock); RF_UNLOCK_MUTEX(reconCtrlPtr->rb_mutex); } @@ -1362,6 +1381,11 @@ CheckHeadSeparation(RF_Raid_t *raidPtr, RF_PerDiskReconCtrl_t *ctrl, * */ RF_LOCK_MUTEX(reconCtrlPtr->rb_mutex); + while(reconCtrlPtr->rb_lock) { + ltsleep(&reconCtrlPtr->rb_lock, PRIBIO, "reconctlchs", 0, &reconCtrlPtr->rb_mutex); + } + reconCtrlPtr->rb_lock = 1; + RF_UNLOCK_MUTEX(reconCtrlPtr->rb_mutex); if ((raidPtr->headSepLimit >= 0) && ((ctrl->headSepCounter - reconCtrlPtr->minHeadSepCounter) > raidPtr->headSepLimit)) { Dprintf5("raid%d: RECON: head sep stall: col %d hsCtr %ld minHSCtr %ld limit %ld\n", @@ -1394,6 +1418,9 @@ CheckHeadSeparation(RF_Raid_t *raidPtr, RF_PerDiskReconCtrl_t *ctrl, ctrl->reconCtrl->reconDesc->hsStallCount++; #endif /* RF_RECON_STATS > 0 */ } + RF_LOCK_MUTEX(reconCtrlPtr->rb_mutex); + reconCtrlPtr->rb_lock = 0; + wakeup(&reconCtrlPtr->rb_lock); RF_UNLOCK_MUTEX(reconCtrlPtr->rb_mutex); return (retval); diff --git a/sys/dev/raidframe/rf_reconstruct.h b/sys/dev/raidframe/rf_reconstruct.h index 708db20c820..4600e4a7768 100644 --- a/sys/dev/raidframe/rf_reconstruct.h +++ b/sys/dev/raidframe/rf_reconstruct.h @@ -1,4 +1,4 @@ -/* $NetBSD: rf_reconstruct.h,v 1.16 2004/03/07 02:49:23 oster Exp $ */ +/* $NetBSD: rf_reconstruct.h,v 1.17 2004/03/18 16:54:54 oster Exp $ */ /* * Copyright (c) 1995 Carnegie-Mellon University. * All rights reserved. @@ -138,8 +138,11 @@ struct RF_ReconCtrl_s { int eq_count; /* debug only */ /* reconstruction buffer management */ - RF_DECLARE_MUTEX(rb_mutex) /* mutex for messing around + RF_DECLARE_MUTEX(rb_mutex) /* mutex for messing around * with recon buffers */ + int rb_lock; /* 1 if someone is mucking + with recon buffers, + 0 otherwise */ RF_ReconBuffer_t *floatingRbufs; /* available floating * reconstruction buffers */ RF_ReconBuffer_t *committedRbufs; /* recon buffers that have diff --git a/sys/dev/raidframe/rf_reconutil.c b/sys/dev/raidframe/rf_reconutil.c index d2b9f4a9bc1..1516932caa0 100644 --- a/sys/dev/raidframe/rf_reconutil.c +++ b/sys/dev/raidframe/rf_reconutil.c @@ -1,4 +1,4 @@ -/* $NetBSD: rf_reconutil.c,v 1.22 2004/03/07 22:15:19 oster Exp $ */ +/* $NetBSD: rf_reconutil.c,v 1.23 2004/03/18 16:54:54 oster Exp $ */ /* * Copyright (c) 1995 Carnegie-Mellon University. * All rights reserved. @@ -31,7 +31,7 @@ ********************************************/ #include <sys/cdefs.h> -__KERNEL_RCSID(0, "$NetBSD: rf_reconutil.c,v 1.22 2004/03/07 22:15:19 oster Exp $"); +__KERNEL_RCSID(0, "$NetBSD: rf_reconutil.c,v 1.23 2004/03/18 16:54:54 oster Exp $"); #include <dev/raidframe/raidframevar.h> @@ -245,6 +245,7 @@ rf_FreeReconBuffer(RF_ReconBuffer_t *rbuf) } #if RF_DEBUG_RECON +XXXX IF you use this, you really want to fix the locking in here. /****************************************************************************** * debug only: sanity check the number of floating recon bufs in use *****************************************************************************/ |
