OWLNext    7.0
Borland's Object Windows Library for the modern age
Loading...
Searching...
No Matches
file.cpp
Go to the documentation of this file.
1//------------------------------------------------------------------------------
2// ObjectWindows
3// Copyright (c) 1993, 1996 by Borland International, All Rights Reserved
4// Copyright (c) 1996-1998 Bidus Yura, All rights Reserved
5//
6/// \file
7/// TFile class implementation.
8/// Fully rewritten by Yura Bidus
9//------------------------------------------------------------------------------
10#include <owl/pch.h>
11#include <owl/file.h>
12#include <owl/wsyscls.h>
13
14#if defined(OWL5_COMPAT) // See TFile::GetStatus.
15#include <owl/filename.h>
16#endif
17
18#if defined(__BORLANDC__)
19# pragma option -w-ccc // Disable warning; "Condition is always true/false".
20# pragma option -w-inl // Disable warning in standard library; "Functions containing 'statement' are not expanded inline".
21#endif
22
23using namespace std;
24
25namespace owl {
26
28
29/// \cond
30
31// ////////////////////////////
32// Internal support structure
33#include <pshpack1.h>
34struct __i_uint32_32{
35 uint32 Lo;
36 uint32 Hi;
37};
38struct __i_int32_32{
39 uint32 Lo;
40 int32 Hi;
41};
42#include <poppack.h>
43
44/// \endcond
45
46
48
49//
50/// Constructs an exception handling class with identity IDS_BADFILEFORMAT.
51//
57
58//
59/// Construct a TXBadFormat exception from scratch, and throws it.
60//
61void
63{
64 TXBadFormat().Throw();
65}
66
67
70{
71 return new TXBadFormat(*this);
72}
73
74
75//
76//
77void
79{
80 throw *this;
81}
82
83//------------------------------------------------------------------------------
84////////////////////////////////////////////////////////////////////////////////
85//
86// class TDiskFileHandle
87// ~~~~~ ~~~~~~~~~~~~~~~
88//
89//
90// helper functions
91static void sys2Mode(uint32& access, uint32& sharedMode, uint32& howOpen, uint32 openMode)
92{
97
99 sharedMode |= 0; // exclisive - default
104
105// if(openMode & TFile::PermNone) // not implemented in WIN32
106// ShareMode |= 0; //
107
109 howOpen |= CREATE_NEW ; // open
111 howOpen |= CREATE_ALWAYS; // open
113 howOpen |= OPEN_EXISTING; // open
115 howOpen |= TRUNCATE_EXISTING; // open
116}
117
118//
119// class TDiskFileHandle
120// ~~~~ ~~~~~~~~~~~~~~~
121//
123{
124 OpenMode = mode;
126
127 uint32 Access = 0;
128 uint32 ShareMode = 0;
129 uint32 HowOpen = 0;
130 sys2Mode(Access, ShareMode, HowOpen, OpenMode);
131
133 Handle = ::CreateFile(FileName.c_str(),Access,ShareMode,nullptr,HowOpen,flags,nullptr);
134}
135
136
137//
139:
140 Handle(handle), OpenMode(mode), FileName(fileName)
141{
142}
143
144
145//
148{
149 HANDLE hHandle = 0;
152 0, false, DUPLICATE_SAME_ACCESS) && hHandle)
153 return new TDiskFileHandle(hHandle, FileName.c_str(), OpenMode);
154 return nullptr;
155}
156
157
158//
160{
161 return ::GetLastError();
162}
163
164
165//
167{
169 return false;
170 return true;
171}
172
173
174//
176{
178 if(::ReadFile(Handle, buffer, numBytes, &u32Ret, nullptr))
179 return u32Ret;
180 return TFILE_ERROR;
181}
182
183
184//
186{
188 if(::WriteFile(Handle, buffer, numBytes, &u32ret, nullptr))
189 return true;
190 return false;
191}
192
193
194//
196{
198 return false;
200 return true;
201 return false;
202}
203
204
205//
207{
208 uint32 ret = ::SetFilePointer(Handle,0,nullptr,static_cast<uint32>(TFile::cur));
209 return uint64(ret);
210}
211
212
213//
215{
217 ul.Lo = ::GetFileSize(Handle, reinterpret_cast<DWORD *>(&ul.Hi));
218 return *reinterpret_cast<uint64*>(&ul);
219}
220
221
222//
224{
225 if(Seek(static_cast<long>(newLen), TFile::beg) == TFILE_ERROR)
226 return false;
228 return true;
229 return false;
230}
231
232
233//
235{
236 uint32 ret = ::SetFilePointer(Handle,0,nullptr,static_cast<uint32>(TFile::cur));
237 if( ret != 0xFFFFFFFF)
238 return ret;
239 return TFILE_ERROR;
240}
241
242
243//
245{
246 uint32 ret = ::GetFileSize(Handle, nullptr);
247 if( ret != 0xFFFFFFFF)
248 return ret;
249 return TFILE_ERROR;
250}
251
252
254{
255 __i_int32_32 ul = *reinterpret_cast<__i_int32_32*>(&offset);
256 ul.Lo = ::SetFilePointer(Handle,ul.Lo,reinterpret_cast<LONG*>(&ul.Hi),static_cast<uint32>(origin));
257 return uint64(*reinterpret_cast<int64*>(&ul));
258}
259
260//
262{
263 uint32 ret = ::SetFilePointer(Handle,offset,nullptr,static_cast<uint32>(origin));
264 if( ret != 0xFFFFFFFF)
265 return ret;
266 return TFILE_ERROR;
267}
268
269
270//
272{
274 return true;
275 return false;
276}
277
278//
280{
281 return ::LockFile(Handle,position,0, count,0);
282}
283
284//
286{
287 if(::UnlockFile(Handle,position, 0, count, 0))
288 return true;
289 return false;
290}
291
292
294{
295 __i_uint32_32 up = *reinterpret_cast<__i_uint32_32*>(&position);
296 __i_uint32_32 uc = *reinterpret_cast<__i_uint32_32*>(&count);
297 return ::LockFile(Handle, up.Lo,up.Hi,uc.Lo,uc.Hi);
298}
299//
301{
302 __i_uint32_32 up = *reinterpret_cast<__i_uint32_32*>(&position);
303 __i_uint32_32 uc = *reinterpret_cast<__i_uint32_32*>(&count);
304 return ::UnlockFile(Handle, up.Lo,up.Hi, uc.Lo,uc.Hi);
305}
306
307
308///////////////////////////////////////////////////////////////////////////
309//--------------------------------------------------------------
310//------------------------------------------------------------------------------
311
351
352
357
358//
360{
361 if (::_tfullpath(status.fullName, FileName.c_str(), COUNTOF(status.fullName)) == nullptr){
362 status.fullName[0] = 0;
363 return false;
364 }
366 if(attrib == TFILE_ERROR)
367 return false;
368
369 status.attribute = __sys2Atr(attrib);
370
372 if(::GetFileTime(Handle, &ftCreate, &ftAccess, &ftWrite) == FALSE)
373 return false;
374
375 //uint16 ftime,fdate;
376 //FileTimeToDosDateTime(&ftCreate, &fdate, &ftime);
377 //status.createTime = __MakeTTime(fdate, ftime);
378 status.createTime = TTime(ftCreate);
379 //FileTimeToDosDateTime(&ftWrite, &fdate, &ftime);
380 //status.modifyTime = __MakeTTime(fdate, ftime);
381 status.modifyTime = TTime(ftWrite);
382 //FileTimeToDosDateTime(&ftAccess, &fdate, &ftime);
383 //status.accessTime = __MakeTTime(fdate, ftime);
384 status.accessTime = TTime(ftAccess);
385 status.size = Length();
386
387 return true;
388}
389
390
391//////////////////////////////////////////////////////////////////////
392// class TFile
393// ~~~~~ ~~~~~
394//
395//
396//
397/// If ShouldClose is true the file is closed. If the Handle is not FileNull Handle
398/// is deleted. Buffer is deleted.
399//
401{
402 if(ShouldClose)
403 Close();
404 if(Handle != FileNull)
405 delete Handle;
406 delete[] Buffer;
407}
408
409
410// if TFileHandle not support Clone() will throw TXNotSupportedCall()
412{
413 if(ShouldClose)
414 Close();
415 if(Handle != FileNull)
416 delete Handle;
417 Handle = file.GetHandle()->Clone();
418 ShouldClose = true;
419
420 CHECK(Handle);
421
422 if(!Handle)
424}
425
426
427/// Opens file name with the given mode. Returns true if successful, false
428/// otherwise. Calling Open when the file is already open will fail.
430{
431 if(IsOpen())
432 return false;
434 if(!Handle->IsOpen()){
435 delete Handle;
437 }
438 ShouldClose = true;
439 return IsOpen();
440}
441
442//------------------------------------------------------------------------------
443
444/// Closes the file. Returns true if successful, false otherwise.
446{
447 if(IsOpen() && ShouldClose){
448 if(!Handle->Close())
449 return false;
450 }
451 if(Handle != FileNull)
452 delete Handle;
454 ShouldClose = false;
455 return true;
456}
457
458
459/// Performs any pending I/O functions. Returns true if successful; false otherwise.
461{
463 return Handle->Flush();
464}
465
466
467/// Locks count bytes, beginning at position of the file. Returns true if
468/// successful; false otherwise.
470{
472 return Handle->LockRange(position, count);
473}
474
475/// Unlocks the range at the given Position. Returns true if successful; false
476/// otherwise.
478{
480 return Handle->UnlockRange(position, count);
481}
482
483
484inline int binCVTCharMBF (uint8* src, uint8* dst, int /*type*/, int size, int count)
485{
486 memcpy(dst, src, count*size);
487 return count*size;
488}
489//------------------------------------------------------------------------------
490static int binCVTShortMBF(uint8* _src, uint8* _dst, int /*type*/, int size, int count)
491{
492 int retval = count*size;
493 uint16* src = reinterpret_cast<uint16*>(_src);
494 uint16* dst = reinterpret_cast<uint16*>(_dst);
495 while(count--)
496 *dst++ = SwapUint16(*src++);
497
498 return retval;
499}
500//------------------------------------------------------------------------------
501static int binCVTLongMBF(uint8* _src, uint8* _dst, int /*type*/, int size, int count)
502{
503 int retval = count*size;
504 uint32* src = reinterpret_cast<uint32*>(_src);
505 uint32* dst = reinterpret_cast<uint32*>(_dst);
506 while(count--)
507 *dst++ = SwapUint32(*src++);
508
509 return retval;
510}
511//------------------------------------------------------------------------------
512static int binCVTFloatMBF (uint8* _src, uint8* _dst, int /*type*/, int size, int count)
513{
514 int retval = count*size;
515 uint32* src = reinterpret_cast<uint32*>(_src);
516 uint32* dst = reinterpret_cast<uint32*>(_dst);
517 while(count--)
518 *dst++ = SwapUint32(*src++);
519
520 return retval;
521}
522//------------------------------------------------------------------------------
523static int binCVTDoubleMBF (uint8*, uint8*, int, int, int)
524{
525 return 0;
526}
527//------------------------------------------------------------------------------
528static int binCVTInt64MBF (uint8* _src, uint8* _dst, int /*type*/, int size, int count) //???????????????????
529{
530 int retval = count*size;
531 __i_uint32_32* src = reinterpret_cast<__i_uint32_32*>(_src);
532 __i_uint32_32* dst = reinterpret_cast<__i_uint32_32*>(_dst);
533 while(count--){
534 dst->Lo = SwapUint32(src->Hi);
535 dst->Hi = SwapUint32(src->Lo);
536 dst++;
537 src++;
538 }
539 return retval;
540}
541//------------------------------------------------------------------------------
542//------------------------------------------------------------------------------
543inline int binCVTCharLBF (uint8* src, uint8* dst, int /*type*/, int size, int count){
544 memcpy(dst, src, count*size);
545 return count*size;
546}
547//------------------------------------------------------------------------------
548static int binCVTShortLBF (uint8* _src, uint8* _dst, int /*type*/, int size, int count)
549{
550 int retval = count*size;
551 uint16* src = reinterpret_cast<uint16*>(_src);
552 uint16* dst = reinterpret_cast<uint16*>(_dst);
553 while(count--)
554 *dst++ = SwapUint16(*src++);
555
556 return retval;
557}
558//------------------------------------------------------------------------------
559static int binCVTLongLBF (uint8* _src, uint8* _dst, int /*type*/, int size, int count)
560{
561 int retval = count*size;
562 uint32* src = reinterpret_cast<uint32*>(_src);
563 uint32* dst = reinterpret_cast<uint32*>(_dst);
564 while(count--)
565 *dst++ = SwapUint32(*src++);
566
567 return retval;
568}
569//------------------------------------------------------------------------------
570static int binCVTFloatLBF (uint8* _src, uint8* _dst, int /*type*/, int size, int count)
571{
572 int retval = count*size;
573 uint32* src = reinterpret_cast<uint32*>(_src);
574 uint32* dst = reinterpret_cast<uint32*>(_dst);
575 while(count--)
576 *dst++ = SwapUint32(*src++);
577
578 return retval;
579}
580//------------------------------------------------------------------------------
581static int binCVTDoubleLBF (uint8*, uint8*, int, int, int)
582{
583 return 0;
584}
585//------------------------------------------------------------------------------
586static int binCVTInt64LBF (uint8* _src, uint8* _dst, int /*type*/, int size, int count)
587{
588 int retval = count*size;
589 __i_uint32_32* src = reinterpret_cast<__i_uint32_32*>(_src);
590 __i_uint32_32* dst = reinterpret_cast<__i_uint32_32*>(_dst);
591 while(count--){
592 dst->Lo = SwapUint32(src->Hi);
593 dst->Hi = SwapUint32(src->Lo);
594 dst++;
595 src++;
596 }
597 return retval;
598}
599//------------------------------------------------------------------------------
600typedef int (*cvtDispatchFunc)(uint8*, uint8*, int, int, int); /* Dispatch table entry */
601static cvtDispatchFunc dispatchMBF[] = { /* MBF -> LBF */
602 nullptr, /* varEnd */
603 binCVTLongMBF, /* varPOINTER */
604 binCVTCharMBF, /* varCHAR */
605 binCVTCharMBF, /* varUCHAR */
606 binCVTShortMBF, /* varSHORT */
607 binCVTLongMBF, /* varLONG */
608 binCVTCharMBF, /* varINT8 */
609 binCVTShortMBF, /* varINT16 */
610 binCVTLongMBF, /* varINT32 */
611 binCVTShortMBF, /* varUSHORT */
612 binCVTLongMBF, /* varULONG */
613 binCVTCharMBF, /* varUINT8 */
614 binCVTShortMBF, /* varUINT16 */
615 binCVTLongMBF, /* varUINT32 */
616 binCVTFloatMBF, /* varFLOAT */
617 binCVTDoubleMBF, /* varDOUBLE */
618 binCVTInt64MBF, /* varINT64 */
619 binCVTInt64MBF, /* varUINT64r */
620};
621
622static cvtDispatchFunc dispatchLBF[] = { /* LBF -> MBF */
623 nullptr, /* varEnd */
624 binCVTLongLBF, /* varPOINTER */
625 binCVTCharLBF, /* varCHAR */
626 binCVTCharLBF, /* varUCHAR */
627 binCVTShortMBF, /* varSHORT */
628 binCVTLongLBF, /* varLONG */
629 binCVTCharLBF, /* varINT8 */
630 binCVTShortMBF, /* varINT16 */
631 binCVTLongLBF, /* varINT32 */
632 binCVTShortLBF, /* varUSHORT */
633 binCVTLongLBF, /* varULONG */
634 binCVTCharLBF, /* varUINT8 */
635 binCVTShortLBF, /* varUINT16 */
636 binCVTLongLBF, /* varUINT32 */
637 binCVTFloatLBF, /* varFLOAT */
638 binCVTDoubleLBF, /* varDOUBLE */
639 binCVTInt64LBF, /* varINT64 */
640 binCVTInt64LBF, /* varUINT64r */
641};
642
643//------------------------------------------------------------------------------
644#define BINCHECKRTYPE(type) \
645 if ( (type) <= 0 || (type) > varLastMember) \
646 return 0;
647
648#define BINCHECKWTYPE(type) \
649 if ((type) <= 0 || (type) > varLastMember) \
650 return 0;
651
652#define BINCHECKNBYTES(nBytes) \
653 if((nBytes) <= 0 ) \
654 return 0;
655//------------------------------------------------------------------------------
656/// Returns the number of bytes in a binary data structure.
658{
659 uint count = 0;
660 for(TBinField *bfp = fields; bfp->Count; bfp++)
661 count += bfp->Count*bfp->Bytes;
662 return count;
663}
664//------------------------------------------------------------------------------
665/// Read binary structure from file.
666/// Returns # of bytes read
668{
669 TBinField *bfp; /* Field pointer */
670 uint count; /* Number of bytes read */
671 int n; /* Read status & # bytes read */
675 // int (*dispatch)(uint8*, uint8*, int, int, int ); /* Dispatch table entry */
676
677 /* Check all values in the fields array before doing anything. */
678 for(bfp = fields; bfp->Count; bfp++ ) {
679 BINCHECKRTYPE(bfp->Type);
680 BINCHECKNBYTES(bfp->Bytes)
681 }
682 // count size of structure
683 count = StructSize(fields);
684
685 // if no conversion
686 if(EndianType() == type)
687 return static_cast<uint>(Read(buffer, count));
688
689 // if Litle endian machine -> read as Big endian -> last choise
690 // else as Little endian
691 binReadDisp = dispatchMBF;
692 if(EndianType() == boBig_Endian)
693 binReadDisp = dispatchLBF;
694
695 if(Buffer && BufSize < count){
696 delete[] Buffer;
697 Buffer = nullptr;
698 }
699
700 if(!Buffer){
701 BufSize = count*5;
702 Buffer = new uint8[BufSize];
703 }
704
705 if(!Read(Buffer, count))
706 return 0;
707
708 count = 0;
710 for(bfp = fields; bfp->Count; bfp++ ){
711 dispatch = binReadDisp[bfp->Type];
712 if ((n = (*dispatch)(curBuffer,static_cast<uint8*>(buffer), bfp->Type, bfp->Bytes, bfp->Count)) == -1)
713 return 0; /* Error occured */
714 count += n;
715 buffer = static_cast<uint8*>(buffer) + bfp->Bytes * bfp->Count;
716 curBuffer += n;
717 }
718 return count;
719}
720//------------------------------------------------------------------------------
721/// Writes structures to binary file based on fields description.
722/// Returns # of bytes written
724{
725 TBinField *bfp; /* Field pointer */
726 uint count; /* Number of bytes read */
727 int n; /* Read status & # bytes read */
731
732 /* Check all values in the fields array before doing anything. */
733 for(bfp = fields; bfp->Count; bfp++ ) {
734 BINCHECKRTYPE(bfp->Type);
735 BINCHECKNBYTES(bfp->Bytes)
736 }
737 // count size of structure
738 count = StructSize(fields);
739
740 // if no conversion
741 if(EndianType() == type)
742 return Write(buffer, count);
743
744 // if Litle endian machine -> read as Big endian -> last choise
745 // else as Little endian
746 binReadDisp = dispatchMBF;
747 if(EndianType() == boBig_Endian)
748 binReadDisp = dispatchLBF;
749
750 if(Buffer && BufSize < count){
751 delete[] Buffer;
752 Buffer = nullptr;
753 }
754
755 if(!Buffer){
756 BufSize = count*5;
757 Buffer = new uint8[BufSize];
758 }
759
760 count = 0;
762 for(bfp = fields; bfp->Count; bfp++ ){
763 dispatch = binReadDisp[bfp->Type];
764 if ((n = (*dispatch)(static_cast<uint8*>(buffer), curBuffer, bfp->Type, bfp->Bytes, bfp->Count)) == -1)
765 return 0; /* Error occured */
766 count += n;
767 buffer = static_cast<uint8*>(buffer) + bfp->Bytes * bfp->Count;
768 curBuffer += n;
769 }
770 return Write(Buffer, count);
771}
772//------------------------------------------------------------------------------
773/// Read binary structure from buffer.
774/// Returns # of bytes read
776{
777 TBinField *bfp; /* Field pointer */
778 int count; /* Number of bytes read */
779 int n; /* Read status & # bytes read */
783// int (*dispatch)(uint8*, uint8*, int, int, int ); /* Dispatch table entry */
784
785 /* Check all values in the fields array before doing anything. */
786 for(bfp = fields; bfp->Count; bfp++ ) {
787 BINCHECKRTYPE(bfp->Type);
788 BINCHECKNBYTES(bfp->Bytes)
789 }
790 // count size of structure
791 count = StructSize(fields);
792
793 // if no conversion
794 if(EndianType() == type){
795 memcpy(buffer, ReadBuf, count);
796 return count;
797 }
798
799 // if Litle endian machine -> read as Big endian -> last choise
800 // else as Little endian
801 binReadDisp = dispatchMBF;
802 if(EndianType() == boBig_Endian)
803 binReadDisp = dispatchLBF;
804
805 count = 0;
807 for(bfp = fields; bfp->Count; bfp++ ){
808 dispatch = binReadDisp[bfp->Type];
809 if ((n = (*dispatch)(curBuffer,static_cast<uint8*>(buffer), bfp->Type, bfp->Bytes, bfp->Count)) == -1)
810 return 0; /* Error occured */
811 count += n;
812 buffer = static_cast<uint8*>(buffer) + bfp->Bytes * bfp->Count;
813 curBuffer += n;
814 }
815 return count;
816}
817//------------------------------------------------------------------------------
818/// Writes structures to buffer based on fields description.
819/// Returns # of bytes written
821{
822 TBinField *bfp; /* Field pointer */
823 int count; /* Number of bytes read */
824 int n; /* Read status & # bytes read */
828
829 /* Check all values in the fields array before doing anything. */
830 for(bfp = fields; bfp->Count; bfp++ ) {
831 BINCHECKRTYPE(bfp->Type);
832 BINCHECKNBYTES(bfp->Bytes)
833 }
834 // count size of structure
835 count = StructSize(fields);
836
837 // if no conversion
838 if(EndianType() == type){
839 memcpy(OutBuf, buffer, count);
840 return count;
841 }
842
843 // if Litle endian machine -> read as Big endian -> last choise
844 // else as Little endian
845 binReadDisp = dispatchMBF;
846 if(EndianType() == boBig_Endian)
847 binReadDisp = dispatchLBF;
848
849 count = 0;
851 for(bfp = fields; bfp->Count; bfp++ ){
852 dispatch = binReadDisp[bfp->Type];
853 if ((n = (*dispatch)(static_cast<uint8*>(buffer), curBuffer, bfp->Type, bfp->Bytes, bfp->Count)) == -1)
854 return 0; /* Error occured */
855 count += n;
856 buffer = static_cast<uint8*>(buffer) + bfp->Bytes * bfp->Count;
857 curBuffer += n;
858 }
859 return count;
860}
861
862
863static TBinField CharField[] = {
864 {varCHAR, 1, 1},
865 {varEnd, 0, 0},
866};
867static TBinField ShortField[] = {
868 {varSHORT, 2, 1},
869 {varEnd, 0, 0},
870};
871static TBinField LongField[] = {
872 {varLONG, 4, 1},
873 {varEnd, 0, 0},
874};
875static TBinField FloatField[] = {
876 {varFLOAT, 4, 1},
877 {varEnd, 0, 0},
878};
879static TBinField DoubleField[] = {
880 {varDOUBLE, 8, 1},
881 {varEnd, 0, 0},
882};
883static TBinField Long64Field[] = {
884 {varDOUBLE, 8, 1},
885 {varEnd, 0, 0},
886};
887static TBinField PointField[] = {
888 {varLONG, 4, 2},
889 {varEnd, 0, 0},
890};
891static TBinField RectField[] = {
892 {varLONG, 4, 2},
893 {varEnd, 0, 0},
894};
895static TBinField* FieldTypes[] = {
896 CharField,
897 ShortField,
898 LongField,
899 FloatField,
900 DoubleField,
901 Long64Field,
902 PointField,
903 RectField,
904};
905//------------------------------------------------------------------------------
906/// Read binary predefined structure from file.
907/// Returns # of bytes read
912//------------------------------------------------------------------------------
913/// Writes predefined structures to binary file.
918
919#if defined(OWL5_COMPAT) // must be moved to TFileName
920//
921/// Fills status with the status for name. Returns nonzero if successful, 0 otherwise.
922/// \note This is only available when OWL has been compiled with
923/// OWL5_COMPAT defined. The TFileName class should be used instead.
925{
926 return TFileName(name).GetStatus(status);
927}
928
929//
930/// Sets file name's status to status.
931/// \note This is only available when OWL has been compiled with OWL5_COMPAT
932/// defined. The TFileName class should be used instead.
933bool TFile::SetStatus(LPCTSTR name, const TFileStatus & status)
934{
935 return TFileName(name).SetStatus(status);
936}
937#endif //
938//
940{
941 int size = static_cast<int>(file.readUint32());
942 s = _T("");
943 s.resize(size+1);
944 if(file.Read(reinterpret_cast<void*>(const_cast<tchar*>(s.c_str())), size) == TFILE_ERROR)
945 size = -1;
946 s[size+1] = _T('\0');
947 return file;
948}
949
950
951
952uint8
954{
955 char c;
956 Read(&c, 1);
957 return c;
958}
959
960
961uint16
963{
964
965 uint16 i;
967 return i;
968}
969
970
971uint32
973 uint32 i;
975 return i;
976}
977
978
979uint64
985
986
987float
989{
990 float i;
992 return i;
993}
994
995
996double
998{
999 double i;
1001 return i;
1002}
1003
1004
1006{
1007 Write(&c, 1);
1008}
1009
1010
1012{
1013 WriteStruct(reinterpret_cast<void*>(const_cast<uint16*>(&i)), TypeShort, boLittle_Endian);
1014}
1015
1016
1017void
1019{
1020 WriteStruct(reinterpret_cast<void*>(const_cast<uint32*>(&i)), TypeLong, boLittle_Endian);
1021}
1022
1023
1024void
1026{
1027 WriteStruct(reinterpret_cast<void*>(const_cast<uint64*>(&i)), TypeLong64, boLittle_Endian);
1028}
1029
1030
1031void
1032TFile::writeFloat( const float f)
1033{
1034 WriteStruct(reinterpret_cast<void*>(const_cast<float*>(&f)), TypeFloat, boLittle_Endian);
1035}
1036
1037
1038void
1039TFile::writeDouble( const double d)
1040{
1041 WriteStruct(reinterpret_cast<void*>(const_cast<double*>(&d)), TypeDouble, boLittle_Endian);
1042}
1043
1044
1045//------------------------------------------------------------------------------
1046//
1047// TBufferedFile
1048// ~~~~~~~~~~~~~
1049
1050//
1051/// The buffer is flushed. If ShouldDelete is true the buffer is deleted.
1052//
1054{
1055 FlushBuffer();
1056 if(ShouldDelete)
1057 delete[] FileBuffer;
1058 FileBuffer = nullptr;
1059}
1060//------------------------------------------------------------------------------
1061/// Allocates a buffer of size bytes.
1063{
1064 BufferEmpty = true;
1065 EndPos = FileBufSize = size;
1066 CurByte = FileBuffer = new uint8[size];
1067 ShouldDelete = true;
1068 CurPos = StartPos = 0;
1069}
1070//------------------------------------------------------------------------------
1071/// Flushes the buffer by writing any unwritten data to the file. This function is
1072/// called by Flush() before the operating system is called to flush its buffers.
1074{
1075 // if open mode -> write flush buffer
1076 if(GetHandle() && (GetHandle()->GetOpenMode() & WriteOnly)){
1077 if(CurPos != StartPos){
1079 WARNX(OwlFileSystem,1, 0,"TBufferedFile::FlushBuffer() error Seek(), line: " << __LINE__);
1080 return false;
1081 }
1082 StartPos = CurPos;
1085 BufferEmpty = true;
1086 }
1087 }
1088 return true;
1089}
1090
1091
1092/// Flushes the current buffer and then deletes it if ShouldDelete is true. If
1093/// buffer is not NULL it is assigned to FileBuffer; otherwise FileBuffer is
1094/// allocated size bytes. ShouldDelete is then set.
1095//
1096void TBufferedFile::SetBuffer(uint8* buffer, uint size, bool shouldDelete)
1097{
1098 FlushBuffer();
1099 if(ShouldDelete)
1100 delete[] FileBuffer;
1101 ShouldDelete = shouldDelete;
1102 if(buffer)
1104 else{
1105 FileBuffer = CurByte = new uint8[size];
1106 ShouldDelete = true;
1107 }
1108 FileBufSize = size;
1109 // StartPos = CurPos; set in FlushBuffer
1111}
1112
1113
1114//
1115/// Repositions the file pointer to offset bytes from the specified
1116/// origin. If the position moved to is outside of the buffer, the buffer is
1117/// flushed. Returns the position moved to or TFILE64_ERROR on error. To get
1118/// extended error information, call LastError.
1119//
1121{
1123 // calculate absolute position ->
1125 if(origin == cur)
1126 position += offset;
1127 else if(origin == end)
1129 else
1130 position = offset;
1133 CurPos = static_cast<uint32>(position);
1135 }
1136 else{
1137 if(!FlushBuffer()){
1138 WARNX(OwlFileSystem,1, 0,"TBufferedFile::Seek() error FlushBuffer(), line: " << __LINE__);
1139 return TFILE64_ERROR;
1140 }
1142 if(newpos != TFILE64_ERROR){
1143 StartPos = CurPos = static_cast<uint32>(position);
1146 BufferEmpty = true;
1147 }
1148 else{
1149 WARNX(OwlFileSystem,1, 0,"TBufferedFile::Seek() error Seek(), line: " << __LINE__);
1150 return TFILE64_ERROR;
1151 }
1152 }
1153 return oldpos;
1154}
1155
1156
1157//
1158/// Repositions the file pointer to offset bytes from the specified origin. If the
1159/// position moved to is outside of the buffer, the buffer is flushed. Returns the
1160/// position moved to or TFILE_ERROR on error. To get extended error information,
1161/// call LastError.
1162//
1164{
1166 // calculate absolute position ->
1168 if(origin == cur)
1169 position += offset;
1170 else if(origin == end)
1171 position = Length() + offset;
1172 else
1173 position = offset;
1175 if(position >= StartPos && position < EndPos){
1176 CurPos = position;
1178 }
1179 else{
1180 if(!FlushBuffer()){
1181 WARNX(OwlFileSystem,1, 0,"TBufferedFile::Seek() error FlushBuffer(), line: " << __LINE__);
1182 return TFILE_ERROR;
1183 }
1185 if(newpos != TFILE_ERROR){
1189 BufferEmpty = true;
1190 }
1191 else{
1192 WARNX(OwlFileSystem,1, 0,"TBufferedFile::Seek() error Seek(), line: " << __LINE__);
1193 return TFILE_ERROR;
1194 }
1195 }
1196 return oldpos;
1197}
1198
1199
1200//
1201/// Reads numBytes from the file into buffer. The number of bytes read is returned.
1202//
1204{
1207 uint8* data = static_cast<uint8*>(buffer);
1208 // fill buffer if empty and buffer exist
1209 if(BufferEmpty && FileBufSize){
1210 StartPos = CurPos = Position();
1212 if(ret == TFILE_ERROR){
1213 WARNX(OwlFileSystem,ret==TFILE_ERROR, 0,"TBufferedFile::Write() error Read(), line: " << __LINE__);
1214 return ret;
1215 }
1217 EndPos = StartPos + ret;
1218 BufferEmpty = false;
1219 }
1220
1221 while(numBytes > 0){
1223 if(numBytes > dataSize){
1224 if(dataSize > 0){
1226 numBytes -= dataSize;
1227 data += dataSize;
1228 }
1229 uint32 ret;
1230 if(numBytes > FileBufSize){
1232 if(ret == TFILE_ERROR){
1233 WARNX(OwlFileSystem,ret==TFILE_ERROR, 0,"TBufferedFile::Write() error Read(), line: " << __LINE__);
1234 return ret;
1235 }
1236 BufferEmpty = true;
1237 numBytes = 0;
1238 }
1239 else{
1241 if(ret == TFILE_ERROR || ret == 0){
1242 if((buffer == data) && (ret == TFILE_ERROR)){
1243 WARNX(OwlFileSystem,ret==TFILE_ERROR, 0,"TBufferedFile::Write() error Read(), line: " << __LINE__);
1244 StartPos = CurPos;
1245 return ret;
1246 }
1247 else{
1249
1250 // Note: The number of read bytes should not exceed numBytes (uint32) so we can cast unchecked.
1251 // TODO: Widen the parameter and return type to avoid this narrowing cast.
1252
1253 size_t n = data - static_cast<uint8*>(buffer);
1254 return static_cast<uint32>(n);
1255 }
1256 }
1257 }
1258 StartPos = CurPos;
1259 EndPos = StartPos + ret;
1261 }
1262 else{
1264 data += numBytes;
1265 CurPos += numBytes;
1266 CurByte += numBytes;
1267 numBytes = 0;
1268 }
1269 }
1270 return retval;
1271}
1272
1273
1274/// Writes numBytes of buffer to the file. If numBytes is greater than the size of
1275/// the buffer the buffer is flushed and the data is written directly to the file;
1276/// if the amount of data in the buffer plus numBytes is greater than the capacity
1277/// of the buffer the buffer is filled and written to the file and the remaining
1278/// data is placed in the buffer; otherwise the data is appended to the buffer.
1279/// Returns true if the operation is successful; false otherwise.
1280//
1282{
1284 // if data size greater then buffer -> write directly
1285 if(numBytes > FileBufSize){
1286 if(!FlushBuffer()){
1287 WARNX(OwlFileSystem,1, 0,"TBufferedFile::Write() error FlushBuffer(), line: " << __LINE__);
1288 return false;
1289 }
1291 return false;
1292 StartPos = CurPos = Position();
1295 return true;
1296 }
1297 // else use buffer for output
1298 uint8* data = static_cast<uint8*>(const_cast<void*>(buffer));
1299 while(numBytes > 0L){
1301 if( numBytes > freeSize ){
1303 numBytes -= freeSize;
1304 data += freeSize;
1305 CurPos += freeSize;
1307 WARNX(OwlFileSystem,1, 0,"TBufferedFile::Write() error Write(), line: " << __LINE__);
1308 return false;
1309 }
1310 StartPos = CurPos;
1313 }
1314 else{
1316 data += numBytes;
1317 CurByte += numBytes;
1318 CurPos += numBytes;
1319 numBytes = 0;
1320 }
1321 }
1322 return true;
1323}
1324
1325
1326//------------------------------------------------------------------------------
1327//
1328// TTextFile
1329// ~~~~~~~~~
1330
1331//
1332/// Reads up to size characters and places them in buffer. Normal termination is
1333/// when a \\r\\n character sequence is encountered. The string in buffer is NULL
1334/// terminated. NULL is returned on failure; a pointer to buffer is returned on
1335/// success.
1336//
1337LPTSTR
1339{
1341
1342 LPTSTR str = buffer;
1343 LPTSTR Buff = reinterpret_cast<LPTSTR>(CurByte);
1344 uint length = 0;
1345 if(BufferEmpty){
1346 StartPos = CurPos = Position();
1348 if(retval == TFILE_ERROR || retval == 0){
1349 WARNX(OwlFileSystem,retval==TFILE_ERROR,0,_T("TTextFile::GetString() error Read(), line: ") << __LINE__);
1350 return nullptr;
1351 }
1354 BufferEmpty = false;
1355 }
1356
1357 while(*Buff && *Buff != _T('\r') && *Buff != _T('\n') && length < size){
1358 // if end -> fill buffer
1359 if(CurPos >= EndPos){
1360 CurByte = reinterpret_cast<uint8*>(Buff);
1362 if((retval == TFILE_ERROR || retval == 0) && length==0){
1363 WARNX(OwlFileSystem,retval==TFILE_ERROR,0,_T("TTextFile::GetString() error Read(), line: ") <<__LINE__);
1364 return nullptr;
1365 }
1366 StartPos = CurPos;
1369 Buff = reinterpret_cast<LPTSTR>(CurByte);
1370 if(!retval)
1371 break;
1372 }
1373#if 0 // check UNICODE support
1374 *str = *Buff;
1375 LPTSTR p = CharNext(str);
1376 length += p - str;
1377 str = p;
1378 p = CharNext(Buff);
1379 uint delta = p - Buff;
1380 CurPos += delta;
1381 Buff += delta;
1382#else
1383 *str++ = *Buff++;
1384 length++;
1385 CurPos++;
1386#endif
1387 }
1388 if(*Buff == _T('\r')){
1389 Buff++;
1390 CurPos++;
1391 }
1392 if(*Buff == _T('\n')){
1393 Buff++;
1394 CurPos++;
1395 }
1396
1397 CurByte = reinterpret_cast<uint8*>(Buff);
1398
1399 // End string with 0
1400 *str = _T('\0');
1401 return (*CurByte || length) ? buffer : nullptr;
1402}
1403
1404namespace
1405{
1406
1407 //
1408 // For use with CopyText
1409 //
1410 struct TTextFileGetString
1411 {
1412 TTextFile& f;
1413 TTextFileGetString(TTextFile& f_) : f(f_) {}
1414 int operator()(LPTSTR buf, int bufSize)
1415 {
1416 LPTSTR r = f.GetString(buf, static_cast<uint32>(bufSize));
1417 return r ? bufSize - 1 : 0;
1418 }
1419 };
1420
1421} // namespace
1422
1423//
1424/// String-aware overload
1425//
1427{
1428 return CopyText(size, TTextFileGetString(*this));
1429}
1430
1431
1432//
1433/// Writes the NULL terminated character string in buffer to the file and adds a
1434/// terminating \\r\\n character sequence. The NULL character is not written. On
1435/// success true is returned; false otherwise.
1436//
1437bool
1439{
1441
1442 size_t len = ::_tcslen(buffer) * sizeof(tchar);
1443
1444 // TODO: Widen the parameter type for Write to avoid this check and the narrowing cast.
1445 //
1447 return false;
1448 bool status = TBufferedFile::Write(buffer, static_cast<uint32>(len));
1449 if(status)
1450 status = TBufferedFile::Write(_T("\r\n"), 2);
1451 return status;
1452}
1453
1454
1455uint8
1457{
1458 uint8 c;
1459 Read(&c, 1);
1460 return c;
1461}
1462
1463
1464uint16
1466{
1467 return static_cast<uint16>(readUint32());
1468}
1469
1470
1471uint32
1473{
1475 return 0; //?????????????????????????
1476}
1477uint64
1479{
1481 return 0; //?????????????????????????
1482}
1483
1484float
1486{
1487 return static_cast<float>(readDouble());
1488}
1489double
1491{
1493 return 0; //?????????????????????????
1494}
1495
1496
1497void
1499{
1500 Write(&u, 1);
1501}
1502
1503
1504void
1506{
1507 writeUint32(u);
1508}
1509
1510
1511void
1513{
1514 tchar buf[20];
1515#if defined __GNUC__
1516 _tprintf(buf, _T("%d"), u);
1517#else
1518 _ltot(u, buf, 10);
1519#endif
1520 Write(buf, static_cast<uint32>(::_tcslen(buf))); // TODO: Widen the paramteter type to avoid this narrowing cast.
1521 return;
1522}
1523
1524
1525void
1527{
1529 return; //?????????????????????????????
1530}
1531void
1533{
1534 writeDouble(f);
1535}
1536void
1538{
1540 return;//????????????????????????????????????????????
1541}
1542
1543
1544//
1545/// Constructor for iterating through file. The bufsize paramater is used for
1546/// setting the buffer size.
1547//
1549:
1550 File(&file),
1551 LineBuffer(nullptr),
1552 BuffSize(bufsize),
1553 LineNumber(0),
1554 Done(false)
1555{
1556 LineBuffer = new tchar[BuffSize];
1557 Done = !NextLine();
1558}
1559//------------------------------------------------------------------------------
1560/// Deletes the buffer.
1565//------------------------------------------------------------------------------
1566// all work do here -> must fill LineBuffer
1567//
1568/// Loads the next line in the file. Returns true if successful; false otherwise.
1569//
1571{
1572 if(!File || !File->IsOpen())
1573 return false;
1574 return ToBool(File->GetString(LineBuffer, BuffSize) != nullptr);
1575}
1576
1577
1578//------------------------------------------------------------------------------
1579
1580/// \cond
1581
1582#include <pshpack1.h>
1583struct __TChunk {
1584 uint32 CkId; // 'RIFF' or 'LIST'
1585 uint32 Size; // data size
1586 uint32 Type; // type for main chunk 'WAVE'
1587};
1588#include <poppack.h>
1589
1590/// \endcond
1591
1592//------------------------------------------------------------------------------
1593static TBinField ChunkField[] = {
1594 {varLONG, 4, 1}, /* FOURCC CkId; // 'RIFF' or 'LIST' */
1595 {varLONG, 4, 1}, /* data size */
1596 {varEnd, 0, 0},
1597};
1598//------------------------------------------------------------------------------
1599static TBinField ListField[] = {
1600 {varLONG, 4, 1}, /* FOURCC CkId; // 'RIFF' or 'LIST' */
1601 {varLONG, 4, 1}, /* data size */
1602 {varLONG, 4, 1}, /* type for main chunk 'WAVE' */
1603 {varEnd, 0, 0},
1604};
1605//------------------------------------------------------------------------------
1606// without first member
1607static TBinField ChunkField1[] = {
1608 {varLONG, 4, 1}, /* data size */
1609 {varEnd, 0, 0},
1610};
1611//------------------------------------------------------------------------------
1612static TBinField ListField1[] = {
1613 {varLONG, 4, 1}, /* data size */
1614 {varLONG, 4, 1}, /* type for main chunk 'WAVE' */
1615 {varEnd, 0, 0},
1616};
1617//------------------------------------------------------------------------------
1618/// Writes a data structure of the specified type to the associated file.
1620{
1621 CHECK(IsOpen());
1622
1624 chunk.CkId = 0;
1625 TBinField* fields = ListField;
1626
1627 info.Flags = TCkInfo::ckDirty;
1628 chunk.CkId = info.CkId; // type of Atom
1629 if(type == cfCreateList){
1630 chunk.CkId = FOURCC_LIST;
1631 info.Flags |= TCkInfo::ckList;
1632 }
1633 else if(type == cfCreateRiff){
1634 chunk.CkId = FOURCC_RIFF;
1635 info.Flags |= TCkInfo::ckRiff;
1636 }
1637
1638 chunk.Type = info.Type; // type of Atom
1639 chunk.Size = 0; // data size not include size of atom
1640
1641 if(type == cfCreateChunk)
1642 fields = ChunkField;
1643
1645 WARNX(OwlFileSystem,1, 0,"TRiffFile::CreateChunk() error WriteStruct(), line: " << __LINE__);
1646 return false;
1647 }
1648
1649 info.Offset = Position();
1650 if(type == cfCreateList || type == cfCreateRiff)
1651 info.Offset -= 4;
1652
1653 return true;
1654}
1655//------------------------------------------------------------------------------
1657{
1658 CHECK(IsOpen());
1659
1660 if(info.Flags & TCkInfo::ckDirty){
1661 info.Size = Position() - info.Offset;
1662 long offset = info.Offset - sizeof(__TChunk) + 4;
1663 if(Seek(offset, beg) == TFILE_ERROR){
1664 WARNX(OwlFileSystem,1, 0,"TRiffFile::Ascent() error Seek(), line: " << __LINE__);
1665 return false;
1666 }
1667
1669 chunk.CkId = info.CkId;
1670 chunk.Type = info.Type;
1671 chunk.Size = info.Size; // data size not include size of atom
1672
1673 if(info.Flags & TCkInfo::ckList)
1674 chunk.CkId = FOURCC_LIST;
1675 else if(info.Flags & TCkInfo::ckRiff)
1676 chunk.CkId = FOURCC_RIFF;
1677
1678 TBinField* fields = ChunkField;
1679 if(info.Flags & TCkInfo::ckList || info.Flags & TCkInfo::ckRiff)
1680 fields = ListField;
1681
1683 WARNX(OwlFileSystem,1, 0,"TRiffFile::Ascent() error WriteStruct(), line: " << __LINE__);
1684 return false;
1685 }
1686 info.Flags = 0;
1687 }
1688 // seek to beginning the next atom if any
1689 long size = info.Offset + info.Size;
1690 if(Seek(size, beg) == TFILE_ERROR){
1691 WARNX(OwlFileSystem,1, 0,"TRiffFile::Ascent() error Seek(), line: " << __LINE__);
1692 return false;
1693 }
1694
1695 return true;
1696}
1697/* -------------------------------------------------------------------------- */
1699{
1700 CHECK(IsOpen());
1701
1703
1704 if(flags & ffReset){
1705 if(parent){
1706 long offset = parent->Offset;
1707 if(parent->Flags & TCkInfo::ckList || parent->Flags & TCkInfo::ckRiff)
1708 offset += 4;
1709 if(Seek(offset, beg) == TFILE_ERROR){
1710 WARNX(OwlFileSystem,1, 0,"TRiffFile::Descent() error Seek(), line: " << __LINE__);
1711 return false;
1712 }
1713 }
1714 else // else if parent = 0
1715 if(SeekToBegin() == TFILE_ERROR){
1716 WARNX(OwlFileSystem,1, 0,"TRiffFile::Descent() error SeekToBegin(), line: " << __LINE__);
1717 return false;
1718 }
1719 }
1720
1721 bool bRiff;
1722 bool done = false;
1723 bool retval = false;
1724 uint32 riff, size;
1726 TBinField longField[] = { {varLONG, 4, 1}, {varEnd, 0, 0},};
1727
1728 do{
1730 WARNX(OwlFileSystem,1, 0,"TRiffFile::Descent() error ReadStruct(), line: " << __LINE__);
1731 return false;
1732 }
1733
1734 fields = ChunkField1;
1735 chunk.CkId = riff;
1736 info.Flags = 0;
1737
1738 bRiff = false;
1739 if(riff == FOURCC_RIFF){
1740 info.Flags |= TCkInfo::ckRiff;
1741 bRiff = true;
1742 fields = ListField1;
1743 }
1744 else if(riff == FOURCC_LIST){
1745 info.Flags |= TCkInfo::ckList;
1746 bRiff = true;
1747 fields = ListField1;
1748 }
1749
1750 if(!ReadStruct(&chunk.Size, fields, boLittle_Endian)){
1751 WARNX(OwlFileSystem,1, 0,"TRiffFile::Descent() error ReadStruct(), line: " << __LINE__);
1752 return false;
1753 }
1754
1755 info.Offset = Position();
1756 if(bRiff)
1757 info.Offset -= 4;
1758
1759 info.Size = chunk.Size;
1760
1761 // if any atom
1762 if(flags & ffFindAny){
1763 info.CkId = chunk.CkId;
1764 info.Type = bRiff ? chunk.Type : 0;
1765 retval = true;
1766 break;
1767 }
1768 //if set flag FindChunk search it
1769 else if(flags & ffFindChunk && chunk.CkId == info.CkId){
1770 info.Type = 0;
1771 retval = true;
1772 break;
1773 }
1774 else if(flags & ffFindList && chunk.Type == info.Type){
1775 info.Type = chunk.Type;
1776 info.CkId = FOURCC_LIST;
1777 retval = true;
1778 break;
1779 }
1780 else if(flags & ffFindRiff && chunk.CkId == FOURCC_RIFF){
1781 info.Type = chunk.Type;
1782 info.CkId = FOURCC_RIFF;
1783 retval = true;
1784 break;
1785 }
1786
1787 size = chunk.Size;
1788 // if list chunk exclude size one field
1789 if(bRiff)
1790 size -= 4;
1791 if(Seek(static_cast<long>(size), cur) == TFILE_ERROR){
1792 done = true;
1793 retval = true;
1794 }
1795 }
1796 while(!done);
1797
1798 return retval;
1799}
1800
1801
1802/// \cond
1803
1804#if !defined(qtstruct_h)
1805#include <pshpack1.h>
1806struct __MacAtom {
1807 uint32 Size;
1808 uint32 Type;
1809};
1810static TBinField MacAtomFields[] = {
1811 {varLONG, 4, 1}, /* uint32 Size; */
1812 {varCHAR, 1, 4}, /* uint32 Type; not swappable */
1813 {varEnd, 0, 0},
1814};
1815#include <poppack.h>
1816#endif
1817
1818/// \endcond
1819
1820/* -------------------------------------------------------------------------- */
1821bool TQtFile::Descent(TQtInfo& info, TQtInfo* parent, const TFindFlags flags)
1822{
1823 CHECK(IsOpen());
1824
1826
1827 uint32 position = 0;
1829
1830 if(flags & ffReset){
1831 if(parent){
1832 if(Seek(static_cast<long>(parent->Offset), beg) == TFILE_ERROR){
1833 WARNX(OwlFileSystem,1, 0,"TQtFile::Descent() error seek line: " << __LINE__);
1834 return false;
1835 }
1836 max_size = parent->Size + parent->Offset;
1837 position = parent->Offset;
1838 }
1839 else{ // else if parent = 0
1840 max_size = Length();
1841 if(SeekToBegin() == TFILE_ERROR){
1842 WARNX(OwlFileSystem,1, 0,"TQtFile::Descent() error seek to begin line: " << __LINE__);
1843 return false;
1844 }
1845 }
1846 }
1847 else{
1848 position = Position();
1849 if(parent)
1850 max_size = parent->Size + parent->Offset - position;
1851 else // else if parent = 0
1852 max_size = Length();
1853 }
1854 bool done = false;
1855 bool status = false;
1856
1857 do{
1859 if(atom.Type == info.Type){
1860 info.Size = atom.Size;
1861 info.Offset = Position();
1862 info.Flags = 0;
1863 status = true;
1864 done = true;
1865 }
1866 //if set flag FindChunk search it
1867 if(atom.Type != info.Type && flags & ffFindChunk){
1868 if (atom.Size==0 ||
1869 Seek(long(atom.Size-sizeof(atom)),cur)==TFILE_ERROR)
1870 done = true;
1871 position += atom.Size;
1872 }
1873 else
1874 done = true;
1875 }
1876 else
1877 done = true;
1878 }
1879 while(!done && position < max_size);
1880
1881 return status;
1882}
1883//------------------------------------------------------------------------------
1885{
1886 CHECK(IsOpen());
1887 if(info.Flags & TQtInfo::qtDirty){
1888 info.Size = Position() - info.Offset + sizeof(__MacAtom);
1889 long offset = info.Offset - sizeof(__MacAtom);
1890 if(Seek(offset, beg)==TFILE_ERROR){
1891 WARNX(OwlFileSystem,1, 0,"TQtFile::Ascent() error seek, line: " << __LINE__);
1892 return false;
1893 }
1894
1896 atom.Type = info.Type; // type of Atom
1897 atom.Size = info.Size; // data size include size of atom
1899 WARNX(OwlFileSystem,1, 0,"TQtFile::Ascent() error write to file, line: " << __LINE__);
1900 return false;
1901 }
1902 info.Flags = 0;
1903 }
1904 // seek to beginning the next atom if any
1905 return ToBool(Seek(long(info.Size+info.Offset-sizeof(__MacAtom)), beg) != TFILE_ERROR);
1906}
1907// -----------------------------------------------------------------------------
1908/// Writes a data structure of the specified type to the associated file.
1910{
1911 CHECK(IsOpen());
1912
1914 info.Flags = TQtInfo::qtDirty;
1915 atom.Type = info.Type; // type of Atom
1916 atom.Size = 0; // data size not include size of atom
1917
1919 WARNX(OwlFileSystem,1, 0,"TQtFile::CreateChunk() error write to file, line: " << __LINE__);
1920 return false;
1921 }
1922
1923 info.Offset = Position();
1924 return ToBool(info.Offset != TFILE_ERROR);
1925}
1926
1927
1928// -----------------------------------------------------------------------------
1929static void sys2StrmMode(int& uMode, uint32 openMode)
1930{
1931 if(!(openMode & TFile::Text))
1932 uMode |= ios::binary;
1934 uMode |= ios::in|ios::out;
1937 uMode |= ios::app;
1938 }
1939 else if(openMode & TFile::ReadOnly)
1940 uMode |= ios::in;
1941 else if(openMode & TFile::WriteOnly)
1942 uMode |= ios::out;
1943
1947 uMode |= ios::trunc; // create
1948}
1949// -----------------------------------------------------------------------------
1950// class TStreamHandle
1951// ~~~~~ ~~~~~~~~~~~~~
1952//
1953//
1955:
1956 Parent(parent),
1957 FileName(fileName),
1958 OpenMode(mode)
1959{
1960 // fstream
1961 int uMode = 0;
1962 sys2StrmMode(uMode, mode);
1964 Parent->open(_W2A(fileName.c_str()), static_cast<ios::openmode>(uMode));
1965}
1966//
1968{
1969 return Parent->bad();
1970}
1971//
1973{
1974 return Parent->rdbuf()->is_open();
1975}
1976//
1979{
1981 return nullptr;//????????????????????????????????
1982}
1983//
1985{
1986 if(Parent->rdbuf()->close() == nullptr)
1987 return false;
1988 return true;
1989}
1990//
1992{
1993 Parent->read(static_cast<tchar*>(buffer), numBytes/sizeof(tchar));
1994 streamsize n = Parent->gcount();
1995
1996 // Note: n cannot be greater than numBytes, so we can cast unchecked.
1997 // TODO: Widen the parameter and return type to avoid this narrowing cast.
1998 //
1999 return Parent->fail() == 0 ? numBytes : static_cast<uint32>(n);
2000}
2001//
2003{
2004 Parent->write(static_cast<const tchar *>(buffer), numBytes/sizeof(tchar));
2005 return Parent->fail()==0 ? true : false;
2006}
2007//
2009{
2010 return Length(static_cast<uint32>(newLen));
2011}
2012//
2014{
2016 if(retval==TFILE_ERROR)
2017 return TFILE64_ERROR;
2018 return uint64(retval);
2019}
2020//
2022{
2023 return uint64(Length());
2024}
2025//
2027{
2028// if(chsize((uint)Handle->GetHandle(), (long)newLen) != TFILE_ERROR)
2029// return true;
2030 TXNotSupportedCall::Raise();//?????????????????????????????
2031 return false;
2032}
2033//
2035{
2038 retval = Parent->tellp();
2039 else
2040 retval = Parent->tellg();
2041 if(retval == streampos(-1))
2042 return TFILE_ERROR;
2043 return static_cast<uint32>(retval);
2044}
2045//
2047{
2049 streampos retval = Parent->tellp();
2050 if(retval == streampos(-1))
2051 return TFILE_ERROR;
2052 return static_cast<uint32>(retval);
2053 }
2054 uint32 last_pos = (const_cast<TStreamHandle*>(this))->Seek(0l, TFile::end);
2055 uint32 pos = Position();
2056 (const_cast<TStreamHandle*>(this))->Seek(static_cast<long>(last_pos), TFile::beg);
2057 return pos;
2058}
2059//
2061{
2062 return uint64(Seek(static_cast<long>(offset), origin));
2063}
2064//
2066{
2069 Parent->seekp(static_cast<streamoff>(offset), static_cast<ios::seekdir>(origin));
2070 else
2071 Parent->seekg(static_cast<streamoff>(offset), static_cast<ios::seekdir>(origin));
2072 return position;
2073}
2074//
2076{
2078 Parent->flush();
2079 return true;
2080}
2081//
2082bool TStreamHandle::LockRange(uint32 /*position*/, uint32 /*count*/)
2083{
2085 return false;
2086}
2087//
2088bool TStreamHandle::UnlockRange(uint32 /*position*/, uint32 /*count*/)
2089{
2091 return false;
2092}
2093//
2094//
2096{
2097 return LockRange(static_cast<uint32>(position), static_cast<uint32>(count));
2098}
2099//
2101{
2102 return UnlockRange(static_cast<uint32>(position), static_cast<uint32>(count));
2103}
2104
2106{
2108 return false;
2109}
2110
2111
2112// -----------------------------------------------------------------------------
2113//
2114// TStreamFile in work
2115// ~~~~~~~~~~~
2116//
2117//------------------------------------------------------------------------------
2119{
2120 if(IsOpen())
2121 return false;
2122 Handle = new TStreamHandle(this, fileName, mode);
2123 if(!Handle->IsOpen()){
2124 delete reinterpret_cast<TStreamFile*>(Handle);
2125 Handle = FileNull;
2126 }
2127 return IsOpen();
2128}
2129//------------------------------------------------------------------------------
2130
2131} // OWL namespace
2132////////////////////////////////////////////////////////////////////////////////
2133////////////////////////////////////////////////////////////////////////////////
2134
#define CHECK(condition)
Definition checks.h:239
#define WARNX(group, condition, level, message)
Definition checks.h:277
#define PRECONDITION(condition)
Definition checks.h:227
#define DIAG_DEFINE_GROUP_INIT(f, g, e, l)
Definition checks.h:429
virtual uint32 Read(void *buffer, uint32 numBytes)
Reads numBytes from the file into buffer. The number of bytes read is returned.
Definition file.cpp:1203
virtual uint32 Length() const
Returns the file length plus the length of unwritten data in the buffer.
Definition file.h:1110
virtual ~TBufferedFile()
The buffer is flushed. If ShouldDelete is true the buffer is deleted.
Definition file.cpp:1053
virtual bool Write(const void *buffer, uint32 numBytes)
Writes numBytes of buffer to the file.
Definition file.cpp:1281
uint32 EndPos
Offset in file to the last data byte in the buffer.
Definition file.h:425
virtual bool FlushBuffer()
Flushes the buffer by writing any unwritten data to the file.
Definition file.cpp:1073
uint8 * CurByte
Pointer to current position in the buffer.
Definition file.h:416
virtual uint64 Length64() const
Returns the file length plus the length of unwritten data in the buffer.
Definition file.h:1096
virtual void InitBuffer(uint size=DefaultBufferSize)
Allocates a buffer of size bytes.
Definition file.cpp:1062
uint FileBufSize
Size of FileBuffer in bytes.
Definition file.h:413
uint8 * FileBuffer
Buffer used to store data in.
Definition file.h:407
bool BufferEmpty
True if the buffer is empty; false otherwise.
Definition file.h:428
uint32 StartPos
Offset in file to byte 0 of the buffer.
Definition file.h:422
virtual uint64 Seek(int64 offset, TSeekDir origin=beg)
Repositions the file pointer to offset bytes from the specified origin.
Definition file.cpp:1120
virtual uint32 Position() const
Returns the current position of the file pointer.
Definition file.h:1106
uint32 CurPos
Offset in file to current position.
Definition file.h:419
bool ShouldDelete
True if the buffer should be deleted.
Definition file.h:410
virtual void SetBuffer(uint8 *buffer, uint size, bool shouldDelete=true)
Flushes the current buffer and then deletes it if ShouldDelete is true.
Definition file.cpp:1096
TDiskFileHandle * Clone() const
Definition file.cpp:147
virtual bool UnlockRange(uint32 position, uint32 count)
Definition file.cpp:285
virtual bool Flush()
Definition file.cpp:271
virtual uint64 Seek(int64 offset, TFile::TSeekDir origin=TFile::beg)
Definition file.cpp:253
virtual bool Write(const void *buffer, uint32 numBytes)
Definition file.cpp:185
virtual bool Close()
Definition file.cpp:166
virtual uint64 Position64() const
Definition file.cpp:206
virtual bool LockRange(uint32 position, uint32 count)
Definition file.cpp:279
tstring FileName
Definition file.h:356
virtual bool GetStatus(TFileStatus &status) const
Definition file.cpp:359
TDiskFileHandle(const tstring &fileName, uint32 mode)
Definition file.cpp:122
virtual uint32 Read(void *buffer, uint32 numBytes)
Definition file.cpp:175
virtual uint32 LastError()
Definition file.cpp:159
virtual uint64 Length64() const
Definition file.cpp:214
virtual uint32 Length() const
Definition file.cpp:244
virtual uint32 Position() const
Definition file.cpp:234
virtual bool LockRange(uint32 position, uint32 count)=0
virtual bool IsOpen()=0
virtual bool UnlockRange(uint32 position, uint32 count)=0
virtual bool Close()=0
virtual bool Flush()=0
The TFile class encapsulates standard file characteristics and operations.
Definition file.h:120
virtual bool Open(const tstring &fileName, const uint32 mode=ReadOnly|PermRead|OpenExisting)
Opens file name with the given mode.
Definition file.cpp:429
bool IsOpen() const
Returns true if the file is open, false otherwise.
Definition file.h:755
virtual uint64 readUint64()
Definition file.cpp:980
uint BufSize
Size of Buffer used with structure read/write.
Definition file.h:275
virtual uint64 Seek(int64 offset, TSeekDir origin=beg)
Repositions the file pointer to offset bytes from the specified origin.
Definition file.h:875
bool ShouldClose
Should C++ object close file on dtor.
Definition file.h:267
@ Text
type Text are used in derived classes only default type is Binary
Definition file.h:158
@ PermWrite
Subsequent open operations on the object will succeed only if write access is requested.
Definition file.h:135
@ ReadOnly
Definition file.h:130
@ WriteOnly
Definition file.h:131
@ CreateNew
Creates a new file. The function fails if the specified file already exists.
Definition file.h:145
@ TruncateExist
Opens the file.
Definition file.h:156
@ OpenExisting
Opens the file. The function fails if the file does not exist.
Definition file.h:151
@ PermRead
Subsequent open operations on the object will succeed only if read access is requested.
Definition file.h:138
@ PermExclusive
Definition file.h:141
@ ReadWrite
Definition file.h:132
@ CreateAlways
Creates a new file. The function overwrites the file if it exists.
Definition file.h:148
uint8 * Buffer
Buffer used with structure read/write.
Definition file.h:272
virtual bool Flush()
Performs any pending I/O functions. Returns true if successful; false otherwise.
Definition file.cpp:460
virtual double readDouble()
Definition file.cpp:997
virtual bool LockRange(uint32 position, uint32 count)
Locks count bytes, beginning at position of the file.
Definition file.cpp:469
virtual void writeUint8(const uint8)
Definition file.cpp:1005
virtual uint32 Read(void *buffer, uint32 numBytes)
Reads numBytes from the file into buffer. The number of bytes read is returned.
Definition file.h:805
uint WriteStruct(void *buffer, TBinType btype, TByteOrderType type)
Writes predefined structures to binary file.
Definition file.cpp:914
virtual float readFloat()
Definition file.cpp:988
virtual void writeFloat(const float)
Definition file.cpp:1032
virtual uint16 readUint16()
Definition file.cpp:962
virtual uint32 readUint32()
Definition file.cpp:972
TFileHandle * Handle
Low-level C file handle.
Definition file.h:266
virtual bool Write(const void *buffer, uint32 numBytes)
Writes numbytes of buffer to the file.
Definition file.h:813
virtual bool UnlockRange(uint32 position, uint32 count)
Unlocks the range at the given Position.
Definition file.cpp:477
virtual void writeDouble(const double)
Definition file.cpp:1039
uint ReadStruct(void *buffer, TBinType btype, TByteOrderType type)
Read binary predefined structure from file.
Definition file.cpp:908
virtual ~TFile()
If ShouldClose is true the file is closed.
Definition file.cpp:400
uint32 GetOpenMode() const
Returns OpenMode.
Definition file.h:760
@ RdOnly
Definition file.h:165
@ Temporary
Definition file.h:171
@ Hidden
Definition file.h:166
@ Normal
Definition file.h:164
@ Directory
Definition file.h:169
@ Archive
Definition file.h:170
@ System
Definition file.h:167
static uint StructSize(TBinField *fields)
Returns the number of bytes in a binary data structure.
Definition file.cpp:657
uint32 SeekToBegin()
Repositions the file pointer to the beginning of the file.
Definition file.h:769
virtual uint8 readUint8()
Definition file.cpp:953
TFile()
Creates a TFile object with a file handle of FileNull.
Definition file.h:715
virtual void writeUint16(const uint16)
Definition file.cpp:1011
TBinType
Binary data type enumerations.
Definition file.h:175
@ TypeLong
Definition file.h:178
@ TypeLong64
Definition file.h:181
@ TypeFloat
Definition file.h:179
@ TypeShort
Definition file.h:177
@ TypeDouble
Definition file.h:180
virtual void writeUint32(const uint32)
Definition file.cpp:1018
virtual TFileHandle * GetHandle() const
Returns Handle.
Definition file.h:743
@ cur
Seek from the current position in the file.
Definition file.h:124
@ end
Seek from the end of the file.
Definition file.h:125
@ beg
Seek from the beginning of the file.
Definition file.h:123
virtual bool Close()
Closes the file. Returns true if successful, false otherwise.
Definition file.cpp:445
virtual void writeUint64(const uint64)
Definition file.cpp:1025
bool GetStatus(TFileStatus &status) const
Fills status with the current file status.
Definition file.h:899
virtual bool NextLine()
Loads the next line in the file. Returns true if successful; false otherwise.
Definition file.cpp:1570
TFileLineIterator()
Protected default constructor. Intializes everything to 0.
Definition file.h:1172
virtual ~TFileLineIterator()
Deletes the buffer.
Definition file.cpp:1561
TCHAR * LineBuffer
Buffer lines of text are loaded into.
Definition file.h:493
uint BuffSize
Size of the buffer allocated for loading a line of text.
Definition file.h:496
TTextFile * File
Pointer to the file being iterated through.
Definition file.h:490
The TFileName class constructs filenames.
Definition filename.h:37
int GetStatus(TFileStatus &status) const
Get the file status struct for the item associated with this filename.
TFileTime is a class derived from the structure FILETIME.
Definition wsyscls.h:362
bool Descent(TQtInfo &info, TQtInfo *parent=0, const TFindFlags=TFindFlags(ffFindChunk|ffReset))
Definition file.cpp:1821
@ ffFindChunk
Definition file.h:616
bool Ascent(TQtInfo &info)
Definition file.cpp:1884
bool CreateChunk(TQtInfo &info)
Writes a data structure of the specified type to the associated file.
Definition file.cpp:1909
bool Ascent(TCkInfo &info)
Definition file.cpp:1656
bool CreateChunk(TCkInfo &info, const TCreateFlags=cfCreateChunk)
Writes a data structure of the specified type to the associated file.
Definition file.cpp:1619
@ cfCreateChunk
Definition file.h:573
bool Descent(TCkInfo &info, TCkInfo *parent=0, const TFindFlags=ffFindAny)
Definition file.cpp:1698
virtual bool Open(const tstring &fileName, const uint32 mode=ReadOnly|PermRead|OpenExisting)
Definition file.cpp:2118
virtual uint32 LastError()
Definition file.cpp:1967
virtual bool Write(const void *buffer, uint32 numBytes)
Definition file.cpp:2002
virtual uint64 Seek(int64 offset, TFile::TSeekDir origin=TFile::beg)
Definition file.cpp:2060
virtual bool Flush()
Definition file.cpp:2075
virtual uint64 Position64() const
Definition file.cpp:2013
TStreamHandle(TStreamFile *parent, const tstring &filename, uint32 mode)
Definition file.cpp:1954
virtual bool LockRange(uint32 position, uint32 count)
Definition file.cpp:2082
virtual bool IsOpen()
Definition file.cpp:1972
virtual bool Close()
Definition file.cpp:1984
virtual uint32 Length() const
Definition file.cpp:2046
TStreamFile * Parent
Definition file.h:681
virtual uint64 Length64() const
Definition file.cpp:2021
TStreamHandle * Clone() const
Definition file.cpp:1978
virtual uint32 Position() const
Definition file.cpp:2034
virtual bool GetStatus(TFileStatus &status) const
Definition file.cpp:2105
virtual bool UnlockRange(uint32 position, uint32 count)
Definition file.cpp:2088
virtual uint32 Read(void *buffer, uint32 numBytes)
Definition file.cpp:1991
The TTextFile class is derived from TBufferedFile and encapsulates standard file characteristics and ...
Definition file.h:436
virtual double readDouble()
Definition file.cpp:1490
virtual uint32 readUint32()
Definition file.cpp:1472
virtual float readFloat()
Definition file.cpp:1485
virtual void writeUint64(const uint64)
Definition file.cpp:1526
virtual uint16 readUint16()
Definition file.cpp:1465
virtual uint64 readUint64()
Definition file.cpp:1478
virtual void writeUint8(const uint8)
Definition file.cpp:1498
virtual void writeUint32(const uint32)
Definition file.cpp:1512
virtual uint8 readUint8()
Definition file.cpp:1456
virtual void writeDouble(const double)
Definition file.cpp:1537
virtual TCHAR * GetString(TCHAR *buffer, uint32 size)
Reads up to size characters and places them in buffer.
Definition file.cpp:1338
virtual void writeFloat(const float)
Definition file.cpp:1532
virtual bool WriteString(LPCTSTR str)
Writes the NULL terminated character string in buffer to the file and adds a terminating \r\n charact...
Definition file.cpp:1438
virtual void writeUint16(const uint16)
Definition file.cpp:1505
The TTime class encapsulates time functions and characteristics.
Definition time.h:38
The TXBadFormat class is used for throwing exceptions when a bad file format is encountered.
Definition file.h:512
void Throw()
Definition file.cpp:78
TXBadFormat * Clone()
Definition file.cpp:69
static void Raise()
Construct a TXBadFormat exception from scratch, and throws it.
Definition file.cpp:62
TXBadFormat()
Constructs an exception handling class with identity IDS_BADFILEFORMAT.
Definition file.cpp:52
TXOwl is root class of the ObjectWindows exception hierarchy.
Definition except.h:38
#define _ltot
Definition cygwin.h:63
#define _tfullpath
Definition cygwin.h:90
#define _tcslen
Definition cygwin.h:74
#define _T(x)
Definition cygwin.h:51
#define BINCHECKRTYPE(type)
Definition file.cpp:644
#define BINCHECKNBYTES(nBytes)
Definition file.cpp:652
static void Raise()
Definition except.cpp:326
TByteOrderType
The byte order type.
Definition file.h:48
#define TFILE_ERROR
Definition file.h:105
#define TFILE64_ERROR
Definition file.h:110
#define FileNull
Represents a NULL file handle.
Definition file.h:108
TByteOrderType EndianType()
Definition file.h:56
@ boLittle_Endian
LSB at lowest address: Intel //.
Definition file.h:49
@ boBig_Endian
MSB at lowest address: Motorola //.
Definition file.h:50
@ varCHAR
Definition file.h:71
@ varLONG
Definition file.h:74
@ varFLOAT
Definition file.h:83
@ varEnd
Definition file.h:69
@ varSHORT
Definition file.h:73
@ varDOUBLE
Definition file.h:84
#define _W2A(lpw)
Definition memory.h:219
#define _USES_CONVERSION
Definition memory.h:217
Object Windows Library (OWLNext Core)
Definition animctrl.h:22
uint16 SwapUint16(uint16 u16)
Definition defs.h:288
__int64 int64
Definition number.h:36
signed long int32
Definition number.h:30
void __MakeDosTime(const TTime &time, uint16 &fdate, uint16 &ftime)
uint __sys2Atr(uint32 attrib)
Definition file.cpp:312
int binCVTCharLBF(uint8 *src, uint8 *dst, int, int size, int count)
Definition file.cpp:543
unsigned char uint8
Definition number.h:32
unsigned long uint32
Definition number.h:34
char tchar
Definition defs.h:77
tstring CopyText(int size, TGetText get_text)
Copies text from a C-string (null-terminated character array) into a string object,...
Definition defs.h:317
bool ToBool(const T &t)
Definition defs.h:291
int(* cvtDispatchFunc)(uint8 *, uint8 *, int, int, int)
Definition file.cpp:600
uint32 SwapUint32(uint32 u32)
Definition defs.h:291
OWL_DIAGINFO
Definition animctrl.cpp:14
TTime __MakeTTime(uint16 fdate, uint16 ftime)
unsigned __int64 uint64
Definition number.h:43
unsigned short uint16
Definition number.h:33
std::string tstring
Definition defs.h:79
unsigned int uint
Definition number.h:25
owl::ipstream & operator>>(owl::ipstream &is, TColor &c)
Extract the color value from a persistent input stream.
Definition color.h:489
int binCVTCharMBF(uint8 *src, uint8 *dst, int, int size, int count)
Definition file.cpp:484
uint __attr2Sys(uint attrib)
Definition file.cpp:331
#define OWL_INI
Definition defs.h:170
#define COUNTOF(s)
Array element count Important: Only use this with an argument of array type.
Definition defs.h:376
The TBinField struct describes a group of like-typed fields in a structure to be read or written usin...
Definition file.h:98
RIFF chunk information data structure.
Definition file.h:541
uint32 Flags
flags used by MMIO functions
Definition file.h:554
uint32 Offset
offset of data portion of chunk
Definition file.h:553
uint32 size
Definition file.h:39
tchar fullName[_MAX_PATH]
Definition file.h:41
uint attribute
Definition file.h:40
TTime modifyTime
Definition file.h:37
TTime createTime
Definition file.h:36
TTime accessTime
Definition file.h:38
QuickTime atom information data structure.
Definition file.h:593
uint32 Offset
Definition file.h:600
uint32 Size
Definition file.h:598
Classes for window system structure and type encapsulation.