/[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 3915 by schoenebeck, Mon Jun 7 18:57:17 2021 UTC revision 3916 by schoenebeck, Mon Jun 7 19:42:17 2021 UTC
# Line 1737  namespace RIFF { Line 1737  namespace RIFF {
1737          : List(this), bIsNewFile(true), Layout(layout_standard),          : List(this), bIsNewFile(true), Layout(layout_standard),
1738            FileOffsetPreference(offset_size_auto)            FileOffsetPreference(offset_size_auto)
1739      {      {
1740            io.isPerThread = false;
1741          #if defined(WIN32)          #if defined(WIN32)
1742          io.hRead = io.hWrite = INVALID_HANDLE_VALUE;          io.hRead = io.hWrite = INVALID_HANDLE_VALUE;
1743          #else          #else
# Line 1832  namespace RIFF { Line 1833  namespace RIFF {
1833       *                         given RIFF file or RIFF-alike file       *                         given RIFF file or RIFF-alike file
1834       */       */
1835      void File::__openExistingFile(const String& path, uint32_t* FileType) {      void File::__openExistingFile(const String& path, uint32_t* FileType) {
1836            io.isPerThread = false;
1837          #if POSIX          #if POSIX
1838          io.hRead = io.hWrite = open(path.c_str(), O_RDONLY | O_NONBLOCK);          io.hRead = io.hWrite = open(path.c_str(), O_RDONLY | O_NONBLOCK);
1839          if (io.hRead == -1) {          if (io.hRead == -1) {
# Line 1992  namespace RIFF { Line 1994  namespace RIFF {
1994       * @see File::IsIOPerThread() for multi-threaded streaming       * @see File::IsIOPerThread() for multi-threaded streaming
1995       */       */
1996      bool File::SetMode(stream_mode_t NewMode) {      bool File::SetMode(stream_mode_t NewMode) {
1997            bool bResetPos = false;
1998            bool res = SetModeInternal(NewMode, &bResetPos);
1999            // resetting position must be handled outside above's call to avoid any
2000            // potential dead lock, as SetModeInternal() acquires a lock and
2001            // __resetPos() acquires a lock by itself (not a theoretical issue!)
2002            if (bResetPos)
2003                __resetPos(); // reset read/write position of ALL 'Chunk' objects
2004            return res;
2005        }
2006    
2007        bool File::SetModeInternal(stream_mode_t NewMode, bool* pResetPos) {
2008          std::lock_guard<std::mutex> lock(io.mutex);          std::lock_guard<std::mutex> lock(io.mutex);
2009          HandlePair& io = FileHandlePairUnsafeRef();          HandlePair& io = FileHandlePairUnsafeRef();
2010          if (NewMode != io.Mode) {          if (NewMode != io.Mode) {
# Line 2022  namespace RIFF { Line 2035  namespace RIFF {
2035                      io.hRead = io.hWrite = fopen(Filename.c_str(), "rb");                      io.hRead = io.hWrite = fopen(Filename.c_str(), "rb");
2036                      if (!io.hRead) throw Exception("Could not (re)open file \"" + Filename + "\" in read mode");                      if (!io.hRead) throw Exception("Could not (re)open file \"" + Filename + "\" in read mode");
2037                      #endif                      #endif
2038                      __resetPos(); // reset read/write position of ALL 'Chunk' objects                      *pResetPos = true;
2039                      break;                      break;
2040                  case stream_mode_read_write:                  case stream_mode_read_write:
2041                      if (_isValidHandle(io.hRead)) _close(io.hRead);                      if (_isValidHandle(io.hRead)) _close(io.hRead);
# Line 2061  namespace RIFF { Line 2074  namespace RIFF {
2074                          throw Exception("Could not open file \"" + Filename + "\" in read+write mode");                          throw Exception("Could not open file \"" + Filename + "\" in read+write mode");
2075                      }                      }
2076                      #endif                      #endif
2077                      __resetPos(); // reset read/write position of ALL 'Chunk' objects                      *pResetPos = true;
2078                      break;                      break;
2079                  case stream_mode_closed:                  case stream_mode_closed:
2080                      if (_isValidHandle(io.hRead)) _close(io.hRead);                      if (_isValidHandle(io.hRead)) _close(io.hRead);
# Line 2520  namespace RIFF { Line 2533  namespace RIFF {
2533       * @see SetIOPerThread()       * @see SetIOPerThread()
2534       */       */
2535      bool File::IsIOPerThread() const {      bool File::IsIOPerThread() const {
2536          std::lock_guard<std::mutex> lock(io.mutex);          //NOTE: Not caring about atomicity here at all, for three reasons:
2537          return !io.byThread.empty();          // 1. SetIOPerThread() is assumed to be called only once for the entire
2538            //    life time of a RIFF::File, usually very early at its lifetime, and
2539            //    hence a change to isPerThread should already safely be propagated
2540            //    before any other thread would actually read this boolean flag.
2541            // 2. This method is called very frequently, and therefore any
2542            //    synchronization techique would hurt runtime efficiency.
2543            // 3. Using even a mutex lock here might easily cause a deadlock due to
2544            //    other locks been taken in this .cpp file, i.e. at a higher call
2545            //    stack level (and this is the main reason why I removed it here).
2546            return io.isPerThread;
2547      }      }
2548    
2549      /** @brief Enable/disable file streams being independent for each thread.      /** @brief Enable/disable file streams being independent for each thread.
# Line 2542  namespace RIFF { Line 2564  namespace RIFF {
2564      void File::SetIOPerThread(bool enable) {      void File::SetIOPerThread(bool enable) {
2565          std::lock_guard<std::mutex> lock(io.mutex);          std::lock_guard<std::mutex> lock(io.mutex);
2566          if (!io.byThread.empty() == enable) return;          if (!io.byThread.empty() == enable) return;
2567            io.isPerThread = enable;
2568          if (enable) {          if (enable) {
2569              const std::thread::id tid = std::this_thread::get_id();              const std::thread::id tid = std::this_thread::get_id();
2570              io.byThread[tid] = io;              io.byThread[tid] = io;

Legend:
Removed from v.3915  
changed lines
  Added in v.3916

  ViewVC Help
Powered by ViewVC