uvch264src: Apply timestamps to outgoing aux buffers

When extracting an aux buffer from an MJPG carrier, at
*least* put the original timestamp on it, even if we
fail to apply any other timestamp (which we always do
at the moment, because the timestamp calculating code
was never finished). Apply a DTS using the camera
supplied delay value as well, assuming that there's
no re-ordering going on (there isn't in the C920,
which is really the only extant camera doing this
stuff) and a warning if that turns out not to be true.
This commit is contained in:
Jan Schmidt 2017-05-18 15:57:22 +02:00
parent 67980f27ce
commit 47abc9a09c

View file

@ -148,6 +148,8 @@ struct _GstUvcH264MjpgDemuxPrivate
/* input segment */
GstSegment segment;
GstClockTime last_pts;
gboolean pts_reordered_warning;
};
typedef struct
@ -231,6 +233,8 @@ gst_uvc_h264_mjpg_demux_init (GstUvcH264MjpgDemux * self)
GstUvcH264MjpgDemuxPrivate);
self->priv->last_pts = GST_CLOCK_TIME_NONE;
self->priv->pts_reordered_warning = FALSE;
self->priv->device_fd = -1;
/* create the sink and src pads */
@ -369,6 +373,7 @@ gst_uvc_h264_mjpg_demux_sink_event (GstPad * pad, GstObject * parent,
switch (GST_EVENT_TYPE (event)) {
case GST_EVENT_SEGMENT:
gst_event_copy_segment (event, &self->priv->segment);
self->priv->last_pts = GST_CLOCK_TIME_NONE;
res = gst_pad_push_event (self->priv->jpeg_pad, event);
break;
case GST_EVENT_CAPS:
@ -654,6 +659,32 @@ gst_uvc_h264_mjpg_demux_chain (GstPad * pad,
/* Push completed aux data */
if (aux_size == 0) {
/* Last attempt to apply timestamp. FIXME: This
* is broken for H.264 with B-frames */
if (GST_BUFFER_PTS (aux_buf) == GST_CLOCK_TIME_NONE) {
if (!self->priv->pts_reordered_warning &&
self->priv->last_pts != GST_CLOCK_TIME_NONE &&
self->priv->last_pts > GST_BUFFER_PTS (buf)) {
GST_WARNING_OBJECT (self, "PTS went backward, timestamping "
"might be broken");
self->priv->pts_reordered_warning = TRUE;
}
self->priv->last_pts = GST_BUFFER_PTS (buf);
GST_BUFFER_PTS (aux_buf) = GST_BUFFER_PTS (buf);
}
if (GST_BUFFER_DTS (aux_buf) == GST_CLOCK_TIME_NONE) {
GstClockTime dts = GST_BUFFER_PTS (aux_buf);
GstClockTime delay = aux_header.delay * GST_MSECOND;
if (dts > delay)
dts -= delay;
else
dts = 0;
GST_BUFFER_DTS (aux_buf) = dts;
GST_LOG_OBJECT (self, "Applied DTS %" GST_TIME_FORMAT
" to aux_buf", GST_TIME_ARGS (dts));
}
GST_DEBUG_OBJECT (self, "Pushing %" GST_FOURCC_FORMAT
" auxiliary buffer %" GST_PTR_FORMAT,
GST_FOURCC_ARGS (aux_header.type), *aux_caps);