/[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 2914 by schoenebeck, Tue May 17 19:04:56 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 125  namespace RIFF { Line 142  namespace RIFF {
142              read(pFile->hFileRead, &ChunkID, 4);              read(pFile->hFileRead, &ChunkID, 4);
143              read(pFile->hFileRead, &ullCurrentChunkSize, pFile->FileOffsetSize);              read(pFile->hFileRead, &ullCurrentChunkSize, pFile->FileOffsetSize);
144          #elif defined(WIN32)          #elif defined(WIN32)
145          const LARGE_INTEGER liFilePos = { .QuadPart = filePos };          LARGE_INTEGER liFilePos;
146            liFilePos.QuadPart = filePos;
147          if (SetFilePointerEx(pFile->hFileRead, liFilePos, NULL/*new pos pointer*/, FILE_BEGIN)) {          if (SetFilePointerEx(pFile->hFileRead, liFilePos, NULL/*new pos pointer*/, FILE_BEGIN)) {
148              DWORD dwBytesRead;              DWORD dwBytesRead;
149              ReadFile(pFile->hFileRead, &ChunkID, 4, &dwBytesRead, NULL);              ReadFile(pFile->hFileRead, &ChunkID, 4, &dwBytesRead, NULL);
# Line 152  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 185  namespace RIFF { Line 203  namespace RIFF {
203              write(pFile->hFileWrite, &ullNewChunkSize, pFile->FileOffsetSize);              write(pFile->hFileWrite, &ullNewChunkSize, pFile->FileOffsetSize);
204          }          }
205          #elif defined(WIN32)          #elif defined(WIN32)
206          const LARGE_INTEGER liFilePos = { .QuadPart = filePos };          LARGE_INTEGER liFilePos;
207            liFilePos.QuadPart = filePos;
208          if (SetFilePointerEx(pFile->hFileWrite, liFilePos, NULL/*new pos pointer*/, FILE_BEGIN)) {          if (SetFilePointerEx(pFile->hFileWrite, liFilePos, NULL/*new pos pointer*/, FILE_BEGIN)) {
209              DWORD dwBytesWritten;              DWORD dwBytesWritten;
210              WriteFile(pFile->hFileWrite, &uiNewChunkID, 4, &dwBytesWritten, NULL);              WriteFile(pFile->hFileWrite, &uiNewChunkID, 4, &dwBytesWritten, NULL);
# Line 220  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 252  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 283  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 311  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 324  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;
352          #elif defined(WIN32)          #elif defined(WIN32)
353          const LARGE_INTEGER liFilePos = { .QuadPart = ullStartPos + ullPos };          LARGE_INTEGER liFilePos;
354            liFilePos.QuadPart = ullStartPos + ullPos;
355          if (!SetFilePointerEx(pFile->hFileRead, liFilePos, NULL/*new pos pointer*/, FILE_BEGIN))          if (!SetFilePointerEx(pFile->hFileRead, liFilePos, NULL/*new pos pointer*/, FILE_BEGIN))
356              return 0;              return 0;
357          DWORD readWords;          DWORD readWords;
# Line 379  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 416  namespace RIFF { Line 436  namespace RIFF {
436          if (writtenWords < 1) throw Exception("POSIX IO Error while trying to write chunk data");          if (writtenWords < 1) throw Exception("POSIX IO Error while trying to write chunk data");
437          writtenWords /= WordSize;          writtenWords /= WordSize;
438          #elif defined(WIN32)          #elif defined(WIN32)
439          const LARGE_INTEGER liFilePos = { .QuadPart = ullStartPos + ullPos };          LARGE_INTEGER liFilePos;
440            liFilePos.QuadPart = ullStartPos + ullPos;
441          if (!SetFilePointerEx(pFile->hFileWrite, liFilePos, NULL/*new pos pointer*/, FILE_BEGIN)) {          if (!SetFilePointerEx(pFile->hFileWrite, liFilePos, NULL/*new pos pointer*/, FILE_BEGIN)) {
442              throw Exception("Could not seek to position " + ToString(ullPos) +              throw Exception("Could not seek to position " + ToString(ullPos) +
443                              " in chunk (" + ToString(ullStartPos + ullPos) + " in file)");                              " in chunk (" + ToString(ullStartPos + ullPos) + " in file)");
# Line 451  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 472  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 488  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 509  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 525  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 546  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 562  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 583  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 599  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 620  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 636  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 653  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 674  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 686  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 702  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 719  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 736  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 753  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 770  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 807  namespace RIFF { Line 828  namespace RIFF {
828              #if POSIX              #if POSIX
829              if (lseek(pFile->hFileRead, ullStartPos, SEEK_SET) == -1) return NULL;              if (lseek(pFile->hFileRead, ullStartPos, SEEK_SET) == -1) return NULL;
830              #elif defined(WIN32)              #elif defined(WIN32)
831              const LARGE_INTEGER liFilePos = { .QuadPart = ullStartPos };              LARGE_INTEGER liFilePos;
832                liFilePos.QuadPart = ullStartPos;
833              if (!SetFilePointerEx(pFile->hFileRead, liFilePos, NULL/*new pos pointer*/, FILE_BEGIN)) return NULL;              if (!SetFilePointerEx(pFile->hFileRead, liFilePos, NULL/*new pos pointer*/, FILE_BEGIN)) return NULL;
834              #else              #else
835              if (fseeko(pFile->hFileRead, ullStartPos, SEEK_SET)) return NULL;              if (fseeko(pFile->hFileRead, ullStartPos, SEEK_SET)) return NULL;
# Line 869  namespace RIFF { Line 891  namespace RIFF {
891       * boundary!       * boundary!
892       *       *
893       * @param NewSize - new chunk body size in bytes (must be greater than zero)       * @param NewSize - new chunk body size in bytes (must be greater than zero)
894       * @throws RIFF::Exception  if \a NewSize is less than 1 or Unrealistic large       * @throws RIFF::Exception  if \a NewSize is less than 1 or unrealistic large
895       * @see File::Save()       * @see File::Save()
896       */       */
897      void Chunk::Resize(file_offset_t NewSize) {      void Chunk::Resize(file_offset_t NewSize) {
# Line 912  namespace RIFF { Line 934  namespace RIFF {
934                  throw Exception("Writing Chunk data (from RAM) failed");                  throw Exception("Writing Chunk data (from RAM) failed");
935              }              }
936              #elif defined(WIN32)              #elif defined(WIN32)
937              const LARGE_INTEGER liFilePos = { .QuadPart = ullWritePos };              LARGE_INTEGER liFilePos;
938                liFilePos.QuadPart = ullWritePos;
939              SetFilePointerEx(pFile->hFileWrite, liFilePos, NULL/*new pos pointer*/, FILE_BEGIN);              SetFilePointerEx(pFile->hFileWrite, liFilePos, NULL/*new pos pointer*/, FILE_BEGIN);
940              DWORD dwBytesWritten;              DWORD dwBytesWritten;
941              WriteFile(pFile->hFileWrite, pChunkData, ullNewChunkSize, &dwBytesWritten, NULL); //FIXME: won't save chunks larger than 2GB !              WriteFile(pFile->hFileWrite, pChunkData, ullNewChunkSize, &dwBytesWritten, NULL); //FIXME: won't save chunks larger than 2GB !
# Line 935  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 = { .QuadPart = ullStartPos + ullCurrentDataOffset + ullOffset };                  LARGE_INTEGER liFilePos;
969                    liFilePos.QuadPart = ullStartPos + ullCurrentDataOffset + ullOffset;
970                  SetFilePointerEx(pFile->hFileRead, liFilePos, NULL/*new pos pointer*/, FILE_BEGIN);                  SetFilePointerEx(pFile->hFileRead, liFilePos, NULL/*new pos pointer*/, FILE_BEGIN);
971                  ReadFile(pFile->hFileRead, pCopyBuffer, iBytesMoved, &iBytesMoved, NULL);                  ReadFile(pFile->hFileRead, pCopyBuffer, iBytesMoved, &iBytesMoved, NULL);
972                  liFilePos.QuadPart = ullWritePos + ullOffset;                  liFilePos.QuadPart = ullWritePos + ullOffset;
# Line 976  namespace RIFF { Line 1000  namespace RIFF {
1000              lseek(pFile->hFileWrite, ullStartPos + ullNewChunkSize, SEEK_SET);              lseek(pFile->hFileWrite, ullStartPos + ullNewChunkSize, SEEK_SET);
1001              write(pFile->hFileWrite, &cPadByte, 1);              write(pFile->hFileWrite, &cPadByte, 1);
1002              #elif defined(WIN32)              #elif defined(WIN32)
1003              const LARGE_INTEGER liFilePos = { .QuadPart = ullStartPos + ullNewChunkSize };              LARGE_INTEGER liFilePos;
1004                liFilePos.QuadPart = ullStartPos + ullNewChunkSize;
1005              SetFilePointerEx(pFile->hFileWrite, liFilePos, NULL/*new pos pointer*/, FILE_BEGIN);              SetFilePointerEx(pFile->hFileWrite, liFilePos, NULL/*new pos pointer*/, FILE_BEGIN);
1006              DWORD dwBytesWritten;              DWORD dwBytesWritten;
1007              WriteFile(pFile->hFileWrite, &cPadByte, 1, &dwBytesWritten, NULL);              WriteFile(pFile->hFileWrite, &cPadByte, 1, &dwBytesWritten, NULL);
# Line 1000  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 1026  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 1061  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 1071  namespace RIFF { Line 1096  namespace RIFF {
1096      /**      /**
1097       *  Returns sublist chunk with list type <i>\a ListType</i> within this       *  Returns sublist chunk with list type <i>\a ListType</i> within this
1098       *  chunk list. Use this method if you expect only one sublist chunk of       *  chunk list. Use this method if you expect only one sublist chunk of
1099       *  that type in the list. It there are more than one, it's undetermined       *  that type in the list. If there are more than one, it's undetermined
1100       *  which one of them will be returned! If there are no sublists with       *  which one of them will be returned! If there are no sublists with
1101       *  that desired list type, NULL will be returned.       *  that desired list type, NULL will be returned.
1102       *       *
# Line 1080  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 1097  namespace RIFF { Line 1122  namespace RIFF {
1122      }      }
1123    
1124      /**      /**
1125       *  Returns the first subchunk within the list. You have to call this       *  Returns the first subchunk within the list (which may be an ordinary
1126         *  chunk as well as a list chunk). You have to call this
1127       *  method before you can call GetNextSubChunk(). Recall it when you want       *  method before you can call GetNextSubChunk(). Recall it when you want
1128       *  to start from the beginning of the list again.       *  to start from the beginning of the list again.
1129       *       *
# Line 1105  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;
1140      }      }
1141    
1142      /**      /**
1143       *  Returns the next subchunk within the list. You have to call       *  Returns the next subchunk within the list (which may be an ordinary
1144         *  chunk as well as a list chunk). You have to call
1145       *  GetFirstSubChunk() before you can use this method!       *  GetFirstSubChunk() before you can use this method!
1146       *       *
1147       *  @returns  pointer to the next subchunk within the list or NULL if       *  @returns  pointer to the next subchunk within the list or NULL if
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 1139  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 1161  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 1176  namespace RIFF { Line 1203  namespace RIFF {
1203      }      }
1204    
1205      /**      /**
1206       *  Returns number of subchunks within the list.       *  Returns number of subchunks within the list (including list chunks).
1207       */       */
1208      unsigned int List::CountSubChunks() {      size_t List::CountSubChunks() {
1209          if (!pSubChunks) LoadSubChunks();          if (!pSubChunks) LoadSubChunks();
1210          return pSubChunks->size();          return pSubChunks->size();
1211      }      }
# Line 1187  namespace RIFF { Line 1214  namespace RIFF {
1214       *  Returns number of subchunks within the list with chunk ID       *  Returns number of subchunks within the list with chunk ID
1215       *  <i>\a ChunkId</i>.       *  <i>\a ChunkId</i>.
1216       */       */
1217      unsigned int List::CountSubChunks(uint32_t ChunkID) {      size_t List::CountSubChunks(uint32_t ChunkID) {
1218          unsigned int result = 0;          size_t result = 0;
1219          if (!pSubChunks) LoadSubChunks();          if (!pSubChunks) LoadSubChunks();
1220          ChunkList::iterator iter = pSubChunks->begin();          ChunkList::iterator iter = pSubChunks->begin();
1221          ChunkList::iterator end  = pSubChunks->end();          ChunkList::iterator end  = pSubChunks->end();
# Line 1204  namespace RIFF { Line 1231  namespace RIFF {
1231      /**      /**
1232       *  Returns number of sublists within the list.       *  Returns number of sublists within the list.
1233       */       */
1234      unsigned int List::CountSubLists() {      size_t List::CountSubLists() {
1235          return CountSubChunks(CHUNK_ID_LIST);          return CountSubChunks(CHUNK_ID_LIST);
1236      }      }
1237    
# Line 1212  namespace RIFF { Line 1239  namespace RIFF {
1239       *  Returns number of sublists within the list with list type       *  Returns number of sublists within the list with list type
1240       *  <i>\a ListType</i>       *  <i>\a ListType</i>
1241       */       */
1242      unsigned int List::CountSubLists(uint32_t ListType) {      size_t List::CountSubLists(uint32_t ListType) {
1243          unsigned int result = 0;          size_t result = 0;
1244          if (!pSubChunks) LoadSubChunks();          if (!pSubChunks) LoadSubChunks();
1245          ChunkList::iterator iter = pSubChunks->begin();          ChunkList::iterator iter = pSubChunks->begin();
1246          ChunkList::iterator end  = pSubChunks->end();          ChunkList::iterator end  = pSubChunks->end();
# Line 1365  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 1375  namespace RIFF { Line 1402  namespace RIFF {
1402          lseek(pFile->hFileRead, filePos + CHUNK_HEADER_SIZE(pFile->FileOffsetSize), SEEK_SET);          lseek(pFile->hFileRead, filePos + CHUNK_HEADER_SIZE(pFile->FileOffsetSize), SEEK_SET);
1403          read(pFile->hFileRead, &ListType, 4);          read(pFile->hFileRead, &ListType, 4);
1404          #elif defined(WIN32)          #elif defined(WIN32)
1405          const LARGE_INTEGER liFilePos = { .QuadPart = filePos + CHUNK_HEADER_SIZE(pFile->FileOffsetSize) };          LARGE_INTEGER liFilePos;
1406            liFilePos.QuadPart = filePos + CHUNK_HEADER_SIZE(pFile->FileOffsetSize);
1407          SetFilePointerEx(pFile->hFileRead, liFilePos, NULL/*new pos pointer*/, FILE_BEGIN);          SetFilePointerEx(pFile->hFileRead, liFilePos, NULL/*new pos pointer*/, FILE_BEGIN);
1408          DWORD dwBytesRead;          DWORD dwBytesRead;
1409          ReadFile(pFile->hFileRead, &ListType, 4, &dwBytesRead, NULL);          ReadFile(pFile->hFileRead, &ListType, 4, &dwBytesRead, NULL);
# Line 1383  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 1400  namespace RIFF { Line 1428  namespace RIFF {
1428          lseek(pFile->hFileWrite, filePos + CHUNK_HEADER_SIZE(pFile->FileOffsetSize), SEEK_SET);          lseek(pFile->hFileWrite, filePos + CHUNK_HEADER_SIZE(pFile->FileOffsetSize), SEEK_SET);
1429          write(pFile->hFileWrite, &ListType, 4);          write(pFile->hFileWrite, &ListType, 4);
1430          #elif defined(WIN32)          #elif defined(WIN32)
1431          const LARGE_INTEGER liFilePos = { .QuadPart = filePos + CHUNK_HEADER_SIZE(pFile->FileOffsetSize) };          LARGE_INTEGER liFilePos;
1432            liFilePos.QuadPart = filePos + CHUNK_HEADER_SIZE(pFile->FileOffsetSize);
1433          SetFilePointerEx(pFile->hFileWrite, liFilePos, NULL/*new pos pointer*/, FILE_BEGIN);          SetFilePointerEx(pFile->hFileWrite, liFilePos, NULL/*new pos pointer*/, FILE_BEGIN);
1434          DWORD dwBytesWritten;          DWORD dwBytesWritten;
1435          WriteFile(pFile->hFileWrite, &ListType, 4, &dwBytesWritten, NULL);          WriteFile(pFile->hFileWrite, &ListType, 4, &dwBytesWritten, NULL);
# Line 1411  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 1428  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 1449  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 1485  namespace RIFF { Line 1514  namespace RIFF {
1514    
1515          // write all subchunks (including sub list chunks) recursively          // write all subchunks (including sub list chunks) recursively
1516          if (pSubChunks) {          if (pSubChunks) {
1517              int i = 0;              size_t i = 0;
1518              const int n = pSubChunks->size();              const size_t n = pSubChunks->size();
1519              for (ChunkList::iterator iter = pSubChunks->begin(), end = pSubChunks->end(); iter != end; ++iter, ++i) {              for (ChunkList::iterator iter = pSubChunks->begin(), end = pSubChunks->end(); iter != end; ++iter, ++i) {
1520                  // divide local progress into subprogress for loading current Instrument                  // divide local progress into subprogress for loading current Instrument
1521                  progress_t subprogress;                  progress_t subprogress;
# Line 1564  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 1611  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 1638  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 1800  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 1842  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 1898  namespace RIFF { Line 1929  namespace RIFF {
1929              #if defined(WIN32)              #if defined(WIN32)
1930              DWORD iBytesMoved = 1; // we have to pass it via pointer to the Windows API, thus the correct size must be ensured              DWORD iBytesMoved = 1; // we have to pass it via pointer to the Windows API, thus the correct size must be ensured
1931              #else              #else
1932              int iBytesMoved = 1;              ssize_t iBytesMoved = 1;
1933              #endif              #endif
1934              for (file_offset_t ullPos = workingFileSize, iNotif = 0; iBytesMoved > 0; ++iNotif) {              for (file_offset_t ullPos = workingFileSize, iNotif = 0; iBytesMoved > 0; ++iNotif) {
1935                  iBytesMoved = (ullPos < 4096) ? ullPos : 4096;                  iBytesMoved = (ullPos < 4096) ? ullPos : 4096;
# Line 1909  namespace RIFF { Line 1940  namespace RIFF {
1940                  lseek(hFileWrite, ullPos + positiveSizeDiff, SEEK_SET);                  lseek(hFileWrite, ullPos + positiveSizeDiff, SEEK_SET);
1941                  iBytesMoved = write(hFileWrite, pCopyBuffer, iBytesMoved);                  iBytesMoved = write(hFileWrite, pCopyBuffer, iBytesMoved);
1942                  #elif defined(WIN32)                  #elif defined(WIN32)
1943                  LARGE_INTEGER liFilePos = { .QuadPart = ullPos };                  LARGE_INTEGER liFilePos;
1944                    liFilePos.QuadPart = ullPos;
1945                  SetFilePointerEx(hFileRead, liFilePos, NULL/*new pos pointer*/, FILE_BEGIN);                  SetFilePointerEx(hFileRead, liFilePos, NULL/*new pos pointer*/, FILE_BEGIN);
1946                  ReadFile(hFileRead, pCopyBuffer, iBytesMoved, &iBytesMoved, NULL);                  ReadFile(hFileRead, pCopyBuffer, iBytesMoved, &iBytesMoved, NULL);
1947                  liFilePos.QuadPart = ullPos + positiveSizeDiff;                  liFilePos.QuadPart = ullPos + positiveSizeDiff;
# Line 2053  namespace RIFF { Line 2085  namespace RIFF {
2085          if (ftruncate(hFileWrite, ullNewSize) < 0)          if (ftruncate(hFileWrite, ullNewSize) < 0)
2086              throw Exception("Could not resize file \"" + Filename + "\"");              throw Exception("Could not resize file \"" + Filename + "\"");
2087          #elif defined(WIN32)          #elif defined(WIN32)
2088          const LARGE_INTEGER liFilePos = { .QuadPart = ullNewSize };          LARGE_INTEGER liFilePos;
2089            liFilePos.QuadPart = ullNewSize;
2090          if (          if (
2091              !SetFilePointerEx(hFileWrite, liFilePos, NULL/*new pos pointer*/, FILE_BEGIN) ||              !SetFilePointerEx(hFileWrite, liFilePos, NULL/*new pos pointer*/, FILE_BEGIN) ||
2092              !SetEndOfFile(hFileWrite)              !SetEndOfFile(hFileWrite)
# Line 2065  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 2237  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.2914  
changed lines
  Added in v.3478

  ViewVC Help
Powered by ViewVC