linux/net/sunrpc/xprtrdma/frwr_ops.c

// SPDX-License-Identifier: GPL-2.0
/*
 * Copyright (c) 2015, 2017 Oracle.  All rights reserved.
 * Copyright (c) 2003-2007 Network Appliance, Inc. All rights reserved.
 */

/* Lightweight memory registration using Fast Registration Work
 * Requests (FRWR).
 *
 * FRWR features ordered asynchronous registration and invalidation
 * of arbitrarily-sized memory regions. This is the fastest and safest
 * but most complex memory registration mode.
 */

/* Normal operation
 *
 * A Memory Region is prepared for RDMA Read or Write using a FAST_REG
 * Work Request (frwr_map). When the RDMA operation is finished, this
 * Memory Region is invalidated using a LOCAL_INV Work Request
 * (frwr_unmap_async and frwr_unmap_sync).
 *
 * Typically FAST_REG Work Requests are not signaled, and neither are
 * RDMA Send Work Requests (with the exception of signaling occasionally
 * to prevent provider work queue overflows). This greatly reduces HCA
 * interrupt workload.
 */

/* Transport recovery
 *
 * frwr_map and frwr_unmap_* cannot run at the same time the transport
 * connect worker is running. The connect worker holds the transport
 * send lock, just as ->send_request does. This prevents frwr_map and
 * the connect worker from running concurrently. When a connection is
 * closed, the Receive completion queue is drained before the allowing
 * the connect worker to get control. This prevents frwr_unmap and the
 * connect worker from running concurrently.
 *
 * When the underlying transport disconnects, MRs that are in flight
 * are flushed and are likely unusable. Thus all MRs are destroyed.
 * New MRs are created on demand.
 */

#include <linux/sunrpc/svc_rdma.h>

#include "xprt_rdma.h"
#include <trace/events/rpcrdma.h>

static void frwr_cid_init(struct rpcrdma_ep *ep,
			  struct rpcrdma_mr *mr)
{}

static void frwr_mr_unmap(struct rpcrdma_mr *mr)
{}

/**
 * frwr_mr_release - Destroy one MR
 * @mr: MR allocated by frwr_mr_init
 *
 */
void frwr_mr_release(struct rpcrdma_mr *mr)
{}

static void frwr_mr_put(struct rpcrdma_mr *mr)
{}

/**
 * frwr_reset - Place MRs back on @req's free list
 * @req: request to reset
 *
 * Used after a failed marshal. For FRWR, this means the MRs
 * don't have to be fully released and recreated.
 *
 * NB: This is safe only as long as none of @req's MRs are
 * involved with an ongoing asynchronous FAST_REG or LOCAL_INV
 * Work Request.
 */
void frwr_reset(struct rpcrdma_req *req)
{}

/**
 * frwr_mr_init - Initialize one MR
 * @r_xprt: controlling transport instance
 * @mr: generic MR to prepare for FRWR
 *
 * Returns zero if successful. Otherwise a negative errno
 * is returned.
 */
int frwr_mr_init(struct rpcrdma_xprt *r_xprt, struct rpcrdma_mr *mr)
{}

/**
 * frwr_query_device - Prepare a transport for use with FRWR
 * @ep: endpoint to fill in
 * @device: RDMA device to query
 *
 * On success, sets:
 *	ep->re_attr
 *	ep->re_max_requests
 *	ep->re_max_rdma_segs
 *	ep->re_max_fr_depth
 *	ep->re_mrtype
 *
 * Return values:
 *   On success, returns zero.
 *   %-EINVAL - the device does not support FRWR memory registration
 *   %-ENOMEM - the device is not sufficiently capable for NFS/RDMA
 */
int frwr_query_device(struct rpcrdma_ep *ep, const struct ib_device *device)
{}

/**
 * frwr_map - Register a memory region
 * @r_xprt: controlling transport
 * @seg: memory region co-ordinates
 * @nsegs: number of segments remaining
 * @writing: true when RDMA Write will be used
 * @xid: XID of RPC using the registered memory
 * @mr: MR to fill in
 *
 * Prepare a REG_MR Work Request to register a memory region
 * for remote access via RDMA READ or RDMA WRITE.
 *
 * Returns the next segment or a negative errno pointer.
 * On success, @mr is filled in.
 */
struct rpcrdma_mr_seg *frwr_map(struct rpcrdma_xprt *r_xprt,
				struct rpcrdma_mr_seg *seg,
				int nsegs, bool writing, __be32 xid,
				struct rpcrdma_mr *mr)
{}

/**
 * frwr_wc_fastreg - Invoked by RDMA provider for a flushed FastReg WC
 * @cq: completion queue
 * @wc: WCE for a completed FastReg WR
 *
 * Each flushed MR gets destroyed after the QP has drained.
 */
static void frwr_wc_fastreg(struct ib_cq *cq, struct ib_wc *wc)
{}

/**
 * frwr_send - post Send WRs containing the RPC Call message
 * @r_xprt: controlling transport instance
 * @req: prepared RPC Call
 *
 * For FRWR, chain any FastReg WRs to the Send WR. Only a
 * single ib_post_send call is needed to register memory
 * and then post the Send WR.
 *
 * Returns the return code from ib_post_send.
 *
 * Caller must hold the transport send lock to ensure that the
 * pointers to the transport's rdma_cm_id and QP are stable.
 */
int frwr_send(struct rpcrdma_xprt *r_xprt, struct rpcrdma_req *req)
{}

/**
 * frwr_reminv - handle a remotely invalidated mr on the @mrs list
 * @rep: Received reply
 * @mrs: list of MRs to check
 *
 */
void frwr_reminv(struct rpcrdma_rep *rep, struct list_head *mrs)
{}

static void frwr_mr_done(struct ib_wc *wc, struct rpcrdma_mr *mr)
{}

/**
 * frwr_wc_localinv - Invoked by RDMA provider for a LOCAL_INV WC
 * @cq: completion queue
 * @wc: WCE for a completed LocalInv WR
 *
 */
static void frwr_wc_localinv(struct ib_cq *cq, struct ib_wc *wc)
{}

/**
 * frwr_wc_localinv_wake - Invoked by RDMA provider for a LOCAL_INV WC
 * @cq: completion queue
 * @wc: WCE for a completed LocalInv WR
 *
 * Awaken anyone waiting for an MR to finish being fenced.
 */
static void frwr_wc_localinv_wake(struct ib_cq *cq, struct ib_wc *wc)
{}

/**
 * frwr_unmap_sync - invalidate memory regions that were registered for @req
 * @r_xprt: controlling transport instance
 * @req: rpcrdma_req with a non-empty list of MRs to process
 *
 * Sleeps until it is safe for the host CPU to access the previously mapped
 * memory regions. This guarantees that registered MRs are properly fenced
 * from the server before the RPC consumer accesses the data in them. It
 * also ensures proper Send flow control: waking the next RPC waits until
 * this RPC has relinquished all its Send Queue entries.
 */
void frwr_unmap_sync(struct rpcrdma_xprt *r_xprt, struct rpcrdma_req *req)
{}

/**
 * frwr_wc_localinv_done - Invoked by RDMA provider for a signaled LOCAL_INV WC
 * @cq:	completion queue
 * @wc:	WCE for a completed LocalInv WR
 *
 */
static void frwr_wc_localinv_done(struct ib_cq *cq, struct ib_wc *wc)
{}

/**
 * frwr_unmap_async - invalidate memory regions that were registered for @req
 * @r_xprt: controlling transport instance
 * @req: rpcrdma_req with a non-empty list of MRs to process
 *
 * This guarantees that registered MRs are properly fenced from the
 * server before the RPC consumer accesses the data in them. It also
 * ensures proper Send flow control: waking the next RPC waits until
 * this RPC has relinquished all its Send Queue entries.
 */
void frwr_unmap_async(struct rpcrdma_xprt *r_xprt, struct rpcrdma_req *req)
{}

/**
 * frwr_wp_create - Create an MR for padding Write chunks
 * @r_xprt: transport resources to use
 *
 * Return 0 on success, negative errno on failure.
 */
int frwr_wp_create(struct rpcrdma_xprt *r_xprt)
{}