[vlc-commits] demux: adaptive: change downloader lock contention

Francois Cartegnie git at videolan.org
Fri Nov 27 11:23:25 CET 2020


vlc | branch: master | Francois Cartegnie <fcvlcdev at free.fr> | Wed Oct 28 18:04:22 2020 +0100| [dae323a91070adcec52769cc4a1c7c6d5d5ee572] | committer: Francois Cartegnie

demux: adaptive: change downloader lock contention

don't hold lock while downloading, allowing to early cancel

> http://git.videolan.org/gitweb.cgi/vlc.git/?a=commit;h=dae323a91070adcec52769cc4a1c7c6d5d5ee572
---

 modules/demux/adaptive/http/Downloader.cpp | 41 +++++++++++++++++-------------
 modules/demux/adaptive/http/Downloader.hpp |  3 ++-
 2 files changed, 26 insertions(+), 18 deletions(-)

diff --git a/modules/demux/adaptive/http/Downloader.cpp b/modules/demux/adaptive/http/Downloader.cpp
index 666c86abdb..1e003d8453 100644
--- a/modules/demux/adaptive/http/Downloader.cpp
+++ b/modules/demux/adaptive/http/Downloader.cpp
@@ -33,6 +33,7 @@ Downloader::Downloader()
 {
     killed = false;
     thread_handle_valid = false;
+    current = NULL;
 }
 
 bool Downloader::start()
@@ -73,8 +74,14 @@ void Downloader::schedule(HTTPChunkBufferedSource *source)
 void Downloader::cancel(HTTPChunkBufferedSource *source)
 {
     vlc::threads::mutex_locker locker {lock};
-    source->release();
-    chunks.remove(source);
+    while (current == source)
+        updated_cond.wait(lock);
+
+    if(!source->isDone())
+    {
+        chunks.remove(source);
+        source->release();
+    }
 }
 
 void * Downloader::downloaderThread(void *opaque)
@@ -84,32 +91,32 @@ void * Downloader::downloaderThread(void *opaque)
     return NULL;
 }
 
-void Downloader::DownloadSource(HTTPChunkBufferedSource *source)
-{
-    if(!source->isDone())
-        source->bufferize(HTTPChunkSource::CHUNK_SIZE);
-}
-
 void Downloader::Run()
 {
-    vlc::threads::mutex_locker locker {lock};
     while(1)
     {
+        lock.lock();
+
         while(chunks.empty() && !killed)
             wait_cond.wait(lock);
 
         if(killed)
+        {
+            lock.unlock();
             break;
+        }
 
-        if(!chunks.empty())
+        current = chunks.front();
+        lock.unlock();
+        current->bufferize(HTTPChunkSource::CHUNK_SIZE);
+        lock.lock();
+        if(current->isDone())
         {
-            HTTPChunkBufferedSource *source = chunks.front();
-            DownloadSource(source);
-            if(source->isDone())
-            {
-                chunks.pop_front();
-                source->release();
-            }
+            chunks.pop_front();
+            current->release();
         }
+        current = NULL;
+        updated_cond.signal();
+        lock.unlock();
     }
 }
diff --git a/modules/demux/adaptive/http/Downloader.hpp b/modules/demux/adaptive/http/Downloader.hpp
index e4ee0d5b93..dc05443adb 100644
--- a/modules/demux/adaptive/http/Downloader.hpp
+++ b/modules/demux/adaptive/http/Downloader.hpp
@@ -44,14 +44,15 @@ namespace adaptive
             private:
                 static void * downloaderThread(void *);
                 void Run();
-                void DownloadSource(HTTPChunkBufferedSource *);
                 void kill();
                 vlc_thread_t thread_handle;
                 vlc::threads::mutex lock;
                 vlc::threads::condition_variable wait_cond;
+                vlc::threads::condition_variable updated_cond;
                 bool         thread_handle_valid;
                 bool         killed;
                 std::list<HTTPChunkBufferedSource *> chunks;
+                HTTPChunkBufferedSource *current;
         };
 
     }



More information about the vlc-commits mailing list