ogg.c 130 KB
Newer Older
1
/*****************************************************************************
Derk-Jan Hartman's avatar
Derk-Jan Hartman committed
2
 * ogg.c : ogg stream demux module for vlc
3
 *****************************************************************************
Jean-Baptiste Kempf's avatar
LGPL  
Jean-Baptiste Kempf committed
4
 * Copyright (C) 2001-2007 VLC authors and VideoLAN
5
 * $Id$
6
 *
7 8
 * Authors: Gildas Bazin <gbazin@netcourrier.com>
 *          Andre Pang <Andre.Pang@csiro.au> (Annodex support)
Sam Hocevar's avatar
Sam Hocevar committed
9
 *
Jean-Baptiste Kempf's avatar
LGPL  
Jean-Baptiste Kempf committed
10 11 12
 * This program is free software; you can redistribute it and/or modify it
 * under the terms of the GNU Lesser General Public License as published by
 * the Free Software Foundation; either version 2.1 of the License, or
13
 * (at your option) any later version.
Sam Hocevar's avatar
Sam Hocevar committed
14
 *
15 16
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
Jean-Baptiste Kempf's avatar
LGPL  
Jean-Baptiste Kempf committed
17 18
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
 * GNU Lesser General Public License for more details.
19
 *
Jean-Baptiste Kempf's avatar
LGPL  
Jean-Baptiste Kempf committed
20 21 22
 * You should have received a copy of the GNU Lesser General Public License
 * along with this program; if not, write to the Free Software Foundation,
 * Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA.
23 24 25 26 27
 *****************************************************************************/

/*****************************************************************************
 * Preamble
 *****************************************************************************/
28 29 30 31
#ifdef HAVE_CONFIG_H
# include "config.h"
#endif

32
#include <vlc_common.h>
33
#include <vlc_plugin.h>
34
#include <vlc_access.h>
Clément Stenac's avatar
Clément Stenac committed
35
#include <vlc_demux.h>
36 37
#include <vlc_meta.h>
#include <vlc_input.h>
38 39 40

#include <ogg/ogg.h>

Clément Stenac's avatar
Clément Stenac committed
41 42
#include <vlc_codecs.h>
#include <vlc_bits.h>
43
#include "xiph.h"
44
#include "xiph_metadata.h"
45
#include "ogg.h"
46
#include "oggseek.h"
47
#include "opus.h"
48

49 50 51 52 53 54
/*****************************************************************************
 * Module descriptor
 *****************************************************************************/
static int  Open ( vlc_object_t * );
static void Close( vlc_object_t * );

55 56 57 58 59 60 61 62 63
vlc_module_begin ()
    set_shortname ( "OGG" )
    set_description( N_("OGG demuxer" ) )
    set_category( CAT_INPUT )
    set_subcategory( SUBCAT_INPUT_DEMUX )
    set_capability( "demux", 50 )
    set_callbacks( Open, Close )
    add_shortcut( "ogg" )
vlc_module_end ()
64

65 66

/*****************************************************************************
Sam Hocevar's avatar
Sam Hocevar committed
67
 * Definitions of structures and functions used by this plugins
68 69
 *****************************************************************************/

70
/* OggDS headers for the new header format (used in ogm files) */
71
typedef struct
72 73 74
{
    ogg_int32_t width;
    ogg_int32_t height;
75
} stream_header_video_t;
Sam Hocevar's avatar
Sam Hocevar committed
76

77
typedef struct
78 79
{
    ogg_int16_t channels;
80
    ogg_int16_t padding;
81 82
    ogg_int16_t blockalign;
    ogg_int32_t avgbytespersec;
83
} stream_header_audio_t;
84

85
typedef struct
86 87 88 89 90 91 92 93 94 95 96 97
{
    char        streamtype[8];
    char        subtype[4];

    ogg_int32_t size;                               /* size of the structure */

    ogg_int64_t time_unit;                              /* in reference time */
    ogg_int64_t samples_per_unit;
    ogg_int32_t default_len;                                /* in media time */

    ogg_int32_t buffersize;
    ogg_int16_t bits_per_sample;
98
    ogg_int16_t padding;
99 100 101 102

    union
    {
        /* Video specific */
103
        stream_header_video_t video;
104
        /* Audio specific */
105
        stream_header_audio_t audio;
106
    } sh;
107
} stream_header_t;
108

109
#define VORBIS_HEADER_IDENTIFICATION 1
110 111 112 113
#define VORBIS_HEADER_COMMENT        2
#define VORBIS_HEADER_SETUP          3
#define VORBIS_HEADER_TO_FLAG(i)     (1 << (i - 1))
#define VORBIS_HEADERS_VALID(p_stream) \
114
    ((p_stream->special.vorbis.i_headers_flags & 0x07) == 0x07) // 0b111
115

116 117 118
/*****************************************************************************
 * Local prototypes
 *****************************************************************************/
119 120
static int  Demux  ( demux_t * );
static int  Control( demux_t *, int, va_list );
121 122

/* Bitstream manipulation */
123
static int  Ogg_ReadPage     ( demux_t *, ogg_page * );
124
static void Ogg_UpdatePCR    ( demux_t *, logical_stream_t *, ogg_packet * );
125
static void Ogg_DecodePacket ( demux_t *, logical_stream_t *, ogg_packet * );
126
static unsigned Ogg_OpusPacketDuration( ogg_packet * );
127
static void Ogg_SendOrQueueBlocks( demux_t *, logical_stream_t *, block_t * );
128

129
static void Ogg_CreateES( demux_t *p_demux );
130 131 132
static int Ogg_BeginningOfStream( demux_t *p_demux );
static int Ogg_FindLogicalStreams( demux_t *p_demux );
static void Ogg_EndOfStream( demux_t *p_demux );
133

134 135 136
/* */
static void Ogg_LogicalStreamDelete( demux_t *p_demux, logical_stream_t *p_stream );
static bool Ogg_LogicalStreamResetEsFormat( demux_t *p_demux, logical_stream_t *p_stream );
137
static void Ogg_ResetStream( logical_stream_t *p_stream );
138

139
/* */
140
static void Ogg_ExtractMeta( demux_t *p_demux, es_format_t *p_fmt, const uint8_t *p_headers, int i_headers );
141

142
/* Logical bitstream headers */
Tristan Matthews's avatar
Tristan Matthews committed
143
static bool Ogg_ReadDaalaHeader( logical_stream_t *, ogg_packet * );
144 145 146
static bool Ogg_ReadTheoraHeader( logical_stream_t *, ogg_packet * );
static bool Ogg_ReadVorbisHeader( logical_stream_t *, ogg_packet * );
static bool Ogg_ReadSpeexHeader( logical_stream_t *, ogg_packet * );
147
static void Ogg_ReadOpusHeader( logical_stream_t *, ogg_packet * );
148
static bool Ogg_ReadKateHeader( logical_stream_t *, ogg_packet * );
149
static bool Ogg_ReadFlacStreamInfo( demux_t *, logical_stream_t *, ogg_packet * );
150
static void Ogg_ReadAnnodexHeader( demux_t *, logical_stream_t *, ogg_packet * );
151
static bool Ogg_ReadDiracHeader( logical_stream_t *, ogg_packet * );
152
static bool Ogg_ReadVP8Header( demux_t *, logical_stream_t *, ogg_packet * );
153
static void Ogg_ReadSkeletonHeader( demux_t *, logical_stream_t *, ogg_packet * );
154
static bool Ogg_ReadOggSpotsHeader( logical_stream_t *, ogg_packet * );
155 156 157 158 159 160

/* Skeleton */
static void Ogg_ReadSkeletonBones( demux_t *, ogg_packet * );
static void Ogg_ReadSkeletonIndex( demux_t *, ogg_packet * );
static void Ogg_FreeSkeleton( ogg_skeleton_t * );
static void Ogg_ApplySkeleton( logical_stream_t * );
161

162 163 164 165 166 167
/* Special decoding */
static void Ogg_CleanSpecificData( logical_stream_t * );
#ifdef HAVE_LIBVORBIS
static void Ogg_DecodeVorbisHeader( logical_stream_t *, ogg_packet *, int );
#endif

168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195
static void fill_channels_info(audio_format_t *audio)
{
    static const int pi_channels_map[9] =
    {
        0,
        AOUT_CHAN_CENTER,
        AOUT_CHAN_LEFT | AOUT_CHAN_RIGHT,
        AOUT_CHAN_CENTER | AOUT_CHAN_LEFT | AOUT_CHAN_RIGHT,
        AOUT_CHAN_LEFT | AOUT_CHAN_RIGHT | AOUT_CHAN_REARLEFT
            | AOUT_CHAN_REARRIGHT,
        AOUT_CHAN_LEFT | AOUT_CHAN_RIGHT | AOUT_CHAN_CENTER
            | AOUT_CHAN_REARLEFT | AOUT_CHAN_REARRIGHT,
        AOUT_CHAN_LEFT | AOUT_CHAN_RIGHT | AOUT_CHAN_CENTER
            | AOUT_CHAN_REARLEFT | AOUT_CHAN_REARRIGHT | AOUT_CHAN_LFE,
        AOUT_CHAN_LEFT | AOUT_CHAN_RIGHT | AOUT_CHAN_CENTER
            | AOUT_CHAN_REARCENTER | AOUT_CHAN_MIDDLELEFT
            | AOUT_CHAN_MIDDLERIGHT | AOUT_CHAN_LFE,
        AOUT_CHAN_LEFT | AOUT_CHAN_RIGHT | AOUT_CHAN_CENTER | AOUT_CHAN_REARLEFT
            | AOUT_CHAN_REARRIGHT | AOUT_CHAN_MIDDLELEFT | AOUT_CHAN_MIDDLERIGHT
            | AOUT_CHAN_LFE,
    };

    unsigned chans = audio->i_channels;
    if (chans < sizeof(pi_channels_map) / sizeof(pi_channels_map[0]))
        audio->i_physical_channels =
        audio->i_original_channels = pi_channels_map[chans];
}

196 197 198 199
/* Special TS value: don't send or derive any pts/pcr from it.
   Represents TS state prior first known valid timestamp */
#define VLC_TS_UNKNOWN (VLC_TS_INVALID - 1)

200
/*****************************************************************************
201
 * Open: initializes ogg demux structures
202
 *****************************************************************************/
203
static int Open( vlc_object_t * p_this )
204
{
205
    demux_t *p_demux = (demux_t *)p_this;
206
    demux_sys_t    *p_sys;
207
    const uint8_t  *p_peek;
208

209
    /* Check if we are dealing with an ogg stream */
210
    if( vlc_stream_Peek( p_demux->s, &p_peek, 4 ) < 4 ) return VLC_EGENERIC;
211
    if( !p_demux->obj.force && memcmp( p_peek, "OggS", 4 ) )
212
    {
213 214 215 216 217 218 219 220 221 222 223 224 225
        char *psz_mime = stream_ContentType( p_demux->s );
        if( !psz_mime )
        {
            return VLC_EGENERIC;
        }
        else if ( strcmp( psz_mime, "application/ogg" ) &&
                  strcmp( psz_mime, "video/ogg" ) &&
                  strcmp( psz_mime, "audio/ogg" ) )
        {
            free( psz_mime );
            return VLC_EGENERIC;
        }
        free( psz_mime );
226
    }
227

Jean-Baptiste Kempf's avatar
Jean-Baptiste Kempf committed
228 229
    /* */
    p_demux->p_sys = p_sys = calloc( 1, sizeof( demux_sys_t ) );
230 231
    if( !p_sys )
        return VLC_ENOMEM;
232

233
    p_sys->i_length = -1;
234
    p_sys->b_preparsing_done = false;
235

236 237
    vlc_stream_Control( p_demux->s, STREAM_GET_PTS_DELAY,
                        &p_sys->i_access_delay );
238

Jean-Baptiste Kempf's avatar
Jean-Baptiste Kempf committed
239 240 241 242
    /* Set exported functions */
    p_demux->pf_demux = Demux;
    p_demux->pf_control = Control;

243 244
    /* Initialize the Ogg physical bitstream parser */
    ogg_sync_init( &p_sys->oy );
245

246
    /* */
247
    TAB_INIT( p_sys->i_seekpoints, p_sys->pp_seekpoints );
248

249 250 251

    while ( !p_sys->b_preparsing_done && p_demux->pf_demux( p_demux ) > 0 )
    {}
252
    if ( p_sys->b_preparsing_done && p_demux->b_preparsing )
253
        Ogg_CreateES( p_demux );
254

255 256 257
    return VLC_SUCCESS;
}

258 259 260 261 262
/*****************************************************************************
 * Close: frees unused data
 *****************************************************************************/
static void Close( vlc_object_t *p_this )
{
263 264
    demux_t *p_demux = (demux_t *)p_this;
    demux_sys_t *p_sys = p_demux->p_sys  ;
265 266 267 268

    /* Cleanup the bitstream parser */
    ogg_sync_clear( &p_sys->oy );

269
    Ogg_EndOfStream( p_demux );
270

271 272 273
    if( p_sys->p_old_stream )
        Ogg_LogicalStreamDelete( p_demux, p_sys->p_old_stream );

274 275 276 277 278 279 280 281
    free( p_sys );
}

/*****************************************************************************
 * Demux: reads and demuxes data packets
 *****************************************************************************
 * Returns -1 in case of error, 0 in case of EOF, 1 otherwise
 *****************************************************************************/
282
static int Demux( demux_t * p_demux )
283
{
284
    demux_sys_t *p_sys = p_demux->p_sys;
285 286
    ogg_packet  oggpacket;
    int         i_stream;
287
    bool b_skipping = false;
288
    bool b_canseek;
289

290
    int i_active_streams = p_sys->i_streams;
291
    for ( int i=0; i < p_sys->i_streams; i++ )
292 293 294 295
    {
        if ( p_sys->pp_stream[i]->b_finished )
            i_active_streams--;
    }
296

297
    if ( i_active_streams == 0 )
298
    {
299
        if ( p_sys->i_streams ) /* All finished */
300
        {
301
            msg_Dbg( p_demux, "end of a group of logical streams" );
302 303 304 305 306 307 308
            /* We keep the ES to try reusing it in Ogg_BeginningOfStream
             * only 1 ES is supported (common case for ogg web radio) */
            if( p_sys->i_streams == 1 )
            {
                p_sys->p_old_stream = p_sys->pp_stream[0];
                TAB_CLEAN( p_sys->i_streams, p_sys->pp_stream );
            }
309
            Ogg_EndOfStream( p_demux );
310
            p_sys->b_chained_boundary = true;
311
            p_sys->i_nzpcr_offset = p_sys->i_nzlast_pts;
312 313
        }

314
        if( Ogg_BeginningOfStream( p_demux ) != VLC_SUCCESS )
315
            return VLC_DEMUXER_EOF;
316

317
        msg_Dbg( p_demux, "beginning of a group of logical streams" );
318 319 320 321

        if ( !p_sys->b_chained_boundary )
        {
            /* Find the real duration */
322
            vlc_stream_Control( p_demux->s, STREAM_CAN_SEEK, &b_canseek );
323 324 325 326
            if ( b_canseek )
                Oggseek_ProbeEnd( p_demux );
        }
        else
327 328 329
        {
            p_sys->b_chained_boundary = false;
        }
330 331
    }

332 333
    if ( p_sys->b_preparsing_done && !p_sys->b_es_created )
        Ogg_CreateES( p_demux );
334

335
    /*
336 337 338 339 340 341 342 343 344 345 346 347
     * The first data page of a physical stream is stored in the relevant logical stream
     * in Ogg_FindLogicalStreams. Therefore, we must not read a page and only update the
     * stream it belongs to if we haven't processed this first page yet. If we do, we
     * will only process that first page whenever we find the second page for this stream.
     * While this is fine for Vorbis and Theora, which are continuous codecs, which means
     * the second page will arrive real quick, this is not fine for Kate, whose second
     * data page will typically arrive much later.
     * This means it is now possible to seek right at the start of a stream where the last
     * logical stream is Kate, without having to wait for the second data page to unblock
     * the first one, which is the one that triggers the 'no more headers to backup' code.
     * And, as we all know, seeking without having backed up all headers is bad, since the
     * codec will fail to initialize if it's missing its headers.
348
     */
349
    if( !p_sys->b_page_waiting)
350
    {
351 352 353
        /*
         * Demux an ogg page from the stream
         */
salsaman's avatar
salsaman committed
354
        if( Ogg_ReadPage( p_demux, &p_sys->current_page ) != VLC_SUCCESS )
355
            return VLC_DEMUXER_EOF; /* EOF */
356
        /* Test for End of Stream */
357 358 359 360
        if( ogg_page_eos( &p_sys->current_page ) )
        {
            /* If we delayed restarting encoders/SET_ES_FMT for more
             * skeleton provided configuration */
361
            if ( p_sys->p_skelstream )
362
            {
363
                if ( p_sys->p_skelstream->i_serial_no == ogg_page_serialno(&p_sys->current_page) )
364
                {
365 366 367
                    msg_Dbg( p_demux, "End of Skeleton" );
                    p_sys->b_preparsing_done = true;
                    for( i_stream = 0; i_stream < p_sys->i_streams; i_stream++ )
368
                    {
369
                        logical_stream_t *p_stream = p_sys->pp_stream[i_stream];
370
                        Ogg_ApplySkeleton( p_stream );
371 372 373 374
                    }
                }
            }

375 376 377 378 379 380 381 382
            for( i_stream = 0; i_stream < p_sys->i_streams; i_stream++ )
            {
                if ( p_sys->pp_stream[i_stream]->i_serial_no == ogg_page_serialno( &p_sys->current_page ) )
                {
                    p_sys->pp_stream[i_stream]->b_finished = true;
                    break;
                }
            }
383
        }
384
    }
385

386 387 388 389 390
    b_skipping = false;
    for( i_stream = 0; i_stream < p_sys->i_streams; i_stream++ )
    {
        b_skipping |= p_sys->pp_stream[i_stream]->i_skip_frames;
    }
391 392 393 394 395

    for( i_stream = 0; i_stream < p_sys->i_streams; i_stream++ )
    {
        logical_stream_t *p_stream = p_sys->pp_stream[i_stream];

396 397 398
        /* if we've just pulled page, look for the right logical stream */
        if( !p_sys->b_page_waiting )
        {
399
            if( p_sys->i_streams == 1 &&
salsaman's avatar
salsaman committed
400
                ogg_page_serialno( &p_sys->current_page ) != p_stream->os.serialno )
401 402
            {
                msg_Err( p_demux, "Broken Ogg stream (serialno) mismatch" );
403
                Ogg_ResetStream( p_stream );
404
                p_sys->i_nzpcr_offset = p_sys->i_nzlast_pts;
salsaman's avatar
salsaman committed
405
                ogg_stream_reset_serialno( &p_stream->os, ogg_page_serialno( &p_sys->current_page ) );
406 407
            }

408
            /* Does fail if serialno differs */
salsaman's avatar
salsaman committed
409
            if( ogg_stream_pagein( &p_stream->os, &p_sys->current_page ) != 0 )
410
            {
411
                continue;
412
            }
413
        }
414

415
        /* clear the finished flag if pages after eos (ex: after a seek) */
416 417
        if ( ! ogg_page_eos( &p_sys->current_page ) && p_sys->p_skelstream != p_stream )
            p_stream->b_finished = false;
418

419 420
        DemuxDebug(
            if ( p_stream->fmt.i_cat == VIDEO_ES )
421
                msg_Dbg(p_demux, "DEMUX READ pageno %ld g%"PRId64" (%d packets) cont %d %ld bytes",
422 423 424 425
                    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),
426
                    p_sys->current_page.body_len )
427 428
        );

429 430 431
        const int i_page_packets = ogg_page_packets( &p_sys->current_page );
        bool b_doprepcr = false;

432 433 434 435 436
        if ( p_stream->i_pcr < VLC_TS_0 && ogg_page_granulepos( &p_sys->current_page ) > 0 )
        {
            // PASS 0
            if ( p_stream->fmt.i_codec == VLC_CODEC_OPUS ||
                 p_stream->fmt.i_codec == VLC_CODEC_VORBIS ||
437
                 p_stream->fmt.i_codec == VLC_CODEC_SPEEX ||
438 439
                 p_stream->fmt.i_cat == VIDEO_ES )
            {
440 441
                assert( p_stream->prepcr.pp_blocks == NULL );
                b_doprepcr = true;
442 443 444
            }
        }

445
        int i_real_page_packets = 0;
446 447
        while( ogg_stream_packetout( &p_stream->os, &oggpacket ) > 0 )
        {
448 449 450 451 452 453 454 455 456 457 458 459 460 461 462 463 464 465
            i_real_page_packets++;
            int i_max_packets = __MAX(i_page_packets, i_real_page_packets);
            if ( b_doprepcr && p_stream->prepcr.i_size < i_max_packets )
            {
                /* always double alloc for performance */
                i_max_packets = __MAX( i_max_packets << 1, 255 );
                /* alloc or realloc */
                block_t **pp_realloc = realloc( p_stream->prepcr.pp_blocks,
                                                sizeof(block_t *) * i_max_packets );
                if ( !pp_realloc )
                {
                    /* drop it then */
                    continue;
                }
                p_stream->prepcr.i_size = i_max_packets;
                p_stream->prepcr.pp_blocks = pp_realloc;
            }

466
            /* Read info from any secondary header packets, if there are any */
Laurent Aimar's avatar
Laurent Aimar committed
467
            if( p_stream->i_secondary_header_packets > 0 )
468
            {
469
                if( p_stream->fmt.i_codec == VLC_CODEC_THEORA &&
470
                        oggpacket.bytes >= 7 &&
471
                        ! memcmp( oggpacket.packet, "\x80theora", 7 ) )
472
                {
473
                    Ogg_ReadTheoraHeader( p_stream, &oggpacket );
Laurent Aimar's avatar
Laurent Aimar committed
474
                    p_stream->i_secondary_header_packets = 0;
475
                }
Tristan Matthews's avatar
Tristan Matthews committed
476 477 478 479 480 481 482
                else if( p_stream->fmt.i_codec == VLC_CODEC_DAALA &&
                        oggpacket.bytes >= 6 &&
                        ! memcmp( oggpacket.packet, "\x80""daala", 6 ) )
                {
                    Ogg_ReadDaalaHeader( p_stream, &oggpacket );
                    p_stream->i_secondary_header_packets = 0;
                }
483
                else if( p_stream->fmt.i_codec == VLC_CODEC_VORBIS &&
484
                        oggpacket.bytes >= 7 &&
485
                        ! memcmp( oggpacket.packet, "\x01vorbis", 7 ) )
486
                {
487
                    Ogg_ReadVorbisHeader( p_stream, &oggpacket );
Laurent Aimar's avatar
Laurent Aimar committed
488
                    p_stream->i_secondary_header_packets = 0;
489
                }
490
                else if( p_stream->fmt.i_codec == VLC_CODEC_CMML )
491
                {
Laurent Aimar's avatar
Laurent Aimar committed
492
                    p_stream->i_secondary_header_packets = 0;
493
                }
494 495

                /* update start of data pointer */
496
                p_stream->i_data_start = vlc_stream_Tell( p_demux->s );
497 498
            }

499
            /* If any streams have i_skip_frames, only decode (pre-roll)
500 501 502
             *  for those streams, but don't skip headers */
            if ( b_skipping && p_stream->i_skip_frames == 0
                 && p_stream->i_secondary_header_packets ) continue;
503

504 505
            if( p_stream->b_reinit )
            {
506 507
                p_stream->b_reinit = false;
                if( p_stream->fmt.i_codec == VLC_CODEC_OPUS )
508
                {
509
                    p_stream->i_skip_frames = p_stream->i_pre_skip;
510
                }
511 512 513 514 515
            }

            Ogg_DecodePacket( p_demux, p_stream, &oggpacket );
        }

516
        if ( p_stream->prepcr.pp_blocks )
517 518 519 520 521 522 523
        {
            int64_t pagestamp = Oggseek_GranuleToAbsTimestamp( p_stream, ogg_page_granulepos(  &p_sys->current_page ), false );
            p_stream->i_previous_pcr = pagestamp;
#ifdef HAVE_LIBVORBIS
            int i_prev_blocksize = 0;
#endif
            // PASS 1
524
            for( int i=0; i<p_stream->prepcr.i_used; i++ )
525
            {
526
                block_t *p_block = p_stream->prepcr.pp_blocks[i];
527 528 529
                ogg_packet dumb_packet;
                dumb_packet.bytes = p_block->i_buffer;
                dumb_packet.packet = p_block->p_buffer;
530

531
                switch( p_stream->fmt.i_codec )
532
                {
533 534 535 536
                case VLC_CODEC_SPEEX:
                    p_block->i_nb_samples = p_stream->special.speex.i_framesize *
                            p_stream->special.speex.i_framesperpacket;
                    break;
537
                case VLC_CODEC_OPUS:
538
                    p_block->i_nb_samples = Ogg_OpusPacketDuration( &dumb_packet );
539 540 541
                    break;
#ifdef HAVE_LIBVORBIS
                case VLC_CODEC_VORBIS:
542
                {
543
                    if( !VORBIS_HEADERS_VALID(p_stream) )
544 545 546 547
                    {
                        msg_Err( p_demux, "missing vorbis headers, can't compute block size" );
                        break;
                    }
548 549 550
                    long i_blocksize = vorbis_packet_blocksize(
                                p_stream->special.vorbis.p_info, &dumb_packet );
                    if ( i_prev_blocksize )
551
                        p_block->i_nb_samples = ( i_blocksize + i_prev_blocksize ) / 4;
552
                    else
553
                        p_block->i_nb_samples = i_blocksize / 2;
554 555 556
                    i_prev_blocksize = i_blocksize;
                }
#endif
557
                }
558
            }
559

560 561
            // PASS 2
            bool b_fixed = false;
562
            for( int i=p_stream->prepcr.i_used - 1; i>=0; i-- )
563
            {
564
                block_t *p_block = p_stream->prepcr.pp_blocks[i];
565
                switch( p_stream->fmt.i_codec )
566
                {
567
                case VLC_CODEC_SPEEX:
568 569 570 571
                case VLC_CODEC_OPUS:
                case VLC_CODEC_VORBIS:
                    pagestamp -= CLOCK_FREQ * p_block->i_nb_samples / p_stream->f_rate;
                    if ( pagestamp < 0 )
572
                    {
573 574
                        p_block->i_pts = VLC_TS_INVALID;
                        p_block->i_flags |= BLOCK_FLAG_PREROLL;
575 576
                    }
                    else
577 578 579 580 581
                        p_block->i_pts = VLC_TS_0 + p_sys->i_nzpcr_offset + pagestamp;
                    b_fixed = true;
                    break;
                default:
                    if ( p_stream->fmt.i_cat == VIDEO_ES )
582
                    {
583
                        pagestamp = pagestamp - ( CLOCK_FREQ / p_stream->f_rate );
584 585 586
                        if( pagestamp < 0 )
                            pagestamp = 0;
                        p_block->i_pts = VLC_TS_0 + p_sys->i_nzpcr_offset + pagestamp;
587
                        b_fixed = true;
588 589 590 591
                    }
                }
            }

592
            if ( b_fixed )
593
            {
594 595 596 597 598
                if ( pagestamp < 0 ) pagestamp = 0;
                p_stream->i_pcr = VLC_TS_0 + pagestamp;
                p_stream->i_pcr += p_sys->i_nzpcr_offset;
                p_stream->i_previous_granulepos = ogg_page_granulepos( &p_sys->current_page );
            }
599

600 601
            FREENULL(p_stream->prepcr.pp_blocks);
            p_stream->prepcr.i_used = 0;
602

603
            Ogg_SendOrQueueBlocks( p_demux, p_stream, NULL );
604

605
        }
606

607 608 609 610 611 612 613
        int64_t i_pagestamp = Oggseek_GranuleToAbsTimestamp( p_stream,
                            ogg_page_granulepos( &p_sys->current_page ), false );
        if ( i_pagestamp > -1 )
        {
            p_stream->i_pcr = VLC_TS_0 + i_pagestamp;
            p_stream->i_pcr += p_sys->i_nzpcr_offset;
        }
614

615 616
        if( !p_sys->b_page_waiting )
            break;
617 618
    }

619 620 621
    /* if a page was waiting, it's now processed */
    p_sys->b_page_waiting = false;

622 623 624 625
    if ( p_sys->p_skelstream && !p_sys->p_skelstream->b_finished )
        p_sys->b_preparsing_done = false;
    else
        p_sys->b_preparsing_done = true;
626

627 628 629 630
    /* We will consider the lowest PCR among tracks, because the audio core badly
     * handles PCR rewind (mute)
     */
    mtime_t i_pcr_candidate = VLC_TS_INVALID;
Laurent Aimar's avatar
Laurent Aimar committed
631
    for( i_stream = 0; i_stream < p_sys->i_streams; i_stream++ )
632 633 634
    {
        logical_stream_t *p_stream = p_sys->pp_stream[i_stream];

635
        if ( p_sys->b_preparsing_done && p_stream->b_initializing )
636 637 638 639 640
        {
            /* We have 1 or more streams needing more than 1 page for preparsing */
            p_sys->b_preparsing_done = false;
        }

641 642
        if( p_stream->fmt.i_cat == SPU_ES )
            continue;
643 644
        if( p_stream->fmt.i_codec == VLC_CODEC_OGGSPOTS )
            continue;
645
        if( p_stream->i_pcr < VLC_TS_0 )
646 647
            continue;
        if ( p_stream->b_finished || p_stream->b_initializing )
648
            continue;
649 650
        if ( p_stream->p_preparse_block )
            continue;
651
        if( i_pcr_candidate < VLC_TS_0
652
            || p_stream->i_pcr <= i_pcr_candidate )
653
        {
654
            i_pcr_candidate = p_stream->i_pcr;
655
        }
656 657
    }

658 659
    if ( i_pcr_candidate > VLC_TS_INVALID && p_sys->i_pcr != i_pcr_candidate )
    {
660 661 662 663 664 665 666 667 668 669 670
        if ( p_sys->i_streams == 1 && p_sys->i_access_delay )
        {
            int64_t i_pcr_jitter = i_pcr_candidate - p_sys->i_pcr;
            if ( i_pcr_jitter > p_sys->i_pcr_jitter )
            {
                p_sys->i_pcr_jitter = i_pcr_jitter;
                if ( p_sys->i_access_delay < i_pcr_jitter )
                    msg_Warn( p_demux, "Consider increasing access caching variable from %"PRId64" to >%"PRId64,
                              p_sys->i_access_delay / 1000, i_pcr_jitter / 1000 );
            }
        }
671 672 673 674

        if( ! b_skipping && p_sys->b_preparsing_done )
        {
            p_sys->i_pcr = i_pcr_candidate;
675
            es_out_Control( p_demux->out, ES_OUT_SET_PCR, p_sys->i_pcr );
676
        }
677
    }
678

679
    return VLC_DEMUXER_SUCCESS;
680 681
}

682
static void Ogg_ResetStream( logical_stream_t *p_stream )
683
{
684 685
#ifdef HAVE_LIBVORBIS
    if ( p_stream->fmt.i_codec == VLC_CODEC_VORBIS )
686
    {
687
        p_stream->special.vorbis.i_prev_blocksize = 0;
688
    }
689 690 691 692 693 694 695
#endif
    /* we'll trash all the data until we find the next pcr */
    p_stream->b_reinit = true;
    p_stream->i_pcr = VLC_TS_UNKNOWN;
    p_stream->i_previous_granulepos = -1;
    p_stream->i_previous_pcr = VLC_TS_UNKNOWN;
    ogg_stream_reset( &p_stream->os );
696 697 698
    FREENULL( p_stream->prepcr.pp_blocks );
    p_stream->prepcr.i_size = 0;
    p_stream->prepcr.i_used = 0;
699 700 701 702 703 704 705
}

static void Ogg_ResetStreamsHelper( demux_sys_t *p_sys )
{
    for( int i = 0; i < p_sys->i_streams; i++ )
        Ogg_ResetStream( p_sys->pp_stream[i] );

706
    ogg_sync_reset( &p_sys->oy );
707
    p_sys->i_pcr = VLC_TS_UNKNOWN;
708 709
}

710 711 712 713 714 715 716
static logical_stream_t * Ogg_GetSelectedStream( demux_t *p_demux )
{
    demux_sys_t *p_sys = p_demux->p_sys;
    logical_stream_t *p_stream = NULL;
    for( int i=0; i<p_sys->i_streams; i++ )
    {
        logical_stream_t *p_candidate = p_sys->pp_stream[i];
717
        if ( !p_candidate->p_es ) continue;
718

719
        bool b_selected = false;
720
        es_out_Control( p_demux->out, ES_OUT_GET_ES_STATE,
721
                        p_candidate->p_es, &b_selected );
722 723 724 725 726 727 728 729 730 731 732 733 734 735 736 737 738
        if ( !b_selected ) continue;

        if ( !p_stream && p_candidate->fmt.i_cat == AUDIO_ES )
        {
            p_stream = p_candidate;
            continue; /* Try to find video anyway */
        }

        if ( p_candidate->fmt.i_cat == VIDEO_ES )
        {
            p_stream = p_candidate;
            break;
        }
    }
    return p_stream;
}

739 740 741
/*****************************************************************************
 * Control:
 *****************************************************************************/
742
static int Control( demux_t *p_demux, int i_query, va_list args )
743
{
744
    demux_sys_t *p_sys  = p_demux->p_sys;
745
    vlc_meta_t *p_meta;
746 747 748
    int64_t *pi64, i64;
    double *pf, f;
    bool *pb_bool, b;
749 750 751

    switch( i_query )
    {
752
        case DEMUX_CAN_SEEK:
753
            return vlc_stream_vaControl( p_demux->s, i_query, args );
754

755 756 757 758 759 760
        case DEMUX_GET_META:
            p_meta = (vlc_meta_t *)va_arg( args, vlc_meta_t* );
            if( p_sys->p_meta )
                vlc_meta_Merge( p_meta, p_sys->p_meta );
            return VLC_SUCCESS;

761
        case DEMUX_HAS_UNSUPPORTED_META:
762 763
            pb_bool = (bool*)va_arg( args, bool* );
            *pb_bool = true;
764 765
            return VLC_SUCCESS;

766 767 768 769 770 771
        case DEMUX_GET_TIME:
            pi64 = (int64_t*)va_arg( args, int64_t * );
            *pi64 = p_sys->i_pcr;
            return VLC_SUCCESS;

        case DEMUX_SET_TIME:
772 773 774 775 776 777 778
            i64 = (int64_t)va_arg( args, int64_t );
            logical_stream_t *p_stream = Ogg_GetSelectedStream( p_demux );
            if ( !p_stream )
            {
                msg_Err( p_demux, "No selected seekable stream found" );
                return VLC_EGENERIC;
            }
779
            vlc_stream_Control( p_demux->s, STREAM_CAN_FASTSEEK, &b );
780 781
            if ( Oggseek_BlindSeektoAbsoluteTime( p_demux, p_stream, i64, b ) )
            {
782
                Ogg_ResetStreamsHelper( p_sys );
783 784 785 786 787 788
                es_out_Control( p_demux->out, ES_OUT_SET_NEXT_DISPLAY_TIME,
                                VLC_TS_0 + i64 );
                return VLC_SUCCESS;
            }
            else
                return VLC_EGENERIC;
789

790 791 792 793 794 795 796 797 798 799
        case DEMUX_GET_ATTACHMENTS:
        {
            input_attachment_t ***ppp_attach =
                (input_attachment_t***)va_arg( args, input_attachment_t*** );
            int *pi_int = (int*)va_arg( args, int * );

            if( p_sys->i_attachments <= 0 )
                return VLC_EGENERIC;

            *pi_int = p_sys->i_attachments;
800
            *ppp_attach = xmalloc( sizeof(input_attachment_t*) * p_sys->i_attachments );
801 802 803 804 805
            for( int i = 0; i < p_sys->i_attachments; i++ )
                (*ppp_attach)[i] = vlc_input_attachment_Duplicate( p_sys->attachments[i] );
            return VLC_SUCCESS;
        }

806 807 808 809 810 811 812 813 814
        case DEMUX_GET_POSITION:
            pf = (double*)va_arg( args, double * );
            if( p_sys->i_length > 0 )
            {
                *pf =  (double) p_sys->i_pcr /
                       (double) ( p_sys->i_length * (mtime_t)1000000 );
            }
            else if( stream_Size( p_demux->s ) > 0 )
            {
815
                i64 = vlc_stream_Tell( p_demux->s );
816 817 818 819 820
                *pf = (double) i64 / stream_Size( p_demux->s );
            }
            else *pf = 0.0;
            return VLC_SUCCESS;

821
        case DEMUX_SET_POSITION:
822 823 824
            /* forbid seeking if we haven't initialized all logical bitstreams yet;
               if we allowed, some headers would not get backed up and decoder init
               would fail, making that logical stream unusable */
825
            for ( int i=0; i< p_sys->i_streams; i++ )
826
            {
827 828
                if ( p_sys->pp_stream[i]->b_initializing )
                    return VLC_EGENERIC;
829 830
            }

831
            p_stream = Ogg_GetSelectedStream( p_demux );
832 833 834 835 836 837
            if ( !p_stream )
            {
                msg_Err( p_demux, "No selected seekable stream found" );
                return VLC_EGENERIC;
            }

838
            vlc_stream_Control( p_demux->s, STREAM_CAN_FASTSEEK, &b );
839 840

            f = (double)va_arg( args, double );
841
            if ( p_sys->i_length <= 0 || !b /* || ! STREAM_CAN_FASTSEEK */ )
842
            {
843
                Ogg_ResetStreamsHelper( p_sys );
844 845 846 847 848
                Oggseek_BlindSeektoPosition( p_demux, p_stream, f, b );
                return VLC_SUCCESS;
            }

            assert( p_sys->i_length > 0 );
Tristan Matthews's avatar
Tristan Matthews committed
849
            i64 = CLOCK_FREQ * p_sys->i_length * f;
850
            Ogg_ResetStreamsHelper( p_sys );
851 852 853 854 855 856 857 858 859
            if ( Oggseek_SeektoAbsolutetime( p_demux, p_stream, i64 ) >= 0 )
            {
                es_out_Control( p_demux->out, ES_OUT_SET_NEXT_DISPLAY_TIME,
                                VLC_TS_0 + i64 );
                return VLC_SUCCESS;
            }

            return VLC_EGENERIC;

860 861 862 863 864 865 866 867
        case DEMUX_GET_LENGTH:
            if ( p_sys->i_length < 0 )
                return demux_vaControlHelper( p_demux->s, 0, -1, p_sys->i_bitrate,
                                              1, i_query, args );
            pi64 = (int64_t*)va_arg( args, int64_t * );
            *pi64 = p_sys->i_length * 1000000;
            return VLC_SUCCESS;

868 869 870 871 872 873 874 875 876 877
        case DEMUX_GET_TITLE_INFO:
        {
            input_title_t ***ppp_title = (input_title_t***)va_arg( args, input_title_t*** );
            int *pi_int    = (int*)va_arg( args, int* );
            int *pi_title_offset = (int*)va_arg( args, int* );
            int *pi_seekpoint_offset = (int*)va_arg( args, int* );

            if( p_sys->i_seekpoints > 0 )
            {
                *pi_int = 1;
878
                *ppp_title = malloc( sizeof( input_title_t* ) );
879 880 881
                input_title_t *p_title = (*ppp_title)[0] = vlc_input_title_New();
                for( int i = 0; i < p_sys->i_seekpoints; i++ )
                {
882 883 884
                    seekpoint_t *p_seekpoint_copy = vlc_seekpoint_Duplicate( p_sys->pp_seekpoints[i] );
                    if ( likely( p_seekpoint_copy ) )
                        TAB_APPEND( p_title->i_seekpoint, p_title->seekpoint, p_seekpoint_copy );
885 886 887 888 889 890 891 892 893 894 895 896 897 898 899 900
                }
                *pi_title_offset = 0;
                *pi_seekpoint_offset = 0;
            }
            return VLC_SUCCESS;
        }
        case DEMUX_SET_TITLE:
        {
            const int i_title = (int)va_arg( args, int );
            if( i_title > 1 )
                return VLC_EGENERIC;
            return VLC_SUCCESS;
        }
        case DEMUX_SET_SEEKPOINT:
        {
            const int i_seekpoint = (int)va_arg( args, int );
901
            if( i_seekpoint > p_sys->i_seekpoints )
902
                return VLC_EGENERIC;
903

904 905 906 907 908 909
            for ( int i=0; i< p_sys->i_streams; i++ )
            {
                if ( p_sys->pp_stream[i]->b_initializing )
                    return VLC_EGENERIC;
            }

910 911 912 913
            i64 = p_sys->pp_seekpoints[i_seekpoint]->i_time_offset;

            p_stream = Ogg_GetSelectedStream( p_demux );
            if ( !p_stream )
914
            {
915
                msg_Err( p_demux, "No selected seekable stream found" );
916 917 918
                return VLC_EGENERIC;
            }

919
            vlc_stream_Control( p_demux->s, STREAM_CAN_FASTSEEK, &b );
920
            if ( Oggseek_BlindSeektoAbsoluteTime( p_demux, p_stream, i64, b ) )
921
            {
922
                Ogg_ResetStreamsHelper( p_sys );
923 924 925 926
                es_out_Control( p_demux->out, ES_OUT_SET_NEXT_DISPLAY_TIME,
                                VLC_TS_0 + i64 );
                p_demux->info.i_update |= INPUT_UPDATE_SEEKPOINT;
                p_demux->info.i_seekpoint = i_seekpoint;
927
                return VLC_SUCCESS;
928 929
            }
            else
930
                return VLC_EGENERIC;
931
        }
932 933

        default:
934
            return demux_vaControlHelper( p_demux->s, 0, -1, p_sys->i_bitrate,
935
                                           1, i_query, args );
936 937 938
    }
}

939 940 941 942 943 944
/****************************************************************************
 * Ogg_ReadPage: Read a full Ogg page from the physical bitstream.
 ****************************************************************************
 * Returns VLC_SUCCESS if a page has been read. An error might happen if we
 * are at the end of stream.
 ****************************************************************************/
945
static int Ogg_ReadPage( demux_t *p_demux, ogg_page *p_oggpage )
946
{
947
    demux_sys_t *p_ogg = p_demux->p_sys  ;
948
    int i_read = 0;
949
    char *p_buffer;
950 951 952

    while( ogg_sync_pageout( &p_ogg->oy, p_oggpage ) != 1 )
    {
953
        p_buffer = ogg_sync_buffer( &p_ogg->oy, OGGSEEK_BYTES_TO_READ );
954

955
        i_read = vlc_stream_Read( p_demux->s, p_buffer, OGGSEEK_BYTES_TO_READ );
956 957 958 959 960 961 962 963 964
        if( i_read <= 0 )
            return VLC_EGENERIC;

        ogg_sync_wrote( &p_ogg->oy, i_read );
    }

    return VLC_SUCCESS;
}

965 966 967 968
/****************************************************************************
 * Ogg_UpdatePCR: update the PCR (90kHz program clock reference) for the
 *                current stream.
 ****************************************************************************/
969
static void Ogg_UpdatePCR( demux_t *p_demux, logical_stream_t *p_stream,
970 971
                           ogg_packet *p_oggpacket )
{
972
    demux_sys_t *p_ogg = p_demux->p_sys;
.'s avatar
. committed
973
    p_stream->i_end_trim = 0;
974

975
    /* Convert the granulepos into a pcr */
976 977 978
    if ( p_oggpacket->granulepos == 0 )
    {
        /* We're in headers, and we haven't parsed 1st data packet yet */
979
//        p_stream->i_pcr = VLC_TS_UNKNOWN;
980 981
    }
    else if( p_oggpacket->granulepos > 0 )
982
    {
983
        if( p_stream->fmt.i_codec == VLC_CODEC_THEORA ||
Tristan Matthews's avatar
Tristan Matthews committed
984
            p_stream->fmt.i_codec == VLC_CODEC_DAALA ||
985
            p_stream->fmt.i_codec == VLC_CODEC_KATE ||
986
            p_stream->fmt.i_codec == VLC_CODEC_VP8 ||
987
            p_stream->fmt.i_codec == VLC_CODEC_DIRAC ||
988
            p_stream->fmt.i_codec == VLC_CODEC_SPEEX ||
989
            p_stream->fmt.i_codec == VLC_CODEC_OGGSPOTS ||
990
            (p_stream->b_oggds && p_stream->fmt.i_cat == VIDEO_ES) )
991
        {
992 993 994
            p_stream->i_pcr = VLC_TS_0 + Oggseek_GranuleToAbsTimestamp( p_stream,
                                         p_oggpacket->granulepos, true );
            p_stream->i_pcr += p_ogg->i_nzpcr_offset;
995
        }
996
        else if ( p_stream->i_previous_granulepos > 0 )