source: XIOS/dev/dev_ym/XIOS_COUPLING/src/distribution/gatherer_connector.hpp @ 1995

Last change on this file since 1995 was 1995, checked in by ymipsl, 3 years ago

bug fix in gatherer connector
YM

  • Property svn:executable set to *
File size: 5.8 KB
Line 
1#ifndef __GATHERER_CONNECTOR_HPP__
2#define __GATHERER_CONNECTOR_HPP__
3
4#include "xios_spl.hpp"
5#include "array_new.hpp"
6#include "distributed_view.hpp"
7#include "mpi.hpp"
8#include "local_view.hpp"
9#include "distributed_view.hpp"
10#include "context_client.hpp"
11
12
13namespace xios
14{
15 
16  class CGathererConnector
17  {
18    private:
19      CDistributedView* srcView_;
20      CLocalView* dstView_;
21      map<int, vector<int>> connector_ ;
22      map<int, vector<bool>> mask_ ;  // mask is on src view
23      int dstSize_ ; 
24      map<int,int> srcSize_ ;
25
26    public:
27      CGathererConnector(CDistributedView* srcView, CLocalView* dstView) : srcView_(srcView), dstView_(dstView) {} ;
28      void computeConnector(void) ;
29     
30      template<typename T>
31      void transfer(int repeat, int sizeT, map<int, CArray<T,1>>& dataIn, CArray<T,1>& dataOut)
32      {
33        // for future, make a specific transfer function for sizeT=1 to avoid multiplication (increasing performance)
34        size_t dstSlice = dstSize_*sizeT ;
35        dataOut.resize(repeat* dstSlice) ; 
36       
37        for(auto& data : dataIn)
38        {
39          T* output = dataOut.dataFirst() ;
40          int rank=data.first ;
41          auto input  = data.second.dataFirst() ;
42          auto& connector=connector_[rank] ;
43          auto& mask=mask_[rank] ;
44          int size=mask.size() ;
45          size_t srcSlice = size * sizeT ;
46          for(int l=0; l<repeat; l++)
47          {   
48            for(int i=0, j=0 ;i<size;i++)
49            {
50              if (mask[i]) 
51              {
52                int cj = connector[j]*sizeT ;
53                int ci = i*sizeT ;
54                for (int k=0;k<sizeT;k++) output[cj+k] = input[ci+k] ;
55                j++ ;
56              }
57            }
58            input+=srcSlice ;
59            output+=dstSlice ;
60          }
61        }
62      }
63
64      template<typename T>
65      void transfer(int sizeT, map<int, CArray<T,1>>& dataIn, CArray<T,1>& dataOut)
66      {
67        transfer(1, sizeT, dataIn, dataOut) ;
68      }
69   
70      template<typename T>
71      void transfer(map<int, CArray<T,1>>& dataIn, CArray<T,1>& dataOut)
72      {
73        transfer(1,dataIn,dataOut) ;
74      }
75
76      template<typename T>
77      void transfer(int rank,  CGathererConnector** connectors, int nConnectors, const T* input, T* output)
78      {
79        auto& connector = connector_[rank] ; // probably costly, find a better way to avoid the map
80        auto& mask = mask_[rank] ; 
81        int srcSize = mask.size() ;
82     
83        if (nConnectors==0)
84        {
85          for(int i=0, j=0; i<srcSize; i++)
86            if (mask[i]) 
87            {
88              *(output+connector[j]) = *(input + i) ;
89              j++ ;
90            }
91
92        }
93        else
94       {
95          int srcSliceSize = (*(connectors-1))->getSrcSliceSize(rank, connectors-1, nConnectors-1) ;
96          int dstSliceSize = (*(connectors-1))->getDstSliceSize(connectors-1, nConnectors-1) ;
97
98          const T* in = input ; 
99          for(int i=0,j=0;i<srcSize;i++) 
100          {
101            if (mask[i]) 
102            {
103              (*(connectors-1))->transfer(rank, connectors-1, nConnectors-1, in, output+connector[j]*dstSliceSize) ; // the multiplication must be avoid in further optimization
104              j++ ;
105            }
106            in += srcSliceSize ;
107          }
108        }
109
110      }
111
112
113      template<typename T>
114      void transfer(map<int, CArray<T,1>>& dataIn, CArray<T,1>& dataOut, T missingValue)
115      {
116        transfer(1, 1, dataIn, dataout, missingValue)
117      }
118     
119      template<typename T>
120      void transfer(int sizeT, map<int, CArray<T,1>>& dataIn, CArray<T,1>& dataOut, T missingValue)
121      {
122         transfer(1, sizeT, dataIn, dataOut, missingValue) ;
123      }
124
125      template<typename T>
126      void transfer(int repeat , int sizeT, map<int, CArray<T,1>>& dataIn, CArray<T,1>& dataOut, T missingValue)
127      {
128        dataOut.resize(repeat*dstSize_*sizeT) ;
129        dataOut=missingValue ;
130        transfer(repeat, sizeT, dataIn, dataOut) ;
131      }
132
133      template<typename T>
134      void transfer(CEventServer& event, int sizeT, CArray<T,1>& dataOut)
135      {
136        map<int, CArray<T,1>> dataIn ;
137        for (auto& subEvent : event.subEvents) 
138        {
139          auto& data = dataIn[subEvent.rank]; 
140          (*subEvent.buffer) >> data ;
141        }
142        transfer(1, sizeT, dataIn, dataOut) ;
143      }
144     
145      template<typename T>
146      void transfer(CEventServer& event, CArray<T,1>& dataOut)
147      {
148        transfer(event, 1, dataOut) ;
149      }
150
151      template<typename T>
152      void transfer(CEventServer& event, int sizeT, CArray<T,1>& dataOut, T missingValue)
153      {
154        map<int, CArray<T,1>> dataIn ;
155        for (auto& subEvent : event.subEvents) 
156        {
157          auto& data = dataIn[subEvent.rank]; 
158          (*subEvent.buffer) >> data ;
159        }
160        transfer(1, sizeT, dataIn, dataOut, missingValue) ;
161      }
162
163      template<typename T>
164      void transfer(CEventServer& event, CArray<T,1>& dataOut, T missingValue)
165      {
166        map<int, CArray<T,1>> dataIn ;
167        for (auto& subEvent : event.subEvents) 
168        {
169          auto& data = dataIn[subEvent.rank]; 
170          (*subEvent.buffer) >> data ;
171        }
172        transfer(1, 1, dataIn, dataOut, missingValue) ;
173      }
174
175    int getSrcSliceSize(int rank, CGathererConnector** connectors, int nConnectors) 
176    { if (nConnectors==0) return srcSize_[rank] ; else return srcSize_[rank] * (*(connectors-1))->getSrcSliceSize(rank, connectors-1,nConnectors-1) ; }
177
178    int getDstSliceSize(CGathererConnector** connectors, int nConnectors) 
179    { if (nConnectors==0) return dstSize_ ; else return dstSize_ * (*(connectors-1))->getDstSliceSize(connectors-1,nConnectors-1) ; }
180 
181    int getDstSize(void) {return dstSize_ ;}
182  } ;
183
184}
185
186#endif
Note: See TracBrowser for help on using the repository browser.