From: RĂ©mi Denis-Courmont Date: Mon, 5 Jan 2009 17:48:17 +0000 (+0200) Subject: Use a proper condition variable for variable callback handling X-Git-Tag: 1.0.0-pre1~1527 X-Git-Url: https://git.sesse.net/?a=commitdiff_plain;h=6accad54cacc1db8bcc445bdd643e0ed42d8687b;p=vlc Use a proper condition variable for variable callback handling --- diff --git a/src/libvlc.h b/src/libvlc.h index 5859ece03b..eadc1faeb7 100644 --- a/src/libvlc.h +++ b/src/libvlc.h @@ -150,6 +150,7 @@ typedef struct vlc_object_internals_t /* Object variables */ variable_t * p_vars; vlc_mutex_t var_lock; + vlc_cond_t var_wait; int i_vars; /* Thread properties, if any */ diff --git a/src/misc/objects.c b/src/misc/objects.c index 5c53b20c24..070193dd40 100644 --- a/src/misc/objects.c +++ b/src/misc/objects.c @@ -173,6 +173,7 @@ void *__vlc_custom_create( vlc_object_t *p_this, size_t i_size, vlc_mutex_init( &p_priv->lock ); vlc_cond_init( &p_priv->wait ); vlc_mutex_init( &p_priv->var_lock ); + vlc_cond_init( &p_priv->var_wait ); vlc_spin_init( &p_priv->spin ); p_priv->pipes[0] = p_priv->pipes[1] = -1; @@ -296,6 +297,7 @@ static void vlc_object_destroy( vlc_object_t *p_this ) } free( p_priv->p_vars ); + vlc_cond_destroy( &p_priv->var_wait ); vlc_mutex_destroy( &p_priv->var_lock ); free( p_this->psz_header ); diff --git a/src/misc/variables.c b/src/misc/variables.c index 0d647a674e..dc0e8e6fef 100644 --- a/src/misc/variables.c +++ b/src/misc/variables.c @@ -762,6 +762,7 @@ int var_SetChecked( vlc_object_t *p_this, const char *psz_name, p_var = &p_priv->p_vars[i_var]; p_var->b_incallback = false; + vlc_cond_broadcast( &p_priv->var_wait ); } /* Free data if needed */ @@ -978,6 +979,7 @@ int __var_TriggerCallback( vlc_object_t *p_this, const char *psz_name ) p_var = &p_priv->p_vars[i_var]; p_var->b_incallback = false; + vlc_cond_broadcast( &p_priv->var_wait ); } vlc_mutex_unlock( &p_priv->var_lock ); @@ -1134,18 +1136,19 @@ cleanup: /* Following functions are local */ /***************************************************************************** - * GetUnused: find an unused variable from its name + * GetUnused: find an unused (not in callback) variable from its name ***************************************************************************** * We do i_tries tries before giving up, just in case the variable is being * modified and called from a callback. *****************************************************************************/ static int GetUnused( vlc_object_t *p_this, const char *psz_name ) { - int i_var, i_tries = 0; vlc_object_internals_t *p_priv = vlc_internals( p_this ); while( true ) { + int i_var; + i_var = Lookup( p_priv->p_vars, p_priv->i_vars, psz_name ); if( i_var < 0 ) { @@ -1157,15 +1160,9 @@ static int GetUnused( vlc_object_t *p_this, const char *psz_name ) return i_var; } - if( i_tries++ > 100 ) - { - msg_Err( p_this, "caught in a callback deadlock? ('%s')", psz_name ); - return VLC_ETIMEOUT; - } - - vlc_mutex_unlock( &p_priv->var_lock ); - msleep( THREAD_SLEEP ); - vlc_mutex_lock( &p_priv->var_lock ); + mutex_cleanup_push( &p_priv->var_lock ); + vlc_cond_wait( &p_priv->var_wait, &p_priv->var_lock ); + vlc_cleanup_pop( ); } }