Commit a558a9bb authored by Christophe Massiot's avatar Christophe Massiot

* Changed default values :

INPUT_PTS_DELAY down to 200 ms ;
video heap down from 10 to 5 pictures ;
decoder fifo size from 1023 to 511 PES ;
* Fixed various bugs in 32 bit-versions of input_ext-dec.h ;
* Fixed a bug in GetChunk() ;
* Renamed GetByte, GetWord, ShowWord to _GetByte, _GetWord, _ShowWord ;
* Moved decoder_fifo-specific code from programs.c to dec.c ;
* Fixed bugs in program.c that prevented vlc to close all decoders ;
* Gave sam a lesson for the use of the bitstream in spu_decoder.c :ppp ;
* Made the video parser unlock the reference pictures before quitting
(still one left, yaknow why ?)
parent ebfaed9b
...@@ -113,7 +113,7 @@ ...@@ -113,7 +113,7 @@
*/ */
/* Size of the FIFO. FIFO_SIZE+1 must be a power of 2 */ /* Size of the FIFO. FIFO_SIZE+1 must be a power of 2 */
#define FIFO_SIZE 1023 #define FIFO_SIZE 511
/* /*
* Paths * Paths
...@@ -207,9 +207,9 @@ ...@@ -207,9 +207,9 @@
* server */ * server */
#define INPUT_VLAN_CHANGE_DELAY (5*CLOCK_FREQ) #define INPUT_VLAN_CHANGE_DELAY (5*CLOCK_FREQ)
/* Duration between the time we receive the TS packet, and the time we will /* Duration between the time we receive the data packet, and the time we will
* mark it to be presented */ * mark it to be presented */
#define DEFAULT_PTS_DELAY (.5*CLOCK_FREQ) #define DEFAULT_PTS_DELAY (.2*CLOCK_FREQ)
#define INPUT_DVD_AUDIO_VAR "vlc_dvd_audio" #define INPUT_DVD_AUDIO_VAR "vlc_dvd_audio"
#define INPUT_DVD_CHANNEL_VAR "vlc_dvd_channel" #define INPUT_DVD_CHANNEL_VAR "vlc_dvd_channel"
...@@ -301,10 +301,10 @@ ...@@ -301,10 +301,10 @@
/* Video heap size - remember that a decompressed picture is big /* Video heap size - remember that a decompressed picture is big
* (~1 Mbyte) before using huge values */ * (~1 Mbyte) before using huge values */
#define VOUT_MAX_PICTURES 10 #define VOUT_MAX_PICTURES 5
/* Number of simultaneous subpictures */ /* Number of simultaneous subpictures */
#define VOUT_MAX_SUBPICTURES 10 #define VOUT_MAX_SUBPICTURES 5
/* Maximum number of active areas in a rendering buffer. Active areas are areas /* Maximum number of active areas in a rendering buffer. Active areas are areas
* of the picture which need to be cleared before re-using the buffer. If a * of the picture which need to be cleared before re-using the buffer. If a
......
...@@ -2,7 +2,7 @@ ...@@ -2,7 +2,7 @@
* input_ext-dec.h: structures exported to the VideoLAN decoders * input_ext-dec.h: structures exported to the VideoLAN decoders
***************************************************************************** *****************************************************************************
* Copyright (C) 1999, 2000 VideoLAN * Copyright (C) 1999, 2000 VideoLAN
* $Id: input_ext-dec.h,v 1.12 2001/01/12 11:36:49 massiot Exp $ * $Id: input_ext-dec.h,v 1.13 2001/01/12 17:33:18 massiot Exp $
* *
* Authors: * Authors:
* *
...@@ -178,9 +178,9 @@ typedef struct bit_stream_s ...@@ -178,9 +178,9 @@ typedef struct bit_stream_s
*/ */
/***************************************************************************** /*****************************************************************************
* GetByte : reads the next byte in the input stream * GetByte : reads the next byte in the input stream (PRIVATE)
*****************************************************************************/ *****************************************************************************/
static __inline__ byte_t GetByte( bit_stream_t * p_bit_stream ) static __inline__ byte_t _GetByte( bit_stream_t * p_bit_stream )
{ {
/* Are there some bytes left in the current data packet ? */ /* Are there some bytes left in the current data packet ? */
/* could change this test to have a if (! (bytes--)) instead */ /* could change this test to have a if (! (bytes--)) instead */
...@@ -209,7 +209,7 @@ static __inline__ void NeedBits( bit_stream_t * p_bit_stream, int i_bits ) ...@@ -209,7 +209,7 @@ static __inline__ void NeedBits( bit_stream_t * p_bit_stream, int i_bits )
{ {
while ( p_bit_stream->fifo.i_available < i_bits ) while ( p_bit_stream->fifo.i_available < i_bits )
{ {
p_bit_stream->fifo.buffer |= ((WORD_TYPE)GetByte( p_bit_stream )) p_bit_stream->fifo.buffer |= ((WORD_TYPE)_GetByte( p_bit_stream ))
<< (sizeof(WORD_TYPE) - 8 << (sizeof(WORD_TYPE) - 8
- p_bit_stream->fifo.i_available); - p_bit_stream->fifo.i_available);
p_bit_stream->fifo.i_available += 8; p_bit_stream->fifo.i_available += 8;
...@@ -245,7 +245,7 @@ static __inline__ void DumpBits( bit_stream_t * p_bit_stream, int i_bits ) ...@@ -245,7 +245,7 @@ static __inline__ void DumpBits( bit_stream_t * p_bit_stream, int i_bits )
/***************************************************************************** /*****************************************************************************
* ShowBits : return i_bits bits from the bit stream * ShowBits : return i_bits bits from the bit stream
*****************************************************************************/ *****************************************************************************/
static __inline__ WORD_TYPE ShowWord( bit_stream_t * p_bit_stream ) static __inline__ WORD_TYPE _ShowWord( bit_stream_t * p_bit_stream )
{ {
if( p_bit_stream->p_byte <= p_bit_stream->p_end - sizeof(WORD_TYPE) ) if( p_bit_stream->p_byte <= p_bit_stream->p_end - sizeof(WORD_TYPE) )
{ {
...@@ -264,14 +264,14 @@ static __inline__ WORD_TYPE ShowBits( bit_stream_t * p_bit_stream, int i_bits ) ...@@ -264,14 +264,14 @@ static __inline__ WORD_TYPE ShowBits( bit_stream_t * p_bit_stream, int i_bits )
} }
return( (p_bit_stream->fifo.buffer | return( (p_bit_stream->fifo.buffer |
(ShowWord( p_bit_stream ) >> p_bit_stream->fifo.i_available)) (_ShowWord( p_bit_stream ) >> p_bit_stream->fifo.i_available))
>> (8 * sizeof(WORD_TYPE) - i_bits) ); >> (8 * sizeof(WORD_TYPE) - i_bits) );
} }
/***************************************************************************** /*****************************************************************************
* GetWord : returns the next word to be read * GetWord : returns the next word to be read (PRIVATE)
*****************************************************************************/ *****************************************************************************/
static __inline__ WORD_TYPE GetWord( bit_stream_t * p_bit_stream ) static __inline__ WORD_TYPE _GetWord( bit_stream_t * p_bit_stream )
{ {
if( p_bit_stream->p_byte <= p_bit_stream->p_end - sizeof(WORD_TYPE) ) if( p_bit_stream->p_byte <= p_bit_stream->p_end - sizeof(WORD_TYPE) )
{ {
...@@ -297,7 +297,7 @@ static __inline__ void RemoveBits( bit_stream_t * p_bit_stream, int i_bits ) ...@@ -297,7 +297,7 @@ static __inline__ void RemoveBits( bit_stream_t * p_bit_stream, int i_bits )
p_bit_stream->fifo.buffer <<= i_bits; p_bit_stream->fifo.buffer <<= i_bits;
return; return;
} }
p_bit_stream->fifo.buffer = GetWord( p_bit_stream ) p_bit_stream->fifo.buffer = _GetWord( p_bit_stream )
<< ( -p_bit_stream->fifo.i_available ); << ( -p_bit_stream->fifo.i_available );
p_bit_stream->fifo.i_available += sizeof(WORD_TYPE) * 8; p_bit_stream->fifo.i_available += sizeof(WORD_TYPE) * 8;
} }
...@@ -310,12 +310,12 @@ static __inline__ void RemoveBits32( bit_stream_t * p_bit_stream ) ...@@ -310,12 +310,12 @@ static __inline__ void RemoveBits32( bit_stream_t * p_bit_stream )
{ {
if( p_bit_stream->fifo.i_available ) if( p_bit_stream->fifo.i_available )
{ {
p_bit_stream->fifo.buffer = GetWord( p_bit_stream ) p_bit_stream->fifo.buffer = _GetWord( p_bit_stream )
<< (32 - p_bit_stream->fifo.i_available); << (32 - p_bit_stream->fifo.i_available);
} }
else else
{ {
p_bit_stream->fifo.buffer = GetWord( p_bit_stream ); _GetWord( p_bit_stream );
} }
} }
...@@ -336,7 +336,7 @@ static __inline__ WORD_TYPE GetBits( bit_stream_t * p_bit_stream, int i_bits ) ...@@ -336,7 +336,7 @@ static __inline__ WORD_TYPE GetBits( bit_stream_t * p_bit_stream, int i_bits )
} }
i_result = p_bit_stream->fifo.buffer >> (8 * sizeof(WORD_TYPE) - i_bits); i_result = p_bit_stream->fifo.buffer >> (8 * sizeof(WORD_TYPE) - i_bits);
p_bit_stream->fifo.buffer = GetWord( p_bit_stream ); p_bit_stream->fifo.buffer = _GetWord( p_bit_stream );
i_result |= p_bit_stream->fifo.buffer i_result |= p_bit_stream->fifo.buffer
>> (8 * sizeof(WORD_TYPE) >> (8 * sizeof(WORD_TYPE)
+ p_bit_stream->fifo.i_available); + p_bit_stream->fifo.i_available);
...@@ -353,18 +353,21 @@ static __inline__ WORD_TYPE GetBits32( bit_stream_t * p_bit_stream ) ...@@ -353,18 +353,21 @@ static __inline__ WORD_TYPE GetBits32( bit_stream_t * p_bit_stream )
{ {
WORD_TYPE i_result; WORD_TYPE i_result;
i_result = p_bit_stream->fifo.buffer;
p_bit_stream->fifo.buffer = GetWord( p_bit_stream );
i_result |= p_bit_stream->fifo.buffer
>> (p_bit_stream->fifo.i_available);
if( p_bit_stream->fifo.i_available ) if( p_bit_stream->fifo.i_available )
{ {
i_result = p_bit_stream->fifo.buffer;
p_bit_stream->fifo.buffer = _GetWord( p_bit_stream );
i_result |= p_bit_stream->fifo.buffer
>> (p_bit_stream->fifo.i_available);
p_bit_stream->fifo.buffer <<= (8 * sizeof(WORD_TYPE) p_bit_stream->fifo.buffer <<= (8 * sizeof(WORD_TYPE)
- p_bit_stream->fifo.i_available); - p_bit_stream->fifo.i_available);
return( i_result );
}
else
{
return( _GetWord( p_bit_stream ) );
} }
return( i_result );
} }
/***************************************************************************** /*****************************************************************************
...@@ -411,7 +414,7 @@ static __inline__ void GetChunk( bit_stream_t * p_bit_stream, ...@@ -411,7 +414,7 @@ static __inline__ void GetChunk( bit_stream_t * p_bit_stream,
p_bit_stream->pf_next_data_packet( p_bit_stream ); p_bit_stream->pf_next_data_packet( p_bit_stream );
} }
while( (i_available = p_bit_stream->p_end - p_bit_stream->p_byte) while( (i_available = p_bit_stream->p_end - p_bit_stream->p_byte)
<= i_buf_len ); <= i_buf_len && !p_bit_stream->p_decoder_fifo->b_die );
if( i_buf_len ) if( i_buf_len )
{ {
......
...@@ -2,7 +2,7 @@ ...@@ -2,7 +2,7 @@
* input_dec.c: Functions for the management of decoders * input_dec.c: Functions for the management of decoders
***************************************************************************** *****************************************************************************
* Copyright (C) 1999, 2000 VideoLAN * Copyright (C) 1999, 2000 VideoLAN
* $Id: input_dec.c,v 1.5 2001/01/12 14:49:55 sam Exp $ * $Id: input_dec.c,v 1.6 2001/01/12 17:33:18 massiot Exp $
* *
* Authors: Christophe Massiot <massiot@via.ecp.fr> * Authors: Christophe Massiot <massiot@via.ecp.fr>
* *
...@@ -26,6 +26,7 @@ ...@@ -26,6 +26,7 @@
*****************************************************************************/ *****************************************************************************/
#include "defs.h" #include "defs.h"
#include <stdlib.h>
#include "config.h" #include "config.h"
#include "common.h" #include "common.h"
#include "threads.h" #include "threads.h"
...@@ -72,6 +73,13 @@ void input_EndDecoder( input_thread_t * p_input, es_descriptor_t * p_es ) ...@@ -72,6 +73,13 @@ void input_EndDecoder( input_thread_t * p_input, es_descriptor_t * p_es )
DECODER_FIFO_START( *p_es->p_decoder_fifo ) ); DECODER_FIFO_START( *p_es->p_decoder_fifo ) );
DECODER_FIFO_INCSTART( *p_es->p_decoder_fifo ); DECODER_FIFO_INCSTART( *p_es->p_decoder_fifo );
} }
/* Destroy the lock and cond */
vlc_cond_destroy( &p_es->p_decoder_fifo->data_wait );
vlc_mutex_destroy( &p_es->p_decoder_fifo->data_lock );
free( p_es->p_decoder_fifo );
p_es->p_decoder_fifo = NULL;
} }
/***************************************************************************** /*****************************************************************************
......
...@@ -2,7 +2,7 @@ ...@@ -2,7 +2,7 @@
* input_programs.c: es_descriptor_t, pgrm_descriptor_t management * input_programs.c: es_descriptor_t, pgrm_descriptor_t management
***************************************************************************** *****************************************************************************
* Copyright (C) 1999, 2000 VideoLAN * Copyright (C) 1999, 2000 VideoLAN
* $Id: input_programs.c,v 1.24 2001/01/12 14:49:55 sam Exp $ * $Id: input_programs.c,v 1.25 2001/01/12 17:33:18 massiot Exp $
* *
* Authors: * Authors:
* *
...@@ -75,19 +75,15 @@ void input_InitStream( input_thread_t * p_input, size_t i_data_len ) ...@@ -75,19 +75,15 @@ void input_InitStream( input_thread_t * p_input, size_t i_data_len )
*****************************************************************************/ *****************************************************************************/
void input_EndStream( input_thread_t * p_input ) void input_EndStream( input_thread_t * p_input )
{ {
int i;
/* Free all programs and associated ES, and associated decoders. */ /* Free all programs and associated ES, and associated decoders. */
for( i = 0; i < p_input->stream.i_pgrm_number; i++ ) while( p_input->stream.i_pgrm_number )
{ {
/* Don't put i instead of 0 !! */
input_DelProgram( p_input, p_input->stream.pp_programs[0] ); input_DelProgram( p_input, p_input->stream.pp_programs[0] );
} }
/* Free standalone ES */ /* Free standalone ES */
for( i = 0; i < p_input->stream.i_es_number; i++ ) while( p_input->stream.i_es_number )
{ {
/* Don't put i instead of 0 !! */
input_DelES( p_input, p_input->stream.pp_es[0] ); input_DelES( p_input, p_input->stream.pp_es[0] );
} }
} }
...@@ -187,16 +183,15 @@ pgrm_descriptor_t * input_AddProgram( input_thread_t * p_input, ...@@ -187,16 +183,15 @@ pgrm_descriptor_t * input_AddProgram( input_thread_t * p_input,
*****************************************************************************/ *****************************************************************************/
void input_DelProgram( input_thread_t * p_input, pgrm_descriptor_t * p_pgrm ) void input_DelProgram( input_thread_t * p_input, pgrm_descriptor_t * p_pgrm )
{ {
int i_index, i_pgrm_index; int i_pgrm_index;
ASSERT( p_pgrm ); ASSERT( p_pgrm );
intf_DbgMsg("Deleting description for pgrm %d", p_pgrm->i_number); intf_DbgMsg("Deleting description for pgrm %d", p_pgrm->i_number);
/* Free the structures that describe the es that belongs to that program */ /* Free the structures that describe the es that belongs to that program */
for( i_index = 0; i_index < p_pgrm->i_es_number; i_index++ ) while( p_pgrm->i_es_number )
{ {
/* Don't put i_index instead of 0 !! */
input_DelES( p_input, p_pgrm->pp_es[0] ); input_DelES( p_input, p_pgrm->pp_es[0] );
} }
...@@ -342,12 +337,6 @@ void input_DelES( input_thread_t * p_input, es_descriptor_t * p_es ) ...@@ -342,12 +337,6 @@ void input_DelES( input_thread_t * p_input, es_descriptor_t * p_es )
if( p_es->p_decoder_fifo != NULL ) if( p_es->p_decoder_fifo != NULL )
{ {
input_EndDecoder( p_input, p_es ); input_EndDecoder( p_input, p_es );
/* Destroy the lock and cond */
vlc_cond_destroy( &p_es->p_decoder_fifo->data_wait );
vlc_mutex_destroy( &p_es->p_decoder_fifo->data_lock );
free( p_es->p_decoder_fifo );
} }
/* Remove this ES from the description of the program if it is associated to /* Remove this ES from the description of the program if it is associated to
......
...@@ -144,174 +144,159 @@ static void RunThread( spudec_thread_t *p_spudec ) ...@@ -144,174 +144,159 @@ static void RunThread( spudec_thread_t *p_spudec )
boolean_t b_valid; boolean_t b_valid;
subpicture_t * p_spu = NULL; subpicture_t * p_spu = NULL;
while( !DECODER_FIFO_ISEMPTY(*p_spudec->p_fifo) ) /* wait for the next SPU ID.
* XXX: We trash 0xff bytes since they probably come from
* an incomplete previous packet */
do
{ {
/* wait for the next SPU ID. i_packet_size = GetBits( &p_spudec->bit_stream, 8 );
* XXX: We trash 0xff bytes since they probably come from }
* an incomplete previous packet */ while( i_packet_size == 0xff );
do
{ if( p_spudec->p_fifo->b_die )
i_packet_size = GetByte( &p_spudec->bit_stream ); {
} break;
while( i_packet_size == 0xff ); }
/* the total size - should equal the sum of the
* PES packet size that form the SPU packet */
i_packet_size = i_packet_size << 8
| GetBits( &p_spudec->bit_stream, 8 );
/* the RLE stuff size */
i_rle_size = GetBits( &p_spudec->bit_stream, 16 );
/* if the values we got aren't too strange, decode the data */
if( i_rle_size < i_packet_size )
{
/* allocate the subpicture.
* FIXME: we should check if the allocation failed */
p_spu = vout_CreateSubPicture( p_spudec->p_vout,
DVD_SUBPICTURE, i_rle_size );
/* get display time */
p_spu->begin_date = p_spu->end_date
= DECODER_FIFO_START(*p_spudec->p_fifo)->i_pts;
/* get RLE data, skip 4 bytes for the first two read offsets */
GetChunk( &p_spudec->bit_stream, p_spu->p_data,
i_rle_size - 4 );
if( p_spudec->p_fifo->b_die ) if( p_spudec->p_fifo->b_die )
{ {
goto bad_packet; break;
} }
/* the total size - should equal the sum of the /* continue parsing after the RLE part */
* PES packet size that form the SPU packet */ i_index = i_rle_size;
i_packet_size = i_packet_size << 8
| GetByte( &p_spudec->bit_stream );
/* the RLE stuff size */ /* assume packet is valid */
i_rle_size = GetByte( &p_spudec->bit_stream ) << 8 b_valid = 1;
| GetByte( &p_spudec->bit_stream );
/* if the values we got aren't too strange, decode the data */ /* getting the control part */
if( i_rle_size < i_packet_size ) do
{ {
/* allocate the subpicture. unsigned char i_cmd;
* FIXME: we should check if the allocation failed */ u16 i_date;
p_spu = vout_CreateSubPicture( p_spudec->p_vout,
DVD_SUBPICTURE, i_rle_size );
/* get display time */
p_spu->begin_date = p_spu->end_date
= DECODER_FIFO_START(*p_spudec->p_fifo)->i_pts;
/* get RLE data, skip 4 bytes for the first two read offsets */
GetChunk( &p_spudec->bit_stream, p_spu->p_data,
i_rle_size - 4 );
if( p_spudec->p_fifo->b_die )
{
goto bad_packet;
}
/* continue parsing after the RLE part */ /* Get the sequence date */
i_index = i_rle_size; i_date = GetBits( &p_spudec->bit_stream, 16 );
/* assume packet is valid */ /* Next offset */
b_valid = 1; i_next = GetBits( &p_spudec->bit_stream, 16 );
i_index += 4;
/* getting the control part */
do do
{ {
unsigned char i_cmd; i_cmd = GetBits( &p_spudec->bit_stream, 8 );
unsigned int i_word, i_date; i_index++;
/* Get the sequence date */
i_date = GetByte( &p_spudec->bit_stream ) << 8
| GetByte( &p_spudec->bit_stream );
/* Next offset */
i_next = GetByte( &p_spudec->bit_stream ) << 8
| GetByte( &p_spudec->bit_stream );
i_index += 4;
do switch( i_cmd )
{ {
i_cmd = GetByte( &p_spudec->bit_stream ); case SPU_CMD_FORCE_DISPLAY:
i_index++; /* 00 (force displaying) */
break;
switch( i_cmd ) /* FIXME: here we have to calculate dates. It's
{ * around i_date * 12000 but I don't know
case SPU_CMD_FORCE_DISPLAY: * how much exactly.
/* 00 (force displaying) */ */
break; case SPU_CMD_START_DISPLAY:
/* FIXME: here we have to calculate dates. It's /* 01 (start displaying) */
* around i_date * 12000 but I don't know p_spu->begin_date += ( i_date * 12000 );
* how much exactly. break;
*/ case SPU_CMD_STOP_DISPLAY:
case SPU_CMD_START_DISPLAY: /* 02 (stop displaying) */
/* 01 (start displaying) */ p_spu->end_date += ( i_date * 12000 );
p_spu->begin_date += ( i_date * 12000 ); break;
break; case SPU_CMD_SET_PALETTE:
case SPU_CMD_STOP_DISPLAY: /* 03xxxx (palette) - trashed */
/* 02 (stop displaying) */ RemoveBits( &p_spudec->bit_stream, 16 );
p_spu->end_date += ( i_date * 12000 ); i_index += 2;
break; break;
case SPU_CMD_SET_PALETTE: case SPU_CMD_SET_ALPHACHANNEL:
/* 03xxxx (palette) */ /* 04xxxx (alpha channel) - trashed */
i_word = GetByte( &p_spudec->bit_stream ) << 8 RemoveBits( &p_spudec->bit_stream, 16 );
| GetByte( &p_spudec->bit_stream ); i_index += 2;
i_index += 2; break;
break; case SPU_CMD_SET_COORDINATES:
case SPU_CMD_SET_ALPHACHANNEL: /* 05xxxyyyxxxyyy (coordinates) */
/* 04xxxx (alpha channel) */ p_spu->i_x =
i_word = GetByte( &p_spudec->bit_stream ) << 8 GetBits( &p_spudec->bit_stream, 12 );
| GetByte( &p_spudec->bit_stream );
i_index += 2; p_spu->i_width = p_spu->i_x -
break; GetBits( &p_spudec->bit_stream, 12 ) + 1;
case SPU_CMD_SET_COORDINATES:
/* 05xxxyyyxxxyyy (coordinates) */ p_spu->i_y =
i_word = GetByte( &p_spudec->bit_stream ); GetBits( &p_spudec->bit_stream, 12 );
p_spu->i_x = (i_word << 4)
| GetBits( &p_spudec->bit_stream, 4 ); p_spu->i_height = p_spu->i_y -
GetBits( &p_spudec->bit_stream, 12 ) + 1;
i_word = GetBits( &p_spudec->bit_stream, 4 );
p_spu->i_width = p_spu->i_x - ( (i_word << 8) i_index += 6;
| GetBits( &p_spudec->bit_stream, 8 ) ) + 1; break;
case SPU_CMD_SET_OFFSETS:
i_word = GetBits( &p_spudec->bit_stream, 8 ); /* 06xxxxyyyy (byte offsets) */
p_spu->i_y = (i_word << 4) p_spu->type.spu.i_offset[0] =
| GetBits( &p_spudec->bit_stream, 4 ); GetBits( &p_spudec->bit_stream, 16 ) - 4;
p_spu->type.spu.i_offset[1] =
i_word = GetBits( &p_spudec->bit_stream, 4 ); GetBits( &p_spudec->bit_stream, 16 ) - 4;
p_spu->i_height = p_spu->i_y - ( (i_word << 8) i_index += 4;
| GetByte( &p_spudec->bit_stream ) ) + 1; break;
case SPU_CMD_END:
i_index += 6; /* ff (end) */
break; break;
case SPU_CMD_SET_OFFSETS: default:
/* 06xxxxyyyy (byte offsets) */ /* ?? (unknown command) */
p_spu->type.spu.i_offset[0] = intf_ErrMsg( "spudec: unknown command 0x%.2x",
( GetByte( &p_spudec->bit_stream ) << 8 i_cmd );
| GetByte( &p_spudec->bit_stream ) ) - 4; b_valid = 0;
p_spu->type.spu.i_offset[1] = break;
( GetByte( &p_spudec->bit_stream ) << 8
| GetByte( &p_spudec->bit_stream ) ) - 4;
i_index += 4;
break;
case SPU_CMD_END:
/* ff (end) */
break;
default:
/* ?? (unknown command) */
intf_ErrMsg( "spudec: unknown command 0x%.2x",
i_cmd );
b_valid = 0;
break;
}
} }
while( b_valid && ( i_cmd != SPU_CMD_END ) );
} }
while( b_valid && ( i_index == i_next ) ); while( b_valid && ( i_cmd != SPU_CMD_END ) );
}
while( b_valid && ( i_index == i_next ) );
if( b_valid ) if( b_valid )
{ {
/* SPU is finished - we can tell the video output /* SPU is finished - we can tell the video output
* to display it */ * to display it */
vout_DisplaySubPicture( p_spudec->p_vout, p_spu ); vout_DisplaySubPicture( p_spudec->p_vout, p_spu );
}
else
{
vout_DestroySubPicture( p_spudec->p_vout, p_spu );
}
} }
else else
{ {
/* Unexpected PES packet - trash it */ vout_DestroySubPicture( p_spudec->p_vout, p_spu );
intf_ErrMsg( "spudec: trying to recover from bad packet" );
vlc_mutex_lock( &p_spudec->p_fifo->data_lock );
p_spudec->p_fifo->pf_delete_pes( p_spudec->p_fifo->p_packets_mgt,
DECODER_FIFO_START(*p_spudec->p_fifo) );
DECODER_FIFO_INCSTART( *p_spudec->p_fifo );
vlc_mutex_unlock( &p_spudec->p_fifo->data_lock );
} }
bad_packet: }
else
{
/* Unexpected PES packet - trash it */
intf_ErrMsg( "spudec: trying to recover from bad packet" );
vlc_mutex_lock( &p_spudec->p_fifo->data_lock );
p_spudec->p_fifo->pf_delete_pes( p_spudec->p_fifo->p_packets_mgt,
DECODER_FIFO_START(*p_spudec->p_fifo) );
DECODER_FIFO_INCSTART( *p_spudec->p_fifo );
vlc_mutex_unlock( &p_spudec->p_fifo->data_lock );
} }
} }
......
...@@ -2,7 +2,7 @@ ...@@ -2,7 +2,7 @@
* video_parser.c : video parser thread * video_parser.c : video parser thread
***************************************************************************** *****************************************************************************
* Copyright (C) 1999, 2000 VideoLAN * Copyright (C) 1999, 2000 VideoLAN
* $Id: video_parser.c,v 1.64 2001/01/10 19:22:11 massiot Exp $ * $Id: video_parser.c,v 1.65 2001/01/12 17:33:18 massiot Exp $
* *
* Authors: Christophe Massiot <massiot@via.ecp.fr> * Authors: Christophe Massiot <massiot@via.ecp.fr>
* Samuel Hocevar <sam@via.ecp.fr> * Samuel Hocevar <sam@via.ecp.fr>
...@@ -308,6 +308,18 @@ static void EndThread( vpar_thread_t *p_vpar ) ...@@ -308,6 +308,18 @@ static void EndThread( vpar_thread_t *p_vpar )
intf_DbgMsg("vpar debug: destroying video parser thread %p", p_vpar); intf_DbgMsg("vpar debug: destroying video parser thread %p", p_vpar);
/* Release used video buffers. */
if( p_vpar->sequence.p_forward != NULL )
{
vout_UnlinkPicture( p_vpar->p_vout, p_vpar->sequence.p_forward );
}
if( p_vpar->sequence.p_backward != NULL )
{
vout_DatePicture( p_vpar->p_vout, p_vpar->sequence.p_backward,
vpar_SynchroDate( p_vpar ) );
vout_UnlinkPicture( p_vpar->p_vout, p_vpar->sequence.p_backward );
}
#ifdef STATS #ifdef STATS
intf_Msg("vpar stats: %d loops among %d sequence(s)", intf_Msg("vpar stats: %d loops among %d sequence(s)",
p_vpar->c_loops, p_vpar->c_sequences); p_vpar->c_loops, p_vpar->c_sequences);
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment