[vlc-devel] [PATCH] fetcher: kill the thread after a delay of 5 seconds

Thomas Guillem thomas at gllm.fr
Wed Jun 1 15:49:36 CEST 2016


Not as easy to factor code with prefetcher since they don't use the same kind
of data structure for the task list.
---
 src/playlist/fetcher.c | 62 ++++++++++++++++++++++++++++++++++++--------------
 1 file changed, 45 insertions(+), 17 deletions(-)

diff --git a/src/playlist/fetcher.c b/src/playlist/fetcher.c
index ff1e94b..29efba9 100644
--- a/src/playlist/fetcher.c
+++ b/src/playlist/fetcher.c
@@ -41,6 +41,8 @@
 #include "fetcher.h"
 #include "input/input_interface.h"
 
+#define THREAD_TTL INT64_C(5000000); /* 5 seconds */
+
 /*****************************************************************************
  * Structures/definitions
  *****************************************************************************/
@@ -75,7 +77,9 @@ struct playlist_fetcher_t
     vlc_object_t   *object;
     vlc_mutex_t     lock;
     vlc_cond_t      wait;
+    vlc_cond_t      thread_wait;
     bool            b_live;
+    bool            b_request_stop;
     vlc_interrupt_t *interrupt;
 
     fetcher_entry_t *p_waiting_head[PASS_COUNT];
@@ -106,7 +110,9 @@ playlist_fetcher_t *playlist_fetcher_New( vlc_object_t *parent )
     p_fetcher->object = parent;
     vlc_mutex_init( &p_fetcher->lock );
     vlc_cond_init( &p_fetcher->wait );
+    vlc_cond_init( &p_fetcher->thread_wait );
     p_fetcher->b_live = false;
+    p_fetcher->b_request_stop = false;
 
     bool b_access = var_InheritBool( parent, "metadata-network-access" );
     if ( !b_access )
@@ -150,6 +156,8 @@ void playlist_fetcher_Push( playlist_fetcher_t *p_fetcher, input_item_t *p_item,
         else
             p_fetcher->b_live = true;
     }
+    else
+        vlc_cond_signal( &p_fetcher->thread_wait );
     vlc_mutex_unlock( &p_fetcher->lock );
 }
 
@@ -173,10 +181,14 @@ void playlist_fetcher_Delete( playlist_fetcher_t *p_fetcher )
         p_fetcher->p_waiting_head[i_queue] = NULL;
     }
 
+    p_fetcher->b_request_stop = true;
+    vlc_cond_signal( &p_fetcher->thread_wait );
+
     while( p_fetcher->b_live )
         vlc_cond_wait( &p_fetcher->wait, &p_fetcher->lock );
     vlc_mutex_unlock( &p_fetcher->lock );
 
+    vlc_cond_destroy( &p_fetcher->thread_wait );
     vlc_cond_destroy( &p_fetcher->wait );
     vlc_mutex_destroy( &p_fetcher->lock );
 
@@ -458,6 +470,33 @@ static void *Thread( void *p_data )
         fetcher_entry_t *p_entry = NULL;
 
         vlc_mutex_lock( &p_fetcher->lock );
+
+        if( p_fetcher->p_waiting_head[PASS1_LOCAL] == NULL
+         && p_fetcher->p_waiting_head[PASS2_NETWORK] == NULL )
+        {
+            const mtime_t deadline = mdate() + THREAD_TTL;
+            int ret = 0;
+
+            /* Abort loop if stop is requested, waiting arrays are not empty or
+             * in case of timeout */
+            while( !p_fetcher->b_request_stop
+                && p_fetcher->p_waiting_head[PASS1_LOCAL] == NULL
+                && p_fetcher->p_waiting_head[PASS2_NETWORK] == NULL
+                && ret == 0 )
+                ret = vlc_cond_timedwait( &p_fetcher->thread_wait,
+                                          &p_fetcher->lock, deadline );
+
+            if( p_fetcher->p_waiting_head[PASS1_LOCAL] == NULL
+             && p_fetcher->p_waiting_head[PASS2_NETWORK] == NULL )
+            {
+                vlc_interrupt_set( NULL );
+                p_fetcher->b_live = false;
+                vlc_cond_signal( &p_fetcher->wait );
+                vlc_mutex_unlock( &p_fetcher->lock );
+                break;
+            }
+        }
+
         for ( int i=0; i<PASS_COUNT; i++ )
         {
             if ( p_fetcher->p_waiting_head[i] )
@@ -467,25 +506,14 @@ static void *Thread( void *p_data )
             }
         }
 
-        if( p_fetcher->p_waiting_head[e_pass] )
-        {
-            p_entry = p_fetcher->p_waiting_head[e_pass];
-            p_fetcher->p_waiting_head[e_pass] = p_entry->p_next;
-            if ( p_entry->p_next == NULL )
-                p_fetcher->p_waiting_tail[e_pass] = NULL;
-            p_entry->p_next = NULL;
-        }
-        else
-        {
-            vlc_interrupt_set( NULL );
-            p_fetcher->b_live = false;
-            vlc_cond_signal( &p_fetcher->wait );
-        }
+        p_entry = p_fetcher->p_waiting_head[e_pass];
+        assert( p_entry );
+        p_fetcher->p_waiting_head[e_pass] = p_entry->p_next;
+        if ( p_entry->p_next == NULL )
+            p_fetcher->p_waiting_tail[e_pass] = NULL;
+        p_entry->p_next = NULL;
         vlc_mutex_unlock( &p_fetcher->lock );
 
-        if( !p_entry )
-            break;
-
         meta_fetcher_scope_t e_prev_scope = p_fetcher->e_scope;
 
         /* scope override */
-- 
2.8.1



More information about the vlc-devel mailing list