Skip to content

Commit f523601

Browse files
author
J. Bruce Fields
committed
nfsd4: convert 4.1 replay encoding
Limits on maxresp_sz mean that we only ever need to replay rpc's that are contained entirely in the head. The one exception is very small zero-copy reads. That's an odd corner case as clients wouldn't normally ask those to be cached. in any case, this seems a little more robust. Signed-off-by: J. Bruce Fields <bfields@redhat.com>
1 parent 2825a7f commit f523601

File tree

3 files changed

+16
-16
lines changed

3 files changed

+16
-16
lines changed

fs/nfsd/nfs4state.c

Lines changed: 14 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -1560,6 +1560,7 @@ gen_callback(struct nfs4_client *clp, struct nfsd4_setclientid *se, struct svc_r
15601560
void
15611561
nfsd4_store_cache_entry(struct nfsd4_compoundres *resp)
15621562
{
1563+
struct xdr_buf *buf = resp->xdr.buf;
15631564
struct nfsd4_slot *slot = resp->cstate.slot;
15641565
unsigned int base;
15651566

@@ -1573,11 +1574,9 @@ nfsd4_store_cache_entry(struct nfsd4_compoundres *resp)
15731574
slot->sl_datalen = 0;
15741575
return;
15751576
}
1576-
slot->sl_datalen = (char *)resp->xdr.p - (char *)resp->cstate.datap;
1577-
base = (char *)resp->cstate.datap -
1578-
(char *)resp->xdr.buf->head[0].iov_base;
1579-
if (read_bytes_from_xdr_buf(resp->xdr.buf, base, slot->sl_data,
1580-
slot->sl_datalen))
1577+
base = resp->cstate.data_offset;
1578+
slot->sl_datalen = buf->len - base;
1579+
if (read_bytes_from_xdr_buf(buf, base, slot->sl_data, slot->sl_datalen))
15811580
WARN("%s: sessions DRC could not cache compound\n", __func__);
15821581
return;
15831582
}
@@ -1618,7 +1617,8 @@ nfsd4_replay_cache_entry(struct nfsd4_compoundres *resp,
16181617
struct nfsd4_sequence *seq)
16191618
{
16201619
struct nfsd4_slot *slot = resp->cstate.slot;
1621-
struct kvec *head = resp->xdr.iov;
1620+
struct xdr_stream *xdr = &resp->xdr;
1621+
__be32 *p;
16221622
__be32 status;
16231623

16241624
dprintk("--> %s slot %p\n", __func__, slot);
@@ -1627,16 +1627,16 @@ nfsd4_replay_cache_entry(struct nfsd4_compoundres *resp,
16271627
if (status)
16281628
return status;
16291629

1630-
/* The sequence operation has been encoded, cstate->datap set. */
1631-
memcpy(resp->cstate.datap, slot->sl_data, slot->sl_datalen);
1630+
p = xdr_reserve_space(xdr, slot->sl_datalen);
1631+
if (!p) {
1632+
WARN_ON_ONCE(1);
1633+
return nfserr_serverfault;
1634+
}
1635+
xdr_encode_opaque_fixed(p, slot->sl_data, slot->sl_datalen);
1636+
xdr_commit_encode(xdr);
16321637

16331638
resp->opcnt = slot->sl_opcnt;
1634-
resp->xdr.p = resp->cstate.datap + XDR_QUADLEN(slot->sl_datalen);
1635-
head->iov_len = (void *)resp->xdr.p - head->iov_base;
1636-
resp->xdr.buf->len = head->iov_len;
1637-
status = slot->sl_status;
1638-
1639-
return status;
1639+
return slot->sl_status;
16401640
}
16411641

16421642
/*

fs/nfsd/nfs4xdr.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3659,7 +3659,7 @@ nfsd4_encode_sequence(struct nfsd4_compoundres *resp, __be32 nfserr,
36593659
WRITE32(seq->maxslots - 1); /* sr_target_highest_slotid */
36603660
WRITE32(seq->status_flags);
36613661

3662-
resp->cstate.datap = p; /* DRC cache data pointer */
3662+
resp->cstate.data_offset = xdr->buf->len; /* DRC cache data pointer */
36633663
return 0;
36643664
}
36653665

fs/nfsd/xdr4.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -58,7 +58,7 @@ struct nfsd4_compound_state {
5858
/* For sessions DRC */
5959
struct nfsd4_session *session;
6060
struct nfsd4_slot *slot;
61-
__be32 *datap;
61+
int data_offset;
6262
size_t iovlen;
6363
u32 minorversion;
6464
__be32 status;

0 commit comments

Comments
 (0)