~ubuntu-branches/ubuntu/precise/code-saturne/precise

« back to all changes in this revision

Viewing changes to src/fvm/fvm_parall.c

  • Committer: Package Import Robot
  • Author(s): Sylvestre Ledru
  • Date: 2011-11-24 00:00:08 UTC
  • mfrom: (6.1.9 sid)
  • Revision ID: package-import@ubuntu.com-20111124000008-2vo99e38267942q5
Tags: 2.1.0-3
Install a missing file

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
/*============================================================================
 
2
 * Base functions for parallelism
 
3
 *============================================================================*/
 
4
 
 
5
/*
 
6
  This file is part of Code_Saturne, a general-purpose CFD tool.
 
7
 
 
8
  Copyright (C) 1998-2011 EDF S.A.
 
9
 
 
10
  This program is free software; you can redistribute it and/or modify it under
 
11
  the terms of the GNU General Public License as published by the Free Software
 
12
  Foundation; either version 2 of the License, or (at your option) any later
 
13
  version.
 
14
 
 
15
  This program is distributed in the hope that it will be useful, but WITHOUT
 
16
  ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
 
17
  FOR A PARTICULAR PURPOSE.  See the GNU General Public License for more
 
18
  details.
 
19
 
 
20
  You should have received a copy of the GNU General Public License along with
 
21
  this program; if not, write to the Free Software Foundation, Inc., 51 Franklin
 
22
  Street, Fifth Floor, Boston, MA 02110-1301, USA.
 
23
*/
 
24
 
 
25
/*----------------------------------------------------------------------------*/
 
26
 
 
27
#if defined(HAVE_CONFIG_H)
 
28
#include "cs_config.h"
 
29
#endif
 
30
 
 
31
/*----------------------------------------------------------------------------
 
32
 * Standard C library headers
 
33
 *----------------------------------------------------------------------------*/
 
34
 
 
35
#include <assert.h>
 
36
#include <stdio.h>
 
37
 
 
38
/*----------------------------------------------------------------------------
 
39
 * BFT library headers
 
40
 *----------------------------------------------------------------------------*/
 
41
 
 
42
#include <bft_mem.h>
 
43
 
 
44
/*----------------------------------------------------------------------------
 
45
 *  Local headers
 
46
 *----------------------------------------------------------------------------*/
 
47
 
 
48
#include "fvm_config_defs.h"
 
49
#include "fvm_defs.h"
 
50
 
 
51
/*----------------------------------------------------------------------------
 
52
 *  Header for the current file
 
53
 *----------------------------------------------------------------------------*/
 
54
 
 
55
#include "fvm_parall.h"
 
56
 
 
57
/*----------------------------------------------------------------------------*/
 
58
 
 
59
#ifdef __cplusplus
 
60
extern "C" {
 
61
#if 0
 
62
} /* Fake brace to force back Emacs auto-indentation back to column 0 */
 
63
#endif
 
64
#endif /* __cplusplus */
 
65
 
 
66
/*============================================================================
 
67
 * Local structure definitions
 
68
 *============================================================================*/
 
69
 
 
70
/*============================================================================
 
71
 * Global variables
 
72
 *============================================================================*/
 
73
 
 
74
#if defined(HAVE_MPI)
 
75
 
 
76
/* Basic communicator info */
 
77
 
 
78
static MPI_Comm  _fvm_mpi_parall_comm = MPI_COMM_NULL;  /* Intra-communicator */
 
79
static int       _fvm_mpi_parall_size = 1;
 
80
static int       _fvm_mpi_parall_rank = 0;
 
81
 
 
82
/* MPI Datatypes associated with fvm datatypes */
 
83
 
 
84
MPI_Datatype  fvm_datatype_to_mpi[] = {MPI_DATATYPE_NULL,
 
85
                                       MPI_CHAR,
 
86
                                       MPI_FLOAT,
 
87
                                       MPI_DOUBLE,
 
88
                                       MPI_INT,            /* FVM_INT32 */
 
89
                                       MPI_LONG_INT,       /* FVM_INT64 */
 
90
                                       MPI_UNSIGNED,       /* FVM_UINT32 */
 
91
                                       MPI_UNSIGNED_LONG}; /* FVM_UINT64 */
 
92
 
 
93
/* Minimum recommended scatter/gather buffer size */
 
94
 
 
95
static size_t _fvm_parall_min_coll_buf_size = 1024*1024*8;
 
96
 
 
97
#endif
 
98
 
 
99
/*=============================================================================
 
100
 * Private function definitions
 
101
 *============================================================================*/
 
102
 
 
103
/*=============================================================================
 
104
 * Public function definitions
 
105
 *============================================================================*/
 
106
 
 
107
#if defined(HAVE_MPI)
 
108
 
 
109
/*----------------------------------------------------------------------------
 
110
 * Return default MPI communicator for FVM library functions.
 
111
 *
 
112
 * returns:
 
113
 *   handle to MPI communicator
 
114
 *----------------------------------------------------------------------------*/
 
115
 
 
116
MPI_Comm
 
117
fvm_parall_get_mpi_comm(void)
 
118
{
 
119
  return _fvm_mpi_parall_comm;
 
120
}
 
121
 
 
122
/*----------------------------------------------------------------------------
 
123
 * Set default MPI communicator for FVM library functions.
 
124
 *
 
125
 * parameters:
 
126
 *   comm <-- handle to MPI communicator
 
127
 *----------------------------------------------------------------------------*/
 
128
 
 
129
void
 
130
fvm_parall_set_mpi_comm(const MPI_Comm  comm)
 
131
{
 
132
  int mpi_flag;
 
133
 
 
134
  MPI_Initialized(&mpi_flag);
 
135
 
 
136
  /* Set communicator */
 
137
 
 
138
  _fvm_mpi_parall_comm = comm;
 
139
 
 
140
  if (mpi_flag != 0 && _fvm_mpi_parall_comm != MPI_COMM_NULL) {
 
141
    MPI_Comm_size(_fvm_mpi_parall_comm, &_fvm_mpi_parall_size);
 
142
    MPI_Comm_rank(_fvm_mpi_parall_comm, &_fvm_mpi_parall_rank);
 
143
  }
 
144
  else {
 
145
    _fvm_mpi_parall_size = 1;
 
146
    _fvm_mpi_parall_rank = 0;
 
147
  }
 
148
 
 
149
  /* Check (correct) fvm_datatype_to_mpi values */
 
150
 
 
151
  if (mpi_flag != 0)
 
152
  {
 
153
    int size_short, size_int, size_long, size_long_long;
 
154
 
 
155
    MPI_Type_size(MPI_SHORT, &size_short);
 
156
    MPI_Type_size(MPI_INT,   &size_int);
 
157
    MPI_Type_size(MPI_LONG,  &size_long);
 
158
 
 
159
#if defined(MPI_LONG_LONG)
 
160
    MPI_Type_size(MPI_LONG_LONG, &size_long_long);
 
161
#else
 
162
    size_long_long = 0;
 
163
#endif
 
164
 
 
165
    if (size_int == 4) {
 
166
      fvm_datatype_to_mpi[FVM_INT32] = MPI_INT;
 
167
      fvm_datatype_to_mpi[FVM_UINT32] = MPI_UNSIGNED;
 
168
    }
 
169
    else if (size_short == 4) {
 
170
      fvm_datatype_to_mpi[FVM_INT32] = MPI_SHORT;
 
171
      fvm_datatype_to_mpi[FVM_UINT32] = MPI_UNSIGNED_SHORT;
 
172
    }
 
173
    else if (size_long == 4) {
 
174
      fvm_datatype_to_mpi[FVM_INT32] = MPI_LONG;
 
175
      fvm_datatype_to_mpi[FVM_UINT32] = MPI_UNSIGNED_LONG;
 
176
    }
 
177
 
 
178
    if (size_int == 8) {
 
179
      fvm_datatype_to_mpi[FVM_INT64] = MPI_INT;
 
180
      fvm_datatype_to_mpi[FVM_UINT64] = MPI_UNSIGNED;
 
181
    }
 
182
    else if (size_long == 8) {
 
183
      fvm_datatype_to_mpi[FVM_INT64] = MPI_LONG;
 
184
      fvm_datatype_to_mpi[FVM_UINT64] = MPI_UNSIGNED_LONG;
 
185
    }
 
186
#if defined(MPI_LONG_LONG)
 
187
    else if (size_long_long == 8) {
 
188
      fvm_datatype_to_mpi[FVM_INT64] = MPI_LONG_LONG;
 
189
#if defined(MPI_UNSIGNED_LONG_LONG)
 
190
      fvm_datatype_to_mpi[FVM_UINT64] = MPI_UNSIGNED_LONG_LONG;
 
191
#else
 
192
      fvm_datatype_to_mpi[FVM_UINT64] = MPI_LONG_LONG;
 
193
#endif
 
194
    }
 
195
#endif
 
196
  }
 
197
 
 
198
}
 
199
 
 
200
#endif
 
201
 
 
202
/*----------------------------------------------------------------------------
 
203
 * Return rank of current process among associated program processes.
 
204
 *
 
205
 * returns:
 
206
 *   rank of current process in current communicator, or 0 in scalar mode
 
207
 *----------------------------------------------------------------------------*/
 
208
 
 
209
int
 
210
fvm_parall_get_rank(void)
 
211
{
 
212
#if defined(HAVE_MPI)
 
213
  return _fvm_mpi_parall_rank;
 
214
#else
 
215
  return 0;
 
216
#endif
 
217
}
 
218
 
 
219
/*----------------------------------------------------------------------------
 
220
 * Return number of processes associated with the current program.
 
221
 *
 
222
 * returns:
 
223
 *   number of processes in current communicator, or 1 in scalar mode
 
224
 *----------------------------------------------------------------------------*/
 
225
 
 
226
int
 
227
fvm_parall_get_size(void)
 
228
{
 
229
#if defined(HAVE_MPI)
 
230
  return _fvm_mpi_parall_size;
 
231
#else
 
232
  return 1;
 
233
#endif
 
234
}
 
235
 
 
236
#if defined(HAVE_MPI)
 
237
 
 
238
/*----------------------------------------------------------------------------
 
239
 * Sum counters on all FVM default communicator processes.
 
240
 *
 
241
 * parameters:
 
242
 *   cpt <-> local counter value  input, global counter value output (array)
 
243
 *   n   <-- number of counter array values
 
244
 *----------------------------------------------------------------------------*/
 
245
 
 
246
void
 
247
fvm_parall_counter(fvm_gnum_t  cpt[],
 
248
                   const int   n)
 
249
{
 
250
 
 
251
  if (_fvm_mpi_parall_size > 1) {
 
252
 
 
253
    int        i;
 
254
    fvm_gnum_t *sum;
 
255
    fvm_gnum_t _sum[64];
 
256
 
 
257
    if (n > 64)
 
258
      BFT_MALLOC(sum, n, fvm_gnum_t);
 
259
    else
 
260
      sum = _sum;
 
261
 
 
262
    MPI_Allreduce(cpt, sum, n, FVM_MPI_GNUM, MPI_SUM,
 
263
                  _fvm_mpi_parall_comm);
 
264
 
 
265
    for (i = 0; i < n ; i++)
 
266
      cpt[i] = sum[i];
 
267
 
 
268
    if (sum != _sum)
 
269
      BFT_FREE(sum);
 
270
 
 
271
  }
 
272
 
 
273
}
 
274
 
 
275
/*----------------------------------------------------------------------------
 
276
 * Maximum values of a counter on all FVM default communicator processes.
 
277
 *
 
278
 * parameters:
 
279
 *   cpt <-> local counter value  input, global counter value output (array)
 
280
 *   n   <-- number of counter array values
 
281
 *----------------------------------------------------------------------------*/
 
282
 
 
283
void
 
284
fvm_parall_counter_max(fvm_lnum_t  cpt[],
 
285
                       const int   n)
 
286
{
 
287
 
 
288
  if (_fvm_mpi_parall_size > 1) {
 
289
 
 
290
    int        i;
 
291
    fvm_lnum_t *maxval;
 
292
    fvm_lnum_t _maxval[64];
 
293
 
 
294
    if (n > 64)
 
295
      BFT_MALLOC(maxval, n, fvm_lnum_t);
 
296
    else
 
297
      maxval = _maxval;
 
298
 
 
299
    MPI_Allreduce(cpt, maxval, n, FVM_MPI_LNUM, MPI_MAX,
 
300
                  _fvm_mpi_parall_comm);
 
301
 
 
302
    for (i = 0; i < n ; i++)
 
303
      cpt[i] = maxval[i];
 
304
 
 
305
    if (maxval != _maxval)
 
306
      BFT_FREE(maxval);
 
307
 
 
308
  }
 
309
 
 
310
}
 
311
 
 
312
#endif /* defined(HAVE_MPI) */
 
313
 
 
314
/*----------------------------------------------------------------------------
 
315
 * Return minimum recommended scatter or gather buffer size.
 
316
 *
 
317
 * This is used by FVM's internal strided and indexed array scatter/gather
 
318
 * algorithms, for non MPI-IO Input/output.
 
319
 *
 
320
 * returns:
 
321
 *   minimum recommended gather buffer size (in bytes)
 
322
 *----------------------------------------------------------------------------*/
 
323
 
 
324
size_t
 
325
fvm_parall_get_min_coll_buf_size(void)
 
326
{
 
327
#if defined(HAVE_MPI)
 
328
  return _fvm_parall_min_coll_buf_size;
 
329
#else
 
330
  return 0;
 
331
#endif
 
332
}
 
333
 
 
334
/*----------------------------------------------------------------------------
 
335
 * Define minimum recommended gather buffer size.
 
336
 *
 
337
 * This is used by FVM's internal strided and indexed array scatter/gather
 
338
 * algorithms, for non MPI-IO Input/output.
 
339
 *
 
340
 * parameters:
 
341
 *   minimum recommended gather buffer size (in bytes)
 
342
 *----------------------------------------------------------------------------*/
 
343
 
 
344
void
 
345
fvm_parall_set_min_coll_buf_size(size_t buffer_size)
 
346
{
 
347
#if defined(HAVE_MPI)
 
348
  _fvm_parall_min_coll_buf_size = buffer_size;
 
349
#endif
 
350
}
 
351
 
 
352
/*----------------------------------------------------------------------------*/
 
353
 
 
354
#ifdef __cplusplus
 
355
}
 
356
#endif /* __cplusplus */