source: XIOS/dev/dev_ym/XIOS_SERVICES/src/manager/servers_ressource.cpp @ 2243

Last change on this file since 2243 was 1764, checked in by ymipsl, 5 years ago

Some Update on XIOS services
Seems to work on Irène for :

  • first level of servers
  • fisrt + second level of servers
  • attached mode

YM

  • Property svn:eol-style set to native
  • Property svn:executable set to *
File size: 4.6 KB
Line 
1#include "servers_ressource.hpp"
2#include "window_manager.hpp"
3#include "ressources_manager.hpp"
4#include "pool_ressource.hpp"
5#include "cxios.hpp"
6#include "mpi.hpp"
7#include <vector>
8#include <string>
9
10
11
12
13namespace xios
14{
15  using namespace std ;
16
17  CServersRessource::CServersRessource(MPI_Comm serverComm) : poolRessource_(nullptr), finalizeSignal_(false)
18  {
19
20    MPI_Comm_dup(serverComm, &serverComm_) ;
21    MPI_Comm xiosComm=CXios::getXiosComm() ;
22 
23    int localRank, globalRank ;
24    MPI_Comm_rank(xiosComm,&globalRank) ;
25    MPI_Comm_rank(serverComm_,&localRank) ;
26   
27    winNotify_ = new CWindowManager(serverComm_, maxBufferSize_) ;
28
29    if (localRank==localLeader_) 
30    {
31      int commSize ;
32      MPI_Comm_size(serverComm_,&commSize) ;
33      CXios::getRessourcesManager()->registerServerLeader(globalRank) ;
34      CXios::getRessourcesManager()->registerRessourcesSize(commSize) ;
35      freeRessourcesRank_.resize(commSize) ;
36      for(int i=0;i<commSize;i++) freeRessourcesRank_[i]=i ;
37    }
38
39    MPI_Comm_dup(serverComm_, &freeRessourcesComm_) ;   
40  }
41
42  void CServersRessource::createPool(const string& poolId, const int size)
43  {
44    int commSize ;
45    MPI_Comm_size(serverComm_,&commSize) ;
46    vector<int> newFreeRessourcesRank(freeRessourcesRank_.size()-size) ;
47
48    bool isPartOf ;
49
50    for(int i=0; i<freeRessourcesRank_.size();i++) 
51    {
52       if (i<size) isPartOf=true ;
53       else 
54       {
55         isPartOf=false ;
56         newFreeRessourcesRank[i]=freeRessourcesRank_[i] ;
57       }
58       
59       notifyOutType_=NOTIFY_CREATE_POOL ;
60       notifyOutCreatePool_ = make_tuple(poolId, isPartOf) ;
61       sendNotification(freeRessourcesRank_[i]) ;
62    }
63    freeRessourcesRank_ = std::move(newFreeRessourcesRank) ;
64  }
65
66  void CServersRessource::finalize(void)
67  {
68    int commSize ;
69    MPI_Comm_size(serverComm_,&commSize) ;
70
71    for(int rank=0; rank<commSize;rank++)
72    { 
73      notifyOutType_=NOTIFY_FINALIZE ;
74      sendNotification(rank) ;
75    }
76  }
77
78  void CServersRessource::sendNotification(int rank)
79  {
80    winNotify_->lockWindow(rank,0) ;
81    winNotify_->pushToWindow(rank, this, &CServersRessource::notificationsDumpOut) ;
82    winNotify_->unlockWindow(rank,0) ;
83  }
84
85
86  void CServersRessource::notificationsDumpOut(CBufferOut& buffer)
87  {
88   
89    buffer.realloc(maxBufferSize_) ;
90   
91    if (notifyOutType_==NOTIFY_CREATE_POOL)
92    {
93      auto& arg=notifyOutCreatePool_ ;
94      buffer << notifyOutType_ << std::get<0>(arg) << std::get<1>(arg) ;
95    }
96    else if (notifyOutType_==NOTIFY_FINALIZE) buffer << notifyOutType_ ;
97  }
98
99  void CServersRessource::notificationsDumpIn(CBufferIn& buffer)
100  {
101    if (buffer.bufferSize() == 0) notifyInType_= NOTIFY_NOTHING ;
102    else
103    {
104      buffer>>notifyInType_;
105      if (notifyInType_==NOTIFY_CREATE_POOL)
106      {
107        auto& arg=notifyInCreatePool_ ;
108        buffer >> std::get<0>(arg) >> std::get<1>(arg)  ;
109      }
110      else if (notifyInType_==NOTIFY_FINALIZE) { /*nothing to do*/}
111    }
112  }
113
114  bool CServersRessource::eventLoop(bool serviceOnly)
115  {
116    checkNotifications() ;
117    if (poolRessource_!=nullptr) 
118    {
119      if (poolRessource_->eventLoop(serviceOnly))
120      {
121        poolRessource_=nullptr ;
122        // don't forget to free pool ressource later
123      } 
124    }
125
126    if (poolRessource_==nullptr && finalizeSignal_) return true ;
127    else return false ;
128  }
129
130  void CServersRessource::checkNotifications(void)
131  {
132    int commRank ;
133    MPI_Comm_rank(serverComm_, &commRank) ;
134    winNotify_->lockWindow(commRank,0) ;
135    winNotify_->popFromWindow(commRank, this, &CServersRessource::notificationsDumpIn) ;
136    winNotify_->unlockWindow(commRank,0) ;
137    if (notifyInType_==NOTIFY_CREATE_POOL) createPool() ;
138    else if (notifyInType_==NOTIFY_FINALIZE) finalizeSignal() ;
139  }
140
141  void CServersRessource::createPool(void)
142  {
143    auto& arg=notifyInCreatePool_ ;
144    string poolId=get<0>(arg) ;
145    bool isPartOf=get<1>(arg) ;
146   
147    int commRank ;
148    MPI_Comm poolComm ;
149    MPI_Comm_rank(freeRessourcesComm_,&commRank) ;
150    MPI_Comm_split(freeRessourcesComm_, isPartOf, commRank, &poolComm) ;
151   
152    if (isPartOf)
153    { 
154      poolRessource_ = new CPoolRessource(poolComm, poolId) ;
155      MPI_Comm_free(&poolComm) ;
156    }
157    else 
158    {
159      MPI_Comm_free(&freeRessourcesComm_) ;
160      freeRessourcesComm_=poolComm ;
161    }
162
163  }
164 
165  void CServersRessource::finalizeSignal(void)
166  {
167    finalizeSignal_=true ;
168    if (poolRessource_!=nullptr) poolRessource_->finalizeSignal() ;
169  }
170
171  bool CServersRessource::isServerLeader(void)
172  {
173    int commRank ;
174    MPI_Comm_rank(serverComm_,&commRank) ;
175    if (commRank==localLeader_) return true ;
176    else return false ;
177  }
178}
Note: See TracBrowser for help on using the repository browser.