PLE
Parallel Location and Exchange
ple_coupling.h
Go to the documentation of this file.
1 #ifndef __PLE_COUPLING_H__
2 #define __PLE_COUPLING_H__
3 
4 /*============================================================================
5  * Set up communication with coupled codes.
6  *============================================================================*/
7 
8 /*
9  This file is part of the "Parallel Location and Exchange" library,
10  intended to provide mesh or particle-based code coupling services.
11 
12  Copyright (C) 2005-2022 EDF S.A.
13 
14  This library is free software; you can redistribute it and/or
15  modify it under the terms of the GNU Lesser General Public
16  License as published by the Free Software Foundation; either
17  version 2.1 of the License, or (at your option) any later version.
18 
19  This library is distributed in the hope that it will be useful,
20  but WITHOUT ANY WARRANTY; without even the implied warranty of
21  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
22  Lesser General Public License for more details.
23 
24  You should have received a copy of the GNU Lesser General Public
25  License along with this library; if not, write to the Free Software
26  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
27 */
28 
29 /*----------------------------------------------------------------------------*/
30 
31 #include "ple_config.h"
32 
33 #if defined(PLE_HAVE_MPI)
34 #include <mpi.h>
35 #endif
36 
37 /*----------------------------------------------------------------------------
38  * Local headers
39  *----------------------------------------------------------------------------*/
40 
41 #include "ple_defs.h"
42 
43 /*----------------------------------------------------------------------------*/
44 
45 #ifdef __cplusplus
46 extern "C" {
47 #if 0
48 } /* Fake brace to force Emacs auto-indentation back to column 0 */
49 #endif
50 #endif /* __cplusplus */
51 
52 /*=============================================================================
53  * Macro definitions
54  *============================================================================*/
55 
56 /*
57  * Mask for synchronization flag
58  */
59 
60 /* Command bits */
61 
62 #define PLE_COUPLING_INIT (1 << 0)
64 #define PLE_COUPLING_NO_SYNC (1 << 1)
65 #define PLE_COUPLING_STOP (1 << 2)
66 #define PLE_COUPLING_LAST (1 << 3)
68 /* Time stepping bits */
69 
70 #define PLE_COUPLING_NEW_ITERATION (1 << 4)
71 #define PLE_COUPLING_REDO_ITERATION (1 << 5)
72 
103 #define PLE_COUPLING_TS_MIN (1 << 6)
104 #define PLE_COUPLING_TS_LEADER (1 << 7)
107 #define PLE_COUPLING_TS_FOLLOWER (1 << 15)
110 #define PLE_COUPLING_TS_INDEPENDENT (1 << 16)
114 /* Calculation type or state information bits */
115 
116 #define PLE_COUPLING_UNSTEADY (1 << 8)
117 #define PLE_COUPLING_STEADY (1 << 9)
118 #define PLE_COUPLING_CONVERGED (1 << 10)
119 
120 /* Optional user code information bits */
121 
122 #define PLE_COUPLING_USER_1 (1 << 11)
123 #define PLE_COUPLING_USER_2 (1 << 12)
124 #define PLE_COUPLING_USER_3 (1 << 13)
125 #define PLE_COUPLING_USER_4 (1 << 14)
126 
127 /*============================================================================
128  * Type definitions
129  *============================================================================*/
130 
131 #if defined(PLE_HAVE_MPI)
132 
133 /* Opaque code coupling information structure */
134 
135 typedef struct _ple_coupling_mpi_set_t ple_coupling_mpi_set_t;
136 
137 /* Info structure for code coupling */
138 
139 typedef struct {
140 
141  int status; /* Status flag for synchronization info */
142  int root_rank; /* Application root rank in MPI_COMM_WORLD */
143  int n_ranks; /* Number of ranks associated with application */
144  const char *app_type; /* Application type name (may be empty) */
145  const char *app_name; /* Application instance name (may be empty) */
146 
148 
149 #endif /* defined(PLE_HAVE_MPI) */
150 
151 /*=============================================================================
152  * Public function prototypes
153  *============================================================================*/
154 
155 #if defined(PLE_HAVE_MPI)
156 
157 /*----------------------------------------------------------------------------
158  * Build a group id within a communicator based on its name.
159  *
160  * If multiple groups are present, ids are number from 0 to n_groups - 1,
161  * based on the odering of group names. If all processes have the same
162  * group name, the returned value is -1.
163  *
164  * The returned id may typically be used as a "color" argument for
165  * MPI_Comm_split().
166  *
167  * As this function requires communication between applications, it
168  * is a collective function in comm.
169  *
170  * parameters:
171  * comm <-- MPI communicator.
172  * group_name <-- name associated with current group.
173  *
174  * returns:
175  * id associated with local name.
176  *----------------------------------------------------------------------------*/
177 
178 int
179 ple_coupling_mpi_name_to_id(MPI_Comm comm,
180  const char *group_name);
181 
182 /*----------------------------------------------------------------------------
183  * Discover other applications in a set with a common communicator.
184  *
185  * In most cases, the base communicator is MPI_COMM_WORLD, and the local
186  * application communicator app_comm is usually obtained from it using
187  * MPI_Comm_split, but other combinations may be possible using MPI-2
188  * process management functions.
189  *
190  * As this function requires communication between applications, it
191  * is a collective function in base_comm.
192  *
193  * parameters:
194  * sync_flag <-- 1 if application is to be synchronized at each
195  * time step, 0 if independent from others.
196  * app_type <-- name of current application type (software name).
197  * app_name <-- name of current application (data/case name).
198  * base_comm <-- communicator associated with all applications.
199  * app_comm <-- communicator associated with local application.
200  *
201  * returns:
202  * PLE coupling MPI set info structure.
203  *----------------------------------------------------------------------------*/
204 
205 ple_coupling_mpi_set_t *
206 ple_coupling_mpi_set_create(int sync_flag,
207  const char *app_type,
208  const char *app_name,
209  MPI_Comm base_comm,
210  MPI_Comm app_comm);
211 
212 /*----------------------------------------------------------------------------
213  * Free an PLE coupling MPI set info structure.
214  *
215  * parameters:
216  * s <-> pointer to structure that should be freed.
217  *----------------------------------------------------------------------------*/
218 
219 void
220 ple_coupling_mpi_set_destroy(ple_coupling_mpi_set_t **s);
221 
222 /*----------------------------------------------------------------------------
223  * Return the number of applications in a coupled set.
224  *
225  * parameters:
226  * s <-- pointer to PLE coupling MPI set info structure.
227  *
228  * returns:
229  * number of application in set's common communicator.
230  *----------------------------------------------------------------------------*/
231 
232 int
233 ple_coupling_mpi_set_n_apps(const ple_coupling_mpi_set_t *s);
234 
235 /*----------------------------------------------------------------------------
236  * Return the id of the local application in a coupled set.
237  *
238  * parameters:
239  * s <-- pointer to PLE coupling MPI set info structure.
240  *
241  * returns:
242  * id of the local application in set's common communicator.
243  *----------------------------------------------------------------------------*/
244 
245 int
246 ple_coupling_mpi_set_get_app_id(const ple_coupling_mpi_set_t *s);
247 
248 /*----------------------------------------------------------------------------
249  * Return application information in set's common communicator.
250  *
251  * parameters:
252  * s <-- pointer to PLE coupling MPI set info structure.
253  * app_id <-- application id
254  *
255  * returns:
256  * application information structure.
257  *----------------------------------------------------------------------------*/
258 
260 ple_coupling_mpi_set_get_info(const ple_coupling_mpi_set_t *s,
261  int app_id);
262 
263 /*----------------------------------------------------------------------------
264  * Synchronize applications in a set.
265  *
266  * Note that if a member of the set has used a PLE_COUPLING_STOP or
267  * PLE_COUPLING_LAST flag when calling ple_coupling_mpi_set_create() or
268  * or at the previous call to this function, it will not be synchronized
269  * anymore (i.e. the PLE_COUPLING_NO_SYNC flag will be added).
270  *
271  * parameters:
272  * s <-- pointer to PLE coupling MPI set info structure.
273  * sync_flag <-- synchronization info for current application.
274  * time_step <-- time step for current application.
275  *----------------------------------------------------------------------------*/
276 
277 void
278 ple_coupling_mpi_set_synchronize(ple_coupling_mpi_set_t *s,
279  int sync_flag,
280  double time_step);
281 
282 /*----------------------------------------------------------------------------
283  * Get status of applications in a set.
284  *
285  * This function allows access to the status flag of each synchronized
286  * application in the set. It may be used immediately after
287  * ple_coupling_mpi_set_create(), and flags are updated after each
288  * call to ple_coupling_mpi_set_synchronize().
289  *
290  * parameters:
291  * s <-- pointer to PLE coupling MPI set info structure.
292  *
293  * returns:
294  * a pointer to the set's array of status flags
295  *----------------------------------------------------------------------------*/
296 
297 const int *
298 ple_coupling_mpi_set_get_status(const ple_coupling_mpi_set_t *s);
299 
300 /*----------------------------------------------------------------------------
301  * Get time steps in a set.
302  *
303  * This function may be called after ple_coupling_mpi_set_synchronize()
304  * to query the time step values of each synchronized application in the set.
305  *
306  * parameters:
307  * s <-- pointer to PLE coupling MPI set info structure.
308  *
309  * returns:
310  * a pointer to the set's array of time steps
311  *----------------------------------------------------------------------------*/
312 
313 const double *
314 ple_coupling_mpi_set_get_timestep(const ple_coupling_mpi_set_t *s);
315 
316 /*----------------------------------------------------------------------------
317  * Compute recommended time step for the current application based on
318  * provided flags and values of applications in a set.
319  *
320  * The flags and values used to compute this recommended time step value
321  * are update at each call to ple_coupling_mpi_set_synchronize().
322  *
323  * parameters:
324  * s <-- pointer to PLE coupling MPI set info structure.
325  *
326  * returns:
327  * computed application time step
328  *----------------------------------------------------------------------------*/
329 
330 double
331 ple_coupling_mpi_set_compute_timestep(const ple_coupling_mpi_set_t *s);
332 
333 /*----------------------------------------------------------------------------
334  * Create an intracommunicator from a local and distant communicator
335  * within a base communicator.
336  *
337  * Note that if a member of the set has used a PLE_COUPLING_STOP or
338  * PLE_COUPLING_LAST flag when calling ple_coupling_mpi_set_create() or
339  * or at the previous call to this function, it will not be synchronized
340  * anymore (i.e. the PLE_COUPLING_NO_SYNC flag will be added).
341  *
342  * parameters:
343  * base_comm <-- communicator associated with both applications
344  * app_comm <-- communicator associated with local application
345  * distant_root <-- rank of distant group leader in base_comm
346  * new_comm --> pointer to new communicator
347  * local_range --> first and past-the last ranks of local application
348  * in new communicator
349  * distant_range --> first and past-the last ranks of distant application
350  * in new communicator
351  *----------------------------------------------------------------------------*/
352 
353 void
354 ple_coupling_mpi_intracomm_create(MPI_Comm base_comm,
355  MPI_Comm app_comm,
356  int distant_root,
357  MPI_Comm *new_comm,
358  int local_range[2],
359  int distant_range[2]);
360 
361 /*----------------------------------------------------------------------------*/
367 /*----------------------------------------------------------------------------*/
368 
369 MPI_Comm
370 ple_coupling_mpi_set_get_base_comm(const ple_coupling_mpi_set_t *s);
371 
372 /*----------------------------------------------------------------------------
373  * Dump printout of an PLE coupling MPI set info structure.
374  *
375  * parameters:
376  * w <-- pointer to PLE coupling MPI set info structure.
377  *----------------------------------------------------------------------------*/
378 
379 void
380 ple_coupling_mpi_set_dump(const ple_coupling_mpi_set_t *s);
381 
382 #endif /* defined(PLE_HAVE_MPI) */
383 
384 /*----------------------------------------------------------------------------*/
385 
386 #ifdef __cplusplus
387 }
388 #endif /* __cplusplus */
389 
390 #endif /* __PLE_COUPLING_H__ */
MPI_Comm ple_coupling_mpi_set_get_base_comm(const ple_coupling_mpi_set_t *s)
Get base communicator of an PLE coupling MPI set.
Definition: ple_coupling.c:1053
int ple_coupling_mpi_set_get_app_id(const ple_coupling_mpi_set_t *s)
Return the id of the local application in a coupled set.
Definition: ple_coupling.c:724
int ple_coupling_mpi_set_n_apps(const ple_coupling_mpi_set_t *s)
Return the number of applications in a coupled set.
Definition: ple_coupling.c:703
const double * ple_coupling_mpi_set_get_timestep(const ple_coupling_mpi_set_t *s)
Get time steps in a set.
Definition: ple_coupling.c:871
void ple_coupling_mpi_set_synchronize(ple_coupling_mpi_set_t *s, int sync_flag, double time_step)
Synchronize applications in a set.
Definition: ple_coupling.c:786
void ple_coupling_mpi_set_dump(const ple_coupling_mpi_set_t *s)
Dump printout of an PLE coupling MPI set info structure.
Definition: ple_coupling.c:1074
ple_coupling_mpi_set_t * ple_coupling_mpi_set_create(int sync_flag, const char *app_type, const char *app_name, MPI_Comm base_comm, MPI_Comm app_comm)
Discover other applications in a set with a common communicator.
Definition: ple_coupling.c:486
void ple_coupling_mpi_intracomm_create(MPI_Comm base_comm, MPI_Comm app_comm, int distant_root, MPI_Comm *new_comm, int local_range[2], int distant_range[2])
Create an intracommunicator from a local and distant communicator within a base communicator.
Definition: ple_coupling.c:976
void ple_coupling_mpi_set_destroy(ple_coupling_mpi_set_t **s)
Free an PLE coupling MPI set info structure.
Definition: ple_coupling.c:679
double ple_coupling_mpi_set_compute_timestep(const ple_coupling_mpi_set_t *s)
Compute recommended time step for the current application based on provided flags and values of appli...
Definition: ple_coupling.c:898
int ple_coupling_mpi_name_to_id(MPI_Comm comm, const char *group_name)
Build a group id within a communicator based on its name.
Definition: ple_coupling.c:313
ple_coupling_mpi_set_info_t ple_coupling_mpi_set_get_info(const ple_coupling_mpi_set_t *s, int app_id)
Return application information in set's common communicator.
Definition: ple_coupling.c:746
const int * ple_coupling_mpi_set_get_status(const ple_coupling_mpi_set_t *s)
Get status of applications in a set.
Definition: ple_coupling.c:846
Definition: ple_coupling.h:139
int n_ranks
Definition: ple_coupling.h:143
int status
Definition: ple_coupling.h:141
const char * app_type
Definition: ple_coupling.h:144
const char * app_name
Definition: ple_coupling.h:145
int root_rank
Definition: ple_coupling.h:142