2
/*******************************************************
4
* Copyright (c) 2003-2010 by University of Queensland
5
* Earth Systems Science Computational Center (ESSCC)
6
* http://www.uq.edu.au/esscc
8
* Primary Business: Queensland, Australia
9
* Licensed under the Open Software License version 3.0
10
* http://www.opensource.org/licenses/osl-3.0.php
12
*******************************************************/
26
/* allocate memory for an mpi_comm, and find the communicator details */
27
Esys_MPIInfo* Esys_MPIInfo_alloc( MPI_Comm comm )
33
Esys_MPIInfo *out=NULL;
35
out = MEMALLOC( 1, Esys_MPIInfo );
37
out->reference_counter = 0;
38
out->msg_tag_counter = 0;
40
error = MPI_Comm_rank( comm, &out->rank )==MPI_SUCCESS && MPI_Comm_size( comm, &out->size )==MPI_SUCCESS;
42
Esys_setError( ESYS_MPI_ERROR, "Esys_MPIInfo_alloc : error finding comm rank/size" );
51
out->reference_counter++;
56
/* free memory for an mpi_comm */
57
void Esys_MPIInfo_free( Esys_MPIInfo *in )
59
if( in && !(--in->reference_counter) )
63
Esys_MPIInfo *Esys_MPIInfo_getReference( Esys_MPIInfo* in )
66
++(in->reference_counter);
70
/* N = #CPUs, k is a CPU number but out of range or even negative. Return a CPU number in 0...n-1. */
71
index_t Esys_MPIInfo_mod(index_t n, index_t k)
85
void Esys_MPIInfo_Split( Esys_MPIInfo *mpi_info, dim_t N, dim_t* local_N,index_t* offset)
94
(*offset)=(*local_N)*r;
96
(*offset)=(*local_N)*r+rest;
101
dim_t Esys_MPIInfo_setDistribution(Esys_MPIInfo* mpi_info ,index_t min_id,index_t max_id,index_t* distribution) {
104
int s=mpi_info->size;
105
dim_t N=max_id-min_id+1;
109
for (p=0; p<s; ++p) {
111
distribution[p]=min_id+(local_N+1)*p;
114
distribution[p]=min_id+rest+local_N*p;
117
distribution[s]=max_id+1;
124
for (p=0; p<s+1; ++p) distribution[p]=min_id;
129
/* checks that there is no error accross all processes in a communicator */
130
/* NOTE : does not make guarentee consistency of error string on each process */
131
bool_t Esys_MPIInfo_noError( Esys_MPIInfo *mpi_info )
133
int errorLocal = Esys_noError() ? 0 : 1;
134
int errorGlobal = errorLocal;
136
return (errorGlobal==0);
139
/**************************************************
141
**************************************************/
143
int Esys_MPIInfo_initialized( void )
146
int error=0, initialised=0;
147
error = MPI_Initialized( &initialised );
148
if( error!=MPI_SUCCESS )
149
Esys_setError( ESYS_MPI_ERROR, "mpi_initialised : MPI error" );
156
/* Append MPI rank to file name if multiple MPI processes */
157
char *Esys_MPI_appendRankToFileName(const char *fileName, int mpi_size, int mpi_rank) {
158
/* Make plenty of room for the mpi_rank number and terminating '\0' */
159
char *newFileName = TMPMEMALLOC(strlen(fileName)+20,char);
160
strncpy(newFileName, fileName, strlen(fileName)+1);
161
if (mpi_size>1) sprintf(newFileName+strlen(newFileName), ".%04d", mpi_rank);