svcrdma: De-duplicate code that locates Write and Reply chunks
authorChuck Lever <chuck.lever@oracle.com>
Mon, 2 Mar 2020 20:01:08 +0000 (15:01 -0500)
committerChuck Lever <chuck.lever@oracle.com>
Mon, 16 Mar 2020 16:04:32 +0000 (12:04 -0400)
Cache the locations of the Requester-provided Write list and Reply
chunk so that the Send path doesn't need to parse the Call header
again.

Signed-off-by: Chuck Lever <chuck.lever@oracle.com>
include/linux/sunrpc/svc_rdma.h
net/sunrpc/xprtrdma/svc_rdma_recvfrom.c
net/sunrpc/xprtrdma/svc_rdma_sendto.c

index c790dbb0dd901bb70cd3522a266c938ac620a6c1..e714e4d90ac535714df96575658b8e6a9e07c169 100644 (file)
@@ -138,6 +138,8 @@ struct svc_rdma_recv_ctxt {
        unsigned int            rc_page_count;
        unsigned int            rc_hdr_count;
        u32                     rc_inv_rkey;
+       __be32                  *rc_write_list;
+       __be32                  *rc_reply_chunk;
        unsigned int            rc_read_payload_offset;
        unsigned int            rc_read_payload_length;
        struct page             *rc_pages[RPCSVC_MAXPAGES];
index bd92ed611b4c7c1150ae674299473da6319f0242..70129d7cc9721b9444f842802063f924b1a3fae9 100644 (file)
@@ -479,6 +479,7 @@ static bool xdr_check_write_list(struct svc_rdma_recv_ctxt *rctxt)
        p = xdr_inline_decode(&rctxt->rc_stream, sizeof(*p));
        if (!p)
                return false;
+       rctxt->rc_write_list = p;
        while (*p != xdr_zero) {
                if (!xdr_check_write_chunk(rctxt, MAX_BYTES_WRITE_CHUNK))
                        return false;
@@ -487,6 +488,8 @@ static bool xdr_check_write_list(struct svc_rdma_recv_ctxt *rctxt)
                if (!p)
                        return false;
        }
+       if (!chcount)
+               rctxt->rc_write_list = NULL;
        return chcount < 2;
 }
 
@@ -509,9 +512,13 @@ static bool xdr_check_reply_chunk(struct svc_rdma_recv_ctxt *rctxt)
        p = xdr_inline_decode(&rctxt->rc_stream, sizeof(*p));
        if (!p)
                return false;
-       if (*p != xdr_zero)
+       rctxt->rc_reply_chunk = p;
+       if (*p != xdr_zero) {
                if (!xdr_check_write_chunk(rctxt, MAX_BYTES_SPECIAL_CHUNK))
                        return false;
+       } else {
+               rctxt->rc_reply_chunk = NULL;
+       }
        return true;
 }
 
index 4add875277f8af84a81c0a611702417148558cfa..94895635c0078e40d8a044e09f9bfe53caf450a2 100644 (file)
@@ -449,36 +449,6 @@ static void svc_rdma_xdr_encode_reply_chunk(__be32 *rdma_resp, __be32 *rp_ch,
        xdr_encode_write_chunk(p, rp_ch, consumed);
 }
 
-/* Parse the RPC Call's transport header.
- */
-static void svc_rdma_get_write_arrays(__be32 *rdma_argp,
-                                     __be32 **write, __be32 **reply)
-{
-       __be32 *p;
-
-       p = rdma_argp + rpcrdma_fixed_maxsz;
-
-       /* Read list */
-       while (*p++ != xdr_zero)
-               p += 5;
-
-       /* Write list */
-       if (*p != xdr_zero) {
-               *write = p;
-               while (*p++ != xdr_zero)
-                       p += 1 + be32_to_cpu(*p) * 4;
-       } else {
-               *write = NULL;
-               p++;
-       }
-
-       /* Reply chunk */
-       if (*p != xdr_zero)
-               *reply = p;
-       else
-               *reply = NULL;
-}
-
 static int svc_rdma_dma_map_page(struct svcxprt_rdma *rdma,
                                 struct svc_rdma_send_ctxt *ctxt,
                                 struct page *page,
@@ -813,14 +783,14 @@ int svc_rdma_sendto(struct svc_rqst *rqstp)
        struct svcxprt_rdma *rdma =
                container_of(xprt, struct svcxprt_rdma, sc_xprt);
        struct svc_rdma_recv_ctxt *rctxt = rqstp->rq_xprt_ctxt;
-       __be32 *p, *rdma_argp, *rdma_resp, *wr_lst, *rp_ch;
+       __be32 *rdma_argp = rctxt->rc_recv_buf;
+       __be32 *wr_lst = rctxt->rc_write_list;
+       __be32 *rp_ch = rctxt->rc_reply_chunk;
        struct xdr_buf *xdr = &rqstp->rq_res;
        struct svc_rdma_send_ctxt *sctxt;
+       __be32 *p, *rdma_resp;
        int ret;
 
-       rdma_argp = rctxt->rc_recv_buf;
-       svc_rdma_get_write_arrays(rdma_argp, &wr_lst, &rp_ch);
-
        /* Create the RDMA response header. xprt->xpt_mutex,
         * acquired in svc_send(), serializes RPC replies. The
         * code path below that inserts the credit grant value