1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24 #ifndef PML_CM_RECVREQ_H
25 #define PML_CM_RECVREQ_H
26
27 #include "pml_cm_request.h"
28 #include "ompi/mca/pml/base/pml_base_recvreq.h"
29 #include "ompi/mca/mtl/mtl.h"
30
31 struct mca_pml_cm_thin_recv_request_t {
32 mca_pml_cm_request_t req_base;
33 mca_mtl_request_t req_mtl;
34 };
35 typedef struct mca_pml_cm_thin_recv_request_t mca_pml_cm_thin_recv_request_t;
36 OBJ_CLASS_DECLARATION(mca_pml_cm_thin_recv_request_t);
37
38 struct mca_pml_cm_hvy_recv_request_t {
39 mca_pml_cm_request_t req_base;
40 void *req_addr;
41 size_t req_count;
42 int32_t req_peer;
43 int32_t req_tag;
44 void *req_buff;
45 size_t req_bytes_packed;
46 bool req_blocking;
47 mca_mtl_request_t req_mtl;
48 };
49 typedef struct mca_pml_cm_hvy_recv_request_t mca_pml_cm_hvy_recv_request_t;
50
51 OBJ_CLASS_DECLARATION(mca_pml_cm_hvy_recv_request_t);
52
53
54
55
56
57
58
59 #define MCA_PML_CM_THIN_RECV_REQUEST_ALLOC(recvreq) \
60 do { \
61 recvreq = (mca_pml_cm_thin_recv_request_t*) \
62 opal_free_list_get (&mca_pml_base_recv_requests); \
63 recvreq->req_base.req_pml_type = MCA_PML_CM_REQUEST_RECV_THIN; \
64 recvreq->req_mtl.ompi_req = (ompi_request_t*) recvreq; \
65 recvreq->req_mtl.completion_callback = mca_pml_cm_recv_request_completion; \
66 } while (0)
67
68 #define MCA_PML_CM_HVY_RECV_REQUEST_ALLOC(recvreq) \
69 do { \
70 recvreq = (mca_pml_cm_hvy_recv_request_t*) \
71 opal_free_list_get (&mca_pml_base_recv_requests); \
72 recvreq->req_base.req_pml_type = MCA_PML_CM_REQUEST_RECV_HEAVY; \
73 recvreq->req_mtl.ompi_req = (ompi_request_t*) recvreq; \
74 recvreq->req_mtl.completion_callback = mca_pml_cm_recv_request_completion; \
75 } while (0)
76
77
78
79
80
81
82
83
84
85
86
87
88
89 #if OPAL_ENABLE_HETEROGENEOUS_SUPPORT
90 #define MCA_PML_CM_THIN_RECV_REQUEST_INIT( request, \
91 ompi_proc, \
92 comm, \
93 src, \
94 datatype, \
95 addr, \
96 count, \
97 flags ) \
98 do { \
99 OMPI_REQUEST_INIT(&(request)->req_base.req_ompi, false); \
100 (request)->req_base.req_ompi.req_mpi_object.comm = comm; \
101 (request)->req_base.req_pml_complete = false; \
102 (request)->req_base.req_free_called = false; \
103 request->req_base.req_comm = comm; \
104 request->req_base.req_datatype = datatype; \
105 OBJ_RETAIN(comm); \
106 OMPI_DATATYPE_RETAIN(datatype); \
107 \
108 if( MPI_ANY_SOURCE == src ) { \
109 ompi_proc = ompi_proc_local_proc; \
110 } else { \
111 ompi_proc = ompi_comm_peer_lookup( comm, src ); \
112 } \
113 MCA_PML_CM_SWITCH_CUDA_CONVERTOR_OFF(flags, datatype, count); \
114 opal_convertor_copy_and_prepare_for_recv( \
115 ompi_proc->super.proc_convertor, \
116 &(datatype->super), \
117 count, \
118 addr, \
119 flags, \
120 &(request)->req_base.req_convertor ); \
121 } while(0)
122 #else
123 #define MCA_PML_CM_THIN_RECV_REQUEST_INIT( request, \
124 ompi_proc, \
125 comm, \
126 src, \
127 datatype, \
128 addr, \
129 count, \
130 flags ) \
131 do { \
132 OMPI_REQUEST_INIT(&(request)->req_base.req_ompi, false); \
133 (request)->req_base.req_ompi.req_mpi_object.comm = comm; \
134 (request)->req_base.req_pml_complete = false; \
135 (request)->req_base.req_free_called = false; \
136 request->req_base.req_comm = comm; \
137 request->req_base.req_datatype = datatype; \
138 OBJ_RETAIN(comm); \
139 OMPI_DATATYPE_RETAIN(datatype); \
140 \
141 MCA_PML_CM_SWITCH_CUDA_CONVERTOR_OFF(flags, datatype, count); \
142 opal_convertor_copy_and_prepare_for_recv( \
143 ompi_mpi_local_convertor, \
144 &(datatype->super), \
145 count, \
146 addr, \
147 flags, \
148 &(request)->req_base.req_convertor ); \
149 } while(0)
150 #endif
151
152 #if OPAL_ENABLE_HETEROGENEOUS_SUPPORT
153 #define MCA_PML_CM_HVY_RECV_REQUEST_INIT( request, \
154 ompi_proc, \
155 comm, \
156 tag, \
157 src, \
158 datatype, \
159 addr, \
160 count, \
161 flags, \
162 persistent) \
163 do { \
164 OMPI_REQUEST_INIT(&(request)->req_base.req_ompi, persistent); \
165 (request)->req_base.req_ompi.req_mpi_object.comm = comm; \
166 (request)->req_base.req_pml_complete = OPAL_INT_TO_BOOL(persistent); \
167 (request)->req_base.req_free_called = false; \
168 request->req_base.req_comm = comm; \
169 request->req_base.req_datatype = datatype; \
170 request->req_tag = tag; \
171 request->req_peer = src; \
172 request->req_addr = addr; \
173 request->req_count = count; \
174 OBJ_RETAIN(comm); \
175 OMPI_DATATYPE_RETAIN(datatype); \
176 \
177 if( MPI_ANY_SOURCE == src ) { \
178 ompi_proc = ompi_proc_local_proc; \
179 } else { \
180 ompi_proc = ompi_comm_peer_lookup( comm, src ); \
181 } \
182 MCA_PML_CM_SWITCH_CUDA_CONVERTOR_OFF(flags, datatype, count); \
183 opal_convertor_copy_and_prepare_for_recv( \
184 ompi_proc->super.proc_convertor, \
185 &(datatype->super), \
186 count, \
187 addr, \
188 flags, \
189 &(request)->req_base.req_convertor ); \
190 } while(0)
191 #else
192 #define MCA_PML_CM_HVY_RECV_REQUEST_INIT( request, \
193 ompi_proc, \
194 comm, \
195 tag, \
196 src, \
197 datatype, \
198 addr, \
199 count, \
200 flags, \
201 persistent) \
202 do { \
203 OMPI_REQUEST_INIT(&(request)->req_base.req_ompi, persistent); \
204 (request)->req_base.req_ompi.req_mpi_object.comm = comm; \
205 (request)->req_base.req_pml_complete = OPAL_INT_TO_BOOL(persistent); \
206 (request)->req_base.req_free_called = false; \
207 request->req_base.req_comm = comm; \
208 request->req_base.req_datatype = datatype; \
209 request->req_tag = tag; \
210 request->req_peer = src; \
211 request->req_addr = addr; \
212 request->req_count = count; \
213 OBJ_RETAIN(comm); \
214 OMPI_DATATYPE_RETAIN(datatype); \
215 \
216 MCA_PML_CM_SWITCH_CUDA_CONVERTOR_OFF(flags, datatype, count); \
217 opal_convertor_copy_and_prepare_for_recv( \
218 ompi_mpi_local_convertor, \
219 &(datatype->super), \
220 count, \
221 addr, \
222 flags, \
223 &(request)->req_base.req_convertor ); \
224 } while(0)
225 #endif
226
227
228
229
230
231
232
233 #define MCA_PML_CM_THIN_RECV_REQUEST_START(request, comm, tag, src, ret) \
234 do { \
235 \
236 request->req_base.req_pml_complete = false; \
237 request->req_base.req_ompi.req_complete = false; \
238 request->req_base.req_ompi.req_state = OMPI_REQUEST_ACTIVE; \
239 \
240
241
242
243 \
244 request->req_base.req_ompi.req_status.MPI_TAG = OMPI_ANY_TAG; \
245 request->req_base.req_ompi.req_status.MPI_ERROR = OMPI_SUCCESS; \
246 request->req_base.req_ompi.req_status._cancelled = 0; \
247 ret = OMPI_MTL_CALL(irecv(ompi_mtl, \
248 comm, \
249 src, \
250 tag, \
251 &recvreq->req_base.req_convertor, \
252 &recvreq->req_mtl)); \
253 } while (0)
254
255 #define MCA_PML_CM_THIN_RECV_REQUEST_MATCHED_START(request, message, ret) \
256 do { \
257 \
258 request->req_base.req_pml_complete = false; \
259 request->req_base.req_ompi.req_complete = false; \
260 request->req_base.req_ompi.req_state = OMPI_REQUEST_ACTIVE; \
261 \
262
263
264
265 \
266 request->req_base.req_ompi.req_status.MPI_TAG = OMPI_ANY_TAG; \
267 request->req_base.req_ompi.req_status.MPI_ERROR = OMPI_SUCCESS; \
268 request->req_base.req_ompi.req_status._cancelled = 0; \
269 ret = OMPI_MTL_CALL(imrecv(ompi_mtl, \
270 &recvreq->req_base.req_convertor, \
271 message, \
272 &recvreq->req_mtl)); \
273 } while (0)
274
275
276 #define MCA_PML_CM_HVY_RECV_REQUEST_START(request, ret) \
277 do { \
278 \
279 \
280 request->req_base.req_pml_complete = false; \
281 request->req_base.req_ompi.req_complete = false; \
282 request->req_base.req_ompi.req_state = OMPI_REQUEST_ACTIVE; \
283 \
284
285
286
287 \
288 request->req_base.req_ompi.req_status.MPI_TAG = OMPI_ANY_TAG; \
289 request->req_base.req_ompi.req_status.MPI_ERROR = OMPI_SUCCESS; \
290 request->req_base.req_ompi.req_status._cancelled = 0; \
291 ret = OMPI_MTL_CALL(irecv(ompi_mtl, \
292 request->req_base.req_comm, \
293 request->req_peer, \
294 request->req_tag, \
295 &recvreq->req_base.req_convertor, \
296 &recvreq->req_mtl)); \
297 } while (0)
298
299
300
301
302
303
304
305 #define MCA_PML_CM_THIN_RECV_REQUEST_MPI_COMPLETE( recvreq ) \
306 do { \
307 ompi_request_complete( &(recvreq->req_base.req_ompi), true ); \
308 } while (0)
309
310
311
312
313
314
315
316 #define MCA_PML_CM_THIN_RECV_REQUEST_PML_COMPLETE(recvreq) \
317 do { \
318 assert( false == recvreq->req_base.req_pml_complete ); \
319 \
320 if( true == recvreq->req_base.req_free_called ) { \
321 MCA_PML_CM_THIN_RECV_REQUEST_RETURN( recvreq ); \
322 } else { \
323 recvreq->req_base.req_pml_complete = true; \
324 ompi_request_complete( &(recvreq->req_base.req_ompi), true ); \
325 } \
326 } while(0)
327
328
329
330
331
332
333
334
335
336 #define MCA_PML_CM_HVY_RECV_REQUEST_PML_COMPLETE(recvreq) \
337 do { \
338 assert( false == recvreq->req_base.req_pml_complete ); \
339 \
340 if( true == recvreq->req_base.req_free_called ) { \
341 MCA_PML_CM_HVY_RECV_REQUEST_RETURN( recvreq ); \
342 } else { \
343 \
344 if(recvreq->req_base.req_ompi.req_persistent) { \
345 \
346 size_t offset = 0; \
347 opal_convertor_set_position(&recvreq->req_base.req_convertor, &offset); \
348 } \
349 recvreq->req_base.req_pml_complete = true; \
350 ompi_request_complete( &(recvreq->req_base.req_ompi), true ); \
351 } \
352 } while(0)
353
354
355
356
357
358 #define MCA_PML_CM_HVY_RECV_REQUEST_RETURN(recvreq) \
359 { \
360 OBJ_RELEASE((recvreq)->req_base.req_comm); \
361 OMPI_DATATYPE_RELEASE((recvreq)->req_base.req_datatype); \
362 OMPI_REQUEST_FINI(&(recvreq)->req_base.req_ompi); \
363 opal_convertor_cleanup( &((recvreq)->req_base.req_convertor) ); \
364 opal_free_list_return ( &mca_pml_base_recv_requests, \
365 (opal_free_list_item_t*)(recvreq)); \
366 }
367
368
369
370
371 #define MCA_PML_CM_THIN_RECV_REQUEST_RETURN(recvreq) \
372 { \
373 OBJ_RELEASE((recvreq)->req_base.req_comm); \
374 OMPI_DATATYPE_RELEASE((recvreq)->req_base.req_datatype); \
375 OMPI_REQUEST_FINI(&(recvreq)->req_base.req_ompi); \
376 opal_convertor_cleanup( &((recvreq)->req_base.req_convertor) ); \
377 opal_free_list_return ( &mca_pml_base_recv_requests, \
378 (opal_free_list_item_t*)(recvreq)); \
379 }
380
381 extern void mca_pml_cm_recv_request_completion(struct mca_mtl_request_t *mtl_request);
382
383 #endif
384
385