summaryrefslogtreecommitdiff
path: root/fs/nfsd/nfsxdr.c
diff options
context:
space:
mode:
authorChuck Lever <chuck.lever@oracle.com>2020-10-02 01:59:49 +0300
committerJ. Bruce Fields <bfields@redhat.com>2020-10-02 16:37:42 +0300
commitf0af22101d9072c6488b8d20d6e33338669029fe (patch)
treed0307fde97f60b3b60c6121dd319deec5f4dcf45 /fs/nfsd/nfsxdr.c
parent1841b9b61492e35234bdca8a5737a0e5df770f27 (diff)
downloadlinux-f0af22101d9072c6488b8d20d6e33338669029fe.tar.xz
NFSD: Call NFSv2 encoders on error returns
Remove special dispatcher logic for NFSv2 error responses. These are rare to the point of becoming extinct, but all NFS responses have to pay the cost of the extra conditional branches. With this change, the NFSv2 error cases now get proper xdr_ressize_check() calls. Signed-off-by: Chuck Lever <chuck.lever@oracle.com> Signed-off-by: J. Bruce Fields <bfields@redhat.com>
Diffstat (limited to 'fs/nfsd/nfsxdr.c')
-rw-r--r--fs/nfsd/nfsxdr.c18
1 files changed, 18 insertions, 0 deletions
diff --git a/fs/nfsd/nfsxdr.c b/fs/nfsd/nfsxdr.c
index 39c004ec7d85..952e71c95d4e 100644
--- a/fs/nfsd/nfsxdr.c
+++ b/fs/nfsd/nfsxdr.c
@@ -434,6 +434,9 @@ nfssvc_encode_attrstat(struct svc_rqst *rqstp, __be32 *p)
{
struct nfsd_attrstat *resp = rqstp->rq_resp;
+ if (resp->status != nfs_ok)
+ return xdr_ressize_check(rqstp, p);
+
p = encode_fattr(rqstp, p, &resp->fh, &resp->stat);
return xdr_ressize_check(rqstp, p);
}
@@ -443,6 +446,9 @@ nfssvc_encode_diropres(struct svc_rqst *rqstp, __be32 *p)
{
struct nfsd_diropres *resp = rqstp->rq_resp;
+ if (resp->status != nfs_ok)
+ return xdr_ressize_check(rqstp, p);
+
p = encode_fh(p, &resp->fh);
p = encode_fattr(rqstp, p, &resp->fh, &resp->stat);
return xdr_ressize_check(rqstp, p);
@@ -453,6 +459,9 @@ nfssvc_encode_readlinkres(struct svc_rqst *rqstp, __be32 *p)
{
struct nfsd_readlinkres *resp = rqstp->rq_resp;
+ if (resp->status != nfs_ok)
+ return xdr_ressize_check(rqstp, p);
+
*p++ = htonl(resp->len);
xdr_ressize_check(rqstp, p);
rqstp->rq_res.page_len = resp->len;
@@ -470,6 +479,9 @@ nfssvc_encode_readres(struct svc_rqst *rqstp, __be32 *p)
{
struct nfsd_readres *resp = rqstp->rq_resp;
+ if (resp->status != nfs_ok)
+ return xdr_ressize_check(rqstp, p);
+
p = encode_fattr(rqstp, p, &resp->fh, &resp->stat);
*p++ = htonl(resp->count);
xdr_ressize_check(rqstp, p);
@@ -490,6 +502,9 @@ nfssvc_encode_readdirres(struct svc_rqst *rqstp, __be32 *p)
{
struct nfsd_readdirres *resp = rqstp->rq_resp;
+ if (resp->status != nfs_ok)
+ return xdr_ressize_check(rqstp, p);
+
xdr_ressize_check(rqstp, p);
p = resp->buffer;
*p++ = 0; /* no more entries */
@@ -505,6 +520,9 @@ nfssvc_encode_statfsres(struct svc_rqst *rqstp, __be32 *p)
struct nfsd_statfsres *resp = rqstp->rq_resp;
struct kstatfs *stat = &resp->stats;
+ if (resp->status != nfs_ok)
+ return xdr_ressize_check(rqstp, p);
+
*p++ = htonl(NFSSVC_MAXBLKSIZE_V2); /* max transfer size */
*p++ = htonl(stat->f_bsize);
*p++ = htonl(stat->f_blocks);