From: Derrick Brashear Date: Thu, 26 May 2011 05:39:18 +0000 (-0400) Subject: macos: bulkstat caller reference handling X-Git-Tag: openafs-devel-1_7_1~462 X-Git-Url: http://git.openafs.org/?p=openafs.git;a=commitdiff_plain;h=7270cf5607e24f8614d75cd40bc46574d330ffab macos: bulkstat caller reference handling if bulkstat is called and fakes up vnodes for non-dir cases, it can guess wrong, and we end up needing to fix up the type by swapping in a new vnode under the vcache. however, references are tracked on the vnode, and more importantly, callers can know about the vnode; unlinking a vcache from a vnode leaves null pointers to blow up on. thing is, we shouldn't end up with a un-fixed-up vcache in use: any caller of ProcessFS will notice if the vnode is the wrong type, and fix it. so in order to reach CStatd, we have to fix it. the only places where we can get a vcache in use not CStatd are: FindVCache, LookupVCache, GetVCache where InReadDir. The last happens only on Linux. LookupVCache doesn't happen anywhere that matters (CForeign, or we immediately dispose...). FindVCache is only called somewhere which won't lead to us fixing up during create, but that vnode isn't returned to callers; we finalize in the result of create and return the vnode that's linked to the vcache, which will be correct. so, the only other place we can have a reference which won't immediately get fixed up is in lookup, across the bulkstat call. if that's true, and we return from bulkstat a non-CStatd vcache, lookup will fill in the entry manually. so, if there are references remaining after we do a fixup, unmark CStatd so the caller (presumably lookup, given the above) will give back the vcache and retry, getting a corrected vnode as a result, with the reference on the vnode we want it on. Change-Id: I3b225c8d48067624f3cbac7b1f897e52193a8d55 Reviewed-on: http://gerrit.openafs.org/4722 Tested-by: BuildBot Reviewed-by: Derrick Brashear --- diff --git a/src/afs/DARWIN/osi_vnodeops.c b/src/afs/DARWIN/osi_vnodeops.c index 3380e8e..0d096fd 100644 --- a/src/afs/DARWIN/osi_vnodeops.c +++ b/src/afs/DARWIN/osi_vnodeops.c @@ -2237,6 +2237,10 @@ afs_darwin_finalizevnode(struct vcache *avc, struct vnode *dvp, vnode_put(ovp); vnode_rele(ovp); } + /* If it's ref'd still, unmark stat'd to force new lookup */ + if ((vnode_vtype(ovp) != avc->f.m.Type) && VREFCOUNT_GT(avc, 1)) + avc->f.states &= ~CStatd; + vnode_put(ovp); vnode_rele(ovp); AFS_GLOCK();