From 7ee0beb5ed58161fb452e88324eaf16cad626f8b Mon Sep 17 00:00:00 2001 From: Andrew Deason Date: Thu, 26 Dec 2013 16:42:46 -0500 Subject: [PATCH] afs: Treat vc_error as a CheckCode-translated code The vcache field vc_error is generally treated as an error code that has been translated through afs_CheckCode, but this is inconsistent in a few places. Fix this in a few ways: - Adjust afs_nfsrdwr so we do not call afs_CheckCode on vc_error, translating the error code twice. - Change afs_close to store vc_error in code_checkcode, and have the logging code check for specific values in code_checkcode as well. Log unknown values of code and code_checkcode, so we can distinguish between e.g. a 'code' value of VBUSY, and a 'code_checkcode' value of ETIMEDOUT. Reviewed-on: http://gerrit.openafs.org/10634 Reviewed-by: Benjamin Kaduk Reviewed-by: Derrick Brashear Tested-by: Derrick Brashear (cherry picked from commit 34e4a4fed356fbda9fc8ace1d01a080bd09238b0) Change-Id: Icceee0c82b0704e0d445f96946b493b4be424506 Reviewed-on: http://gerrit.openafs.org/10813 Tested-by: BuildBot Reviewed-by: Benjamin Kaduk Reviewed-by: D Brashear Reviewed-by: Stephan Wiesand --- src/afs/SOLARIS/osi_vnodeops.c | 9 +++++++-- src/afs/VNOPS/afs_vnop_write.c | 23 ++++++++++++++--------- 2 files changed, 21 insertions(+), 11 deletions(-) diff --git a/src/afs/SOLARIS/osi_vnodeops.c b/src/afs/SOLARIS/osi_vnodeops.c index ff1e124bc..478d19625 100644 --- a/src/afs/SOLARIS/osi_vnodeops.c +++ b/src/afs/SOLARIS/osi_vnodeops.c @@ -676,6 +676,7 @@ afs_nfsrdwr(struct vcache *avc, struct uio *auio, enum uio_rw arw, { afs_int32 code; afs_int32 code2; + afs_int32 code_checkcode = 0; int counter; afs_int32 mode, sflags; char *data; @@ -1008,7 +1009,7 @@ afs_nfsrdwr(struct vcache *avc, struct uio *auio, enum uio_rw arw, } if (!code && avc->vc_error) { - code = avc->vc_error; + code = code_checkcode = avc->vc_error; } ReleaseWriteLock(&avc->lock); afs_BozonUnlock(&avc->pvnLock, avc); @@ -1031,7 +1032,11 @@ afs_nfsrdwr(struct vcache *avc, struct uio *auio, enum uio_rw arw, if (code == 0 && extraResid > 0) auio->uio_resid += extraResid; #endif - return afs_CheckCode(code, &treq, 46); + if (code_checkcode) { + return code_checkcode; + } else { + return afs_CheckCode(code, &treq, 46); + } } int diff --git a/src/afs/VNOPS/afs_vnop_write.c b/src/afs/VNOPS/afs_vnop_write.c index 50e070296..70429816a 100644 --- a/src/afs/VNOPS/afs_vnop_write.c +++ b/src/afs/VNOPS/afs_vnop_write.c @@ -787,9 +787,13 @@ afs_close(OSI_VC_DECL(avc), afs_int32 aflags, afs_ucred_t *acred) #ifdef AFS_AIX32_ENV osi_ReleaseVM(avc, acred); #endif - /* printf("avc->vc_error=%d\n", avc->vc_error); */ - code = avc->vc_error; - code_checkcode = 0; + /* We don't know what the original raw error code was, so set + * 'code' to 0. But we have the afs_CheckCode-translated error + * code, so put that in code_checkcode. We cannot just set code + * to avc->vc_error, since vc_error is a checkcode-translated + * error code, and 'code' is supposed to be a raw error code. */ + code = 0; + code_checkcode = avc->vc_error; avc->vc_error = 0; } ReleaseWriteLock(&avc->lock); @@ -799,19 +803,19 @@ afs_close(OSI_VC_DECL(avc), afs_int32 aflags, afs_ucred_t *acred) afs_warnuser("afs: failed to store file (network problems)\n"); } #ifdef AFS_SUN5_ENV - else if (code == ENOSPC) { + else if (code == ENOSPC || code_checkcode == ENOSPC) { afs_warnuser ("afs: failed to store file (over quota or partition full)\n"); } #else - else if (code == ENOSPC) { + else if (code == ENOSPC || code_checkcode == ENOSPC) { afs_warnuser("afs: failed to store file (partition full)\n"); - } else if (code == EDQUOT) { + } else if (code == EDQUOT || code_checkcode == EDQUOT) { afs_warnuser("afs: failed to store file (over quota)\n"); } #endif - else if (code != 0) - afs_warnuser("afs: failed to store file (%d)\n", code); + else if (code || code_checkcode) + afs_warnuser("afs: failed to store file (%d/%d)\n", code, code_checkcode); /* finally, we flush any text pages lying around here */ hzero(avc->flushDV); @@ -827,7 +831,8 @@ afs_close(OSI_VC_DECL(avc), afs_int32 aflags, afs_ucred_t *acred) #ifdef AFS_AIX32_ENV osi_ReleaseVM(avc, acred); #endif - code = avc->vc_error; + code = 0; + code_checkcode = avc->vc_error; avc->vc_error = 0; } #if defined(AFS_FBSD80_ENV) -- 2.39.5