OSDN Git Service

NFSD: add support for sending CB_RECALL_ANY
authorDai Ngo <dai.ngo@oracle.com>
Thu, 17 Nov 2022 03:44:46 +0000 (19:44 -0800)
committerChuck Lever <cel@kernel.org>
Sat, 10 Dec 2022 16:01:12 +0000 (11:01 -0500)
Add XDR encode and decode function for CB_RECALL_ANY.

Signed-off-by: Dai Ngo <dai.ngo@oracle.com>
Signed-off-by: Chuck Lever <chuck.lever@oracle.com>
fs/nfsd/nfs4callback.c
fs/nfsd/state.h
fs/nfsd/xdr4.h
fs/nfsd/xdr4cb.h

index f0e69ed..1b57f2c 100644 (file)
@@ -76,6 +76,17 @@ static __be32 *xdr_encode_empty_array(__be32 *p)
  * 1 Protocol"
  */
 
+static void encode_uint32(struct xdr_stream *xdr, u32 n)
+{
+       WARN_ON_ONCE(xdr_stream_encode_u32(xdr, n) < 0);
+}
+
+static void encode_bitmap4(struct xdr_stream *xdr, const __u32 *bitmap,
+                          size_t len)
+{
+       WARN_ON_ONCE(xdr_stream_encode_uint32_array(xdr, bitmap, len) < 0);
+}
+
 /*
  *     nfs_cb_opnum4
  *
@@ -329,6 +340,24 @@ static void encode_cb_recall4args(struct xdr_stream *xdr,
 }
 
 /*
+ * CB_RECALLANY4args
+ *
+ *     struct CB_RECALLANY4args {
+ *             uint32_t        craa_objects_to_keep;
+ *             bitmap4         craa_type_mask;
+ *     };
+ */
+static void
+encode_cb_recallany4args(struct xdr_stream *xdr,
+       struct nfs4_cb_compound_hdr *hdr, struct nfsd4_cb_recall_any *ra)
+{
+       encode_nfs_cb_opnum4(xdr, OP_CB_RECALL_ANY);
+       encode_uint32(xdr, ra->ra_keep);
+       encode_bitmap4(xdr, ra->ra_bmval, ARRAY_SIZE(ra->ra_bmval));
+       hdr->nops++;
+}
+
+/*
  * CB_SEQUENCE4args
  *
  *     struct CB_SEQUENCE4args {
@@ -482,6 +511,26 @@ static void nfs4_xdr_enc_cb_recall(struct rpc_rqst *req, struct xdr_stream *xdr,
        encode_cb_nops(&hdr);
 }
 
+/*
+ * 20.6. Operation 8: CB_RECALL_ANY - Keep Any N Recallable Objects
+ */
+static void
+nfs4_xdr_enc_cb_recall_any(struct rpc_rqst *req,
+               struct xdr_stream *xdr, const void *data)
+{
+       const struct nfsd4_callback *cb = data;
+       struct nfsd4_cb_recall_any *ra;
+       struct nfs4_cb_compound_hdr hdr = {
+               .ident = cb->cb_clp->cl_cb_ident,
+               .minorversion = cb->cb_clp->cl_minorversion,
+       };
+
+       ra = container_of(cb, struct nfsd4_cb_recall_any, ra_cb);
+       encode_cb_compound4args(xdr, &hdr);
+       encode_cb_sequence4args(xdr, cb, &hdr);
+       encode_cb_recallany4args(xdr, &hdr, ra);
+       encode_cb_nops(&hdr);
+}
 
 /*
  * NFSv4.0 and NFSv4.1 XDR decode functions
@@ -520,6 +569,28 @@ static int nfs4_xdr_dec_cb_recall(struct rpc_rqst *rqstp,
        return decode_cb_op_status(xdr, OP_CB_RECALL, &cb->cb_status);
 }
 
+/*
+ * 20.6. Operation 8: CB_RECALL_ANY - Keep Any N Recallable Objects
+ */
+static int
+nfs4_xdr_dec_cb_recall_any(struct rpc_rqst *rqstp,
+                                 struct xdr_stream *xdr,
+                                 void *data)
+{
+       struct nfsd4_callback *cb = data;
+       struct nfs4_cb_compound_hdr hdr;
+       int status;
+
+       status = decode_cb_compound4res(xdr, &hdr);
+       if (unlikely(status))
+               return status;
+       status = decode_cb_sequence4res(xdr, cb);
+       if (unlikely(status || cb->cb_seq_status))
+               return status;
+       status =  decode_cb_op_status(xdr, OP_CB_RECALL_ANY, &cb->cb_status);
+       return status;
+}
+
 #ifdef CONFIG_NFSD_PNFS
 /*
  * CB_LAYOUTRECALL4args
@@ -783,6 +854,7 @@ static const struct rpc_procinfo nfs4_cb_procedures[] = {
 #endif
        PROC(CB_NOTIFY_LOCK,    COMPOUND,       cb_notify_lock, cb_notify_lock),
        PROC(CB_OFFLOAD,        COMPOUND,       cb_offload,     cb_offload),
+       PROC(CB_RECALL_ANY,     COMPOUND,       cb_recall_any,  cb_recall_any),
 };
 
 static unsigned int nfs4_cb_counts[ARRAY_SIZE(nfs4_cb_procedures)];
index eadd7f4..e30882f 100644 (file)
@@ -636,6 +636,7 @@ enum nfsd4_cb_op {
        NFSPROC4_CLNT_CB_OFFLOAD,
        NFSPROC4_CLNT_CB_SEQUENCE,
        NFSPROC4_CLNT_CB_NOTIFY_LOCK,
+       NFSPROC4_CLNT_CB_RECALL_ANY,
 };
 
 /* Returns true iff a is later than b: */
index 0eb0010..4fd2cf6 100644 (file)
@@ -896,5 +896,10 @@ struct nfsd4_operation {
                        union nfsd4_op_u *);
 };
 
+struct nfsd4_cb_recall_any {
+       struct nfsd4_callback   ra_cb;
+       u32                     ra_keep;
+       u32                     ra_bmval[1];
+};
 
 #endif
index 547cf07..0d39af1 100644 (file)
@@ -48,3 +48,9 @@
 #define NFS4_dec_cb_offload_sz         (cb_compound_dec_hdr_sz  +      \
                                        cb_sequence_dec_sz +            \
                                        op_dec_sz)
+#define NFS4_enc_cb_recall_any_sz      (cb_compound_enc_hdr_sz +       \
+                                       cb_sequence_enc_sz +            \
+                                       1 + 1 + 1)
+#define NFS4_dec_cb_recall_any_sz      (cb_compound_dec_hdr_sz  +      \
+                                       cb_sequence_dec_sz +            \
+                                       op_dec_sz)