v4l2: Keep decoder capture fps same as output fps if it's not set
authorHou Qi <qi.hou@nxp.com>
Tue, 27 Jul 2021 02:43:21 +0000 (10:43 +0800)
committerHou Qi <qi.hou@nxp.com>
Mon, 2 Aug 2021 09:37:52 +0000 (17:37 +0800)
Part-of: <https://gitlab.freedesktop.org/gstreamer/gst-plugins-good/-/merge_requests/1035>

sys/v4l2/gstv4l2object.c
sys/v4l2/gstv4l2videodec.c

index 813f9cb..db60cbc 100644 (file)
@@ -2219,6 +2219,26 @@ done:
   return ret;
 }
 
+static gboolean
+gst_v4l2_object_get_streamparm (GstV4l2Object * v4l2object, GstVideoInfo * info)
+{
+  struct v4l2_streamparm streamparm;
+  memset (&streamparm, 0x00, sizeof (struct v4l2_streamparm));
+  streamparm.type = v4l2object->type;
+  if (v4l2object->ioctl (v4l2object->video_fd, VIDIOC_G_PARM, &streamparm) < 0) {
+    GST_WARNING_OBJECT (v4l2object->dbg_obj, "VIDIOC_G_PARM failed");
+    return FALSE;
+  }
+  if (v4l2object->type == V4L2_BUF_TYPE_VIDEO_CAPTURE
+      || v4l2object->type == V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE) {
+    GST_VIDEO_INFO_FPS_N (info) =
+        streamparm.parm.capture.timeperframe.denominator;
+    GST_VIDEO_INFO_FPS_D (info) =
+        streamparm.parm.capture.timeperframe.numerator;
+  }
+  return TRUE;
+}
+
 static int
 gst_v4l2_object_try_fmt (GstV4l2Object * v4l2object,
     struct v4l2_format *try_fmt)
@@ -4218,6 +4238,14 @@ gst_v4l2_object_acquire_format (GstV4l2Object * v4l2object, GstVideoInfo * info)
       height);
 
   gst_v4l2_object_get_colorspace (v4l2object, &fmt, &info->colorimetry);
+  gst_v4l2_object_get_streamparm (v4l2object, info);
+  if ((info->fps_n == 0) && (v4l2object->type == V4L2_BUF_TYPE_VIDEO_CAPTURE
+          || v4l2object->type == V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE)) {
+    info->fps_d = v4l2object->info.fps_d;
+    info->fps_n = v4l2object->info.fps_n;
+    GST_DEBUG_OBJECT (v4l2object->dbg_obj, "Set capture fps to %d/%d",
+        info->fps_n, info->fps_d);
+  }
 
   gst_v4l2_object_save_format (v4l2object, fmtdesc, &fmt, info, &align);
 
index 65a9d40..097f3ca 100644 (file)
@@ -690,6 +690,10 @@ gst_v4l2_video_dec_handle_frame (GstVideoDecoder * decoder,
 
     gst_buffer_unref (codec_data);
 
+    /* init capture fps according to output */
+    self->v4l2capture->info.fps_d = self->v4l2output->info.fps_d;
+    self->v4l2capture->info.fps_n = self->v4l2output->info.fps_n;
+
     /* For decoders G_FMT returns coded size, G_SELECTION returns visible size
      * in the compose rectangle. gst_v4l2_object_acquire_format() checks both
      * and returns the visible size as with/height and the coded size as