112198SEiji.Ota@Sun.COM /*
212198SEiji.Ota@Sun.COM * CDDL HEADER START
312198SEiji.Ota@Sun.COM *
412198SEiji.Ota@Sun.COM * The contents of this file are subject to the terms of the
512198SEiji.Ota@Sun.COM * Common Development and Distribution License (the "License").
612198SEiji.Ota@Sun.COM * You may not use this file except in compliance with the License.
712198SEiji.Ota@Sun.COM *
812198SEiji.Ota@Sun.COM * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
912198SEiji.Ota@Sun.COM * or http://www.opensolaris.org/os/licensing.
1012198SEiji.Ota@Sun.COM * See the License for the specific language governing permissions
1112198SEiji.Ota@Sun.COM * and limitations under the License.
1212198SEiji.Ota@Sun.COM *
1312198SEiji.Ota@Sun.COM * When distributing Covered Code, include this CDDL HEADER in each
1412198SEiji.Ota@Sun.COM * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
1512198SEiji.Ota@Sun.COM * If applicable, add the following below this CDDL HEADER, with the
1612198SEiji.Ota@Sun.COM * fields enclosed by brackets "[]" replaced with your own identifying
1712198SEiji.Ota@Sun.COM * information: Portions Copyright [yyyy] [name of copyright owner]
1812198SEiji.Ota@Sun.COM *
1912198SEiji.Ota@Sun.COM * CDDL HEADER END
2012198SEiji.Ota@Sun.COM */
2112198SEiji.Ota@Sun.COM /*
2212198SEiji.Ota@Sun.COM * Copyright (c) 2010, Oracle and/or its affiliates. All rights reserved.
2312198SEiji.Ota@Sun.COM */
2412198SEiji.Ota@Sun.COM
2512198SEiji.Ota@Sun.COM #ifndef _RDSV3_IMPL_H
2612198SEiji.Ota@Sun.COM #define _RDSV3_IMPL_H
2712198SEiji.Ota@Sun.COM
2812198SEiji.Ota@Sun.COM #include <sys/atomic.h>
2912198SEiji.Ota@Sun.COM
3012198SEiji.Ota@Sun.COM /*
3112198SEiji.Ota@Sun.COM * This file is only present in Solaris
3212198SEiji.Ota@Sun.COM */
3312198SEiji.Ota@Sun.COM
3412198SEiji.Ota@Sun.COM #ifdef __cplusplus
3512198SEiji.Ota@Sun.COM extern "C" {
3612198SEiji.Ota@Sun.COM #endif
3712198SEiji.Ota@Sun.COM
3812198SEiji.Ota@Sun.COM extern dev_info_t *rdsv3_dev_info;
3912198SEiji.Ota@Sun.COM
4012198SEiji.Ota@Sun.COM #define uint16_be_t uint16_t
4112198SEiji.Ota@Sun.COM #define uint32_be_t uint32_t
4212198SEiji.Ota@Sun.COM #define uint64_be_t uint64_t
4312198SEiji.Ota@Sun.COM
4412198SEiji.Ota@Sun.COM /*
4512198SEiji.Ota@Sun.COM * RDS Well known service id
4612198SEiji.Ota@Sun.COM * Format: 0x1h00144Fhhhhhhhh
4712198SEiji.Ota@Sun.COM * "00144F" is the Sun OUI
4812198SEiji.Ota@Sun.COM * 'h' can be any hex-decimal digit.
4912198SEiji.Ota@Sun.COM */
5012198SEiji.Ota@Sun.COM #define RDS_SERVICE_ID 0x1000144F00000001ULL
5112198SEiji.Ota@Sun.COM
5212198SEiji.Ota@Sun.COM /*
5312198SEiji.Ota@Sun.COM * Atomic operations
5412198SEiji.Ota@Sun.COM */
5512198SEiji.Ota@Sun.COM typedef unsigned int atomic_t;
5612198SEiji.Ota@Sun.COM #define ATOMIC_INIT(a) a
5712198SEiji.Ota@Sun.COM
5812198SEiji.Ota@Sun.COM #define atomic_get(p) (*(p))
5912198SEiji.Ota@Sun.COM
6012198SEiji.Ota@Sun.COM #define atomic_cmpset_long(p, c, n) \
6112198SEiji.Ota@Sun.COM ((c == atomic_cas_uint(p, c, n)) ? c : -1)
6212198SEiji.Ota@Sun.COM
6312198SEiji.Ota@Sun.COM #define atomic_dec_and_test(a) \
6412198SEiji.Ota@Sun.COM (atomic_dec_uint_nv((a)) == 0)
6512198SEiji.Ota@Sun.COM
6612198SEiji.Ota@Sun.COM #define atomic_cmpxchg(a, o, n) \
6712198SEiji.Ota@Sun.COM atomic_cas_uint(a, o, n)
6812198SEiji.Ota@Sun.COM
6912198SEiji.Ota@Sun.COM #ifdef _LP64
7012198SEiji.Ota@Sun.COM #define set_bit(b, p) \
7112198SEiji.Ota@Sun.COM atomic_or_ulong(((volatile ulong_t *)(void *)(p)) + ((b) >> 6), \
7212198SEiji.Ota@Sun.COM 1ul << ((b) & 0x3f))
7312198SEiji.Ota@Sun.COM
7412198SEiji.Ota@Sun.COM #define clear_bit(b, p) \
7512198SEiji.Ota@Sun.COM atomic_and_ulong(((volatile ulong_t *)(void *)(p)) + ((b) >> 6), \
7612198SEiji.Ota@Sun.COM ~(1ul << ((b) & 0x3f)))
7712198SEiji.Ota@Sun.COM
7812198SEiji.Ota@Sun.COM #define test_bit(b, p) \
7912198SEiji.Ota@Sun.COM (((volatile ulong_t *)(void *)(p))[(b) >> 6] & (1ul << ((b) & 0x3f)))
8012198SEiji.Ota@Sun.COM
8112198SEiji.Ota@Sun.COM #define test_and_set_bit(b, p) \
8212198SEiji.Ota@Sun.COM atomic_set_long_excl(((ulong_t *)(void *)(p)) + \
8312198SEiji.Ota@Sun.COM ((b) >> 6), ((b) & 0x3f))
8412198SEiji.Ota@Sun.COM #define test_and_clear_bit(b, p) \
8512198SEiji.Ota@Sun.COM !atomic_clear_long_excl(((ulong_t *)(void *)(p)) + ((b) >> 6), \
8612198SEiji.Ota@Sun.COM ((b) & 0x3f))
8712198SEiji.Ota@Sun.COM #else
8812198SEiji.Ota@Sun.COM #define set_bit(b, p) \
8912198SEiji.Ota@Sun.COM atomic_or_uint(((volatile uint_t *)(void *)p) + (b >> 5), \
9012198SEiji.Ota@Sun.COM 1ul << (b & 0x1f))
9112198SEiji.Ota@Sun.COM
9212198SEiji.Ota@Sun.COM #define clear_bit(b, p) \
9312198SEiji.Ota@Sun.COM atomic_and_uint(((volatile uint_t *)(void *)p) + (b >> 5), \
9412198SEiji.Ota@Sun.COM ~(1ul << (b & 0x1f)))
9512198SEiji.Ota@Sun.COM
9612198SEiji.Ota@Sun.COM #define test_bit(b, p) \
9712198SEiji.Ota@Sun.COM (((volatile uint_t *)(void *)p)[b >> 5] & (1ul << (b & 0x1f)))
9812198SEiji.Ota@Sun.COM
9912198SEiji.Ota@Sun.COM #define test_and_set_bit(b, p) \
10012198SEiji.Ota@Sun.COM atomic_set_long_excl(((ulong_t *)(void *)p) + (b >> 5), (b & 0x1f))
10112198SEiji.Ota@Sun.COM #define test_and_clear_bit(b, p) \
10212198SEiji.Ota@Sun.COM !atomic_clear_long_excl(((ulong_t *)(void *)p) + (b >> 5), (b & 0x1f))
10312198SEiji.Ota@Sun.COM #endif
10412198SEiji.Ota@Sun.COM
105*12414SEiji.Ota@Sun.COM /*
106*12414SEiji.Ota@Sun.COM * These macros and/or constants are used instead of Linux
107*12414SEiji.Ota@Sun.COM * generic_{test,__{clear,set}}_le_bit().
108*12414SEiji.Ota@Sun.COM */
109*12414SEiji.Ota@Sun.COM #if defined(sparc)
110*12414SEiji.Ota@Sun.COM #define LE_BIT_XOR ((BITS_PER_LONG-1) & ~0x7)
111*12414SEiji.Ota@Sun.COM #else
112*12414SEiji.Ota@Sun.COM #define LE_BIT_XOR 0
113*12414SEiji.Ota@Sun.COM #endif
114*12414SEiji.Ota@Sun.COM
115*12414SEiji.Ota@Sun.COM #define set_le_bit(b, p) set_bit(b ^ LE_BIT_XOR, p)
116*12414SEiji.Ota@Sun.COM #define clear_le_bit(b, p) clear_bit(b ^ LE_BIT_XOR, p)
117*12414SEiji.Ota@Sun.COM #define test_le_bit(b, p) test_bit(b ^ LE_BIT_XOR, p)
11812198SEiji.Ota@Sun.COM
11912198SEiji.Ota@Sun.COM uint_t rdsv3_one_sec_in_hz;
12012198SEiji.Ota@Sun.COM
12112198SEiji.Ota@Sun.COM #define jiffies 100
12212198SEiji.Ota@Sun.COM #define HZ (drv_hztousec(1))
12312198SEiji.Ota@Sun.COM #define container_of(m, s, name) \
12412198SEiji.Ota@Sun.COM (void *)((uintptr_t)(m) - (uintptr_t)offsetof(s, name))
12512198SEiji.Ota@Sun.COM #define ARRAY_SIZE(x) (sizeof (x) / sizeof (x[0]))
12612198SEiji.Ota@Sun.COM /* setting this to PAGESIZE throws build errors */
12712198SEiji.Ota@Sun.COM #define PAGE_SIZE 4096 /* xxx - fix this */
12812198SEiji.Ota@Sun.COM #define BITS_PER_LONG (sizeof (unsigned long) * 8)
12912198SEiji.Ota@Sun.COM
13012198SEiji.Ota@Sun.COM /* debug */
13112198SEiji.Ota@Sun.COM #define RDSV3_PANIC() cmn_err(CE_PANIC, "Panic forced by RDSV3");
13212198SEiji.Ota@Sun.COM
13312198SEiji.Ota@Sun.COM /* ERR */
13412198SEiji.Ota@Sun.COM #define MAX_ERRNO 4095
13512198SEiji.Ota@Sun.COM #define ERR_PTR(x) ((void *)(uintptr_t)x)
13612198SEiji.Ota@Sun.COM #define IS_ERR(ptr) (((uintptr_t)ptr) >= (uintptr_t)-MAX_ERRNO)
13712198SEiji.Ota@Sun.COM #define PTR_ERR(ptr) (int)(uintptr_t)ptr
13812198SEiji.Ota@Sun.COM
13912198SEiji.Ota@Sun.COM #define MAX_SCHEDULE_TIMEOUT (~0UL>>1)
14012198SEiji.Ota@Sun.COM
14112198SEiji.Ota@Sun.COM #define RDMA_CM_EVENT_ADDR_CHANGE 14
14212198SEiji.Ota@Sun.COM
14312198SEiji.Ota@Sun.COM /* list */
14412198SEiji.Ota@Sun.COM /* copied and modified list_remove_node */
14512198SEiji.Ota@Sun.COM #define list_remove_node(node) \
14612198SEiji.Ota@Sun.COM if ((node)->list_next != NULL) { \
14712198SEiji.Ota@Sun.COM (node)->list_prev->list_next = (node)->list_next; \
14812198SEiji.Ota@Sun.COM (node)->list_next->list_prev = (node)->list_prev; \
14912198SEiji.Ota@Sun.COM (node)->list_next = (node)->list_prev = NULL; \
15012198SEiji.Ota@Sun.COM }
15112198SEiji.Ota@Sun.COM
15212198SEiji.Ota@Sun.COM #define list_splice(src, dst) { \
15312198SEiji.Ota@Sun.COM list_create(dst, (src)->list_size, (src)->list_offset); \
15412198SEiji.Ota@Sun.COM list_move_tail(dst, src); \
15512198SEiji.Ota@Sun.COM }
15612198SEiji.Ota@Sun.COM
15712198SEiji.Ota@Sun.COM #define RDSV3_FOR_EACH_LIST_NODE(objp, listp, member) \
15812198SEiji.Ota@Sun.COM for (objp = list_head(listp); objp; objp = list_next(listp, objp))
15912198SEiji.Ota@Sun.COM #define RDSV3_FOR_EACH_LIST_NODE_SAFE(objp, tmp, listp, member) \
16012198SEiji.Ota@Sun.COM for (objp = list_head(listp), tmp = (objp != NULL) ? \
16112198SEiji.Ota@Sun.COM list_next(listp, objp) : NULL; \
16212198SEiji.Ota@Sun.COM objp; \
16312198SEiji.Ota@Sun.COM objp = tmp, tmp = (objp != NULL) ? \
16412198SEiji.Ota@Sun.COM list_next(listp, objp) : NULL)
16512198SEiji.Ota@Sun.COM
16612198SEiji.Ota@Sun.COM /* simulate wait_queue_head_t */
16712198SEiji.Ota@Sun.COM typedef struct rdsv3_wait_queue_s {
16812198SEiji.Ota@Sun.COM kmutex_t waitq_mutex;
16912198SEiji.Ota@Sun.COM kcondvar_t waitq_cv;
17012320SGiri.Adari@Sun.COM uint_t waitq_waiters;
17112198SEiji.Ota@Sun.COM } rdsv3_wait_queue_t;
17212198SEiji.Ota@Sun.COM
17312198SEiji.Ota@Sun.COM #define rdsv3_init_waitqueue(waitqp) \
17412198SEiji.Ota@Sun.COM mutex_init(&(waitqp)->waitq_mutex, NULL, MUTEX_DRIVER, NULL); \
17512320SGiri.Adari@Sun.COM cv_init(&(waitqp)->waitq_cv, NULL, CV_DRIVER, NULL); \
17612320SGiri.Adari@Sun.COM (waitqp)->waitq_waiters = 0
17712198SEiji.Ota@Sun.COM
17812198SEiji.Ota@Sun.COM #define rdsv3_exit_waitqueue(waitqp) \
17912320SGiri.Adari@Sun.COM ASSERT((waitqp)->waitq_waiters == 0); \
18012198SEiji.Ota@Sun.COM mutex_destroy(&(waitqp)->waitq_mutex); \
18112198SEiji.Ota@Sun.COM cv_destroy(&(waitqp)->waitq_cv)
18212198SEiji.Ota@Sun.COM
18312198SEiji.Ota@Sun.COM #define rdsv3_wake_up(waitqp) { \
18412198SEiji.Ota@Sun.COM mutex_enter(&(waitqp)->waitq_mutex); \
18512320SGiri.Adari@Sun.COM if ((waitqp)->waitq_waiters) \
18612320SGiri.Adari@Sun.COM cv_signal(&(waitqp)->waitq_cv); \
18712198SEiji.Ota@Sun.COM mutex_exit(&(waitqp)->waitq_mutex); \
18812198SEiji.Ota@Sun.COM }
18912198SEiji.Ota@Sun.COM
19012198SEiji.Ota@Sun.COM #define rdsv3_wake_up_all(waitqp) { \
19112198SEiji.Ota@Sun.COM mutex_enter(&(waitqp)->waitq_mutex); \
19212320SGiri.Adari@Sun.COM if ((waitqp)->waitq_waiters) \
19312320SGiri.Adari@Sun.COM cv_broadcast(&(waitqp)->waitq_cv); \
19412198SEiji.Ota@Sun.COM mutex_exit(&(waitqp)->waitq_mutex); \
19512198SEiji.Ota@Sun.COM }
19612198SEiji.Ota@Sun.COM
19712320SGiri.Adari@Sun.COM /* analogous to cv_wait */
19812198SEiji.Ota@Sun.COM #define rdsv3_wait_event(waitq, condition) \
19912198SEiji.Ota@Sun.COM { \
20012320SGiri.Adari@Sun.COM mutex_enter(&(waitq)->waitq_mutex); \
20112320SGiri.Adari@Sun.COM (waitq)->waitq_waiters++; \
20212198SEiji.Ota@Sun.COM while (!(condition)) { \
20312320SGiri.Adari@Sun.COM cv_wait(&(waitq)->waitq_cv, &(waitq)->waitq_mutex); \
20412198SEiji.Ota@Sun.COM } \
20512320SGiri.Adari@Sun.COM (waitq)->waitq_waiters--; \
20612320SGiri.Adari@Sun.COM mutex_exit(&(waitq)->waitq_mutex); \
20712320SGiri.Adari@Sun.COM }
20812198SEiji.Ota@Sun.COM
20912320SGiri.Adari@Sun.COM /* analogous to cv_wait_sig */
21012320SGiri.Adari@Sun.COM #define rdsv3_wait_sig(waitqp, condition) \
21112198SEiji.Ota@Sun.COM ( \
21212198SEiji.Ota@Sun.COM { \
21312320SGiri.Adari@Sun.COM int cv_return = 1; \
21412320SGiri.Adari@Sun.COM mutex_enter(&(waitqp)->waitq_mutex); \
21512320SGiri.Adari@Sun.COM (waitqp)->waitq_waiters++; \
21612320SGiri.Adari@Sun.COM while (!(condition)) { \
21712320SGiri.Adari@Sun.COM cv_return = cv_wait_sig(&(waitqp)->waitq_cv, \
21812320SGiri.Adari@Sun.COM &(waitqp)->waitq_mutex); \
21912198SEiji.Ota@Sun.COM if (cv_return == 0) { \
22012198SEiji.Ota@Sun.COM break; \
22112198SEiji.Ota@Sun.COM } \
22212198SEiji.Ota@Sun.COM } \
22312320SGiri.Adari@Sun.COM (waitqp)->waitq_waiters--; \
22412320SGiri.Adari@Sun.COM mutex_exit(&(waitqp)->waitq_mutex); \
22512198SEiji.Ota@Sun.COM cv_return; \
22612198SEiji.Ota@Sun.COM } \
22712198SEiji.Ota@Sun.COM )
22812198SEiji.Ota@Sun.COM
22912198SEiji.Ota@Sun.COM #define SOCK_DEAD 1ul
23012198SEiji.Ota@Sun.COM
23112198SEiji.Ota@Sun.COM /* socket */
23212198SEiji.Ota@Sun.COM typedef struct rsock {
23312198SEiji.Ota@Sun.COM sock_upper_handle_t sk_upper_handle;
23412198SEiji.Ota@Sun.COM sock_upcalls_t *sk_upcalls;
23512198SEiji.Ota@Sun.COM
23612198SEiji.Ota@Sun.COM kmutex_t sk_lock;
23712198SEiji.Ota@Sun.COM ulong_t sk_flag;
23812320SGiri.Adari@Sun.COM rdsv3_wait_queue_t *sk_sleep; /* Also protected by rs_recv_lock */
23912198SEiji.Ota@Sun.COM int sk_sndbuf;
24012198SEiji.Ota@Sun.COM int sk_rcvbuf;
24112198SEiji.Ota@Sun.COM atomic_t sk_refcount;
24212198SEiji.Ota@Sun.COM
24312198SEiji.Ota@Sun.COM struct rdsv3_sock *sk_protinfo;
24412198SEiji.Ota@Sun.COM } rsock_t;
24512198SEiji.Ota@Sun.COM
24612198SEiji.Ota@Sun.COM typedef struct rdsv3_conn_info_s {
24712198SEiji.Ota@Sun.COM uint32_be_t c_laddr;
24812198SEiji.Ota@Sun.COM uint32_be_t c_faddr;
24912198SEiji.Ota@Sun.COM } rdsv3_conn_info_t;
25012198SEiji.Ota@Sun.COM
25112198SEiji.Ota@Sun.COM /* WQ */
25212198SEiji.Ota@Sun.COM typedef struct rdsv3_workqueue_struct_s {
25312198SEiji.Ota@Sun.COM kmutex_t wq_lock;
25412198SEiji.Ota@Sun.COM uint_t wq_state;
25512198SEiji.Ota@Sun.COM int wq_pending;
25612198SEiji.Ota@Sun.COM list_t wq_queue;
25712198SEiji.Ota@Sun.COM } rdsv3_workqueue_struct_t;
25812198SEiji.Ota@Sun.COM
25912198SEiji.Ota@Sun.COM struct rdsv3_work_s;
26012198SEiji.Ota@Sun.COM typedef void (*rdsv3_work_func_t)(struct rdsv3_work_s *);
26112198SEiji.Ota@Sun.COM typedef struct rdsv3_work_s {
26212198SEiji.Ota@Sun.COM list_node_t work_item;
26312198SEiji.Ota@Sun.COM rdsv3_work_func_t func;
26412198SEiji.Ota@Sun.COM } rdsv3_work_t;
26512198SEiji.Ota@Sun.COM
26612198SEiji.Ota@Sun.COM /* simulate delayed_work */
26712198SEiji.Ota@Sun.COM typedef struct rdsv3_delayed_work_s {
26812198SEiji.Ota@Sun.COM kmutex_t lock;
26912198SEiji.Ota@Sun.COM rdsv3_work_t work;
27012198SEiji.Ota@Sun.COM timeout_id_t timeid;
27112198SEiji.Ota@Sun.COM rdsv3_workqueue_struct_t *wq;
27212198SEiji.Ota@Sun.COM } rdsv3_delayed_work_t;
27312198SEiji.Ota@Sun.COM
27412198SEiji.Ota@Sun.COM #define RDSV3_INIT_WORK(wp, f) (wp)->func = f
27512198SEiji.Ota@Sun.COM #define RDSV3_INIT_DELAYED_WORK(dwp, f) \
27612198SEiji.Ota@Sun.COM (dwp)->work.func = f; \
27712198SEiji.Ota@Sun.COM mutex_init(&(dwp)->lock, NULL, MUTEX_DRIVER, NULL); \
27812198SEiji.Ota@Sun.COM (dwp)->timeid = 0
27912198SEiji.Ota@Sun.COM
28012198SEiji.Ota@Sun.COM /* simulate scatterlist */
28112198SEiji.Ota@Sun.COM struct rdsv3_scatterlist {
28212198SEiji.Ota@Sun.COM caddr_t vaddr;
28312198SEiji.Ota@Sun.COM uint_t length;
28412198SEiji.Ota@Sun.COM ibt_wr_ds_t *sgl;
28512198SEiji.Ota@Sun.COM ibt_mi_hdl_t mihdl;
28612198SEiji.Ota@Sun.COM };
28712198SEiji.Ota@Sun.COM #define rdsv3_sg_page(scat) (scat)->vaddr
28812198SEiji.Ota@Sun.COM #define rdsv3_sg_len(scat) (scat)->length
28912198SEiji.Ota@Sun.COM #define rdsv3_sg_set_page(scat, pg, len, off) \
29012198SEiji.Ota@Sun.COM (scat)->vaddr = (caddr_t)(pg + off); \
29112198SEiji.Ota@Sun.COM (scat)->length = len
29212198SEiji.Ota@Sun.COM #define rdsv3_ib_sg_dma_len(dev, scat) rdsv3_sg_len(scat)
29312198SEiji.Ota@Sun.COM
29412198SEiji.Ota@Sun.COM /* copied from sys/socket.h */
29512198SEiji.Ota@Sun.COM #if defined(__sparc)
29612198SEiji.Ota@Sun.COM /* To maintain backward compatibility, alignment needs to be 8 on sparc. */
29712198SEiji.Ota@Sun.COM #define _CMSG_HDR_ALIGNMENT 8
29812198SEiji.Ota@Sun.COM #else
29912198SEiji.Ota@Sun.COM /* for __i386 (and other future architectures) */
30012198SEiji.Ota@Sun.COM #define _CMSG_HDR_ALIGNMENT 4
30112198SEiji.Ota@Sun.COM #endif /* defined(__sparc) */
30212198SEiji.Ota@Sun.COM
30312198SEiji.Ota@Sun.COM /*
30412198SEiji.Ota@Sun.COM * The cmsg headers (and macros dealing with them) were made available as
30512198SEiji.Ota@Sun.COM * part of UNIX95 and hence need to be protected with a _XPG4_2 define.
30612198SEiji.Ota@Sun.COM */
30712198SEiji.Ota@Sun.COM #define _CMSG_DATA_ALIGNMENT (sizeof (int))
30812198SEiji.Ota@Sun.COM #define _CMSG_HDR_ALIGN(x) (((uintptr_t)(x) + _CMSG_HDR_ALIGNMENT - 1) & \
30912198SEiji.Ota@Sun.COM ~(_CMSG_HDR_ALIGNMENT - 1))
31012198SEiji.Ota@Sun.COM #define _CMSG_DATA_ALIGN(x) (((uintptr_t)(x) + _CMSG_DATA_ALIGNMENT - 1) & \
31112198SEiji.Ota@Sun.COM ~(_CMSG_DATA_ALIGNMENT - 1))
31212198SEiji.Ota@Sun.COM #define CMSG_DATA(c) \
31312198SEiji.Ota@Sun.COM ((unsigned char *)_CMSG_DATA_ALIGN((struct cmsghdr *)(c) + 1))
31412198SEiji.Ota@Sun.COM
31512198SEiji.Ota@Sun.COM #define CMSG_FIRSTHDR(m) \
31612198SEiji.Ota@Sun.COM (((m)->msg_controllen < sizeof (struct cmsghdr)) ? \
31712198SEiji.Ota@Sun.COM (struct cmsghdr *)0 : (struct cmsghdr *)((m)->msg_control))
31812198SEiji.Ota@Sun.COM
31912198SEiji.Ota@Sun.COM #define CMSG_NXTHDR(m, c) \
32012198SEiji.Ota@Sun.COM (((c) == 0) ? CMSG_FIRSTHDR(m) : \
32112198SEiji.Ota@Sun.COM ((((uintptr_t)_CMSG_HDR_ALIGN((char *)(c) + \
32212198SEiji.Ota@Sun.COM ((struct cmsghdr *)(c))->cmsg_len) + sizeof (struct cmsghdr)) > \
32312198SEiji.Ota@Sun.COM (((uintptr_t)((struct msghdr *)(m))->msg_control) + \
32412198SEiji.Ota@Sun.COM ((uintptr_t)((struct msghdr *)(m))->msg_controllen))) ? \
32512198SEiji.Ota@Sun.COM ((struct cmsghdr *)0) : \
32612198SEiji.Ota@Sun.COM ((struct cmsghdr *)_CMSG_HDR_ALIGN((char *)(c) + \
32712198SEiji.Ota@Sun.COM ((struct cmsghdr *)(c))->cmsg_len))))
32812198SEiji.Ota@Sun.COM
32912198SEiji.Ota@Sun.COM /* Amount of space + padding needed for a message of length l */
33012198SEiji.Ota@Sun.COM #define CMSG_SPACE(l) \
33112198SEiji.Ota@Sun.COM ((unsigned int)_CMSG_HDR_ALIGN(sizeof (struct cmsghdr) + (l)))
33212198SEiji.Ota@Sun.COM
33312198SEiji.Ota@Sun.COM /* Value to be used in cmsg_len, does not include trailing padding */
33412198SEiji.Ota@Sun.COM #define CMSG_LEN(l) \
33512198SEiji.Ota@Sun.COM ((unsigned int)_CMSG_DATA_ALIGN(sizeof (struct cmsghdr)) + (l))
33612198SEiji.Ota@Sun.COM
33712198SEiji.Ota@Sun.COM /* OFUV -> IB */
33812198SEiji.Ota@Sun.COM #define RDSV3_IBDEV2HCAHDL(device) (device)->hca_hdl
33912198SEiji.Ota@Sun.COM #define RDSV3_QP2CHANHDL(qp) (qp)->ibt_qp
34012198SEiji.Ota@Sun.COM #define RDSV3_PD2PDHDL(pd) (pd)->ibt_pd
34112198SEiji.Ota@Sun.COM #define RDSV3_CQ2CQHDL(cq) (cq)->ibt_cq
34212198SEiji.Ota@Sun.COM
34312198SEiji.Ota@Sun.COM struct rdsv3_hdrs_mr {
34412198SEiji.Ota@Sun.COM ibt_lkey_t lkey;
34512198SEiji.Ota@Sun.COM caddr_t addr;
34612198SEiji.Ota@Sun.COM size_t size;
34712198SEiji.Ota@Sun.COM ibt_mr_hdl_t hdl;
34812198SEiji.Ota@Sun.COM };
34912198SEiji.Ota@Sun.COM
35012198SEiji.Ota@Sun.COM /* rdsv3_impl.c */
35112198SEiji.Ota@Sun.COM void rdsv3_trans_init();
35212198SEiji.Ota@Sun.COM boolean_t rdsv3_capable_interface(struct lifreq *lifrp);
35312198SEiji.Ota@Sun.COM int rdsv3_do_ip_ioctl(ksocket_t so4, void **ipaddrs, int *size, int *nifs);
35412198SEiji.Ota@Sun.COM int rdsv3_do_ip_ioctl_old(ksocket_t so4, void **ipaddrs, int *size, int *nifs);
35512198SEiji.Ota@Sun.COM boolean_t rdsv3_isloopback(ipaddr_t addr);
35612198SEiji.Ota@Sun.COM void rdsv3_cancel_delayed_work(rdsv3_delayed_work_t *dwp);
35712198SEiji.Ota@Sun.COM void rdsv3_flush_workqueue(rdsv3_workqueue_struct_t *wq);
35812198SEiji.Ota@Sun.COM void rdsv3_queue_work(rdsv3_workqueue_struct_t *wq, rdsv3_work_t *wp);
35912198SEiji.Ota@Sun.COM void rdsv3_queue_delayed_work(rdsv3_workqueue_struct_t *wq,
36012198SEiji.Ota@Sun.COM rdsv3_delayed_work_t *dwp, uint_t delay);
36112198SEiji.Ota@Sun.COM struct rsock *rdsv3_sk_alloc();
36212198SEiji.Ota@Sun.COM void rdsv3_sock_init_data(struct rsock *sk);
36312198SEiji.Ota@Sun.COM void rdsv3_sock_exit_data(struct rsock *sk);
36412198SEiji.Ota@Sun.COM void rdsv3_destroy_task_workqueue(rdsv3_workqueue_struct_t *wq);
36512198SEiji.Ota@Sun.COM rdsv3_workqueue_struct_t *rdsv3_create_task_workqueue(char *name);
36612198SEiji.Ota@Sun.COM int rdsv3_conn_constructor(void *buf, void *arg, int kmflags);
36712198SEiji.Ota@Sun.COM void rdsv3_conn_destructor(void *buf, void *arg);
36812198SEiji.Ota@Sun.COM int rdsv3_conn_compare(const void *conn1, const void *conn2);
36912198SEiji.Ota@Sun.COM void rdsv3_loop_init();
37012198SEiji.Ota@Sun.COM int rdsv3_mr_compare(const void *mr1, const void *mr2);
37112198SEiji.Ota@Sun.COM int rdsv3_put_cmsg(struct nmsghdr *msg, int level, int type, size_t size,
37212198SEiji.Ota@Sun.COM void *payload);
37312198SEiji.Ota@Sun.COM int rdsv3_verify_bind_address(ipaddr_t addr);
37412198SEiji.Ota@Sun.COM uint16_t rdsv3_ip_fast_csum(void *buffer, size_t length);
37512198SEiji.Ota@Sun.COM uint_t rdsv3_ib_dma_map_sg(struct ib_device *dev, struct rdsv3_scatterlist
37612198SEiji.Ota@Sun.COM *scat, uint_t num);
37712198SEiji.Ota@Sun.COM void rdsv3_ib_dma_unmap_sg(ib_device_t *dev, struct rdsv3_scatterlist *scat,
37812198SEiji.Ota@Sun.COM uint_t num);
37912228SEiji.Ota@Sun.COM static inline void
rdsv3_sk_sock_hold(struct rsock * sk)38012198SEiji.Ota@Sun.COM rdsv3_sk_sock_hold(struct rsock *sk)
38112198SEiji.Ota@Sun.COM {
38212198SEiji.Ota@Sun.COM atomic_add_32(&sk->sk_refcount, 1);
38312198SEiji.Ota@Sun.COM }
38412228SEiji.Ota@Sun.COM static inline void
rdsv3_sk_sock_put(struct rsock * sk)38512198SEiji.Ota@Sun.COM rdsv3_sk_sock_put(struct rsock *sk)
38612198SEiji.Ota@Sun.COM {
38712198SEiji.Ota@Sun.COM if (atomic_dec_and_test(&sk->sk_refcount))
38812198SEiji.Ota@Sun.COM rdsv3_sock_exit_data(sk);
38912198SEiji.Ota@Sun.COM }
39012228SEiji.Ota@Sun.COM static inline int
rdsv3_sk_sock_flag(struct rsock * sk,uint_t flag)39112198SEiji.Ota@Sun.COM rdsv3_sk_sock_flag(struct rsock *sk, uint_t flag)
39212198SEiji.Ota@Sun.COM {
39312198SEiji.Ota@Sun.COM return (test_bit(flag, &sk->sk_flag));
39412198SEiji.Ota@Sun.COM }
39512228SEiji.Ota@Sun.COM static inline void
rdsv3_sk_sock_orphan(struct rsock * sk)39612198SEiji.Ota@Sun.COM rdsv3_sk_sock_orphan(struct rsock *sk)
39712198SEiji.Ota@Sun.COM {
39812198SEiji.Ota@Sun.COM set_bit(SOCK_DEAD, &sk->sk_flag);
39912198SEiji.Ota@Sun.COM }
40012198SEiji.Ota@Sun.COM
401*12414SEiji.Ota@Sun.COM #define rdsv3_sndtimeo(a, b) b ? 0 : 3600 /* check this value on linux */
402*12414SEiji.Ota@Sun.COM #define rdsv3_rcvtimeo(a, b) b ? 0 : 3600 /* check this value on linux */
40312198SEiji.Ota@Sun.COM
40412198SEiji.Ota@Sun.COM void rdsv3_ib_free_conn(void *arg);
40512198SEiji.Ota@Sun.COM
40612198SEiji.Ota@Sun.COM #ifdef __cplusplus
40712198SEiji.Ota@Sun.COM }
40812198SEiji.Ota@Sun.COM #endif
40912198SEiji.Ota@Sun.COM
41012198SEiji.Ota@Sun.COM #endif /* _RDSV3_IMPL_H */
411