v4l2videodec: Keep part of the input buffer
authorNicolas Dufresne <nicolas.dufresne@collabora.com>
Tue, 7 Jun 2016 20:42:09 +0000 (16:42 -0400)
committerNicolas Dufresne <nicolas.dufresne@collabora.com>
Tue, 7 Jun 2016 21:03:40 +0000 (17:03 -0400)
Instead of completely getting rid of the input buffer, copy
the metadata, the flags and the timestamp into an empty buffer.
This way the decoder base class can copy that information again
to the output buffer.

https://bugzilla.gnome.org/show_bug.cgi?id=758424

sys/v4l2/gstv4l2videodec.c

index 0a2eace32f36d4666ed032c4a145a1234449059b..d148b66ad5a320577cb558484010a0a83998b10e 100644 (file)
@@ -522,6 +522,8 @@ gst_v4l2_video_dec_handle_frame (GstVideoDecoder * decoder,
   GstV4l2Error error = GST_V4L2_ERROR_INIT;
   GstV4l2VideoDec *self = GST_V4L2_VIDEO_DEC (decoder);
   GstFlowReturn ret = GST_FLOW_OK;
+  gboolean processed = FALSE;
+  GstBuffer *tmp;
 
   GST_DEBUG_OBJECT (self, "Handling frame %d", frame->system_frame_number);
 
@@ -555,8 +557,8 @@ gst_v4l2_video_dec_handle_frame (GstVideoDecoder * decoder,
     if (codec_data) {
       gst_buffer_ref (codec_data);
     } else {
-      codec_data = frame->input_buffer;
-      frame->input_buffer = NULL;
+      codec_data = gst_buffer_ref (frame->input_buffer);
+      processed = TRUE;
     }
 
     /* Ensure input internal pool is active */
@@ -666,7 +668,7 @@ gst_v4l2_video_dec_handle_frame (GstVideoDecoder * decoder,
       goto start_task_failed;
   }
 
-  if (frame->input_buffer) {
+  if (!processed) {
     GST_VIDEO_DECODER_STREAM_UNLOCK (decoder);
     ret =
         gst_v4l2_buffer_pool_process (GST_V4L2_BUFFER_POOL (self->v4l2output->
@@ -680,11 +682,16 @@ gst_v4l2_video_dec_handle_frame (GstVideoDecoder * decoder,
     } else if (ret != GST_FLOW_OK) {
       goto process_failed;
     }
-
-    /* No need to keep input arround */
-    gst_buffer_replace (&frame->input_buffer, NULL);
   }
 
+  /* No need to keep input arround */
+  tmp = frame->input_buffer;
+  frame->input_buffer = gst_buffer_new ();
+  gst_buffer_copy_into (frame->input_buffer, tmp,
+      GST_BUFFER_COPY_FLAGS | GST_BUFFER_COPY_TIMESTAMPS |
+      GST_BUFFER_COPY_META, 0, 0);
+  gst_buffer_unref (tmp);
+
   gst_video_codec_frame_unref (frame);
   return ret;