source: XMLIO_V2/dev/dev_rv/src4/xmlio/mpi/mpi_interface.cpp @ 242

Last change on this file since 242 was 242, checked in by hozdoba, 10 years ago

Ajout d'une partie d'Interface fortran pour la version 4

File size: 6.7 KB
Line 
1/* ************************************************************************** *
2 *      Copyright © IPSL/LSCE, XMLIOServer, Avril 2010 - Octobre 2011         *
3 * ************************************************************************** */
4 
5 /**
6 * \file    mpi_interface.hpp
7 * \brief   Gestion des communications MPI via une surcouche interne (implémentation).
8 * \author  Hervé Ozdoba
9 * \version 0.4
10 * \date    28 Juin 2011
11 */
12 
13// XMLIOServer headers
14#include "mpi_interface.hpp"
15
16// /////////////////////////////// Définitions ////////////////////////////// //
17
18namespace xmlioserver {
19namespace comm {
20
21   // ---------------------- Initialisation & Finalisation ---------------------
22
23   void CMPIManager::Initialise(int * _argc, char *** _argv)
24   {
25      int flag = 0;
26      if (MPI_Initialized(&flag) != MPI_SUCCESS)
27         XIOS_ERROR("CMPIManager::Initialise(arc, argv)", << " MPI Error !");
28      if (!flag)
29      {
30         if (MPI_Init(_argc, _argv) != MPI_SUCCESS)
31            XIOS_ERROR("CMPIManager::Initialise(arc, argv)", << " MPI Error !");
32      }
33
34   }
35   
36   void CMPIManager::Finalize(void)
37   {
38      if (MPI_Finalize() != MPI_SUCCESS)
39         XIOS_ERROR("CMPIManager::Finalize(void)", << " MPI Error !");
40   }
41   
42   // ------------------------------ Communicateurs ----------------------------
43   
44   int CMPIManager::GetCommRank(MPI_Comm _comm)
45   {
46      int rank = 0;
47      if (MPI_Comm_rank(_comm, &rank) != MPI_SUCCESS)
48         XIOS_ERROR("CMPIManager::GetCommRank(comm)", << " MPI Error !");
49      return (rank);
50   }
51   
52   int CMPIManager::GetCommSize(MPI_Comm _comm)
53   {
54      int size = 0;
55      if (MPI_Comm_size(_comm, &size) != MPI_SUCCESS)
56         XIOS_ERROR("CMPIManager::GetCommSize(comm)", << " MPI Error !");
57      return (size);
58   }
59   
60   MPI_Comm CMPIManager::CreateComm(MPI_Group _group, MPI_Comm _pcomm)
61   {
62      MPI_Comm commu;     
63      if (MPI_Comm_create(_pcomm, _group, &commu) != MPI_SUCCESS)
64         XIOS_ERROR("CMPIManager::CreateComm(group, pcomm)", << " MPI Error !");
65      return (commu);
66   }
67   
68   MPI_Comm CMPIManager::GetCommWorld(void)
69   {
70      return (MPI_COMM_WORLD); 
71   }
72   
73   // ---------------------------------- Autre ---------------------------------
74         
75   void CMPIManager::Barrier(MPI_Comm _comm)
76   {
77      if (MPI_Barrier(_comm) != MPI_SUCCESS)
78         XIOS_ERROR("CMPIManager::Barrier(comm)", << " MPI Error !");
79   }
80
81   // --------------------------------- Groupes --------------------------------
82         
83   MPI_Group CMPIManager::GetGroupWorld(void)
84   {
85      MPI_Group group = 0;
86      if (MPI_Comm_group(CMPIManager::GetCommWorld(), &group) != MPI_SUCCESS)
87         XIOS_ERROR("CMPIManager::GetGroupWorld()", << " MPI Error !");
88      return (group);
89   }
90   
91   MPI_Group CMPIManager::CreateSubGroup(MPI_Group _pgroup, const std::vector<int> & _ranks)
92   {
93      MPI_Group group = 0;
94      if (MPI_Group_incl(_pgroup, _ranks.size(), const_cast<int*>(&(_ranks[0])), &group) != MPI_SUCCESS)
95         XIOS_ERROR("CMPIManager::CreateSubGroup(pgroup, ranks)", << " MPI Error !");
96      return (group);
97   }
98   
99   MPI_Group CMPIManager::CreateSubGroup
100      (MPI_Group _pgroup, int _min_rank, int _max_rank, int _intval)
101   {
102      std::vector<int> ranks;
103      for (int i = _min_rank; i <= _max_rank; i += _intval)
104         ranks.push_back(i);
105      return (CMPIManager::CreateSubGroup(_pgroup, ranks));
106   }
107
108   // ----------------------------------- Tests --------------------------------
109         
110   bool CMPIManager::IsMaster(MPI_Comm _comm)
111   {
112      return (CMPIManager::GetCommRank(_comm) == 0); 
113   }
114   
115   bool CMPIManager::IsRank(int _rank, MPI_Comm _comm)
116   {
117      return (CMPIManager::GetCommRank(_comm) == _rank); 
118   }
119
120   // --------------------------- Communication simple -------------------------
121         
122   void CMPIManager::Send (MPI_Comm _comm, int _dest_rank, char * _data,
123                           std::size_t _size, MPI_Request & _request)
124   {
125      int nsize = _size;   
126      if (MPI_Issend(_data, nsize, MPI_CHAR, _dest_rank, 0, _comm, &_request) != MPI_SUCCESS)
127         XIOS_ERROR("CMPIManager::Send (comm, dest_rank, data, size, request)", << " MPI Error !");
128   }
129   
130   void CMPIManager::Wait (MPI_Request & _request)
131   {
132      MPI_Status status;
133      if (MPI_Wait(&_request, &status) != MPI_SUCCESS)
134         XIOS_ERROR("CMPIManager::Wait (request)", << " MPI Error !");
135   }
136   
137   bool CMPIManager::Test (MPI_Request & _request)
138   {
139      MPI_Status status;
140      int flag = 0;
141      if (MPI_Test(&_request, &flag, &status) != MPI_SUCCESS)
142         XIOS_ERROR("CMPIManager::Test (request)", << " MPI Error !");
143      return (flag);
144   }
145
146   bool CMPIManager::HasReceivedData(MPI_Comm _comm, int _src_rank)
147   {
148      MPI_Status status;
149      int flag = 0;
150      if (MPI_Iprobe(_src_rank, MPI_ANY_TAG, _comm, &flag, &status) != MPI_SUCCESS)
151         XIOS_ERROR("CMPIManager::HasReceivedData (comm, rank)", << " MPI Error !");
152      return (flag);
153   }
154   
155   std::size_t CMPIManager::GetReceivedDataSize(MPI_Comm _comm, int _src_rank)
156   {
157      MPI_Status status;
158      int flag = 0, size = 0;
159      if (MPI_Iprobe(_src_rank, MPI_ANY_TAG, _comm, &flag, &status) != MPI_SUCCESS)
160         XIOS_ERROR("CMPIManager::getReceivedDataSize (comm, rank)", << " MPI Error !");
161      if (!flag) return (0); 
162      if (MPI_Get_count(&status, MPI_CHAR, &size) != MPI_SUCCESS)
163         XIOS_ERROR("CMPIManager::getReceivedDataSize (comm, rank)", << " MPI Error !");
164
165      return (size);
166   }
167   
168   void CMPIManager::Receive(MPI_Comm _comm, int _src_rank, char * _data)
169   {
170      MPI_Request request = 0;
171      int size = CMPIManager::GetReceivedDataSize(_comm, _src_rank);
172      if (MPI_Irecv(_data, size, MPI_CHAR, _src_rank, MPI_ANY_TAG, _comm, &request) != MPI_SUCCESS)
173         XIOS_ERROR("CMPIManager::Receive (comm, src_rank, data)", << " MPI Error !");
174      CMPIManager::Wait (request); // Temporaire
175   }
176         
177   // ------------------------- Communication 'complexe' -----------------------
178         
179   //void SendLinearBuffer(MPIComm comm, int dest_rank, CLinearBuffer & buff, MPIRequest & request);
180   //void ReceiveLinearBuffer(MPIComm comm, int src_rank, CLinearBuffer & buff);
181   //boost::shared_ptr<CLinearBuffer> ReceiveLinearBuffer(MPIComm comm, int src_rank);
182   //void ReceiveCircularBuffer(MPIComm comm, int src_rank, CCircularBuffer & buff);
183
184   // ---------------------- Mémoire (non fonctionnel ....) --------------------
185         
186   void CMPIManager::AllocMemory(void * _data, std::size_t _size)
187   {
188      if (MPI_Alloc_mem(sizeof(char) * _size, MPI_INFO_NULL, _data) != MPI_SUCCESS)
189         XIOS_ERROR("CMPIManager::AllocMem(data, size)", << " MPI Error !");
190   }
191   
192   void CMPIManager::FreeMemory (void * _data)
193   {
194      MPI_Free_mem(_data);
195   }
196
197} // namespace comm
198} // namespace xmlioserver
199
Note: See TracBrowser for help on using the repository browser.