static void BStore(struct brequest *ab) { struct vcache *tvc; afs_int32 code; struct vrequest *treq = NULL; #if defined(AFS_SGI_ENV) struct cred *tmpcred; #endif AFS_STATCNT(BStore); if ((code = afs_CreateReq(&treq, ab->cred))) return; tvc = ab->vc; #if defined(AFS_SGI_ENV) /* * Since StoreOnLastReference can end up calling osi_SyncVM which * calls into VM code that assumes that u.u_cred has the * correct credentials, we set our to theirs for this xaction */ tmpcred = OSI_GET_CURRENT_CRED(); OSI_SET_CURRENT_CRED(ab->cred); /* * To avoid recursion since the WriteLock may be released during VM * operations, we hold the VOP_RWLOCK across this transaction as * do the other callers of StoreOnLastReference */ AFS_RWLOCK((vnode_t *) tvc, 1); #endif ObtainWriteLock(&tvc->lock, 209); code = afs_StoreOnLastReference(tvc, treq); ReleaseWriteLock(&tvc->lock); #if defined(AFS_SGI_ENV) OSI_SET_CURRENT_CRED(tmpcred); AFS_RWUNLOCK((vnode_t *) tvc, 1); #endif /* now set final return code, and wakeup anyone waiting */ if ((ab->flags & BUVALID) == 0) { /* To explain code_raw/code_checkcode: * Anyone that's waiting won't have our treq, so they won't be able to * call afs_CheckCode themselves on the return code we provide here. * But if we give back only the afs_CheckCode value, they won't know * what the "raw" value was. So give back both values, so the waiter * can know the "raw" value for interpreting the value internally, as * well as the afs_CheckCode value to give to the OS. */ ab->code_raw = code; ab->code_checkcode = afs_CheckCode(code, treq, 430); ab->flags |= BUVALID; if (ab->flags & BUWAIT) { ab->flags &= ~BUWAIT; afs_osi_Wakeup(ab); } } afs_DestroyReq(treq); }
static void BStore(struct brequest *ab) { struct vcache *tvc; afs_int32 code; struct vrequest treq; #if defined(AFS_SGI_ENV) struct cred *tmpcred; #endif AFS_STATCNT(BStore); if ((code = afs_InitReq(&treq, ab->cred))) return; code = 0; tvc = ab->vc; #if defined(AFS_SGI_ENV) /* * Since StoreOnLastReference can end up calling osi_SyncVM which * calls into VM code that assumes that u.u_cred has the * correct credentials, we set our to theirs for this xaction */ tmpcred = OSI_GET_CURRENT_CRED(); OSI_SET_CURRENT_CRED(ab->cred); /* * To avoid recursion since the WriteLock may be released during VM * operations, we hold the VOP_RWLOCK across this transaction as * do the other callers of StoreOnLastReference */ AFS_RWLOCK((vnode_t *) tvc, 1); #endif ObtainWriteLock(&tvc->lock, 209); code = afs_StoreOnLastReference(tvc, &treq); ReleaseWriteLock(&tvc->lock); #if defined(AFS_SGI_ENV) OSI_SET_CURRENT_CRED(tmpcred); AFS_RWUNLOCK((vnode_t *) tvc, 1); #endif /* now set final return code, and wakeup anyone waiting */ if ((ab->flags & BUVALID) == 0) { ab->code = afs_CheckCode(code, &treq, 43); /* set final code, since treq doesn't go across processes */ ab->flags |= BUVALID; if (ab->flags & BUWAIT) { ab->flags &= ~BUWAIT; afs_osi_Wakeup(ab); } } }