source: XIOS/dev/branch_openmp/extern/ep_dev/ep_send.cpp @ 1503

Last change on this file since 1503 was 1503, checked in by yushan, 3 years ago

rank_map is passed from vector to map, in order to have more flexibility in comm_split

File size: 13.4 KB
Line 
1/*!
2   \file ep_send.hpp
3   \since 2 may 2016
4
5   \brief Definitions of MPI send functions: MPI_Send, MPI_Ssend, MPI_Isend, MPI_Issend
6 */
7
8#include "ep_lib.hpp"
9#include <mpi.h>
10#include "ep_declaration.hpp"
11#include "ep_mpi.hpp"
12
13
14namespace ep_lib
15{
16 
17  int MPI_Send(void *buf, int count, MPI_Datatype datatype, int dest, int tag, MPI_Comm comm)
18  {
19    if(!comm->is_ep)       return MPI_Send_mpi(buf, count, datatype, dest, tag, comm);
20    if(comm->is_intercomm) return MPI_Send_intercomm(buf, count, datatype, dest, tag, comm);
21   
22    Debug("\nMPI_Send with EP\n");
23   
24    int ep_src_loc  = comm->ep_comm_ptr->size_rank_info[1].first;
25    int ep_dest_loc = comm->ep_comm_ptr->comm_list[0]->ep_rank_map->at(dest).first;
26    int mpi_tag     = tag_combine(tag, ep_src_loc, ep_dest_loc);
27    int mpi_dest    = comm->ep_comm_ptr->comm_list[0]->ep_rank_map->at(dest).second;
28
29#ifdef _check_sum   
30    check_sum_send(buf, count, datatype, dest, tag, comm);
31#endif
32
33    return ::MPI_Send(buf, count, to_mpi_type(datatype), mpi_dest, mpi_tag, to_mpi_comm(comm->mpi_comm));
34  }
35
36
37  int MPI_Ssend(void *buf, int count, MPI_Datatype datatype, int dest, int tag, MPI_Comm comm)
38  {
39    if(!comm->is_ep)       return MPI_Ssend_mpi(buf, count, datatype, dest, tag, comm);
40    if(comm->is_intercomm) return MPI_Ssend_intercomm(buf, count, datatype, dest, tag, comm);
41   
42    Debug("\nMPI_Ssend with EP\n");
43
44    int ep_src_loc  = comm->ep_comm_ptr->size_rank_info[1].first;
45    int ep_dest_loc = comm->ep_comm_ptr->comm_list[0]->ep_rank_map->at(dest).first;
46    int mpi_tag     = tag_combine(tag, ep_src_loc, ep_dest_loc);
47    int mpi_dest    = comm->ep_comm_ptr->comm_list[0]->ep_rank_map->at(dest).second;
48   
49#ifdef _check_sum   
50    check_sum_send(buf, count, datatype, dest, tag, comm);
51#endif
52   
53    return ::MPI_Ssend(buf, count, to_mpi_type(datatype), mpi_dest, mpi_tag, to_mpi_comm(comm->mpi_comm));
54  }
55 
56
57
58
59
60  int MPI_Isend(const void *buf, int count, MPI_Datatype datatype, int dest, int tag, MPI_Comm comm, MPI_Request *request)
61  {
62    if(!comm->is_ep)       return MPI_Isend_mpi(buf, count, datatype, dest, tag, comm, request);
63    if(comm->is_intercomm) return MPI_Isend_intercomm(buf, count, datatype, dest, tag, comm, request);
64
65    Debug("\nMPI_Isend with EP\n");
66   
67    int src_rank;
68    MPI_Comm_rank(comm, &src_rank);
69
70
71#ifdef _check_sum   
72    check_sum_send(buf, count, datatype, dest, tag, comm);
73#endif
74   
75    *request = new ep_request;
76    memcheck("new "<< *request <<" : in ep_lib::MPI_Isend, *request = new ep_request");
77
78    (*request)->mpi_request = new ::MPI_Request;
79    memcheck("new "<< (*request)->mpi_request <<" : in ep_lib::MPI_Isend, (*request)->mpi_request = new ::MPI_Request");
80   
81
82    int ep_src_loc  = comm->ep_comm_ptr->size_rank_info[1].first;
83    int ep_dest_loc = comm->ep_comm_ptr->comm_list[0]->ep_rank_map->at(dest).first;
84    int mpi_tag     = tag_combine(tag, ep_src_loc, ep_dest_loc);
85    int mpi_dest    = comm->ep_comm_ptr->comm_list[0]->ep_rank_map->at(dest).second;
86
87    (*request)->ep_src  = src_rank;
88    (*request)->ep_tag  = tag;
89    (*request)->ep_datatype = datatype;
90
91    (*request)->type = 1;    // used in wait
92    (*request)->comm = comm;
93    (*request)->buf = const_cast<void*>(buf);
94
95
96    return ::MPI_Isend(buf, count, to_mpi_type(datatype), mpi_dest, mpi_tag, to_mpi_comm(comm->mpi_comm), to_mpi_request_ptr(*request));
97  }
98
99
100
101
102  int MPI_Issend(const void *buf, int count, MPI_Datatype datatype, int dest, int tag, MPI_Comm comm, MPI_Request *request)
103  {
104 
105    if(!comm->is_ep) return MPI_Issend_mpi(buf, count, datatype, dest, tag, comm, request);
106    if(comm->is_intercomm) return MPI_Issend_intercomm(buf, count, datatype, dest, tag, comm, request);
107
108    Debug("\nMPI_Issend with EP\n");
109   
110    int src_rank;
111    MPI_Comm_rank(comm, &src_rank);
112
113
114#ifdef _check_sum   
115    check_sum_send(buf, count, datatype, dest, tag, comm);
116#endif
117   
118    *request = new ep_request;
119    memcheck("new "<< *request <<" : in ep_lib::MPI_Issend, *request = new ep_request");
120
121    (*request)->mpi_request = new ::MPI_Request;
122    memcheck("new "<< (*request)->mpi_request <<" : in ep_lib::MPI_Issend, (*request)->mpi_request = new ::MPI_Request");
123   
124
125    int ep_src_loc  = comm->ep_comm_ptr->size_rank_info[1].first;
126    int ep_dest_loc = comm->ep_comm_ptr->comm_list[0]->ep_rank_map->at(dest).first;
127    int mpi_tag     = tag_combine(tag, ep_src_loc, ep_dest_loc);
128    int mpi_dest    = comm->ep_comm_ptr->comm_list[0]->ep_rank_map->at(dest).second;
129
130    (*request)->ep_src  = src_rank;
131    (*request)->ep_tag  = tag;
132    (*request)->ep_datatype = datatype;
133
134    (*request)->type = 1;    // used in wait
135    (*request)->comm = comm;
136    (*request)->buf = const_cast<void*>(buf);
137   
138    return ::MPI_Issend(buf, count, to_mpi_type(datatype), mpi_dest, mpi_tag, to_mpi_comm(comm->mpi_comm), to_mpi_request_ptr(*request));   
139  }
140 
141  int MPI_Send_mpi(void *buf, int count, MPI_Datatype datatype, int dest, int tag, MPI_Comm comm)
142  {
143    Debug("\nMPI_Send with MPI\n");
144    return ::MPI_Send(buf, count, to_mpi_type(datatype), dest, tag, to_mpi_comm(comm->mpi_comm));
145  }
146 
147  int MPI_Send_intercomm(void *buf, int count, MPI_Datatype datatype, int dest, int tag, MPI_Comm comm)
148  {
149    Debug("\nMPI_Send with EP_Intercomm\n");
150    MPI_Request request;
151    MPI_Status status;
152    MPI_Isend(buf, count, datatype, dest, tag, comm, &request);
153    MPI_Wait(&request, &status);
154    return MPI_SUCCESS;
155  }
156 
157 
158  int MPI_Ssend_mpi(void *buf, int count, MPI_Datatype datatype, int dest, int tag, MPI_Comm comm)
159  {
160    Debug("\nMPI_Ssend with MPI\n");
161    return ::MPI_Ssend(buf, count, to_mpi_type(datatype), dest, tag, to_mpi_comm(comm->mpi_comm));
162  }
163 
164
165  int MPI_Ssend_intercomm(void *buf, int count, MPI_Datatype datatype, int dest, int tag, MPI_Comm comm)
166  {
167    Debug("\nMPI_Ssend with EP_Intercomm\n");
168    MPI_Request request;
169    MPI_Status status;
170    MPI_Issend(buf, count, datatype, dest, tag, comm, &request);
171    MPI_Wait(&request, &status);
172    return MPI_SUCCESS;
173  }
174 
175  int MPI_Isend_mpi(const void *buf, int count, MPI_Datatype datatype, int dest, int tag, MPI_Comm comm, MPI_Request *request)
176  {
177    Debug("\nMPI_Isend with MPI\n");
178   
179    int src_rank;
180    MPI_Comm_rank(comm, &src_rank);
181   
182    *request = new ep_request;
183    memcheck("new "<< *request <<" : in ep_lib::MPI_Isend, *request = new ep_request");
184
185    (*request)->mpi_request = new ::MPI_Request;
186    memcheck("new "<< (*request)->mpi_request <<" : in ep_lib::MPI_Isend, (*request)->mpi_request = new ::MPI_Request");
187     
188    (*request)->ep_src = src_rank;
189    (*request)->ep_tag = tag;
190    (*request)->ep_datatype = datatype;
191    (*request)->type = 1;
192    (*request)->comm = comm;
193   
194    return ::MPI_Isend(buf, count, to_mpi_type(datatype), dest, tag, to_mpi_comm(comm->mpi_comm), to_mpi_request_ptr(*request));
195  }
196 
197  int MPI_Isend_intercomm(const void *buf, int count, MPI_Datatype datatype, int dest, int tag, MPI_Comm comm, MPI_Request *request)
198  {
199    Debug("MPI_Isend with EP_Intercomm\n");
200
201#ifdef _check_sum   
202    check_sum_send(buf, count, datatype, dest, tag, comm);
203#endif
204
205    int dest_remote_ep_rank    = comm->ep_comm_ptr->intercomm->remote_rank_map->at(dest).first;
206    int dest_remote_comm_label = comm->ep_comm_ptr->intercomm->remote_rank_map->at(dest).second;
207
208    int src_ep_rank    = comm->ep_comm_ptr->intercomm->size_rank_info[0].first;
209    int src_comm_label;
210
211    src_comm_label = comm->ep_comm_ptr->intercomm->local_rank_map->at(src_ep_rank).second;
212    //Message_Check(comm);
213
214    if(dest_remote_comm_label == src_comm_label)       // mpi_dest differs
215    {
216      int inter_src = comm->ep_comm_ptr->intercomm->local_rank_map->at(src_ep_rank).first;
217      int ep_src_loc = comm->ep_rank_map->at(inter_src).first;
218      int ep_dest_loc = comm->ep_rank_map->at(dest_remote_ep_rank).first;
219      int mpi_dest    = comm->ep_rank_map->at(dest_remote_ep_rank).second;
220      int mpi_tag = tag_combine(tag, ep_src_loc, ep_dest_loc);
221
222      *request = new ep_request;
223      memcheck("new "<< *request <<" : in ep_lib::MPI_Isend_intercomm, *request = new ep_request");
224
225      (*request)->mpi_request = new ::MPI_Request;
226      memcheck("new "<< (*request)->mpi_request <<" : in ep_lib::MPI_Isend_intercomm, (*request)->mpi_request = new ::MPI_Request");
227     
228      (*request)->type = 1;    // used in wait
229      (*request)->comm = comm;
230      (*request)->ep_src = src_ep_rank;
231      (*request)->ep_tag = tag;
232      (*request)->ep_datatype = datatype;
233
234      return ::MPI_Isend(buf, count, to_mpi_type(datatype), mpi_dest, mpi_tag, to_mpi_comm(comm->mpi_comm), to_mpi_request_ptr(*request));
235
236    }
237
238    else   // dest_remote_comm_label != src_comm_label
239    { 
240      int inter_src = comm->ep_comm_ptr->intercomm->local_rank_map->at(src_ep_rank).first;
241      int ep_src_loc = comm->ep_rank_map->at(inter_src).first;
242      int ep_dest_loc = comm->ep_comm_ptr->intercomm->intercomm_rank_map->at(dest_remote_ep_rank).first;
243      int mpi_dest    = comm->ep_comm_ptr->intercomm->intercomm_rank_map->at(dest_remote_ep_rank).second;
244      int mpi_tag = tag_combine(tag, ep_src_loc, ep_dest_loc);
245
246      *request = new ep_request;
247      memcheck("new "<< *request <<" : in ep_lib::MPI_Isend_intercomm, *request = new ep_request");
248
249      (*request)->mpi_request = new ::MPI_Request;
250      memcheck("new "<< (*request)->mpi_request <<" : in ep_lib::MPI_Isend_intercomm, (*request)->mpi_request = new ::MPI_Request");
251
252      (*request)->type = 1;    // used in wait
253      (*request)->comm = comm;
254      (*request)->ep_src = src_ep_rank;
255      (*request)->ep_tag = tag;
256      (*request)->ep_datatype = datatype;
257     
258      return ::MPI_Isend(buf, count, to_mpi_type(datatype), mpi_dest, mpi_tag, to_mpi_comm(comm->ep_comm_ptr->intercomm->mpi_inter_comm), to_mpi_request_ptr(*request)); 
259    }
260  }
261
262  int MPI_Issend_mpi(const void *buf, int count, MPI_Datatype datatype, int dest, int tag, MPI_Comm comm, MPI_Request *request)
263  {
264    Debug("\nMPI_Issend with MPI\n");
265   
266    int src_rank;
267    MPI_Comm_rank(comm, &src_rank);
268   
269    *request = new ep_request;
270    memcheck("new "<< *request <<" : in ep_lib::MPI_Issend, *request = new ep_request");
271
272    (*request)->mpi_request = new ::MPI_Request;
273    memcheck("new "<< (*request)->mpi_request <<" : in ep_lib::MPI_Issend, (*request)->mpi_request = new ::MPI_Request");
274     
275    (*request)->ep_src = src_rank;
276    (*request)->ep_tag = tag;
277    (*request)->ep_datatype = datatype;
278    (*request)->type = 1;
279    (*request)->comm = comm;
280   
281    return ::MPI_Issend(buf, count, to_mpi_type(datatype), dest, tag, to_mpi_comm(comm->mpi_comm), to_mpi_request_ptr(*request));
282  }
283
284
285  int MPI_Issend_intercomm(const void *buf, int count, MPI_Datatype datatype, int dest, int tag, MPI_Comm comm, MPI_Request *request)
286  {
287    Debug("MPI_Issend with EP_Intercomm\n");
288
289#ifdef _check_sum   
290    check_sum_send(buf, count, datatype, dest, tag, comm);
291#endif
292
293    int dest_remote_ep_rank    = comm->ep_comm_ptr->intercomm->remote_rank_map->at(dest).first;
294    int dest_remote_comm_label = comm->ep_comm_ptr->intercomm->remote_rank_map->at(dest).second;
295
296    int src_ep_rank    = comm->ep_comm_ptr->intercomm->size_rank_info[0].first;
297    int src_comm_label;
298
299    src_comm_label = comm->ep_comm_ptr->intercomm->local_rank_map->at(src_ep_rank).second;
300    //Message_Check(comm);
301
302    if(dest_remote_comm_label == src_comm_label)       // mpi_dest differs
303    {
304      int inter_src = comm->ep_comm_ptr->intercomm->local_rank_map->at(src_ep_rank).first;
305      int ep_src_loc = comm->ep_rank_map->at(inter_src).first;
306      int ep_dest_loc = comm->ep_rank_map->at(dest_remote_ep_rank).first;
307      int mpi_dest    = comm->ep_rank_map->at(dest_remote_ep_rank).second;
308      int mpi_tag = tag_combine(tag, ep_src_loc, ep_dest_loc);
309
310      *request = new ep_request;
311      memcheck("new "<< *request <<" : in ep_lib::MPI_Issend_intercomm, *request = new ep_request");
312
313      (*request)->mpi_request = new ::MPI_Request;
314      memcheck("new "<< (*request)->mpi_request <<" : in ep_lib::MPI_Issend_intercomm, (*request)->mpi_request = new ::MPI_Request");
315     
316      (*request)->type = 1;    // used in wait
317      (*request)->comm = comm;
318      (*request)->ep_src = src_ep_rank;
319      (*request)->ep_tag = tag;
320      (*request)->ep_datatype = datatype;
321
322      return ::MPI_Issend(buf, count, to_mpi_type(datatype), mpi_dest, mpi_tag, to_mpi_comm(comm->mpi_comm), to_mpi_request_ptr(*request));
323
324    }
325
326    else   // dest_remote_comm_label != src_comm_label
327    { 
328      int inter_src = comm->ep_comm_ptr->intercomm->local_rank_map->at(src_ep_rank).first;
329      int ep_src_loc = comm->ep_rank_map->at(inter_src).first;
330      int ep_dest_loc = comm->ep_comm_ptr->intercomm->intercomm_rank_map->at(dest_remote_ep_rank).first;
331      int mpi_dest    = comm->ep_comm_ptr->intercomm->intercomm_rank_map->at(dest_remote_ep_rank).second;
332      int mpi_tag = tag_combine(tag, ep_src_loc, ep_dest_loc);
333
334      *request = new ep_request;
335      memcheck("new "<< *request <<" : in ep_lib::MPI_Issend_intercomm, *request = new ep_request");
336
337      (*request)->mpi_request = new ::MPI_Request;
338      memcheck("new "<< (*request)->mpi_request <<" : in ep_lib::MPI_Issend_intercomm, (*request)->mpi_request = new ::MPI_Request");
339
340      (*request)->type = 1;    // used in wait
341      (*request)->comm = comm;
342      (*request)->ep_src = src_ep_rank;
343      (*request)->ep_tag = tag;
344      (*request)->ep_datatype = datatype;
345     
346      return ::MPI_Issend(buf, count, to_mpi_type(datatype), mpi_dest, mpi_tag, to_mpi_comm(comm->ep_comm_ptr->intercomm->mpi_inter_comm), to_mpi_request_ptr(*request)); 
347    }
348  }
349 
350}
351
352
353
354
355
356
Note: See TracBrowser for help on using the repository browser.