/[svn]/libgig/trunk/src/RIFF.cpp
ViewVC logotype

Diff of /libgig/trunk/src/RIFF.cpp

Parent Directory Parent Directory | Revision Log Revision Log | View Patch Patch

revision 2922 by schoenebeck, Wed May 18 18:04:49 2016 UTC revision 3478 by schoenebeck, Thu Feb 21 20:10:08 2019 UTC
# Line 2  Line 2 
2   *                                                                         *   *                                                                         *
3   *   libgig - C++ cross-platform Gigasampler format file access library    *   *   libgig - C++ cross-platform Gigasampler format file access library    *
4   *                                                                         *   *                                                                         *
5   *   Copyright (C) 2003-2016 by Christian Schoenebeck                      *   *   Copyright (C) 2003-2019 by Christian Schoenebeck                      *
6   *                              <cuse@users.sourceforge.net>               *   *                              <cuse@users.sourceforge.net>               *
7   *                                                                         *   *                                                                         *
8   *   This library is free software; you can redistribute it and/or modify  *   *   This library is free software; you can redistribute it and/or modify  *
# Line 64  namespace RIFF { Line 64  namespace RIFF {
64          __range_max = 1.0f;          __range_max = 1.0f;
65      }      }
66    
67        /**
68         * Divides this progress task into the requested amount of sub-progress
69         * tasks and returns a vector with those subprogress tasks.
70         *
71         * @param iSubtasks - total amount sub tasks this task should be subdivided
72         * @returns subtasks
73         */
74        std::vector<progress_t> progress_t::subdivide(int iSubtasks) {
75            std::vector<progress_t> v;
76            for (int i = 0; i < iSubtasks; ++i) {
77                progress_t p;
78                __divide_progress(this, &p, iSubtasks, i);
79                v.push_back(p);
80            }
81            return v;
82        }
83    
84    
85    
86  // *************** Chunk **************  // *************** Chunk **************
87  // *  // *
88    
89      Chunk::Chunk(File* pFile) {      Chunk::Chunk(File* pFile) {
90          #if DEBUG          #if DEBUG_RIFF
91          std::cout << "Chunk::Chunk(File* pFile)" << std::endl;          std::cout << "Chunk::Chunk(File* pFile)" << std::endl;
92          #endif // DEBUG          #endif // DEBUG_RIFF
93          ullPos     = 0;          ullPos     = 0;
94          pParent    = NULL;          pParent    = NULL;
95          pChunkData = NULL;          pChunkData = NULL;
# Line 84  namespace RIFF { Line 101  namespace RIFF {
101      }      }
102    
103      Chunk::Chunk(File* pFile, file_offset_t StartPos, List* Parent) {      Chunk::Chunk(File* pFile, file_offset_t StartPos, List* Parent) {
104          #if DEBUG          #if DEBUG_RIFF
105          std::cout << "Chunk::Chunk(File*,file_offset_t,List*),StartPos=" << StartPos << std::endl;          std::cout << "Chunk::Chunk(File*,file_offset_t,List*),StartPos=" << StartPos << std::endl;
106          #endif // DEBUG          #endif // DEBUG_RIFF
107          this->pFile   = pFile;          this->pFile   = pFile;
108          ullStartPos   = StartPos + CHUNK_HEADER_SIZE(pFile->FileOffsetSize);          ullStartPos   = StartPos + CHUNK_HEADER_SIZE(pFile->FileOffsetSize);
109          pParent       = Parent;          pParent       = Parent;
# Line 115  namespace RIFF { Line 132  namespace RIFF {
132      }      }
133    
134      void Chunk::ReadHeader(file_offset_t filePos) {      void Chunk::ReadHeader(file_offset_t filePos) {
135          #if DEBUG          #if DEBUG_RIFF
136          std::cout << "Chunk::Readheader(" << filePos << ") ";          std::cout << "Chunk::Readheader(" << filePos << ") ";
137          #endif // DEBUG          #endif // DEBUG_RIFF
138          ChunkID = 0;          ChunkID = 0;
139          ullNewChunkSize = ullCurrentChunkSize = 0;          ullNewChunkSize = ullCurrentChunkSize = 0;
140          #if POSIX          #if POSIX
# Line 153  namespace RIFF { Line 170  namespace RIFF {
170                  else                  else
171                      swapBytes_64(&ullCurrentChunkSize);                      swapBytes_64(&ullCurrentChunkSize);
172              }              }
173              #if DEBUG              #if DEBUG_RIFF
174              std::cout << "ckID=" << convertToString(ChunkID) << " ";              std::cout << "ckID=" << convertToString(ChunkID) << " ";
175              std::cout << "ckSize=" << ullCurrentChunkSize << " ";              std::cout << "ckSize=" << ullCurrentChunkSize << " ";
176              std::cout << "bEndianNative=" << pFile->bEndianNative << std::endl;              std::cout << "bEndianNative=" << pFile->bEndianNative << std::endl;
177              #endif // DEBUG              #endif // DEBUG_RIFF
178              ullNewChunkSize = ullCurrentChunkSize;              ullNewChunkSize = ullCurrentChunkSize;
179          }          }
180      }      }
# Line 222  namespace RIFF { Line 239  namespace RIFF {
239       *                  data       *                  data
240       */       */
241      file_offset_t Chunk::SetPos(file_offset_t Where, stream_whence_t Whence) {      file_offset_t Chunk::SetPos(file_offset_t Where, stream_whence_t Whence) {
242          #if DEBUG          #if DEBUG_RIFF
243          std::cout << "Chunk::SetPos(file_offset_t,stream_whence_t)" << std::endl;          std::cout << "Chunk::SetPos(file_offset_t,stream_whence_t)" << std::endl;
244          #endif // DEBUG          #endif // DEBUG_RIFF
245          switch (Whence) {          switch (Whence) {
246              case stream_curpos:              case stream_curpos:
247                  ullPos += Where;                  ullPos += Where;
# Line 254  namespace RIFF { Line 271  namespace RIFF {
271       *  @returns  number of bytes left to read       *  @returns  number of bytes left to read
272       */       */
273      file_offset_t Chunk::RemainingBytes() const {      file_offset_t Chunk::RemainingBytes() const {
274          #if DEBUG          #if DEBUG_RIFF
275          std::cout << "Chunk::Remainingbytes()=" << ullCurrentChunkSize - ullPos << std::endl;          std::cout << "Chunk::Remainingbytes()=" << ullCurrentChunkSize - ullPos << std::endl;
276          #endif // DEBUG          #endif // DEBUG_RIFF
277          return (ullCurrentChunkSize > ullPos) ? ullCurrentChunkSize - ullPos : 0;          return (ullCurrentChunkSize > ullPos) ? ullCurrentChunkSize - ullPos : 0;
278      }      }
279    
# Line 285  namespace RIFF { Line 302  namespace RIFF {
302       *    possible without SetPos()       *    possible without SetPos()
303       */       */
304      stream_state_t Chunk::GetState() const {      stream_state_t Chunk::GetState() const {
305          #if DEBUG          #if DEBUG_RIFF
306          std::cout << "Chunk::GetState()" << std::endl;          std::cout << "Chunk::GetState()" << std::endl;
307          #endif // DEBUG          #endif // DEBUG_RIFF
308          #if POSIX          #if POSIX
309          if (pFile->hFileRead == 0) return stream_closed;          if (pFile->hFileRead == 0) return stream_closed;
310          #elif defined (WIN32)          #elif defined (WIN32)
# Line 313  namespace RIFF { Line 330  namespace RIFF {
330       *  @param WordCount  number of data words to read       *  @param WordCount  number of data words to read
331       *  @param WordSize   size of each data word to read       *  @param WordSize   size of each data word to read
332       *  @returns          number of successfully read data words or 0 if end       *  @returns          number of successfully read data words or 0 if end
333       *                    of file reached or error occured       *                    of file reached or error occurred
334       */       */
335      file_offset_t Chunk::Read(void* pData, file_offset_t WordCount, file_offset_t WordSize) {      file_offset_t Chunk::Read(void* pData, file_offset_t WordCount, file_offset_t WordSize) {
336          #if DEBUG          #if DEBUG_RIFF
337          std::cout << "Chunk::Read(void*,file_offset_t,file_offset_t)" << std::endl;          std::cout << "Chunk::Read(void*,file_offset_t,file_offset_t)" << std::endl;
338          #endif // DEBUG          #endif // DEBUG_RIFF
339          //if (ulStartPos == 0) return 0; // is only 0 if this is a new chunk, so nothing to read (yet)          //if (ulStartPos == 0) return 0; // is only 0 if this is a new chunk, so nothing to read (yet)
340          if (ullPos >= ullCurrentChunkSize) return 0;          if (ullPos >= ullCurrentChunkSize) return 0;
341          if (ullPos + WordCount * WordSize >= ullCurrentChunkSize) WordCount = (ullCurrentChunkSize - ullPos) / WordSize;          if (ullPos + WordCount * WordSize >= ullCurrentChunkSize) WordCount = (ullCurrentChunkSize - ullPos) / WordSize;
# Line 326  namespace RIFF { Line 343  namespace RIFF {
343          if (lseek(pFile->hFileRead, ullStartPos + ullPos, SEEK_SET) < 0) return 0;          if (lseek(pFile->hFileRead, ullStartPos + ullPos, SEEK_SET) < 0) return 0;
344          ssize_t readWords = read(pFile->hFileRead, pData, WordCount * WordSize);          ssize_t readWords = read(pFile->hFileRead, pData, WordCount * WordSize);
345          if (readWords < 1) {          if (readWords < 1) {
346              #if DEBUG              #if DEBUG_RIFF
347              std::cerr << "POSIX read() failed: " << strerror(errno) << std::endl << std::flush;              std::cerr << "POSIX read() failed: " << strerror(errno) << std::endl << std::flush;
348              #endif // DEBUG              #endif // DEBUG_RIFF
349              return 0;              return 0;
350          }          }
351          readWords /= WordSize;          readWords /= WordSize;
# Line 382  namespace RIFF { Line 399  namespace RIFF {
399       *  @param WordSize   size of each data word to write       *  @param WordSize   size of each data word to write
400       *  @returns          number of successfully written data words       *  @returns          number of successfully written data words
401       *  @throws RIFF::Exception  if write operation would exceed current       *  @throws RIFF::Exception  if write operation would exceed current
402       *                           chunk size or any IO error occured       *                           chunk size or any IO error occurred
403       *  @see Resize()       *  @see Resize()
404       */       */
405      file_offset_t Chunk::Write(void* pData, file_offset_t WordCount, file_offset_t WordSize) {      file_offset_t Chunk::Write(void* pData, file_offset_t WordCount, file_offset_t WordSize) {
# Line 455  namespace RIFF { Line 472  namespace RIFF {
472       * @param pData             destination buffer       * @param pData             destination buffer
473       * @param WordCount         number of 8 Bit signed integers to read       * @param WordCount         number of 8 Bit signed integers to read
474       * @returns                 number of read integers       * @returns                 number of read integers
475       * @throws RIFF::Exception  if an error occured or less than       * @throws RIFF::Exception  if an error occurred or less than
476       *                          \a WordCount integers could be read!       *                          \a WordCount integers could be read!
477       */       */
478      file_offset_t Chunk::ReadInt8(int8_t* pData, file_offset_t WordCount) {      file_offset_t Chunk::ReadInt8(int8_t* pData, file_offset_t WordCount) {
479          #if DEBUG          #if DEBUG_RIFF
480          std::cout << "Chunk::ReadInt8(int8_t*,file_offset_t)" << std::endl;          std::cout << "Chunk::ReadInt8(int8_t*,file_offset_t)" << std::endl;
481          #endif // DEBUG          #endif // DEBUG_RIFF
482          return ReadSceptical(pData, WordCount, 1);          return ReadSceptical(pData, WordCount, 1);
483      }      }
484    
# Line 476  namespace RIFF { Line 493  namespace RIFF {
493       * @param pData             source buffer (containing the data)       * @param pData             source buffer (containing the data)
494       * @param WordCount         number of 8 Bit signed integers to write       * @param WordCount         number of 8 Bit signed integers to write
495       * @returns                 number of written integers       * @returns                 number of written integers
496       * @throws RIFF::Exception  if an IO error occured       * @throws RIFF::Exception  if an IO error occurred
497       * @see Resize()       * @see Resize()
498       */       */
499      file_offset_t Chunk::WriteInt8(int8_t* pData, file_offset_t WordCount) {      file_offset_t Chunk::WriteInt8(int8_t* pData, file_offset_t WordCount) {
# Line 492  namespace RIFF { Line 509  namespace RIFF {
509       * @param pData             destination buffer       * @param pData             destination buffer
510       * @param WordCount         number of 8 Bit unsigned integers to read       * @param WordCount         number of 8 Bit unsigned integers to read
511       * @returns                 number of read integers       * @returns                 number of read integers
512       * @throws RIFF::Exception  if an error occured or less than       * @throws RIFF::Exception  if an error occurred or less than
513       *                          \a WordCount integers could be read!       *                          \a WordCount integers could be read!
514       */       */
515      file_offset_t Chunk::ReadUint8(uint8_t* pData, file_offset_t WordCount) {      file_offset_t Chunk::ReadUint8(uint8_t* pData, file_offset_t WordCount) {
516          #if DEBUG          #if DEBUG_RIFF
517          std::cout << "Chunk::ReadUint8(uint8_t*,file_offset_t)" << std::endl;          std::cout << "Chunk::ReadUint8(uint8_t*,file_offset_t)" << std::endl;
518          #endif // DEBUG          #endif // DEBUG_RIFF
519          return ReadSceptical(pData, WordCount, 1);          return ReadSceptical(pData, WordCount, 1);
520      }      }
521    
# Line 513  namespace RIFF { Line 530  namespace RIFF {
530       * @param pData             source buffer (containing the data)       * @param pData             source buffer (containing the data)
531       * @param WordCount         number of 8 Bit unsigned integers to write       * @param WordCount         number of 8 Bit unsigned integers to write
532       * @returns                 number of written integers       * @returns                 number of written integers
533       * @throws RIFF::Exception  if an IO error occured       * @throws RIFF::Exception  if an IO error occurred
534       * @see Resize()       * @see Resize()
535       */       */
536      file_offset_t Chunk::WriteUint8(uint8_t* pData, file_offset_t WordCount) {      file_offset_t Chunk::WriteUint8(uint8_t* pData, file_offset_t WordCount) {
# Line 529  namespace RIFF { Line 546  namespace RIFF {
546       * @param pData             destination buffer       * @param pData             destination buffer
547       * @param WordCount         number of 16 Bit signed integers to read       * @param WordCount         number of 16 Bit signed integers to read
548       * @returns                 number of read integers       * @returns                 number of read integers
549       * @throws RIFF::Exception  if an error occured or less than       * @throws RIFF::Exception  if an error occurred or less than
550       *                          \a WordCount integers could be read!       *                          \a WordCount integers could be read!
551       */       */
552      file_offset_t Chunk::ReadInt16(int16_t* pData, file_offset_t WordCount) {      file_offset_t Chunk::ReadInt16(int16_t* pData, file_offset_t WordCount) {
553          #if DEBUG          #if DEBUG_RIFF
554          std::cout << "Chunk::ReadInt16(int16_t*,file_offset_t)" << std::endl;          std::cout << "Chunk::ReadInt16(int16_t*,file_offset_t)" << std::endl;
555          #endif // DEBUG          #endif // DEBUG_RIFF
556          return ReadSceptical(pData, WordCount, 2);          return ReadSceptical(pData, WordCount, 2);
557      }      }
558    
# Line 550  namespace RIFF { Line 567  namespace RIFF {
567       * @param pData             source buffer (containing the data)       * @param pData             source buffer (containing the data)
568       * @param WordCount         number of 16 Bit signed integers to write       * @param WordCount         number of 16 Bit signed integers to write
569       * @returns                 number of written integers       * @returns                 number of written integers
570       * @throws RIFF::Exception  if an IO error occured       * @throws RIFF::Exception  if an IO error occurred
571       * @see Resize()       * @see Resize()
572       */       */
573      file_offset_t Chunk::WriteInt16(int16_t* pData, file_offset_t WordCount) {      file_offset_t Chunk::WriteInt16(int16_t* pData, file_offset_t WordCount) {
# Line 566  namespace RIFF { Line 583  namespace RIFF {
583       * @param pData             destination buffer       * @param pData             destination buffer
584       * @param WordCount         number of 8 Bit unsigned integers to read       * @param WordCount         number of 8 Bit unsigned integers to read
585       * @returns                 number of read integers       * @returns                 number of read integers
586       * @throws RIFF::Exception  if an error occured or less than       * @throws RIFF::Exception  if an error occurred or less than
587       *                          \a WordCount integers could be read!       *                          \a WordCount integers could be read!
588       */       */
589      file_offset_t Chunk::ReadUint16(uint16_t* pData, file_offset_t WordCount) {      file_offset_t Chunk::ReadUint16(uint16_t* pData, file_offset_t WordCount) {
590          #if DEBUG          #if DEBUG_RIFF
591          std::cout << "Chunk::ReadUint16(uint16_t*,file_offset_t)" << std::endl;          std::cout << "Chunk::ReadUint16(uint16_t*,file_offset_t)" << std::endl;
592          #endif // DEBUG          #endif // DEBUG_RIFF
593          return ReadSceptical(pData, WordCount, 2);          return ReadSceptical(pData, WordCount, 2);
594      }      }
595    
# Line 587  namespace RIFF { Line 604  namespace RIFF {
604       * @param pData             source buffer (containing the data)       * @param pData             source buffer (containing the data)
605       * @param WordCount         number of 16 Bit unsigned integers to write       * @param WordCount         number of 16 Bit unsigned integers to write
606       * @returns                 number of written integers       * @returns                 number of written integers
607       * @throws RIFF::Exception  if an IO error occured       * @throws RIFF::Exception  if an IO error occurred
608       * @see Resize()       * @see Resize()
609       */       */
610      file_offset_t Chunk::WriteUint16(uint16_t* pData, file_offset_t WordCount) {      file_offset_t Chunk::WriteUint16(uint16_t* pData, file_offset_t WordCount) {
# Line 603  namespace RIFF { Line 620  namespace RIFF {
620       * @param pData             destination buffer       * @param pData             destination buffer
621       * @param WordCount         number of 32 Bit signed integers to read       * @param WordCount         number of 32 Bit signed integers to read
622       * @returns                 number of read integers       * @returns                 number of read integers
623       * @throws RIFF::Exception  if an error occured or less than       * @throws RIFF::Exception  if an error occurred or less than
624       *                          \a WordCount integers could be read!       *                          \a WordCount integers could be read!
625       */       */
626      file_offset_t Chunk::ReadInt32(int32_t* pData, file_offset_t WordCount) {      file_offset_t Chunk::ReadInt32(int32_t* pData, file_offset_t WordCount) {
627          #if DEBUG          #if DEBUG_RIFF
628          std::cout << "Chunk::ReadInt32(int32_t*,file_offset_t)" << std::endl;          std::cout << "Chunk::ReadInt32(int32_t*,file_offset_t)" << std::endl;
629          #endif // DEBUG          #endif // DEBUG_RIFF
630          return ReadSceptical(pData, WordCount, 4);          return ReadSceptical(pData, WordCount, 4);
631      }      }
632    
# Line 624  namespace RIFF { Line 641  namespace RIFF {
641       * @param pData             source buffer (containing the data)       * @param pData             source buffer (containing the data)
642       * @param WordCount         number of 32 Bit signed integers to write       * @param WordCount         number of 32 Bit signed integers to write
643       * @returns                 number of written integers       * @returns                 number of written integers
644       * @throws RIFF::Exception  if an IO error occured       * @throws RIFF::Exception  if an IO error occurred
645       * @see Resize()       * @see Resize()
646       */       */
647      file_offset_t Chunk::WriteInt32(int32_t* pData, file_offset_t WordCount) {      file_offset_t Chunk::WriteInt32(int32_t* pData, file_offset_t WordCount) {
# Line 640  namespace RIFF { Line 657  namespace RIFF {
657       * @param pData             destination buffer       * @param pData             destination buffer
658       * @param WordCount         number of 32 Bit unsigned integers to read       * @param WordCount         number of 32 Bit unsigned integers to read
659       * @returns                 number of read integers       * @returns                 number of read integers
660       * @throws RIFF::Exception  if an error occured or less than       * @throws RIFF::Exception  if an error occurred or less than
661       *                          \a WordCount integers could be read!       *                          \a WordCount integers could be read!
662       */       */
663      file_offset_t Chunk::ReadUint32(uint32_t* pData, file_offset_t WordCount) {      file_offset_t Chunk::ReadUint32(uint32_t* pData, file_offset_t WordCount) {
664          #if DEBUG          #if DEBUG_RIFF
665          std::cout << "Chunk::ReadUint32(uint32_t*,file_offset_t)" << std::endl;          std::cout << "Chunk::ReadUint32(uint32_t*,file_offset_t)" << std::endl;
666          #endif // DEBUG          #endif // DEBUG_RIFF
667          return ReadSceptical(pData, WordCount, 4);          return ReadSceptical(pData, WordCount, 4);
668      }      }
669    
# Line 657  namespace RIFF { Line 674  namespace RIFF {
674       *       *
675       * @param s                 destination string       * @param s                 destination string
676       * @param size              number of characters to read       * @param size              number of characters to read
677       * @throws RIFF::Exception  if an error occured or less than       * @throws RIFF::Exception  if an error occurred or less than
678       *                          \a size characters could be read!       *                          \a size characters could be read!
679       */       */
680      void Chunk::ReadString(String& s, int size) {      void Chunk::ReadString(String& s, int size) {
# Line 678  namespace RIFF { Line 695  namespace RIFF {
695       * @param pData             source buffer (containing the data)       * @param pData             source buffer (containing the data)
696       * @param WordCount         number of 32 Bit unsigned integers to write       * @param WordCount         number of 32 Bit unsigned integers to write
697       * @returns                 number of written integers       * @returns                 number of written integers
698       * @throws RIFF::Exception  if an IO error occured       * @throws RIFF::Exception  if an IO error occurred
699       * @see Resize()       * @see Resize()
700       */       */
701      file_offset_t Chunk::WriteUint32(uint32_t* pData, file_offset_t WordCount) {      file_offset_t Chunk::WriteUint32(uint32_t* pData, file_offset_t WordCount) {
# Line 690  namespace RIFF { Line 707  namespace RIFF {
707       * the chunk.       * the chunk.
708       *       *
709       * @returns                 read integer word       * @returns                 read integer word
710       * @throws RIFF::Exception  if an error occured       * @throws RIFF::Exception  if an error occurred
711       */       */
712      int8_t Chunk::ReadInt8() {      int8_t Chunk::ReadInt8() {
713          #if DEBUG          #if DEBUG_RIFF
714          std::cout << "Chunk::ReadInt8()" << std::endl;          std::cout << "Chunk::ReadInt8()" << std::endl;
715          #endif // DEBUG          #endif // DEBUG_RIFF
716          int8_t word;          int8_t word;
717          ReadSceptical(&word,1,1);          ReadSceptical(&word,1,1);
718          return word;          return word;
# Line 706  namespace RIFF { Line 723  namespace RIFF {
723       * within the chunk.       * within the chunk.
724       *       *
725       * @returns                 read integer word       * @returns                 read integer word
726       * @throws RIFF::Exception  if an error occured       * @throws RIFF::Exception  if an error occurred
727       */       */
728      uint8_t Chunk::ReadUint8() {      uint8_t Chunk::ReadUint8() {
729          #if DEBUG          #if DEBUG_RIFF
730          std::cout << "Chunk::ReadUint8()" << std::endl;          std::cout << "Chunk::ReadUint8()" << std::endl;
731          #endif // DEBUG          #endif // DEBUG_RIFF
732          uint8_t word;          uint8_t word;
733          ReadSceptical(&word,1,1);          ReadSceptical(&word,1,1);
734          return word;          return word;
# Line 723  namespace RIFF { Line 740  namespace RIFF {
740       * needed.       * needed.
741       *       *
742       * @returns                 read integer word       * @returns                 read integer word
743       * @throws RIFF::Exception  if an error occured       * @throws RIFF::Exception  if an error occurred
744       */       */
745      int16_t Chunk::ReadInt16() {      int16_t Chunk::ReadInt16() {
746          #if DEBUG          #if DEBUG_RIFF
747          std::cout << "Chunk::ReadInt16()" << std::endl;          std::cout << "Chunk::ReadInt16()" << std::endl;
748          #endif // DEBUG          #endif // DEBUG_RIFF
749          int16_t word;          int16_t word;
750          ReadSceptical(&word,1,2);          ReadSceptical(&word,1,2);
751          return word;          return word;
# Line 740  namespace RIFF { Line 757  namespace RIFF {
757       * needed.       * needed.
758       *       *
759       * @returns                 read integer word       * @returns                 read integer word
760       * @throws RIFF::Exception  if an error occured       * @throws RIFF::Exception  if an error occurred
761       */       */
762      uint16_t Chunk::ReadUint16() {      uint16_t Chunk::ReadUint16() {
763          #if DEBUG          #if DEBUG_RIFF
764          std::cout << "Chunk::ReadUint16()" << std::endl;          std::cout << "Chunk::ReadUint16()" << std::endl;
765          #endif // DEBUG          #endif // DEBUG_RIFF
766          uint16_t word;          uint16_t word;
767          ReadSceptical(&word,1,2);          ReadSceptical(&word,1,2);
768          return word;          return word;
# Line 757  namespace RIFF { Line 774  namespace RIFF {
774       * needed.       * needed.
775       *       *
776       * @returns                 read integer word       * @returns                 read integer word
777       * @throws RIFF::Exception  if an error occured       * @throws RIFF::Exception  if an error occurred
778       */       */
779      int32_t Chunk::ReadInt32() {      int32_t Chunk::ReadInt32() {
780          #if DEBUG          #if DEBUG_RIFF
781          std::cout << "Chunk::ReadInt32()" << std::endl;          std::cout << "Chunk::ReadInt32()" << std::endl;
782          #endif // DEBUG          #endif // DEBUG_RIFF
783          int32_t word;          int32_t word;
784          ReadSceptical(&word,1,4);          ReadSceptical(&word,1,4);
785          return word;          return word;
# Line 774  namespace RIFF { Line 791  namespace RIFF {
791       * needed.       * needed.
792       *       *
793       * @returns                 read integer word       * @returns                 read integer word
794       * @throws RIFF::Exception  if an error occured       * @throws RIFF::Exception  if an error occurred
795       */       */
796      uint32_t Chunk::ReadUint32() {      uint32_t Chunk::ReadUint32() {
797          #if DEBUG          #if DEBUG_RIFF
798          std::cout << "Chunk::ReadUint32()" << std::endl;          std::cout << "Chunk::ReadUint32()" << std::endl;
799          #endif // DEBUG          #endif // DEBUG_RIFF
800          uint32_t word;          uint32_t word;
801          ReadSceptical(&word,1,4);          ReadSceptical(&word,1,4);
802          return word;          return word;
# Line 941  namespace RIFF { Line 958  namespace RIFF {
958              int iBytesMoved = 1;              int iBytesMoved = 1;
959              #endif              #endif
960              for (file_offset_t ullOffset = 0; ullToMove > 0 && iBytesMoved > 0; ullOffset += iBytesMoved, ullToMove -= iBytesMoved) {              for (file_offset_t ullOffset = 0; ullToMove > 0 && iBytesMoved > 0; ullOffset += iBytesMoved, ullToMove -= iBytesMoved) {
961                  iBytesMoved = (ullToMove < 4096) ? ullToMove : 4096;                  iBytesMoved = (ullToMove < 4096) ? int(ullToMove) : 4096;
962                  #if POSIX                  #if POSIX
963                  lseek(pFile->hFileRead, ullStartPos + ullCurrentDataOffset + ullOffset, SEEK_SET);                  lseek(pFile->hFileRead, ullStartPos + ullCurrentDataOffset + ullOffset, SEEK_SET);
964                  iBytesMoved = read(pFile->hFileRead, pCopyBuffer, iBytesMoved);                  iBytesMoved = (int) read(pFile->hFileRead, pCopyBuffer, (size_t) iBytesMoved);
965                  lseek(pFile->hFileWrite, ullWritePos + ullOffset, SEEK_SET);                  lseek(pFile->hFileWrite, ullWritePos + ullOffset, SEEK_SET);
966                  iBytesMoved = write(pFile->hFileWrite, pCopyBuffer, iBytesMoved);                  iBytesMoved = (int) write(pFile->hFileWrite, pCopyBuffer, (size_t) iBytesMoved);
967                  #elif defined(WIN32)                  #elif defined(WIN32)
968                  LARGE_INTEGER liFilePos;                  LARGE_INTEGER liFilePos;
969                  liFilePos.QuadPart = ullStartPos + ullCurrentDataOffset + ullOffset;                  liFilePos.QuadPart = ullStartPos + ullCurrentDataOffset + ullOffset;
# Line 1008  namespace RIFF { Line 1025  namespace RIFF {
1025  // *  // *
1026    
1027      List::List(File* pFile) : Chunk(pFile) {      List::List(File* pFile) : Chunk(pFile) {
1028          #if DEBUG          #if DEBUG_RIFF
1029          std::cout << "List::List(File* pFile)" << std::endl;          std::cout << "List::List(File* pFile)" << std::endl;
1030          #endif // DEBUG          #endif // DEBUG_RIFF
1031          pSubChunks    = NULL;          pSubChunks    = NULL;
1032          pSubChunksMap = NULL;          pSubChunksMap = NULL;
1033      }      }
1034    
1035      List::List(File* pFile, file_offset_t StartPos, List* Parent)      List::List(File* pFile, file_offset_t StartPos, List* Parent)
1036        : Chunk(pFile, StartPos, Parent) {        : Chunk(pFile, StartPos, Parent) {
1037          #if DEBUG          #if DEBUG_RIFF
1038          std::cout << "List::List(File*,file_offset_t,List*)" << std::endl;          std::cout << "List::List(File*,file_offset_t,List*)" << std::endl;
1039          #endif // DEBUG          #endif // DEBUG_RIFF
1040          pSubChunks    = NULL;          pSubChunks    = NULL;
1041          pSubChunksMap = NULL;          pSubChunksMap = NULL;
1042          ReadHeader(StartPos);          ReadHeader(StartPos);
# Line 1034  namespace RIFF { Line 1051  namespace RIFF {
1051      }      }
1052    
1053      List::~List() {      List::~List() {
1054          #if DEBUG          #if DEBUG_RIFF
1055          std::cout << "List::~List()" << std::endl;          std::cout << "List::~List()" << std::endl;
1056          #endif // DEBUG          #endif // DEBUG_RIFF
1057          DeleteChunkList();          DeleteChunkList();
1058      }      }
1059    
# Line 1069  namespace RIFF { Line 1086  namespace RIFF {
1086       *                   that ID       *                   that ID
1087       */       */
1088      Chunk* List::GetSubChunk(uint32_t ChunkID) {      Chunk* List::GetSubChunk(uint32_t ChunkID) {
1089          #if DEBUG          #if DEBUG_RIFF
1090          std::cout << "List::GetSubChunk(uint32_t)" << std::endl;          std::cout << "List::GetSubChunk(uint32_t)" << std::endl;
1091          #endif // DEBUG          #endif // DEBUG_RIFF
1092          if (!pSubChunksMap) LoadSubChunks();          if (!pSubChunksMap) LoadSubChunks();
1093          return (*pSubChunksMap)[ChunkID];          return (*pSubChunksMap)[ChunkID];
1094      }      }
# Line 1088  namespace RIFF { Line 1105  namespace RIFF {
1105       *                    that type       *                    that type
1106       */       */
1107      List* List::GetSubList(uint32_t ListType) {      List* List::GetSubList(uint32_t ListType) {
1108          #if DEBUG          #if DEBUG_RIFF
1109          std::cout << "List::GetSubList(uint32_t)" << std::endl;          std::cout << "List::GetSubList(uint32_t)" << std::endl;
1110          #endif // DEBUG          #endif // DEBUG_RIFF
1111          if (!pSubChunks) LoadSubChunks();          if (!pSubChunks) LoadSubChunks();
1112          ChunkList::iterator iter = pSubChunks->begin();          ChunkList::iterator iter = pSubChunks->begin();
1113          ChunkList::iterator end  = pSubChunks->end();          ChunkList::iterator end  = pSubChunks->end();
# Line 1114  namespace RIFF { Line 1131  namespace RIFF {
1131       *            otherwise       *            otherwise
1132       */       */
1133      Chunk* List::GetFirstSubChunk() {      Chunk* List::GetFirstSubChunk() {
1134          #if DEBUG          #if DEBUG_RIFF
1135          std::cout << "List::GetFirstSubChunk()" << std::endl;          std::cout << "List::GetFirstSubChunk()" << std::endl;
1136          #endif // DEBUG          #endif // DEBUG_RIFF
1137          if (!pSubChunks) LoadSubChunks();          if (!pSubChunks) LoadSubChunks();
1138          ChunksIterator = pSubChunks->begin();          ChunksIterator = pSubChunks->begin();
1139          return (ChunksIterator != pSubChunks->end()) ? *ChunksIterator : NULL;          return (ChunksIterator != pSubChunks->end()) ? *ChunksIterator : NULL;
# Line 1131  namespace RIFF { Line 1148  namespace RIFF {
1148       *            end of list is reached       *            end of list is reached
1149       */       */
1150      Chunk* List::GetNextSubChunk() {      Chunk* List::GetNextSubChunk() {
1151          #if DEBUG          #if DEBUG_RIFF
1152          std::cout << "List::GetNextSubChunk()" << std::endl;          std::cout << "List::GetNextSubChunk()" << std::endl;
1153          #endif // DEBUG          #endif // DEBUG_RIFF
1154          if (!pSubChunks) return NULL;          if (!pSubChunks) return NULL;
1155          ChunksIterator++;          ChunksIterator++;
1156          return (ChunksIterator != pSubChunks->end()) ? *ChunksIterator : NULL;          return (ChunksIterator != pSubChunks->end()) ? *ChunksIterator : NULL;
# Line 1149  namespace RIFF { Line 1166  namespace RIFF {
1166       *            otherwise       *            otherwise
1167       */       */
1168      List* List::GetFirstSubList() {      List* List::GetFirstSubList() {
1169          #if DEBUG          #if DEBUG_RIFF
1170          std::cout << "List::GetFirstSubList()" << std::endl;          std::cout << "List::GetFirstSubList()" << std::endl;
1171          #endif // DEBUG          #endif // DEBUG_RIFF
1172          if (!pSubChunks) LoadSubChunks();          if (!pSubChunks) LoadSubChunks();
1173          ListIterator            = pSubChunks->begin();          ListIterator            = pSubChunks->begin();
1174          ChunkList::iterator end = pSubChunks->end();          ChunkList::iterator end = pSubChunks->end();
# Line 1171  namespace RIFF { Line 1188  namespace RIFF {
1188       *            end of list is reached       *            end of list is reached
1189       */       */
1190      List* List::GetNextSubList() {      List* List::GetNextSubList() {
1191          #if DEBUG          #if DEBUG_RIFF
1192          std::cout << "List::GetNextSubList()" << std::endl;          std::cout << "List::GetNextSubList()" << std::endl;
1193          #endif // DEBUG          #endif // DEBUG_RIFF
1194          if (!pSubChunks) return NULL;          if (!pSubChunks) return NULL;
1195          if (ListIterator == pSubChunks->end()) return NULL;          if (ListIterator == pSubChunks->end()) return NULL;
1196          ListIterator++;          ListIterator++;
# Line 1375  namespace RIFF { Line 1392  namespace RIFF {
1392      }      }
1393    
1394      void List::ReadHeader(file_offset_t filePos) {      void List::ReadHeader(file_offset_t filePos) {
1395          #if DEBUG          #if DEBUG_RIFF
1396          std::cout << "List::Readheader(file_offset_t) ";          std::cout << "List::Readheader(file_offset_t) ";
1397          #endif // DEBUG          #endif // DEBUG_RIFF
1398          Chunk::ReadHeader(filePos);          Chunk::ReadHeader(filePos);
1399          if (ullCurrentChunkSize < 4) return;          if (ullCurrentChunkSize < 4) return;
1400          ullNewChunkSize = ullCurrentChunkSize -= 4;          ullNewChunkSize = ullCurrentChunkSize -= 4;
# Line 1394  namespace RIFF { Line 1411  namespace RIFF {
1411          fseeko(pFile->hFileRead, filePos + CHUNK_HEADER_SIZE(pFile->FileOffsetSize), SEEK_SET);          fseeko(pFile->hFileRead, filePos + CHUNK_HEADER_SIZE(pFile->FileOffsetSize), SEEK_SET);
1412          fread(&ListType, 4, 1, pFile->hFileRead);          fread(&ListType, 4, 1, pFile->hFileRead);
1413          #endif // POSIX          #endif // POSIX
1414          #if DEBUG          #if DEBUG_RIFF
1415          std::cout << "listType=" << convertToString(ListType) << std::endl;          std::cout << "listType=" << convertToString(ListType) << std::endl;
1416          #endif // DEBUG          #endif // DEBUG_RIFF
1417          if (!pFile->bEndianNative) {          if (!pFile->bEndianNative) {
1418              //swapBytes_32(&ListType);              //swapBytes_32(&ListType);
1419          }          }
# Line 1423  namespace RIFF { Line 1440  namespace RIFF {
1440      }      }
1441    
1442      void List::LoadSubChunks(progress_t* pProgress) {      void List::LoadSubChunks(progress_t* pProgress) {
1443          #if DEBUG          #if DEBUG_RIFF
1444          std::cout << "List::LoadSubChunks()";          std::cout << "List::LoadSubChunks()";
1445          #endif // DEBUG          #endif // DEBUG_RIFF
1446          if (!pSubChunks) {          if (!pSubChunks) {
1447              pSubChunks    = new ChunkList();              pSubChunks    = new ChunkList();
1448              pSubChunksMap = new ChunkMap();              pSubChunksMap = new ChunkMap();
# Line 1440  namespace RIFF { Line 1457  namespace RIFF {
1457                  Chunk* ck;                  Chunk* ck;
1458                  uint32_t ckid;                  uint32_t ckid;
1459                  Read(&ckid, 4, 1);                  Read(&ckid, 4, 1);
1460                  #if DEBUG                  #if DEBUG_RIFF
1461                  std::cout << " ckid=" << convertToString(ckid) << std::endl;                  std::cout << " ckid=" << convertToString(ckid) << std::endl;
1462                  #endif // DEBUG                  #endif // DEBUG_RIFF
1463                  if (ckid == CHUNK_ID_LIST) {                  if (ckid == CHUNK_ID_LIST) {
1464                      ck = new RIFF::List(pFile, ullStartPos + ullPos - 4, this);                      ck = new RIFF::List(pFile, ullStartPos + ullPos - 4, this);
1465                      SetPos(ck->GetSize() + LIST_HEADER_SIZE(pFile->FileOffsetSize) - 4, RIFF::stream_curpos);                      SetPos(ck->GetSize() + LIST_HEADER_SIZE(pFile->FileOffsetSize) - 4, RIFF::stream_curpos);
# Line 1461  namespace RIFF { Line 1478  namespace RIFF {
1478      }      }
1479    
1480      void List::LoadSubChunksRecursively(progress_t* pProgress) {      void List::LoadSubChunksRecursively(progress_t* pProgress) {
1481          const int n = CountSubLists();          const int n = (int) CountSubLists();
1482          int i = 0;          int i = 0;
1483          for (List* pList = GetFirstSubList(); pList; pList = GetNextSubList(), ++i) {          for (List* pList = GetFirstSubList(); pList; pList = GetNextSubList(), ++i) {
1484              // divide local progress into subprogress              // divide local progress into subprogress
# Line 1576  namespace RIFF { Line 1593  namespace RIFF {
1593       * Loads an existing RIFF file with all its chunks.       * Loads an existing RIFF file with all its chunks.
1594       *       *
1595       * @param path - path and file name of the RIFF file to open       * @param path - path and file name of the RIFF file to open
1596       * @throws RIFF::Exception if error occured while trying to load the       * @throws RIFF::Exception if error occurred while trying to load the
1597       *                         given RIFF file       *                         given RIFF file
1598       */       */
1599      File::File(const String& path)      File::File(const String& path)
1600          : List(this), Filename(path), bIsNewFile(false), Layout(layout_standard),          : List(this), Filename(path), bIsNewFile(false), Layout(layout_standard),
1601            FileOffsetPreference(offset_size_auto)            FileOffsetPreference(offset_size_auto)
1602      {      {
1603          #if DEBUG          #if DEBUG_RIFF
1604          std::cout << "File::File("<<path<<")" << std::endl;          std::cout << "File::File("<<path<<")" << std::endl;
1605          #endif // DEBUG          #endif // DEBUG_RIFF
1606          bEndianNative = true;          bEndianNative = true;
1607          FileOffsetSize = 4;          FileOffsetSize = 4;
1608          try {          try {
# Line 1623  namespace RIFF { Line 1640  namespace RIFF {
1640       * @param Endian - whether the file uses little endian or big endian layout       * @param Endian - whether the file uses little endian or big endian layout
1641       * @param layout - general file structure type       * @param layout - general file structure type
1642       * @param fileOffsetSize - (optional) preference how to deal with large files       * @param fileOffsetSize - (optional) preference how to deal with large files
1643       * @throws RIFF::Exception if error occured while trying to load the       * @throws RIFF::Exception if error occurred while trying to load the
1644       *                         given RIFF-alike file       *                         given RIFF-alike file
1645       */       */
1646      File::File(const String& path, uint32_t FileType, endian_t Endian, layout_t layout, offset_size_t fileOffsetSize)      File::File(const String& path, uint32_t FileType, endian_t Endian, layout_t layout, offset_size_t fileOffsetSize)
# Line 1650  namespace RIFF { Line 1667  namespace RIFF {
1667       * @param path - path and file name of the RIFF file or RIFF-alike file to       * @param path - path and file name of the RIFF file or RIFF-alike file to
1668       *               be opened       *               be opened
1669       * @param FileType - (optional) expected chunk ID of first chunk in file       * @param FileType - (optional) expected chunk ID of first chunk in file
1670       * @throws RIFF::Exception if error occured while trying to load the       * @throws RIFF::Exception if error occurred while trying to load the
1671       *                         given RIFF file or RIFF-alike file       *                         given RIFF file or RIFF-alike file
1672       */       */
1673      void File::__openExistingFile(const String& path, uint32_t* FileType) {      void File::__openExistingFile(const String& path, uint32_t* FileType) {
# Line 1812  namespace RIFF { Line 1829  namespace RIFF {
1829                      #if POSIX                      #if POSIX
1830                      if (hFileRead)  close(hFileRead);                      if (hFileRead)  close(hFileRead);
1831                      if (hFileWrite) close(hFileWrite);                      if (hFileWrite) close(hFileWrite);
1832                        hFileRead = hFileWrite = 0;
1833                      #elif defined(WIN32)                      #elif defined(WIN32)
1834                      if (hFileRead  != INVALID_HANDLE_VALUE) CloseHandle(hFileRead);                      if (hFileRead  != INVALID_HANDLE_VALUE) CloseHandle(hFileRead);
1835                      if (hFileWrite != INVALID_HANDLE_VALUE) CloseHandle(hFileWrite);                      if (hFileWrite != INVALID_HANDLE_VALUE) CloseHandle(hFileWrite);
1836                        hFileRead = hFileWrite = INVALID_HANDLE_VALUE;
1837                      #else                      #else
1838                      if (hFileRead)  fclose(hFileRead);                      if (hFileRead)  fclose(hFileRead);
1839                      if (hFileWrite) fclose(hFileWrite);                      if (hFileWrite) fclose(hFileWrite);
1840                        hFileRead = hFileWrite = NULL;
1841                      #endif                      #endif
                     hFileRead = hFileWrite = 0;  
1842                      break;                      break;
1843                  default:                  default:
1844                      throw Exception("Unknown file access mode");                      throw Exception("Unknown file access mode");
# Line 1854  namespace RIFF { Line 1873  namespace RIFF {
1873       *       *
1874       * @param pProgress - optional: callback function for progress notification       * @param pProgress - optional: callback function for progress notification
1875       * @throws RIFF::Exception if there is an empty chunk or empty list       * @throws RIFF::Exception if there is an empty chunk or empty list
1876       *                         chunk or any kind of IO error occured       *                         chunk or any kind of IO error occurred
1877       */       */
1878      void File::Save(progress_t* pProgress) {      void File::Save(progress_t* pProgress) {
1879          //TODO: implementation for the case where first chunk is not a global container (List chunk) is not implemented yet (i.e. Korg files)          //TODO: implementation for the case where first chunk is not a global container (List chunk) is not implemented yet (i.e. Korg files)
# Line 2079  namespace RIFF { Line 2098  namespace RIFF {
2098      }      }
2099    
2100      File::~File() {      File::~File() {
2101          #if DEBUG          #if DEBUG_RIFF
2102          std::cout << "File::~File()" << std::endl;          std::cout << "File::~File()" << std::endl;
2103          #endif // DEBUG          #endif // DEBUG_RIFF
2104          Cleanup();          Cleanup();
2105      }      }
2106    
# Line 2251  namespace RIFF { Line 2270  namespace RIFF {
2270  // *************** Exception ***************  // *************** Exception ***************
2271  // *  // *
2272    
2273        Exception::Exception() {
2274        }
2275    
2276        Exception::Exception(String format, ...) {
2277            va_list arg;
2278            va_start(arg, format);
2279            Message = assemble(format, arg);
2280            va_end(arg);
2281        }
2282    
2283        Exception::Exception(String format, va_list arg) {
2284            Message = assemble(format, arg);
2285        }
2286    
2287      void Exception::PrintMessage() {      void Exception::PrintMessage() {
2288          std::cout << "RIFF::Exception: " << Message << std::endl;          std::cout << "RIFF::Exception: " << Message << std::endl;
2289      }      }
2290    
2291        String Exception::assemble(String format, va_list arg) {
2292            char* buf = NULL;
2293            vasprintf(&buf, format.c_str(), arg);
2294            String s = buf;
2295            free(buf);
2296            return s;
2297        }
2298    
2299    
2300  // *************** functions ***************  // *************** functions ***************
2301  // *  // *

Legend:
Removed from v.2922  
changed lines
  Added in v.3478

  ViewVC Help
Powered by ViewVC