/* Bitstream manipulation */
static int Ogg_ReadPage ( demux_t *, ogg_page * );
-static void Ogg_UpdatePCR ( logical_stream_t *, ogg_packet * );
+static void Ogg_UpdatePCR ( demux_t *, logical_stream_t *, ogg_packet * );
static void Ogg_DecodePacket ( demux_t *, logical_stream_t *, ogg_packet * );
static int Ogg_OpusPacketDuration( logical_stream_t *, ogg_packet * );
for( i_stream = 0; i_stream < p_sys->i_streams; i_stream++ )
{
logical_stream_t *p_stream = p_sys->pp_stream[i_stream];
- if ( p_stream->b_have_updated_format && p_stream->p_es )
- {
- p_stream->b_have_updated_format = false;
- if ( p_stream->p_skel ) Ogg_ApplySkeleton( p_stream );
- msg_Dbg( p_demux, "Resetting format for stream %d", i_stream );
- es_out_Control( p_demux->out, ES_OUT_SET_ES_FMT,
- p_stream->p_es, &p_stream->fmt );
- }
+ Ogg_ApplySkeleton( p_stream );
}
}
}
DemuxDebug(
if ( p_stream->fmt.i_cat == VIDEO_ES )
- msg_Dbg(p_demux, "DEMUX READ pageno %ld g%"PRId64" (%d packets) cont %d %ld bytes eos %d ",
+ msg_Dbg(p_demux, "DEMUX READ pageno %ld g%"PRId64" (%d packets) cont %d %ld bytes",
ogg_page_pageno( &p_sys->current_page ),
ogg_page_granulepos( &p_sys->current_page ),
ogg_page_packets( &p_sys->current_page ),
ogg_page_continued(&p_sys->current_page),
- p_sys->current_page.body_len, p_sys->i_eos )
+ p_sys->current_page.body_len )
);
while( ogg_stream_packetout( &p_stream->os, &oggpacket ) > 0 )
{
/* If synchro is re-initialized we need to drop all the packets
* until we find a new dated one. */
- Ogg_UpdatePCR( p_stream, &oggpacket );
+ Ogg_UpdatePCR( p_demux, p_stream, &oggpacket );
}
if( p_stream->i_pcr >= 0 )
/* if a page was waiting, it's now processed */
p_sys->b_page_waiting = false;
- p_sys->b_preparsing_done = true;
+ if ( p_sys->p_skelstream && !p_sys->p_skelstream->b_finished )
+ p_sys->b_preparsing_done = false;
+ else
+ p_sys->b_preparsing_done = true;
p_sys->i_pcr = -1;
for( i_stream = 0; i_stream < p_sys->i_streams; i_stream++ )
{
logical_stream_t *p_stream = p_sys->pp_stream[i_stream];
- if ( p_stream->b_force_backup )
+ if ( p_sys->b_preparsing_done && p_stream->b_initializing )
{
/* We have 1 or more streams needing more than 1 page for preparsing */
p_sys->b_preparsing_done = false;
* Ogg_UpdatePCR: update the PCR (90kHz program clock reference) for the
* current stream.
****************************************************************************/
-static void Ogg_UpdatePCR( logical_stream_t *p_stream,
+static void Ogg_UpdatePCR( demux_t *p_demux, logical_stream_t *p_stream,
ogg_packet *p_oggpacket )
{
+ demux_sys_t *p_ogg = p_demux->p_sys;
p_stream->i_end_trim = 0;
/* Convert the granulepos into a pcr */
p_stream->i_pcr = sample * CLOCK_FREQ / p_stream->f_rate;
}
- p_stream->i_pcr += VLC_TS_0;
+ if ( !p_ogg->i_pcr_offset )
+ p_stream->i_pcr += VLC_TS_0;
+ else
+ p_stream->i_pcr += p_ogg->i_pcr_offset;
p_stream->i_interpolated_pcr = p_stream->i_pcr;
}
else
sample = 0;
p_stream->i_interpolated_pcr =
VLC_TS_0 + sample * CLOCK_FREQ / p_stream->f_rate;
+ p_stream->i_interpolated_pcr += p_ogg->i_pcr_offset;
}
else if( p_stream->fmt.i_bitrate )
{
p_stream->i_interpolated_pcr +=
( p_oggpacket->bytes * CLOCK_FREQ /
p_stream->fmt.i_bitrate / 8 );
+ p_stream->i_interpolated_pcr += p_ogg->i_pcr_offset;
}
}
p_stream->i_previous_granulepos = p_oggpacket->granulepos;
else
p_stream->fmt.i_extra = 0;
- if( Ogg_LogicalStreamResetEsFormat( p_demux, p_stream ) )
- {
- if ( p_ogg->p_skelstream )
- {
- /* We delay until eos is reached on skeleton.
- * There should only be headers, as no data page is
- * allowed before skeleton's eos.
- * Skeleton data is appended to fmt on skeleton eos.
- */
- p_stream->b_have_updated_format = true;
- }
- else
- {
- if ( p_stream->p_es )
- /* Otherwise we set config from first headers */
- es_out_Control( p_demux->out, ES_OUT_SET_ES_FMT,
- p_stream->p_es, &p_stream->fmt );
- }
- }
if( p_stream->i_headers > 0 )
Ogg_ExtractMeta( p_demux, & p_stream->fmt,
p_stream->p_headers, p_stream->i_headers );
b_selected = false; /* Discard the header packet */
}
+ else
+ p_stream->b_initializing = false;
/* Convert the pcr into a pts */
if( p_stream->fmt.i_codec == VLC_CODEC_VORBIS ||
{
if( p_stream->i_pcr >= 0 )
{
- /* This is for streams where the granulepos of the header packets
- * doesn't match these of the data packets (eg. ogg web radios). */
- if( p_stream->i_previous_pcr == 0 &&
- p_stream->i_pcr > 3 * DEFAULT_PTS_DELAY )
- {
-
- /* Call the pace control */
- es_out_Control( p_demux->out, ES_OUT_SET_PCR,
- VLC_TS_0 + p_stream->i_pcr );
- }
-
p_stream->i_previous_pcr = p_stream->i_pcr;
-
/* The granulepos is the end date of the sample */
i_pts = p_stream->i_pcr;
}
/* Convert the granulepos into the next pcr */
i_interpolated_pts = p_stream->i_interpolated_pcr;
- Ogg_UpdatePCR( p_stream, p_oggpacket );
-
- /* SPU streams are typically discontinuous, do not mind large gaps */
- if( p_stream->fmt.i_cat != SPU_ES )
- {
- if( p_stream->i_pcr >= 0 )
- {
- /* This is for streams where the granulepos of the header packets
- * doesn't match these of the data packets (eg. ogg web radios). */
- if( p_stream->i_previous_pcr == 0 &&
- p_stream->i_pcr > 3 * DEFAULT_PTS_DELAY )
- {
-
- /* Call the pace control */
- es_out_Control( p_demux->out, ES_OUT_SET_PCR, VLC_TS_0 + p_stream->i_pcr );
- }
- }
- }
+ Ogg_UpdatePCR( p_demux, p_stream, p_oggpacket );
if( p_stream->fmt.i_codec != VLC_CODEC_VORBIS &&
p_stream->fmt.i_codec != VLC_CODEC_SPEEX &&
p_block->i_buffer = 0;
}
- if ( p_stream->b_reusing_with_other_fmt )
- {
- p_stream->b_reusing_with_other_fmt = false;
- p_block->i_flags |= BLOCK_FLAG_DISCONTINUITY;
- }
if( p_stream->fmt.i_codec == VLC_CODEC_TARKIN )
{
es_format_Init( &p_stream->fmt, 0, 0 );
es_format_Init( &p_stream->fmt_old, 0, 0 );
+ p_stream->b_initializing = true;
/* Setup the logical stream */
p_stream->i_serial_no = ogg_page_serialno( &p_ogg->current_page );
}
/* we'll need to get all headers */
- p_ogg->pp_stream[i_stream]->b_initializing |= p_ogg->pp_stream[i_stream]->b_force_backup;
+ p_ogg->pp_stream[i_stream]->b_initializing &= p_ogg->pp_stream[i_stream]->b_force_backup;
if( Ogg_ReadPage( p_demux, &p_ogg->current_page ) != VLC_SUCCESS )
return VLC_EGENERIC;
p_stream->b_finished = false;
p_stream->b_reinit = false;
p_stream->b_initializing = false;
-
es_format_Copy( &p_stream->fmt_old, &p_old_stream->fmt );
- if ( !es_format_IsSimilar( &p_stream->fmt_old, &p_old_stream->fmt ) )
- {
- msg_Dbg( p_demux, "recreating decoders using SET_FMT" );
- es_out_Control( p_demux->out, ES_OUT_SET_ES_FMT,
- p_stream->p_es, &p_stream->fmt );
- p_stream->b_reusing_with_other_fmt = true;
- }
-
p_old_stream->p_es = NULL;
p_old_stream = NULL;
+ es_out_Control( p_demux->out, ES_OUT_SET_ES_FMT,
+ p_stream->p_es, &p_stream->fmt );
}
else
{
}
}
-
-
/****************************************************************************
* Ogg_BeginningOfStream: Look for Beginning of Stream ogg pages and add
* Elementary streams.
p_ogg->skeleton.major = 0;
p_ogg->skeleton.minor = 0;
p_ogg->b_preparsing_done = false;
+ p_ogg->i_pcr_offset = p_ogg->i_pcr;
/* */
if( p_ogg->p_meta )