]> SALOME platform Git repositories - modules/med.git/blob - src/MEDMEM/MEDMEM_Med.cxx
Salome HOME
sources v1.2
[modules/med.git] / src / MEDMEM / MEDMEM_Med.cxx
1 //  MED MEDMEM : MED files in memory
2 //
3 //  Copyright (C) 2003  OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
4 //  CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS 
5 // 
6 //  This library is free software; you can redistribute it and/or 
7 //  modify it under the terms of the GNU Lesser General Public 
8 //  License as published by the Free Software Foundation; either 
9 //  version 2.1 of the License. 
10 // 
11 //  This library is distributed in the hope that it will be useful, 
12 //  but WITHOUT ANY WARRANTY; without even the implied warranty of 
13 //  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU 
14 //  Lesser General Public License for more details. 
15 // 
16 //  You should have received a copy of the GNU Lesser General Public 
17 //  License along with this library; if not, write to the Free Software 
18 //  Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA 
19 // 
20 //  See http://www.opencascade.org/SALOME/ or email : webmaster.salome@opencascade.org 
21 //
22 //
23 //
24 //  File   : MEDMEM_Med.cxx
25 //  Module : MED
26
27 using namespace std;
28 # include <string> 
29
30 # include "MEDMEM_Med.hxx"
31  
32 # include "MEDMEM_STRING.hxx"
33
34 # include "MEDMEM_Mesh.hxx"
35 # include "MEDMEM_Grid.hxx"
36 # include "MEDMEM_Field.hxx"
37
38 # include "MEDMEM_Exception.hxx"
39 # include "utilities.h"
40
41 /*!
42   Constructor.
43 */
44 MED::MED() {
45   MESSAGE("MED::MED()");
46 };
47
48 /*!
49   Constructor.
50 */
51 MED::MED(driverTypes driverType, const string & fileName)
52 {
53   const char * LOC = "MED::MED(driverTypes driverType, const string & fileName) : ";
54   BEGIN_OF(LOC);
55
56   MED_MED_RDONLY_DRIVER * myDriver = new MED_MED_RDONLY_DRIVER(fileName,this) ;
57   int current = addDriver(*myDriver);
58   //int current= addDriver(driverType,fileName);
59
60   _drivers[current]->open();
61   _drivers[current]->readFileStruct();
62   _drivers[current]->close();
63
64   END_OF(LOC);
65 };
66
67 /*!
68   Destructor.
69 */
70 MED::~MED()
71 {
72   const char * LOC = "MED::~MED() : ";
73   BEGIN_OF(LOC);
74
75   // Analysis of the object MED
76
77   int index;
78
79   map<FIELD_ *, MESH_NAME_>::const_iterator currentField;
80   index = 0;
81   for ( currentField=_meshName.begin();currentField != _meshName.end(); currentField++ ) {
82     if ( (*currentField).first != NULL) index++;
83   }
84
85   MESSAGE(LOC << " there is(are) " << index << " field(s):");
86   for ( currentField=_meshName.begin();currentField != _meshName.end(); currentField++ ) {
87     if ( (*currentField).first != NULL) MESSAGE("             " << ((*currentField).first)->getName().c_str());
88   }
89
90   map<MESH_NAME_, map<MED_FR::med_entite_maillage,SUPPORT *> >::iterator itSupportOnMesh ;
91   index = 0;
92   for ( itSupportOnMesh=_support.begin();itSupportOnMesh != _support.end(); itSupportOnMesh++ ) {
93     map<MED_FR::med_entite_maillage,SUPPORT *>::iterator itSupport ;
94     for ( itSupport=(*itSupportOnMesh).second.begin();itSupport!=(*itSupportOnMesh).second.end();itSupport++)
95       index++;
96   }
97
98   MESSAGE(LOC << " there is(are) " << index << " support(s):");
99
100   map<MESH_NAME_,MESH*>::const_iterator  currentMesh;
101   index =0;
102   for ( currentMesh=_meshes.begin();currentMesh != _meshes.end(); currentMesh++ ) {
103     if ( (*currentMesh).second != NULL)
104       index++;
105   }
106
107   MESSAGE(LOC << " there is(are) " << index << " meshe(s):");
108 //   for ( currentMesh=_meshes.begin();currentMesh != _meshes.end(); currentMesh++ ) {
109 //     if ( (*currentMesh).second != NULL)
110 //       {
111 //      SCRUTE((*currentMesh).second);
112
113 //      string meshName = ((*currentMesh).second)->getName();
114
115 //      MESSAGE("             " << meshName);
116 //       }
117 //   }
118
119   // delete all ? : PG : YES !
120   //  map<FIELD_ *, MESH_NAME_>::const_iterator currentField;
121   for ( currentField=_meshName.begin();currentField != _meshName.end(); currentField++ ) {
122     if ( (*currentField).first != NULL) {
123       // cast in right type to delete it !
124       switch ((*currentField).first->getValueType()) {
125       case MED_INT32 :
126         // mpv: such recursive destructors call is problematic for current ALLIANCES algorithms 
127         //delete (FIELD<int>*) (*currentField).first ;
128         break ;
129       case MED_REEL64 :
130         // mpv: such recursive destructors call is problematic for current ALLIANCES algorithms 
131         //delete (FIELD<double>*) (*currentField).first ;
132         break ;
133       default : 
134         INFOS("Field has type different of int or double, could not destroy its values array !") ;
135         // mpv: such recursive destructors call is problematic for current ALLIANCES algorithms 
136         //delete (*currentField).first;
137       }
138     }
139   }
140   //  map<MESH_NAME_, map<MED_FR::med_entite_maillage,SUPPORT *> >::iterator itSupportOnMesh ;
141   for ( itSupportOnMesh=_support.begin();itSupportOnMesh != _support.end(); itSupportOnMesh++ ) {
142     map<MED_FR::med_entite_maillage,SUPPORT *>::iterator itSupport ;
143     for ( itSupport=(*itSupportOnMesh).second.begin();itSupport!=(*itSupportOnMesh).second.end();itSupport++)
144         ;// mpv: such recursive destructors call is problematic for current ALLIANCES algorithms 
145         //delete (*itSupport).second ;
146   }
147
148   //  map<MESH_NAME_,MESH*>::const_iterator  currentMesh;
149   for ( currentMesh=_meshes.begin();currentMesh != _meshes.end(); currentMesh++ ) {
150     if ( (*currentMesh).second != NULL)
151       {
152         if (!((*currentMesh).second)->getIsAGrid())
153           ;// mpv: such recursive destructors call is problematic for current ALLIANCES algorithms 
154           //delete (*currentMesh).second;
155         else
156           ;// mpv: such recursive destructors call is problematic for current ALLIANCES algorithms 
157           //delete (GRID *) (*currentMesh).second;
158       }
159   }
160
161   index =_drivers.size();
162
163   MESSAGE(LOC << "In this object MED there is(are) " << index << " driver(s):");
164
165   for (int ind=0; ind < _drivers.size(); ind++ )
166     {
167       SCRUTE(_drivers[ind]);
168       if ( _drivers[ind] != NULL) delete _drivers[ind];
169     }
170
171
172
173   END_OF(LOC);
174 } ;
175
176 // ------- Drivers Management Part
177
178 // Add your new driver instance declaration here (step 3-1)
179 MED::INSTANCE_DE<MED_MED_RDWR_DRIVER> MED::inst_med ;
180 MED::INSTANCE_DE<VTK_MED_DRIVER> MED::inst_vtk ;
181
182 // Add your new driver instance in the MED instance list (step 3-2)
183 const MED::INSTANCE * const MED::instances[] = { &MED::inst_med, &MED::inst_vtk }; 
184
185 /*!
186   Create the specified driver and return its index reference to path to 
187   read or write methods.
188 */
189 int MED::addDriver(driverTypes driverType, const string & fileName="Default File Name.med") {
190
191   const char * LOC = "MED::addDriver(driverTypes driverType, const string & fileName=\"Default File Name.med\") : ";
192   GENDRIVER * driver;
193   int current;
194
195   BEGIN_OF(LOC);
196
197   MESSAGE(LOC << " the file name is " << fileName);
198   driver = instances[driverType]->run(fileName, this) ;
199   current = _drivers.size()-1;
200   driver->setId(current); 
201
202   END_OF(LOC);
203   return current;
204 }
205
206 /*!
207   Duplicate the given driver and return its index reference to path to 
208   read or write methods.
209 */
210 int  MED::addDriver(GENDRIVER & driver) {
211   const char * LOC = "MED::addDriver(GENDRIVER &) : ";
212   int current;
213
214   BEGIN_OF(LOC);
215   
216   SCRUTE(_drivers.size());
217
218   _drivers.push_back(&driver);
219
220   SCRUTE(_drivers.size());
221
222   SCRUTE(_drivers[0]);
223   SCRUTE(driver);
224
225   current = _drivers.size()-1;
226   driver.setId(current); 
227   
228   END_OF(LOC);
229   return current;
230   
231 }
232
233 /*!
234   Remove the driver referenced by its index.
235 */
236 void MED::rmDriver (int index/*=0*/)
237   throw (MED_EXCEPTION)
238 {
239   const char * LOC = "MED::rmDriver (int index=0): ";
240   BEGIN_OF(LOC);
241
242   if (_drivers[index])
243     //_drivers.erase(&_drivers[index]); 
244     {}
245   else
246     throw MED_EXCEPTION ( LOCALIZED( STRING(LOC) 
247                                      << "The index given is invalid, index must be between 0 and |" 
248                                      << _drivers.size()
249                                      )
250                           );   
251   END_OF(LOC);
252 }
253
254 /*!
255   ??? to do comment ???
256 */
257 void MED::writeFrom (int index/*=0*/)
258   throw (MED_EXCEPTION)
259 {
260   const char * LOC = "MED::write (int index=0): ";
261   BEGIN_OF(LOC);
262
263   if (_drivers[index]) {
264     // open and close are made by all objects !
265     _drivers[index]->writeFrom();
266   }
267   throw MED_EXCEPTION ( LOCALIZED( STRING(LOC) 
268                                    << "The index given is invalid, index must be between 0 and |" 
269                                    << _drivers.size()
270                                    )
271                         ); 
272   END_OF(LOC);
273 }; 
274
275 /*!
276   Write all objects with the driver given by its index.
277 */
278 void MED::write (int index/*=0*/)
279   throw (MED_EXCEPTION)
280 {
281   const char * LOC = "MED::write (int index=0): ";
282   BEGIN_OF(LOC);
283
284   if (_drivers[index]) {
285     // open and close are made by the subsequent objects !
286     _drivers[index]->write(); 
287   }
288   else
289     throw MED_EXCEPTION ( LOCALIZED( STRING(LOC) 
290                                      << "The index given is invalid, index must be between  0 and |" 
291                                      << _drivers.size()
292                                      )
293                           ); 
294   END_OF(LOC);
295 }; 
296
297 /*!
298   Parse all the file and generate empty object.
299
300   All object must be read explicitly later with their own method read 
301   or use MED::read to read all.
302
303   This method is automaticaly call by constructor with driver information.
304 */
305 void MED::readFileStruct (int index/*=0*/)
306   throw (MED_EXCEPTION)
307 {
308   const char * LOC = "MED::readFileStruct (int index=0): ";
309   BEGIN_OF(LOC);
310   
311   if (_drivers[index]) {
312     _drivers[index]->open(); 
313     _drivers[index]->readFileStruct(); 
314     _drivers[index]->close(); 
315   }
316   else
317     throw MED_EXCEPTION ( LOCALIZED( STRING(LOC) 
318                                      << "The index given is invalid, index must be between 0 and |" 
319                                      << _drivers.size()
320                                      )
321                           );   
322   END_OF(LOC);
323 }
324
325 /*!
326   Read all objects in the file specified in the driver given by its index.
327 */
328 void MED::read  (int index/*=0*/)
329   throw (MED_EXCEPTION)
330 {
331   const char * LOC = "MED::read (int index=0): ";
332   BEGIN_OF(LOC);
333   
334   if (_drivers[index]) {
335     // open and close are made by all objects !
336     SCRUTE(index);
337     SCRUTE(_drivers[index]);
338     SCRUTE(&_drivers[index]);
339     //    _drivers[index]->open();
340     _drivers[index]->read();
341     //    _drivers[index]->close();
342   }
343   else
344     throw MED_EXCEPTION ( LOCALIZED( STRING(LOC) 
345                                      << "The index given is invalid, index must be between  >0 and < |" 
346                                      << _drivers.size()-1 
347                                      )
348                           );  
349   END_OF(LOC);
350   
351 };
352
353 // ------- End Of Drivers Management Part
354
355 /*!
356   Get the number of MESH objects.
357 */
358 int      MED::getNumberOfMeshes ( void ) const {
359
360   const char * LOC = "MED::getNumberOfMeshes ( void ) const : ";
361   BEGIN_OF(LOC);
362
363   return _meshes.size();
364
365   END_OF(LOC);
366 };   
367     
368 /*!
369   Get the number of FIELD objects.
370 */
371 int      MED::getNumberOfFields ( void ) const {
372
373   const char * LOC = "MED::getNumberOfFields ( void ) const : ";
374   BEGIN_OF(LOC);
375
376   return _fields.size(); // we get number of field with different name
377
378   END_OF(LOC);
379 };       
380
381 /*!
382   Get the names of all MESH objects.
383
384   meshNames is an in/out argument.
385
386   It is a string array of size the
387   number of MESH objects. It must be allocated before calling
388   this method. All names are put in it.
389 */
390 void MED::getMeshNames      ( string * meshNames ) const
391   throw (MED_EXCEPTION)
392 {
393   const char * LOC = "MED::getMeshNames ( string * ) const : ";
394   BEGIN_OF(LOC);
395   int meshNamesSize;
396   
397   if (  ( meshNamesSize = sizeof(meshNames) / sizeof(string *) )
398        != _meshes.size() )
399     throw MED_EXCEPTION ( LOCALIZED( STRING(LOC) 
400                                      << "Size of parameter meshNames is |" 
401                                      << meshNamesSize    << "| and should be |" 
402                                      << _meshes.size() << "| and should be |" 
403                                      )
404                           );   
405   
406   // REM : ALLOCATION D'UN TABLEAU DE POINTEURS SUR STRING FAITE PAR LE CLIENT
407   map<MESH_NAME_,MESH*>::const_iterator  currentMesh; // ??ITERATEUR CONST SUR UN OBJET NON CONST ??
408
409   int meshNamesIndex = 0;
410
411   for ( currentMesh=_meshes.begin();currentMesh != _meshes.end(); currentMesh++ ) {
412     meshNames[meshNamesIndex]=(*currentMesh).first;
413     meshNamesIndex++;                               // CF OPTIMISATION
414   }
415
416   END_OF(LOC);
417 };
418
419 /*!
420   Get the names of all MESH objects.
421
422   Return a deque<string> object which contain the name of all MESH objects.
423 */
424 deque<string> MED::getMeshNames      () const {
425   
426   const char * LOC = "MED::getMeshNames () const : ";
427   BEGIN_OF(LOC);
428
429   deque<string> meshNames(_meshes.size());
430   
431   map<MESH_NAME_,MESH*>::const_iterator  currentMesh; // ??ITERATEUR CONST SUR UN OBJET NON CONST ??
432
433   int meshNamesIndex = 0;
434
435   for ( currentMesh=_meshes.begin();currentMesh != _meshes.end(); currentMesh++ ) {
436     meshNames[meshNamesIndex]=(*currentMesh).first;
437     meshNamesIndex++;                               // CF OPTIMISATION
438   }
439
440   END_OF(LOC);
441   return meshNames ;
442 };
443
444
445 /*!
446   Return a reference to the MESH object named meshName.
447 */
448 MESH   * MED::getMesh           ( const string & meshName )  const
449   throw (MED_EXCEPTION)
450 {
451
452   const char * LOC = "MED::getMesh ( const string & meshName ) const : ";
453   BEGIN_OF(LOC);
454
455   map<MESH_NAME_,MESH*>::const_iterator itMeshes =  _meshes.find(meshName);
456
457   if ( itMeshes == _meshes.end() )
458     throw MED_EXCEPTION ( LOCALIZED( STRING(LOC) 
459                                      << "There is no known mesh named |" 
460                                      << meshName << "|"
461                                      )
462                           );
463   
464   return (*itMeshes).second;
465   
466   END_OF(LOC);
467 }
468
469 /*!
470  \internal Return a reference to the MESH object associated with 
471  field argument.
472 */
473 MESH   * MED::getMesh           (const FIELD_ * const field ) const
474   throw (MED_EXCEPTION)
475 {
476  
477   const char * LOC = "MED::getMesh ( const FIELD * field ) const : ";
478   BEGIN_OF(LOC);
479
480   FIELD_ * f = const_cast< FIELD_* > (field);     //  Comment faire mieux ?
481   map<FIELD_ *, MESH_NAME_>::const_iterator itMeshName = _meshName.find(f);
482
483   if ( itMeshName  == _meshName.end() )
484     throw MED_EXCEPTION ( LOCALIZED( STRING(LOC) 
485                                      << "There is no known mesh associated with |" 
486                                      << field << "| pointer"
487                                      )
488                           );   
489   
490   string meshName = (*itMeshName).second;
491   map<MESH_NAME_,MESH*>::const_iterator itMeshes =  _meshes.find(meshName);
492   if ( itMeshes == _meshes.end() )
493     throw MED_EXCEPTION ( LOCALIZED( STRING(LOC) 
494                                      << "There is no known mesh named |"
495                                      << meshName << " while it's associated with the found field |" 
496                                      << field << "| pointer"
497                                      )
498                           );   
499   
500   return (*itMeshes).second;
501   
502   END_OF(LOC);
503 };
504
505
506 /*!
507   Get the names of all FIELD objects.
508
509   fieldNames is an in/out argument.
510
511   It is an array of string of size the
512   number of FIELD objects. It must be allocated before calling
513   this method. All names are put in it.
514 */
515 void MED::getFieldNames     ( string * fieldNames ) const
516   throw (MED_EXCEPTION)
517 {
518   const char * LOC = "MED::getFieldNames ( string * ) const : ";
519   BEGIN_OF(LOC);
520
521   int fieldNamesSize =  sizeof(fieldNames) / sizeof(string *);
522  
523   if ( fieldNamesSize != _fields.size() )
524     throw MED_EXCEPTION ( LOCALIZED( STRING(LOC) 
525                                      << "Size of parameter fieldNames is |" 
526                                      << fieldNamesSize     << "| and should be |" 
527                                      << _fields.size() << "| and should be |" 
528                                      )
529                           );   
530   
531   // REM : ALLOCATION D'UN TABLEAU DE POINTEURS SUR STRING FAITE PAR LE CLIENT
532   map<FIELD_NAME_,MAP_DT_IT_>::const_iterator  currentField;
533
534   int fieldNamesIndex = 0;
535   for ( currentField=_fields.begin();currentField != _fields.end(); currentField++ ) {
536     fieldNames[fieldNamesIndex]=(*currentField).first;
537     fieldNamesIndex++;                               // CF OPTIMISATION
538   }
539
540   END_OF(LOC);
541
542 };
543
544 /*!
545   Get the names of all FIELD objects.
546
547   Return a deque<string> object which contain the name of all FIELD objects.
548 */
549 deque<string> MED::getFieldNames     () const {
550
551   const char * LOC = "MED::getFieldNames ( ) const : ";
552   BEGIN_OF(LOC);
553
554   deque<string> fieldNames(_fields.size());
555
556   map<FIELD_NAME_,MAP_DT_IT_>::const_iterator  currentField;
557
558   int fieldNamesIndex = 0;
559
560   for ( currentField=_fields.begin();currentField != _fields.end(); currentField++ ) {
561     fieldNames[fieldNamesIndex]=(*currentField).first;
562     fieldNamesIndex++;                               // CF OPTIMISATION
563   }
564
565   END_OF(LOC);
566   return fieldNames ;
567 };
568
569 /*!
570   Return a deque<DT_IT_> which contain all iteration step for the FIELD 
571   identified by its name.
572 */
573 deque<DT_IT_> MED::getFieldIteration (const string & fieldName) const
574   throw (MED_EXCEPTION)
575 {
576
577   const char * LOC = "MED::getFieldIteration ( const string & ) const : ";
578   BEGIN_OF(LOC);
579
580   map<FIELD_NAME_,MAP_DT_IT_>::const_iterator itFields = _fields.find(fieldName);
581   
582   if ( itFields == _fields.end() ) 
583     throw MED_EXCEPTION ( LOCALIZED( STRING(LOC) 
584                                      << "There is no known field named |" 
585                                      << fieldName << "|"
586                                      )
587                           );   
588   //  const MAP_DT_IT_ & myIterationMap =  const_cast<const MAP_DT_IT_ & > ((*itFields).second);
589   const MAP_DT_IT_ & myIterationMap =  (*itFields).second ;
590   MAP_DT_IT_::const_iterator currentIterator ;
591   
592   deque<DT_IT_> Iteration(myIterationMap.size());
593   
594   int iterationIndex = 0;
595   
596   for ( currentIterator=myIterationMap.begin();currentIterator != myIterationMap.end(); currentIterator++ ) {
597     Iteration[iterationIndex]=(*currentIterator).first;
598     iterationIndex++;                               // CF OPTIMISATION
599   }
600
601   END_OF(LOC);
602   return Iteration ;
603 };
604
605 /*!
606  Return a reference to the FIELD object named fieldName with 
607  time step number dt and order number it.
608 */
609 FIELD_  * MED::getField          ( const string & fieldName, const int dt=MED_NOPDT, const int it=MED_NOPDT ) const
610   throw (MED_EXCEPTION)
611 {
612
613   const char * LOC = "MED::getField ( const string &, const int, const int ) const : ";
614   BEGIN_OF(LOC);
615
616   MESSAGE(LOC << "fieldName = "<<fieldName<<", dt ="<<dt<<", it = "<<it);
617
618   DT_IT_ dtIt;
619
620   dtIt.dt= dt;
621   dtIt.it= it;
622
623   map<FIELD_NAME_,MAP_DT_IT_>::const_iterator itFields = _fields.find(fieldName);
624
625   if ( itFields == _fields.end() ) 
626     throw MED_EXCEPTION ( LOCALIZED( STRING(LOC) 
627                                      << "There is no known field named |" 
628                                      << fieldName << "|"
629                                      )
630                           );   
631
632   const MAP_DT_IT_ & map_dtIt =  const_cast<const MAP_DT_IT_ & > ((*itFields).second);
633   MAP_DT_IT_::const_iterator itMap_dtIt =  map_dtIt.find(dtIt);
634
635   if ( itMap_dtIt == map_dtIt.end() )
636     throw MED_EXCEPTION ( LOCALIZED( STRING(LOC) 
637                                      << "There is no (dt,it) |("
638                                      << dt << "," << it << ")| associated with the found field |" 
639                                      << fieldName << "|"
640                                      )
641                           );   
642
643   END_OF(LOC);
644
645   //return _fields[fieldName][dtIt];
646   return (*itMap_dtIt).second;
647   
648 };
649
650
651 // fiend ostream & MED::operator<<(ostream &os,const MED & med) const {
652 //   return os;
653 // };
654
655 /*!
656   Return a map<MED_FR::med_entite_maillage,SUPPORT*> which contain 
657   foreach entity, a reference to the SUPPORT on all elements.
658 */
659 const map<MED_FR::med_entite_maillage,SUPPORT*> & MED::getSupports(const string & meshName) const
660   throw (MED_EXCEPTION)
661 {
662   const char * LOC = "MED::getSupports ( const string ) const : ";
663   BEGIN_OF(LOC);
664
665   map<MESH_NAME_, map<MED_FR::med_entite_maillage,SUPPORT *> >::const_iterator itSupportOnMesh = _support.find(meshName) ;
666   
667   if ( itSupportOnMesh == _support.end() )
668     throw MED_EXCEPTION ( LOCALIZED( STRING(LOC) 
669                                      << "There is no support on mesh named |" 
670                                      << meshName << "|"
671                                      )
672                           );
673   END_OF(LOC);
674   return (*itSupportOnMesh).second ;
675 }
676
677 /*!
678   Return a reference to the SUPPORT object on all elements of entity 
679   for the MESH named meshName.
680 */
681 SUPPORT *  MED::getSupport (const string & meshName,MED_FR::med_entite_maillage entity) const 
682   throw (MED_EXCEPTION)
683 {
684   const char * LOC = "MED::getSupport ( const string, MED_FR::med_entite_maillage ) const : ";
685   BEGIN_OF(LOC);
686
687   map<MESH_NAME_, map<MED_FR::med_entite_maillage,SUPPORT *> >::const_iterator itSupportOnMesh = _support.find(meshName) ;
688   
689   if ( itSupportOnMesh == _support.end() )
690     throw MED_EXCEPTION ( LOCALIZED( STRING(LOC) 
691                                      << "There is no support on mesh named |" 
692                                      << meshName << "|"
693                                      )
694                           );
695  
696   map<MED_FR::med_entite_maillage,SUPPORT *> & SupportOnMesh = (map<MED_FR::med_entite_maillage,SUPPORT *>&) ((*itSupportOnMesh).second) ;
697   map<MED_FR::med_entite_maillage,SUPPORT *>::const_iterator itSupport = SupportOnMesh.find(entity) ;
698   
699   if (itSupport == SupportOnMesh.end() )
700     throw MED_EXCEPTION ( LOCALIZED( STRING(LOC) 
701                                      << "There is no support on entity "
702                                      << entity << " in mesh named |" 
703                                      << meshName << "|"
704                                      )
705                           );
706   END_OF(LOC);
707   return (*itSupport).second ;
708 };
709
710 /*!
711   Temporary method : when all MESH objects are read, this methods 
712   update all SUPPORT objects with the rigth dimension.
713 */
714 void MED::updateSupport ()
715 {
716  
717   const char * LOC = "MED::updateSupport () : ";
718   BEGIN_OF(LOC);
719
720   map<MESH_NAME_, map<MED_FR::med_entite_maillage,SUPPORT *> >::iterator itSupportOnMesh ;
721   for ( itSupportOnMesh=_support.begin();itSupportOnMesh != _support.end(); itSupportOnMesh++ ) {
722     map<MED_FR::med_entite_maillage,SUPPORT *>::iterator itSupport ;
723     for ( itSupport=(*itSupportOnMesh).second.begin();itSupport!=(*itSupportOnMesh).second.end();itSupport++)
724       try {
725         (*itSupport).second->update() ;
726       }
727       catch (MEDEXCEPTION & ex) {
728         // entity not defined in mesh -> we remove support on it !
729         MESSAGE(LOC<<ex.what());
730         delete (*itSupport).second ;
731         (*itSupportOnMesh).second.erase(itSupport) ; // that's rigth ????
732         itSupport-- ;
733       }
734   }
735
736   END_OF(LOC);
737 }
738
739 /*!
740   Add the given MESH object. MED object control it,
741   and destroy it, so you must not destroy it after.
742
743   The meshName is given by the MESH object.
744 */
745 void MED::addMesh( MESH * const ptrMesh)
746   throw (MED_EXCEPTION)
747 {
748   const char * LOC = "MED::addMesh(const MESH * ptrMesh): ";
749   BEGIN_OF(LOC);
750
751   if ( ! ptrMesh ) 
752     throw MED_EXCEPTION ( LOCALIZED( STRING(LOC) << "ptrMesh must not be NULL !"));
753  
754   string meshName;
755   if ( ! ( meshName = ptrMesh->getName()).size() ) 
756     throw MED_EXCEPTION ( LOCALIZED( STRING(LOC) << "ptrMesh->_name must not be NULL !"));
757
758   _meshes[meshName] = ptrMesh; // if ptrMesh->meshName already exists it is modified
759
760   END_OF(LOC);
761 }
762
763 /*!
764   Add the given FIELD object. MED object control it,
765   and destroy it, so you must not destroy it after.
766
767   The fieldName is given by the FIELD object.
768 */
769 void MED::addField( FIELD_ * const ptrField)
770   throw (MED_EXCEPTION)
771 {
772   const char * LOC = "MED::addField(const FIELD_ * const ptrField): ";
773   BEGIN_OF(LOC);
774   
775   if ( ! ptrField ) 
776     throw MED_EXCEPTION ( LOCALIZED( STRING(LOC) << "ptrField must not be NULL !"));
777
778   string fieldName;
779   if ( ! (fieldName = ptrField->getName()).size() ) 
780     throw MED_EXCEPTION ( LOCALIZED( STRING(LOC) << "ptrField->_name must not be NULL !"));
781   
782   SUPPORT * ptrSupport;
783   if ( ! ( ptrSupport = (SUPPORT * ) ptrField->getSupport()) ) 
784     throw MED_EXCEPTION ( LOCALIZED( STRING(LOC) << "ptrField->_support must not be NULL !"));
785   
786   MESH * ptrMesh;
787   if ( ! ( ptrMesh = ptrSupport->getMesh()) ) 
788     throw MED_EXCEPTION ( LOCALIZED( STRING(LOC) << "ptrField->_support->_mesh must not be NULL !"));
789
790   string meshName;
791   if ( ! ( meshName = ptrMesh->getName()).size() ) 
792     throw MED_EXCEPTION ( LOCALIZED( STRING(LOC) << "ptrField->_support->_mesh->_name must not be NULL !"));
793
794   DT_IT_ dtIt;
795   dtIt.dt  = ptrField->getIterationNumber();
796   dtIt.it  = ptrField->getOrderNumber();
797                 
798   _fields   [fieldName][dtIt] = ptrField; // if it already exists it is replaced
799   _meshName [ptrField]        = meshName; // if it already exists it is replaced
800   _meshes   [meshName]        = ptrMesh;  // if it already exists it is replaced
801
802   int  numberOfTypes = ptrSupport->getNumberOfTypes();
803   _support  [meshName][ (MED_FR::med_entite_maillage) ptrSupport->getEntity()] = ptrSupport;// if it already exists it is replaced
804
805
806   END_OF(LOC);
807 }