source: XMLIO_V2/dev/common/src/xmlio/manager/xios_manager.cpp @ 274

Last change on this file since 274 was 274, checked in by hozdoba, 13 years ago

nouvelle interface fortran et corrections

File size: 15.4 KB
Line 
1#include "xios_manager.hpp"
2
3#include "tree_manager.hpp"
4#include "data_treatment.hpp"
5#include "nc4_data_output.hpp"
6#include "attribute_template_impl.hpp"
7#include "group_template_impl.hpp"
8
9namespace xmlioserver
10{
11      /// ////////////////////// Définitions ////////////////////// ///
12     
13      void CXIOSManager::Initialise(XIOSType type, int * argc, char *** argv)
14      {
15         CXIOSManager::Type = type;
16         if (type != CLIENT)
17         {
18            // Initialisation de la biliothÚque MPI si nécessaire
19            comm::CMPIManager::Initialise(argc, argv);
20            ExeName = StdString((*argv)[0]);
21            for (int i = 1; i < *argc; i++)
22               ExeOptions.push_back(StdString((*argv)[i]));
23         }
24      }
25
26      void CXIOSManager::Finalize(void)
27      {
28         if (CXIOSManager::Type != CLIENT)
29         {
30            // Finalisation de la biliothÚque MPI si nécessaire
31            comm::CMPIManager::Finalize();
32         }
33      }
34
35      ///-------------------------------------------------------------
36
37      StdString CXIOSManager::ExeName("unknown");
38      std::vector<StdString> CXIOSManager::ExeOptions;
39
40      CXIOSManager::XIOSType   CXIOSManager::Type    = CLIENT;
41      CXIOSManager::XIOSStatus CXIOSManager::Status  = LOC_UNUSED;
42
43      StdString     CXIOSManager::ClientName("unknown name");
44      comm::MPIComm CXIOSManager::Comm_Client_Server = -1;
45      comm::MPIComm CXIOSManager::Comm_Server = -1;
46
47      xios_map<StdString, CXIOSManager::XIOSClient> CXIOSManager::Clients;
48
49      ///--------------------------------------------------------------
50     
51      void CXIOSManager::RunServer
52         (StdString clientName, comm::MPIComm comm_client_server, comm::MPIComm comm_server)
53      {
54         using namespace comm;
55         
56         // Reconstruction de l'arborescence d'objet à l'aide des données envoyées par chacun des
57         // clients associés à ce serveur.
58         std::vector<boost::shared_ptr<CLinearBuffer> > clientBuffer;
59         for (int i = 1; i < CMPIManager::GetCommSize(comm_client_server); i++)
60         {
61            while (!CMPIManager::HasReceivedData(comm_client_server, i)){}
62            clientBuffer.push_back(CMPIManager::ReceiveLinearBuffer(comm_client_server, i));
63         }
64         
65         // La quasi-totalité de l'arborescence est obtenue depuis les informations
66         // fournies par le client 1 du sous-groupe.
67         StdString main_data_tree = clientBuffer[0]->getString(0);       
68         tree::CTreeManager::FromBinary(main_data_tree);
69         std::cout << "main_data_tree" << main_data_tree.size() << std::endl;
70         
71         // Obtention des sous-domaines clients.
72         for (StdSize j = 1; j < clientBuffer.size(); j++)
73         {
74            main_data_tree = clientBuffer[j]->getString(0);
75            tree::CTreeManager::DomainsFromBinary(main_data_tree);
76         }
77         
78         StdOStringStream osss;
79         osss << StdString("./def_server_next.")
80              << CMPIManager::GetCommRank(CMPIManager::GetCommWorld());
81         CTreeManager::PrintTreeToFile(osss.str());
82
83         {  // Traitement de tous les contextes
84            StdString currentContextId = CObjectFactory::GetCurrentContextId();
85            std::vector<boost::shared_ptr<CContext> > def_vector =
86                                   CContext::GetContextGroup()->getChildList();
87            std::vector<boost::shared_ptr<CContext> >::iterator
88                               it = def_vector.begin(), end = def_vector.end();
89
90            //for (; it != end; it++ )
91            {
92               boost::shared_ptr<CContext> context = *it;
93               CTreeManager::SetCurrentContextId(context->getId());
94               boost::shared_ptr<data::CDataTreatment> dt(new data::CDataTreatment (context));
95               context->setDataTreatment(dt);
96               dt->createDataOutput<io::CNc4DataOutput>();
97            }
98            CTreeManager::SetCurrentContextId(currentContextId);
99         }
100       
101         StdOStringStream oss;
102         oss << StdString("./def_server_end.")
103             << CMPIManager::GetCommRank(CMPIManager::GetCommWorld());
104         CTreeManager::PrintTreeToFile(oss.str());     
105 
106      }
107     
108      //--------------------------------------------------------------
109     
110      void CXIOSManager::ShowInformation_CS(comm::MPIComm comm_client_server)
111      {
112         using namespace comm;
113         typedef std::pair<StdString, XIOSClient> StdPairStrClient;
114         if (CMPIManager::IsMaster(comm_client_server))
115         {
116            std::cout << " *************************************** " << std::endl
117                      << " *     XmlIOServer (Client/Server)     * " << std::endl
118                      << " *************************************** " << std::endl;
119            std::cout << " > Nombre de processus : "
120                      << CMPIManager::GetCommSize(comm_client_server) << std::endl;
121            std::cout << " > Nombre de processus utilisés : "
122                      << (CXIOSManager::GetNbClient() + CXIOSManager::GetNbServer()) << std::endl;
123            std::cout << " > Nombre de clients : "
124                      << CXIOSManager::GetNbClient() << std::endl;
125            std::cout << " > Nombre de serveurs : "
126                      << CXIOSManager::GetNbServer() << std::endl;
127
128            xios_map<StdString, XIOSClient>::iterator
129               iit  = CXIOSManager::Clients.begin(),
130               eend = CXIOSManager::Clients.end();
131
132            for (;iit != eend; iit++)
133            {
134               const StdPairStrClient & elem = *iit;
135               std::cout << " - " << elem.first
136                         << " > nombre de clients : "             
137                         << elem.second.nbClient
138                         << " , nombre de clients par serveur : " 
139                         << elem.second.nbClientPServer
140                         << " , nombre de serveurs : "           
141                         << elem.second.nbClient/elem.second.nbClientPServer
142                         << std::endl;
143            }
144
145            std::cout << " *************************************** " << std::endl;
146         }
147
148         comm::CMPIManager::Barrier();
149         
150      }
151     
152      //--------------------------------------------------------------
153     
154      void CXIOSManager::RunClientServer(comm::MPIComm comm_client_server)
155      {
156         using namespace comm;
157         typedef std::pair<StdString, XIOSClient> StdPairStrClient;
158         
159         CXIOSManager::ShowInformation_CS(comm_client_server);
160         
161         xios_map<StdString, XIOSClient>::iterator
162               iit  = CXIOSManager::Clients.begin(),
163               eend = CXIOSManager::Clients.end();
164         
165         StdSize start = 0, end   = 0;
166         
167         bool isClient = true, isIncl = false, isIncl_ = false;
168         MPIComm comm_client = 0, comm_client_grp = 0; comm_client_server = 0;
169
170         for (;iit != eend; iit++)
171         {
172            const StdPairStrClient & elem = *iit;
173
174            std::vector<int> clieindex, servindex ;
175            StdSize   currentRank      = CMPIManager::GetCommRank();
176            StdString clientName       = elem.first;
177            StdSize   nbClient         = elem.second.nbClient;
178            StdSize   nbClientPServer  = elem.second.nbClientPServer;
179            StdSize   nbServer         = (elem.second.nbClient)/(elem.second.nbClientPServer);
180
181            for (StdSize i = 0; i<nbServer; i++)
182            {
183               end = start + nbClientPServer;
184               MPIComm comm_  =  CMPIManager::CreateComm
185                  (CMPIManager::CreateSubGroup(CMPIManager::GetGroupWorld(), start, end));
186               MPIComm comm__ =  CMPIManager::CreateComm
187                  (CMPIManager::CreateSubGroup(CMPIManager::GetGroupWorld(), start+1, end));
188                 
189               servindex.push_back(start);
190               for (StdSize j = start+1; j <= end; j++)
191                  clieindex.push_back(j);
192                               
193               if ((currentRank >= start) && (currentRank <= end))
194               {
195                  comm_client_server = comm_;
196                  comm_client_grp    = comm__;
197                  isIncl = true;
198                  CXIOSManager::ClientName = clientName;
199                  CXIOSManager::Status = LOC_CLIENT;
200               }
201               if (currentRank == start)
202               {
203                  isClient = false; isIncl_  = true;
204                  CXIOSManager::Comm_Client_Server = comm_;
205                  CXIOSManager::Status = LOC_SERVER;
206               }               
207               if (clieindex.size() == nbClient)
208               {
209                  MPIComm comm___ = CMPIManager::CreateComm
210                  (CMPIManager::CreateSubGroup(CMPIManager::GetGroupWorld(), clieindex));
211                  if (isIncl) comm_client = comm___;
212                  clieindex.clear();
213                  isIncl = false;
214               }
215               
216               start = start + nbClientPServer + 1;
217            }
218            MPIComm comm____ = CMPIManager::CreateComm
219               (CMPIManager::CreateSubGroup(CMPIManager::GetGroupWorld(), servindex));
220            if (isIncl_) CXIOSManager::Comm_Server = comm____;               
221            servindex.clear();
222            isIncl_ = false;           
223         }
224         
225         if (isClient && (CXIOSManager::Clients.find(CXIOSManager::ClientName) !=
226                          CXIOSManager::Clients.end()))
227         {
228            CXIOSManager::Clients[CXIOSManager::ClientName].entry
229               (comm_client, comm_client_grp, comm_client_server);
230         }
231         else if(CXIOSManager::Clients.find(CXIOSManager::ClientName) !=
232                 CXIOSManager::Clients.end())
233         {
234            CXIOSManager::RunServer(CXIOSManager::ClientName, 
235                                    CXIOSManager::Comm_Client_Server,
236                                    CXIOSManager::Comm_Server);
237         }
238      }
239     
240      //---------------------------------------------------------------
241     
242      void CXIOSManager::RunClient(bool launch, comm::MPIComm comm_client)
243      {
244         if (launch)
245         {
246            CXIOSManager::Status  = LOC_CLIENT_SERVER;         
247            (CXIOSManager::Clients.begin()->second.entry)
248               (comm_client, comm_client, comm_client);
249         }
250         else
251         {
252            CXIOSManager::Status  = LOC_CLIENT;
253         }
254      }
255
256      //---------------------------------------------------------------
257
258      void CXIOSManager::AddClient(StdString clientName, StdSize nbClient, StdSize nbClientPServer,
259                                   void (*entry_point)(comm::MPIComm, comm::MPIComm, comm::MPIComm))
260      {
261         StdSize nbprocess  = comm::CMPIManager::GetCommSize(comm::CMPIManager::GetCommWorld());
262         StdSize nbprocess_used = CXIOSManager::GetNbClient() + CXIOSManager::GetNbServer();
263
264         if (nbClient < nbClientPServer)
265            ERROR("CXIOSManager::AddClient(...)", 
266                  << "nbClient < nbClientPServer");
267                 
268         if ((nbClient % nbClientPServer) != 0)
269            ERROR("CXIOSManager::AddClient(...)",
270                  << " (nbClient % nbClientPServer) != 0 !");
271                 
272         if ((nbprocess-nbprocess_used) < (nbClient + nbClient/nbClientPServer))
273            ERROR("CXIOSManager::AddClient(...)",
274                  << " Pas assez de processus disponibles !");
275                 
276         if (CXIOSManager::Clients.find(clientName) != CXIOSManager::Clients.end())
277            ERROR("CXIOSManager::AddClient(...)",
278                  << " Un client portant le même nom existe déjà !");
279
280         XIOSClient client = {nbClient, nbClientPServer, entry_point };
281         CXIOSManager::Clients[clientName] = client;
282      }
283
284      //---------------------------------------------------------------
285
286      StdSize CXIOSManager::GetNbClient(void)
287      {
288         switch (CXIOSManager::Type)
289         {
290            case (CLIENT_SERVER):
291            {
292               StdSize retvalue = 0;
293               typedef std::pair<StdString, XIOSClient> StdPairStrClient;
294               xios_map<StdString, XIOSClient>::iterator
295                  iit  = CXIOSManager::Clients.begin(),
296                  eend = CXIOSManager::Clients.end();
297
298               for (;iit != eend; iit++)
299               {
300                  const StdPairStrClient & elem = *iit;
301                  retvalue += CXIOSManager::GetNbLocClient(elem.first);
302               }
303               
304               return (retvalue);
305            }
306            case (CLIENT):
307               return (comm::CMPIManager::GetCommSize(CXIOSManager::Comm_Server));
308            case (SERVER):
309               return (comm::CMPIManager::GetCommSize(CXIOSManager::Comm_Client_Server) - 1);
310            default:
311               return (0);
312         }
313      }
314     
315      //---------------------------------------------------------------
316
317      StdSize CXIOSManager::GetNbLocClient(const StdString & clientName)
318      {
319         switch (CXIOSManager::Type)
320         {
321            case (CLIENT_SERVER):
322               return (CXIOSManager::Clients[clientName].nbClient);
323            case (CLIENT):
324            case (SERVER):
325               return (CXIOSManager::GetNbClient());
326            default:
327               return (0);
328         }
329      }
330
331      //---------------------------------------------------------------
332
333      StdSize CXIOSManager::GetNbServer(void)
334      {
335         switch (CXIOSManager::Type)
336         {
337            case (CLIENT_SERVER):
338            {
339               StdSize retvalue = 0;
340               typedef std::pair<StdString, XIOSClient> StdPairStrClient;             
341
342               xios_map<StdString, XIOSClient>::iterator
343                  iit  = CXIOSManager::Clients.begin(),
344                  eend = CXIOSManager::Clients.end();
345
346               for (;iit != eend; iit++)
347               {
348                  const StdPairStrClient & elem = *iit;
349                  retvalue += CXIOSManager::GetNbLocServer(elem.first);
350               }                 
351                 
352               return (retvalue);
353            }
354            case (CLIENT):
355               return (comm::CMPIManager::GetCommSize(CXIOSManager::Comm_Server));
356            case (SERVER):
357               return (1);
358            default:
359               return (0);
360         }
361      }
362
363      //---------------------------------------------------------------
364
365      StdSize CXIOSManager::GetNbLocServer(const StdString & clientName)
366      {
367         switch (CXIOSManager::Type)
368         {
369            case (CLIENT_SERVER):
370               return (CXIOSManager::Clients[clientName].nbClient /
371                       CXIOSManager::Clients[clientName].nbClientPServer);
372            case (CLIENT):
373            case (SERVER):
374               return (CXIOSManager::GetNbServer());
375            default:
376               return (0);
377         }
378      }
379     
380      //---------------------------------------------------------------
381     
382      CXIOSManager::XIOSType   CXIOSManager::GetType(void)
383      {
384         return (CXIOSManager::Type);
385      }
386     
387      //---------------------------------------------------------------
388     
389      CXIOSManager::XIOSStatus CXIOSManager::GetStatus(void)
390      {
391         return (CXIOSManager::Status);
392      }
393     
394      //---------------------------------------------------------------
395     
396      StdString  CXIOSManager::GetClientName(void)
397      {
398         return (CXIOSManager::ClientName);
399      }
400
401      ///--------------------------------------------------------------
402
403} // namespace xmlioserver
Note: See TracBrowser for help on using the repository browser.