From d73d9a1011cc3e1e5acfbc970434373f732c066e Mon Sep 17 00:00:00 2001 From: Derrick Brashear Date: Wed, 19 Jan 2011 23:11:11 -0500 Subject: [PATCH] MacOS: allow cdead vcaches to be found in FindVCache if requested if we are trying to find a dead vcache, let it be found, don't immediately attempt to recycle FIXES 128511 Change-Id: I7f86f7d4a88e1b89887b64617246e750654b0334 Reviewed-on: http://gerrit.openafs.org/3691 Tested-by: BuildBot Reviewed-by: Derrick Brashear Tested-by: Derrick Brashear --- src/afs/VNOPS/afs_vnop_lookup.c | 2 +- src/afs/afs.h | 1 + src/afs/afs_vcache.c | 88 +++++++++++++++++++++++---------- 3 files changed, 64 insertions(+), 27 deletions(-) diff --git a/src/afs/VNOPS/afs_vnop_lookup.c b/src/afs/VNOPS/afs_vnop_lookup.c index 0bc1c06aa..127d00291 100644 --- a/src/afs/VNOPS/afs_vnop_lookup.c +++ b/src/afs/VNOPS/afs_vnop_lookup.c @@ -816,7 +816,7 @@ afs_DoBulkStat(struct vcache *adp, long dirCookie, struct vrequest *areqp) do { retry = 0; ObtainWriteLock(&afs_xvcache, 130); - tvcp = afs_FindVCache(&tfid, &retry, IS_WLOCK /* no stats | LRU */ ); + tvcp = afs_FindVCache(&tfid, &retry, IS_WLOCK|FIND_BULKDEAD /* no stats | LRU */ ); if (tvcp && retry) { ReleaseWriteLock(&afs_xvcache); afs_PutVCache(tvcp); diff --git a/src/afs/afs.h b/src/afs/afs.h index 9dd97fc77..496b8eaaf 100644 --- a/src/afs/afs.h +++ b/src/afs/afs.h @@ -1329,6 +1329,7 @@ extern struct brequest afs_brs[NBRS]; /* request structures */ #define IS_SLOCK 4 #define IS_WLOCK 8 #define FIND_CDEAD 16 +#define FIND_BULKDEAD 32 /* values for adown value of afs_LoopServers */ #define AFS_LS_UP 0 diff --git a/src/afs/afs_vcache.c b/src/afs/afs_vcache.c index d96bfc022..dc6a79980 100644 --- a/src/afs/afs_vcache.c +++ b/src/afs/afs_vcache.c @@ -2647,6 +2647,7 @@ afs_FindVCache(struct VenusFid *afid, afs_int32 * retry, afs_int32 flag) struct vcache *tvc; afs_int32 i; #ifdef AFS_DARWIN80_ENV + struct vcache *deadvc = NULL, *livevc = NULL; vnode_t tvp; #endif @@ -2656,47 +2657,78 @@ afs_FindVCache(struct VenusFid *afid, afs_int32 * retry, afs_int32 flag) i = VCHash(afid); for (tvc = afs_vhashT[i]; tvc; tvc = tvc->hnext) { if (FidMatches(afid, tvc)) { +#ifdef AFS_DARWIN80_ENV + if (flag & FIND_CDEAD) { + if (tvc->f.states & (CDeadVnode|CBulkFetching)) { + deadvc = tvc; + continue; + } + } else { + if (tvc->f.states & CDeadVnode) + if ((tvc->f.states & CBulkFetching) && + !(flag & FIND_BULKDEAD)) + continue; + } +#endif if (tvc->f.states & CVInit) { findvc_sleep(tvc, flag); goto findloop; - } -#ifdef AFS_DARWIN80_ENV - if (tvc->f.states & CDeadVnode) { - if (!(flag & FIND_CDEAD)) { - findvc_sleep(tvc, flag); - goto findloop; - } } - tvp = AFSTOV(tvc); - if (vnode_get(tvp)) - continue; - if (vnode_ref(tvp)) { - AFS_GUNLOCK(); - /* AFSTOV(tvc) may be NULL */ - vnode_put(tvp); - AFS_GLOCK(); +#ifdef AFS_DARWIN80_ENV + if (tvc->f.states & CDeadVnode) { + findvc_sleep(tvc, flag); + goto findloop; + } + if (flag & FIND_CDEAD) { + livevc = tvc; continue; } - if (tvc->f.states & (CBulkFetching|CDeadVnode)) { - AFS_GUNLOCK(); - vnode_recycle(AFSTOV(tvc)); - AFS_GLOCK(); - } #endif break; } } +#ifdef AFS_DARWIN80_ENV + if (flag & FIND_CDEAD) { + if (livevc && deadvc) { + /* discard deadvc */ + AFS_GUNLOCK(); + vnode_recycle(AFSTOV(deadvc)); + vnode_put(AFSTOV(deadvc)); + vnode_rele(AFSTOV(deadvc)); + AFS_GLOCK(); + deadvc = NULL; + } + + /* return what's left */ + tvc = livevc ? livevc : deadvc; + } +#endif /* should I have a read lock on the vnode here? */ if (tvc) { if (retry) *retry = 0; -#if !defined(AFS_DARWIN80_ENV) - osi_vnhold(tvc, retry); /* already held, above */ - if (retry && *retry) - return 0; -#endif -#if defined(AFS_DARWIN_ENV) && !defined(AFS_DARWIN80_ENV) +#if defined(AFS_DARWIN80_ENV) + tvp = AFSTOV(tvc); + if (vnode_get(tvp)) + tvp = NULL; + if (tvp && vnode_ref(tvp)) { + AFS_GUNLOCK(); + /* AFSTOV(tvc) may be NULL */ + vnode_put(tvp); + AFS_GLOCK(); + tvp = NULL; + } + if (tvp && (tvc->f.states & (CBulkFetching|CDeadVnode))) { + AFS_GUNLOCK(); + vnode_recycle(AFSTOV(tvc)); + AFS_GLOCK(); + } + if (!tvp) { + tvc = NULL; + return tvc; + } +#elif defined(AFS_DARWIN_ENV) tvc->f.states |= CUBCinit; AFS_GUNLOCK(); if (UBCINFOMISSING(AFSTOV(tvc)) || @@ -2705,6 +2737,10 @@ afs_FindVCache(struct VenusFid *afid, afs_int32 * retry, afs_int32 flag) } AFS_GLOCK(); tvc->f.states &= ~CUBCinit; +#else + osi_vnhold(tvc, retry); /* already held, above */ + if (retry && *retry) + return 0; #endif /* * only move to front of vlru if we have proper vcache locking) -- 2.39.5