[FFmpeg-devel] Using copyts with mpegts output fails after 26, 5 hours
Panagiotis Malakoudis
malakudi at gmail.com
Thu May 2 20:13:10 EEST 2019
When outputing to mpegts format, using -copyts option makes program
fail after the oveflow of mpegts PCR happens at around 26 hours and 30
minutes. When not using -copyts, only a warning is reported.
In order to reproduce the issue, you first have to create a 27 hour
mpegts video.
I have described the problem in thorough at ticket
https://trac.ffmpeg.org/ticket/7876
The issue is resolved if you use a patch created originally by Arut
(Roman Arutyunyan) at
https://github.com/arut/ffmpeg-patches/blob/master/mpegts-33bit
I have converted the patch in order to apply with current git and
confirmed working fine, fixing the above mentioned issue. Original
author describes the patch as: "Implements smooth 33-bit mpeg-ts
timestamp overflow in mpegts muxer."
Here it is:
--- libavformat/mpegts.c 2019-04-30 16:11:49.000000000 +0300
+++ libavformat/mpegts.c 2019-04-30 18:55:12.736428766 +0300
@@ -163,6 +163,9 @@
/** structure to keep track of Program->pids mapping */
unsigned int nb_prg;
struct Program *prg;
+
+ /** base timestamp for smooth rolling over 33bits */
+ int64_t base_ts;
int8_t crc_validity[NB_PID_MAX];
/** filters for various streams specified by PMT + for the PAT and PMT */
@@ -982,6 +985,26 @@
pkt->size = len;
}
+static int64_t unroll_timestamp(MpegTSContext *ts, int64_t t)
+{
+ int64_t dt;
+
+ if (t == AV_NOPTS_VALUE)
+ return t;
+
+ if (!ts->base_ts)
+ ts->base_ts = t;
+
+ dt = (t - ts->base_ts) & 0x01ffffffffll;
+ if (dt & 0x0100000000ll) {
+ dt |= 0xffffffff00000000ll;
+ }
+
+ ts->base_ts += dt;
+
+ return ts->base_ts;
+}
+
static int new_pes_packet(PESContext *pes, AVPacket *pkt)
{
uint8_t *sd;
@@ -1005,8 +1028,8 @@
pkt->stream_index = pes->sub_st->index;
else
pkt->stream_index = pes->st->index;
- pkt->pts = pes->pts;
- pkt->dts = pes->dts;
+ pkt->pts = unroll_timestamp(pes->ts, pes->pts);
+ pkt->dts = unroll_timestamp(pes->ts, pes->dts);
/* store position of first TS packet of this PES packet */
pkt->pos = pes->ts_packet_pos;
pkt->flags = pes->flags;
More information about the ffmpeg-devel
mailing list