[vlc-devel] [PATCH 5/9] demux: mkv: differentiate between internal and externally triggered seek

Steve Lhomme robux4 at ycbcr.xyz
Mon Jul 16 12:34:34 CEST 2018


On 2018-07-16 5:19, Filip Roséen wrote:
> When the core requests the demux to seek it will, as is expected and
> most often required, reset the PCR associated with the current input.
> The core can of course not help the demux with this if it seeks by
> itself (as can happen when changing segment, or respecting a
> GotoAndPlay-matroska command).
>
> These changes allows for such differantiation, and will effectively
> reset the PCR where required.
>
> fixes: #20447
> ---
>   modules/demux/mkv/matroska_segment.cpp | 14 +++++++++++---
>   modules/demux/mkv/matroska_segment.hpp |  2 +-
>   modules/demux/mkv/mkv.cpp              |  7 ++++++-
>   modules/demux/mkv/mkv.hpp              |  6 ++++++
>   modules/demux/mkv/virtual_segment.cpp  |  9 ++-------
>   modules/demux/mkv/virtual_segment.hpp  |  2 +-
>   6 files changed, 27 insertions(+), 13 deletions(-)
>
> diff --git a/modules/demux/mkv/matroska_segment.cpp b/modules/demux/mkv/matroska_segment.cpp
> index 2919130bab..f660ccfbd6 100644
> --- a/modules/demux/mkv/matroska_segment.cpp
> +++ b/modules/demux/mkv/matroska_segment.cpp
> @@ -791,7 +791,7 @@ bool matroska_segment_c::LoadSeekHeadItem( const EbmlCallbacks & ClassInfos, int
>       return true;
>   }
>   
> -bool matroska_segment_c::Seek( demux_t &demuxer, vlc_tick_t i_absolute_mk_date, vlc_tick_t i_mk_time_offset, bool b_accurate )
> +bool matroska_segment_c::Seek( demux_t &demuxer, vlc_tick_t i_absolute_mk_date, vlc_tick_t i_mk_time_offset, unsigned i_flags )
>   {
>       SegmentSeeker::tracks_seekpoint_t seekpoints;
>   
> @@ -801,6 +801,9 @@ bool matroska_segment_c::Seek( demux_t &demuxer, vlc_tick_t i_absolute_mk_date,
>       SegmentSeeker::track_ids_t selected_tracks;
>       SegmentSeeker::track_ids_t priority;
>   
> +    if( !( i_flags & MKV_DEMUX_SEEK_TRIGGERED_EXTERNALLY ) )
> +        i_flags |= MKV_DEMUX_SEEK_PRECISE;
> +

Are we sure about that ? We could decide to use fast-seeking internally 
as well.

>       // reset information for all tracks //
>   
>       for( tracks_map_t::iterator it = tracks.begin(); it != tracks.end(); ++it )
> @@ -861,7 +864,7 @@ bool matroska_segment_c::Seek( demux_t &demuxer, vlc_tick_t i_absolute_mk_date,
>           }
>   
>           // blocks that will be not be read until this fpos
> -        if ( b_accurate )
> +        if ( i_flags & MKV_DEMUX_SEEK_PRECISE )
>               trackit->second->i_skip_until_fpos = it->second.fpos;
>           else
>               trackit->second->i_skip_until_fpos = std::numeric_limits<uint64_t>::max();
> @@ -876,9 +879,11 @@ bool matroska_segment_c::Seek( demux_t &demuxer, vlc_tick_t i_absolute_mk_date,
>   
>       // propogate seek information //
>   
> +    vlc_tick_t i_orig_pts = sys.i_pts;
> +
>       sys.i_pcr           = VLC_TICK_INVALID;
>       sys.i_pts           = VLC_TICK_0 + i_mk_seek_time + i_mk_time_offset;
> -    if (b_accurate)
> +    if( i_flags & MKV_DEMUX_SEEK_PRECISE )
>           sys.i_start_pts = VLC_TICK_0 + i_absolute_mk_date;
>       else
>           sys.i_start_pts = sys.i_pts;
> @@ -892,6 +897,9 @@ bool matroska_segment_c::Seek( demux_t &demuxer, vlc_tick_t i_absolute_mk_date,
>       msg_Dbg( &sys.demuxer, "seek: preroll{ req: %" PRId64 ", start-pts: %" PRId64 ", start-fpos: %" PRIu64 "} ",
>         sys.i_start_pts, sys.i_pts, i_seek_position );
>   
> +    if( !( i_flags & MKV_DEMUX_SEEK_TRIGGERED_EXTERNALLY ) )
> +        es_out_Control( sys.demuxer.out, ES_OUT_RESET_PCR );
> +

Is this replacing the call from UpdateCurrentToChapter() ? Do we want to 
reset the PCR when switching to the next hard-linked segment ? (ie 
basically the exact continuation of the previous segment). It *is* an 
internal seek. Will it cause buffer flushing which is definitely not 
wanted here.

>       // blocks that will be read and decoded but discarded until this pts
>       es_out_Control( sys.demuxer.out, ES_OUT_SET_NEXT_DISPLAY_TIME, sys.i_start_pts );
>       return true;
> diff --git a/modules/demux/mkv/matroska_segment.hpp b/modules/demux/mkv/matroska_segment.hpp
> index 20cfd594f3..9620ef3999 100644
> --- a/modules/demux/mkv/matroska_segment.hpp
> +++ b/modules/demux/mkv/matroska_segment.hpp
> @@ -144,7 +144,7 @@ public:
>       bool PreloadClusters( uint64 i_cluster_position );
>       void InformationCreate();
>   
> -    bool Seek( demux_t &, vlc_tick_t i_mk_date, vlc_tick_t i_mk_time_offset, bool b_accurate );
> +    bool Seek( demux_t &, vlc_tick_t i_mk_date, vlc_tick_t i_mk_time_offset, unsigned i_seek_flags );
>   
>       int BlockGet( KaxBlock * &, KaxSimpleBlock * &, bool *, bool *, int64_t *);
>   
> diff --git a/modules/demux/mkv/mkv.cpp b/modules/demux/mkv/mkv.cpp
> index 23c1b39776..c0184db280 100644
> --- a/modules/demux/mkv/mkv.cpp
> +++ b/modules/demux/mkv/mkv.cpp
> @@ -506,7 +506,12 @@ static int Seek( demux_t *p_demux, vlc_tick_t i_mk_date, double f_percent, virtu
>       {
>           i_mk_date = int64_t( f_percent * p_sys->f_duration * 1000.0 );
>       }
> -    return p_vsegment->Seek( *p_demux, i_mk_date, p_vchapter, b_precise ) ? VLC_SUCCESS : VLC_EGENERIC;
> +
> +    int i_seek_flags = MKV_DEMUX_SEEK_TRIGGERED_EXTERNALLY;
> +    if( b_precise )
> +        i_seek_flags |= MKV_DEMUX_SEEK_PRECISE;
> +
> +    return p_vsegment->Seek( *p_demux, i_mk_date, p_vchapter, i_seek_flags ) ? VLC_SUCCESS : VLC_EGENERIC;
>   }
>   
>   /* Needed by matroska_segment::Seek() and Seek */
> diff --git a/modules/demux/mkv/mkv.hpp b/modules/demux/mkv/mkv.hpp
> index 17a3fd0e67..ae5fe6a323 100644
> --- a/modules/demux/mkv/mkv.hpp
> +++ b/modules/demux/mkv/mkv.hpp
> @@ -111,6 +111,12 @@ enum
>       MATROSKA_ENCODING_SCOPE_NEXT = 4 /* unsupported */
>   };
>   
> +enum
> +{
> +    MKV_DEMUX_SEEK_PRECISE = 0x1,
> +    MKV_DEMUX_SEEK_TRIGGERED_EXTERNALLY = 0x2,
> +};
> +
>   #define MKVD_TIMECODESCALE 1000000
>   
>   #define MKV_IS_ID( el, C ) ( el != NULL && typeid( *el ) == typeid( C ) )
> diff --git a/modules/demux/mkv/virtual_segment.cpp b/modules/demux/mkv/virtual_segment.cpp
> index cde60b580e..02e39ec0b0 100644
> --- a/modules/demux/mkv/virtual_segment.cpp
> +++ b/modules/demux/mkv/virtual_segment.cpp
> @@ -458,8 +458,6 @@ bool virtual_segment_c::UpdateCurrentToChapter( demux_t & demux )
>                       ( p_current_vchapter && &p_current_vchapter->segment != &p_cur_vchapter->segment ) ||
>                       ( p_current_vchapter->p_chapter->i_end_time != p_cur_vchapter->p_chapter->i_start_time ))
>                   {
> -                    /* Forcing reset pcr */
> -                    es_out_Control( demux.out, ES_OUT_RESET_PCR);
>                       Seek( demux, p_cur_vchapter->i_mk_virtual_start_time, p_cur_vchapter );
>                       return true;
>                   }
> @@ -512,7 +510,7 @@ bool virtual_chapter_c::EnterAndLeave( virtual_chapter_c *p_leaving_vchapter, bo
>   }
>   
>   bool virtual_segment_c::Seek( demux_t & demuxer, vlc_tick_t i_mk_date,
> -                              virtual_chapter_c *p_vchapter, bool b_precise )
> +                              virtual_chapter_c *p_vchapter, unsigned i_flags )
>   {
>       demux_sys_t *p_sys = (demux_sys_t *)demuxer.p_sys;
>   
> @@ -544,9 +542,6 @@ bool virtual_segment_c::Seek( demux_t & demuxer, vlc_tick_t i_mk_date,
>               msg_Dbg( &demuxer, "SWITCH CHAPTER uid=%" PRId64, p_vchapter->p_chapter ? p_vchapter->p_chapter->i_uid : 0 );
>               p_current_vchapter = p_vchapter;
>   
> -            /* only use for soft linking, hard linking should be continous */

I think this is this explanation on why we only do the RESET_PCR in some 
case when we seek internally but not others.

> -            es_out_Control( demuxer.out, ES_OUT_RESET_PCR );
> -
>               p_sys->PreparePlayback( *this, i_mk_date );
>               return true;
>           }
> @@ -554,7 +549,7 @@ bool virtual_segment_c::Seek( demux_t & demuxer, vlc_tick_t i_mk_date,
>           {
>               p_current_vchapter = p_vchapter;
>   
> -            return p_current_vchapter->segment.Seek( demuxer, i_mk_date, i_mk_time_offset, b_precise );
> +            return p_current_vchapter->segment.Seek( demuxer, i_mk_date, i_mk_time_offset, i_flags );
>           }
>       }
>       return false;
> diff --git a/modules/demux/mkv/virtual_segment.hpp b/modules/demux/mkv/virtual_segment.hpp
> index d09913b689..1474f201a1 100644
> --- a/modules/demux/mkv/virtual_segment.hpp
> +++ b/modules/demux/mkv/virtual_segment.hpp
> @@ -162,7 +162,7 @@ public:
>       virtual_chapter_c * FindChapter( int64_t i_find_uid );
>   
>       bool UpdateCurrentToChapter( demux_t & demux );
> -    bool Seek( demux_t & demuxer, vlc_tick_t i_mk_date, virtual_chapter_c *p_vchapter, bool b_precise = true );
> +    bool Seek( demux_t & demuxer, vlc_tick_t i_mk_date, virtual_chapter_c *p_vchapter, unsigned i_flags  = MKV_DEMUX_SEEK_PRECISE );
>   private:
>       void KeepTrackSelection( matroska_segment_c & old, matroska_segment_c & next );
>   };
> -- 
> 2.18.0
>
> _______________________________________________
> vlc-devel mailing list
> To unsubscribe or modify your subscription options:
> https://mailman.videolan.org/listinfo/vlc-devel



More information about the vlc-devel mailing list