1 /*****************************************************************************
2 * decoder.c: Functions for the management of decoders
3 *****************************************************************************
4 * Copyright (C) 1999-2004 VLC authors and VideoLAN
7 * Authors: Christophe Massiot <massiot@via.ecp.fr>
8 * Gildas Bazin <gbazin@videolan.org>
9 * Laurent Aimar <fenrir@via.ecp.fr>
11 * This program is free software; you can redistribute it and/or modify it
12 * under the terms of the GNU Lesser General Public License as published by
13 * the Free Software Foundation; either version 2.1 of the License, or
14 * (at your option) any later version.
16 * This program is distributed in the hope that it will be useful,
17 * but WITHOUT ANY WARRANTY; without even the implied warranty of
18 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
19 * GNU Lesser General Public License for more details.
21 * You should have received a copy of the GNU Lesser General Public License
22 * along with this program; if not, write to the Free Software Foundation,
23 * Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA.
24 *****************************************************************************/
26 /*****************************************************************************
28 *****************************************************************************/
34 #include <vlc_common.h>
36 #include <vlc_atomic.h>
37 #include <vlc_block.h>
41 #include <vlc_codec.h>
44 #include <vlc_dialog.h>
45 #include <vlc_modules.h>
47 #include "audio_output/aout_internal.h"
48 #include "stream_output/stream_output.h"
49 #include "input_internal.h"
55 #include "../video_output/vout_control.h"
57 struct decoder_owner_sys_t
59 input_thread_t
*p_input
;
60 input_resource_t
*p_resource
;
61 input_clock_t
*p_clock
;
64 vout_thread_t
*p_spu_vout
;
68 sout_instance_t
*p_sout
;
69 sout_packetizer_input_t
*p_sout_input
;
73 /* Some decoders require already packetized data (ie. not truncated) */
74 decoder_t
*p_packetizer
;
77 /* Current format in use by the output */
81 bool b_fmt_description
;
82 vlc_meta_t
*p_description
;
87 /* Lock for communication with decoder thread */
89 vlc_cond_t wait_request
;
90 vlc_cond_t wait_acknowledge
;
91 vlc_cond_t wait_fifo
; /* TODO: merge with wait_acknowledge */
92 vlc_cond_t wait_timed
;
94 /* -- These variables need locking on write(only) -- */
95 audio_output_t
*p_aout
;
97 vout_thread_t
*p_vout
;
99 /* -- Theses variables need locking on read *and* write -- */
101 int64_t i_preroll_end
;
104 unsigned frames_countdown
;
123 decoder_t
*pp_decoder
[4];
130 /* Pictures which are DECODER_BOGUS_VIDEO_DELAY or more in advance probably have
131 * a bogus PTS and won't be displayed */
132 #define DECODER_BOGUS_VIDEO_DELAY ((mtime_t)(DEFAULT_PTS_DELAY * 30))
135 #define DECODER_SPU_VOUT_WAIT_DURATION ((int)(0.200*CLOCK_FREQ))
138 * Load a decoder module
140 static int LoadDecoder( decoder_t
*p_dec
, bool b_packetizer
,
141 const es_format_t
*restrict p_fmt
)
143 p_dec
->b_frame_drop_allowed
= true;
144 p_dec
->i_extra_picture_buffers
= 0;
146 p_dec
->pf_decode_audio
= NULL
;
147 p_dec
->pf_decode_video
= NULL
;
148 p_dec
->pf_decode_sub
= NULL
;
149 p_dec
->pf_get_cc
= NULL
;
150 p_dec
->pf_packetize
= NULL
;
151 p_dec
->pf_flush
= NULL
;
153 es_format_Copy( &p_dec
->fmt_in
, p_fmt
);
154 es_format_Init( &p_dec
->fmt_out
, UNKNOWN_ES
, 0 );
156 /* Find a suitable decoder/packetizer module */
158 p_dec
->p_module
= module_need( p_dec
, "decoder", "$codec", false );
160 p_dec
->p_module
= module_need( p_dec
, "packetizer", "$packetizer", false );
162 if( !p_dec
->p_module
)
164 es_format_Clean( &p_dec
->fmt_in
);
172 * Unload a decoder module
174 static void UnloadDecoder( decoder_t
*p_dec
)
176 if( p_dec
->p_module
)
178 module_unneed( p_dec
, p_dec
->p_module
);
179 p_dec
->p_module
= NULL
;
182 if( p_dec
->p_description
)
184 vlc_meta_Delete( p_dec
->p_description
);
185 p_dec
->p_description
= NULL
;
188 es_format_Clean( &p_dec
->fmt_in
);
189 es_format_Clean( &p_dec
->fmt_out
);
190 p_dec
->b_error
= false;
193 static void DecoderUpdateFormatLocked( decoder_t
*p_dec
)
195 decoder_owner_sys_t
*p_owner
= p_dec
->p_owner
;
197 vlc_assert_locked( &p_owner
->lock
);
199 es_format_Clean( &p_owner
->fmt
);
200 es_format_Copy( &p_owner
->fmt
, &p_dec
->fmt_out
);
202 /* Move p_description */
203 if( p_dec
->p_description
!= NULL
)
205 if( p_owner
->p_description
!= NULL
)
206 vlc_meta_Delete( p_owner
->p_description
);
207 p_owner
->p_description
= p_dec
->p_description
;
208 p_dec
->p_description
= NULL
;
211 p_owner
->b_fmt_description
= true;
214 /*****************************************************************************
215 * Buffers allocation callbacks for the decoders
216 *****************************************************************************/
217 static vout_thread_t
*aout_request_vout( void *p_private
,
218 vout_thread_t
*p_vout
, video_format_t
*p_fmt
, bool b_recyle
)
220 decoder_t
*p_dec
= p_private
;
221 decoder_owner_sys_t
*p_owner
= p_dec
->p_owner
;
222 input_thread_t
*p_input
= p_owner
->p_input
;
224 p_vout
= input_resource_RequestVout( p_owner
->p_resource
, p_vout
, p_fmt
, 1,
226 if( p_input
!= NULL
)
227 input_SendEventVout( p_input
);
232 static int aout_update_format( decoder_t
*p_dec
)
234 decoder_owner_sys_t
*p_owner
= p_dec
->p_owner
;
237 && !AOUT_FMTS_IDENTICAL(&p_dec
->fmt_out
.audio
, &p_owner
->fmt
.audio
) )
239 audio_output_t
*p_aout
= p_owner
->p_aout
;
241 /* Parameters changed, restart the aout */
242 vlc_mutex_lock( &p_owner
->lock
);
243 p_owner
->p_aout
= NULL
;
244 vlc_mutex_unlock( &p_owner
->lock
);
245 aout_DecDelete( p_aout
);
247 input_resource_PutAout( p_owner
->p_resource
, p_aout
);
250 if( p_owner
->p_aout
== NULL
)
252 p_dec
->fmt_out
.audio
.i_format
= p_dec
->fmt_out
.i_codec
;
254 audio_sample_format_t format
= p_dec
->fmt_out
.audio
;
255 aout_FormatPrepare( &format
);
257 const int i_force_dolby
= var_InheritInteger( p_dec
, "force-dolby-surround" );
259 (format
.i_original_channels
&AOUT_CHAN_PHYSMASK
) ==
260 (AOUT_CHAN_LEFT
|AOUT_CHAN_RIGHT
) )
262 if( i_force_dolby
== 1 )
264 format
.i_original_channels
= format
.i_original_channels
|
265 AOUT_CHAN_DOLBYSTEREO
;
267 else /* i_force_dolby == 2 */
269 format
.i_original_channels
= format
.i_original_channels
&
270 ~AOUT_CHAN_DOLBYSTEREO
;
274 aout_request_vout_t request_vout
= {
275 .pf_request_vout
= aout_request_vout
,
278 audio_output_t
*p_aout
;
280 p_aout
= input_resource_GetAout( p_owner
->p_resource
);
283 if( aout_DecNew( p_aout
, &format
,
284 &p_dec
->fmt_out
.audio_replay_gain
,
287 input_resource_PutAout( p_owner
->p_resource
, p_aout
);
292 vlc_mutex_lock( &p_owner
->lock
);
293 p_owner
->p_aout
= p_aout
;
295 DecoderUpdateFormatLocked( p_dec
);
296 aout_FormatPrepare( &p_owner
->fmt
.audio
);
297 vlc_mutex_unlock( &p_owner
->lock
);
299 if( p_owner
->p_input
!= NULL
)
300 input_SendEventAout( p_owner
->p_input
);
304 msg_Err( p_dec
, "failed to create audio output" );
305 p_dec
->b_error
= true;
309 p_dec
->fmt_out
.audio
.i_bytes_per_frame
=
310 p_owner
->fmt
.audio
.i_bytes_per_frame
;
311 p_dec
->fmt_out
.audio
.i_frame_length
=
312 p_owner
->fmt
.audio
.i_frame_length
;
317 static int vout_update_format( decoder_t
*p_dec
)
319 decoder_owner_sys_t
*p_owner
= p_dec
->p_owner
;
321 if( p_owner
->p_vout
== NULL
322 || p_dec
->fmt_out
.video
.i_width
!= p_owner
->fmt
.video
.i_width
323 || p_dec
->fmt_out
.video
.i_height
!= p_owner
->fmt
.video
.i_height
324 || p_dec
->fmt_out
.video
.i_visible_width
!= p_owner
->fmt
.video
.i_visible_width
325 || p_dec
->fmt_out
.video
.i_visible_height
!= p_owner
->fmt
.video
.i_visible_height
326 || p_dec
->fmt_out
.video
.i_x_offset
!= p_owner
->fmt
.video
.i_x_offset
327 || p_dec
->fmt_out
.video
.i_y_offset
!= p_owner
->fmt
.video
.i_y_offset
328 || p_dec
->fmt_out
.i_codec
!= p_owner
->fmt
.video
.i_chroma
329 || (int64_t)p_dec
->fmt_out
.video
.i_sar_num
* p_owner
->fmt
.video
.i_sar_den
!=
330 (int64_t)p_dec
->fmt_out
.video
.i_sar_den
* p_owner
->fmt
.video
.i_sar_num
||
331 p_dec
->fmt_out
.video
.orientation
!= p_owner
->fmt
.video
.orientation
)
333 vout_thread_t
*p_vout
;
335 if( !p_dec
->fmt_out
.video
.i_width
||
336 !p_dec
->fmt_out
.video
.i_height
)
338 /* Can't create a new vout without display size */
342 video_format_t fmt
= p_dec
->fmt_out
.video
;
343 fmt
.i_chroma
= p_dec
->fmt_out
.i_codec
;
345 if( vlc_fourcc_IsYUV( fmt
.i_chroma
) )
347 const vlc_chroma_description_t
*dsc
= vlc_fourcc_GetChromaDescription( fmt
.i_chroma
);
348 for( unsigned int i
= 0; dsc
&& i
< dsc
->plane_count
; i
++ )
350 while( fmt
.i_width
% dsc
->p
[i
].w
.den
)
352 while( fmt
.i_height
% dsc
->p
[i
].h
.den
)
357 if( !fmt
.i_visible_width
|| !fmt
.i_visible_height
)
359 if( p_dec
->fmt_in
.video
.i_visible_width
&&
360 p_dec
->fmt_in
.video
.i_visible_height
)
362 fmt
.i_visible_width
= p_dec
->fmt_in
.video
.i_visible_width
;
363 fmt
.i_visible_height
= p_dec
->fmt_in
.video
.i_visible_height
;
364 fmt
.i_x_offset
= p_dec
->fmt_in
.video
.i_x_offset
;
365 fmt
.i_y_offset
= p_dec
->fmt_in
.video
.i_y_offset
;
369 fmt
.i_visible_width
= fmt
.i_width
;
370 fmt
.i_visible_height
= fmt
.i_height
;
376 if( fmt
.i_visible_height
== 1088 &&
377 var_CreateGetBool( p_dec
, "hdtv-fix" ) )
379 fmt
.i_visible_height
= 1080;
380 if( !(fmt
.i_sar_num
% 136))
382 fmt
.i_sar_num
*= 135;
383 fmt
.i_sar_den
*= 136;
385 msg_Warn( p_dec
, "Fixing broken HDTV stream (display_height=1088)");
388 if( !fmt
.i_sar_num
|| !fmt
.i_sar_den
)
394 vlc_ureduce( &fmt
.i_sar_num
, &fmt
.i_sar_den
,
395 fmt
.i_sar_num
, fmt
.i_sar_den
, 50000 );
397 vlc_mutex_lock( &p_owner
->lock
);
399 p_vout
= p_owner
->p_vout
;
400 p_owner
->p_vout
= NULL
;
401 vlc_mutex_unlock( &p_owner
->lock
);
404 switch( p_dec
->fmt_in
.i_codec
)
408 case VLC_CODEC_DIRAC
: /* FIXME valid ? */
421 p_vout
= input_resource_RequestVout( p_owner
->p_resource
,
424 p_dec
->i_extra_picture_buffers
+ 1,
426 vlc_mutex_lock( &p_owner
->lock
);
427 p_owner
->p_vout
= p_vout
;
429 DecoderUpdateFormatLocked( p_dec
);
430 p_owner
->fmt
.video
.i_chroma
= p_dec
->fmt_out
.i_codec
;
431 vlc_mutex_unlock( &p_owner
->lock
);
433 if( p_owner
->p_input
!= NULL
)
434 input_SendEventVout( p_owner
->p_input
);
437 msg_Err( p_dec
, "failed to create video output" );
444 static picture_t
*vout_new_buffer( decoder_t
*p_dec
)
446 decoder_owner_sys_t
*p_owner
= p_dec
->p_owner
;
448 return vout_GetPicture( p_owner
->p_vout
);
451 static subpicture_t
*spu_new_buffer( decoder_t
*p_dec
,
452 const subpicture_updater_t
*p_updater
)
454 decoder_owner_sys_t
*p_owner
= p_dec
->p_owner
;
455 vout_thread_t
*p_vout
= NULL
;
456 subpicture_t
*p_subpic
;
459 while( i_attempts
-- )
464 p_vout
= input_resource_HoldVout( p_owner
->p_resource
);
468 msleep( DECODER_SPU_VOUT_WAIT_DURATION
);
473 msg_Warn( p_dec
, "no vout found, dropping subpicture" );
477 if( p_owner
->p_spu_vout
!= p_vout
)
479 p_owner
->i_spu_channel
= vout_RegisterSubpictureChannel( p_vout
);
480 p_owner
->i_spu_order
= 0;
481 p_owner
->p_spu_vout
= p_vout
;
484 p_subpic
= subpicture_New( p_updater
);
487 p_subpic
->i_channel
= p_owner
->i_spu_channel
;
488 p_subpic
->i_order
= p_owner
->i_spu_order
++;
489 p_subpic
->b_subtitle
= true;
492 vlc_object_release( p_vout
);
497 static int DecoderGetInputAttachments( decoder_t
*p_dec
,
498 input_attachment_t
***ppp_attachment
,
501 input_thread_t
*p_input
= p_dec
->p_owner
->p_input
;
503 if( unlikely(p_input
== NULL
) )
505 return input_Control( p_input
, INPUT_GET_ATTACHMENTS
,
506 ppp_attachment
, pi_attachment
);
509 static mtime_t
DecoderGetDisplayDate( decoder_t
*p_dec
, mtime_t i_ts
)
511 decoder_owner_sys_t
*p_owner
= p_dec
->p_owner
;
513 vlc_mutex_lock( &p_owner
->lock
);
514 if( p_owner
->b_waiting
)
515 i_ts
= VLC_TS_INVALID
;
516 vlc_mutex_unlock( &p_owner
->lock
);
518 if( !p_owner
->p_clock
|| i_ts
<= VLC_TS_INVALID
)
521 if( input_clock_ConvertTS( VLC_OBJECT(p_dec
), p_owner
->p_clock
, NULL
, &i_ts
, NULL
, INT64_MAX
) ) {
522 msg_Err(p_dec
, "Could not get display date for timestamp %"PRId64
"", i_ts
);
523 return VLC_TS_INVALID
;
529 static int DecoderGetDisplayRate( decoder_t
*p_dec
)
531 decoder_owner_sys_t
*p_owner
= p_dec
->p_owner
;
533 if( !p_owner
->p_clock
)
534 return INPUT_RATE_DEFAULT
;
535 return input_clock_GetRate( p_owner
->p_clock
);
538 /*****************************************************************************
540 *****************************************************************************/
541 block_t
*decoder_NewAudioBuffer( decoder_t
*dec
, int samples
)
543 if( decoder_UpdateAudioFormat( dec
) )
546 size_t length
= samples
* dec
->fmt_out
.audio
.i_bytes_per_frame
547 / dec
->fmt_out
.audio
.i_frame_length
;
548 block_t
*block
= block_Alloc( length
);
549 if( likely(block
!= NULL
) )
551 block
->i_nb_samples
= samples
;
552 block
->i_pts
= block
->i_length
= 0;
557 subpicture_t
*decoder_NewSubpicture( decoder_t
*p_decoder
,
558 const subpicture_updater_t
*p_dyn
)
560 subpicture_t
*p_subpicture
= p_decoder
->pf_spu_buffer_new( p_decoder
, p_dyn
);
562 msg_Warn( p_decoder
, "can't get output subpicture" );
566 /* decoder_GetInputAttachments:
568 int decoder_GetInputAttachments( decoder_t
*p_dec
,
569 input_attachment_t
***ppp_attachment
,
572 if( !p_dec
->pf_get_attachments
)
575 return p_dec
->pf_get_attachments( p_dec
, ppp_attachment
, pi_attachment
);
577 /* decoder_GetDisplayDate:
579 mtime_t
decoder_GetDisplayDate( decoder_t
*p_dec
, mtime_t i_ts
)
581 if( !p_dec
->pf_get_display_date
)
582 return VLC_TS_INVALID
;
584 return p_dec
->pf_get_display_date( p_dec
, i_ts
);
586 /* decoder_GetDisplayRate:
588 int decoder_GetDisplayRate( decoder_t
*p_dec
)
590 if( !p_dec
->pf_get_display_rate
)
591 return INPUT_RATE_DEFAULT
;
593 return p_dec
->pf_get_display_rate( p_dec
);
596 void decoder_AbortPictures( decoder_t
*p_dec
, bool b_abort
)
598 decoder_owner_sys_t
*p_owner
= p_dec
->p_owner
;
600 vlc_mutex_lock( &p_owner
->lock
);
601 if( p_owner
->p_vout
!= NULL
)
602 vout_Cancel( p_owner
->p_vout
, b_abort
);
603 vlc_mutex_unlock( &p_owner
->lock
);
606 static void DecoderWaitUnblock( decoder_t
*p_dec
)
608 decoder_owner_sys_t
*p_owner
= p_dec
->p_owner
;
610 vlc_assert_locked( &p_owner
->lock
);
614 if( !p_owner
->b_waiting
|| !p_owner
->b_has_data
)
616 vlc_cond_wait( &p_owner
->wait_request
, &p_owner
->lock
);
620 /* DecoderTimedWait: Interruptible wait
621 * Returns VLC_SUCCESS if wait was not interrupted, and VLC_EGENERIC otherwise */
622 static int DecoderTimedWait( decoder_t
*p_dec
, mtime_t deadline
)
624 decoder_owner_sys_t
*p_owner
= p_dec
->p_owner
;
626 if (deadline
- mdate() <= 0)
629 vlc_fifo_Lock( p_owner
->p_fifo
);
630 while( !p_owner
->flushing
631 && vlc_fifo_TimedWaitCond( p_owner
->p_fifo
, &p_owner
->wait_timed
,
633 int ret
= p_owner
->flushing
? VLC_EGENERIC
: VLC_SUCCESS
;
634 vlc_fifo_Unlock( p_owner
->p_fifo
);
638 static inline void DecoderUpdatePreroll( int64_t *pi_preroll
, const block_t
*p
)
640 if( p
->i_flags
& (BLOCK_FLAG_PREROLL
|BLOCK_FLAG_DISCONTINUITY
) )
641 *pi_preroll
= INT64_MAX
;
642 else if( p
->i_dts
> VLC_TS_INVALID
)
643 *pi_preroll
= __MIN( *pi_preroll
, p
->i_dts
);
644 else if( p
->i_pts
> VLC_TS_INVALID
)
645 *pi_preroll
= __MIN( *pi_preroll
, p
->i_pts
);
648 static void DecoderFixTs( decoder_t
*p_dec
, mtime_t
*pi_ts0
, mtime_t
*pi_ts1
,
649 mtime_t
*pi_duration
, int *pi_rate
, mtime_t i_ts_bound
)
651 decoder_owner_sys_t
*p_owner
= p_dec
->p_owner
;
652 input_clock_t
*p_clock
= p_owner
->p_clock
;
654 vlc_assert_locked( &p_owner
->lock
);
656 const mtime_t i_es_delay
= p_owner
->i_ts_delay
;
661 const bool b_ephemere
= pi_ts1
&& *pi_ts0
== *pi_ts1
;
664 if( *pi_ts0
> VLC_TS_INVALID
)
666 *pi_ts0
+= i_es_delay
;
667 if( pi_ts1
&& *pi_ts1
> VLC_TS_INVALID
)
668 *pi_ts1
+= i_es_delay
;
669 if( i_ts_bound
!= INT64_MAX
)
670 i_ts_bound
+= i_es_delay
;
671 if( input_clock_ConvertTS( VLC_OBJECT(p_dec
), p_clock
, &i_rate
, pi_ts0
, pi_ts1
, i_ts_bound
) ) {
673 msg_Err(p_dec
, "Could not convert timestamps %"PRId64
674 ", %"PRId64
"", *pi_ts0
, *pi_ts1
);
676 msg_Err(p_dec
, "Could not convert timestamp %"PRId64
, *pi_ts0
);
677 *pi_ts0
= VLC_TS_INVALID
;
682 i_rate
= input_clock_GetRate( p_clock
);
685 /* Do not create ephemere data because of rounding errors */
686 if( !b_ephemere
&& pi_ts1
&& *pi_ts0
== *pi_ts1
)
690 *pi_duration
= ( *pi_duration
* i_rate
+ INPUT_RATE_DEFAULT
-1 )
691 / INPUT_RATE_DEFAULT
;
698 static int DecoderPlaySout( decoder_t
*p_dec
, block_t
*p_sout_block
)
700 decoder_owner_sys_t
*p_owner
= p_dec
->p_owner
;
702 assert( p_owner
->p_clock
);
703 assert( !p_sout_block
->p_next
);
705 vlc_mutex_lock( &p_owner
->lock
);
707 if( p_owner
->b_waiting
)
709 p_owner
->b_has_data
= true;
710 vlc_cond_signal( &p_owner
->wait_acknowledge
);
713 DecoderWaitUnblock( p_dec
);
714 DecoderFixTs( p_dec
, &p_sout_block
->i_dts
, &p_sout_block
->i_pts
,
715 &p_sout_block
->i_length
, NULL
, INT64_MAX
);
717 vlc_mutex_unlock( &p_owner
->lock
);
719 /* FIXME --VLC_TS_INVALID inspect stream_output*/
720 return sout_InputSendBuffer( p_owner
->p_sout_input
, p_sout_block
);
723 /* This function process a block for sout
725 static void DecoderProcessSout( decoder_t
*p_dec
, block_t
*p_block
)
727 decoder_owner_sys_t
*p_owner
= p_dec
->p_owner
;
728 block_t
*p_sout_block
;
729 block_t
**pp_block
= p_block
? &p_block
: NULL
;
731 while( ( p_sout_block
=
732 p_dec
->pf_packetize( p_dec
, pp_block
) ) )
734 if( p_owner
->p_sout_input
== NULL
)
736 vlc_mutex_lock( &p_owner
->lock
);
737 DecoderUpdateFormatLocked( p_dec
);
738 vlc_mutex_unlock( &p_owner
->lock
);
740 p_owner
->fmt
.i_group
= p_dec
->fmt_in
.i_group
;
741 p_owner
->fmt
.i_id
= p_dec
->fmt_in
.i_id
;
742 if( p_dec
->fmt_in
.psz_language
)
744 free( p_owner
->fmt
.psz_language
);
745 p_owner
->fmt
.psz_language
=
746 strdup( p_dec
->fmt_in
.psz_language
);
749 p_owner
->p_sout_input
=
750 sout_InputNew( p_owner
->p_sout
, &p_owner
->fmt
);
752 if( p_owner
->p_sout_input
== NULL
)
754 msg_Err( p_dec
, "cannot create packetizer output (%4.4s)",
755 (char *)&p_owner
->fmt
.i_codec
);
756 p_dec
->b_error
= true;
758 block_ChainRelease(p_sout_block
);
763 while( p_sout_block
)
765 block_t
*p_next
= p_sout_block
->p_next
;
767 p_sout_block
->p_next
= NULL
;
769 if( DecoderPlaySout( p_dec
, p_sout_block
) == VLC_EGENERIC
)
771 msg_Err( p_dec
, "cannot continue streaming due to errors" );
773 p_dec
->b_error
= true;
776 block_ChainRelease( p_next
);
780 p_sout_block
= p_next
;
786 static void DecoderGetCc( decoder_t
*p_dec
, decoder_t
*p_dec_cc
)
788 decoder_owner_sys_t
*p_owner
= p_dec
->p_owner
;
791 bool b_processed
= false;
795 assert( p_dec_cc
->pf_get_cc
!= NULL
);
797 /* Do not try retreiving CC if not wanted (sout) or cannot be retreived */
798 if( !p_owner
->cc
.b_supported
)
801 p_cc
= p_dec_cc
->pf_get_cc( p_dec_cc
, pb_present
);
805 vlc_mutex_lock( &p_owner
->lock
);
806 for( i
= 0, i_cc_decoder
= 0; i
< 4; i
++ )
808 p_owner
->cc
.pb_present
[i
] |= pb_present
[i
];
809 if( p_owner
->cc
.pp_decoder
[i
] )
813 for( i
= 0; i
< 4; i
++ )
815 if( !p_owner
->cc
.pp_decoder
[i
] )
818 block_FifoPut( p_owner
->cc
.pp_decoder
[i
]->p_owner
->p_fifo
,
819 (i_cc_decoder
> 1) ? block_Duplicate(p_cc
) : p_cc
);
824 vlc_mutex_unlock( &p_owner
->lock
);
827 block_Release( p_cc
);
830 static void DecoderPlayVideo( decoder_t
*p_dec
, picture_t
*p_picture
,
831 int *pi_played_sum
, int *pi_lost_sum
)
833 decoder_owner_sys_t
*p_owner
= p_dec
->p_owner
;
834 vout_thread_t
*p_vout
= p_owner
->p_vout
;
836 if( p_picture
->date
<= VLC_TS_INVALID
)
838 msg_Warn( p_dec
, "non-dated video buffer received" );
840 picture_Release( p_picture
);
845 vlc_mutex_lock( &p_owner
->lock
);
847 if( p_owner
->b_waiting
&& !p_owner
->b_first
)
849 p_owner
->b_has_data
= true;
850 vlc_cond_signal( &p_owner
->wait_acknowledge
);
852 bool b_first_after_wait
= p_owner
->b_waiting
&& p_owner
->b_has_data
;
854 DecoderWaitUnblock( p_dec
);
856 if( p_owner
->b_waiting
)
858 assert( p_owner
->b_first
);
859 msg_Dbg( p_dec
, "Received first picture" );
860 p_owner
->b_first
= false;
861 p_picture
->b_force
= true;
864 const bool b_dated
= p_picture
->date
> VLC_TS_INVALID
;
865 int i_rate
= INPUT_RATE_DEFAULT
;
866 DecoderFixTs( p_dec
, &p_picture
->date
, NULL
, NULL
,
867 &i_rate
, DECODER_BOGUS_VIDEO_DELAY
);
869 vlc_mutex_unlock( &p_owner
->lock
);
871 /* FIXME: The *input* FIFO should not be locked here. This will not work
872 * properly if/when pictures are queued asynchronously. */
873 vlc_fifo_Lock( p_owner
->p_fifo
);
874 if( unlikely(p_owner
->paused
) && likely(p_owner
->frames_countdown
> 0) )
875 p_owner
->frames_countdown
--;
876 vlc_fifo_Unlock( p_owner
->p_fifo
);
879 if( p_picture
->b_force
|| p_picture
->date
> VLC_TS_INVALID
)
880 /* FIXME: VLC_TS_INVALID -- verify video_output */
882 if( i_rate
!= p_owner
->i_last_rate
|| b_first_after_wait
)
884 /* Be sure to not display old picture after our own */
885 vout_Flush( p_vout
, p_picture
->date
);
886 p_owner
->i_last_rate
= i_rate
;
888 vout_PutPicture( p_vout
, p_picture
);
893 msg_Warn( p_dec
, "early picture skipped" );
895 msg_Warn( p_dec
, "non-dated video buffer received" );
898 picture_Release( p_picture
);
902 vout_GetResetStatistic( p_vout
, &i_tmp_display
, &i_tmp_lost
);
904 *pi_played_sum
+= i_tmp_display
;
905 *pi_lost_sum
+= i_tmp_lost
;
908 static int DecoderPreparePlayVideo( decoder_t
*p_dec
, picture_t
*p_pic
)
910 decoder_owner_sys_t
*p_owner
= p_dec
->p_owner
;
911 vout_thread_t
*p_vout
= p_owner
->p_vout
;
914 vlc_mutex_lock( &p_owner
->lock
);
915 if( p_owner
->i_preroll_end
> p_pic
->date
)
917 vlc_mutex_unlock( &p_owner
->lock
);
918 picture_Release( p_pic
);
922 prerolled
= p_owner
->i_preroll_end
> INT64_MIN
;
923 p_owner
->i_preroll_end
= INT64_MIN
;
924 vlc_mutex_unlock( &p_owner
->lock
);
926 if( unlikely(prerolled
) )
928 msg_Dbg( p_dec
, "end of video preroll" );
931 vout_Flush( p_vout
, VLC_TS_INVALID
+1 );
934 if( p_dec
->pf_get_cc
&&
935 ( !p_owner
->p_packetizer
|| !p_owner
->p_packetizer
->pf_get_cc
) )
936 DecoderGetCc( p_dec
, p_dec
);
941 static void DecoderUpdateStatVideo( decoder_t
*p_dec
, int i_decoded
,
942 int i_lost
, int i_displayed
)
944 decoder_owner_sys_t
*p_owner
= p_dec
->p_owner
;
945 input_thread_t
*p_input
= p_owner
->p_input
;
947 /* Update ugly stat */
948 if( p_input
!= NULL
&& (i_decoded
> 0 || i_lost
> 0 || i_displayed
> 0) )
950 vlc_mutex_lock( &p_input
->p
->counters
.counters_lock
);
951 stats_Update( p_input
->p
->counters
.p_decoded_video
, i_decoded
, NULL
);
952 stats_Update( p_input
->p
->counters
.p_lost_pictures
, i_lost
, NULL
);
953 stats_Update( p_input
->p
->counters
.p_displayed_pictures
,
955 vlc_mutex_unlock( &p_input
->p
->counters
.counters_lock
);
959 static int DecoderQueueVideo( decoder_t
*p_dec
, picture_t
*p_pic
)
966 if( ( i_ret
= DecoderPreparePlayVideo( p_dec
, p_pic
) ) == 0 )
967 DecoderPlayVideo( p_dec
, p_pic
, &i_displayed
, &i_lost
);
969 DecoderUpdateStatVideo( p_dec
, 1, i_lost
, i_displayed
);
973 static void DecoderDecodeVideo( decoder_t
*p_dec
, block_t
*p_block
)
976 block_t
**pp_block
= p_block
? &p_block
: NULL
;
981 while( (p_pic
= p_dec
->pf_decode_video( p_dec
, pp_block
) ) )
985 if( DecoderPreparePlayVideo( p_dec
, p_pic
) != 0 )
988 DecoderPlayVideo( p_dec
, p_pic
, &i_displayed
, &i_lost
);
991 DecoderUpdateStatVideo( p_dec
, i_decoded
, i_lost
, i_displayed
);
994 /* This function process a video block
996 static void DecoderProcessVideo( decoder_t
*p_dec
, block_t
*p_block
)
998 decoder_owner_sys_t
*p_owner
= p_dec
->p_owner
;
1000 if( p_owner
->p_packetizer
)
1002 block_t
*p_packetized_block
;
1003 block_t
**pp_block
= p_block
? &p_block
: NULL
;
1004 decoder_t
*p_packetizer
= p_owner
->p_packetizer
;
1006 while( (p_packetized_block
=
1007 p_packetizer
->pf_packetize( p_packetizer
, pp_block
) ) )
1009 if( !es_format_IsSimilar( &p_dec
->fmt_in
, &p_packetizer
->fmt_out
) )
1011 msg_Dbg( p_dec
, "restarting module due to input format change");
1013 /* Drain the decoder module */
1014 DecoderDecodeVideo( p_dec
, NULL
);
1015 /* Restart the decoder module */
1016 UnloadDecoder( p_dec
);
1017 if( LoadDecoder( p_dec
, false, &p_packetizer
->fmt_out
) )
1019 p_dec
->b_error
= true;
1020 block_ChainRelease( p_packetized_block
);
1025 if( p_packetizer
->pf_get_cc
)
1026 DecoderGetCc( p_dec
, p_packetizer
);
1028 while( p_packetized_block
)
1030 block_t
*p_next
= p_packetized_block
->p_next
;
1031 p_packetized_block
->p_next
= NULL
;
1033 DecoderDecodeVideo( p_dec
, p_packetized_block
);
1035 p_packetized_block
= p_next
;
1038 /* Drain the decoder after the packetizer is drained */
1040 DecoderDecodeVideo( p_dec
, NULL
);
1044 DecoderDecodeVideo( p_dec
, p_block
);
1048 static void DecoderPlayAudio( decoder_t
*p_dec
, block_t
*p_audio
,
1049 int *pi_played_sum
, int *pi_lost_sum
)
1051 decoder_owner_sys_t
*p_owner
= p_dec
->p_owner
;
1054 if( p_audio
->i_pts
<= VLC_TS_INVALID
) // FIXME --VLC_TS_INVALID verify audio_output/*
1056 msg_Warn( p_dec
, "non-dated audio buffer received" );
1058 block_Release( p_audio
);
1063 vlc_mutex_lock( &p_owner
->lock
);
1064 if( p_owner
->b_waiting
)
1066 p_owner
->b_has_data
= true;
1067 vlc_cond_signal( &p_owner
->wait_acknowledge
);
1071 int i_rate
= INPUT_RATE_DEFAULT
;
1073 DecoderWaitUnblock( p_dec
);
1074 DecoderFixTs( p_dec
, &p_audio
->i_pts
, NULL
, &p_audio
->i_length
,
1075 &i_rate
, AOUT_MAX_ADVANCE_TIME
);
1076 vlc_mutex_unlock( &p_owner
->lock
);
1078 audio_output_t
*p_aout
= p_owner
->p_aout
;
1080 if( p_aout
== NULL
|| p_audio
->i_pts
<= VLC_TS_INVALID
1081 || i_rate
< INPUT_RATE_DEFAULT
/AOUT_MAX_INPUT_RATE
1082 || i_rate
> INPUT_RATE_DEFAULT
*AOUT_MAX_INPUT_RATE
1083 || DecoderTimedWait( p_dec
, p_audio
->i_pts
- AOUT_MAX_PREPARE_TIME
) )
1085 msg_Dbg( p_dec
, "discarded audio buffer" );
1087 block_Release( p_audio
);
1091 if( aout_DecPlay( p_aout
, p_audio
, i_rate
) == 0 )
1092 *pi_played_sum
+= 1;
1094 *pi_lost_sum
+= aout_DecGetResetLost( p_aout
);
1097 static int DecoderPreparePlayAudio( decoder_t
*p_dec
, block_t
*p_aout_buf
)
1099 decoder_owner_sys_t
*p_owner
= p_dec
->p_owner
;
1102 vlc_mutex_lock( &p_owner
->lock
);
1103 if( p_owner
->i_preroll_end
> p_aout_buf
->i_pts
)
1105 vlc_mutex_unlock( &p_owner
->lock
);
1106 block_Release( p_aout_buf
);
1110 prerolled
= p_owner
->i_preroll_end
> INT64_MIN
;
1111 p_owner
->i_preroll_end
= INT64_MIN
;
1112 vlc_mutex_unlock( &p_owner
->lock
);
1114 if( unlikely(prerolled
) )
1116 msg_Dbg( p_dec
, "end of audio preroll" );
1118 if( p_owner
->p_aout
)
1119 aout_DecFlush( p_owner
->p_aout
, false );
1125 static void DecoderUpdateStatAudio( decoder_t
*p_dec
, int i_decoded
,
1126 int i_lost
, int i_played
)
1128 decoder_owner_sys_t
*p_owner
= p_dec
->p_owner
;
1129 input_thread_t
*p_input
= p_owner
->p_input
;
1131 /* Update ugly stat */
1132 if( p_input
!= NULL
&& (i_decoded
> 0 || i_lost
> 0 || i_played
> 0) )
1134 vlc_mutex_lock( &p_input
->p
->counters
.counters_lock
);
1135 stats_Update( p_input
->p
->counters
.p_lost_abuffers
, i_lost
, NULL
);
1136 stats_Update( p_input
->p
->counters
.p_played_abuffers
, i_played
, NULL
);
1137 stats_Update( p_input
->p
->counters
.p_decoded_audio
, i_decoded
, NULL
);
1138 vlc_mutex_unlock( &p_input
->p
->counters
.counters_lock
);
1142 static int DecoderQueueAudio( decoder_t
*p_dec
, block_t
*p_aout_buf
)
1144 assert( p_aout_buf
);
1149 if( ( i_ret
= DecoderPreparePlayAudio( p_dec
, p_aout_buf
) ) == 0 )
1150 DecoderPlayAudio( p_dec
, p_aout_buf
, &i_played
, &i_lost
);
1152 DecoderUpdateStatAudio( p_dec
, 1, i_lost
, i_played
);
1157 static void DecoderDecodeAudio( decoder_t
*p_dec
, block_t
*p_block
)
1159 block_t
*p_aout_buf
;
1160 block_t
**pp_block
= p_block
? &p_block
: NULL
;
1165 while( (p_aout_buf
= p_dec
->pf_decode_audio( p_dec
, pp_block
) ) )
1169 if( DecoderPreparePlayAudio( p_dec
, p_aout_buf
) != 0 )
1172 DecoderPlayAudio( p_dec
, p_aout_buf
, &i_played
, &i_lost
);
1175 DecoderUpdateStatAudio( p_dec
, i_decoded
, i_lost
, i_played
);
1178 /* This function process a audio block
1180 static void DecoderProcessAudio( decoder_t
*p_dec
, block_t
*p_block
)
1182 decoder_owner_sys_t
*p_owner
= p_dec
->p_owner
;
1184 if( p_owner
->p_packetizer
)
1186 block_t
*p_packetized_block
;
1187 block_t
**pp_block
= p_block
? &p_block
: NULL
;
1188 decoder_t
*p_packetizer
= p_owner
->p_packetizer
;
1190 while( (p_packetized_block
=
1191 p_packetizer
->pf_packetize( p_packetizer
, pp_block
) ) )
1193 if( !es_format_IsSimilar( &p_dec
->fmt_in
, &p_packetizer
->fmt_out
) )
1195 msg_Dbg( p_dec
, "restarting module due to input format change");
1197 /* Drain the decoder module */
1198 DecoderDecodeAudio( p_dec
, NULL
);
1199 /* Restart the decoder module */
1200 UnloadDecoder( p_dec
);
1201 if( LoadDecoder( p_dec
, false, &p_packetizer
->fmt_out
) )
1203 p_dec
->b_error
= true;
1204 block_ChainRelease( p_packetized_block
);
1209 while( p_packetized_block
)
1211 block_t
*p_next
= p_packetized_block
->p_next
;
1212 p_packetized_block
->p_next
= NULL
;
1214 DecoderDecodeAudio( p_dec
, p_packetized_block
);
1216 p_packetized_block
= p_next
;
1219 /* Drain the decoder after the packetizer is drained */
1221 DecoderDecodeAudio( p_dec
, NULL
);
1225 DecoderDecodeAudio( p_dec
, p_block
);
1229 static void DecoderPlaySpu( decoder_t
*p_dec
, subpicture_t
*p_subpic
)
1231 decoder_owner_sys_t
*p_owner
= p_dec
->p_owner
;
1232 vout_thread_t
*p_vout
= p_owner
->p_spu_vout
;
1235 if( p_subpic
->i_start
<= VLC_TS_INVALID
)
1237 msg_Warn( p_dec
, "non-dated spu buffer received" );
1238 subpicture_Delete( p_subpic
);
1243 vlc_mutex_lock( &p_owner
->lock
);
1245 if( p_owner
->b_waiting
)
1247 p_owner
->b_has_data
= true;
1248 vlc_cond_signal( &p_owner
->wait_acknowledge
);
1251 DecoderWaitUnblock( p_dec
);
1252 DecoderFixTs( p_dec
, &p_subpic
->i_start
, &p_subpic
->i_stop
, NULL
,
1254 vlc_mutex_unlock( &p_owner
->lock
);
1256 if( p_subpic
->i_start
<= VLC_TS_INVALID
1257 || DecoderTimedWait( p_dec
, p_subpic
->i_start
- SPU_MAX_PREPARE_TIME
) )
1259 subpicture_Delete( p_subpic
);
1263 vout_PutSubpicture( p_vout
, p_subpic
);
1266 static int DecoderQueueSpu( decoder_t
*p_dec
, subpicture_t
*p_spu
)
1269 decoder_owner_sys_t
*p_owner
= p_dec
->p_owner
;
1270 input_thread_t
*p_input
= p_owner
->p_input
;
1272 if( p_input
!= NULL
)
1274 vlc_mutex_lock( &p_input
->p
->counters
.counters_lock
);
1275 stats_Update( p_input
->p
->counters
.p_decoded_sub
, 1, NULL
);
1276 vlc_mutex_unlock( &p_input
->p
->counters
.counters_lock
);
1280 vout_thread_t
*p_vout
= input_resource_HoldVout( p_owner
->p_resource
);
1281 if( p_vout
&& p_owner
->p_spu_vout
== p_vout
)
1283 /* Preroll does not work very well with subtitle */
1284 vlc_mutex_lock( &p_owner
->lock
);
1285 if( p_spu
->i_start
> VLC_TS_INVALID
&&
1286 p_spu
->i_start
< p_owner
->i_preroll_end
&&
1287 ( p_spu
->i_stop
<= VLC_TS_INVALID
|| p_spu
->i_stop
< p_owner
->i_preroll_end
) )
1289 vlc_mutex_unlock( &p_owner
->lock
);
1290 subpicture_Delete( p_spu
);
1294 vlc_mutex_unlock( &p_owner
->lock
);
1295 DecoderPlaySpu( p_dec
, p_spu
);
1301 subpicture_Delete( p_spu
);
1304 vlc_object_release( p_vout
);
1308 /* This function process a subtitle block
1310 static void DecoderProcessSpu( decoder_t
*p_dec
, block_t
*p_block
)
1312 subpicture_t
*p_spu
;
1313 block_t
**pp_block
= p_block
? &p_block
: NULL
;
1315 while( (p_spu
= p_dec
->pf_decode_sub( p_dec
, pp_block
) ) )
1316 DecoderQueueSpu( p_dec
, p_spu
);
1322 * \param p_dec the decoder object
1323 * \param p_block the block to decode
1324 * \return VLC_SUCCESS or an error code
1326 static void DecoderProcess( decoder_t
*p_dec
, block_t
*p_block
)
1328 decoder_owner_sys_t
*p_owner
= p_dec
->p_owner
;
1330 if( p_dec
->b_error
)
1333 block_Release( p_block
);
1337 if( p_block
&& p_block
->i_buffer
<= 0 )
1339 block_Release( p_block
);
1345 vlc_mutex_lock( &p_owner
->lock
);
1346 DecoderUpdatePreroll( &p_owner
->i_preroll_end
, p_block
);
1347 vlc_mutex_unlock( &p_owner
->lock
);
1351 if( p_owner
->p_sout
!= NULL
)
1353 DecoderProcessSout( p_dec
, p_block
);
1358 if( p_dec
->fmt_out
.i_cat
== AUDIO_ES
)
1360 DecoderProcessAudio( p_dec
, p_block
);
1362 else if( p_dec
->fmt_out
.i_cat
== VIDEO_ES
)
1364 DecoderProcessVideo( p_dec
, p_block
);
1366 else if( p_dec
->fmt_out
.i_cat
== SPU_ES
)
1368 DecoderProcessSpu( p_dec
, p_block
);
1372 msg_Err( p_dec
, "unknown ES format" );
1373 p_dec
->b_error
= true;
1378 static void DecoderProcessFlush( decoder_t
*p_dec
)
1380 decoder_owner_sys_t
*p_owner
= p_dec
->p_owner
;
1381 decoder_t
*p_packetizer
= p_owner
->p_packetizer
;
1383 if( p_dec
->b_error
)
1386 if( p_packetizer
!= NULL
&& p_packetizer
->pf_flush
!= NULL
)
1387 p_packetizer
->pf_flush( p_packetizer
);
1389 if ( p_dec
->pf_flush
!= NULL
)
1390 p_dec
->pf_flush( p_dec
);
1393 if ( p_owner
->p_sout_input
!= NULL
)
1395 sout_InputFlush( p_owner
->p_sout_input
);
1398 if( p_dec
->fmt_out
.i_cat
== AUDIO_ES
)
1400 if( p_owner
->p_aout
)
1401 aout_DecFlush( p_owner
->p_aout
, false );
1403 else if( p_dec
->fmt_out
.i_cat
== VIDEO_ES
)
1405 if( p_owner
->p_vout
)
1406 vout_Flush( p_owner
->p_vout
, VLC_TS_INVALID
+1 );
1408 else if( p_dec
->fmt_out
.i_cat
== SPU_ES
)
1410 if( p_owner
->p_spu_vout
)
1412 vout_thread_t
*p_vout
= input_resource_HoldVout( p_owner
->p_resource
);
1414 if( p_vout
&& p_owner
->p_spu_vout
== p_vout
)
1415 vout_FlushSubpictureChannel( p_vout
, p_owner
->i_spu_channel
);
1418 vlc_object_release( p_vout
);
1422 vlc_mutex_lock( &p_owner
->lock
);
1423 p_owner
->i_preroll_end
= INT64_MIN
;
1424 vlc_mutex_unlock( &p_owner
->lock
);
1428 * The decoding main loop
1430 * \param p_dec the decoder
1432 static void *DecoderThread( void *p_data
)
1434 decoder_t
*p_dec
= (decoder_t
*)p_data
;
1435 decoder_owner_sys_t
*p_owner
= p_dec
->p_owner
;
1436 bool paused
= false;
1438 /* The decoder's main loop */
1439 vlc_fifo_Lock( p_owner
->p_fifo
);
1440 vlc_fifo_CleanupPush( p_owner
->p_fifo
);
1444 if( p_owner
->flushing
)
1445 { /* Flush before/regardless of pause. We do not want to resume just
1446 * for the sake of flushing (glitches could otherwise happen). */
1447 int canc
= vlc_savecancel();
1449 vlc_fifo_Unlock( p_owner
->p_fifo
);
1451 /* Flush the decoder (and the output) */
1452 DecoderProcessFlush( p_dec
);
1454 vlc_fifo_Lock( p_owner
->p_fifo
);
1455 vlc_restorecancel( canc
);
1457 /* Reset flushing after DecoderProcess in case input_DecoderFlush
1458 * is called again. This will avoid a second useless flush (but
1460 p_owner
->flushing
= false;
1465 if( paused
!= p_owner
->paused
)
1466 { /* Update playing/paused status of the output */
1467 int canc
= vlc_savecancel();
1468 mtime_t date
= p_owner
->pause_date
;
1470 paused
= p_owner
->paused
;
1471 vlc_fifo_Unlock( p_owner
->p_fifo
);
1473 /* NOTE: Only the audio and video outputs care about pause. */
1474 msg_Dbg( p_dec
, "toggling %s", paused
? "resume" : "pause" );
1475 if( p_owner
->p_vout
!= NULL
)
1476 vout_ChangePause( p_owner
->p_vout
, paused
, date
);
1477 if( p_owner
->p_aout
!= NULL
)
1478 aout_DecChangePause( p_owner
->p_aout
, paused
, date
);
1480 vlc_restorecancel( canc
);
1481 vlc_fifo_Lock( p_owner
->p_fifo
);
1485 if( p_owner
->paused
&& p_owner
->frames_countdown
== 0 )
1486 { /* Wait for resumption from pause */
1487 p_owner
->b_idle
= true;
1488 vlc_fifo_Wait( p_owner
->p_fifo
);
1489 p_owner
->b_idle
= false;
1493 vlc_cond_signal( &p_owner
->wait_fifo
);
1494 vlc_testcancel(); /* forced expedited cancellation in case of stop */
1496 block_t
*p_block
= vlc_fifo_DequeueUnlocked( p_owner
->p_fifo
);
1497 if( p_block
== NULL
)
1499 if( likely(!p_owner
->b_draining
) )
1500 { /* Wait for a block to decode (or a request to drain) */
1501 p_owner
->b_idle
= true;
1502 vlc_fifo_Wait( p_owner
->p_fifo
);
1503 p_owner
->b_idle
= false;
1506 /* We have emptied the FIFO and there is a pending request to
1507 * drain. Pass p_block = NULL to decoder just once. */
1508 p_owner
->b_draining
= false;
1511 vlc_fifo_Unlock( p_owner
->p_fifo
);
1513 int canc
= vlc_savecancel();
1514 DecoderProcess( p_dec
, p_block
);
1516 if( p_block
== NULL
)
1517 { /* Draining: the decoder is drained and all decoded buffers are
1518 * queued to the output at this point. Now drain the output. */
1519 if( p_owner
->p_aout
!= NULL
)
1520 aout_DecFlush( p_owner
->p_aout
, true );
1522 vlc_restorecancel( canc
);
1524 /* Given that the drained flag is only polled, an atomic variable is
1525 * sufficient. TODO? Wait for draining instead of polling. */
1526 atomic_store( &p_owner
->drained
, (p_block
== NULL
) );
1528 vlc_mutex_lock( &p_owner
->lock
);
1529 vlc_fifo_Lock( p_owner
->p_fifo
);
1530 vlc_cond_signal( &p_owner
->wait_acknowledge
);
1531 vlc_mutex_unlock( &p_owner
->lock
);
1534 vlc_assert_unreachable();
1538 * Create a decoder object
1540 * \param p_input the input thread
1541 * \param p_es the es descriptor
1542 * \param b_packetizer instead of a decoder
1543 * \return the decoder object
1545 static decoder_t
* CreateDecoder( vlc_object_t
*p_parent
,
1546 input_thread_t
*p_input
,
1547 const es_format_t
*fmt
,
1548 input_resource_t
*p_resource
,
1549 sout_instance_t
*p_sout
)
1552 decoder_owner_sys_t
*p_owner
;
1554 p_dec
= vlc_custom_create( p_parent
, sizeof( *p_dec
), "decoder" );
1558 /* Allocate our private structure for the decoder */
1559 p_dec
->p_owner
= p_owner
= malloc( sizeof( decoder_owner_sys_t
) );
1560 if( unlikely(p_owner
== NULL
) )
1562 vlc_object_release( p_dec
);
1565 p_owner
->i_preroll_end
= INT64_MIN
;
1566 p_owner
->i_last_rate
= INPUT_RATE_DEFAULT
;
1567 p_owner
->p_input
= p_input
;
1568 p_owner
->p_resource
= p_resource
;
1569 p_owner
->p_aout
= NULL
;
1570 p_owner
->p_vout
= NULL
;
1571 p_owner
->p_spu_vout
= NULL
;
1572 p_owner
->i_spu_channel
= 0;
1573 p_owner
->i_spu_order
= 0;
1574 p_owner
->p_sout
= p_sout
;
1575 p_owner
->p_sout_input
= NULL
;
1576 p_owner
->p_packetizer
= NULL
;
1578 p_owner
->b_fmt_description
= false;
1579 p_owner
->p_description
= NULL
;
1581 p_owner
->paused
= false;
1582 p_owner
->pause_date
= VLC_TS_INVALID
;
1583 p_owner
->frames_countdown
= 0;
1585 p_owner
->b_waiting
= false;
1586 p_owner
->b_first
= true;
1587 p_owner
->b_has_data
= false;
1589 p_owner
->flushing
= false;
1590 p_owner
->b_draining
= false;
1591 atomic_init( &p_owner
->drained
, false );
1592 p_owner
->b_idle
= false;
1594 es_format_Init( &p_owner
->fmt
, UNKNOWN_ES
, 0 );
1597 p_owner
->p_fifo
= block_FifoNew();
1598 if( unlikely(p_owner
->p_fifo
== NULL
) )
1601 vlc_object_release( p_dec
);
1605 vlc_mutex_init( &p_owner
->lock
);
1606 vlc_cond_init( &p_owner
->wait_request
);
1607 vlc_cond_init( &p_owner
->wait_acknowledge
);
1608 vlc_cond_init( &p_owner
->wait_fifo
);
1609 vlc_cond_init( &p_owner
->wait_timed
);
1611 /* Set buffers allocation callbacks for the decoders */
1612 p_dec
->pf_aout_format_update
= aout_update_format
;
1613 p_dec
->pf_vout_format_update
= vout_update_format
;
1614 p_dec
->pf_vout_buffer_new
= vout_new_buffer
;
1615 p_dec
->pf_spu_buffer_new
= spu_new_buffer
;
1617 p_dec
->pf_get_attachments
= DecoderGetInputAttachments
;
1618 p_dec
->pf_get_display_date
= DecoderGetDisplayDate
;
1619 p_dec
->pf_get_display_rate
= DecoderGetDisplayRate
;
1620 p_dec
->pf_queue_video
= DecoderQueueVideo
;
1621 p_dec
->pf_queue_audio
= DecoderQueueAudio
;
1622 p_dec
->pf_queue_sub
= DecoderQueueSpu
;
1624 /* Load a packetizer module if the input is not already packetized */
1625 if( p_sout
== NULL
&& !fmt
->b_packetized
)
1627 p_owner
->p_packetizer
=
1628 vlc_custom_create( p_parent
, sizeof( decoder_t
), "packetizer" );
1629 if( p_owner
->p_packetizer
)
1631 if( LoadDecoder( p_owner
->p_packetizer
, true, fmt
) )
1633 vlc_object_release( p_owner
->p_packetizer
);
1634 p_owner
->p_packetizer
= NULL
;
1638 p_owner
->p_packetizer
->fmt_out
.b_packetized
= true;
1639 fmt
= &p_owner
->p_packetizer
->fmt_out
;
1644 /* Find a suitable decoder/packetizer module */
1645 if( LoadDecoder( p_dec
, p_sout
!= NULL
, fmt
) )
1648 /* Copy ourself the input replay gain */
1649 if( fmt
->i_cat
== AUDIO_ES
)
1651 for( unsigned i
= 0; i
< AUDIO_REPLAY_GAIN_MAX
; i
++ )
1653 if( !p_dec
->fmt_out
.audio_replay_gain
.pb_peak
[i
] )
1655 p_dec
->fmt_out
.audio_replay_gain
.pb_peak
[i
] = fmt
->audio_replay_gain
.pb_peak
[i
];
1656 p_dec
->fmt_out
.audio_replay_gain
.pf_peak
[i
] = fmt
->audio_replay_gain
.pf_peak
[i
];
1658 if( !p_dec
->fmt_out
.audio_replay_gain
.pb_gain
[i
] )
1660 p_dec
->fmt_out
.audio_replay_gain
.pb_gain
[i
] = fmt
->audio_replay_gain
.pb_gain
[i
];
1661 p_dec
->fmt_out
.audio_replay_gain
.pf_gain
[i
] = fmt
->audio_replay_gain
.pf_gain
[i
];
1667 p_owner
->cc
.b_supported
= false;
1668 if( p_sout
== NULL
)
1670 if( p_owner
->p_packetizer
&& p_owner
->p_packetizer
->pf_get_cc
)
1671 p_owner
->cc
.b_supported
= true;
1672 if( p_dec
->pf_get_cc
)
1673 p_owner
->cc
.b_supported
= true;
1676 for( unsigned i
= 0; i
< 4; i
++ )
1678 p_owner
->cc
.pb_present
[i
] = false;
1679 p_owner
->cc
.pp_decoder
[i
] = NULL
;
1681 p_owner
->i_ts_delay
= 0;
1686 * Destroys a decoder object
1688 * \param p_dec the decoder object
1691 static void DeleteDecoder( decoder_t
* p_dec
)
1693 decoder_owner_sys_t
*p_owner
= p_dec
->p_owner
;
1695 msg_Dbg( p_dec
, "killing decoder fourcc `%4.4s', %u PES in FIFO",
1696 (char*)&p_dec
->fmt_in
.i_codec
,
1697 (unsigned)block_FifoCount( p_owner
->p_fifo
) );
1699 const bool b_flush_spu
= p_dec
->fmt_out
.i_cat
== SPU_ES
;
1700 UnloadDecoder( p_dec
);
1702 /* Free all packets still in the decoder fifo. */
1703 block_FifoRelease( p_owner
->p_fifo
);
1706 if( p_owner
->p_aout
)
1708 /* TODO: REVISIT gap-less audio */
1709 aout_DecFlush( p_owner
->p_aout
, false );
1710 aout_DecDelete( p_owner
->p_aout
);
1711 input_resource_PutAout( p_owner
->p_resource
, p_owner
->p_aout
);
1712 if( p_owner
->p_input
!= NULL
)
1713 input_SendEventAout( p_owner
->p_input
);
1715 if( p_owner
->p_vout
)
1717 /* Hack to make sure all the the pictures are freed by the decoder
1718 * and that the vout is not paused anymore */
1719 vout_Reset( p_owner
->p_vout
);
1722 input_resource_RequestVout( p_owner
->p_resource
, p_owner
->p_vout
, NULL
,
1724 if( p_owner
->p_input
!= NULL
)
1725 input_SendEventVout( p_owner
->p_input
);
1729 if( p_owner
->p_sout_input
)
1731 sout_InputDelete( p_owner
->p_sout_input
);
1734 es_format_Clean( &p_owner
->fmt
);
1738 vout_thread_t
*p_vout
= input_resource_HoldVout( p_owner
->p_resource
);
1741 if( p_owner
->p_spu_vout
== p_vout
)
1742 vout_FlushSubpictureChannel( p_vout
, p_owner
->i_spu_channel
);
1743 vlc_object_release( p_vout
);
1747 if( p_owner
->p_description
)
1748 vlc_meta_Delete( p_owner
->p_description
);
1750 if( p_owner
->p_packetizer
)
1752 UnloadDecoder( p_owner
->p_packetizer
);
1753 vlc_object_release( p_owner
->p_packetizer
);
1756 vlc_cond_destroy( &p_owner
->wait_timed
);
1757 vlc_cond_destroy( &p_owner
->wait_fifo
);
1758 vlc_cond_destroy( &p_owner
->wait_acknowledge
);
1759 vlc_cond_destroy( &p_owner
->wait_request
);
1760 vlc_mutex_destroy( &p_owner
->lock
);
1762 vlc_object_release( p_dec
);
1768 static void DecoderUnsupportedCodec( decoder_t
*p_dec
, const es_format_t
*fmt
)
1770 if (fmt
->i_codec
!= VLC_FOURCC('u','n','d','f')) {
1771 const char *desc
= vlc_fourcc_GetDescription(fmt
->i_cat
, fmt
->i_codec
);
1772 if (!desc
|| !*desc
)
1773 desc
= N_("No description for this codec");
1774 msg_Err( p_dec
, "Codec `%4.4s' (%s) is not supported.", (char*)&fmt
->i_codec
, desc
);
1775 dialog_Fatal( p_dec
, _("Codec not supported"),
1776 _("VLC could not decode the format \"%4.4s\" (%s)"),
1777 (char*)&fmt
->i_codec
, desc
);
1779 msg_Err( p_dec
, "could not identify codec" );
1780 dialog_Fatal( p_dec
, _("Unidentified codec"),
1781 _("VLC could not identify the audio or video codec" ) );
1785 /* TODO: pass p_sout through p_resource? -- Courmisch */
1786 static decoder_t
*decoder_New( vlc_object_t
*p_parent
, input_thread_t
*p_input
,
1787 const es_format_t
*fmt
, input_clock_t
*p_clock
,
1788 input_resource_t
*p_resource
,
1789 sout_instance_t
*p_sout
)
1791 decoder_t
*p_dec
= NULL
;
1792 const char *psz_type
= p_sout
? N_("packetizer") : N_("decoder");
1795 /* Create the decoder configuration structure */
1796 p_dec
= CreateDecoder( p_parent
, p_input
, fmt
, p_resource
, p_sout
);
1799 msg_Err( p_parent
, "could not create %s", psz_type
);
1800 dialog_Fatal( p_parent
, _("Streaming / Transcoding failed"),
1801 _("VLC could not open the %s module."),
1802 vlc_gettext( psz_type
) );
1806 if( !p_dec
->p_module
)
1808 DecoderUnsupportedCodec( p_dec
, fmt
);
1810 DeleteDecoder( p_dec
);
1814 p_dec
->p_owner
->p_clock
= p_clock
;
1815 assert( p_dec
->fmt_out
.i_cat
!= UNKNOWN_ES
);
1817 if( p_dec
->fmt_out
.i_cat
== AUDIO_ES
)
1818 i_priority
= VLC_THREAD_PRIORITY_AUDIO
;
1820 i_priority
= VLC_THREAD_PRIORITY_VIDEO
;
1822 /* Spawn the decoder thread */
1823 if( vlc_clone( &p_dec
->p_owner
->thread
, DecoderThread
, p_dec
, i_priority
) )
1825 msg_Err( p_dec
, "cannot spawn decoder thread" );
1826 DeleteDecoder( p_dec
);
1835 * Spawns a new decoder thread from the input thread
1837 * \param p_input the input thread
1838 * \param p_es the es descriptor
1839 * \return the spawned decoder object
1841 decoder_t
*input_DecoderNew( input_thread_t
*p_input
,
1842 es_format_t
*fmt
, input_clock_t
*p_clock
,
1843 sout_instance_t
*p_sout
)
1845 return decoder_New( VLC_OBJECT(p_input
), p_input
, fmt
, p_clock
,
1846 p_input
->p
->p_resource
, p_sout
);
1850 * Spawn a decoder thread outside of the input thread.
1852 decoder_t
*input_DecoderCreate( vlc_object_t
*p_parent
, const es_format_t
*fmt
,
1853 input_resource_t
*p_resource
)
1855 return decoder_New( p_parent
, NULL
, fmt
, NULL
, p_resource
, NULL
);
1860 * Kills a decoder thread and waits until it's finished
1862 * \param p_input the input thread
1863 * \param p_es the es descriptor
1866 void input_DecoderDelete( decoder_t
*p_dec
)
1868 decoder_owner_sys_t
*p_owner
= p_dec
->p_owner
;
1870 vlc_cancel( p_owner
->thread
);
1872 vlc_fifo_Lock( p_owner
->p_fifo
);
1873 /* Signal DecoderTimedWait */
1874 p_owner
->flushing
= true;
1875 vlc_cond_signal( &p_owner
->wait_timed
);
1876 vlc_fifo_Unlock( p_owner
->p_fifo
);
1878 /* Make sure we aren't waiting/decoding anymore */
1879 vlc_mutex_lock( &p_owner
->lock
);
1880 p_owner
->b_waiting
= false;
1881 vlc_cond_signal( &p_owner
->wait_request
);
1883 /* If the video output is paused or slow, or if the picture pool size was
1884 * under-estimated (e.g. greedy video filter, buggy decoder...), the
1885 * the picture pool may be empty, and the decoder thread or any decoder
1886 * module worker threads may be stuck waiting for free picture buffers.
1888 * This unblocks the thread, allowing the decoder module to join all its
1889 * worker threads (if any) and the decoder thread to terminate. */
1890 if( p_owner
->p_vout
!= NULL
)
1891 vout_Cancel( p_owner
->p_vout
, true );
1892 vlc_mutex_unlock( &p_owner
->lock
);
1894 vlc_join( p_owner
->thread
, NULL
);
1897 if( p_dec
->p_owner
->cc
.b_supported
)
1900 for( i
= 0; i
< 4; i
++ )
1901 input_DecoderSetCcState( p_dec
, false, i
);
1904 /* Delete decoder */
1905 DeleteDecoder( p_dec
);
1909 * Put a block_t in the decoder's fifo.
1910 * Thread-safe w.r.t. the decoder. May be a cancellation point.
1912 * \param p_dec the decoder object
1913 * \param p_block the data block
1915 void input_DecoderDecode( decoder_t
*p_dec
, block_t
*p_block
, bool b_do_pace
)
1917 decoder_owner_sys_t
*p_owner
= p_dec
->p_owner
;
1919 vlc_fifo_Lock( p_owner
->p_fifo
);
1922 /* FIXME: ideally we would check the time amount of data
1923 * in the FIFO instead of its size. */
1924 /* 400 MiB, i.e. ~ 50mb/s for 60s */
1925 if( vlc_fifo_GetBytes( p_owner
->p_fifo
) > 400*1024*1024 )
1927 msg_Warn( p_dec
, "decoder/packetizer fifo full (data not "
1928 "consumed quickly enough), resetting fifo!" );
1929 block_ChainRelease( vlc_fifo_DequeueAllUnlocked( p_owner
->p_fifo
) );
1933 if( !p_owner
->b_waiting
)
1934 { /* The FIFO is not consumed when waiting, so pacing would deadlock VLC.
1935 * Locking is not necessary as b_waiting is only read, not written by
1936 * the decoder thread. */
1937 while( vlc_fifo_GetCount( p_owner
->p_fifo
) >= 10 )
1938 vlc_fifo_WaitCond( p_owner
->p_fifo
, &p_owner
->wait_fifo
);
1941 vlc_fifo_QueueUnlocked( p_owner
->p_fifo
, p_block
);
1942 vlc_fifo_Unlock( p_owner
->p_fifo
);
1945 bool input_DecoderIsEmpty( decoder_t
* p_dec
)
1947 decoder_owner_sys_t
*p_owner
= p_dec
->p_owner
;
1949 assert( !p_owner
->b_waiting
);
1951 if( block_FifoCount( p_dec
->p_owner
->p_fifo
) > 0 )
1956 vlc_mutex_lock( &p_owner
->lock
);
1957 if( p_owner
->p_sout_input
!= NULL
)
1958 b_empty
= sout_InputIsEmpty( p_owner
->p_sout_input
);
1959 else if( p_owner
->fmt
.i_cat
== VIDEO_ES
&& p_owner
->p_vout
!= NULL
)
1960 b_empty
= vout_IsEmpty( p_owner
->p_vout
);
1961 else if( p_owner
->fmt
.i_cat
== AUDIO_ES
)
1962 b_empty
= atomic_load( &p_owner
->drained
);
1964 b_empty
= true; /* TODO subtitles support */
1965 vlc_mutex_unlock( &p_owner
->lock
);
1971 * Signals that there are no further blocks to decode, and requests that the
1972 * decoder drain all pending buffers. This is used to ensure that all
1973 * intermediate buffers empty and no samples get lost at the end of the stream.
1975 * @note The function does not actually wait for draining. It just signals that
1976 * draining should be performed once the decoder has emptied FIFO.
1978 void input_DecoderDrain( decoder_t
*p_dec
)
1980 decoder_owner_sys_t
*p_owner
= p_dec
->p_owner
;
1982 vlc_fifo_Lock( p_owner
->p_fifo
);
1983 p_owner
->b_draining
= true;
1984 vlc_fifo_Signal( p_owner
->p_fifo
);
1985 vlc_fifo_Unlock( p_owner
->p_fifo
);
1989 * Requests that the decoder immediately discard all pending buffers.
1990 * This is useful when seeking or when deselecting a stream.
1992 void input_DecoderFlush( decoder_t
*p_dec
)
1994 decoder_owner_sys_t
*p_owner
= p_dec
->p_owner
;
1996 vlc_fifo_Lock( p_owner
->p_fifo
);
1998 /* Empty the fifo */
1999 block_ChainRelease( vlc_fifo_DequeueAllUnlocked( p_owner
->p_fifo
) );
2001 /* Don't need to wait for the DecoderThread to flush. Indeed, if called a
2002 * second time, this function will clear the FIFO again before anything was
2003 * dequeued by DecoderThread and there is no need to flush a second time in
2005 p_owner
->flushing
= true;
2007 /* Flushing video decoder when paused: increment frames_countdown in order
2008 * to display one frame */
2009 if( p_owner
->fmt
.i_cat
== VIDEO_ES
&& p_owner
->paused
2010 && p_owner
->frames_countdown
== 0 )
2011 p_owner
->frames_countdown
++;
2013 vlc_fifo_Signal( p_owner
->p_fifo
);
2014 vlc_cond_signal( &p_owner
->wait_timed
);
2016 vlc_fifo_Unlock( p_owner
->p_fifo
);
2019 void input_DecoderIsCcPresent( decoder_t
*p_dec
, bool pb_present
[4] )
2021 decoder_owner_sys_t
*p_owner
= p_dec
->p_owner
;
2024 vlc_mutex_lock( &p_owner
->lock
);
2025 for( i
= 0; i
< 4; i
++ )
2026 pb_present
[i
] = p_owner
->cc
.pb_present
[i
];
2027 vlc_mutex_unlock( &p_owner
->lock
);
2030 int input_DecoderSetCcState( decoder_t
*p_dec
, bool b_decode
, int i_channel
)
2032 decoder_owner_sys_t
*p_owner
= p_dec
->p_owner
;
2034 //msg_Warn( p_dec, "input_DecoderSetCcState: %d @%d", b_decode, i_channel );
2036 if( i_channel
< 0 || i_channel
>= 4 || !p_owner
->cc
.pb_present
[i_channel
] )
2037 return VLC_EGENERIC
;
2041 static const vlc_fourcc_t fcc
[4] = {
2042 VLC_FOURCC('c', 'c', '1', ' '),
2043 VLC_FOURCC('c', 'c', '2', ' '),
2044 VLC_FOURCC('c', 'c', '3', ' '),
2045 VLC_FOURCC('c', 'c', '4', ' '),
2050 es_format_Init( &fmt
, SPU_ES
, fcc
[i_channel
] );
2051 p_cc
= input_DecoderNew( p_owner
->p_input
, &fmt
,
2052 p_dec
->p_owner
->p_clock
, p_owner
->p_sout
);
2055 msg_Err( p_dec
, "could not create decoder" );
2056 dialog_Fatal( p_dec
, _("Streaming / Transcoding failed"), "%s",
2057 _("VLC could not open the decoder module.") );
2058 return VLC_EGENERIC
;
2060 else if( !p_cc
->p_module
)
2062 DecoderUnsupportedCodec( p_dec
, &fmt
);
2063 input_DecoderDelete(p_cc
);
2064 return VLC_EGENERIC
;
2066 p_cc
->p_owner
->p_clock
= p_owner
->p_clock
;
2068 vlc_mutex_lock( &p_owner
->lock
);
2069 p_owner
->cc
.pp_decoder
[i_channel
] = p_cc
;
2070 vlc_mutex_unlock( &p_owner
->lock
);
2076 vlc_mutex_lock( &p_owner
->lock
);
2077 p_cc
= p_owner
->cc
.pp_decoder
[i_channel
];
2078 p_owner
->cc
.pp_decoder
[i_channel
] = NULL
;
2079 vlc_mutex_unlock( &p_owner
->lock
);
2082 input_DecoderDelete(p_cc
);
2087 int input_DecoderGetCcState( decoder_t
*p_dec
, bool *pb_decode
, int i_channel
)
2089 decoder_owner_sys_t
*p_owner
= p_dec
->p_owner
;
2092 if( i_channel
< 0 || i_channel
>= 4 || !p_owner
->cc
.pb_present
[i_channel
] )
2093 return VLC_EGENERIC
;
2095 vlc_mutex_lock( &p_owner
->lock
);
2096 *pb_decode
= p_owner
->cc
.pp_decoder
[i_channel
] != NULL
;
2097 vlc_mutex_unlock( &p_owner
->lock
);
2098 return VLC_EGENERIC
;
2101 void input_DecoderChangePause( decoder_t
*p_dec
, bool b_paused
, mtime_t i_date
)
2103 decoder_owner_sys_t
*p_owner
= p_dec
->p_owner
;
2105 /* Normally, p_owner->b_paused != b_paused here. But if a track is added
2106 * while the input is paused (e.g. add sub file), then b_paused is
2107 * (incorrectly) false. FIXME: This is a bug in the decoder owner. */
2108 vlc_fifo_Lock( p_owner
->p_fifo
);
2109 p_owner
->paused
= b_paused
;
2110 p_owner
->pause_date
= i_date
;
2111 p_owner
->frames_countdown
= 0;
2112 vlc_fifo_Signal( p_owner
->p_fifo
);
2113 vlc_fifo_Unlock( p_owner
->p_fifo
);
2116 void input_DecoderChangeDelay( decoder_t
*p_dec
, mtime_t i_delay
)
2118 decoder_owner_sys_t
*p_owner
= p_dec
->p_owner
;
2120 vlc_mutex_lock( &p_owner
->lock
);
2121 p_owner
->i_ts_delay
= i_delay
;
2122 vlc_mutex_unlock( &p_owner
->lock
);
2125 void input_DecoderStartWait( decoder_t
*p_dec
)
2127 decoder_owner_sys_t
*p_owner
= p_dec
->p_owner
;
2129 assert( !p_owner
->b_waiting
);
2131 vlc_mutex_lock( &p_owner
->lock
);
2132 p_owner
->b_first
= true;
2133 p_owner
->b_has_data
= false;
2134 p_owner
->b_waiting
= true;
2135 vlc_cond_signal( &p_owner
->wait_request
);
2136 vlc_mutex_unlock( &p_owner
->lock
);
2139 void input_DecoderStopWait( decoder_t
*p_dec
)
2141 decoder_owner_sys_t
*p_owner
= p_dec
->p_owner
;
2143 assert( p_owner
->b_waiting
);
2145 vlc_mutex_lock( &p_owner
->lock
);
2146 p_owner
->b_waiting
= false;
2147 vlc_cond_signal( &p_owner
->wait_request
);
2148 vlc_mutex_unlock( &p_owner
->lock
);
2151 void input_DecoderWait( decoder_t
*p_dec
)
2153 decoder_owner_sys_t
*p_owner
= p_dec
->p_owner
;
2155 assert( p_owner
->b_waiting
);
2157 vlc_mutex_lock( &p_owner
->lock
);
2158 while( !p_owner
->b_has_data
)
2160 /* Don't need to lock p_owner->paused since it's only modified by the
2162 if( p_owner
->paused
)
2164 vlc_fifo_Lock( p_owner
->p_fifo
);
2165 if( p_owner
->b_idle
&& vlc_fifo_IsEmpty( p_owner
->p_fifo
) )
2167 msg_Err( p_dec
, "buffer deadlock prevented" );
2168 vlc_fifo_Unlock( p_owner
->p_fifo
);
2171 vlc_fifo_Unlock( p_owner
->p_fifo
);
2172 vlc_cond_wait( &p_owner
->wait_acknowledge
, &p_owner
->lock
);
2174 vlc_mutex_unlock( &p_owner
->lock
);
2177 void input_DecoderFrameNext( decoder_t
*p_dec
, mtime_t
*pi_duration
)
2179 decoder_owner_sys_t
*p_owner
= p_dec
->p_owner
;
2181 assert( p_owner
->paused
);
2184 vlc_fifo_Lock( p_owner
->p_fifo
);
2185 p_owner
->frames_countdown
++;
2186 vlc_fifo_Signal( p_owner
->p_fifo
);
2187 vlc_fifo_Unlock( p_owner
->p_fifo
);
2189 vlc_mutex_lock( &p_owner
->lock
);
2190 if( p_owner
->fmt
.i_cat
== VIDEO_ES
)
2192 if( p_owner
->p_vout
)
2193 vout_NextPicture( p_owner
->p_vout
, pi_duration
);
2195 vlc_mutex_unlock( &p_owner
->lock
);
2198 bool input_DecoderHasFormatChanged( decoder_t
*p_dec
, es_format_t
*p_fmt
, vlc_meta_t
**pp_meta
)
2200 decoder_owner_sys_t
*p_owner
= p_dec
->p_owner
;
2203 vlc_mutex_lock( &p_owner
->lock
);
2204 b_changed
= p_owner
->b_fmt_description
;
2208 es_format_Copy( p_fmt
, &p_owner
->fmt
);
2213 if( p_owner
->p_description
)
2215 *pp_meta
= vlc_meta_New();
2217 vlc_meta_Merge( *pp_meta
, p_owner
->p_description
);
2220 p_owner
->b_fmt_description
= false;
2222 vlc_mutex_unlock( &p_owner
->lock
);
2226 size_t input_DecoderGetFifoSize( decoder_t
*p_dec
)
2228 decoder_owner_sys_t
*p_owner
= p_dec
->p_owner
;
2230 return block_FifoSize( p_owner
->p_fifo
);
2233 void input_DecoderGetObjects( decoder_t
*p_dec
,
2234 vout_thread_t
**pp_vout
, audio_output_t
**pp_aout
)
2236 decoder_owner_sys_t
*p_owner
= p_dec
->p_owner
;
2238 vlc_mutex_lock( &p_owner
->lock
);
2240 *pp_vout
= p_owner
->p_vout
? vlc_object_hold( p_owner
->p_vout
) : NULL
;
2242 *pp_aout
= p_owner
->p_aout
? vlc_object_hold( p_owner
->p_aout
) : NULL
;
2243 vlc_mutex_unlock( &p_owner
->lock
);