From: Edward Hervey Date: Thu, 22 Jul 2021 13:14:26 +0000 (+0200) Subject: tsdemux: Handle PCR-less streams X-Git-Tag: 1.19.3~507^2~164 X-Git-Url: http://review.tizen.org/git/?a=commitdiff_plain;h=a79a756b79aa1675e4ae14eced8b08cdd578d50a;p=platform%2Fupstream%2Fgstreamer.git tsdemux: Handle PCR-less streams Some programs specify a PCR PID but don't actually store any PCR values, or are way too far apart. In order to gracefully handle those situations, we will queue up to a certain amount of pending buffers before deciding to give up on that PCR PID and not use any (i.e. using DTS/PTS values as-is) Fixes https://gitlab.freedesktop.org/gstreamer/gst-plugins-bad/-/issues/1629 Part-of: --- diff --git a/gst/mpegtsdemux/tsdemux.c b/gst/mpegtsdemux/tsdemux.c index 2747f14..0a2a769 100644 --- a/gst/mpegtsdemux/tsdemux.c +++ b/gst/mpegtsdemux/tsdemux.c @@ -2261,6 +2261,7 @@ check_pending_buffers (GstTSDemux * demux) guint64 offset = 0; GList *tmp; gboolean have_only_sparse = TRUE; + gboolean exceeded_threshold = FALSE; /* 0. Do we only have sparse stream */ for (tmp = demux->program->stream_list; tmp; tmp = tmp->next) { @@ -2282,12 +2283,38 @@ check_pending_buffers (GstTSDemux * demux) have_observation = TRUE; break; } + /* 1.2 Check if we exceeded the maximum threshold of pending data */ + if (tmpstream->pending && (tmpstream->raw_dts != -1 + || tmpstream->raw_pts != -1)) { + PendingBuffer *pend = tmpstream->pending->data; + guint64 lastval = + tmpstream->raw_dts != -1 ? tmpstream->raw_dts : tmpstream->raw_pts; + guint64 firstval = pend->dts != -1 ? pend->dts : pend->pts; + GstClockTime dur; + g_assert (firstval != -1); + dur = MPEGTIME_TO_GSTTIME (lastval - firstval); + GST_DEBUG_OBJECT (tmpstream->pad, + "Pending content duration: %" GST_TIME_FORMAT, GST_TIME_ARGS (dur)); + if (dur > 500 * GST_MSECOND) { + exceeded_threshold = TRUE; + break; + } + } } } - /* 2. If we don't have a valid value yet, break out */ - if (have_observation == FALSE) - return FALSE; + if (have_observation == FALSE) { + /* 2. If we don't have a valid value yet, break out */ + if (!exceeded_threshold) + return FALSE; + + /* Except if we've exceed the maximum amount of pending buffers, in which + * case we ignore PCR from now on */ + GST_DEBUG_OBJECT (demux, + "Saw more than 500ms of data without PCR. Ignoring PCR from now on"); + GST_MPEGTS_BASE (demux)->ignore_pcr = TRUE; + demux->program->pcr_pid = 0x1fff; + } /* 3. Go over all streams that have current/pending data */ for (tmp = demux->program->stream_list; tmp; tmp = tmp->next) {