1321936Shselasky/*
2321936Shselasky * Copyright (c) 2005 Voltaire Inc.  All rights reserved.
3321936Shselasky * Copyright (c) 2005-2014 Intel Corporation.  All rights reserved.
4321936Shselasky *
5321936Shselasky * This software is available to you under a choice of one of two
6321936Shselasky * licenses.  You may choose to be licensed under the terms of the GNU
7321936Shselasky * General Public License (GPL) Version 2, available from the file
8321936Shselasky * COPYING in the main directory of this source tree, or the
9321936Shselasky * OpenIB.org BSD license below:
10321936Shselasky *
11321936Shselasky *     Redistribution and use in source and binary forms, with or
12321936Shselasky *     without modification, are permitted provided that the following
13321936Shselasky *     conditions are met:
14321936Shselasky *
15321936Shselasky *      - Redistributions of source code must retain the above
16321936Shselasky *        copyright notice, this list of conditions and the following
17321936Shselasky *        disclaimer.
18321936Shselasky *
19321936Shselasky *      - Redistributions in binary form must reproduce the above
20321936Shselasky *        copyright notice, this list of conditions and the following
21321936Shselasky *        disclaimer in the documentation and/or other materials
22321936Shselasky *        provided with the distribution.
23321936Shselasky *
24321936Shselasky * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
25321936Shselasky * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
26321936Shselasky * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
27321936Shselasky * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
28321936Shselasky * BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
29321936Shselasky * ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
30321936Shselasky * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
31321936Shselasky * SOFTWARE.
32321936Shselasky */
33321936Shselasky
34321936Shselasky#if !defined(RDMA_CMA_H)
35321936Shselasky#define RDMA_CMA_H
36321936Shselasky
37321936Shselasky#include <netinet/in.h>
38321936Shselasky#include <sys/socket.h>
39321936Shselasky#include <infiniband/verbs.h>
40321936Shselasky#include <infiniband/sa.h>
41321936Shselasky
42321936Shselasky#ifdef __cplusplus
43321936Shselaskyextern "C" {
44321936Shselasky#endif
45321936Shselasky
46321936Shselasky/*
47321936Shselasky * Upon receiving a device removal event, users must destroy the associated
48321936Shselasky * RDMA identifier and release all resources allocated with the device.
49321936Shselasky */
50321936Shselaskyenum rdma_cm_event_type {
51321936Shselasky	RDMA_CM_EVENT_ADDR_RESOLVED,
52321936Shselasky	RDMA_CM_EVENT_ADDR_ERROR,
53321936Shselasky	RDMA_CM_EVENT_ROUTE_RESOLVED,
54321936Shselasky	RDMA_CM_EVENT_ROUTE_ERROR,
55321936Shselasky	RDMA_CM_EVENT_CONNECT_REQUEST,
56321936Shselasky	RDMA_CM_EVENT_CONNECT_RESPONSE,
57321936Shselasky	RDMA_CM_EVENT_CONNECT_ERROR,
58321936Shselasky	RDMA_CM_EVENT_UNREACHABLE,
59321936Shselasky	RDMA_CM_EVENT_REJECTED,
60321936Shselasky	RDMA_CM_EVENT_ESTABLISHED,
61321936Shselasky	RDMA_CM_EVENT_DISCONNECTED,
62321936Shselasky	RDMA_CM_EVENT_DEVICE_REMOVAL,
63321936Shselasky	RDMA_CM_EVENT_MULTICAST_JOIN,
64321936Shselasky	RDMA_CM_EVENT_MULTICAST_ERROR,
65321936Shselasky	RDMA_CM_EVENT_ADDR_CHANGE,
66321936Shselasky	RDMA_CM_EVENT_TIMEWAIT_EXIT
67321936Shselasky};
68321936Shselasky
69321936Shselaskyenum rdma_port_space {
70321936Shselasky	RDMA_PS_IPOIB = 0x0002,
71321936Shselasky	RDMA_PS_TCP   = 0x0106,
72321936Shselasky	RDMA_PS_UDP   = 0x0111,
73321936Shselasky	RDMA_PS_IB    = 0x013F,
74321936Shselasky};
75321936Shselasky
76321936Shselasky#define RDMA_IB_IP_PS_MASK   0xFFFFFFFFFFFF0000ULL
77321936Shselasky#define RDMA_IB_IP_PORT_MASK 0x000000000000FFFFULL
78321936Shselasky#define RDMA_IB_IP_PS_TCP    0x0000000001060000ULL
79321936Shselasky#define RDMA_IB_IP_PS_UDP    0x0000000001110000ULL
80321936Shselasky#define RDMA_IB_PS_IB        0x00000000013F0000ULL
81321936Shselasky
82321936Shselasky/*
83321936Shselasky * Global qkey value for UDP QPs and multicast groups created via the
84321936Shselasky * RDMA CM.
85321936Shselasky */
86321936Shselasky#define RDMA_UDP_QKEY 0x01234567
87321936Shselasky
88321936Shselaskystruct rdma_ib_addr {
89321936Shselasky	union ibv_gid	sgid;
90321936Shselasky	union ibv_gid	dgid;
91321936Shselasky	__be16		pkey;
92321936Shselasky};
93321936Shselasky
94321936Shselaskystruct rdma_addr {
95321936Shselasky	union {
96321936Shselasky		struct sockaddr		src_addr;
97321936Shselasky		struct sockaddr_in	src_sin;
98321936Shselasky		struct sockaddr_in6	src_sin6;
99321936Shselasky		struct sockaddr_storage src_storage;
100321936Shselasky	};
101321936Shselasky	union {
102321936Shselasky		struct sockaddr		dst_addr;
103321936Shselasky		struct sockaddr_in	dst_sin;
104321936Shselasky		struct sockaddr_in6	dst_sin6;
105321936Shselasky		struct sockaddr_storage dst_storage;
106321936Shselasky	};
107321936Shselasky	union {
108321936Shselasky		struct rdma_ib_addr	ibaddr;
109321936Shselasky	} addr;
110321936Shselasky};
111321936Shselasky
112321936Shselaskystruct rdma_route {
113321936Shselasky	struct rdma_addr	 addr;
114321936Shselasky	struct ibv_sa_path_rec	*path_rec;
115321936Shselasky	int			 num_paths;
116321936Shselasky};
117321936Shselasky
118321936Shselaskystruct rdma_event_channel {
119321936Shselasky	int			fd;
120321936Shselasky};
121321936Shselasky
122321936Shselaskystruct rdma_cm_id {
123321936Shselasky	struct ibv_context	*verbs;
124321936Shselasky	struct rdma_event_channel *channel;
125321936Shselasky	void			*context;
126321936Shselasky	struct ibv_qp		*qp;
127321936Shselasky	struct rdma_route	 route;
128321936Shselasky	enum rdma_port_space	 ps;
129321936Shselasky	uint8_t			 port_num;
130321936Shselasky	struct rdma_cm_event	*event;
131321936Shselasky	struct ibv_comp_channel *send_cq_channel;
132321936Shselasky	struct ibv_cq		*send_cq;
133321936Shselasky	struct ibv_comp_channel *recv_cq_channel;
134321936Shselasky	struct ibv_cq		*recv_cq;
135321936Shselasky	struct ibv_srq		*srq;
136321936Shselasky	struct ibv_pd		*pd;
137321936Shselasky	enum ibv_qp_type	qp_type;
138321936Shselasky};
139321936Shselasky
140321936Shselaskyenum {
141321936Shselasky	RDMA_MAX_RESP_RES = 0xFF,
142321936Shselasky	RDMA_MAX_INIT_DEPTH = 0xFF
143321936Shselasky};
144321936Shselasky
145321936Shselaskystruct rdma_conn_param {
146321936Shselasky	const void *private_data;
147321936Shselasky	uint8_t private_data_len;
148321936Shselasky	uint8_t responder_resources;
149321936Shselasky	uint8_t initiator_depth;
150321936Shselasky	uint8_t flow_control;
151321936Shselasky	uint8_t retry_count;		/* ignored when accepting */
152321936Shselasky	uint8_t rnr_retry_count;
153321936Shselasky	/* Fields below ignored if a QP is created on the rdma_cm_id. */
154321936Shselasky	uint8_t srq;
155321936Shselasky	uint32_t qp_num;
156321936Shselasky};
157321936Shselasky
158321936Shselaskystruct rdma_ud_param {
159321936Shselasky	const void *private_data;
160321936Shselasky	uint8_t private_data_len;
161321936Shselasky	struct ibv_ah_attr ah_attr;
162321936Shselasky	uint32_t qp_num;
163321936Shselasky	uint32_t qkey;
164321936Shselasky};
165321936Shselasky
166321936Shselaskystruct rdma_cm_event {
167321936Shselasky	struct rdma_cm_id	*id;
168321936Shselasky	struct rdma_cm_id	*listen_id;
169321936Shselasky	enum rdma_cm_event_type	 event;
170321936Shselasky	int			 status;
171321936Shselasky	union {
172321936Shselasky		struct rdma_conn_param conn;
173321936Shselasky		struct rdma_ud_param   ud;
174321936Shselasky	} param;
175321936Shselasky};
176321936Shselasky
177321936Shselasky#define RAI_PASSIVE		0x00000001
178321936Shselasky#define RAI_NUMERICHOST		0x00000002
179321936Shselasky#define RAI_NOROUTE		0x00000004
180321936Shselasky#define RAI_FAMILY		0x00000008
181321936Shselasky
182321936Shselaskystruct rdma_addrinfo {
183321936Shselasky	int			ai_flags;
184321936Shselasky	int			ai_family;
185321936Shselasky	int			ai_qp_type;
186321936Shselasky	int			ai_port_space;
187321936Shselasky	socklen_t		ai_src_len;
188321936Shselasky	socklen_t		ai_dst_len;
189321936Shselasky	struct sockaddr		*ai_src_addr;
190321936Shselasky	struct sockaddr		*ai_dst_addr;
191321936Shselasky	char			*ai_src_canonname;
192321936Shselasky	char			*ai_dst_canonname;
193321936Shselasky	size_t			ai_route_len;
194321936Shselasky	void			*ai_route;
195321936Shselasky	size_t			ai_connect_len;
196321936Shselasky	void			*ai_connect;
197321936Shselasky	struct rdma_addrinfo	*ai_next;
198321936Shselasky};
199321936Shselasky
200321936Shselasky/**
201321936Shselasky * rdma_create_event_channel - Open a channel used to report communication events.
202321936Shselasky * Description:
203321936Shselasky *   Asynchronous events are reported to users through event channels.  Each
204321936Shselasky *   event channel maps to a file descriptor.
205321936Shselasky * Notes:
206321936Shselasky *   All created event channels must be destroyed by calling
207321936Shselasky *   rdma_destroy_event_channel.  Users should call rdma_get_cm_event to
208321936Shselasky *   retrieve events on an event channel.
209321936Shselasky * See also:
210321936Shselasky *   rdma_get_cm_event, rdma_destroy_event_channel
211321936Shselasky */
212321936Shselaskystruct rdma_event_channel *rdma_create_event_channel(void);
213321936Shselasky
214321936Shselasky/**
215321936Shselasky * rdma_destroy_event_channel - Close an event communication channel.
216321936Shselasky * @channel: The communication channel to destroy.
217321936Shselasky * Description:
218321936Shselasky *   Release all resources associated with an event channel and closes the
219321936Shselasky *   associated file descriptor.
220321936Shselasky * Notes:
221321936Shselasky *   All rdma_cm_id's associated with the event channel must be destroyed,
222321936Shselasky *   and all returned events must be acked before calling this function.
223321936Shselasky * See also:
224321936Shselasky *  rdma_create_event_channel, rdma_get_cm_event, rdma_ack_cm_event
225321936Shselasky */
226321936Shselaskyvoid rdma_destroy_event_channel(struct rdma_event_channel *channel);
227321936Shselasky
228321936Shselasky/**
229321936Shselasky * rdma_create_id - Allocate a communication identifier.
230321936Shselasky * @channel: The communication channel that events associated with the
231321936Shselasky *   allocated rdma_cm_id will be reported on.
232321936Shselasky * @id: A reference where the allocated communication identifier will be
233321936Shselasky *   returned.
234321936Shselasky * @context: User specified context associated with the rdma_cm_id.
235321936Shselasky * @ps: RDMA port space.
236321936Shselasky * Description:
237321936Shselasky *   Creates an identifier that is used to track communication information.
238321936Shselasky * Notes:
239321936Shselasky *   Rdma_cm_id's are conceptually equivalent to a socket for RDMA
240321936Shselasky *   communication.  The difference is that RDMA communication requires
241321936Shselasky *   explicitly binding to a specified RDMA device before communication
242321936Shselasky *   can occur, and most operations are asynchronous in nature.  Communication
243321936Shselasky *   events on an rdma_cm_id are reported through the associated event
244321936Shselasky *   channel.  Users must release the rdma_cm_id by calling rdma_destroy_id.
245321936Shselasky * See also:
246321936Shselasky *   rdma_create_event_channel, rdma_destroy_id, rdma_get_devices,
247321936Shselasky *   rdma_bind_addr, rdma_resolve_addr, rdma_connect, rdma_listen,
248321936Shselasky */
249321936Shselaskyint rdma_create_id(struct rdma_event_channel *channel,
250321936Shselasky		   struct rdma_cm_id **id, void *context,
251321936Shselasky		   enum rdma_port_space ps);
252321936Shselasky
253321936Shselasky/**
254321936Shselasky * rdma_create_ep - Allocate a communication identifier and qp.
255321936Shselasky * @id: A reference where the allocated communication identifier will be
256321936Shselasky *   returned.
257321936Shselasky * @res: Result from rdma_getaddrinfo, which specifies the source and
258321936Shselasky *   destination addresses, plus optional routing and connection information.
259321936Shselasky * @pd: Optional protection domain.  This parameter is ignored if qp_init_attr
260321936Shselasky *   is NULL.
261321936Shselasky * @qp_init_attr: Optional attributes for a QP created on the rdma_cm_id.
262321936Shselasky * Description:
263321936Shselasky *   Create an identifier and option QP used for communication.
264321936Shselasky * Notes:
265321936Shselasky *   If qp_init_attr is provided, then a queue pair will be allocated and
266321936Shselasky *   associated with the rdma_cm_id.  If a pd is provided, the QP will be
267321936Shselasky *   created on that PD.  Otherwise, the QP will be allocated on a default
268321936Shselasky *   PD.
269321936Shselasky *   The rdma_cm_id will be set to use synchronous operations (connect,
270321936Shselasky *   listen, and get_request).  To convert to asynchronous operation, the
271321936Shselasky *   rdma_cm_id should be migrated to a user allocated event channel.
272321936Shselasky * See also:
273321936Shselasky *   rdma_create_id, rdma_create_qp, rdma_migrate_id, rdma_connect,
274321936Shselasky *   rdma_listen
275321936Shselasky */
276321936Shselaskyint rdma_create_ep(struct rdma_cm_id **id, struct rdma_addrinfo *res,
277321936Shselasky		   struct ibv_pd *pd, struct ibv_qp_init_attr *qp_init_attr);
278321936Shselasky
279321936Shselasky/**
280321936Shselasky * rdma_destroy_ep - Deallocates a communication identifier and qp.
281321936Shselasky * @id: The communication identifier to destroy.
282321936Shselasky * Description:
283321936Shselasky *   Destroys the specified rdma_cm_id and any associated QP created
284321936Shselasky *   on that id.
285321936Shselasky * See also:
286321936Shselasky *   rdma_create_ep
287321936Shselasky */
288321936Shselaskyvoid rdma_destroy_ep(struct rdma_cm_id *id);
289321936Shselasky
290321936Shselasky/**
291321936Shselasky * rdma_destroy_id - Release a communication identifier.
292321936Shselasky * @id: The communication identifier to destroy.
293321936Shselasky * Description:
294321936Shselasky *   Destroys the specified rdma_cm_id and cancels any outstanding
295321936Shselasky *   asynchronous operation.
296321936Shselasky * Notes:
297321936Shselasky *   Users must free any associated QP with the rdma_cm_id before
298321936Shselasky *   calling this routine and ack an related events.
299321936Shselasky * See also:
300321936Shselasky *   rdma_create_id, rdma_destroy_qp, rdma_ack_cm_event
301321936Shselasky */
302321936Shselaskyint rdma_destroy_id(struct rdma_cm_id *id);
303321936Shselasky
304321936Shselasky/**
305321936Shselasky * rdma_bind_addr - Bind an RDMA identifier to a source address.
306321936Shselasky * @id: RDMA identifier.
307321936Shselasky * @addr: Local address information.  Wildcard values are permitted.
308321936Shselasky * Description:
309321936Shselasky *   Associates a source address with an rdma_cm_id.  The address may be
310321936Shselasky *   wildcarded.  If binding to a specific local address, the rdma_cm_id
311321936Shselasky *   will also be bound to a local RDMA device.
312321936Shselasky * Notes:
313321936Shselasky *   Typically, this routine is called before calling rdma_listen to bind
314321936Shselasky *   to a specific port number, but it may also be called on the active side
315321936Shselasky *   of a connection before calling rdma_resolve_addr to bind to a specific
316321936Shselasky *   address.
317321936Shselasky * See also:
318321936Shselasky *   rdma_create_id, rdma_listen, rdma_resolve_addr, rdma_create_qp
319321936Shselasky */
320321936Shselaskyint rdma_bind_addr(struct rdma_cm_id *id, struct sockaddr *addr);
321321936Shselasky
322321936Shselasky/**
323321936Shselasky * rdma_resolve_addr - Resolve destination and optional source addresses.
324321936Shselasky * @id: RDMA identifier.
325321936Shselasky * @src_addr: Source address information.  This parameter may be NULL.
326321936Shselasky * @dst_addr: Destination address information.
327321936Shselasky * @timeout_ms: Time to wait for resolution to complete.
328321936Shselasky * Description:
329321936Shselasky *   Resolve destination and optional source addresses from IP addresses
330321936Shselasky *   to an RDMA address.  If successful, the specified rdma_cm_id will
331321936Shselasky *   be bound to a local device.
332321936Shselasky * Notes:
333321936Shselasky *   This call is used to map a given destination IP address to a usable RDMA
334321936Shselasky *   address.  If a source address is given, the rdma_cm_id is bound to that
335321936Shselasky *   address, the same as if rdma_bind_addr were called.  If no source
336321936Shselasky *   address is given, and the rdma_cm_id has not yet been bound to a device,
337321936Shselasky *   then the rdma_cm_id will be bound to a source address based on the
338321936Shselasky *   local routing tables.  After this call, the rdma_cm_id will be bound to
339321936Shselasky *   an RDMA device.  This call is typically made from the active side of a
340321936Shselasky *   connection before calling rdma_resolve_route and rdma_connect.
341321936Shselasky * See also:
342321936Shselasky *   rdma_create_id, rdma_resolve_route, rdma_connect, rdma_create_qp,
343321936Shselasky *   rdma_get_cm_event, rdma_bind_addr
344321936Shselasky */
345321936Shselaskyint rdma_resolve_addr(struct rdma_cm_id *id, struct sockaddr *src_addr,
346321936Shselasky		      struct sockaddr *dst_addr, int timeout_ms);
347321936Shselasky
348321936Shselasky/**
349321936Shselasky * rdma_resolve_route - Resolve the route information needed to establish a connection.
350321936Shselasky * @id: RDMA identifier.
351321936Shselasky * @timeout_ms: Time to wait for resolution to complete.
352321936Shselasky * Description:
353321936Shselasky *   Resolves an RDMA route to the destination address in order to establish
354321936Shselasky *   a connection.  The destination address must have already been resolved
355321936Shselasky *   by calling rdma_resolve_addr.
356321936Shselasky * Notes:
357321936Shselasky *   This is called on the client side of a connection after calling
358321936Shselasky *   rdma_resolve_addr, but before calling rdma_connect.
359321936Shselasky * See also:
360321936Shselasky *   rdma_resolve_addr, rdma_connect, rdma_get_cm_event
361321936Shselasky */
362321936Shselaskyint rdma_resolve_route(struct rdma_cm_id *id, int timeout_ms);
363321936Shselasky
364321936Shselasky/**
365321936Shselasky * rdma_create_qp - Allocate a QP.
366321936Shselasky * @id: RDMA identifier.
367321936Shselasky * @pd: Optional protection domain for the QP.
368321936Shselasky * @qp_init_attr: initial QP attributes.
369321936Shselasky * Description:
370321936Shselasky *  Allocate a QP associated with the specified rdma_cm_id and transition it
371321936Shselasky *  for sending and receiving.
372321936Shselasky * Notes:
373321936Shselasky *   The rdma_cm_id must be bound to a local RDMA device before calling this
374321936Shselasky *   function, and the protection domain must be for that same device.
375321936Shselasky *   QPs allocated to an rdma_cm_id are automatically transitioned by the
376321936Shselasky *   librdmacm through their states.  After being allocated, the QP will be
377321936Shselasky *   ready to handle posting of receives.  If the QP is unconnected, it will
378321936Shselasky *   be ready to post sends.
379321936Shselasky *   If pd is NULL, then the QP will be allocated using a default protection
380321936Shselasky *   domain associated with the underlying RDMA device.
381321936Shselasky * See also:
382321936Shselasky *   rdma_bind_addr, rdma_resolve_addr, rdma_destroy_qp, ibv_create_qp,
383321936Shselasky *   ibv_modify_qp
384321936Shselasky */
385321936Shselaskyint rdma_create_qp(struct rdma_cm_id *id, struct ibv_pd *pd,
386321936Shselasky		   struct ibv_qp_init_attr *qp_init_attr);
387321936Shselaskyint rdma_create_qp_ex(struct rdma_cm_id *id,
388321936Shselasky		      struct ibv_qp_init_attr_ex *qp_init_attr);
389321936Shselasky
390321936Shselasky/**
391321936Shselasky * rdma_destroy_qp - Deallocate a QP.
392321936Shselasky * @id: RDMA identifier.
393321936Shselasky * Description:
394321936Shselasky *   Destroy a QP allocated on the rdma_cm_id.
395321936Shselasky * Notes:
396321936Shselasky *   Users must destroy any QP associated with an rdma_cm_id before
397321936Shselasky *   destroying the ID.
398321936Shselasky * See also:
399321936Shselasky *   rdma_create_qp, rdma_destroy_id, ibv_destroy_qp
400321936Shselasky */
401321936Shselaskyvoid rdma_destroy_qp(struct rdma_cm_id *id);
402321936Shselasky
403321936Shselasky/**
404321936Shselasky * rdma_connect - Initiate an active connection request.
405321936Shselasky * @id: RDMA identifier.
406321936Shselasky * @conn_param: optional connection parameters.
407321936Shselasky * Description:
408321936Shselasky *   For a connected rdma_cm_id, this call initiates a connection request
409321936Shselasky *   to a remote destination.  For an unconnected rdma_cm_id, it initiates
410321936Shselasky *   a lookup of the remote QP providing the datagram service.
411321936Shselasky * Notes:
412321936Shselasky *   Users must have resolved a route to the destination address
413321936Shselasky *   by having called rdma_resolve_route before calling this routine.
414321936Shselasky *   A user may override the default connection parameters and exchange
415321936Shselasky *   private data as part of the connection by using the conn_param parameter.
416321936Shselasky * See also:
417321936Shselasky *   rdma_resolve_route, rdma_disconnect, rdma_listen, rdma_get_cm_event
418321936Shselasky */
419321936Shselaskyint rdma_connect(struct rdma_cm_id *id, struct rdma_conn_param *conn_param);
420321936Shselasky
421321936Shselasky/**
422321936Shselasky * rdma_listen - Listen for incoming connection requests.
423321936Shselasky * @id: RDMA identifier.
424321936Shselasky * @backlog: backlog of incoming connection requests.
425321936Shselasky * Description:
426321936Shselasky *   Initiates a listen for incoming connection requests or datagram service
427321936Shselasky *   lookup.  The listen will be restricted to the locally bound source
428321936Shselasky *   address.
429321936Shselasky * Notes:
430321936Shselasky *   Users must have bound the rdma_cm_id to a local address by calling
431321936Shselasky *   rdma_bind_addr before calling this routine.  If the rdma_cm_id is
432321936Shselasky *   bound to a specific IP address, the listen will be restricted to that
433321936Shselasky *   address and the associated RDMA device.  If the rdma_cm_id is bound
434321936Shselasky *   to an RDMA port number only, the listen will occur across all RDMA
435321936Shselasky *   devices.
436321936Shselasky * See also:
437321936Shselasky *   rdma_bind_addr, rdma_connect, rdma_accept, rdma_reject, rdma_get_cm_event
438321936Shselasky */
439321936Shselaskyint rdma_listen(struct rdma_cm_id *id, int backlog);
440321936Shselasky
441321936Shselasky/**
442321936Shselasky * rdma_get_request
443321936Shselasky */
444321936Shselaskyint rdma_get_request(struct rdma_cm_id *listen, struct rdma_cm_id **id);
445321936Shselasky
446321936Shselasky/**
447321936Shselasky * rdma_accept - Called to accept a connection request.
448321936Shselasky * @id: Connection identifier associated with the request.
449321936Shselasky * @conn_param: Optional information needed to establish the connection.
450321936Shselasky * Description:
451321936Shselasky *   Called from the listening side to accept a connection or datagram
452321936Shselasky *   service lookup request.
453321936Shselasky * Notes:
454321936Shselasky *   Unlike the socket accept routine, rdma_accept is not called on a
455321936Shselasky *   listening rdma_cm_id.  Instead, after calling rdma_listen, the user
456321936Shselasky *   waits for a connection request event to occur.  Connection request
457321936Shselasky *   events give the user a newly created rdma_cm_id, similar to a new
458321936Shselasky *   socket, but the rdma_cm_id is bound to a specific RDMA device.
459321936Shselasky *   rdma_accept is called on the new rdma_cm_id.
460321936Shselasky *   A user may override the default connection parameters and exchange
461321936Shselasky *   private data as part of the connection by using the conn_param parameter.
462321936Shselasky * See also:
463321936Shselasky *   rdma_listen, rdma_reject, rdma_get_cm_event
464321936Shselasky */
465321936Shselaskyint rdma_accept(struct rdma_cm_id *id, struct rdma_conn_param *conn_param);
466321936Shselasky
467321936Shselasky/**
468321936Shselasky * rdma_reject - Called to reject a connection request.
469321936Shselasky * @id: Connection identifier associated with the request.
470321936Shselasky * @private_data: Optional private data to send with the reject message.
471321936Shselasky * @private_data_len: Size of the private_data to send, in bytes.
472321936Shselasky * Description:
473321936Shselasky *   Called from the listening side to reject a connection or datagram
474321936Shselasky *   service lookup request.
475321936Shselasky * Notes:
476321936Shselasky *   After receiving a connection request event, a user may call rdma_reject
477321936Shselasky *   to reject the request.  If the underlying RDMA transport supports
478321936Shselasky *   private data in the reject message, the specified data will be passed to
479321936Shselasky *   the remote side.
480321936Shselasky * See also:
481321936Shselasky *   rdma_listen, rdma_accept, rdma_get_cm_event
482321936Shselasky */
483321936Shselaskyint rdma_reject(struct rdma_cm_id *id, const void *private_data,
484321936Shselasky		uint8_t private_data_len);
485321936Shselasky
486321936Shselasky/**
487321936Shselasky * rdma_notify - Notifies the librdmacm of an asynchronous event.
488321936Shselasky * @id: RDMA identifier.
489321936Shselasky * @event: Asynchronous event.
490321936Shselasky * Description:
491321936Shselasky *   Used to notify the librdmacm of asynchronous events that have occurred
492321936Shselasky *   on a QP associated with the rdma_cm_id.
493321936Shselasky * Notes:
494321936Shselasky *   Asynchronous events that occur on a QP are reported through the user's
495321936Shselasky *   device event handler.  This routine is used to notify the librdmacm of
496321936Shselasky *   communication events.  In most cases, use of this routine is not
497321936Shselasky *   necessary, however if connection establishment is done out of band
498321936Shselasky *   (such as done through Infiniband), it's possible to receive data on a
499321936Shselasky *   QP that is not yet considered connected.  This routine forces the
500321936Shselasky *   connection into an established state in this case in order to handle
501321936Shselasky *   the rare situation where the connection never forms on its own.
502321936Shselasky *   Events that should be reported to the CM are: IB_EVENT_COMM_EST.
503321936Shselasky * See also:
504321936Shselasky *   rdma_connect, rdma_accept, rdma_listen
505321936Shselasky */
506321936Shselaskyint rdma_notify(struct rdma_cm_id *id, enum ibv_event_type event);
507321936Shselasky
508321936Shselasky/**
509321936Shselasky * rdma_disconnect - This function disconnects a connection.
510321936Shselasky * @id: RDMA identifier.
511321936Shselasky * Description:
512321936Shselasky *   Disconnects a connection and transitions any associated QP to the
513321936Shselasky *   error state.
514321936Shselasky * See also:
515321936Shselasky *   rdma_connect, rdma_listen, rdma_accept
516321936Shselasky */
517321936Shselaskyint rdma_disconnect(struct rdma_cm_id *id);
518321936Shselasky
519321936Shselasky/**
520321936Shselasky * rdma_join_multicast - Joins a multicast group.
521321936Shselasky * @id: Communication identifier associated with the request.
522321936Shselasky * @addr: Multicast address identifying the group to join.
523321936Shselasky * @context: User-defined context associated with the join request.
524321936Shselasky * Description:
525321936Shselasky *   Joins a multicast group and attaches an associated QP to the group.
526321936Shselasky * Notes:
527321936Shselasky *   Before joining a multicast group, the rdma_cm_id must be bound to
528321936Shselasky *   an RDMA device by calling rdma_bind_addr or rdma_resolve_addr.  Use of
529321936Shselasky *   rdma_resolve_addr requires the local routing tables to resolve the
530321936Shselasky *   multicast address to an RDMA device.  The user must call
531321936Shselasky *   rdma_leave_multicast to leave the multicast group and release any
532321936Shselasky *   multicast resources.  The context is returned to the user through
533321936Shselasky *   the private_data field in the rdma_cm_event.
534321936Shselasky * See also:
535321936Shselasky *   rdma_leave_multicast, rdma_bind_addr, rdma_resolve_addr, rdma_create_qp
536321936Shselasky */
537321936Shselaskyint rdma_join_multicast(struct rdma_cm_id *id, struct sockaddr *addr,
538321936Shselasky			void *context);
539321936Shselasky
540321936Shselasky/**
541321936Shselasky * rdma_leave_multicast - Leaves a multicast group.
542321936Shselasky * @id: Communication identifier associated with the request.
543321936Shselasky * @addr: Multicast address identifying the group to leave.
544321936Shselasky * Description:
545321936Shselasky *   Leaves a multicast group and detaches an associated QP from the group.
546321936Shselasky * Notes:
547321936Shselasky *   Calling this function before a group has been fully joined results in
548321936Shselasky *   canceling the join operation.  Users should be aware that messages
549321936Shselasky *   received from the multicast group may stilled be queued for
550321936Shselasky *   completion processing immediately after leaving a multicast group.
551321936Shselasky *   Destroying an rdma_cm_id will automatically leave all multicast groups.
552321936Shselasky * See also:
553321936Shselasky *   rdma_join_multicast, rdma_destroy_qp
554321936Shselasky */
555321936Shselaskyint rdma_leave_multicast(struct rdma_cm_id *id, struct sockaddr *addr);
556321936Shselasky
557321936Shselasky/**
558321936Shselasky * rdma_get_cm_event - Retrieves the next pending communication event.
559321936Shselasky * @channel: Event channel to check for events.
560321936Shselasky * @event: Allocated information about the next communication event.
561321936Shselasky * Description:
562321936Shselasky *   Retrieves a communication event.  If no events are pending, by default,
563321936Shselasky *   the call will block until an event is received.
564321936Shselasky * Notes:
565321936Shselasky *   The default synchronous behavior of this routine can be changed by
566321936Shselasky *   modifying the file descriptor associated with the given channel.  All
567321936Shselasky *   events that are reported must be acknowledged by calling rdma_ack_cm_event.
568321936Shselasky *   Destruction of an rdma_cm_id will block until related events have been
569321936Shselasky *   acknowledged.
570321936Shselasky * See also:
571321936Shselasky *   rdma_ack_cm_event, rdma_create_event_channel, rdma_event_str
572321936Shselasky */
573321936Shselaskyint rdma_get_cm_event(struct rdma_event_channel *channel,
574321936Shselasky		      struct rdma_cm_event **event);
575321936Shselasky
576321936Shselasky/**
577321936Shselasky * rdma_ack_cm_event - Free a communication event.
578321936Shselasky * @event: Event to be released.
579321936Shselasky * Description:
580321936Shselasky *   All events which are allocated by rdma_get_cm_event must be released,
581321936Shselasky *   there should be a one-to-one correspondence between successful gets
582321936Shselasky *   and acks.
583321936Shselasky * See also:
584321936Shselasky *   rdma_get_cm_event, rdma_destroy_id
585321936Shselasky */
586321936Shselaskyint rdma_ack_cm_event(struct rdma_cm_event *event);
587321936Shselasky
588321936Shselasky__be16 rdma_get_src_port(struct rdma_cm_id *id);
589321936Shselasky__be16 rdma_get_dst_port(struct rdma_cm_id *id);
590321936Shselasky
591321936Shselaskystatic inline struct sockaddr *rdma_get_local_addr(struct rdma_cm_id *id)
592321936Shselasky{
593321936Shselasky	return &id->route.addr.src_addr;
594321936Shselasky}
595321936Shselasky
596321936Shselaskystatic inline struct sockaddr *rdma_get_peer_addr(struct rdma_cm_id *id)
597321936Shselasky{
598321936Shselasky	return &id->route.addr.dst_addr;
599321936Shselasky}
600321936Shselasky
601321936Shselasky/**
602321936Shselasky * rdma_get_devices - Get list of RDMA devices currently available.
603321936Shselasky * @num_devices: If non-NULL, set to the number of devices returned.
604321936Shselasky * Description:
605321936Shselasky *   Return a NULL-terminated array of opened RDMA devices.  Callers can use
606321936Shselasky *   this routine to allocate resources on specific RDMA devices that will be
607321936Shselasky *   shared across multiple rdma_cm_id's.
608321936Shselasky * Notes:
609321936Shselasky *   The returned array must be released by calling rdma_free_devices.  Devices
610321936Shselasky *   remain opened while the librdmacm is loaded.
611321936Shselasky * See also:
612321936Shselasky *   rdma_free_devices
613321936Shselasky */
614321936Shselaskystruct ibv_context **rdma_get_devices(int *num_devices);
615321936Shselasky
616321936Shselasky/**
617321936Shselasky * rdma_free_devices - Frees the list of devices returned by rdma_get_devices.
618321936Shselasky * @list: List of devices returned from rdma_get_devices.
619321936Shselasky * Description:
620321936Shselasky *   Frees the device array returned by rdma_get_devices.
621321936Shselasky * See also:
622321936Shselasky *   rdma_get_devices
623321936Shselasky */
624321936Shselaskyvoid rdma_free_devices(struct ibv_context **list);
625321936Shselasky
626321936Shselasky/**
627321936Shselasky * rdma_event_str - Returns a string representation of an rdma cm event.
628321936Shselasky * @event: Asynchronous event.
629321936Shselasky * Description:
630321936Shselasky *   Returns a string representation of an asynchronous event.
631321936Shselasky * See also:
632321936Shselasky *   rdma_get_cm_event
633321936Shselasky */
634321936Shselaskyconst char *rdma_event_str(enum rdma_cm_event_type event);
635321936Shselasky
636321936Shselasky/* Option levels */
637321936Shselaskyenum {
638321936Shselasky	RDMA_OPTION_ID		= 0,
639321936Shselasky	RDMA_OPTION_IB		= 1
640321936Shselasky};
641321936Shselasky
642321936Shselasky/* Option details */
643321936Shselaskyenum {
644321936Shselasky	RDMA_OPTION_ID_TOS	 = 0,	/* uint8_t: RFC 2474 */
645321936Shselasky	RDMA_OPTION_ID_REUSEADDR = 1,   /* int: ~SO_REUSEADDR */
646321936Shselasky	RDMA_OPTION_ID_AFONLY	 = 2,   /* int: ~IPV6_V6ONLY */
647321936Shselasky	RDMA_OPTION_IB_PATH	 = 1	/* struct ibv_path_data[] */
648321936Shselasky};
649321936Shselasky
650321936Shselasky/**
651321936Shselasky * rdma_set_option - Set options for an rdma_cm_id.
652321936Shselasky * @id: Communication identifier to set option for.
653321936Shselasky * @level: Protocol level of the option to set.
654321936Shselasky * @optname: Name of the option to set.
655321936Shselasky * @optval: Reference to the option data.
656321936Shselasky * @optlen: The size of the %optval buffer.
657321936Shselasky */
658321936Shselaskyint rdma_set_option(struct rdma_cm_id *id, int level, int optname,
659321936Shselasky		    void *optval, size_t optlen);
660321936Shselasky
661321936Shselasky/**
662321936Shselasky * rdma_migrate_id - Move an rdma_cm_id to a new event channel.
663321936Shselasky * @id: Communication identifier to migrate.
664321936Shselasky * @channel: New event channel for rdma_cm_id events.
665321936Shselasky */
666321936Shselaskyint rdma_migrate_id(struct rdma_cm_id *id, struct rdma_event_channel *channel);
667321936Shselasky
668321936Shselasky/**
669321936Shselasky * rdma_getaddrinfo - RDMA address and route resolution service.
670321936Shselasky */
671321936Shselaskyint rdma_getaddrinfo(const char *node, const char *service,
672321936Shselasky		     const struct rdma_addrinfo *hints,
673321936Shselasky		     struct rdma_addrinfo **res);
674321936Shselasky
675321936Shselaskyvoid rdma_freeaddrinfo(struct rdma_addrinfo *res);
676321936Shselasky
677321936Shselasky#ifdef __cplusplus
678321936Shselasky}
679321936Shselasky#endif
680321936Shselasky
681321936Shselasky#endif /* RDMA_CMA_H */
682