Salome HOME
1fb5f45e183ef4fb6c37402f11a2e0cac6267196
[modules/kernel.git] / src / DataTypeCatalog / SALOME_DataTypeCatalog_impl.cxx
1 //  SALOME DataTypeCatalog : catalog of data types
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   : SALOME_DataTypeCatalog_impl.cxx
25 //  Author : Estelle Deville
26 //  Module : SALOME
27 //  $Header$
28
29 using namespace std;
30 #include "SALOME_DataTypeCatalog_impl.hxx"
31 #include "Utils_ExceptHandlers.hxx"
32 #include <fstream>
33
34 UNEXPECT_CATCH(DTC_NotFound, SALOME_DataTypeCatalog::NotFound);
35
36 //----------------------------------------------------------------------
37 // Function : SALOME_DataTypeCatalogImpl
38 // Purpose  : Constructor 
39 //----------------------------------------------------------------------
40 SALOME_DataTypeCatalogImpl::SALOME_DataTypeCatalogImpl(int argc, char** argv)
41 {
42   MESSAGE("DataType Catalog creation");
43
44   // Empty used variables
45   _datatype_list.resize(0);
46
47   // Parse the arguments given at server run
48   if (!_parseArguments(argc, argv,&_path_datatype))
49     MESSAGE( "Error while argument parsing" )
50
51   // Test existency of files
52   if (_path_datatype == NULL)
53     MESSAGE( "Error the data type catalog should be indicated" )
54   else
55     {
56       MESSAGE("Parse data type catalog");
57       // Affect the variable _datatype_list 
58       _parse_xml_file(_path_datatype,_datatype_list);
59
60       // Verification of _datatype_list content
61       if(!_verify_data_type(_datatype_list))
62         MESSAGE( "Error while parsing the data type list" )
63       else MESSAGE("Data Type list OK");
64     }
65 }
66
67 //----------------------------------------------------------------------
68 // Function : ~SALOME_DataTypeCatalogImpl
69 // Purpose  : Destructor 
70 //----------------------------------------------------------------------
71 SALOME_DataTypeCatalogImpl::~SALOME_DataTypeCatalogImpl()
72 {
73   MESSAGE("DataType Catalog Destruction");
74 }
75
76
77 //----------------------------------------------------------------------
78 // Function : GetDataTypeList
79 // Purpose  : get a data type name list
80 //----------------------------------------------------------------------
81 SALOME_DataTypeCatalog::ListOfDataTypeName* 
82 SALOME_DataTypeCatalogImpl::GetDataTypeList()
83 {
84   MESSAGE("Begin of GetDataTypeList");
85   SALOME_DataTypeCatalog::ListOfDataTypeName_var _list_data = 
86     new SALOME_DataTypeCatalog::ListOfDataTypeName;
87
88   _list_data->length(_datatype_list.size());
89
90   // Duplicate each data type name defined in the catalog
91   for (unsigned int ind=0; ind < _datatype_list.size();ind++)
92     {
93        _list_data[ind]=CORBA::string_dup(_datatype_list[ind].Parserdata_name.c_str());
94        // SCRUTE(_list_data[ind]) ;
95     }
96
97   return _list_data._retn();
98 }
99
100 //----------------------------------------------------------------------
101 // Function : isDerivedFrom
102 // Purpose  : return true if type_out is derived from type_in
103 //----------------------------------------------------------------------
104 CORBA::Boolean 
105 SALOME_DataTypeCatalogImpl::isDerivedFrom(const char* type_in,
106                                           const char* type_out)
107                             throw(SALOME_DataTypeCatalog::NotFound)
108 {
109   Unexpect aCatch(DTC_NotFound);
110   CORBA::Boolean _return_value = false ;
111   bool _found_in = false;
112   bool _found_out = false;
113   for (unsigned int ind=0; ind < _datatype_list.size();ind++)
114     {
115       if (strcmp((_datatype_list[ind].Parserdata_name).c_str(),type_out) == 0)
116         {
117           //type_out found
118           _found_out = true;
119           // Looking if type_in is indicated in the parents list
120           _return_value = _explore_parents(type_in,_datatype_list[ind]); 
121         }
122       if (strcmp((_datatype_list[ind].Parserdata_name).c_str(),type_in) == 0)
123         _found_in = true;
124     }
125
126   if(!_found_in)
127     {
128       MESSAGE("The data type " << type_in << " was not found in the data type catalog")
129       throw SALOME_DataTypeCatalog::NotFound() ;
130     }
131   if(!_found_out)
132     {
133       MESSAGE( "The data type " << type_out << " was not found in the data type catalog")
134       throw SALOME_DataTypeCatalog::NotFound() ;
135     }
136
137   return _return_value;
138
139 }
140
141 //----------------------------------------------------------------------
142 // Function : GetDataInterfaceRead
143 // Purpose  : get the read interface name
144 //----------------------------------------------------------------------
145 char*
146 SALOME_DataTypeCatalogImpl::GetDataInterfaceRead(const char* type)
147                             throw(SALOME_DataTypeCatalog::NotFound)
148 {
149   Unexpect aCatch(DTC_NotFound);
150   char* return_value = NULL;
151   bool _find = false;
152   for (unsigned int ind=0; ind < _datatype_list.size();ind++)
153     {
154       if (strcmp((_datatype_list[ind].Parserdata_name).c_str(),type) == 0)
155         {
156           _find = true;
157           return_value =  CORBA::string_dup(_datatype_list[ind].Parserdata_interface_read.c_str());
158         }
159     }
160   
161   // NotFound Exceptin is thrown if the data type indicated is not found in the catalog
162   if(!_find)
163     {
164       MESSAGE( "The data type " << type << " was not found in the data type catalog")
165       throw SALOME_DataTypeCatalog::NotFound() ;
166     }
167
168   return return_value;
169 }
170
171 //----------------------------------------------------------------------
172 // Function : GetDataInterfaceWrite
173 // Purpose  : get the write interface name
174 //----------------------------------------------------------------------
175 char*
176 SALOME_DataTypeCatalogImpl::GetDataInterfaceWrite(const char* type)
177                             throw(SALOME_DataTypeCatalog::NotFound)
178 {
179   Unexpect aCatch(DTC_NotFound);
180   char* return_value = NULL;
181   bool _find = false;
182   for (unsigned int ind=0; ind < _datatype_list.size();ind++)
183     {
184       if (strcmp((_datatype_list[ind].Parserdata_name).c_str(),type) == 0)
185         {
186           _find = true;
187           return_value =  CORBA::string_dup(_datatype_list[ind].Parserdata_interface_write.c_str());
188         }
189     }
190
191   // NotFound Exceptin is thrown if the data type indicated is not found in the catalog
192   if(!_find)
193     {
194       MESSAGE( "The data type " << type << " was not found in the data type catalog")
195       throw SALOME_DataTypeCatalog::NotFound() ;
196     }
197   return return_value;
198 }
199
200 //----------------------------------------------------------------------
201 // Function : GetDataTypeParents
202 // Purpose  : get Parents data type name list
203 //----------------------------------------------------------------------
204 SALOME_DataTypeCatalog::ListOfDataTypeName* 
205 SALOME_DataTypeCatalogImpl::GetDataTypeParents(const char* type) throw(SALOME_DataTypeCatalog::NotFound)
206 {
207   Unexpect aCatch(DTC_NotFound);
208
209   bool _find = false ;
210
211   SALOME_DataTypeCatalog::ListOfDataTypeName_var _list_data = 
212     new SALOME_DataTypeCatalog::ListOfDataTypeName;
213
214   for (unsigned int ind=0; ind < _datatype_list.size();ind++)
215     {
216       if (strcmp((_datatype_list[ind].Parserdata_name).c_str(),type) == 0)
217         {
218           // Wanted type is found
219           // Get all the parents data type name of the type
220           _find = true; 
221           _list_data->length(_datatype_list[ind].Parserdata_parents.size());
222           for (unsigned int ind1=0; ind1 < _datatype_list[ind].Parserdata_parents.size();ind1++)
223             {
224               _list_data[ind1]=CORBA::string_dup(_datatype_list[ind].Parserdata_parents[ind1].c_str());
225               // SCRUTE(_list_data[ind1]) ;
226             }
227         }
228     }
229
230   // NotFound Exception is thrown if the data type indicated is not found 
231   // in the catalog
232   if(!_find)
233     {
234       MESSAGE( "The data type " << type << " was not found in the data type catalog")
235       throw SALOME_DataTypeCatalog::NotFound() ;
236     }
237
238   return _list_data._retn();
239 }
240
241 //----------------------------------------------------------------------
242 // Function : _explore_parents
243 // Purpose  : return true if type_out is derived from type_in
244 //----------------------------------------------------------------------
245 CORBA::Boolean 
246 SALOME_DataTypeCatalogImpl::_explore_parents(const char* type_in,
247                                              ParserDataType& data_out)
248 {
249
250   MESSAGE( "Begin of _explore_parents with data_out_name  " << data_out.Parserdata_name);
251
252   CORBA::Boolean found = false ;
253   if (data_out.Parserdata_name == type_in)
254     found = true ;
255   else
256     if (data_out.Parserdata_parents.size() >0)
257       for (unsigned int ind=0; ind < data_out.Parserdata_parents.size();ind++)
258         {
259           if (data_out.Parserdata_parents[ind] == type_in)
260             found = true ;
261           else
262             for (unsigned ip =0; ip < _datatype_list.size();ip++)
263               {
264                 // run _explore_parents for each parent data of data_out
265                 if (_datatype_list[ip].Parserdata_name == data_out.Parserdata_parents[ind])
266                   found = _explore_parents(type_in, _datatype_list[ip]);
267               }
268         }
269   return found ;
270 }
271
272 //----------------------------------------------------------------------
273 // Function : _parse_xml_file
274 // Purpose  : parse one module catalog 
275 //----------------------------------------------------------------------
276 void 
277 SALOME_DataTypeCatalogImpl::_parse_xml_file(const char* file,
278                                             ListOfParserDataType& datatypelist) 
279 {
280   SALOME_DataTypeCatalog_Handler* handler = new SALOME_DataTypeCatalog_Handler();
281   QFile xmlFile(file);
282
283   QXmlInputSource source(xmlFile);
284
285   QXmlSimpleReader reader;
286   reader.setContentHandler( handler );
287   reader.setErrorHandler( handler );
288   reader.parse( source );
289   xmlFile.close();
290   datatypelist = _datatypelist;
291 }
292
293
294 //----------------------------------------------------------------------
295 // Function : _verify_data_type
296 // Purpose  : verify the data type structures from the catalog parsing
297 //            Verify that the parents type associated to a type are defined
298 //            in the catalog
299 //----------------------------------------------------------------------
300 bool
301 SALOME_DataTypeCatalogImpl::_verify_data_type(ListOfParserDataType datatypelist)
302 {
303    bool _return_value = true;
304    bool _bool = false ;
305    vector<string> _data_name_list;
306    
307    _data_name_list.resize(0);;
308   for (unsigned int ind = 0; ind < _datatype_list.size(); ind++)
309     _data_name_list.push_back(_datatype_list[ind].Parserdata_name) ;
310
311    // Parse if parents data type name of a data type are defined in the 
312    // datatype catalog
313   for (unsigned int ind = 0; ind < _datatype_list.size(); ind++)
314     {
315       // Scrute data type parents
316       // MESSAGE("Treatment of " << _datatype_list[ind].Parserdata_name);
317       for (unsigned int ind1 = 0 ; ind1 < _datatype_list[ind].Parserdata_parents.size(); ind1++)
318        {
319          // MESSAGE("Looking for " << _datatype_list[ind].Parserdata_parents[ind1] << " in the catalog data type");
320          _bool = false;
321          // Compare parent data type name to all data type names defined in the catalog
322          for (unsigned int ind2 = 0 ; ind2 < _data_name_list.size(); ind2++)
323            {
324              if(_datatype_list[ind].Parserdata_parents[ind1].compare(_data_name_list[ind2]) == 0)
325                {
326                  // Type found : OK
327                  MESSAGE("The parents data type " << _datatype_list[ind].Parserdata_parents[ind1] << " of " << _datatype_list[ind].Parserdata_name << " was found in the catalog type");
328                  _bool = true; 
329                }
330            }
331          if(!_bool)
332            {
333              MESSAGE( "The parents data type " << _datatype_list[ind].Parserdata_parents[ind1] << " of " << _datatype_list[ind].Parserdata_name << " is not defined in the data type catalog" )
334              _return_value = false ;
335            }
336        }
337     }
338   return _return_value;
339 }
340
341
342 //----------------------------------------------------------------------
343 // Function : _parseArguments
344 // Purpose  : parse arguments to get general and personal catalog files
345 //----------------------------------------------------------------------
346 bool
347 SALOME_DataTypeCatalogImpl::_parseArguments(int argc, char **argv, 
348                                             char **_path_data)
349 {
350   bool _return_value = true;
351   *_path_data = NULL;
352   for (int ind = 0; ind < argc ; ind++)
353     {
354
355       if (strcmp(argv[ind],"-help") == 0)
356         {
357           MESSAGE( "Usage: " << argv[0] << " -common 'path to data type catalog' -ORBInitRef NameService=corbaname::localhost");
358             _return_value = false ;
359         }
360       if (strcmp(argv[ind],"-common") == 0)
361         {
362           if (ind + 1 <= argc)
363             {
364               // General catalog file
365               *_path_data = argv[ind + 1] ;
366               ifstream _path_data_file(*_path_data);
367               if (!_path_data_file)
368                 {
369                   MESSAGE( "Sorry the file " << *_path_data << " can't be open" )
370                   *_path_data = NULL;
371                   _return_value = false;
372                 }
373             }
374         }
375      
376     }
377   return _return_value;
378 }