Skip to content

Commit 76ed24e

Browse files
committed
libavformat/matroskadec: set fixed duration for subtitles
The matroska specification states the start time and duration of subtitle entries are encoded in the block TimeStamp and BlockDuration. Furthermore, for all subtitle formats except S_HDMV/PGS the BlockDuration must always be defined and have an absolute value even if it is simply 0. ffmpeg assumes that a duration of 0 means the duration is still unknown and tries to adjust based on the next packet pts. This is wrong for all formats except S_HDMV/PGS. Since changing the semantics of duration 0 is not an option (touches too many parts of the code) this change introduces AV_PKT_FLAG_FIXED_DURATION flag which decoders might use to flag the duration of a given packet should not be changed. Signed-off-by: Miguel Borges de Freitas <[email protected]>
1 parent 94aa70d commit 76ed24e

File tree

3 files changed

+12
-1
lines changed

3 files changed

+12
-1
lines changed

libavcodec/packet.h

+5
Original file line numberDiff line numberDiff line change
@@ -446,6 +446,11 @@ typedef struct AVPacketList {
446446
* be discarded by the decoder. I.e. Non-reference frames.
447447
*/
448448
#define AV_PKT_FLAG_DISPOSABLE 0x0010
449+
/**
450+
* Flag is used to indicate packets in which the duration is absolute
451+
* and should not be changed.
452+
*/
453+
#define AV_PKT_FLAG_FIXED_DURATION 0x0020
449454

450455
enum AVSideDataParamChangeFlags {
451456
#if FF_API_OLD_CHANNEL_LAYOUT

libavformat/demux.c

+3-1
Original file line numberDiff line numberDiff line change
@@ -914,7 +914,9 @@ static void update_initial_durations(AVFormatContext *s, AVStream *st,
914914
pktl->pkt.dts = cur_dts;
915915
if (!sti->avctx->has_b_frames)
916916
pktl->pkt.pts = cur_dts;
917-
pktl->pkt.duration = duration;
917+
if ((pktl->pkt.flags & AV_PKT_FLAG_FIXED_DURATION) != AV_PKT_FLAG_FIXED_DURATION)
918+
pktl->pkt.duration = duration;
919+
pktl->pkt.flags &= ~AV_PKT_FLAG_FIXED_DURATION;
918920
} else
919921
break;
920922
cur_dts = pktl->pkt.dts + pktl->pkt.duration;

libavformat/matroskadec.c

+4
Original file line numberDiff line numberDiff line change
@@ -3673,6 +3673,10 @@ static int matroska_parse_frame(MatroskaDemuxContext *matroska,
36733673
pkt->pos = pos;
36743674
pkt->duration = lace_duration;
36753675

3676+
if (st->codecpar->codec_type == AVMEDIA_TYPE_SUBTITLE &&
3677+
st->codecpar->codec_id != AV_CODEC_ID_HDMV_PGS_SUBTITLE)
3678+
pkt->flags |= AV_PKT_FLAG_FIXED_DURATION;
3679+
36763680
res = avpriv_packet_list_put(&matroska->queue, pkt, NULL, 0);
36773681
if (res < 0) {
36783682
av_packet_unref(pkt);

0 commit comments

Comments
 (0)