diff options
author | J. Bruce Fields <bfields@redhat.com> | 2014-03-12 21:39:35 -0400 |
---|---|---|
committer | J. Bruce Fields <bfields@redhat.com> | 2014-05-30 17:32:02 -0400 |
commit | 47ee52986472dba068e8223cbaf1b65d74238781 (patch) | |
tree | 4436adf69861759600318696325b8bb9633d4602 /fs/nfsd/nfs4state.c | |
parent | db3f58a95beea6752d90fed03f9f198d282a3913 (diff) |
nfsd4: adjust buflen to session channel limit
We can simplify session limit enforcement by restricting the xdr buflen
to the session size.
Also fix a preexisting bug: we should really have been taking into
account the auth-required space when comparing against session limits,
which are limits on the size of the entire rpc reply, including any krb5
overhead.
Signed-off-by: J. Bruce Fields <bfields@redhat.com>
Diffstat (limited to 'fs/nfsd/nfs4state.c')
-rw-r--r-- | fs/nfsd/nfs4state.c | 11 |
1 files changed, 11 insertions, 0 deletions
diff --git a/fs/nfsd/nfs4state.c b/fs/nfsd/nfs4state.c index 8e22ea485f99..612b85ac414b 100644 --- a/fs/nfsd/nfs4state.c +++ b/fs/nfsd/nfs4state.c | |||
@@ -2208,11 +2208,13 @@ nfsd4_sequence(struct svc_rqst *rqstp, | |||
2208 | struct nfsd4_sequence *seq) | 2208 | struct nfsd4_sequence *seq) |
2209 | { | 2209 | { |
2210 | struct nfsd4_compoundres *resp = rqstp->rq_resp; | 2210 | struct nfsd4_compoundres *resp = rqstp->rq_resp; |
2211 | struct xdr_stream *xdr = &resp->xdr; | ||
2211 | struct nfsd4_session *session; | 2212 | struct nfsd4_session *session; |
2212 | struct nfs4_client *clp; | 2213 | struct nfs4_client *clp; |
2213 | struct nfsd4_slot *slot; | 2214 | struct nfsd4_slot *slot; |
2214 | struct nfsd4_conn *conn; | 2215 | struct nfsd4_conn *conn; |
2215 | __be32 status; | 2216 | __be32 status; |
2217 | int buflen; | ||
2216 | struct nfsd_net *nn = net_generic(SVC_NET(rqstp), nfsd_net_id); | 2218 | struct nfsd_net *nn = net_generic(SVC_NET(rqstp), nfsd_net_id); |
2217 | 2219 | ||
2218 | if (resp->opcnt != 1) | 2220 | if (resp->opcnt != 1) |
@@ -2281,6 +2283,15 @@ nfsd4_sequence(struct svc_rqst *rqstp, | |||
2281 | if (status) | 2283 | if (status) |
2282 | goto out_put_session; | 2284 | goto out_put_session; |
2283 | 2285 | ||
2286 | buflen = (seq->cachethis) ? | ||
2287 | session->se_fchannel.maxresp_cached : | ||
2288 | session->se_fchannel.maxresp_sz; | ||
2289 | status = (seq->cachethis) ? nfserr_rep_too_big_to_cache : | ||
2290 | nfserr_rep_too_big; | ||
2291 | if (xdr_restrict_buflen(xdr, buflen - 2 * RPC_MAX_AUTH_SIZE)) | ||
2292 | goto out_put_session; | ||
2293 | |||
2294 | status = nfs_ok; | ||
2284 | /* Success! bump slot seqid */ | 2295 | /* Success! bump slot seqid */ |
2285 | slot->sl_seqid = seq->seqid; | 2296 | slot->sl_seqid = seq->seqid; |
2286 | slot->sl_flags |= NFSD4_SLOT_INUSE; | 2297 | slot->sl_flags |= NFSD4_SLOT_INUSE; |