From: Laurent Aimar Date: Thu, 5 Feb 2009 22:22:01 +0000 (+0100) Subject: Fixed aout visual vout recycling. X-Git-Tag: 1.0.0-pre1~850 X-Git-Url: https://git.sesse.net/?a=commitdiff_plain;h=00b6b76217c39d6a7abfa0ada531b743b2aa594a;p=vlc Fixed aout visual vout recycling. It closes #2471 It changes a bit the public API but cannot(?) be avoided. --- diff --git a/include/vlc_aout.h b/include/vlc_aout.h index 98a2a58474..e721fa217d 100644 --- a/include/vlc_aout.h +++ b/include/vlc_aout.h @@ -226,7 +226,7 @@ struct aout_fifo_t typedef struct { vout_thread_t *(*pf_request_vout)( void *, - vout_thread_t *, video_format_t * ); + vout_thread_t *, video_format_t *, bool b_recycle ); void *p_private; } aout_request_vout_t; @@ -314,6 +314,7 @@ struct aout_input_t mtime_t i_pause_date; /* */ + bool b_recycle_vout; aout_request_vout_t request_vout; }; diff --git a/src/audio_output/filters.c b/src/audio_output/filters.c index 4cd202b32d..d29352f901 100644 --- a/src/audio_output/filters.c +++ b/src/audio_output/filters.c @@ -383,6 +383,7 @@ vout_thread_t *aout_filter_RequestVout( aout_filter_t *p_filter, { if( !p_filter->request_vout.pf_request_vout ) return NULL; - return p_filter->request_vout.pf_request_vout( p_filter->request_vout.p_private, p_vout, p_fmt ); + return p_filter->request_vout.pf_request_vout( p_filter->request_vout.p_private, + p_vout, p_fmt, true ); } diff --git a/src/audio_output/input.c b/src/audio_output/input.c index c2dd544e4f..b4d9c48546 100644 --- a/src/audio_output/input.c +++ b/src/audio_output/input.c @@ -63,7 +63,10 @@ static int ReplayGainCallback( vlc_object_t *, char const *, static void ReplayGainSelect( aout_instance_t *, aout_input_t * ); static vout_thread_t *RequestVout( void *, - vout_thread_t *, video_format_t * ); + vout_thread_t *, video_format_t *, bool ); +static vout_thread_t *RequestVoutFromFilter( void *, + vout_thread_t *, video_format_t *, bool ); + /***************************************************************************** * aout_InputNew : allocate a new input and rework the filter pipeline *****************************************************************************/ @@ -232,9 +235,10 @@ int aout_InputNew( aout_instance_t * p_aout, aout_input_t * p_input, const aout_ psz_filters = var_GetString( p_aout, "audio-filter" ); psz_visual = var_GetString( p_aout, "audio-visual"); - psz_scaletempo = var_GetBool( p_aout, "audio-time-stretch" ) ? strdup( "scaletempo" ) : NULL; + p_input->b_recycle_vout = psz_visual && *psz_visual; + /* parse user filter lists */ for( i_visual = 0; i_visual < 3 && !AOUT_FMT_NON_LINEAR(&chain_output_format); i_visual++ ) { @@ -282,7 +286,9 @@ int aout_InputNew( aout_instance_t * p_aout, aout_input_t * p_input, const aout_ vlc_object_attach( p_filter , p_aout ); - p_filter->request_vout = p_input->request_vout; + p_filter->request_vout.pf_request_vout = RequestVoutFromFilter; + p_filter->request_vout.p_private = p_input; + p_filter->p_owner = malloc( sizeof(*p_filter->p_owner) ); p_filter->p_owner->p_aout = p_aout; p_filter->p_owner->p_input = p_input; @@ -479,7 +485,16 @@ int aout_InputNew( aout_instance_t * p_aout, aout_input_t * p_input, const aout_ int aout_InputDelete( aout_instance_t * p_aout, aout_input_t * p_input ) { AOUT_ASSERT_MIXER_LOCKED; - if ( p_input->b_error ) return 0; + if ( p_input->b_error ) + return 0; + + /* XXX We need to update b_recycle_vout before calling aout_FiltersDestroyPipeline. + * FIXME They can be a race condition if audio-visual is updated between + * aout_InputDelete and aout_InputNew. + */ + char *psz_visual = var_GetString( p_aout, "audio-visual"); + p_input->b_recycle_vout = psz_visual && *psz_visual; + free( psz_visual ); aout_FiltersDestroyPipeline( p_aout, p_input->pp_filters, p_input->i_nb_filters ); @@ -803,12 +818,23 @@ static void inputResamplingStop( aout_input_t *p_input ) } static vout_thread_t *RequestVout( void *p_private, - vout_thread_t *p_vout, video_format_t *p_fmt ) + vout_thread_t *p_vout, video_format_t *p_fmt, bool b_recycle ) { aout_instance_t *p_aout = p_private; + VLC_UNUSED(b_recycle); return vout_Request( p_aout, p_vout, p_fmt ); } +static vout_thread_t *RequestVoutFromFilter( void *p_private, + vout_thread_t *p_vout, video_format_t *p_fmt, bool b_recycle ) +{ + aout_input_t *p_input = p_private; + aout_request_vout_t *p_request = &p_input->request_vout; + + return p_request->pf_request_vout( p_request->p_private, + p_vout, p_fmt, p_input->b_recycle_vout && b_recycle ); +} + static int ChangeFiltersString( aout_instance_t * p_aout, const char* psz_variable, const char *psz_name, bool b_add ) { diff --git a/src/input/decoder.c b/src/input/decoder.c index 4a5eeff1d9..bcae5fe91f 100644 --- a/src/input/decoder.c +++ b/src/input/decoder.c @@ -2105,12 +2105,17 @@ static void DecoderUpdateFormatLocked( decoder_t *p_dec ) p_dec->p_description = NULL; } static vout_thread_t *aout_request_vout( void *p_private, - vout_thread_t *p_vout, video_format_t *p_fmt ) + vout_thread_t *p_vout, video_format_t *p_fmt, bool b_recyle ) { decoder_t *p_dec = p_private; - - p_vout = input_ressource_RequestVout( p_dec->p_owner->p_input->p->p_ressource, p_vout, p_fmt ); - input_SendEventVout( p_dec->p_owner->p_input ); + input_thread_t *p_input = p_dec->p_owner->p_input; + + p_vout = input_ressource_RequestVout( p_input->p->p_ressource, p_vout, p_fmt ); + /* TODO it would be better to give b_recyle to input_ressource_RequestVout + * as here we are not sure of which vout we destroy */ + if( !b_recyle ) + input_ressource_TerminateVout( p_input->p->p_ressource ); + input_SendEventVout( p_input ); return p_vout; }