[vlc-devel] [RFC PATCH 8/9] decoder: reload module if aout device changes
Thomas Guillem
thomas at gllm.fr
Sat Jul 9 12:20:16 CEST 2016
In order to be able to change from PCM to SPDIF and from SPDIF to PCM.
There is a Time of check to time of use issue here. DecoderPlayAudio() can
still be called when the decoder is configured with a wrong audio device. This
will result in a loss of few audio blocks. This is hard to avoid when the user
choose to change audio devices.
---
src/input/decoder.c | 27 +++++++++++++++++++++++++++
1 file changed, 27 insertions(+)
diff --git a/src/input/decoder.c b/src/input/decoder.c
index de03dd6..a437930 100644
--- a/src/input/decoder.c
+++ b/src/input/decoder.c
@@ -82,6 +82,7 @@ struct decoder_owner_sys_t
/* */
bool b_fmt_description;
vlc_meta_t *p_description;
+ atomic_bool aout_device_changed;
/* fifo */
block_fifo_t *p_fifo;
@@ -270,6 +271,20 @@ static vout_thread_t *aout_request_vout( void *p_private,
return p_vout;
}
+static int aout_device_changed( vlc_object_t *p_obj, const char *p_var,
+ vlc_value_t prev, vlc_value_t cur, void *p_data)
+{
+ (void) p_obj; (void) p_var;
+ decoder_t *p_dec = p_data;
+ decoder_owner_sys_t *p_owner = p_dec->p_owner;
+
+ if( prev.psz_string == NULL || cur.psz_string == NULL
+ || strcmp( prev.psz_string, cur.psz_string ) != 0 )
+ atomic_store( &p_owner->aout_device_changed, true );
+
+ return VLC_SUCCESS;
+}
+
static int aout_update_format( decoder_t *p_dec )
{
decoder_owner_sys_t *p_owner = p_dec->p_owner;
@@ -283,6 +298,7 @@ static int aout_update_format( decoder_t *p_dec )
vlc_mutex_lock( &p_owner->lock );
p_owner->p_aout = NULL;
vlc_mutex_unlock( &p_owner->lock );
+ var_DelCallback( p_aout, "device", aout_device_changed, p_dec );
aout_DecDelete( p_aout );
input_resource_PutAout( p_owner->p_resource, p_aout );
@@ -328,6 +344,8 @@ static int aout_update_format( decoder_t *p_dec )
input_resource_PutAout( p_owner->p_resource, p_aout );
p_aout = NULL;
}
+ else
+ var_AddCallback( p_aout, "device", aout_device_changed, p_dec );
}
vlc_mutex_lock( &p_owner->lock );
@@ -1418,6 +1436,14 @@ static void DecoderProcess( decoder_t *p_dec, block_t *p_block )
if( p_dec->b_error )
goto error;
+ if( atomic_exchange( &p_owner->aout_device_changed, false ) )
+ {
+ msg_Warn( p_dec, "Restarting decoder since the audio device changed" );
+
+ if( ReloadDecoder( p_dec, NULL, &p_dec->fmt_in ) != VLC_SUCCESS )
+ goto error;
+ }
+
if( p_block )
{
if( p_block->i_buffer <= 0 )
@@ -1668,6 +1694,7 @@ static decoder_t * CreateDecoder( vlc_object_t *p_parent,
p_owner->flushing = false;
p_owner->b_draining = false;
atomic_init( &p_owner->drained, false );
+ atomic_init( &p_owner->aout_device_changed, false );
p_owner->b_idle = false;
es_format_Init( &p_owner->fmt, UNKNOWN_ES, 0 );
--
2.8.1
More information about the vlc-devel
mailing list