xref: /illumos-gate/usr/src/uts/common/rpc/rpc_rdma.h (revision 0a701b1ec2b55bddc48b62124df936152ff820f7)
17c478bd9Sstevel@tonic-gate /*
27c478bd9Sstevel@tonic-gate  * CDDL HEADER START
37c478bd9Sstevel@tonic-gate  *
47c478bd9Sstevel@tonic-gate  * The contents of this file are subject to the terms of the
5*0a701b1eSRobert Gordon  * Common Development and Distribution License (the "License").
6*0a701b1eSRobert Gordon  * You may not use this file except in compliance with the License.
77c478bd9Sstevel@tonic-gate  *
87c478bd9Sstevel@tonic-gate  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
97c478bd9Sstevel@tonic-gate  * or http://www.opensolaris.org/os/licensing.
107c478bd9Sstevel@tonic-gate  * See the License for the specific language governing permissions
117c478bd9Sstevel@tonic-gate  * and limitations under the License.
127c478bd9Sstevel@tonic-gate  *
137c478bd9Sstevel@tonic-gate  * When distributing Covered Code, include this CDDL HEADER in each
147c478bd9Sstevel@tonic-gate  * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
157c478bd9Sstevel@tonic-gate  * If applicable, add the following below this CDDL HEADER, with the
167c478bd9Sstevel@tonic-gate  * fields enclosed by brackets "[]" replaced with your own identifying
177c478bd9Sstevel@tonic-gate  * information: Portions Copyright [yyyy] [name of copyright owner]
187c478bd9Sstevel@tonic-gate  *
197c478bd9Sstevel@tonic-gate  * CDDL HEADER END
207c478bd9Sstevel@tonic-gate  */
217c478bd9Sstevel@tonic-gate /*
22*0a701b1eSRobert Gordon  * Copyright 2008 Sun Microsystems, Inc.  All rights reserved.
237c478bd9Sstevel@tonic-gate  * Use is subject to license terms.
247c478bd9Sstevel@tonic-gate  */
257c478bd9Sstevel@tonic-gate 
26*0a701b1eSRobert Gordon /*
27*0a701b1eSRobert Gordon  * Copyright (c) 2007, The Ohio State University. All rights reserved.
28*0a701b1eSRobert Gordon  *
29*0a701b1eSRobert Gordon  * Portions of this source code is developed by the team members of
30*0a701b1eSRobert Gordon  * The Ohio State University's Network-Based Computing Laboratory (NBCL),
31*0a701b1eSRobert Gordon  * headed by Professor Dhabaleswar K. (DK) Panda.
32*0a701b1eSRobert Gordon  *
33*0a701b1eSRobert Gordon  * Acknowledgements to contributions from developors:
34*0a701b1eSRobert Gordon  *   Ranjit Noronha: noronha@cse.ohio-state.edu
35*0a701b1eSRobert Gordon  *   Lei Chai      : chail@cse.ohio-state.edu
36*0a701b1eSRobert Gordon  *   Weikuan Yu    : yuw@cse.ohio-state.edu
37*0a701b1eSRobert Gordon  *
38*0a701b1eSRobert Gordon  */
39*0a701b1eSRobert Gordon 
407c478bd9Sstevel@tonic-gate #ifndef	_RPC_RPC_RDMA_H
417c478bd9Sstevel@tonic-gate #define	_RPC_RPC_RDMA_H
427c478bd9Sstevel@tonic-gate 
437c478bd9Sstevel@tonic-gate #include <rpc/rpc.h>
447c478bd9Sstevel@tonic-gate #include <rpc/rpc_sztypes.h>
457c478bd9Sstevel@tonic-gate #include <sys/sunddi.h>
467c478bd9Sstevel@tonic-gate #include <sys/sunldi.h>
477c478bd9Sstevel@tonic-gate 
487c478bd9Sstevel@tonic-gate #ifdef __cplusplus
497c478bd9Sstevel@tonic-gate extern "C" {
507c478bd9Sstevel@tonic-gate #endif
517c478bd9Sstevel@tonic-gate 
52*0a701b1eSRobert Gordon #define	RPCRDMA_VERS	1	/* Version of the RPC over RDMA protocol */
537c478bd9Sstevel@tonic-gate #define	RDMATF_VERS	1	/* Version of the API used by RPC for RDMA */
547c478bd9Sstevel@tonic-gate #define	RDMATF_VERS_1	1	/* Current version of RDMATF */
557c478bd9Sstevel@tonic-gate 
567c478bd9Sstevel@tonic-gate /*
577c478bd9Sstevel@tonic-gate  * The size of an RPC call or reply message
587c478bd9Sstevel@tonic-gate  */
59*0a701b1eSRobert Gordon #define	RPC_MSG_SZ	1024
60*0a701b1eSRobert Gordon 
61*0a701b1eSRobert Gordon /*
62*0a701b1eSRobert Gordon  * RDMA chunk size
63*0a701b1eSRobert Gordon  */
64*0a701b1eSRobert Gordon #define	RDMA_MINCHUNK	1024
657c478bd9Sstevel@tonic-gate 
667c478bd9Sstevel@tonic-gate /*
677c478bd9Sstevel@tonic-gate  * Storage for a chunk list
687c478bd9Sstevel@tonic-gate  */
697c478bd9Sstevel@tonic-gate #define	RPC_CL_SZ  1024
707c478bd9Sstevel@tonic-gate 
717c478bd9Sstevel@tonic-gate /*
727c478bd9Sstevel@tonic-gate  * Chunk size
737c478bd9Sstevel@tonic-gate  */
747c478bd9Sstevel@tonic-gate #define	MINCHUNK  1024
757c478bd9Sstevel@tonic-gate 
767c478bd9Sstevel@tonic-gate /*
777c478bd9Sstevel@tonic-gate  * Size of receive buffer
787c478bd9Sstevel@tonic-gate  */
797c478bd9Sstevel@tonic-gate #define	RPC_BUF_SIZE	2048
807c478bd9Sstevel@tonic-gate 
817c478bd9Sstevel@tonic-gate #define	NOWAIT	0	/* don't wait for operation of complete */
827c478bd9Sstevel@tonic-gate #define	WAIT	1	/* wait and ensure that operation is complete */
837c478bd9Sstevel@tonic-gate 
847c478bd9Sstevel@tonic-gate /*
857c478bd9Sstevel@tonic-gate  * RDMA xdr buffer control and other control flags. Add new flags here,
867c478bd9Sstevel@tonic-gate  * set them in private structure for xdr over RDMA in xdr_rdma.c
877c478bd9Sstevel@tonic-gate  */
88*0a701b1eSRobert Gordon #define	XDR_RDMA_CHUNK			0x1
89*0a701b1eSRobert Gordon #define	XDR_RDMA_WLIST_REG		0x2
90*0a701b1eSRobert Gordon #define	XDR_RDMA_RLIST_REG		0x4
91*0a701b1eSRobert Gordon 
92*0a701b1eSRobert Gordon #define	LONG_REPLY_LEN	65536
93*0a701b1eSRobert Gordon #define	WCL_BUF_LEN	32768
94*0a701b1eSRobert Gordon #define	RCL_BUF_LEN	32768
95*0a701b1eSRobert Gordon 
96*0a701b1eSRobert Gordon 
97*0a701b1eSRobert Gordon #define	RDMA_BUFS_RQST	34	/* Num bufs requested by client */
98*0a701b1eSRobert Gordon #define	RDMA_BUFS_GRANT	32	/* Num bufs granted by server */
99*0a701b1eSRobert Gordon 
100*0a701b1eSRobert Gordon struct xdr_ops *xdrrdma_xops(void);
101*0a701b1eSRobert Gordon 
102*0a701b1eSRobert Gordon /*
103*0a701b1eSRobert Gordon  * Credit Control Structures.
104*0a701b1eSRobert Gordon  */
105*0a701b1eSRobert Gordon typedef enum rdma_cc_type {
106*0a701b1eSRobert Gordon 	RDMA_CC_CLNT,	/* CONN is for a client */
107*0a701b1eSRobert Gordon 	RDMA_CC_SRV	/* CONN is for a server */
108*0a701b1eSRobert Gordon } rdma_cc_type_t;
109*0a701b1eSRobert Gordon 
110*0a701b1eSRobert Gordon /*
111*0a701b1eSRobert Gordon  * Client side credit control data structure.
112*0a701b1eSRobert Gordon  */
113*0a701b1eSRobert Gordon typedef struct rdma_clnt_cred_ctrl {
114*0a701b1eSRobert Gordon 	uint32_t	clnt_cc_granted_ops;
115*0a701b1eSRobert Gordon 	uint32_t	clnt_cc_in_flight_ops;
116*0a701b1eSRobert Gordon 	kcondvar_t	clnt_cc_cv;
117*0a701b1eSRobert Gordon } rdma_clnt_cred_ctrl_t;
118*0a701b1eSRobert Gordon 
119*0a701b1eSRobert Gordon /*
120*0a701b1eSRobert Gordon  * Server side credit control data structure.
121*0a701b1eSRobert Gordon  */
122*0a701b1eSRobert Gordon typedef struct rdma_srv_cred_ctrl {
123*0a701b1eSRobert Gordon 	uint32_t	srv_cc_buffers_granted;
124*0a701b1eSRobert Gordon 	uint32_t	srv_cc_cur_buffers_used;
125*0a701b1eSRobert Gordon 	uint32_t	srv_cc_posted;
126*0a701b1eSRobert Gordon 	uint32_t	srv_cc_max_buf_size;	/* to be determined by CCP */
127*0a701b1eSRobert Gordon 	uint32_t	srv_cc_cur_buf_size;	/* to be determined by CCP */
128*0a701b1eSRobert Gordon } rdma_srv_cred_ctrl_t;
129*0a701b1eSRobert Gordon 
130*0a701b1eSRobert Gordon typedef enum {
131*0a701b1eSRobert Gordon     RPCCALL_WLIST,
132*0a701b1eSRobert Gordon     RPCCALL_WCHUNK,
133*0a701b1eSRobert Gordon     RPCCALL_NOWRITE
134*0a701b1eSRobert Gordon }rpccall_write_t;
135*0a701b1eSRobert Gordon 
136*0a701b1eSRobert Gordon typedef enum {
137*0a701b1eSRobert Gordon 	CLIST_REG_SOURCE,
138*0a701b1eSRobert Gordon 	CLIST_REG_DST
139*0a701b1eSRobert Gordon } clist_dstsrc;
1407c478bd9Sstevel@tonic-gate 
1417c478bd9Sstevel@tonic-gate /*
1427c478bd9Sstevel@tonic-gate  * Return codes from RDMA operations
1437c478bd9Sstevel@tonic-gate  */
1447c478bd9Sstevel@tonic-gate typedef enum {
1457c478bd9Sstevel@tonic-gate 
1467c478bd9Sstevel@tonic-gate 	RDMA_SUCCESS = 0,	/* successful operation */
1477c478bd9Sstevel@tonic-gate 
1487c478bd9Sstevel@tonic-gate 	RDMA_INVAL = 1,		/* invalid parameter */
1497c478bd9Sstevel@tonic-gate 	RDMA_TIMEDOUT = 2,	/* operation timed out */
1507c478bd9Sstevel@tonic-gate 	RDMA_INTR = 3,		/* operation interrupted */
1517c478bd9Sstevel@tonic-gate 	RDMA_NORESOURCE = 4,	/* insufficient resource */
1527c478bd9Sstevel@tonic-gate 	/*
1537c478bd9Sstevel@tonic-gate 	 * connection errors
1547c478bd9Sstevel@tonic-gate 	 */
1557c478bd9Sstevel@tonic-gate 	RDMA_REJECT = 5,	/* connection req rejected */
1567c478bd9Sstevel@tonic-gate 	RDMA_NOLISTENER = 6,	/* no listener on server */
1577c478bd9Sstevel@tonic-gate 	RDMA_UNREACHABLE = 7,	/* host unreachable */
1587c478bd9Sstevel@tonic-gate 	RDMA_CONNLOST = 8,	/* connection lost */
1597c478bd9Sstevel@tonic-gate 
1607c478bd9Sstevel@tonic-gate 	RDMA_XPRTFAILED = 9,	/* RDMA transport failed */
1617c478bd9Sstevel@tonic-gate 	RDMA_PROTECTERR = 10,	/* memory protection error */
1627c478bd9Sstevel@tonic-gate 	RDMA_OVERRUN = 11,	/* transport overrun */
1637c478bd9Sstevel@tonic-gate 	RDMA_RECVQEMPTY = 12,	/* incoming pkt dropped, recv q empty */
1647c478bd9Sstevel@tonic-gate 	RDMA_PROTFAILED = 13,	/* RDMA protocol failed */
1657c478bd9Sstevel@tonic-gate 	RDMA_NOTSUPP = 14,	/* requested feature not supported */
1667c478bd9Sstevel@tonic-gate 	RDMA_REMOTERR = 15,	/* error at remote end */
1677c478bd9Sstevel@tonic-gate 	/*
1687c478bd9Sstevel@tonic-gate 	 * RDMATF errors
1697c478bd9Sstevel@tonic-gate 	 */
1707c478bd9Sstevel@tonic-gate 	RDMA_BADVERS = 16,	/* mismatch RDMATF versions */
1717c478bd9Sstevel@tonic-gate 	RDMA_REG_EXIST = 17,	/* RDMATF registration already exists */
1727c478bd9Sstevel@tonic-gate 
1737c478bd9Sstevel@tonic-gate 	/*
1747c478bd9Sstevel@tonic-gate 	 * fallback error
1757c478bd9Sstevel@tonic-gate 	 */
1767c478bd9Sstevel@tonic-gate 	RDMA_FAILED = 18	/* generic error */
1777c478bd9Sstevel@tonic-gate } rdma_stat;
1787c478bd9Sstevel@tonic-gate 
1797c478bd9Sstevel@tonic-gate /*
1807c478bd9Sstevel@tonic-gate  * Memory region context. This is an RDMA provider generated
1817c478bd9Sstevel@tonic-gate  * handle for a registered arbitrary size contiguous virtual
1827c478bd9Sstevel@tonic-gate  * memory. The RDMA Interface Adapter needs this for local or
1837c478bd9Sstevel@tonic-gate  * remote memory access.
1847c478bd9Sstevel@tonic-gate  *
1857c478bd9Sstevel@tonic-gate  * The mrc_rmr field holds the remote memory region context
1867c478bd9Sstevel@tonic-gate  * which is sent over-the-wire to provide the remote host
1877c478bd9Sstevel@tonic-gate  * with RDMA access to the memory region.
1887c478bd9Sstevel@tonic-gate  */
1897c478bd9Sstevel@tonic-gate struct mrc {
1907c478bd9Sstevel@tonic-gate 	uint32_t	mrc_rmr;	/* Remote MR context, sent OTW */
1917c478bd9Sstevel@tonic-gate 	union {
1927c478bd9Sstevel@tonic-gate 		struct mr {
1937c478bd9Sstevel@tonic-gate 			uint32_t	lmr; 	/* Local MR context */
1947c478bd9Sstevel@tonic-gate 			uint64_t	linfo;	/* Local memory info */
1957c478bd9Sstevel@tonic-gate 		} mr;
1967c478bd9Sstevel@tonic-gate 	} lhdl;
1977c478bd9Sstevel@tonic-gate };
1987c478bd9Sstevel@tonic-gate 
1997c478bd9Sstevel@tonic-gate #define	mrc_lmr		lhdl.mr.lmr
2007c478bd9Sstevel@tonic-gate #define	mrc_linfo	lhdl.mr.linfo
2017c478bd9Sstevel@tonic-gate 
202*0a701b1eSRobert Gordon /*
203*0a701b1eSRobert Gordon  * Memory management for the RDMA buffers
204*0a701b1eSRobert Gordon  */
205*0a701b1eSRobert Gordon /*
206*0a701b1eSRobert Gordon  * RDMA buffer types
207*0a701b1eSRobert Gordon  */
208*0a701b1eSRobert Gordon typedef enum {
209*0a701b1eSRobert Gordon 	SEND_BUFFER,	/* buf for send msg */
210*0a701b1eSRobert Gordon 	SEND_DESCRIPTOR, /* buf used for send msg descriptor in plugins only */
211*0a701b1eSRobert Gordon 	RECV_BUFFER,	/* buf for recv msg */
212*0a701b1eSRobert Gordon 	RECV_DESCRIPTOR, /* buf used for recv msg descriptor in plugins only */
213*0a701b1eSRobert Gordon 	RDMA_LONG_BUFFER /* chunk buf used in RDMATF only and not in plugins */
214*0a701b1eSRobert Gordon } rdma_btype;
215*0a701b1eSRobert Gordon 
216*0a701b1eSRobert Gordon /*
217*0a701b1eSRobert Gordon  * RDMA buffer information
218*0a701b1eSRobert Gordon  */
219*0a701b1eSRobert Gordon typedef struct rdma_buf {
220*0a701b1eSRobert Gordon 	rdma_btype	type;	/* buffer type */
221*0a701b1eSRobert Gordon 	uint_t		len;	/* length of buffer */
222*0a701b1eSRobert Gordon 	caddr_t		addr;	/* buffer address */
223*0a701b1eSRobert Gordon 	struct mrc	handle;	/* buffer registration handle */
224*0a701b1eSRobert Gordon 	caddr_t		rb_private;
225*0a701b1eSRobert Gordon } rdma_buf_t;
226*0a701b1eSRobert Gordon 
227*0a701b1eSRobert Gordon 
2287c478bd9Sstevel@tonic-gate /*
2297c478bd9Sstevel@tonic-gate  * The XDR offset value is used by the XDR
2307c478bd9Sstevel@tonic-gate  * routine to identify the position in the
2317c478bd9Sstevel@tonic-gate  * RPC message where the opaque object would
2327c478bd9Sstevel@tonic-gate  * normally occur. Neither the data content
2337c478bd9Sstevel@tonic-gate  * of the chunk, nor its size field are included
2347c478bd9Sstevel@tonic-gate  * in the RPC message.  The XDR offset is calculated
2357c478bd9Sstevel@tonic-gate  * as if the chunks were present.
2367c478bd9Sstevel@tonic-gate  *
2377c478bd9Sstevel@tonic-gate  * The remaining fields identify the chunk of data
2387c478bd9Sstevel@tonic-gate  * on the sender.  The c_memhandle identifies a
2397c478bd9Sstevel@tonic-gate  * registered RDMA memory region and the c_addr
2407c478bd9Sstevel@tonic-gate  * and c_len fields identify the chunk within it.
2417c478bd9Sstevel@tonic-gate  */
2427c478bd9Sstevel@tonic-gate struct clist {
2437c478bd9Sstevel@tonic-gate 	uint32		c_xdroff;	/* XDR offset */
2447c478bd9Sstevel@tonic-gate 	uint32		c_len;		/* Length */
2457c478bd9Sstevel@tonic-gate 	struct mrc	c_smemhandle;	/* src memory handle */
2467c478bd9Sstevel@tonic-gate 	uint64 		c_ssynchandle;	/* src sync handle */
247*0a701b1eSRobert Gordon 	union {
248*0a701b1eSRobert Gordon 		uint64		c_saddr;	/* src address */
249*0a701b1eSRobert Gordon 		caddr_t 	c_saddr3;
250*0a701b1eSRobert Gordon 	} w;
2517c478bd9Sstevel@tonic-gate 	struct mrc	c_dmemhandle;	/* dst memory handle */
2527c478bd9Sstevel@tonic-gate 	uint64		c_dsynchandle;	/* dst sync handle */
253*0a701b1eSRobert Gordon 	union {
254*0a701b1eSRobert Gordon 		uint64	c_daddr;	/* dst address */
255*0a701b1eSRobert Gordon 		caddr_t	c_daddr3;
256*0a701b1eSRobert Gordon 	} u;
257*0a701b1eSRobert Gordon 	struct as	*c_adspc;	/* address space for saddr/daddr */
258*0a701b1eSRobert Gordon 	rdma_buf_t	rb_longbuf;	/* used for long requests/replies */
2597c478bd9Sstevel@tonic-gate 	struct clist	*c_next;	/* Next chunk */
2607c478bd9Sstevel@tonic-gate };
2617c478bd9Sstevel@tonic-gate 
2627c478bd9Sstevel@tonic-gate typedef struct clist clist;
2637c478bd9Sstevel@tonic-gate 
264*0a701b1eSRobert Gordon /*
265*0a701b1eSRobert Gordon  * max 4M wlist xfer size
266*0a701b1eSRobert Gordon  * This is defined because the rfs3_tsize service requires
267*0a701b1eSRobert Gordon  * svc_req struct (which we don't have that in krecv).
268*0a701b1eSRobert Gordon  */
269*0a701b1eSRobert Gordon #define	MAX_SVC_XFER_SIZE (4*1024*1024)
270*0a701b1eSRobert Gordon 
2717c478bd9Sstevel@tonic-gate enum rdma_proc {
2727c478bd9Sstevel@tonic-gate 	RDMA_MSG	= 0,	/* chunk list and RPC msg follow */
2737c478bd9Sstevel@tonic-gate 	RDMA_NOMSG	= 1,	/* only chunk list follows */
2747c478bd9Sstevel@tonic-gate 	RDMA_MSGP	= 2,	/* chunk list and RPC msg with padding follow */
2757c478bd9Sstevel@tonic-gate 	RDMA_DONE	= 3	/* signal completion of chunk transfer */
2767c478bd9Sstevel@tonic-gate };
2777c478bd9Sstevel@tonic-gate 
2787c478bd9Sstevel@tonic-gate /*
2797c478bd9Sstevel@tonic-gate  * Listener information for a service
2807c478bd9Sstevel@tonic-gate  */
2817c478bd9Sstevel@tonic-gate struct rdma_svc_data {
2827c478bd9Sstevel@tonic-gate 	queue_t		q;	/* queue_t to place incoming pkts */
2837c478bd9Sstevel@tonic-gate 	int		active;	/* If active, after registeration startup */
2847c478bd9Sstevel@tonic-gate 	rdma_stat	err_code;	/* Error code from plugin layer */
2857c478bd9Sstevel@tonic-gate 	int32_t		svcid;		/* RDMA based service identifier */
2867c478bd9Sstevel@tonic-gate };
2877c478bd9Sstevel@tonic-gate 
2887c478bd9Sstevel@tonic-gate /*
2897c478bd9Sstevel@tonic-gate  * Per RDMA plugin module information.
2907c478bd9Sstevel@tonic-gate  * Will be populated by each plugin
2917c478bd9Sstevel@tonic-gate  * module during its initialization.
2927c478bd9Sstevel@tonic-gate  */
2937c478bd9Sstevel@tonic-gate typedef struct rdma_mod {
2947c478bd9Sstevel@tonic-gate 	char 		*rdma_api;		/* "kvipl", "ibtf", etc */
2957c478bd9Sstevel@tonic-gate 	uint_t 		rdma_version;		/* RDMATF API version */
2967c478bd9Sstevel@tonic-gate 	int		rdma_count;		/* # of devices */
2977c478bd9Sstevel@tonic-gate 	struct rdmaops 	*rdma_ops;		/* rdma op vector for api */
2987c478bd9Sstevel@tonic-gate } rdma_mod_t;
2997c478bd9Sstevel@tonic-gate 
3007c478bd9Sstevel@tonic-gate /*
3017c478bd9Sstevel@tonic-gate  * Registry of RDMA plugins
3027c478bd9Sstevel@tonic-gate  */
3037c478bd9Sstevel@tonic-gate typedef struct rdma_registry {
3047c478bd9Sstevel@tonic-gate 	rdma_mod_t	*r_mod;		/* plugin mod info */
3057c478bd9Sstevel@tonic-gate 	struct rdma_registry *r_next;	/* next registered RDMA plugin */
3067c478bd9Sstevel@tonic-gate } rdma_registry_t;
3077c478bd9Sstevel@tonic-gate 
3087c478bd9Sstevel@tonic-gate /*
3097c478bd9Sstevel@tonic-gate  * RDMA transport information
3107c478bd9Sstevel@tonic-gate  */
3117c478bd9Sstevel@tonic-gate typedef struct rdma_info {
3127c478bd9Sstevel@tonic-gate 	uint_t	addrlen;	/* address length */
3137c478bd9Sstevel@tonic-gate 	uint_t  mts;		/* max transfer size */
3147c478bd9Sstevel@tonic-gate 	uint_t  mtu;		/* native mtu size of unlerlying network */
3157c478bd9Sstevel@tonic-gate } rdma_info_t;
3167c478bd9Sstevel@tonic-gate 
317*0a701b1eSRobert Gordon typedef enum {
318*0a701b1eSRobert Gordon 	C_IDLE		= 0x00000001,
319*0a701b1eSRobert Gordon 	C_CONN_PEND	= 0x00000002,
320*0a701b1eSRobert Gordon 	C_CONNECTED	= 0x00000004,
321*0a701b1eSRobert Gordon 	C_ERROR_CONN	= 0x00000008,
322*0a701b1eSRobert Gordon 	C_DISCONN_PEND	= 0x00000010,
323*0a701b1eSRobert Gordon 	C_REMOTE_DOWN	= 0x00000020
324*0a701b1eSRobert Gordon } conn_c_state;
325*0a701b1eSRobert Gordon 
3267c478bd9Sstevel@tonic-gate /*
3277c478bd9Sstevel@tonic-gate  * RDMA Connection information
3287c478bd9Sstevel@tonic-gate  */
3297c478bd9Sstevel@tonic-gate typedef struct conn {
3307c478bd9Sstevel@tonic-gate 	rdma_mod_t	*c_rdmamod;	/* RDMA transport info for conn */
3317c478bd9Sstevel@tonic-gate 	struct netbuf	c_raddr;	/* remote address */
3327c478bd9Sstevel@tonic-gate 	struct netbuf	c_laddr;	/* local address */
3337c478bd9Sstevel@tonic-gate 	int		c_ref;		/* no. of clients of connection */
3347c478bd9Sstevel@tonic-gate 	struct conn	*c_next;	/* next in list of connections */
3357c478bd9Sstevel@tonic-gate 	struct conn	*c_prev;	/* prev in list of connections */
3367c478bd9Sstevel@tonic-gate 	caddr_t		c_private;	/* transport specific stuff */
337*0a701b1eSRobert Gordon 	conn_c_state	c_state;	/* state of connection */
338*0a701b1eSRobert Gordon 	rdma_cc_type_t	c_cc_type;	/* client or server, for credit cntrl */
339*0a701b1eSRobert Gordon 	union {
340*0a701b1eSRobert Gordon 		rdma_clnt_cred_ctrl_t	c_clnt_cc;
341*0a701b1eSRobert Gordon 		rdma_srv_cred_ctrl_t	c_srv_cc;
342*0a701b1eSRobert Gordon 	} rdma_conn_cred_ctrl_u;
3437c478bd9Sstevel@tonic-gate 	kmutex_t	c_lock;		/* protect c_state and c_ref fields */
3447c478bd9Sstevel@tonic-gate 	kcondvar_t	c_cv;		/* to signal when pending is done */
3457c478bd9Sstevel@tonic-gate } CONN;
3467c478bd9Sstevel@tonic-gate 
3477c478bd9Sstevel@tonic-gate 
3487c478bd9Sstevel@tonic-gate /*
3497c478bd9Sstevel@tonic-gate  * Data transferred from plugin interrupt to svc_queuereq()
3507c478bd9Sstevel@tonic-gate  */
351*0a701b1eSRobert Gordon typedef struct rdma_recv_data {
3527c478bd9Sstevel@tonic-gate 	CONN		*conn;
3537c478bd9Sstevel@tonic-gate 	int		status;
3547c478bd9Sstevel@tonic-gate 	rdma_buf_t	rpcmsg;
355*0a701b1eSRobert Gordon } rdma_recv_data_t;
356*0a701b1eSRobert Gordon 
357*0a701b1eSRobert Gordon /* structure used to pass information for READ over rdma write */
358*0a701b1eSRobert Gordon typedef enum {
359*0a701b1eSRobert Gordon 	RCI_WRITE_UIO_CHUNK = 1,
360*0a701b1eSRobert Gordon 	RCI_WRITE_ADDR_CHUNK = 2,
361*0a701b1eSRobert Gordon 	RCI_REPLY_CHUNK = 3
362*0a701b1eSRobert Gordon } rci_type_t;
363*0a701b1eSRobert Gordon 
364*0a701b1eSRobert Gordon typedef struct {
365*0a701b1eSRobert Gordon 	rci_type_t rci_type;
366*0a701b1eSRobert Gordon 	union {
367*0a701b1eSRobert Gordon 		struct uio *rci_uiop;
368*0a701b1eSRobert Gordon 		caddr_t    rci_addr;
369*0a701b1eSRobert Gordon 	} rci_a;
370*0a701b1eSRobert Gordon 	uint32	rci_len;
371*0a701b1eSRobert Gordon 	struct clist	**rci_clpp; /* point to write chunk list in readargs */
372*0a701b1eSRobert Gordon } rdma_chunkinfo_t;
373*0a701b1eSRobert Gordon 
374*0a701b1eSRobert Gordon typedef struct {
375*0a701b1eSRobert Gordon 	uint_t rcil_len;
376*0a701b1eSRobert Gordon 	uint_t rcil_len_alt;
377*0a701b1eSRobert Gordon } rdma_chunkinfo_lengths_t;
378*0a701b1eSRobert Gordon 
379*0a701b1eSRobert Gordon typedef struct {
380*0a701b1eSRobert Gordon 	struct	clist	*rwci_wlist;
381*0a701b1eSRobert Gordon 	CONN		*rwci_conn;
382*0a701b1eSRobert Gordon } rdma_wlist_conn_info_t;
3837c478bd9Sstevel@tonic-gate 
3847c478bd9Sstevel@tonic-gate /*
3857c478bd9Sstevel@tonic-gate  * Operations vector for RDMA transports.
3867c478bd9Sstevel@tonic-gate  */
3877c478bd9Sstevel@tonic-gate typedef struct rdmaops {
3887c478bd9Sstevel@tonic-gate 	/* Network */
3897c478bd9Sstevel@tonic-gate 	rdma_stat	(*rdma_reachable)(int addr_type, struct netbuf *,
3907c478bd9Sstevel@tonic-gate 						void **handle);
3917c478bd9Sstevel@tonic-gate 	/* Connection */
3927c478bd9Sstevel@tonic-gate 	rdma_stat	(*rdma_get_conn)(struct netbuf *, int addr_type,
3937c478bd9Sstevel@tonic-gate 						void *, CONN **);
3947c478bd9Sstevel@tonic-gate 	rdma_stat	(*rdma_rel_conn)(CONN *);
3957c478bd9Sstevel@tonic-gate 	/* Server side listner start and stop routines */
3967c478bd9Sstevel@tonic-gate 	void		(*rdma_svc_listen)(struct rdma_svc_data *);
3977c478bd9Sstevel@tonic-gate 	void		(*rdma_svc_stop)(struct rdma_svc_data *);
3987c478bd9Sstevel@tonic-gate 	/* Memory */
399*0a701b1eSRobert Gordon 	rdma_stat	(*rdma_regmem)(CONN *, caddr_t, caddr_t,
400*0a701b1eSRobert Gordon 			    uint_t, struct mrc *);
4017c478bd9Sstevel@tonic-gate 	rdma_stat	(*rdma_deregmem)(CONN *, caddr_t, struct mrc);
402*0a701b1eSRobert Gordon 	rdma_stat	(*rdma_regmemsync)(CONN *, caddr_t, caddr_t, uint_t,
403*0a701b1eSRobert Gordon 				struct mrc *, void **, void *);
4047c478bd9Sstevel@tonic-gate 	rdma_stat	(*rdma_deregmemsync)(CONN *, caddr_t, struct mrc,
405*0a701b1eSRobert Gordon 			    void *, void *);
4067c478bd9Sstevel@tonic-gate 	rdma_stat	(*rdma_syncmem)(CONN *, void *, caddr_t, int, int);
4077c478bd9Sstevel@tonic-gate 	/* Buffer */
4087c478bd9Sstevel@tonic-gate 	rdma_stat	(*rdma_buf_alloc)(CONN *, rdma_buf_t *);
4097c478bd9Sstevel@tonic-gate 	void		(*rdma_buf_free)(CONN *, rdma_buf_t *);
4107c478bd9Sstevel@tonic-gate 	/* Transfer */
4117c478bd9Sstevel@tonic-gate 	rdma_stat	(*rdma_send)(CONN *, clist *, uint32_t);
4127c478bd9Sstevel@tonic-gate 	rdma_stat	(*rdma_send_resp)(CONN *, clist *, uint32_t);
4137c478bd9Sstevel@tonic-gate 	rdma_stat	(*rdma_clnt_recvbuf)(CONN *, clist *, uint32_t);
414*0a701b1eSRobert Gordon 	rdma_stat	(*rdma_clnt_recvbuf_remove)(CONN *, uint32_t);
4157c478bd9Sstevel@tonic-gate 	rdma_stat	(*rdma_svc_recvbuf)(CONN *, clist *);
4167c478bd9Sstevel@tonic-gate 	rdma_stat	(*rdma_recv)(CONN *, clist **, uint32_t);
4177c478bd9Sstevel@tonic-gate 	/* RDMA */
4187c478bd9Sstevel@tonic-gate 	rdma_stat	(*rdma_read)(CONN *, clist *, int);
4197c478bd9Sstevel@tonic-gate 	rdma_stat	(*rdma_write)(CONN *, clist *, int);
4207c478bd9Sstevel@tonic-gate 	/* INFO */
4217c478bd9Sstevel@tonic-gate 	rdma_stat	(*rdma_getinfo)(rdma_info_t *info);
4227c478bd9Sstevel@tonic-gate } rdmaops_t;
4237c478bd9Sstevel@tonic-gate 
4247c478bd9Sstevel@tonic-gate /*
4257c478bd9Sstevel@tonic-gate  * RDMA operations.
4267c478bd9Sstevel@tonic-gate  */
4277c478bd9Sstevel@tonic-gate #define	RDMA_REACHABLE(rdma_ops, addr_type, addr, handle)	\
4287c478bd9Sstevel@tonic-gate 	(*(rdma_ops)->rdma_reachable)(addr_type, addr, handle)
4297c478bd9Sstevel@tonic-gate 
4307c478bd9Sstevel@tonic-gate #define	RDMA_GET_CONN(rdma_ops, addr, addr_type, handle, conn)	\
4317c478bd9Sstevel@tonic-gate 	(*(rdma_ops)->rdma_get_conn)(addr, addr_type, handle, conn)
4327c478bd9Sstevel@tonic-gate 
4337c478bd9Sstevel@tonic-gate #define	RDMA_REL_CONN(conn)	\
4347c478bd9Sstevel@tonic-gate 	(*(conn)->c_rdmamod->rdma_ops->rdma_rel_conn)(conn)
4357c478bd9Sstevel@tonic-gate 
436*0a701b1eSRobert Gordon #define	RDMA_REGMEM(conn, adsp, buff, len, handle)	\
437*0a701b1eSRobert Gordon 	(*(conn)->c_rdmamod->rdma_ops->rdma_regmem)(conn, adsp,	\
438*0a701b1eSRobert Gordon 		buff, len, handle)
4397c478bd9Sstevel@tonic-gate 
4407c478bd9Sstevel@tonic-gate #define	RDMA_DEREGMEM(conn, buff, handle)	\
4417c478bd9Sstevel@tonic-gate 	(*(conn)->c_rdmamod->rdma_ops->rdma_deregmem)(conn, buff, handle)
4427c478bd9Sstevel@tonic-gate 
443*0a701b1eSRobert Gordon #define	RDMA_REGMEMSYNC(conn, adsp, buff, len, handle, synchandle, lrc)	\
444*0a701b1eSRobert Gordon 	(*(conn)->c_rdmamod->rdma_ops->rdma_regmemsync)(conn, adsp, buff, \
445*0a701b1eSRobert Gordon 	len, handle, synchandle, lrc)
4467c478bd9Sstevel@tonic-gate 
447*0a701b1eSRobert Gordon #define	RDMA_DEREGMEMSYNC(conn, buff, handle, synchandle, lrc)	\
448*0a701b1eSRobert Gordon 	(*(conn)->c_rdmamod->rdma_ops->rdma_deregmemsync)(conn, buff,	\
449*0a701b1eSRobert Gordon 	handle, synchandle, lrc)
4507c478bd9Sstevel@tonic-gate 
4517c478bd9Sstevel@tonic-gate #define	RDMA_SYNCMEM(conn, handle, buff, len, direction)	\
4527c478bd9Sstevel@tonic-gate 	(*(conn)->c_rdmamod->rdma_ops->rdma_syncmem)(conn, handle, \
4537c478bd9Sstevel@tonic-gate 	    buff, len, direction)
4547c478bd9Sstevel@tonic-gate 
4557c478bd9Sstevel@tonic-gate #define	RDMA_BUF_ALLOC(conn, rbuf)	\
4567c478bd9Sstevel@tonic-gate 	(*(conn)->c_rdmamod->rdma_ops->rdma_buf_alloc)(conn, rbuf)
4577c478bd9Sstevel@tonic-gate 
4587c478bd9Sstevel@tonic-gate #define	RDMA_BUF_FREE(conn, rbuf)	\
4597c478bd9Sstevel@tonic-gate 	(*(conn)->c_rdmamod->rdma_ops->rdma_buf_free)(conn, rbuf)
4607c478bd9Sstevel@tonic-gate 
4617c478bd9Sstevel@tonic-gate #define	RDMA_SEND(conn, sendlist, xid)	\
4627c478bd9Sstevel@tonic-gate 	(*(conn)->c_rdmamod->rdma_ops->rdma_send)(conn, sendlist, xid)
4637c478bd9Sstevel@tonic-gate 
4647c478bd9Sstevel@tonic-gate #define	RDMA_SEND_RESP(conn, sendlist, xid)	\
4657c478bd9Sstevel@tonic-gate 	(*(conn)->c_rdmamod->rdma_ops->rdma_send_resp)(conn, sendlist, xid)
4667c478bd9Sstevel@tonic-gate 
4677c478bd9Sstevel@tonic-gate #define	RDMA_CLNT_RECVBUF(conn, cl, xid)	\
4687c478bd9Sstevel@tonic-gate 	(*(conn)->c_rdmamod->rdma_ops->rdma_clnt_recvbuf)(conn, cl, xid)
4697c478bd9Sstevel@tonic-gate 
470*0a701b1eSRobert Gordon #define	RDMA_CLNT_RECVBUF_REMOVE(conn, xid)	\
471*0a701b1eSRobert Gordon 	(*(conn)->c_rdmamod->rdma_ops->rdma_clnt_recvbuf_remove)(conn, xid)
472*0a701b1eSRobert Gordon 
4737c478bd9Sstevel@tonic-gate #define	RDMA_SVC_RECVBUF(conn, cl)	\
4747c478bd9Sstevel@tonic-gate 	(*(conn)->c_rdmamod->rdma_ops->rdma_svc_recvbuf)(conn, cl)
4757c478bd9Sstevel@tonic-gate 
4767c478bd9Sstevel@tonic-gate #define	RDMA_RECV(conn, recvlist, xid)	\
4777c478bd9Sstevel@tonic-gate 	(*(conn)->c_rdmamod->rdma_ops->rdma_recv)(conn, recvlist, xid)
4787c478bd9Sstevel@tonic-gate 
4797c478bd9Sstevel@tonic-gate #define	RDMA_READ(conn, cl, wait)	\
4807c478bd9Sstevel@tonic-gate 	(*(conn)->c_rdmamod->rdma_ops->rdma_read)(conn, cl, wait)
4817c478bd9Sstevel@tonic-gate 
4827c478bd9Sstevel@tonic-gate #define	RDMA_WRITE(conn, cl, wait)	\
4837c478bd9Sstevel@tonic-gate 	(*(conn)->c_rdmamod->rdma_ops->rdma_write)(conn, cl, wait)
4847c478bd9Sstevel@tonic-gate 
4857c478bd9Sstevel@tonic-gate #define	RDMA_GETINFO(rdma_mod, info)	\
4867c478bd9Sstevel@tonic-gate 	(*(rdma_mod)->rdma_ops->rdma_getinfo)(info)
4877c478bd9Sstevel@tonic-gate 
4887c478bd9Sstevel@tonic-gate #ifdef _KERNEL
4897c478bd9Sstevel@tonic-gate extern rdma_registry_t	*rdma_mod_head;
4907c478bd9Sstevel@tonic-gate extern krwlock_t rdma_lock;		/* protects rdma_mod_head list */
4917c478bd9Sstevel@tonic-gate extern int rdma_modloaded;		/* flag for loading RDMA plugins */
4927c478bd9Sstevel@tonic-gate extern int rdma_dev_available;		/* rdma device is loaded or not */
4937c478bd9Sstevel@tonic-gate extern kmutex_t rdma_modload_lock;	/* protects rdma_modloaded flag */
4947c478bd9Sstevel@tonic-gate extern uint_t rdma_minchunk;
4957c478bd9Sstevel@tonic-gate extern ldi_ident_t rpcmod_li; 		/* needed by layed driver framework */
4967c478bd9Sstevel@tonic-gate 
4977c478bd9Sstevel@tonic-gate /*
4987c478bd9Sstevel@tonic-gate  * General RDMA routines
4997c478bd9Sstevel@tonic-gate  */
500*0a701b1eSRobert Gordon extern struct clist *clist_alloc(void);
501*0a701b1eSRobert Gordon extern void clist_add(struct clist **, uint32_t, int,
502*0a701b1eSRobert Gordon 	struct mrc *, caddr_t, struct mrc *, caddr_t);
503*0a701b1eSRobert Gordon extern void clist_free(struct clist *);
504*0a701b1eSRobert Gordon extern rdma_stat clist_register(CONN *conn, struct clist *cl, clist_dstsrc);
505*0a701b1eSRobert Gordon extern rdma_stat clist_deregister(CONN *conn, struct clist *cl, clist_dstsrc);
506*0a701b1eSRobert Gordon extern rdma_stat clist_syncmem(CONN *conn, struct clist *cl, clist_dstsrc);
507*0a701b1eSRobert Gordon extern rdma_stat rdma_clnt_postrecv(CONN *conn, uint32_t xid);
508*0a701b1eSRobert Gordon extern rdma_stat rdma_clnt_postrecv_remove(CONN *conn, uint32_t xid);
509*0a701b1eSRobert Gordon extern rdma_stat rdma_svc_postrecv(CONN *conn);
5107c478bd9Sstevel@tonic-gate extern rdma_stat rdma_register_mod(rdma_mod_t *mod);
5117c478bd9Sstevel@tonic-gate extern rdma_stat rdma_unregister_mod(rdma_mod_t *mod);
512*0a701b1eSRobert Gordon extern rdma_stat rdma_buf_alloc(CONN *, rdma_buf_t *);
513*0a701b1eSRobert Gordon extern void rdma_buf_free(CONN *, rdma_buf_t *);
5147c478bd9Sstevel@tonic-gate extern int rdma_modload();
515*0a701b1eSRobert Gordon extern bool_t   rdma_get_wchunk(struct svc_req *, iovec_t *, struct clist *);
5167c478bd9Sstevel@tonic-gate 
5177c478bd9Sstevel@tonic-gate /*
5187c478bd9Sstevel@tonic-gate  * RDMA XDR
5197c478bd9Sstevel@tonic-gate  */
5207c478bd9Sstevel@tonic-gate extern void xdrrdma_create(XDR *, caddr_t, uint_t, int, struct clist *,
5217c478bd9Sstevel@tonic-gate 	enum xdr_op, CONN *);
5227c478bd9Sstevel@tonic-gate extern void xdrrdma_destroy(XDR *);
523*0a701b1eSRobert Gordon 
5247c478bd9Sstevel@tonic-gate extern uint_t xdrrdma_getpos(XDR *);
5257c478bd9Sstevel@tonic-gate extern bool_t xdrrdma_setpos(XDR *, uint_t);
5267c478bd9Sstevel@tonic-gate extern bool_t xdr_clist(XDR *, clist *);
5277c478bd9Sstevel@tonic-gate extern bool_t xdr_do_clist(XDR *, clist **);
5287c478bd9Sstevel@tonic-gate extern uint_t xdr_getbufsize(XDR *);
529*0a701b1eSRobert Gordon extern unsigned int xdrrdma_sizeof(xdrproc_t, void *, int, uint_t *, uint_t *);
530*0a701b1eSRobert Gordon extern unsigned int xdrrdma_authsize(AUTH *, struct cred *, int);
531*0a701b1eSRobert Gordon 
532*0a701b1eSRobert Gordon extern void xdrrdma_store_wlist(XDR *, struct clist *);
533*0a701b1eSRobert Gordon extern struct clist *xdrrdma_wclist(XDR *);
534*0a701b1eSRobert Gordon extern bool_t xdr_decode_reply_wchunk(XDR *, struct clist **);
535*0a701b1eSRobert Gordon extern bool_t xdr_decode_wlist(XDR *xdrs, struct clist **, bool_t *);
536*0a701b1eSRobert Gordon extern bool_t xdr_decode_wlist_svc(XDR *xdrs, struct clist **, bool_t *,
537*0a701b1eSRobert Gordon 	uint32_t *, CONN *);
538*0a701b1eSRobert Gordon extern bool_t xdr_encode_rlist_svc(XDR *, clist *);
539*0a701b1eSRobert Gordon extern bool_t xdr_encode_wlist(XDR *, clist *);
540*0a701b1eSRobert Gordon extern bool_t xdr_encode_reply_wchunk(XDR *, struct clist *,
541*0a701b1eSRobert Gordon 		uint32_t seg_array_len);
542*0a701b1eSRobert Gordon bool_t xdrrdma_getrdmablk(XDR *, struct clist **, uint_t *,
543*0a701b1eSRobert Gordon 	CONN **conn, const uint_t);
544*0a701b1eSRobert Gordon bool_t xdrrdma_read_from_client(struct clist **, CONN **, uint_t);
545*0a701b1eSRobert Gordon bool_t xdrrdma_send_read_data(XDR *, struct clist *);
546*0a701b1eSRobert Gordon bool_t xdrrdma_free_clist(CONN *, struct clist *);
5477c478bd9Sstevel@tonic-gate #endif /* _KERNEL */
5487c478bd9Sstevel@tonic-gate 
5497c478bd9Sstevel@tonic-gate #ifdef __cplusplus
5507c478bd9Sstevel@tonic-gate }
5517c478bd9Sstevel@tonic-gate #endif
5527c478bd9Sstevel@tonic-gate 
5537c478bd9Sstevel@tonic-gate #endif	/* _RPC_RPC_RDMA_H */
554