[vlc-commits] [Git][videolan/vlc][master] 3 commits: demux: mkv: process the block duration once we have read the whole BlockGroup
Steve Lhomme (@robUx4)
gitlab at videolan.org
Fri Aug 21 11:02:55 UTC 2026
Steve Lhomme pushed to branch master at VideoLAN / VLC
Commits:
2494e66a by Steve Lhomme at 2026-08-21T10:50:47+00:00
demux: mkv: process the block duration once we have read the whole BlockGroup
The order of elements doesn't guarantee we get the BlockDuration before the DiscardPadding.
- - - - -
144d5345 by Steve Lhomme at 2026-08-21T10:50:47+00:00
demux: mkv: ignore negative DiscardPadding
A negative value means we have to pad the decoded data with silence
at the beginning [^1]. But VLC doesn't support that feature.
Co-authored-by: zhengjianfeng <jianfeng.zheng at mthreads.dev>
[^1]: https://www.rfc-editor.org/info/rfc9559/#section-5.1.3.5.7
- - - - -
a35c3723 by Steve Lhomme at 2026-08-21T10:50:47+00:00
demux: mkv: handle the block duration as always unsigned
- - - - -
6 changed files:
- modules/demux/mkv/matroska_segment.cpp
- modules/demux/mkv/matroska_segment.hpp
- modules/demux/mkv/matroska_segment_seeker.cpp
- modules/demux/mkv/mkv.cpp
- modules/demux/mkv/util.cpp
- modules/demux/mkv/util.hpp
Changes:
=====================================
modules/demux/mkv/matroska_segment.cpp
=====================================
@@ -1158,7 +1158,7 @@ void matroska_segment_c::ESDestroy( )
int matroska_segment_c::BlockGet( KaxBlock * & pp_block, KaxSimpleBlock * & pp_simpleblock,
KaxBlockAdditions * & pp_additions,
bool *pb_key_picture, bool *pb_discardable_picture,
- int64_t *pi_duration )
+ uint64_t *pi_duration )
{
pp_simpleblock = NULL;
pp_block = NULL;
@@ -1168,6 +1168,9 @@ int matroska_segment_c::BlockGet( KaxBlock * & pp_block, KaxSimpleBlock * & pp_s
*pb_discardable_picture = false;
*pi_duration = 0;
+ uint64_t duration = 0;
+ int64_t duration_padding = 0;
+
struct BlockPayload {
matroska_segment_c * const obj;
EbmlParser * const ep;
@@ -1176,14 +1179,15 @@ int matroska_segment_c::BlockGet( KaxBlock * & pp_block, KaxSimpleBlock * & pp_s
KaxSimpleBlock *& simpleblock;
KaxBlockAdditions *& additions;
- int64_t & i_duration;
+ uint64_t & i_duration;
+ int64_t & duration_padding;
bool & b_key_picture;
bool & b_discardable_picture;
bool b_cluster_timecode;
} payload = {
this, &ep, &sys.demuxer, pp_block, pp_simpleblock, pp_additions,
- *pi_duration, *pb_key_picture, *pb_discardable_picture, true
+ duration, duration_padding, *pb_key_picture, *pb_discardable_picture, true
};
MKV_SWITCH_CREATE( EbmlTypeDispatcher, BlockGetHandler_l1, BlockPayload )
@@ -1325,12 +1329,7 @@ int matroska_segment_c::BlockGet( KaxBlock * & pp_block, KaxSimpleBlock * & pp_s
E_CASE( KaxDiscardPadding, kdiscardp )
{
kdiscardp.ReadData( vars.obj->es.I_O() );
- int64_t i_duration = static_cast<int64_t>( kdiscardp );
-
- if( vars.i_duration < i_duration )
- vars.i_duration = 0;
- else
- vars.i_duration -= i_duration;
+ vars.duration_padding = static_cast<int64_t>( kdiscardp );
}
#endif
E_CASE_DEFAULT( element )
@@ -1388,6 +1387,20 @@ int matroska_segment_c::BlockGet( KaxBlock * & pp_block, KaxSimpleBlock * & pp_s
}
}
+ /* A negative DiscardPadding designates padding at the start of
+ * the block, which we don't handle; some files in the wild also
+ * carry bogus negative values due to encoder bugs. Never let it
+ * extend the block duration. */
+ if ( duration_padding < 0)
+ {
+ msg_Warn( &sys.demuxer, "ignoring negative DiscardPadding (%" PRId64 ")", duration_padding );
+ *pi_duration = duration;
+ }
+ else if( duration < (uint64_t)duration_padding )
+ *pi_duration = 0;
+ else
+ *pi_duration = duration - duration_padding;
+
return VLC_SUCCESS;
}
=====================================
modules/demux/mkv/matroska_segment.hpp
=====================================
@@ -147,7 +147,7 @@ public:
bool Seek( demux_t &, vlc_tick_t i_mk_date, vlc_tick_t i_mk_time_offset, bool b_accurate );
int BlockGet( KaxBlock * &, KaxSimpleBlock * &, KaxBlockAdditions * &,
- bool *, bool *, int64_t *);
+ bool *, bool *, uint64_t *);
mkv_track_t * FindTrackByBlock(const KaxBlock *, const KaxSimpleBlock * );
=====================================
modules/demux/mkv/matroska_segment_seeker.cpp
=====================================
@@ -368,7 +368,7 @@ SegmentSeeker::index_unsearched_range( matroska_segment_c& ms, Range search_area
bool b_key_picture;
bool b_discardable_picture;
- int64_t i_block_duration;
+ uint64_t i_block_duration;
track_id_t track_id;
if( ms.BlockGet( block, simpleblock, additions,
=====================================
modules/demux/mkv/mkv.cpp
=====================================
@@ -539,7 +539,7 @@ static void ReleaseVpxAlpha(void *opaque)
/* Needed by matroska_segment::Seek() and Seek */
static void BlockDecode( demux_t *p_demux, KaxBlock *block, KaxSimpleBlock *simpleblock,
const KaxBlockAdditions *additions,
- vlc_tick_t i_pts, int64_t i_duration, bool b_key_picture,
+ vlc_tick_t i_pts, uint64_t i_duration, bool b_key_picture,
bool b_discardable_picture )
{
demux_sys_t *p_sys = (demux_sys_t *)p_demux->p_sys;
@@ -833,7 +833,7 @@ static int Demux( demux_t *p_demux)
KaxBlock *block;
KaxSimpleBlock *simpleblock;
KaxBlockAdditions *additions;
- int64_t i_block_duration = 0;
+ uint64_t i_block_duration = 0;
bool b_key_picture;
bool b_discardable_picture;
=====================================
modules/demux/mkv/util.cpp
=====================================
@@ -426,7 +426,7 @@ int UpdatePCR( demux_t * p_demux )
return VLC_SUCCESS;
}
-void send_Block( demux_t * p_demux, mkv_track_t * p_tk, block_t * p_block, unsigned int i_number_frames, int64_t i_duration )
+void send_Block( demux_t * p_demux, mkv_track_t * p_tk, block_t * p_block, unsigned int i_number_frames, uint64_t i_duration )
{
demux_sys_t *p_sys = (demux_sys_t *)p_demux->p_sys;
matroska_segment_c *p_segment = p_sys->GetCurrentVSegment()->CurrentSegment();
=====================================
modules/demux/mkv/util.hpp
=====================================
@@ -37,7 +37,7 @@ block_t *MemToBlock( uint8_t *p_mem, size_t i_mem, size_t offset);
void handle_real_audio(demux_t * p_demux, mkv_track_t * p_tk, block_t * p_blk, vlc_tick_t i_pts);
block_t *WEBVTT_Repack_Sample(block_t *p_block, bool b_webm = false,
const uint8_t * = NULL, size_t = 0);
-void send_Block( demux_t * p_demux, mkv_track_t * p_tk, block_t * p_block, unsigned int i_number_frames, int64_t i_duration );
+void send_Block( demux_t * p_demux, mkv_track_t * p_tk, block_t * p_block, unsigned int i_number_frames, uint64_t i_duration );
int UpdatePCR( demux_t * p_demux );
class ByteReader
View it on GitLab: https://code.videolan.org/videolan/vlc/-/compare/8c2b88db9ac5157d11ca4d3592c3efec715c7623...a35c3723f0c8423df4e9711abbb8fa0941e655f4
--
View it on GitLab: https://code.videolan.org/videolan/vlc/-/compare/8c2b88db9ac5157d11ca4d3592c3efec715c7623...a35c3723f0c8423df4e9711abbb8fa0941e655f4
You're receiving this email because of your account on code.videolan.org. Manage all notifications: https://code.videolan.org/-/profile/notifications | Help: https://code.videolan.org/help
More information about the vlc-commits
mailing list