source: XIOS/trunk/src/interface/c/icdata.cpp @ 489

Last change on this file since 489 was 489, checked in by mhnguyen, 7 years ago

Ticket 50: Implementing the getting/setting methods for Fortran interface

+) Add some C and Fortran functions to set and get data to/from CVariable with an id
+) Add method to send, receive and dispatch in CVariable
+) Add dispatch method in server class

Test
-) On Curie
-) Test data: integer, float, double, boolean, string
-) File: one and multiple, using_server: ON and OFF
+) All test cases passed and had correct results

  • Property svn:eol-style set to native
File size: 15.7 KB
Line 
1/* ************************************************************************** *
2 *      Copyright © IPSL/LSCE, xios, Avril 2010 - Octobre 2011         *
3 * ************************************************************************** */
4
5#include <boost/multi_array.hpp>
6#include <boost/shared_ptr.hpp>
7#include <string>
8#include <cstring>
9#include <iostream>
10
11
12#include "xmlioserver.hpp"
13#include "oasis_cinterface.hpp"
14
15#include "attribute_template.hpp"
16#include "object_template.hpp"
17#include "group_template.hpp"
18
19#include "icutil.hpp"
20#include "cxios.hpp"
21#include "client.hpp"
22#include "field.hpp"
23#include "context.hpp"
24#include "context_client.hpp"
25#include "mpi.hpp"
26#include "timer.hpp"
27#include "array_new.hpp"
28
29
30extern "C"
31{
32// /////////////////////////////// Définitions ////////////////////////////// //
33
34   // ----------------------- Redéfinition de types ----------------------------
35
36   typedef enum { NETCDF4 = 0 } XFileType;
37
38   typedef xios::CContext * XContextPtr;
39
40   // -------------------- Traitement des données ------------------------------
41   void cxios_init_server(void)
42   {
43     CXios::initServerSide();
44   }
45
46   void cxios_init_client(const char * client_id , int len_client_id, MPI_Fint* f_local_comm, MPI_Fint* f_return_comm )
47   {
48      std::string str;
49      MPI_Comm local_comm ;
50      MPI_Comm return_comm ;
51
52      if (!cstr2string(client_id, len_client_id, str)) return;
53
54      int initialized ;
55      MPI_Initialized(&initialized) ;
56      if (initialized) local_comm=MPI_Comm_f2c(*f_local_comm) ;
57      else local_comm=MPI_COMM_NULL ;
58      CXios::initClientSide(str,local_comm,return_comm);
59      *f_return_comm=MPI_Comm_c2f(return_comm) ;
60      CTimer::get("XIOS init").suspend() ;
61      CTimer::get("XIOS").suspend() ;
62   }
63
64   void cxios_context_initialize(const char * context_id , int len_context_id, MPI_Fint* f_comm)
65   {
66     std::string str;
67     MPI_Comm comm ;
68
69     if (!cstr2string(context_id, len_context_id, str)) return;
70     CTimer::get("XIOS").resume() ;
71     CTimer::get("XIOS init context").resume() ;
72     comm=MPI_Comm_f2c(*f_comm) ;
73     CClient::registerContext(str,comm) ;
74     CTimer::get("XIOS init context").suspend() ;
75     CTimer::get("XIOS").suspend() ;
76   }
77
78   void cxios_context_is_initialized(const char * context_id , int len_context_id, bool* initialized)
79   {
80     std::string str;
81
82     if (!cstr2string(context_id, len_context_id, str)) return;
83     CTimer::get("XIOS").resume() ;
84     CContext* context = CContext::get(str,str) ;
85     *initialized=context->isInitialized() ;
86     CTimer::get("XIOS").suspend() ;
87   }
88
89    void cxios_context_close_definition()
90   {
91     CTimer::get("XIOS").resume() ;
92     CTimer::get("XIOS close definition").resume() ;
93     CContext* context = CContext::getCurrent() ;
94     context->closeDefinition() ;
95     CTimer::get("XIOS close definition").suspend() ;
96     CTimer::get("XIOS").suspend() ;
97   }
98
99   void cxios_context_finalize()
100   {
101     CTimer::get("XIOS").resume() ;
102     CTimer::get("XIOS context finalize").resume() ;
103     CContext* context = CContext::getCurrent() ;
104     context->finalize() ;
105     CTimer::get("XIOS context finalize").suspend() ;
106     CTimer::get("XIOS").suspend() ;
107   }
108
109   void cxios_finalize()
110   {
111     CTimer::get("XIOS").resume() ;
112     CTimer::get("XIOS finalize").resume() ;
113     CXios::clientFinalize() ;
114   }
115
116   void cxios_solve_inheritance()
117   {
118     CTimer::get("XIOS").resume() ;
119     CContext* context = CContext::getCurrent() ;
120     context->solveAllInheritance(false) ;
121     CTimer::get("XIOS").suspend() ;
122   }
123
124   /*! \brief This group of functions retrieve variable information from the configuration file (.xml)
125    *
126    * These functions provide intermediate C interfaces to get variable information of the configuration file (e.x iodef.xml),
127    * from a Fortran one, for example the value of a variable with id = "using_server".
128    * Each function corresponds to each basic type.
129    * \param varId        [in] id of the variable that we'd like to get
130    * \param varIdSize    [in] size of the variable type (integer, float, double, string)
131    * \param dataInt      [in/out] the retrieved data
132    * \param isVarExisted [in/out] Verify whether variable with varId exists
133   */
134   void cxios_get_variable_data_k8(const char * varId, int varIdSize, double * data, bool * isVarExisted)
135   {
136      std::string varIdStr;
137      if (!cstr2string(varId, varIdSize, varIdStr)) return;
138
139      CTimer::get("XIOS").resume();
140      CTimer::get("XIOS get variable data").resume();
141
142      CContext* context = CContext::getCurrent();
143      *isVarExisted = CVariable::has(context->getId(), varIdStr);
144
145      if (*isVarExisted)
146      {
147        *data = CVariable::get(context->getId(),varIdStr)->getData<double>();
148      }
149
150      CTimer::get("XIOS get variable data").suspend() ;
151      CTimer::get("XIOS").suspend() ;
152   }
153
154   void cxios_get_variable_data_k4(const char * varId, int varIdSize, float * data, bool * isVarExisted)
155   {
156      std::string varIdStr;
157      if (!cstr2string(varId, varIdSize, varIdStr)) return;
158
159      CTimer::get("XIOS").resume();
160      CTimer::get("XIOS get variable data").resume();
161
162      CContext* context = CContext::getCurrent();
163      *isVarExisted = CVariable::has(context->getId(), varIdStr);
164
165      if (*isVarExisted)
166      {
167        *data = CVariable::get(context->getId(),varIdStr)->getData<float>();
168      }
169
170      CTimer::get("XIOS get variable data").suspend() ;
171      CTimer::get("XIOS").suspend() ;
172   }
173
174   void cxios_get_variable_data_int(const char * varId, int varIdSize, int * data, bool * isVarExisted)
175   {
176      std::string varIdStr;
177      if (!cstr2string(varId, varIdSize, varIdStr)) return;
178
179      CTimer::get("XIOS").resume();
180      CTimer::get("XIOS get variable data").resume();
181
182      CContext* context = CContext::getCurrent();
183      *isVarExisted = CVariable::has(context->getId(), varIdStr);
184
185      if (*isVarExisted)
186      {
187        *data = CVariable::get(context->getId(),varIdStr)->getData<int>();
188      }
189
190      CTimer::get("XIOS get variable data").suspend() ;
191      CTimer::get("XIOS").suspend() ;
192   }
193
194   void cxios_get_variable_data_logic(const char * varId, int varIdSize, bool * data, bool * isVarExisted)
195   {
196      std::string varIdStr;
197      if (!cstr2string(varId, varIdSize, varIdStr)) return;
198
199      CTimer::get("XIOS").resume();
200      CTimer::get("XIOS get variable data").resume();
201
202      CContext* context = CContext::getCurrent();
203      *isVarExisted = CVariable::has(context->getId(), varIdStr);
204
205      if (*isVarExisted)
206      {
207        *data = CVariable::get(context->getId(),varIdStr)->getData<bool>();
208      }
209
210      CTimer::get("XIOS get variable data").suspend() ;
211      CTimer::get("XIOS").suspend() ;
212   }
213
214   void cxios_get_variable_data_char(const char * varId, int varIdSize, char * data, int dataSizeIn, bool * isVarExisted)
215   {
216      std::string varIdStr;
217      if (!cstr2string(varId, varIdSize, varIdStr)) return;
218
219      CTimer::get("XIOS").resume();
220      CTimer::get("XIOS get variable data").resume();
221
222      CContext* context = CContext::getCurrent();
223      *isVarExisted = CVariable::has(context->getId(), varIdStr);
224
225      if (*isVarExisted)
226      {
227        int dataSizeOut = CVariable::get(context->getId(),varIdStr)->getData<string>().length();
228        strncpy(data, CVariable::get(context->getId(),varIdStr)->getData<string>().c_str(), std::min(dataSizeIn, dataSizeOut));
229      }
230
231      CTimer::get("XIOS get variable data").suspend() ;
232      CTimer::get("XIOS").suspend() ;
233   }
234
235   /*! \brief This group of functions write information into existing variable in the configuration file (.xml)
236    *
237    *  These functions provide intermediate C interfaces to get variable information of the configuration file (e.x iodef.xml),
238    * from a Fortran one, for example the value of a variable with id = "using_server".
239    * Each function corresponds to each basic type.
240    * \param varId        [in] id of the variable that we'd like to get
241    * \param varIdSize    [in] size of the variable type (integer, float, double, string)
242    * \param data         [in] the input data
243    * \param isVarExisted [in/out] Verify whether variable with varId exists
244   */
245   void cxios_set_variable_data_k8(const char * varId, int varIdSize, double data, bool * isVarExisted)
246   {
247      std::string varIdStr;
248      if (!cstr2string(varId, varIdSize, varIdStr)) return;
249
250      CTimer::get("XIOS").resume();
251      CTimer::get("XIOS set variable data").resume();
252
253      CContext* context = CContext::getCurrent() ;
254      *isVarExisted = CVariable::has(context->getId(), varIdStr);
255
256      if (*isVarExisted)
257      {
258        CVariable::get(context->getId(),varIdStr)->setData<double>(data);
259        CVariable::get(context->getId(),varIdStr)->sendValue();
260      }
261
262      CTimer::get("XIOS set variable data").suspend() ;
263      CTimer::get("XIOS").suspend() ;
264   }
265
266   void cxios_set_variable_data_k4(const char * varId, int varIdSize, float data, bool * isVarExisted)
267   {
268      std::string varIdStr;
269      if (!cstr2string(varId, varIdSize, varIdStr)) return;
270
271      CTimer::get("XIOS").resume();
272      CTimer::get("XIOS set variable data").resume();
273
274      CContext* context = CContext::getCurrent() ;
275      *isVarExisted = CVariable::has(context->getId(), varIdStr);
276
277      if (*isVarExisted)
278      {
279        CVariable::get(context->getId(),varIdStr)->setData<float>(data);
280        CVariable::get(context->getId(),varIdStr)->sendValue();
281      }
282
283      CTimer::get("XIOS set variable data").suspend() ;
284      CTimer::get("XIOS").suspend() ;
285   }
286
287   void cxios_set_variable_data_int(const char * varId, int varIdSize, int data, bool * isVarExisted)
288   {
289      std::string varIdStr;
290      if (!cstr2string(varId, varIdSize, varIdStr)) return;
291
292      CTimer::get("XIOS").resume();
293      CTimer::get("XIOS set variable data").resume();
294
295      CContext* context = CContext::getCurrent() ;
296      *isVarExisted = CVariable::has(context->getId(), varIdStr);
297
298      if (*isVarExisted)
299      {
300        CVariable::get(context->getId(),varIdStr)->setData<int>(data);
301        CVariable::get(context->getId(),varIdStr)->sendValue();
302      }
303
304
305      CTimer::get("XIOS set variable data").suspend() ;
306      CTimer::get("XIOS").suspend() ;
307   }
308
309   void cxios_set_variable_data_logic(const char * varId, int varIdSize, bool data, bool * isVarExisted)
310   {
311      std::string varIdStr;
312      if (!cstr2string(varId, varIdSize, varIdStr)) return;
313
314      CTimer::get("XIOS").resume();
315      CTimer::get("XIOS set variable data").resume();
316
317      CContext* context = CContext::getCurrent() ;
318      *isVarExisted = CVariable::has(context->getId(), varIdStr);
319
320      if (*isVarExisted)
321      {
322        CVariable::get(context->getId(),varIdStr)->setData<bool>(data);
323        CVariable::get(context->getId(),varIdStr)->sendValue();
324      }
325
326      CTimer::get("XIOS set variable data").suspend() ;
327      CTimer::get("XIOS").suspend() ;
328   }
329
330   void cxios_set_variable_data_char(const char * varId, int varIdSize, const char * data, int dataSizeIn, bool * isVarExisted)
331   {
332      std::string varIdStr, dataStr;
333      if (!cstr2string(varId, varIdSize, varIdStr)) return;
334      if (!cstr2string(data, dataSizeIn, dataStr))
335      {
336        *isVarExisted = false;
337        return;
338      }
339
340      CTimer::get("XIOS").resume();
341      CTimer::get("XIOS set variable data").resume();
342
343      CContext* context = CContext::getCurrent() ;
344      *isVarExisted = CVariable::has(context->getId(), varIdStr);
345
346      if (*isVarExisted)
347      {
348        CVariable::get(context->getId(),varIdStr)->setData<string>(dataStr);
349        CVariable::get(context->getId(),varIdStr)->sendValue();
350      }
351
352      CTimer::get("XIOS set variable data").suspend() ;
353      CTimer::get("XIOS").suspend() ;
354   }
355
356
357   // ---------------------- Ecriture des données ------------------------------
358
359   void cxios_write_data_k81(const char * fieldid, int fieldid_size, double * data_k8, int data_Xsize)
360   {
361      std::string fieldid_str;
362      if (!cstr2string(fieldid, fieldid_size, fieldid_str)) return;
363
364      CTimer::get("XIOS").resume() ;
365      CTimer::get("XIOS send field").resume() ;
366      CContext* context = CContext::getCurrent() ;
367      if (!context->hasServer) context->client->checkBuffers() ;
368      CArray<double,(StdSize)1> data(data_k8,shape(data_Xsize),neverDeleteData) ;
369      CField::get(fieldid_str)->setData(data) ;
370      CField toto ;
371      toto.setData(data) ;
372      CTimer::get("XIOS send field").suspend() ;
373      CTimer::get("XIOS").suspend() ;
374   }
375
376   void cxios_write_data_k82(const char * fieldid, int fieldid_size, double * data_k8, int data_Xsize, int data_Ysize)
377   {
378      std::string fieldid_str;
379      if (!cstr2string(fieldid, fieldid_size, fieldid_str)) return;
380
381      CTimer::get("XIOS").resume() ;
382      CTimer::get("XIOS send field").resume() ;
383      CContext* context = CContext::getCurrent() ;
384      if (!context->hasServer) context->client->checkBuffers() ;
385
386      CArray<double,2>data(data_k8,shape(data_Xsize,data_Ysize),neverDeleteData) ;
387      CField::get(fieldid_str)->setData(data) ;
388      CTimer::get("XIOS send field").suspend() ;
389      CTimer::get("XIOS").suspend() ;
390   }
391
392   void cxios_write_data_k83(const char * fieldid, int fieldid_size, double * data_k8, int data_Xsize, int data_Ysize, int data_Zsize)
393   {
394      std::string fieldid_str;
395      if (!cstr2string(fieldid, fieldid_size, fieldid_str)) return;
396
397      CTimer::get("XIOS").resume() ;
398      CTimer::get("XIOS send field").resume() ;
399      CContext* context = CContext::getCurrent() ;
400      if (!context->hasServer) context->client->checkBuffers() ;
401
402      CArray<double,3>data(data_k8,shape(data_Xsize,data_Ysize,data_Zsize),neverDeleteData) ;
403      CField::get(fieldid_str)->setData(data) ;
404      CTimer::get("XIOS send field").suspend() ;
405      CTimer::get("XIOS").suspend() ;
406   }
407
408   void cxios_write_data_k41(const char * fieldid, int fieldid_size, float * data_k4, int data_Xsize)
409   {
410      std::string fieldid_str;
411     if (!cstr2string(fieldid, fieldid_size, fieldid_str)) return;
412
413      CTimer::get("XIOS").resume() ;
414      CTimer::get("XIOS send field").resume() ;
415      CContext* context = CContext::getCurrent() ;
416      if (!context->hasServer) context->client->checkBuffers() ;
417
418      CArray<float,1> data_tmp(data_k4,shape(data_Xsize),neverDeleteData) ;
419      CArray<double,1> data(data_Xsize) ;
420      data=data_tmp ;
421      CField::get(fieldid_str)->setData(data) ;
422      CTimer::get("XIOS send field").suspend() ;
423      CTimer::get("XIOS").suspend() ;
424   }
425
426   void cxios_write_data_k42(const char * fieldid, int fieldid_size, float * data_k4, int data_Xsize, int data_Ysize)
427   {
428      std::string fieldid_str;
429      if (!cstr2string(fieldid, fieldid_size, fieldid_str)) return;
430
431      CTimer::get("XIOS").resume() ;
432      CTimer::get("XIOS send field").resume() ;
433      CContext* context = CContext::getCurrent() ;
434      if (!context->hasServer) context->client->checkBuffers() ;
435
436      CArray<float,2> data_tmp(data_k4,shape(data_Xsize,data_Ysize),neverDeleteData) ;
437      CArray<double,2> data(data_Xsize,data_Ysize) ;
438      data=data_tmp ;
439      CField::get(fieldid_str)->setData(data) ;
440      CTimer::get("XIOS send field").suspend() ;
441      CTimer::get("XIOS").suspend() ;
442   }
443
444   void cxios_write_data_k43(const char * fieldid, int fieldid_size, float * data_k4, int data_Xsize, int data_Ysize, int data_Zsize)
445   {
446      std::string fieldid_str;
447
448      if (!cstr2string(fieldid, fieldid_size, fieldid_str)) return;
449
450      CTimer::get("XIOS").resume() ;
451      CTimer::get("XIOS send field").resume() ;
452      CContext* context = CContext::getCurrent() ;
453      if (!context->hasServer) context->client->checkBuffers() ;
454
455      CArray<float,3> data_tmp(data_k4,shape(data_Xsize,data_Ysize,data_Zsize),neverDeleteData) ;
456      CArray<double,3> data(data_Xsize,data_Ysize,data_Zsize) ;
457      data=data_tmp ;
458
459      CField::get(fieldid_str)->setData(data) ;
460      CTimer::get("XIOS send field").suspend() ;
461      CTimer::get("XIOS").suspend() ;
462
463    }
464
465} // extern "C"
Note: See TracBrowser for help on using the repository browser.