1/*
2 * Copyright (c) 2004-2006 Intel Corporation.  All rights reserved.
3 * Copyright (c) 2004 Topspin Corporation.  All rights reserved.
4 * Copyright (c) 2004 Voltaire Corporation.  All rights reserved.
5 *
6 * This software is available to you under a choice of one of two
7 * licenses.  You may choose to be licensed under the terms of the GNU
8 * General Public License (GPL) Version 2, available from the file
9 * COPYING in the main directory of this source tree, or the
10 * OpenIB.org BSD license below:
11 *
12 *     Redistribution and use in source and binary forms, with or
13 *     without modification, are permitted provided that the following
14 *     conditions are met:
15 *
16 *      - Redistributions of source code must retain the above
17 *        copyright notice, this list of conditions and the following
18 *        disclaimer.
19 *
20 *      - Redistributions in binary form must reproduce the above
21 *        copyright notice, this list of conditions and the following
22 *        disclaimer in the documentation and/or other materials
23 *        provided with the distribution.
24 *
25 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
26 * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
27 * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
28 * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
29 * BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
30 * ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
31 * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
32 * SOFTWARE.
33 *
34 * $Id$
35 */
36#if !defined(CM_H)
37#define CM_H
38
39#include <infiniband/verbs.h>
40#include <infiniband/sa.h>
41#include <infiniband/byteorder.h>
42
43#ifdef __cplusplus
44extern "C" {
45#endif
46
47enum ib_cm_event_type {
48	IB_CM_REQ_ERROR,
49	IB_CM_REQ_RECEIVED,
50	IB_CM_REP_ERROR,
51	IB_CM_REP_RECEIVED,
52	IB_CM_RTU_RECEIVED,
53	IB_CM_USER_ESTABLISHED,
54	IB_CM_DREQ_ERROR,
55	IB_CM_DREQ_RECEIVED,
56	IB_CM_DREP_RECEIVED,
57	IB_CM_TIMEWAIT_EXIT,
58	IB_CM_MRA_RECEIVED,
59	IB_CM_REJ_RECEIVED,
60	IB_CM_LAP_ERROR,
61	IB_CM_LAP_RECEIVED,
62	IB_CM_APR_RECEIVED,
63	IB_CM_SIDR_REQ_ERROR,
64	IB_CM_SIDR_REQ_RECEIVED,
65	IB_CM_SIDR_REP_RECEIVED
66};
67
68enum ib_cm_data_size {
69	IB_CM_REQ_PRIVATE_DATA_SIZE	 = 92,
70	IB_CM_MRA_PRIVATE_DATA_SIZE	 = 222,
71	IB_CM_REJ_PRIVATE_DATA_SIZE	 = 148,
72	IB_CM_REP_PRIVATE_DATA_SIZE	 = 196,
73	IB_CM_RTU_PRIVATE_DATA_SIZE	 = 224,
74	IB_CM_DREQ_PRIVATE_DATA_SIZE	 = 220,
75	IB_CM_DREP_PRIVATE_DATA_SIZE	 = 224,
76	IB_CM_REJ_ARI_LENGTH		 = 72,
77	IB_CM_LAP_PRIVATE_DATA_SIZE	 = 168,
78	IB_CM_APR_PRIVATE_DATA_SIZE	 = 148,
79	IB_CM_APR_INFO_LENGTH		 = 72,
80	IB_CM_SIDR_REQ_PRIVATE_DATA_SIZE = 216,
81	IB_CM_SIDR_REP_PRIVATE_DATA_SIZE = 136,
82	IB_CM_SIDR_REP_INFO_LENGTH	 = 72
83};
84
85struct ib_cm_device {
86	struct ibv_context	*device_context;
87	int			fd;
88};
89
90struct ib_cm_id {
91	void			*context;
92	struct ib_cm_device	*device;
93	uint32_t		handle;
94};
95
96struct ib_cm_req_event_param {
97	struct ib_cm_id		*listen_id;
98	uint8_t			port;
99
100	struct ibv_sa_path_rec	*primary_path;
101	struct ibv_sa_path_rec	*alternate_path;
102
103	uint64_t		remote_ca_guid; /* netork-byte order */
104	uint32_t		remote_qkey;
105	uint32_t		remote_qpn;
106	enum ibv_qp_type	qp_type;
107
108	uint32_t		starting_psn;
109	uint8_t			responder_resources;
110	uint8_t			initiator_depth;
111	unsigned int		local_cm_response_timeout:5;
112	unsigned int		flow_control:1;
113	unsigned int		remote_cm_response_timeout:5;
114	unsigned int		retry_count:3;
115	unsigned int		rnr_retry_count:3;
116	unsigned int		srq:1;
117};
118
119struct ib_cm_rep_event_param {
120	uint64_t		remote_ca_guid; /* network-byte order */
121	uint32_t		remote_qkey;
122	uint32_t		remote_qpn;
123	uint32_t		starting_psn;
124	uint8_t			responder_resources;
125	uint8_t			initiator_depth;
126	unsigned int		target_ack_delay:5;
127	unsigned int		failover_accepted:2;
128	unsigned int		flow_control:1;
129	unsigned int		rnr_retry_count:3;
130	unsigned int		srq:1;
131};
132
133enum ib_cm_rej_reason {
134	IB_CM_REJ_NO_QP				= 1,
135	IB_CM_REJ_NO_EEC			= 2,
136	IB_CM_REJ_NO_RESOURCES			= 3,
137	IB_CM_REJ_TIMEOUT			= 4,
138	IB_CM_REJ_UNSUPPORTED			= 5,
139	IB_CM_REJ_INVALID_COMM_ID		= 6,
140	IB_CM_REJ_INVALID_COMM_INSTANCE		= 7,
141	IB_CM_REJ_INVALID_SERVICE_ID		= 8,
142	IB_CM_REJ_INVALID_TRANSPORT_TYPE	= 9,
143	IB_CM_REJ_STALE_CONN			= 10,
144	IB_CM_REJ_RDC_NOT_EXIST			= 11,
145	IB_CM_REJ_INVALID_GID			= 12,
146	IB_CM_REJ_INVALID_LID			= 13,
147	IB_CM_REJ_INVALID_SL			= 14,
148	IB_CM_REJ_INVALID_TRAFFIC_CLASS		= 15,
149	IB_CM_REJ_INVALID_HOP_LIMIT		= 16,
150	IB_CM_REJ_INVALID_PACKET_RATE		= 17,
151	IB_CM_REJ_INVALID_ALT_GID		= 18,
152	IB_CM_REJ_INVALID_ALT_LID		= 19,
153	IB_CM_REJ_INVALID_ALT_SL		= 20,
154	IB_CM_REJ_INVALID_ALT_TRAFFIC_CLASS	= 21,
155	IB_CM_REJ_INVALID_ALT_HOP_LIMIT		= 22,
156	IB_CM_REJ_INVALID_ALT_PACKET_RATE	= 23,
157	IB_CM_REJ_PORT_CM_REDIRECT		= 24,
158	IB_CM_REJ_PORT_REDIRECT			= 25,
159	IB_CM_REJ_INVALID_MTU			= 26,
160	IB_CM_REJ_INSUFFICIENT_RESP_RESOURCES	= 27,
161	IB_CM_REJ_CONSUMER_DEFINED		= 28,
162	IB_CM_REJ_INVALID_RNR_RETRY		= 29,
163	IB_CM_REJ_DUPLICATE_LOCAL_COMM_ID	= 30,
164	IB_CM_REJ_INVALID_CLASS_VERSION		= 31,
165	IB_CM_REJ_INVALID_FLOW_LABEL		= 32,
166	IB_CM_REJ_INVALID_ALT_FLOW_LABEL	= 33
167};
168
169struct ib_cm_rej_event_param {
170	enum ib_cm_rej_reason	reason;
171	void			*ari;
172	uint8_t			ari_length;
173};
174
175struct ib_cm_mra_event_param {
176	uint8_t	service_timeout;
177};
178
179struct ib_cm_lap_event_param {
180	struct ibv_sa_path_rec	*alternate_path;
181};
182
183enum ib_cm_apr_status {
184	IB_CM_APR_SUCCESS,
185	IB_CM_APR_INVALID_COMM_ID,
186	IB_CM_APR_UNSUPPORTED,
187	IB_CM_APR_REJECT,
188	IB_CM_APR_REDIRECT,
189	IB_CM_APR_IS_CURRENT,
190	IB_CM_APR_INVALID_QPN_EECN,
191	IB_CM_APR_INVALID_LID,
192	IB_CM_APR_INVALID_GID,
193	IB_CM_APR_INVALID_FLOW_LABEL,
194	IB_CM_APR_INVALID_TCLASS,
195	IB_CM_APR_INVALID_HOP_LIMIT,
196	IB_CM_APR_INVALID_PACKET_RATE,
197	IB_CM_APR_INVALID_SL
198};
199
200struct ib_cm_apr_event_param {
201	enum ib_cm_apr_status	ap_status;
202	void			*apr_info;
203	uint8_t			info_len;
204};
205
206struct ib_cm_sidr_req_event_param {
207	struct ib_cm_id	 *listen_id;
208	uint8_t		  port;
209	uint16_t          pkey;
210};
211
212enum ib_cm_sidr_status {
213	IB_SIDR_SUCCESS,
214	IB_SIDR_UNSUPPORTED,
215	IB_SIDR_REJECT,
216	IB_SIDR_NO_QP,
217	IB_SIDR_REDIRECT,
218	IB_SIDR_UNSUPPORTED_VERSION
219};
220
221struct ib_cm_sidr_rep_event_param {
222	enum ib_cm_sidr_status	status;
223	uint32_t		qkey;
224	uint32_t		qpn;
225	void			*info;
226	uint8_t			info_len;
227};
228
229struct ib_cm_event {
230	struct ib_cm_id	      *cm_id;
231	enum ib_cm_event_type event;
232	union {
233		struct ib_cm_req_event_param	req_rcvd;
234		struct ib_cm_rep_event_param	rep_rcvd;
235		/* No data for RTU received events. */
236		struct ib_cm_rej_event_param	rej_rcvd;
237		struct ib_cm_mra_event_param	mra_rcvd;
238		struct ib_cm_lap_event_param	lap_rcvd;
239		struct ib_cm_apr_event_param	apr_rcvd;
240		/* No data for DREQ/DREP received events. */
241		struct ib_cm_sidr_req_event_param sidr_req_rcvd;
242		struct ib_cm_sidr_rep_event_param sidr_rep_rcvd;
243		enum ibv_wc_status		send_status;
244	} param;
245
246	void			*private_data;
247};
248
249/**
250 * ib_cm_get_event - Retrieves the next pending communications event,
251 *   if no event is pending waits for an event.
252 * @device: CM device to retrieve the event.
253 * @event: Allocated information about the next communication event.
254 *    Event should be freed using ib_cm_ack_event()
255 *
256 * IB_CM_REQ_RECEIVED and IB_CM_SIDR_REQ_RECEIVED communication events
257 * generated as a result of listen requests result in the allocation of a
258 * new @cm_id.
259 * Clients are responsible for destroying the new @cm_id.  For peer-to-peer
260 * IB_CM_REQ_RECEIVED and all other events, the returned @cm_id corresponds
261 * to a user's existing communication identifier.
262 */
263int ib_cm_get_event(struct ib_cm_device *device, struct ib_cm_event **event);
264
265/**
266 * ib_cm_ack_event - Free a communications event.
267 * @event: Event to be released.
268 *
269 * All events which are allocated by ib_cm_get_event() must be released,
270 * there should be a one-to-one correspondence between successful gets
271 * and puts.
272 */
273int ib_cm_ack_event(struct ib_cm_event *event);
274
275/**
276 * ib_cm_open_device - Returns the device the CM uses to submit requests
277 *   and retrieve events, corresponding to the specified verbs device.
278 *
279 * The CM device contains the file descriptor that the CM uses to
280 * communicate with the kernel CM component.  The primary use of the
281 * file descriptor is to test for CM readiness events. When the CM
282 * becomes ready to READ there is a pending event ready, and a subsequent
283 * call to ib_cm_get_event will not block.
284 * Note: The user should not read or write directly to the CM file
285 *       descriptor, it will likely result in an error or unexpected
286 *       results.
287 */
288struct ib_cm_device* ib_cm_open_device(struct ibv_context *device_context);
289
290/**
291 * ib_cm_close_device - Close a CM device.
292 * @device: Device to close.
293 */
294void ib_cm_close_device(struct ib_cm_device *device);
295
296/**
297 * ib_cm_create_id - Allocate a communication identifier.
298 *
299 * Communication identifiers are used to track connection states, service
300 * ID resolution requests, and listen requests.
301 */
302int ib_cm_create_id(struct ib_cm_device *device,
303		    struct ib_cm_id **cm_id, void *context);
304
305/**
306 * ib_cm_destroy_id - Destroy a connection identifier.
307 * @cm_id: Connection identifier to destroy.
308 */
309int ib_cm_destroy_id(struct ib_cm_id *cm_id);
310
311struct ib_cm_attr_param {
312	uint64_t		service_id;   /* network-byte order */
313	uint64_t		service_mask; /* network-byte order */
314	uint32_t		local_id;
315	uint32_t		remote_id;
316};
317
318/**
319 * ib_cm_attr_id - Get connection identifier attributes.
320 * @cm_id: Connection identifier to retrieve attributes.
321 * @param: Destination of retreived parameters.
322 *
323 * Not all parameters are valid during all connection states.
324 */
325int ib_cm_attr_id(struct ib_cm_id *cm_id,
326		  struct ib_cm_attr_param *param);
327
328#define IB_CM_ASSIGN_SERVICE_ID_MASK __constant_cpu_to_be64(0xFF00000000000000ULL)
329#define IB_CM_ASSIGN_SERVICE_ID      __constant_cpu_to_be64(0x0200000000000000ULL)
330
331/**
332 * ib_cm_listen - Initiates listening on the specified service ID for
333 *   connection and service ID resolution requests.
334 * @cm_id: Connection identifier associated with the listen request.
335 * @service_id: Service identifier matched against incoming connection
336 *   and service ID resolution requests.  The service ID should be specified
337 *   network-byte order.
338 * @service_mask: Mask applied to service ID used to listen across a
339 *   range of service IDs.  If set to 0, the service ID is matched
340 *   exactly.
341 */
342int ib_cm_listen(struct ib_cm_id *cm_id,
343		 uint64_t service_id,
344		 uint64_t service_mask);
345
346struct ib_cm_req_param {
347	struct ibv_sa_path_rec	*primary_path;
348	struct ibv_sa_path_rec	*alternate_path;
349	uint64_t		service_id; /* network-byte order */
350	uint32_t		qp_num;
351	enum ibv_qp_type	qp_type;
352	uint32_t		starting_psn;
353	void			*private_data;
354	uint8_t			private_data_len;
355	uint8_t			peer_to_peer;
356	uint8_t			responder_resources;
357	uint8_t			initiator_depth;
358	uint8_t			remote_cm_response_timeout;
359	uint8_t			flow_control;
360	uint8_t			local_cm_response_timeout;
361	uint8_t			retry_count;
362	uint8_t			rnr_retry_count;
363	uint8_t			max_cm_retries;
364	uint8_t			srq;
365};
366
367/**
368 * ib_cm_send_req - Sends a connection request to the remote node.
369 * @cm_id: Connection identifier that will be associated with the
370 *   connection request.
371 * @param: Connection request information needed to establish the
372 *   connection.
373 */
374int ib_cm_send_req(struct ib_cm_id *cm_id,
375		   struct ib_cm_req_param *param);
376
377struct ib_cm_rep_param {
378	uint32_t	qp_num;
379	uint32_t	starting_psn;
380	void		*private_data;
381	uint8_t		private_data_len;
382	uint8_t		responder_resources;
383	uint8_t		initiator_depth;
384	uint8_t		target_ack_delay;
385	uint8_t		failover_accepted;
386	uint8_t		flow_control;
387	uint8_t		rnr_retry_count;
388	uint8_t		srq;
389};
390
391/**
392 * ib_cm_send_rep - Sends a connection reply in response to a connection
393 *   request.
394 * @cm_id: Connection identifier that will be associated with the
395 *   connection request.
396 * @param: Connection reply information needed to establish the
397 *   connection.
398 */
399int ib_cm_send_rep(struct ib_cm_id *cm_id,
400		   struct ib_cm_rep_param *param);
401
402/**
403 * ib_cm_send_rtu - Sends a connection ready to use message in response
404 *   to a connection reply message.
405 * @cm_id: Connection identifier associated with the connection request.
406 * @private_data: Optional user-defined private data sent with the
407 *   ready to use message.
408 * @private_data_len: Size of the private data buffer, in bytes.
409 */
410int ib_cm_send_rtu(struct ib_cm_id *cm_id,
411		   void *private_data,
412		   uint8_t private_data_len);
413
414/**
415 * ib_cm_send_dreq - Sends a disconnection request for an existing
416 *   connection.
417 * @cm_id: Connection identifier associated with the connection being
418 *   released.
419 * @private_data: Optional user-defined private data sent with the
420 *   disconnection request message.
421 * @private_data_len: Size of the private data buffer, in bytes.
422 */
423int ib_cm_send_dreq(struct ib_cm_id *cm_id,
424		    void *private_data,
425		    uint8_t private_data_len);
426
427/**
428 * ib_cm_send_drep - Sends a disconnection reply to a disconnection request.
429 * @cm_id: Connection identifier associated with the connection being
430 *   released.
431 * @private_data: Optional user-defined private data sent with the
432 *   disconnection reply message.
433 * @private_data_len: Size of the private data buffer, in bytes.
434 */
435int ib_cm_send_drep(struct ib_cm_id *cm_id,
436		    void *private_data,
437		    uint8_t private_data_len);
438
439/**
440 * ib_cm_notify - Notifies the CM of an event reported to the consumer.
441 * @cm_id: Connection identifier to transition to established.
442 * @event: Type of event.
443 *
444 * This routine should be invoked by users to notify the CM of relevant
445 * communication events.  Events that should be reported to the CM and
446 * when to report them are:
447 *
448 * IBV_EVENT_COMM_EST - Used when a message is received on a connected
449 *    QP before an RTU has been received.
450 * IBV_EVENT_PATH_MIG - Notifies the CM that the connection has failed over
451 *   to the alternate path.
452 */
453int ib_cm_notify(struct ib_cm_id *cm_id, enum ibv_event_type event);
454
455/**
456 * ib_cm_send_rej - Sends a connection rejection message to the
457 *   remote node.
458 * @cm_id: Connection identifier associated with the connection being
459 *   rejected.
460 * @reason: Reason for the connection request rejection.
461 * @ari: Optional additional rejection information.
462 * @ari_length: Size of the additional rejection information, in bytes.
463 * @private_data: Optional user-defined private data sent with the
464 *   rejection message.
465 * @private_data_len: Size of the private data buffer, in bytes.
466 */
467int ib_cm_send_rej(struct ib_cm_id *cm_id,
468		   enum ib_cm_rej_reason reason,
469		   void *ari,
470		   uint8_t ari_length,
471		   void *private_data,
472		   uint8_t private_data_len);
473
474/**
475 * ib_cm_send_mra - Sends a message receipt acknowledgement to a connection
476 *   message.
477 * @cm_id: Connection identifier associated with the connection message.
478 * @service_timeout: The maximum time required for the sender to reply to
479 *   to the connection message.
480 * @private_data: Optional user-defined private data sent with the
481 *   message receipt acknowledgement.
482 * @private_data_len: Size of the private data buffer, in bytes.
483 */
484int ib_cm_send_mra(struct ib_cm_id *cm_id,
485		   uint8_t service_timeout,
486		   void *private_data,
487		   uint8_t private_data_len);
488
489/**
490 * ib_cm_send_lap - Sends a load alternate path request.
491 * @cm_id: Connection identifier associated with the load alternate path
492 *   message.
493 * @alternate_path: A path record that identifies the alternate path to
494 *   load.
495 * @private_data: Optional user-defined private data sent with the
496 *   load alternate path message.
497 * @private_data_len: Size of the private data buffer, in bytes.
498 */
499int ib_cm_send_lap(struct ib_cm_id *cm_id,
500		   struct ibv_sa_path_rec *alternate_path,
501		   void *private_data,
502		   uint8_t private_data_len);
503
504/**
505 * ib_cm_init_qp_attr - Initializes the QP attributes for use in transitioning
506 *   to a specified QP state.
507 * @cm_id: Communication identifier associated with the QP attributes to
508 *   initialize.
509 * @qp_attr: On input, specifies the desired QP state.  On output, the
510 *   mandatory and desired optional attributes will be set in order to
511 *   modify the QP to the specified state.
512 * @qp_attr_mask: The QP attribute mask that may be used to transition the
513 *   QP to the specified state.
514 *
515 * Users must set the @qp_attr->qp_state to the desired QP state.  This call
516 * will set all required attributes for the given transition, along with
517 * known optional attributes.  Users may override the attributes returned from
518 * this call before calling ib_modify_qp.
519 */
520int ib_cm_init_qp_attr(struct ib_cm_id *cm_id,
521		       struct ibv_qp_attr *qp_attr,
522		       int *qp_attr_mask);
523
524/**
525 * ib_cm_send_apr - Sends an alternate path response message in response to
526 *   a load alternate path request.
527 * @cm_id: Connection identifier associated with the alternate path response.
528 * @status: Reply status sent with the alternate path response.
529 * @info: Optional additional information sent with the alternate path
530 *   response.
531 * @info_length: Size of the additional information, in bytes.
532 * @private_data: Optional user-defined private data sent with the
533 *   alternate path response message.
534 * @private_data_len: Size of the private data buffer, in bytes.
535 */
536int ib_cm_send_apr(struct ib_cm_id *cm_id,
537		   enum ib_cm_apr_status status,
538		   void *info,
539		   uint8_t info_length,
540		   void *private_data,
541		   uint8_t private_data_len);
542
543struct ib_cm_sidr_req_param {
544	struct ibv_sa_path_rec	*path;
545	uint64_t		service_id; /* network-byte order */
546	int			timeout_ms;
547	void			*private_data;
548	uint8_t			private_data_len;
549	uint8_t			max_cm_retries;
550};
551
552/**
553 * ib_cm_send_sidr_req - Sends a service ID resolution request to the
554 *   remote node.
555 * @cm_id: Communication identifier that will be associated with the
556 *   service ID resolution request.
557 * @param: Service ID resolution request information.
558 */
559int ib_cm_send_sidr_req(struct ib_cm_id *cm_id,
560			struct ib_cm_sidr_req_param *param);
561
562struct ib_cm_sidr_rep_param {
563	uint32_t		qp_num;
564	uint32_t		qkey;
565	enum ib_cm_sidr_status	status;
566	void			*info;
567	uint8_t			info_length;
568	void			*private_data;
569	uint8_t			private_data_len;
570};
571
572/**
573 * ib_cm_send_sidr_rep - Sends a service ID resolution reply to the
574 *   remote node.
575 * @cm_id: Communication identifier associated with the received service ID
576 *   resolution request.
577 * @param: Service ID resolution reply information.
578 */
579int ib_cm_send_sidr_rep(struct ib_cm_id *cm_id,
580			struct ib_cm_sidr_rep_param *param);
581
582#ifdef __cplusplus
583}
584#endif
585
586#endif /* CM_H */
587