[DAPL] fix x86(32-bit) pointer sign extension warning when going to wr_id (u64).
[mirror/winof/.git] / ulp / dapl / dapl / ibal / dapl_ibal_dto.h
1 \r
2 /*\r
3  * Copyright (c) 2002, Network Appliance, Inc. All rights reserved. \r
4  * \r
5  * This Software is licensed under the terms of the "Common Public\r
6  * License" a copy of which is in the file LICENSE.txt in the root\r
7  * directory. The license is also available from the Open Source\r
8  * Initiative, see http://www.opensource.org/licenses/cpl.php.\r
9  *\r
10  */\r
11 \r
12 /**********************************************************************\r
13  * \r
14  * MODULE: dapl_ibal_dto.h\r
15  *\r
16  * PURPOSE: Utility routines for data transfer operations using the\r
17  * IBAL APIs\r
18  *\r
19  * $Id$\r
20  *\r
21  **********************************************************************/\r
22 \r
23 #ifndef _DAPL_IBAL_DTO_H\r
24 #define _DAPL_IBAL_DTO_H\r
25 \r
26 #include "dapl_ibal_util.h"\r
27 \r
28 STATIC _INLINE_ int\r
29 dapls_cqe_opcode_convert (ib_work_completion_t *cqe_p);\r
30 \r
31 extern DAT_RETURN\r
32 dapls_ib_cq_late_alloc (\r
33         IN  ib_pd_handle_t      pd_handle,\r
34         IN  DAPL_EVD            *evd_ptr);\r
35 \r
36 #define         DAPL_DEFAULT_DS_ENTRIES         8\r
37 \r
38 /*\r
39  * dapls_ib_post_recv\r
40  *\r
41  * Provider specific Post RECV function\r
42  */\r
43 STATIC _INLINE_ DAT_RETURN \r
44 dapls_ib_post_recv (\r
45         IN  DAPL_EP                             *ep_ptr,\r
46         IN  DAPL_COOKIE                 *cookie,\r
47         IN  DAT_COUNT                   num_segments,\r
48         IN  DAT_LMR_TRIPLET             *local_iov)\r
49 {\r
50     ib_api_status_t     ib_status;\r
51     ib_recv_wr_t                recv_wr, *failed_wr_p;\r
52     ib_local_ds_t       ds_array[DAPL_DEFAULT_DS_ENTRIES], *ds_array_p;\r
53     DAT_COUNT           i, total_len;\r
54 \r
55     dapl_os_memzero(&recv_wr, sizeof(ib_recv_wr_t));\r
56 #ifndef _WIN64\r
57         // Fix MS compiler warning C4826: Conversion from 'DAPL_COOKIE *' to\r
58         // 'DAT_UINT64' sign-extends; This may cause unexpected runtime behavior.\r
59     recv_wr.wr_id        = (DAT_UINT64) (DAT_UINT32) cookie;\r
60 #else\r
61     recv_wr.wr_id        = (DAT_UINT64) cookie;\r
62 #endif\r
63     recv_wr.num_ds       = num_segments;\r
64 \r
65         if( num_segments <= DAPL_DEFAULT_DS_ENTRIES )\r
66         {\r
67                 ds_array_p = ds_array;\r
68         }\r
69         else\r
70         {\r
71                 ds_array_p = dapl_os_alloc( num_segments * sizeof(ib_local_ds_t) );\r
72         }\r
73     recv_wr.ds_array = ds_array_p;\r
74 \r
75     if (NULL == ds_array_p)\r
76     {\r
77         return (DAT_INSUFFICIENT_RESOURCES);\r
78     }\r
79 \r
80     total_len = 0;\r
81 \r
82     for (i = 0; i < num_segments; i++, ds_array_p++)\r
83     {\r
84                 ds_array_p->length = (uint32_t)local_iov[i].segment_length;\r
85                 ds_array_p->lkey   = local_iov[i].lmr_context;\r
86                 ds_array_p->vaddr  = local_iov[i].virtual_address;\r
87                 total_len         += ds_array_p->length;\r
88     }\r
89 \r
90     if (cookie != NULL)\r
91     {\r
92                 cookie->val.dto.size = total_len;\r
93         dapl_dbg_log (DAPL_DBG_TYPE_EP,\r
94                                         "--> DsPR: EP = %p QP = %p cookie= %p, num_seg= %d\n", \r
95                                         ep_ptr, ep_ptr->qp_handle, cookie, num_segments);\r
96     }\r
97     recv_wr.p_next = NULL;\r
98 \r
99     ib_status = ib_post_recv( ep_ptr->qp_handle, &recv_wr, &failed_wr_p );\r
100 \r
101         if( num_segments > DAPL_DEFAULT_DS_ENTRIES )\r
102                 dapl_os_free( recv_wr.ds_array, num_segments * sizeof(ib_local_ds_t) );\r
103 \r
104     if (IB_SUCCESS == ib_status)\r
105     {\r
106                 return DAT_SUCCESS;\r
107     }\r
108 \r
109     dapl_dbg_log (DAPL_DBG_TYPE_DTO_COMP_ERR,\r
110                                         "--> DsPR: post_recv status %s\n",\r
111                                         ib_get_err_str(ib_status));\r
112     /*\r
113      * Moving QP to error state; \r
114      */\r
115     (void) dapls_modify_qp_state_to_error ( ep_ptr->qp_handle);\r
116     ep_ptr->qp_state = IB_QPS_ERROR;\r
117 \r
118         return (dapl_ib_status_convert (ib_status));\r
119 }\r
120 \r
121 \r
122 /*\r
123  * dapls_ib_post_send\r
124  *\r
125  * Provider specific Post SEND function\r
126  */\r
127 STATIC _INLINE_ DAT_RETURN \r
128 dapls_ib_post_send (\r
129         IN  DAPL_EP                *ep_ptr,\r
130         IN  ib_send_op_type_t      op_type,\r
131         IN  DAPL_COOKIE                    *cookie,\r
132         IN  DAT_COUNT                      num_segments,\r
133         IN  DAT_LMR_TRIPLET                *local_iov,\r
134         IN  const DAT_RMR_TRIPLET  *remote_iov,\r
135         IN  DAT_COMPLETION_FLAGS   completion_flags )\r
136 {\r
137     ib_api_status_t     ib_status;\r
138     ib_send_wr_t                send_wr, *failed_wr_p;\r
139     ib_local_ds_t       ds_array[DAPL_DEFAULT_DS_ENTRIES], *ds_array_p;\r
140     DAT_COUNT                   i, total_len;\r
141 \r
142         if (ep_ptr->param.ep_state != DAT_EP_STATE_CONNECTED)\r
143         {\r
144                 ib_qp_attr_t             qp_attr;\r
145 \r
146                 (void) ib_query_qp ( ep_ptr->qp_handle, &qp_attr );\r
147 \r
148                 dapl_dbg_log (DAPL_DBG_TYPE_ERR,\r
149                       "--> DsPS: !CONN EP (%p) ep_state=%d QP_state=%d\n", \r
150                       ep_ptr, ep_ptr->param.ep_state, qp_attr.state );\r
151 \r
152         return(DAT_ERROR(DAT_INVALID_STATE, DAT_INVALID_STATE_EP_DISCONNECTED));\r
153         }\r
154     dapl_os_memzero (&send_wr, sizeof(ib_send_wr_t));\r
155 \r
156     send_wr.wr_type             = op_type;\r
157     send_wr.num_ds              = num_segments;\r
158 \r
159         if( num_segments <= DAPL_DEFAULT_DS_ENTRIES )\r
160         {\r
161                 ds_array_p = ds_array;\r
162         }\r
163         else\r
164         {\r
165                 ds_array_p = dapl_os_alloc( num_segments * sizeof(ib_local_ds_t) );\r
166         }\r
167     send_wr.ds_array = ds_array_p;\r
168 \r
169     if (NULL == ds_array_p)\r
170     {\r
171                 return (DAT_INSUFFICIENT_RESOURCES);\r
172     }\r
173 \r
174     total_len = 0;\r
175 \r
176     for (i = 0; i < num_segments; i++, ds_array_p++)\r
177     {\r
178         ds_array_p->length = (uint32_t)local_iov[i].segment_length;\r
179         ds_array_p->lkey   = local_iov[i].lmr_context;\r
180         ds_array_p->vaddr  = local_iov[i].virtual_address;\r
181         total_len         += ds_array_p->length;\r
182     }\r
183 \r
184         /* NULL cookie is OK if no Completion event is requested */\r
185     if (cookie != NULL)\r
186     {\r
187         dapl_os_assert( cookie->ep == ep_ptr );\r
188             cookie->val.dto.size            =  total_len;\r
189 \r
190                 dapl_dbg_log (DAPL_DBG_TYPE_EP, "--> DsPS: EVD=%p EP=%p QP=%p type=%d "\r
191             "sg=%d ln=%d ck=%p 0x" F64x "\n", \r
192                         ep_ptr->param.request_evd_handle, ep_ptr, ep_ptr->qp_handle, \r
193                         op_type, num_segments, total_len,\r
194                         cookie, cookie->val.dto.cookie.as_64 );\r
195     }\r
196 #ifndef _WIN64\r
197         // Fix MS compiler warning C4826: Conversion from 'DAPL_COOKIE *' to\r
198         // 'DAT_UTIN64' sign-extends; This may cause unexpected runtime behavior.\r
199     send_wr.wr_id = (DAT_UINT64) (DAT_UINT32)cookie;\r
200 #else\r
201     send_wr.wr_id = (DAT_UINT64) cookie;\r
202 #endif\r
203 \r
204     /* RC for now */\r
205     if (total_len > 0)\r
206     {\r
207         send_wr.remote_ops.vaddr = remote_iov->target_address;\r
208         send_wr.remote_ops.rkey  = remote_iov->rmr_context;\r
209     }\r
210 \r
211     send_wr.send_opt = 0;\r
212 \r
213     send_wr.send_opt |= (DAT_COMPLETION_BARRIER_FENCE_FLAG & \r
214                                                                 completion_flags) ? IB_SEND_OPT_FENCE : 0;\r
215     send_wr.send_opt |= (DAT_COMPLETION_SUPPRESS_FLAG & \r
216                                                                 completion_flags) ? 0 : IB_SEND_OPT_SIGNALED;\r
217     send_wr.send_opt |= (DAT_COMPLETION_SOLICITED_WAIT_FLAG & \r
218                                                                 completion_flags) ? IB_SEND_OPT_SOLICITED : 0;\r
219 \r
220     dapl_dbg_log (DAPL_DBG_TYPE_EP, "--> DsPS: EP=%p QP=%p send_opt=0x%x,"\r
221                   "rem_addr=%p, rem_rkey=0x%x completion_flags=0x%x\n",\r
222                   ep_ptr, ep_ptr->qp_handle,  \r
223                   send_wr.send_opt, (void *)(uintptr_t) send_wr.remote_ops.vaddr,\r
224                   send_wr.remote_ops.rkey, completion_flags);\r
225 \r
226     send_wr.p_next = NULL;\r
227 \r
228         /* hold reference for QP command serialization on destruction */\r
229         dapl_os_atomic_inc (&ep_ptr->req_count);\r
230     ib_status = ib_post_send( ep_ptr->qp_handle, &send_wr, &failed_wr_p );\r
231         dapl_os_atomic_dec (&ep_ptr->req_count);\r
232 \r
233         if( num_segments > DAPL_DEFAULT_DS_ENTRIES )\r
234                 dapl_os_free( send_wr.ds_array, num_segments * sizeof(ib_local_ds_t) );\r
235 \r
236     if (IB_SUCCESS == ib_status)\r
237     {\r
238         return DAT_SUCCESS;\r
239     }\r
240 \r
241     dapl_dbg_log (DAPL_DBG_TYPE_DTO_COMP_ERR,\r
242                                   "--> DsPS: EP=%p post_send status %s\n", \r
243                   ep_ptr, ib_get_err_str(ib_status));\r
244     /*\r
245      * Moving QP to error state; \r
246      */\r
247     (void) dapls_modify_qp_state_to_error ( ep_ptr->qp_handle);\r
248     ep_ptr->qp_state = IB_QPS_ERROR;\r
249 \r
250         return (dapl_ib_status_convert (ib_status));\r
251 }\r
252 \r
253 /*\r
254  * dapls_ib_optional_prv_dat\r
255  *\r
256  * Allocate space for private data to be used in CR calls\r
257  *\r
258  * Input:\r
259  *      cr_ptr                  CR handle\r
260  *      event_data              data provided by the provider callback function\r
261  *      cr_pp                   Pointer for private data\r
262  *\r
263  * Output:\r
264  *      cr_pp                   Area \r
265  *\r
266  * Returns:\r
267  *      DAT_SUCCESS\r
268  *      DAT_INSUFFICIENT_RESOURCES\r
269  *\r
270  */\r
271 STATIC _INLINE_ DAT_RETURN\r
272 dapls_ib_optional_prv_dat (\r
273         IN  DAPL_CR             *cr_ptr,\r
274         IN  const void          *event_data,\r
275         OUT DAPL_CR             **cr_pp)\r
276 {\r
277         DAT_RETURN dat_status = DAT_SUCCESS;\r
278         DAPL_PRIVATE *p_prv_data = (DAPL_PRIVATE *)event_data;\r
279 \r
280         if ( ! cr_ptr->param.private_data_size )\r
281         {\r
282                 cr_ptr->param.private_data_size = sizeof(cr_ptr->private_data);\r
283                 cr_ptr->param.private_data = cr_ptr->private_data;\r
284                 dapl_os_memcpy(cr_ptr->private_data, p_prv_data->private_data, cr_ptr->param.private_data_size );\r
285                 *cr_pp = (DAPL_CR *)cr_ptr->param.private_data;\r
286         }\r
287     return dat_status;\r
288 }\r
289 \r
290 \r
291 STATIC _INLINE_ int\r
292 dapls_cqe_opcode_convert (ib_work_completion_t *cqe_p)\r
293 {\r
294     switch (((ib_work_completion_t *)cqe_p)->wc_type)\r
295     {\r
296         case IB_WC_SEND:\r
297         {\r
298             return (OP_SEND);\r
299         }\r
300         case IB_WC_RDMA_WRITE:\r
301         case IB_WC_RECV_RDMA_WRITE:\r
302         {\r
303             return (OP_RDMA_WRITE);\r
304         }\r
305         case IB_WC_RDMA_READ:\r
306         {\r
307             return (OP_RDMA_READ);\r
308         }\r
309         case IB_WC_COMPARE_SWAP:\r
310         {\r
311             return (OP_COMP_AND_SWAP);\r
312         }\r
313         case IB_WC_FETCH_ADD:\r
314         {\r
315             return (OP_FETCH_AND_ADD);\r
316         }\r
317         case IB_WC_MW_BIND:\r
318         {\r
319             return (OP_BIND_MW);\r
320         }\r
321         case IB_WC_RECV:        \r
322         {\r
323             return (OP_RECEIVE);\r
324         }\r
325         default :       \r
326         {\r
327            /* error */ \r
328             return (IB_ERROR);\r
329         }\r
330     }\r
331 }\r
332 \r
333 #define DAPL_GET_CQE_WRID(cqe_p) ((ib_work_completion_t *)cqe_p)->wr_id\r
334 #define DAPL_GET_CQE_OPTYPE(cqe_p) dapls_cqe_opcode_convert(cqe_p)\r
335 #define DAPL_GET_CQE_BYTESNUM(cqe_p) ((ib_work_completion_t *)cqe_p)->length\r
336 #define DAPL_GET_CQE_STATUS(cqe_p) ((ib_work_completion_t *)cqe_p)->status\r
337 \r
338 #endif /* _DAPL_IBAL_DTO_H */\r