0023274: MSVC++ warnings issued during compilation for 64bits
[occt.git] / src / FSD / FSD_File.cxx
1 // Copyright (c) 1998-1999 Matra Datavision
2 // Copyright (c) 1999-2012 OPEN CASCADE SAS
3 //
4 // The content of this file is subject to the Open CASCADE Technology Public
5 // License Version 6.5 (the "License"). You may not use the content of this file
6 // except in compliance with the License. Please obtain a copy of the License
7 // at http://www.opencascade.org and read it completely before using this file.
8 //
9 // The Initial Developer of the Original Code is Open CASCADE S.A.S., having its
10 // main offices at: 1, place des Freres Montgolfier, 78280 Guyancourt, France.
11 //
12 // The Original Code and all software distributed under the License is
13 // distributed on an "AS IS" basis, without warranty of any kind, and the
14 // Initial Developer hereby disclaims all such warranties, including without
15 // limitation, any warranties of merchantability, fitness for a particular
16 // purpose or non-infringement. Please see the License for the specific terms
17 // and conditions governing the rights and limitations under the License.
18
19 #include <FSD_File.ixx>
20 #include <OSD.hxx>
21
22 const Standard_CString MAGICNUMBER = "FSDFILE";
23 const Standard_CString ENDOFNORMALEXTENDEDSECTION = "BEGIN_REF_SECTION";
24 const Standard_Integer SIZEOFNORMALEXTENDEDSECTION = 16;
25
26 //#define USEOSDREAL 1
27
28 //=======================================================================
29 //function : FSD_File
30 //purpose  : 
31 //=======================================================================
32
33 FSD_File::FSD_File()
34 {
35
36 }
37
38 //=======================================================================
39 //function : IsGoodFileType
40 //purpose  : INFO SECTION
41 //           write
42 //=======================================================================
43
44 Storage_Error FSD_File::IsGoodFileType(const TCollection_AsciiString& aName)
45 {
46   FSD_File      f;
47   Storage_Error s;
48
49   s = f.Open(aName,Storage_VSRead);
50
51   if (s == Storage_VSOk) {
52     TCollection_AsciiString l;
53     Standard_Size        len = strlen(FSD_File::MagicNumber());
54
55     f.ReadChar(l,len);
56
57     f.Close();
58
59     if (strncmp(FSD_File::MagicNumber(),l.ToCString(),len) != 0) {
60       s = Storage_VSFormatError;
61     }
62   }
63
64   return s;
65 }
66
67 //=======================================================================
68 //function : Open
69 //purpose  : 
70 //=======================================================================
71
72 Storage_Error FSD_File::Open(const TCollection_AsciiString& aName,const Storage_OpenMode aMode)
73 {
74   Storage_Error result = Storage_VSOk;
75
76   SetName(aName);
77
78   if (OpenMode() == Storage_VSNone) {
79     if (aMode == Storage_VSRead) {
80       myStream.open(aName.ToCString(),ios::in); // ios::nocreate is not portable
81     }
82     else if (aMode == Storage_VSWrite) {
83       myStream.open(aName.ToCString(),ios::out);
84     }
85     else if (aMode == Storage_VSReadWrite) {
86       myStream.open(aName.ToCString(),ios::in|ios::out);
87     }
88     
89     if (myStream.fail()) {
90       result = Storage_VSOpenError;
91     }
92     else {
93       myStream.precision(17);
94       SetOpenMode(aMode);
95     }
96   }
97   else {
98     result = Storage_VSAlreadyOpen;
99   }
100
101   return result;
102 }
103
104 //=======================================================================
105 //function : IsEnd
106 //purpose  : 
107 //=======================================================================
108
109 Standard_Boolean FSD_File::IsEnd()
110 {
111   return myStream.eof();
112 }
113
114 //=======================================================================
115 //function : Close
116 //purpose  : 
117 //=======================================================================
118
119 Storage_Error FSD_File::Close()
120 {
121   Storage_Error result = Storage_VSOk;
122
123   if (OpenMode() != Storage_VSNone) {
124     myStream.close();
125     SetOpenMode(Storage_VSNone);
126   }
127   else {
128     result = Storage_VSNotOpen;
129   }
130
131   return result;
132 }
133
134 //=======================================================================
135 //function : MagicNumber
136 //purpose  : ------------------ PROTECTED
137 //=======================================================================
138
139 const Standard_CString FSD_File::MagicNumber()
140 {
141   return MAGICNUMBER;
142 }
143
144 //=======================================================================
145 //function : FlushEndOfLine
146 //purpose  : 
147 //=======================================================================
148
149 void FSD_File::FlushEndOfLine()
150 {
151   TCollection_AsciiString aDummy;
152   ReadLine (aDummy); // flush is nothing more than to read till the line-break
153 /*  static char Buffer[8192];
154   char c;
155   Standard_Boolean IsEnd = Standard_False;
156
157   while (!IsEnd && !FSD_File::IsEnd()) {
158     Buffer[0] = '\0';
159     myStream.get(Buffer,8192,'\n');
160
161     if (myStream.get(c) && c != '\n') {
162     }
163     else {
164       IsEnd = Standard_True;
165     }
166   }*/
167 }
168
169 //=======================================================================
170 //function : ReadLine
171 //purpose  : read from the current position to the end of line.
172 //=======================================================================
173
174 void FSD_File::ReadLine(TCollection_AsciiString& buffer)
175 {
176   char Buffer[8193];
177   Standard_Boolean IsEnd = Standard_False;
178   
179   buffer.Clear();
180
181   while (!IsEnd && !FSD_File::IsEnd()) {
182     Buffer[0] = '\0';
183     myStream.getline(Buffer,8192,'\n');
184     
185 //    char c;
186 //    if (myStream.get(c) && c != '\n') {
187 //      buffer += Buffer;
188 //      buffer += c;
189 //    }
190 //    else {
191       buffer += Buffer;
192       IsEnd = Standard_True;
193 //    }
194   }
195 }
196
197 //=======================================================================
198 //function : WriteExtendedLine
199 //purpose  : write from the current position to the end of line.
200 //=======================================================================
201
202 void FSD_File::WriteExtendedLine(const TCollection_ExtendedString& buffer)
203 {
204   Standard_ExtString extBuffer;
205   Standard_Integer   i,c,d;
206
207   extBuffer = buffer.ToExtString();
208
209   for (i = 0; i < buffer.Length(); i++) {
210     c = (extBuffer[i] & 0x0000FF00 ) >> 8 ;
211     d = extBuffer[i] & 0x000000FF;
212
213     myStream << (char)c << (char)d;
214   }
215
216   myStream << (char)0 << "\n";
217 }
218
219 //=======================================================================
220 //function : ReadExtendedLine
221 //purpose  : 
222 //=======================================================================
223
224 void FSD_File::ReadExtendedLine(TCollection_ExtendedString& buffer)
225 {
226   char c = '\0';
227   Standard_ExtCharacter i = 0,j,count = 0;
228   Standard_Boolean fin = Standard_False;
229   Standard_CString tg = ENDOFNORMALEXTENDEDSECTION;
230  
231   buffer.Clear();
232
233   while (!fin && !IsEnd()) {
234     myStream.get(c);
235
236     if (c == tg[count]) count++;
237     else count = 0;
238     if (count < SIZEOFNORMALEXTENDEDSECTION) {
239       i = 0; j = 0;
240       i += (Standard_ExtCharacter)c;
241       if (c == '\0') fin = Standard_True;
242       i = (i << 8);
243       
244       myStream.get(c);
245       if (c == tg[count]) count++;
246       else count = 0;
247       if (count < SIZEOFNORMALEXTENDEDSECTION) {
248         j += (Standard_ExtCharacter)c;
249         if (c != '\n') {
250           fin = Standard_False;
251           i |= (0x00FF & j);
252           buffer += (Standard_ExtCharacter)i;
253         }
254       }
255       else {
256         Storage_StreamExtCharParityError::Raise();      
257       }
258     }
259     else {
260       Storage_StreamExtCharParityError::Raise();
261     }
262   }
263 }
264
265 //=======================================================================
266 //function : ReadChar
267 //purpose  : read <rsize> character from the current position.
268 //=======================================================================
269
270 void FSD_File::ReadChar(TCollection_AsciiString& buffer, const Standard_Size rsize)
271 {
272   char             c;
273   Standard_Size ccount = 0;
274
275   buffer.Clear();
276
277   while (!IsEnd() && (ccount < rsize)) {
278     myStream.get(c);
279     buffer += c;
280     ccount++;
281   }
282 }
283
284 //=======================================================================
285 //function : ReadString
286 //purpose  : read from the first none space character position to the end of line.
287 //=======================================================================
288
289 void FSD_File::ReadString(TCollection_AsciiString& buffer)
290 {
291   char Buffer[8193];
292   char *bpos;
293   Standard_Boolean IsEnd = Standard_False,isFirstTime = Standard_True;
294   
295   buffer.Clear();
296   
297   while (!IsEnd && !FSD_File::IsEnd()) {
298     Buffer[0] = '\0';
299     myStream.getline(Buffer,8192,'\n');
300     bpos = Buffer;
301
302     // LeftAdjust
303     //
304     if (isFirstTime) {
305       isFirstTime = Standard_False;
306       while (*bpos == '\n' || *bpos == ' ') bpos++;
307     }
308 //    char c;
309 //    if (myStream.get(c) && c != '\n') {
310 //      buffer += bpos;
311 //      buffer += c;
312 //    }
313 //    else {
314       buffer += bpos;
315       IsEnd = Standard_True;
316 //    }
317   }
318   
319 }
320
321 //=======================================================================
322 //function : ReadWord
323 //purpose  : read from the current position to the next white space or end of line.
324 //=======================================================================
325
326 void FSD_File::ReadWord(TCollection_AsciiString& buffer)
327 {
328   char c;
329   char b[8193],*tmpb;
330   Standard_Boolean IsEnd = Standard_False;
331   Standard_Integer i;
332
333   tmpb = b;
334   memset(b,'\0',8193);
335   buffer.Clear();
336
337   while (!IsEnd && !FSD_File::IsEnd()) {
338     myStream.get(c);
339     if ((c != ' ') && (c != '\n')) IsEnd = Standard_True;
340   }
341
342   IsEnd = Standard_False;
343   i = 0;
344
345   while (!IsEnd && !FSD_File::IsEnd()) {
346     if (i == 8192) {
347       buffer += b;
348       tmpb = b;
349       memset(b,'\0',8193);
350       i = 0;
351     }
352     *tmpb = c;
353     tmpb++; i++;
354     myStream.get(c);
355     if ((c == '\n') || (c == ' ')) IsEnd = Standard_True;
356   }
357
358   buffer += b;
359 }
360
361 //=======================================================================
362 //function : FindTag
363 //purpose  : 
364 //=======================================================================
365
366 Storage_Error FSD_File::FindTag(const Standard_CString aTag)
367 {
368   TCollection_AsciiString l;
369   
370   ReadString(l);
371
372   while ((strcmp(l.ToCString(),aTag) != 0) && !IsEnd()) {
373     ReadString(l);
374   }
375
376   if (IsEnd()) {
377     return Storage_VSSectionNotFound;
378   }
379   else {
380     return Storage_VSOk;
381   }
382 }
383
384 //=======================================================================
385 //function : SkipObject
386 //purpose  : 
387 //=======================================================================
388
389 void FSD_File::SkipObject()
390 {
391   FlushEndOfLine();
392 }
393
394 //=======================================================================
395 //function : PutReference
396 //purpose  : ---------------------- PUBLIC : PUT
397 //=======================================================================
398
399 Storage_BaseDriver& FSD_File::PutReference(const Standard_Integer aValue)
400 {
401   myStream << aValue << " ";
402   if (myStream.bad()) Storage_StreamWriteError::Raise();
403   return *this;
404 }
405
406 //=======================================================================
407 //function : PutCharacter
408 //purpose  : 
409 //=======================================================================
410
411 Storage_BaseDriver& FSD_File::PutCharacter(const Standard_Character aValue)
412 {
413   unsigned short i;
414
415   i = aValue;
416   myStream << i << " ";
417   if (myStream.bad()) Storage_StreamWriteError::Raise();
418   return *this;
419 }
420
421 //=======================================================================
422 //function : PutExtCharacter
423 //purpose  : 
424 //=======================================================================
425
426 Storage_BaseDriver& FSD_File::PutExtCharacter(const Standard_ExtCharacter aValue)
427 {
428   myStream << aValue << " ";
429   if (myStream.bad()) Storage_StreamWriteError::Raise();
430   return *this;
431 }
432
433 //=======================================================================
434 //function : PutInteger
435 //purpose  : 
436 //=======================================================================
437
438 Storage_BaseDriver& FSD_File::PutInteger(const Standard_Integer aValue)
439 {
440   myStream << aValue << " ";
441   if (myStream.bad()) Storage_StreamWriteError::Raise();
442   return *this;
443 }
444
445 //=======================================================================
446 //function : PutBoolean
447 //purpose  : 
448 //=======================================================================
449
450 Storage_BaseDriver& FSD_File::PutBoolean(const Standard_Boolean aValue)
451 {
452   myStream << ((Standard_Integer)aValue) << " ";
453   if (myStream.bad()) Storage_StreamWriteError::Raise();
454   return *this;
455 }
456
457 //=======================================================================
458 //function : PutReal
459 //purpose  : 
460 //=======================================================================
461
462 Storage_BaseDriver& FSD_File::PutReal(const Standard_Real aValue)
463 {
464 #ifdef USEOSDREAL
465   char realbuffer[100];
466
467   realbuffer[0] = '\0';
468   if (OSD::RealToCString(aValue,realbuffer)) {
469     myStream << realbuffer << " ";
470   }
471   else {
472     Storage_StreamWriteError::Raise();
473   }
474   if (myStream.bad()) Storage_StreamWriteError::Raise();
475
476   return *this;
477 #else
478   myStream << ((Standard_Real)aValue) << " ";
479
480   if (myStream.bad()) Storage_StreamWriteError::Raise();
481   return *this;
482 #endif
483 }
484
485 //=======================================================================
486 //function : PutShortReal
487 //purpose  : 
488 //=======================================================================
489
490 Storage_BaseDriver& FSD_File::PutShortReal(const Standard_ShortReal aValue)
491 {
492 #ifdef USEOSDREAL
493   char realbuffer[100];
494
495   realbuffer[0] = '\0';
496   if (OSD::RealToCString(aValue,realbuffer)) {
497     myStream << realbuffer << " ";
498   }
499   else {
500     Storage_StreamWriteError::Raise();
501   }
502   if (myStream.bad()) Storage_StreamWriteError::Raise();
503
504   return *this;
505 #else
506   myStream << aValue << " ";
507
508   if (myStream.bad()) Storage_StreamWriteError::Raise();
509   return *this;
510 #endif
511 }
512
513 //=======================================================================
514 //function : GetReference
515 //purpose  : ----------------- PUBLIC : GET
516 //=======================================================================
517
518 Storage_BaseDriver& FSD_File::GetReference(Standard_Integer& aValue)
519 {
520   if (!(myStream >> aValue)) Storage_StreamTypeMismatchError::Raise();
521
522   return *this;
523 }
524
525 //=======================================================================
526 //function : GetCharacter
527 //purpose  : 
528 //=======================================================================
529
530 Storage_BaseDriver& FSD_File::GetCharacter(Standard_Character& aValue)
531 {
532   unsigned short i = 0;
533   if (!(myStream >> i)) {
534     // SGI : donne une erreur mais a une bonne valeur pour les caracteres ecrits
535     //       signes (-80 fait ios::badbit, mais la variable i est initialisee)
536     //
537     if (i == 0) Storage_StreamTypeMismatchError::Raise();
538     myStream.clear(ios::goodbit); // .clear(0) is not portable
539   }
540   aValue = (char)i;
541
542   return *this;
543 }
544
545 //=======================================================================
546 //function : GetExtCharacter
547 //purpose  : 
548 //=======================================================================
549
550 Storage_BaseDriver& FSD_File::GetExtCharacter(Standard_ExtCharacter& aValue)
551 {
552   if (!(myStream >> aValue)) Storage_StreamTypeMismatchError::Raise();
553   
554   return *this;
555 }
556
557 //=======================================================================
558 //function : GetInteger
559 //purpose  : 
560 //=======================================================================
561
562 Storage_BaseDriver& FSD_File::GetInteger(Standard_Integer& aValue)
563 {
564   if (!(myStream >> aValue)) Storage_StreamTypeMismatchError::Raise();
565
566   return *this;
567 }
568
569 //=======================================================================
570 //function : GetBoolean
571 //purpose  : 
572 //=======================================================================
573
574 Storage_BaseDriver& FSD_File::GetBoolean(Standard_Boolean& aValue)
575 {
576   if (!(myStream >> aValue)) Storage_StreamTypeMismatchError::Raise();
577
578   return *this;
579 }
580
581 //=======================================================================
582 //function : GetReal
583 //purpose  : 
584 //=======================================================================
585
586 Storage_BaseDriver& FSD_File::GetReal(Standard_Real& aValue)
587 {
588 #ifdef USEOSDREAL
589   char realbuffer[100];
590
591   realbuffer[0] = '\0';
592   if (!(myStream >> realbuffer)) Storage_StreamTypeMismatchError::Raise();
593   if (!OSD::CStringToReal(realbuffer,aValue)) Storage_StreamTypeMismatchError::Raise();
594
595   return *this;
596 #else
597   if (!(myStream >> aValue)) Storage_StreamTypeMismatchError::Raise();
598
599   return *this;
600 #endif
601 }
602
603 //=======================================================================
604 //function : GetShortReal
605 //purpose  : 
606 //=======================================================================
607
608 Storage_BaseDriver& FSD_File::GetShortReal(Standard_ShortReal& aValue)
609 {
610 #ifdef USEOSDREAL
611   char realbuffer[100];
612   Standard_Real r = 0.0;
613
614   realbuffer[0] = '\0';
615   if (!(myStream >> realbuffer)) Storage_StreamTypeMismatchError::Raise();
616   if (!OSD::CStringToReal(realbuffer,r)) Storage_StreamTypeMismatchError::Raise();
617
618   aValue = r;
619
620   return *this;
621 #else
622   if (!(myStream >> aValue)) Storage_StreamTypeMismatchError::Raise();
623  return *this;
624 #endif
625 }
626
627 //=======================================================================
628 //function : Destroy
629 //purpose  : 
630 //=======================================================================
631
632 void FSD_File::Destroy()
633 {
634   if (OpenMode() != Storage_VSNone) {
635     Close();
636   }
637 }
638
639 //=======================================================================
640 //function : BeginWriteInfoSection
641 //purpose  : -------------------------- INFO : WRITE
642 //=======================================================================
643
644 Storage_Error FSD_File::BeginWriteInfoSection() 
645 {
646   myStream << FSD_File::MagicNumber() << '\n';
647   myStream << "BEGIN_INFO_SECTION\n";
648   if (myStream.bad()) Storage_StreamWriteError::Raise();
649
650   return Storage_VSOk;
651 }
652
653 //=======================================================================
654 //function : WriteInfo
655 //purpose  : 
656 //=======================================================================
657
658 void FSD_File::WriteInfo(const Standard_Integer nbObj,
659                          const TCollection_AsciiString& dbVersion,
660                          const TCollection_AsciiString& date,
661                          const TCollection_AsciiString& schemaName,
662                          const TCollection_AsciiString& schemaVersion,
663                          const TCollection_ExtendedString& appName,
664                          const TCollection_AsciiString& appVersion,
665                          const TCollection_ExtendedString& dataType,
666                          const TColStd_SequenceOfAsciiString& userInfo) 
667 {
668   Standard_Integer i;
669
670   myStream << nbObj;
671   myStream << "\n";
672   myStream << dbVersion.ToCString() << "\n";
673   myStream << date.ToCString() << "\n";
674   myStream << schemaName.ToCString() << "\n";
675   myStream << schemaVersion.ToCString() << "\n";
676   WriteExtendedLine(appName);
677   myStream << appVersion.ToCString() << "\n";
678   WriteExtendedLine(dataType);
679   myStream << userInfo.Length() << "\n";
680
681   if (myStream.bad()) Storage_StreamWriteError::Raise();
682
683   for (i = 1; i <= userInfo.Length(); i++) {
684     myStream << userInfo.Value(i).ToCString() << "\n";
685     if (myStream.bad()) Storage_StreamWriteError::Raise();
686   }
687 }
688
689 //=======================================================================
690 //function : EndWriteInfoSection
691 //purpose  : read
692 //=======================================================================
693
694 Storage_Error FSD_File::EndWriteInfoSection() 
695 {
696   myStream << "END_INFO_SECTION\n";
697   if (myStream.bad())  Storage_StreamWriteError::Raise();
698   return Storage_VSOk;
699 }
700
701 //=======================================================================
702 //function : BeginReadInfoSection
703 //purpose  : 
704 //=======================================================================
705
706 Storage_Error FSD_File::BeginReadInfoSection() 
707 {
708   Storage_Error s;
709   TCollection_AsciiString l;
710   Standard_Size        len = strlen(FSD_File::MagicNumber());
711
712   ReadChar(l,len);
713   
714   if (strncmp(FSD_File::MagicNumber(),l.ToCString(),len) != 0) {
715     s = Storage_VSFormatError;
716   }
717   else {
718     s = FindTag("BEGIN_INFO_SECTION");
719   }
720
721   return s;
722 }
723
724 //=======================================================================
725 //function : ReadInfo
726 //purpose  : ------------------- INFO : READ
727 //=======================================================================
728
729 void FSD_File::ReadInfo(Standard_Integer& nbObj,
730                         TCollection_AsciiString& dbVersion,
731                         TCollection_AsciiString& date,
732                         TCollection_AsciiString& schemaName,
733                         TCollection_AsciiString& schemaVersion,
734                         TCollection_ExtendedString& appName,
735                         TCollection_AsciiString& appVersion,
736                         TCollection_ExtendedString& dataType,
737                         TColStd_SequenceOfAsciiString& userInfo) 
738 {
739   if (!(myStream >> nbObj)) Storage_StreamTypeMismatchError::Raise();
740
741   FlushEndOfLine();
742
743   ReadLine(dbVersion);
744   ReadLine(date);
745   ReadLine(schemaName);
746   ReadLine(schemaVersion);
747   ReadExtendedLine(appName);
748   ReadLine(appVersion);
749   ReadExtendedLine(dataType);
750
751   Standard_Integer i,len = 0;
752
753   if (!(myStream >> len)) Storage_StreamTypeMismatchError::Raise();
754
755   FlushEndOfLine();
756
757   TCollection_AsciiString line;
758
759   for (i = 1; i <= len && !IsEnd(); i++) {
760     ReadLine(line);
761     userInfo.Append(line);
762     line.Clear();
763   }
764 }
765
766 //=======================================================================
767 //function : EndReadInfoSection
768 //purpose  : COMMENTS SECTION
769 //           write
770 //=======================================================================
771
772 Storage_Error FSD_File::EndReadInfoSection() 
773 {
774   return FindTag("END_INFO_SECTION");
775 }
776
777 //=======================================================================
778 //function : BeginWriteCommentSection
779 //purpose  : ---------------- COMMENTS : WRITE
780 //=======================================================================
781
782 Storage_Error FSD_File::BeginWriteCommentSection() 
783 {
784   myStream << "BEGIN_COMMENT_SECTION\n";
785   if (myStream.bad()) Storage_StreamWriteError::Raise();
786   return Storage_VSOk;
787 }
788
789 //=======================================================================
790 //function : WriteComment
791 //purpose  : 
792 //=======================================================================
793
794 void FSD_File::WriteComment(const TColStd_SequenceOfExtendedString& aCom)
795 {
796  Standard_Integer i,aSize;
797
798  aSize = aCom.Length();
799  myStream << aSize << "\n";
800  if (myStream.bad()) Storage_StreamWriteError::Raise();
801
802  for (i = 1; i <= aSize; i++) {
803    WriteExtendedLine(aCom.Value(i));
804    if (myStream.bad()) Storage_StreamWriteError::Raise();
805  }
806 }
807
808 //=======================================================================
809 //function : EndWriteCommentSection
810 //purpose  : read
811 //=======================================================================
812
813 Storage_Error FSD_File::EndWriteCommentSection() 
814 {
815   myStream << "END_COMMENT_SECTION\n";
816   if (myStream.bad()) Storage_StreamWriteError::Raise();
817   return Storage_VSOk;
818 }
819
820 //=======================================================================
821 //function : BeginReadCommentSection
822 //purpose  : ---------------- COMMENTS : READ
823 //=======================================================================
824
825 Storage_Error FSD_File::BeginReadCommentSection() 
826 {
827   return FindTag("BEGIN_COMMENT_SECTION");
828 }
829
830 //=======================================================================
831 //function : ReadComment
832 //purpose  : 
833 //=======================================================================
834
835 void FSD_File::ReadComment(TColStd_SequenceOfExtendedString& aCom)
836 {
837   TCollection_ExtendedString line;
838   Standard_Integer           len,i;
839
840   if (!(myStream >> len)) Storage_StreamTypeMismatchError::Raise();
841   
842   FlushEndOfLine();  
843
844   for (i = 1; i <= len && !IsEnd(); i++) {
845     ReadExtendedLine(line);
846     aCom.Append(line);
847     line.Clear();
848   }
849 }
850
851 //=======================================================================
852 //function : EndReadCommentSection
853 //purpose  : 
854 //=======================================================================
855
856 Storage_Error FSD_File::EndReadCommentSection() 
857 {
858   return FindTag("END_COMMENT_SECTION");
859 }
860
861 //=======================================================================
862 //function : BeginWriteTypeSection
863 //purpose  : --------------- TYPE : WRITE
864 //=======================================================================
865
866 Storage_Error FSD_File::BeginWriteTypeSection() 
867 {
868   myStream << "BEGIN_TYPE_SECTION\n";
869   if (myStream.bad()) Storage_StreamWriteError::Raise();
870   return Storage_VSOk;
871 }
872
873 //=======================================================================
874 //function : SetTypeSectionSize
875 //purpose  : 
876 //=======================================================================
877
878 void FSD_File::SetTypeSectionSize(const Standard_Integer aSize) 
879 {
880   myStream << aSize << "\n";
881   if (myStream.bad()) Storage_StreamWriteError::Raise();
882 }
883
884 //=======================================================================
885 //function : WriteTypeInformations
886 //purpose  : 
887 //=======================================================================
888
889 void FSD_File::WriteTypeInformations(const Standard_Integer typeNum,
890                                       const TCollection_AsciiString& typeName) 
891 {
892   myStream << typeNum << " " << typeName.ToCString() << "\n";
893   if (myStream.bad()) Storage_StreamWriteError::Raise();
894 }
895
896 //=======================================================================
897 //function : EndWriteTypeSection
898 //purpose  : read
899 //=======================================================================
900
901 Storage_Error FSD_File::EndWriteTypeSection() 
902 {
903   myStream << "END_TYPE_SECTION\n";
904   if (myStream.bad()) Storage_StreamWriteError::Raise();
905   return Storage_VSOk;
906 }
907
908 //=======================================================================
909 //function : BeginReadTypeSection
910 //purpose  : ------------------- TYPE : READ
911 //=======================================================================
912
913 Storage_Error FSD_File::BeginReadTypeSection() 
914 {
915   return FindTag("BEGIN_TYPE_SECTION");
916 }
917
918 //=======================================================================
919 //function : TypeSectionSize
920 //purpose  : 
921 //=======================================================================
922
923 Standard_Integer FSD_File::TypeSectionSize() 
924 {
925   Standard_Integer i;
926
927   if (!(myStream >> i)) Storage_StreamTypeMismatchError::Raise();
928
929   FlushEndOfLine();
930
931   return i;
932 }
933
934 //=======================================================================
935 //function : ReadTypeInformations
936 //purpose  : 
937 //=======================================================================
938
939 void FSD_File::ReadTypeInformations(Standard_Integer& typeNum,
940                                     TCollection_AsciiString& typeName) 
941 {
942   if (!(myStream >> typeNum)) Storage_StreamTypeMismatchError::Raise();
943   if (!(myStream >> typeName)) Storage_StreamTypeMismatchError::Raise();
944   FlushEndOfLine();
945 }
946
947 //=======================================================================
948 //function : EndReadTypeSection
949 //purpose  : ROOT SECTION
950 //           write
951 //=======================================================================
952
953 Storage_Error FSD_File::EndReadTypeSection() 
954 {
955   return FindTag("END_TYPE_SECTION");
956 }
957
958 //=======================================================================
959 //function : BeginWriteRootSection
960 //purpose  : -------------------- ROOT : WRITE
961 //=======================================================================
962
963 Storage_Error FSD_File::BeginWriteRootSection() 
964 {
965   myStream << "BEGIN_ROOT_SECTION\n";
966   if (myStream.bad()) Storage_StreamWriteError::Raise();
967   return Storage_VSOk;
968 }
969
970 //=======================================================================
971 //function : SetRootSectionSize
972 //purpose  : 
973 //=======================================================================
974
975 void FSD_File::SetRootSectionSize(const Standard_Integer aSize) 
976 {
977   myStream << aSize << "\n";
978   if (myStream.bad()) Storage_StreamWriteError::Raise();
979 }
980
981 //=======================================================================
982 //function : WriteRoot
983 //purpose  : 
984 //=======================================================================
985
986 void FSD_File::WriteRoot(const TCollection_AsciiString& rootName, const Standard_Integer aRef, const TCollection_AsciiString& rootType) 
987 {
988   myStream << aRef << " " << rootName.ToCString() << " " << rootType.ToCString() << "\n";
989   if (myStream.bad()) Storage_StreamWriteError::Raise();
990 }
991
992 //=======================================================================
993 //function : EndWriteRootSection
994 //purpose  : read
995 //=======================================================================
996
997 Storage_Error FSD_File::EndWriteRootSection() 
998 {
999   myStream << "END_ROOT_SECTION\n";
1000   if (myStream.bad()) Storage_StreamWriteError::Raise();
1001   return Storage_VSOk;
1002 }
1003
1004 //=======================================================================
1005 //function : BeginReadRootSection
1006 //purpose  : ----------------------- ROOT : READ
1007 //=======================================================================
1008
1009 Storage_Error FSD_File::BeginReadRootSection() 
1010 {
1011   return FindTag("BEGIN_ROOT_SECTION");
1012 }
1013
1014 //=======================================================================
1015 //function : RootSectionSize
1016 //purpose  : 
1017 //=======================================================================
1018
1019 Standard_Integer FSD_File::RootSectionSize() 
1020 {
1021   Standard_Integer i;
1022
1023   if (!(myStream >> i)) Storage_StreamTypeMismatchError::Raise();
1024   
1025   FlushEndOfLine();
1026   
1027   return i;
1028 }
1029
1030 //=======================================================================
1031 //function : ReadRoot
1032 //purpose  : 
1033 //=======================================================================
1034
1035 void FSD_File::ReadRoot(TCollection_AsciiString& rootName, Standard_Integer& aRef,TCollection_AsciiString& rootType) 
1036 {
1037   if (!(myStream >> aRef)) Storage_StreamTypeMismatchError::Raise();
1038   ReadWord(rootName);
1039   ReadWord(rootType);
1040 }
1041
1042 //=======================================================================
1043 //function : EndReadRootSection
1044 //purpose  : REF SECTION
1045 //           write
1046 //=======================================================================
1047
1048 Storage_Error FSD_File::EndReadRootSection() 
1049 {
1050   return FindTag("END_ROOT_SECTION");
1051 }
1052
1053 //=======================================================================
1054 //function : BeginWriteRefSection
1055 //purpose  : -------------------------- REF : WRITE
1056 //=======================================================================
1057
1058 Storage_Error FSD_File::BeginWriteRefSection() 
1059 {
1060   myStream << "BEGIN_REF_SECTION\n";
1061   if (myStream.bad()) Storage_StreamWriteError::Raise();
1062   return Storage_VSOk;
1063 }
1064
1065 //=======================================================================
1066 //function : SetRefSectionSize
1067 //purpose  : 
1068 //=======================================================================
1069
1070 void FSD_File::SetRefSectionSize(const Standard_Integer aSize) 
1071 {
1072   myStream << aSize << "\n";
1073   if (myStream.bad()) Storage_StreamWriteError::Raise();
1074 }
1075
1076 //=======================================================================
1077 //function : WriteReferenceType
1078 //purpose  : 
1079 //=======================================================================
1080
1081 void FSD_File::WriteReferenceType(const Standard_Integer reference,
1082                                   const Standard_Integer typeNum) 
1083 {
1084   myStream << reference << " " << typeNum << "\n";
1085   if (myStream.bad()) Storage_StreamWriteError::Raise();
1086 }
1087
1088 //=======================================================================
1089 //function : EndWriteRefSection
1090 //purpose  : read
1091 //=======================================================================
1092
1093 Storage_Error FSD_File::EndWriteRefSection() 
1094 {
1095   myStream << "END_REF_SECTION\n";
1096   if (myStream.bad()) Storage_StreamWriteError::Raise();
1097   return Storage_VSOk;
1098 }
1099
1100 //=======================================================================
1101 //function : BeginReadRefSection
1102 //purpose  : ----------------------- REF : READ
1103 //=======================================================================
1104
1105 Storage_Error FSD_File::BeginReadRefSection() 
1106 {
1107   return FindTag("BEGIN_REF_SECTION");
1108 }
1109
1110 //=======================================================================
1111 //function : RefSectionSize
1112 //purpose  : 
1113 //=======================================================================
1114
1115 Standard_Integer FSD_File::RefSectionSize() 
1116 {
1117   Standard_Integer i;
1118
1119   if (!(myStream >> i)) Storage_StreamTypeMismatchError::Raise();
1120   FlushEndOfLine();
1121
1122   return i;
1123 }
1124
1125 //=======================================================================
1126 //function : ReadReferenceType
1127 //purpose  : 
1128 //=======================================================================
1129
1130 void FSD_File::ReadReferenceType(Standard_Integer& reference,
1131                                  Standard_Integer& typeNum) 
1132 {
1133   if (!(myStream >> reference)) Storage_StreamTypeMismatchError::Raise();
1134   if (!(myStream >> typeNum)) Storage_StreamTypeMismatchError::Raise();
1135   FlushEndOfLine();
1136 }
1137
1138 //=======================================================================
1139 //function : EndReadRefSection
1140 //purpose  : DATA SECTION
1141 //           write
1142 //=======================================================================
1143
1144 Storage_Error FSD_File::EndReadRefSection() 
1145 {
1146   return FindTag("END_REF_SECTION");
1147 }
1148
1149 //=======================================================================
1150 //function : BeginWriteDataSection
1151 //purpose  : -------------------- DATA : WRITE
1152 //=======================================================================
1153
1154 Storage_Error FSD_File::BeginWriteDataSection() 
1155 {
1156   myStream << "BEGIN_DATA_SECTION";
1157   if (myStream.bad()) Storage_StreamWriteError::Raise();
1158   return Storage_VSOk;
1159 }
1160
1161 //=======================================================================
1162 //function : WritePersistentObjectHeader
1163 //purpose  : 
1164 //=======================================================================
1165
1166 void FSD_File::WritePersistentObjectHeader(const Standard_Integer aRef,
1167                                            const Standard_Integer aType) 
1168 {
1169   myStream << "\n#" << aRef << "=%" << aType;
1170   if (myStream.bad()) Storage_StreamWriteError::Raise();
1171 }
1172
1173 //=======================================================================
1174 //function : BeginWritePersistentObjectData
1175 //purpose  : 
1176 //=======================================================================
1177
1178 void FSD_File::BeginWritePersistentObjectData() 
1179 {
1180   myStream << "( ";
1181   if (myStream.bad()) Storage_StreamWriteError::Raise();
1182 }
1183
1184 //=======================================================================
1185 //function : BeginWriteObjectData
1186 //purpose  : 
1187 //=======================================================================
1188
1189 void FSD_File::BeginWriteObjectData() 
1190 {
1191   myStream << "( ";
1192   if (myStream.bad()) Storage_StreamWriteError::Raise();
1193 }
1194
1195 //=======================================================================
1196 //function : EndWriteObjectData
1197 //purpose  : 
1198 //=======================================================================
1199
1200 void FSD_File::EndWriteObjectData() 
1201 {
1202   myStream << ") ";
1203   if (myStream.bad()) Storage_StreamWriteError::Raise();
1204 }
1205
1206 //=======================================================================
1207 //function : EndWritePersistentObjectData
1208 //purpose  : 
1209 //=======================================================================
1210
1211 void FSD_File::EndWritePersistentObjectData() 
1212 {
1213   myStream << ")";
1214   if (myStream.bad()) Storage_StreamWriteError::Raise();
1215 }
1216
1217 //=======================================================================
1218 //function : EndWriteDataSection
1219 //purpose  : read
1220 //=======================================================================
1221
1222 Storage_Error FSD_File::EndWriteDataSection() 
1223 {
1224   myStream << "\nEND_DATA_SECTION\n";
1225   if (myStream.bad()) Storage_StreamWriteError::Raise();
1226   return Storage_VSOk;
1227 }
1228
1229 //=======================================================================
1230 //function : BeginReadDataSection
1231 //purpose  : ---------------------- DATA : READ
1232 //=======================================================================
1233
1234 Storage_Error FSD_File::BeginReadDataSection() 
1235 {
1236   return FindTag("BEGIN_DATA_SECTION");
1237 }
1238
1239 //=======================================================================
1240 //function : ReadPersistentObjectHeader
1241 //purpose  : 
1242 //=======================================================================
1243
1244 void FSD_File::ReadPersistentObjectHeader(Standard_Integer& aRef,
1245                                           Standard_Integer& aType) 
1246 {
1247   char c;
1248
1249   myStream.get(c);
1250
1251   while (c != '#') {
1252     if (IsEnd() || (c != ' ') || (c == '\n')) {
1253       Storage_StreamFormatError::Raise();
1254     }
1255     myStream.get(c);
1256   }
1257
1258   if (!(myStream >> aRef)) Storage_StreamTypeMismatchError::Raise();
1259
1260   myStream.get(c);
1261
1262
1263    while (c != '=') {
1264     if (IsEnd() || (c != ' ') || (c == '\n')) {
1265       Storage_StreamFormatError::Raise();
1266     }
1267     myStream.get(c);
1268   }
1269
1270   myStream.get(c);
1271
1272   while (c != '%') {
1273     if (IsEnd() || (c != ' ') || (c == '\n')) {
1274       Storage_StreamFormatError::Raise();
1275     }
1276     myStream.get(c);
1277   }
1278
1279   if (!(myStream >> aType)) Storage_StreamTypeMismatchError::Raise();
1280 //  cout << "REF:" << aRef << " TYPE:"<< aType << endl;
1281 }
1282
1283 //=======================================================================
1284 //function : BeginReadPersistentObjectData
1285 //purpose  : 
1286 //=======================================================================
1287
1288 void FSD_File::BeginReadPersistentObjectData() 
1289 {
1290   char c;
1291   myStream.get(c);
1292   while (c != '(') {
1293     if (IsEnd() || (c != ' ') || (c == '\n')) {
1294       Storage_StreamFormatError::Raise();
1295     }
1296     myStream.get(c);
1297   }
1298
1299 //cout << "BeginReadPersistentObjectData" << endl;
1300 }
1301
1302 //=======================================================================
1303 //function : BeginReadObjectData
1304 //purpose  : 
1305 //=======================================================================
1306
1307 void FSD_File::BeginReadObjectData() 
1308 {
1309
1310   char c;
1311   myStream.get(c);
1312   while (c != '(') {
1313     if (IsEnd() || (c != ' ') || (c == '\n')) {
1314       Storage_StreamFormatError::Raise();
1315     }
1316     myStream.get(c);
1317   }
1318
1319 //  cout << "BeginReadObjectData" << endl;
1320 }
1321
1322 //=======================================================================
1323 //function : EndReadObjectData
1324 //purpose  : 
1325 //=======================================================================
1326
1327 void FSD_File::EndReadObjectData() 
1328 {
1329
1330   char c;
1331   myStream.get(c);
1332   while (c != ')') {
1333     if (IsEnd() || (c != ' ') || (c == '\n')) {
1334       Storage_StreamFormatError::Raise();
1335     }
1336     myStream.get(c);
1337   }
1338
1339 //  cout << "EndReadObjectData" << endl;
1340 }
1341
1342 //=======================================================================
1343 //function : EndReadPersistentObjectData
1344 //purpose  : 
1345 //=======================================================================
1346
1347 void FSD_File::EndReadPersistentObjectData() 
1348 {
1349
1350   char c;
1351
1352   myStream.get(c);
1353   while (c != ')') {
1354     if (IsEnd() || (c != ' ') || (c == '\n')) {
1355       Storage_StreamFormatError::Raise();
1356     }
1357     myStream.get(c);
1358   }
1359
1360   myStream.get(c);
1361   while (c != '\n') {
1362     if (IsEnd() || (c != ' ')) {
1363       Storage_StreamFormatError::Raise();
1364     }
1365     myStream.get(c);
1366   }
1367 //  cout << "EndReadPersistentObjectData" << endl;
1368 }
1369
1370 //=======================================================================
1371 //function : EndReadDataSection
1372 //purpose  : 
1373 //=======================================================================
1374
1375 Storage_Error FSD_File::EndReadDataSection() 
1376 {
1377   return FindTag("END_DATA_SECTION");
1378 }
1379
1380 //=======================================================================
1381 //function : Tell
1382 //purpose  : return position in the file. Return -1 upon error.
1383 //=======================================================================
1384
1385 Storage_Position FSD_File::Tell()
1386 {
1387   switch (OpenMode()) {
1388   case Storage_VSRead:
1389     return (Storage_Position) myStream.tellp();
1390   case Storage_VSWrite:
1391     return (Storage_Position) myStream.tellg();
1392   case Storage_VSReadWrite: {
1393     Storage_Position aPosR  = (Storage_Position) myStream.tellp();
1394     Storage_Position aPosW  = (Storage_Position) myStream.tellg();
1395     if (aPosR < aPosW)
1396       return aPosW;
1397     else
1398       return aPosR;
1399   }
1400   default: return -1;
1401   }
1402   return -1;
1403 }