Salome HOME
BugID: IPAL9392, modified methods GetRowUnits.
[modules/kernel.git] / src / HDFPersist / HDFascii.cc
1 //  File      : SALOMEDS_Tool.cxx
2 //  Created   : Mon Oct 21 16:24:34 2002
3 //  Author    : Sergey RUIN
4
5 //  Project   : SALOME
6 //  Module    : SALOMEDS
7 //  Copyright : Open CASCADE
8
9 #include "HDFOI.hxx"
10
11 #include <OSD_Path.hxx>
12 #include <OSD_File.hxx>
13 #include <OSD_Protection.hxx>
14 #include <OSD_Directory.hxx>
15 #include <TCollection_AsciiString.hxx> 
16
17 #include <stdlib.h>
18 #include <string.h>
19 #include <fcntl.h>
20 #include <stdio.h>
21
22 #ifdef WNT
23 #include <io.h>
24 #include <time.h>
25 #endif
26
27 using namespace std;
28
29 bool CreateAttributeFromASCII(HDFinternalObject *father, FILE* fp);
30 bool CreateDatasetFromASCII(HDFcontainerObject *father, FILE *fp);
31 bool CreateGroupFromASCII(HDFcontainerObject *father, FILE *fp);
32
33 void SaveAttributeInASCIIfile(HDFattribute *hdf_attribute, FILE* fp, int ident);
34 void SaveGroupInASCIIfile(HDFgroup *hdf_group, FILE* fp, int ident);
35 void SaveDatasetInASCIIfile(HDFdataset *hdf_dataset, FILE* fp, int ident);
36
37 char* GetTmpDir();
38 char* makeName(char* name);
39 char* restoreName(char* name);
40 void write_float64(FILE* fp, hdf_float64* value);
41 void read_float64(FILE* fp, hdf_float64* value);
42
43 #define MAX_STRING_SIZE   65535
44 #define MAX_ID_SIZE       20
45 #define NB_FLOAT_IN_ROW   3
46 #define NB_INTEGER_IN_ROW 9
47
48 #define ASCIIHDF_ID  "ASCIIHDF"
49 #define ATTRIBUTE_ID "ATTRIBUTE"
50 #define DATASET_ID   "DATASET"
51 #define GROUP_ID     "GROUP"
52
53 #define ASCIIHDF_ID_END  "ASCIIHDF_END"
54 #define ATTRIBUTE_ID_END "ATTRIBUTE_END"
55 #define DATASET_ID_END   "DATASET_END"
56 #define GROUP_ID_END     "GROUP_END"
57
58
59 //============================================================================
60 // function : isASCII
61 // purpose  : Returns True if the file is a converted to ASCII HDF file
62 //============================================================================
63 bool HDFascii::isASCII(const char* thePath) {
64   int fd;
65   if(!(fd = open(thePath, O_RDONLY))) return false;
66   char* aBuffer = new char[9];
67   aBuffer[8] = (char)0;
68   read(fd, aBuffer, 8); 
69   close(fd);
70
71   if(strcmp(aBuffer, ASCIIHDF_ID) == 0) return true;
72
73   return false;
74 }
75
76 //############################## HDF => ASCII ################################
77
78 //============================================================================
79 // function : ConvertFromHDFToASCII
80 // purpose  : Converts a file pointed by thePath to ASCII format
81 //            If isReplace is true the newly created file will replace the existent one.
82 //            If isReplace is false theExtension will be added to a created file name 
83 //            Returns the file name of ASCII file
84 //============================================================================
85 char* HDFascii::ConvertFromHDFToASCII(const char* thePath,
86                                       bool isReplace,
87                                       const char* theExtension)
88 {
89   TCollection_AsciiString aPath((char*)thePath);
90   if(!isReplace) { 
91     if(theExtension == NULL) aPath += ".asc";    
92     else aPath += (char*)theExtension;
93   }
94
95   TCollection_AsciiString aFileName(aPath);
96   if(isReplace) aFileName=aPath+".ascii_tmp";
97  
98   HDFfile *hdf_file = new HDFfile((char*)thePath); 
99   hdf_file->OpenOnDisk(HDF_RDONLY);
100
101   char name[HDF_NAME_MAX_LEN+1];
102   int nbsons = hdf_file->nInternalObjects(), nbAttr = hdf_file->nAttributes(); 
103
104   FILE* fp = fopen(aFileName.ToCString(), "w");
105   fprintf(fp, "%s\n", ASCIIHDF_ID);
106   fprintf(fp, "%i\n", nbsons+nbAttr);
107
108   for(unsigned j=0; j<nbAttr; j++) {
109     char* attr_name = hdf_file->GetAttributeName(j);
110     HDFattribute *hdf_attribute = new HDFattribute(attr_name, hdf_file);
111     delete attr_name;
112     SaveAttributeInASCIIfile(hdf_attribute, fp, 0);
113     hdf_attribute = 0;
114   }
115
116   for (Standard_Integer i=0; i<nbsons; i++) {
117     hdf_file->InternalObjectIndentify(i,name);
118     if (strncmp(name, "INTERNAL_COMPLEX",16) == 0) continue;
119
120     hdf_object_type type = hdf_file->InternalObjectType(name);
121
122     if(type == HDF_DATASET) { 
123       HDFdataset* hdf_dataset = new HDFdataset(name, hdf_file);
124       SaveDatasetInASCIIfile(hdf_dataset, fp, 0);
125       hdf_dataset = 0; 
126     } else if(type == HDF_GROUP) {
127       HDFgroup *hdf_group = new HDFgroup(name, hdf_file); 
128       SaveGroupInASCIIfile(hdf_group, fp, 0);
129       hdf_group = 0;
130     }
131   }
132
133   fprintf(fp, "%s", ASCIIHDF_ID_END);
134
135   fclose(fp);
136
137   hdf_file->CloseOnDisk();
138   delete hdf_file;
139
140   if(isReplace) {
141     OSD_Path anOSDPath(aFileName);
142     OSD_File anOSDFile(anOSDPath);
143     if(anOSDFile.Exists())
144       anOSDFile.Move(aPath);
145     else 
146       return NULL;
147   }
148
149   int length = strlen(aPath.ToCString());
150   char *new_str = new char[ 1+length ];
151   strcpy(new_str , aPath.ToCString()) ;
152
153   return new_str;
154 }
155
156
157 //============================================================================
158 // function : SaveGroupInASCIIfile
159 // purpose  : 
160 //============================================================================
161 void SaveGroupInASCIIfile(HDFgroup *hdf_group, FILE* fp, int ident)
162 {
163   hdf_group->OpenOnDisk();
164
165   TCollection_AsciiString anIdent(ident, '\t');
166   int nbsons = hdf_group->nInternalObjects(), nbAttr = hdf_group->nAttributes(); 
167
168   /*fprintf(fp, "%s%s\n", anIdent.ToCString(), GROUP_ID);*/
169   fprintf(fp, "%s\n", GROUP_ID);
170
171   char* name = makeName(hdf_group->GetName());
172
173   /*fprintf(fp, "%s%s %i\n", anIdent.ToCString(), name, nbsons+nbAttr);*/
174   fprintf(fp, "%s %i\n", name, nbsons+nbAttr);
175   delete name;
176
177   for(unsigned j=0; j<nbAttr; j++) {
178     name = hdf_group->GetAttributeName(j);
179     HDFattribute *hdf_attribute = new HDFattribute(name, hdf_group);
180     delete name;
181     SaveAttributeInASCIIfile(hdf_attribute, fp, ident+1);
182     hdf_attribute = 0;
183   }
184
185   char objName[HDF_NAME_MAX_LEN+1];
186  
187   for (int i=0; i<nbsons; i++) {
188     hdf_group->InternalObjectIndentify(i, objName);
189
190     if (strncmp(objName, "INTERNAL_COMPLEX",16) == 0)  continue;
191
192     hdf_object_type type = hdf_group->InternalObjectType(objName);
193
194     if  (type == HDF_DATASET) {
195       HDFdataset* hdf_dataset = new HDFdataset(objName, hdf_group);
196       SaveDatasetInASCIIfile(hdf_dataset, fp, ident+1);
197       hdf_dataset = 0;
198     } else if (type == HDF_GROUP)   {      
199       HDFgroup *hdf_subgroup = new HDFgroup(objName, hdf_group);
200       SaveGroupInASCIIfile(hdf_subgroup, fp, ident+1);
201       hdf_subgroup = 0;
202     } 
203   }
204
205   /*fprintf(fp, "%s%s\n", anIdent.ToCString(), GROUP_ID_END);*/
206   fprintf(fp, "%s\n", GROUP_ID_END);
207
208   hdf_group->CloseOnDisk();  
209 }
210
211 //============================================================================
212 // function : SaveDatasetInASCIIfile
213 // purpose  : 
214 //============================================================================
215 void SaveDatasetInASCIIfile(HDFdataset *hdf_dataset, FILE* fp, int ident)
216 {
217   hdf_dataset->OpenOnDisk();
218
219   long size =  hdf_dataset->GetSize();
220   long ndim = hdf_dataset->nDim(); //Get number of dimesions
221   hdf_size *dim = new hdf_size[ndim];
222   hdf_type type = hdf_dataset->GetType();
223   int nbAttr = hdf_dataset->nAttributes(), j; 
224
225   TCollection_AsciiString anIdent(ident, '\t');
226   TCollection_AsciiString anIdentChild(ident+1, '\t');
227
228   char* name = makeName(hdf_dataset->GetName());
229
230   /*fprintf(fp, "%s%s\n", anIdent.ToCString(), DATASET_ID);*/
231   fprintf(fp, "%s\n", DATASET_ID);
232   /*fprintf(fp, "%s%s %i %i\n", anIdent.ToCString(), name, type, nbAttr);*/
233   fprintf(fp, "%s %i %i\n", name, type, nbAttr);
234   delete name;
235
236   hdf_dataset->GetDim(dim);
237   /*fprintf(fp, "%s %i\n", anIdentChild.ToCString(), ndim);*/
238   fprintf(fp, " %i\n", ndim);
239
240   for(int i = 0;i < ndim;i++) {
241     /*fprintf(fp, "%s%i",  anIdentChild.ToCString(), dim[i]);*/
242     fprintf(fp, " %i", dim[i]);
243   }
244
245   /*fprintf(fp, "%s\n", anIdentChild.ToCString());*/
246   fprintf(fp, "\n");
247   delete dim;
248
249   /*fprintf(fp, "%s%li:", anIdentChild.ToCString(), size);*/
250   fprintf(fp, "%li:", size);
251
252   if (type == HDF_STRING) {     
253     char* val = new char[size];
254     hdf_dataset->ReadFromDisk(val);
255     fwrite(val, 1, size, fp);
256     delete val;
257   } else if (type == HDF_FLOAT64) {
258     hdf_float64* val = new hdf_float64[size];
259     hdf_dataset->ReadFromDisk(val);
260     fprintf(fp, "\n");
261     for (int i = 0, j = 0; i < size; i++) {
262       write_float64(fp, &val[i]);
263       if(++j == NB_FLOAT_IN_ROW) {
264         fprintf(fp, "\n");
265         j = 0;
266       }
267       else fprintf(fp,"  ");
268     }
269     delete val;
270   } else if(type == HDF_INT64) {
271     hdf_int64* val = new hdf_int64[size];
272     hdf_dataset->ReadFromDisk(val);
273     fprintf(fp, "\n");
274     for (int i = 0, j = 0; i < size; i++) {
275       fprintf(fp, " %li", val[i]);
276       if(++j == NB_INTEGER_IN_ROW) {
277         fprintf(fp, "\n");
278         j = 0;
279       }
280     }
281     delete val;
282   } else if(type == HDF_INT32) {
283     hdf_int32* val = new hdf_int32[size];
284     hdf_dataset->ReadFromDisk(val);
285     fprintf(fp, "\n");
286     for (int i = 0, j = 0; i < size; i++) {
287       fprintf(fp, " %i", val[i]);
288       if(++j == NB_INTEGER_IN_ROW) {
289         fprintf(fp, "\n");
290         j = 0;
291       }
292     }
293     delete val;
294   }
295   
296   fprintf(fp, "\n");
297
298 #ifndef WNT
299   for(unsigned j=0; j<nbAttr; j++) {
300 #else
301   for(j=0; j<nbAttr; j++) {
302 #endif
303     name = hdf_dataset->GetAttributeName(j);
304     HDFattribute *hdf_attribute = new HDFattribute(name, hdf_dataset);
305     delete name;
306     SaveAttributeInASCIIfile(hdf_attribute, fp, ident+1);
307     hdf_attribute = 0;
308   }
309
310   /*fprintf(fp, "%s%s\n", anIdent.ToCString(), DATASET_ID_END); */
311   fprintf(fp, "%s\n", DATASET_ID_END);
312
313   hdf_dataset->CloseOnDisk(); 
314 }
315
316
317 //============================================================================
318 // function : SaveAttributeInASCIIfile
319 // purpose  : 
320 //============================================================================
321 void SaveAttributeInASCIIfile(HDFattribute *hdf_attribute, FILE* fp, int ident)
322 {
323   hdf_attribute->OpenOnDisk();
324
325   hdf_type type = hdf_attribute->GetType();
326
327   TCollection_AsciiString anIdent(ident, '\t');
328   TCollection_AsciiString anIdentChild(ident+1, '\t');
329
330   char* name = makeName(hdf_attribute->GetName());
331   int size = hdf_attribute->GetSize();
332
333   /*fprintf(fp, "%s%s\n", anIdent.ToCString(), ATTRIBUTE_ID);*/
334   fprintf(fp, "%s\n", ATTRIBUTE_ID);
335   /*fprintf(fp, "%s%s %i %i\n", anIdent.ToCString(), name, type, size);*/
336   fprintf(fp, "%s %i %i\n", name, type, size);
337
338   delete name;
339
340   if (type == HDF_STRING) {    
341     char* val = new char[size+1];
342     hdf_attribute->ReadFromDisk(val);
343     /*fprintf(fp, "%s:", anIdentChild.ToCString());*/
344     fprintf(fp, ":");
345     fwrite(val, 1, size, fp);
346     fprintf(fp, "\n");
347     delete val;
348   } else if (type == HDF_FLOAT64) {
349     hdf_float64 val;
350     hdf_attribute->ReadFromDisk(&val);
351     /*fprintf(fp, "%s",  anIdentChild.ToCString());*/
352     write_float64(fp, &val);
353     fprintf(fp, "\n");
354   } else if(type == HDF_INT64) {
355     hdf_int64 val;
356     hdf_attribute->ReadFromDisk(&val);
357     /*fprintf(fp, "%s%li \n", anIdentChild.ToCString(), val);*/
358     fprintf(fp, "%li \n", val);
359   } else if(type == HDF_INT32) {
360     hdf_int32 val;
361     hdf_attribute->ReadFromDisk(&val);
362     /*fprintf(fp, "%s%i \n", anIdentChild.ToCString(), val);*/
363     fprintf(fp, "%i \n", val);
364   }
365
366   /*fprintf(fp, "%s%s\n", anIdent.ToCString(), ATTRIBUTE_ID_END);*/
367   fprintf(fp, "%s\n", ATTRIBUTE_ID_END);
368
369   hdf_attribute->CloseOnDisk();  
370 }
371
372 //############################## ASCII => HDF ################################
373
374 //============================================================================
375 // function : ConvertFromASCIIToHDF
376 // purpose  : Converts a file pointed by thePath to HDF format
377 //            Returns a name of directory where a created HDF file is placed
378 //            The created file is named "hdf_from_ascii.hdf"
379 //============================================================================
380 char* HDFascii::ConvertFromASCIIToHDF(const char* thePath)
381 {
382   // Get a temporary directory to store a file
383   TCollection_AsciiString aTmpDir = GetTmpDir(), aFileName("hdf_from_ascii.hdf");
384   // Build a full file name of temporary file
385   TCollection_AsciiString aFullName = aTmpDir + aFileName;
386
387   HDFfile *hdf_file = new HDFfile(aFullName.ToCString()); 
388   hdf_file->CreateOnDisk();
389   
390   FILE *fp = fopen(thePath, "r");
391   if(!fp) return NULL;
392
393   char type[9];
394   int nbsons, i;
395   fscanf(fp, "%s", type);
396   fscanf(fp, "%i",&nbsons);
397
398   if(strcmp(type, ASCIIHDF_ID) != 0) return NULL;
399
400   for(i = 0; i < nbsons; i++) {
401     char id_of_begin[MAX_ID_SIZE];
402     fscanf(fp, "%s\n", id_of_begin);
403
404     if(strcmp(id_of_begin, GROUP_ID) == 0) {
405       if(!CreateGroupFromASCII(hdf_file, fp)) {
406         cout << "ConvertFromASCIIToHDF : Can not create group number " << i << endl;
407         return NULL;
408       }
409     }
410     else if(strcmp(id_of_begin, DATASET_ID) == 0) {
411       if(!CreateDatasetFromASCII(hdf_file, fp)) {
412         cout << "ConvertFromASCIIToHDF :Can not create dataset number " << i << endl;
413         return NULL;
414       }
415     }
416     else if(strcmp(id_of_begin, ATTRIBUTE_ID) == 0) {
417       if(!CreateAttributeFromASCII(hdf_file, fp)) {
418         cout << "ConvertFromASCIIToHDF :Can not create attribute number " << i << endl;
419         return NULL;
420       }
421     }
422     else 
423       cout << "ConvertFromASCIIToHDF : Unrecognized type " << id_of_begin << endl; 
424   }
425
426   char id_of_end[MAX_ID_SIZE];
427   fscanf(fp, "%s", id_of_end);
428   if(strcmp(id_of_end, ASCIIHDF_ID_END) != 0) {
429     cout << "ConvertFromASCIIToHDF : Can not find the end ASCII token " << endl;
430     return false;  
431   }
432
433   hdf_file->CloseOnDisk();
434   delete hdf_file;
435
436   int length = strlen(aTmpDir.ToCString());
437   char *new_str = new char[ 1+length ];
438   strcpy(new_str , aTmpDir.ToCString()) ;
439
440   return new_str;
441 }
442
443
444 //============================================================================
445 // function : CreateGroupFromASCII
446 // purpose  : Creates a HDF group from a set attributes situated under theLabel
447 //============================================================================
448 bool CreateGroupFromASCII(HDFcontainerObject *father, FILE *fp)
449 {
450   char name[HDF_NAME_MAX_LEN+1];
451   int nbsons, i;
452   fscanf(fp, "%s %i\n", name, &nbsons);  
453
454   char* new_name = restoreName(name);
455
456   HDFgroup* hdf_group = new HDFgroup(new_name, father);
457
458   delete new_name;
459
460   hdf_group->CreateOnDisk();
461
462   for(i = 0; i < nbsons; i++) {
463     char id_of_begin[MAX_ID_SIZE];
464     fscanf(fp, "%s\n", id_of_begin);
465     
466     if(strcmp(id_of_begin, GROUP_ID) == 0) {
467       if(!CreateGroupFromASCII(hdf_group, fp)) {
468         cout << "Can not create subgroup " << i << " for group " << name << endl;
469         return false;
470       }
471     }
472     else if(strcmp(id_of_begin, DATASET_ID) == 0) {
473       if(!CreateDatasetFromASCII(hdf_group, fp)) {
474         cout << "Can not create dataset " << i << " for group " << name << endl;
475         return false;
476       }
477     }
478     else if(strcmp(id_of_begin, ATTRIBUTE_ID) == 0) {
479       if(!CreateAttributeFromASCII(hdf_group, fp)) {
480         cout << "Can not create attribute " << i << " for group " << name << endl;
481         return false;
482       }
483     }
484     else 
485       cout << "CreateGroupFromASCII : Unrecognized type " << id_of_begin << endl; 
486   }
487   
488   hdf_group->CloseOnDisk();
489   hdf_group = 0; //will be deleted by father destructor
490
491   char id_of_end[MAX_ID_SIZE];
492   fscanf(fp, "%s\n", id_of_end);
493   if(strcmp(id_of_end, GROUP_ID_END) != 0) {
494     cout << "CreateGroupFromASCII : Invalid end token : " << id_of_end << endl;
495     return false;
496   }
497
498   return true;
499 }
500
501
502 //============================================================================
503 // function : CreateDatasetFromASCII
504 // purpose  : Creates a HDF dataset from a set attributes situated under theLabel
505 //============================================================================
506 bool CreateDatasetFromASCII(HDFcontainerObject *father, FILE *fp)
507 {
508   char name[HDF_NAME_MAX_LEN+1];
509   hdf_type type;
510   int nbDim, nbAttr;
511   long i, size;
512
513   fscanf(fp, "%s %i %i\n", name, &type, &nbAttr);
514   char* new_name = restoreName(name);
515
516   fscanf(fp, "%i\n", &nbDim);
517
518   hdf_size* sizeArray = new hdf_size[nbDim];
519   for(i = 0; i<nbDim; i++) {
520     fscanf(fp, "%i\n", &(sizeArray[i]));
521   }
522  
523   HDFdataset* hdf_dataset = new HDFdataset(new_name, father,type, sizeArray, nbDim);
524   delete new_name;
525   delete sizeArray;
526
527   hdf_dataset->CreateOnDisk();
528
529   char tmp;
530   fscanf(fp, "%li%c", &size, &tmp);
531
532   if (type == HDF_STRING) {     
533     char *val = new char[size+1];
534     fread(val, 1, size, fp);
535     hdf_dataset->WriteOnDisk(val);
536     delete val;
537   } else if (type == HDF_FLOAT64) {
538     hdf_float64* val = new hdf_float64[size];
539     for(i=0; i<size; i++) {
540       read_float64(fp, &(val[i]));
541     }
542     hdf_dataset->WriteOnDisk(val);
543     delete val;
544   } else if(type == HDF_INT64) {
545     hdf_int64* val = new hdf_int64[size];
546     for(i=0; i<size; i++) {
547       fscanf(fp, " %li", &(val[i]));
548     }
549     hdf_dataset->WriteOnDisk(val);
550     delete val;
551   } else if(type == HDF_INT32) {
552     hdf_int32* val = new hdf_int32[size];
553     for(i=0; i<size; i++) {
554       fscanf(fp, " %i", &(val[i]));
555     }
556     hdf_dataset->WriteOnDisk(val);
557     delete val;
558   }
559
560   char token[MAX_ID_SIZE];
561
562   for(i = 0; i < nbAttr; i++) {
563     fscanf(fp, "%s\n", token);
564     
565     if(strcmp(token, ATTRIBUTE_ID) == 0) {
566       if(!CreateAttributeFromASCII(hdf_dataset, fp)) {
567         cout << "Can not create attribute " << i << " for dataset " << name << endl;
568         return false;
569       }
570     }
571     else {
572       cout << "CreateGroupFromASCII : Unrecognized type " << token << endl; 
573       return false;
574     }
575   }
576   
577   fscanf(fp, "%s\n", token);
578   if(strcmp(token, DATASET_ID_END) != 0) {
579     cout << "CreateDatasetFromASCII : Invalid end token : " << token << endl;
580     return false;
581   }
582
583   hdf_dataset->CloseOnDisk();
584   hdf_dataset = 0; //will be deleted by father destructor
585
586   return true;
587 }
588
589
590 //============================================================================
591 // function : CreateAttributeFromASCII
592 // purpose  : Creates a HDF attribute from a set attributes situated under theLabel
593 //============================================================================
594 bool CreateAttributeFromASCII(HDFinternalObject *father, FILE* fp)
595 {
596   char name[HDF_NAME_MAX_LEN+1];
597
598   hdf_type type;
599   int size;
600   fscanf(fp, "%s %i %i\n", name, &type, &size);
601   char* new_name = restoreName(name);
602   HDFattribute* hdf_attribute = new HDFattribute(new_name, father, type, size);
603
604   hdf_attribute->CreateOnDisk();
605
606   delete new_name;
607   
608   if (type == HDF_STRING) {     
609     char tmp;
610     fscanf(fp, "%c", &tmp);
611     char *val = new char[size+1];
612     val[size] = (char)0;
613     fread(val, 1, size, fp);
614     hdf_attribute->WriteOnDisk(val);
615     delete val;
616   } else if (type == HDF_FLOAT64) {
617     hdf_float64 val;
618     read_float64(fp, &val);
619     hdf_attribute->WriteOnDisk(&val);
620   } else if(type == HDF_INT64) {
621     hdf_int64 val;
622     fscanf(fp, "%li", &val);
623     hdf_attribute->WriteOnDisk(&val);
624   } else if(type == HDF_INT32) {
625     hdf_int32 val;
626     fscanf(fp, "%i", &val);
627     hdf_attribute->WriteOnDisk(&val);
628   }
629   
630   hdf_attribute->CloseOnDisk();
631   hdf_attribute = 0; //will be deleted by father destructor
632
633
634   char id_of_end[MAX_ID_SIZE];
635   fscanf(fp, "%s\n", id_of_end);
636   if(strcmp(id_of_end, ATTRIBUTE_ID_END) != 0) {
637     cout << "CreateAttributeFromASCII : Invalid end token : " << id_of_end << endl;
638     return false;
639   }
640
641   return true;
642 }
643
644
645 //============================================================================
646 // function : GetTempDir
647 // purpose  : Return a temp directory to store created files like "/tmp/sub_dir/" 
648 //============================================================================ 
649 char* GetTmpDir()
650 {
651   //Find a temporary directory to store a file
652
653   TCollection_AsciiString aTmpDir;
654
655 #ifdef WNT
656   char *aTmp;
657   aTmp = getenv("TMP");
658   if(aTmp != NULL)
659         aTmpDir = TCollection_AsciiString(aTmp);
660   else
661         aTmpDir = TCollection_AsciiString("C:\\");
662 #else
663   aTmpDir = TCollection_AsciiString("/tmp/");
664 #endif
665
666   srand((unsigned int)time(NULL));
667
668   int aRND = 999 + (int)(100000.0*rand()/(RAND_MAX+1.0)); //Get a random number to present a name of a sub directory
669   TCollection_AsciiString aSubDir(aRND);
670   if(aSubDir.Length() <= 1) aSubDir = TCollection_AsciiString("123409876");
671
672   aTmpDir += aSubDir; //Get RND sub directory
673
674 #ifdef WIN32
675   if(aTmpDir.Value(aTmpDir.Length()) != '\\') aTmpDir+='\\';
676 #else
677   if(aTmpDir.Value(aTmpDir.Length()) != '/') aTmpDir+='/';
678 #endif
679
680   OSD_Path aPath(aTmpDir);
681   OSD_Directory aDir(aPath);
682
683   for(aRND = 0; aDir.Exists(); aRND++) {
684     aTmpDir.Insert((aTmpDir.Length() - 1), TCollection_AsciiString(aRND));  //Build a unique directory name
685     aPath = OSD_Path(aTmpDir);
686     aDir = OSD_Directory(aPath);
687   }
688
689   OSD_Protection aProtection(OSD_RW, OSD_RWX, OSD_RX, OSD_RX);
690   aDir.Build(aProtection);
691
692   int length = strlen(aTmpDir.ToCString());
693   char *new_str = new char[ 1+length ];
694   strcpy(new_str , aTmpDir.ToCString());
695
696   return new_str;
697 }
698
699 char* makeName(char* name)
700 {
701   TCollection_AsciiString aName(name), aNewName;
702   Standard_Integer i, length = aName.Length();
703   char replace = (char)19;
704
705   for(i=1; i<=length; i++) {
706     if(aName.Value(i) == ' ') aNewName+=replace;
707     else aNewName += aName.Value(i);
708   }
709
710   length = strlen(aNewName.ToCString());
711   char *new_str = new char[ 1+length ];
712   strcpy(new_str , aNewName.ToCString()) ;
713   return new_str;
714 }
715
716 char* restoreName(char* name)
717 {
718   TCollection_AsciiString aName(name), aNewName;
719   Standard_Integer i, length = aName.Length();
720   char replace = (char)19;
721
722   for(i=1; i<=length; i++) {
723     if(aName.Value(i) == replace) aNewName+=' ';
724     else aNewName += aName.Value(i);
725   }
726
727   length = strlen(aNewName.ToCString());
728   char *new_str = new char[ 1+length ];
729   strcpy(new_str , aNewName.ToCString()) ;
730   return new_str;
731 }
732
733 void write_float64(FILE* fp, hdf_float64* value)
734 {
735   unsigned char* array = (unsigned char*)value;
736   for(int i = 0; i < sizeof(hdf_float64); i++) {
737     unsigned tmp = (unsigned short)array[i];
738     fprintf(fp, " %2x", tmp);
739   }
740 }
741
742 void read_float64(FILE* fp, hdf_float64* value)
743 {
744   unsigned char* array = (unsigned char*)value;
745   for(int i = 0; i < sizeof(hdf_float64); i++) {
746     unsigned tmp;
747     fscanf(fp, " %x", &tmp); 
748     array[i] = (unsigned char)tmp;
749   }
750 }