diff options
Diffstat (limited to 'common/recipes-multimedia/gstreamer/gst-plugins-good/0022-videocrop-move-output-buffer-size-calculation-to-tra.patch')
-rw-r--r-- | common/recipes-multimedia/gstreamer/gst-plugins-good/0022-videocrop-move-output-buffer-size-calculation-to-tra.patch | 178 |
1 files changed, 178 insertions, 0 deletions
diff --git a/common/recipes-multimedia/gstreamer/gst-plugins-good/0022-videocrop-move-output-buffer-size-calculation-to-tra.patch b/common/recipes-multimedia/gstreamer/gst-plugins-good/0022-videocrop-move-output-buffer-size-calculation-to-tra.patch new file mode 100644 index 0000000..1c62e0d --- /dev/null +++ b/common/recipes-multimedia/gstreamer/gst-plugins-good/0022-videocrop-move-output-buffer-size-calculation-to-tra.patch @@ -0,0 +1,178 @@ +From e22281e0458c48f1d38b7a2abf20121378a811f8 Mon Sep 17 00:00:00 2001 +From: Kazunori Kobayashi <kkobayas@igel.co.jp> +Date: Thu, 18 Oct 2012 18:27:03 +0900 +Subject: [PATCH 22/31] videocrop: move output buffer size calculation to + transform_size() + +transform_size() is the optional method that can be overridden to +calculate buffer sizes. The default implementation uses get_unit_size(), +but when performing zero-copy cropping, transform_size() should be used +because the buffer size calculation is different from the default. +The buffer size calculation should be performed using the tranform_size() +override, rather than being inlined in prepare_output_buffer(). +--- + gst/videocrop/gstvideocrop.c | 120 +++++++++++++++++++++++++++++++++--------- + 1 file changed, 95 insertions(+), 25 deletions(-) + +diff --git a/gst/videocrop/gstvideocrop.c b/gst/videocrop/gstvideocrop.c +index 4d2a027..4887137 100644 +--- a/gst/videocrop/gstvideocrop.c ++++ b/gst/videocrop/gstvideocrop.c +@@ -140,6 +140,9 @@ static gboolean gst_video_crop_src_event (GstBaseTransform * trans, + static GstFlowReturn gst_video_crop_prepare_output_buffer (GstBaseTransform * + trans, GstBuffer * input, gint size, GstCaps * caps, GstBuffer ** buf); + static gboolean gst_video_crop_query_stride_supported (GstVideoCrop * vcrop); ++static gboolean gst_videocrop_transform_size (GstBaseTransform * trans, ++ GstPadDirection direction, GstCaps * caps, guint size, GstCaps * othercaps, ++ guint * othersize); + + static void + gst_video_crop_base_init (gpointer g_class) +@@ -234,6 +237,8 @@ gst_video_crop_class_init (GstVideoCropClass * klass) + GST_DEBUG_FUNCPTR (gst_video_crop_get_unit_size); + basetransform_class->prepare_output_buffer = + GST_DEBUG_FUNCPTR (gst_video_crop_prepare_output_buffer); ++ basetransform_class->transform_size = ++ GST_DEBUG_FUNCPTR (gst_videocrop_transform_size); + + basetransform_class->passthrough_on_same_caps = FALSE; + basetransform_class->src_event = GST_DEBUG_FUNCPTR (gst_video_crop_src_event); +@@ -838,7 +843,6 @@ gst_video_crop_prepare_output_buffer (GstBaseTransform * trans, + GstBuffer * input, gint size, GstCaps * caps, GstBuffer ** buf) + { + GstVideoCrop *vcrop = GST_VIDEO_CROP (trans); +- guint sub_offset, sub_size; + + if (!gst_video_crop_query_stride_supported (vcrop)) { + GST_LOG_OBJECT +@@ -847,30 +851,7 @@ gst_video_crop_prepare_output_buffer (GstBaseTransform * trans, + return GST_FLOW_OK; + } + +- if (vcrop->in.packing == VIDEO_CROP_PIXEL_FORMAT_PACKED_SIMPLE) { +- sub_offset = (vcrop->crop_top * vcrop->in.stride) + +- (vcrop->crop_left * vcrop->in.bytes_per_pixel); +- } else if (vcrop->in.packing == VIDEO_CROP_PIXEL_FORMAT_PACKED_COMPLEX) { +- sub_offset = (vcrop->crop_top * vcrop->in.stride) + +- (ROUND_DOWN_2 (vcrop->crop_left) * vcrop->in.bytes_per_pixel); +- } else if (vcrop->in.packing == VIDEO_CROP_PIXEL_FORMAT_SEMI_PLANAR) { +- GstStructure *structure; +- +- structure = gst_caps_get_structure (caps, 0); +- if (vcrop->interlaced) +- sub_offset = (vcrop->crop_top / 2 * vcrop->in.stride) + +- ROUND_DOWN_2 (vcrop->crop_left); +- else +- sub_offset = (vcrop->crop_top * vcrop->in.stride) + +- ROUND_DOWN_2 (vcrop->crop_left); +- } else { +- GST_LOG_OBJECT (vcrop, +- "can't do zero-copy cropping except for packed format"); +- return GST_FLOW_OK; +- } +- +- sub_size = vcrop->in.size - sub_offset; +- *buf = gst_buffer_create_sub (input, sub_offset, sub_size); ++ *buf = gst_buffer_create_sub (input, vcrop->in.size - size, size); + if (*buf == NULL) { + GST_ERROR_OBJECT (vcrop, "failed to create subbuffer"); + return GST_FLOW_ERROR; +@@ -880,6 +861,95 @@ gst_video_crop_prepare_output_buffer (GstBaseTransform * trans, + return GST_FLOW_OK; + } + ++static gboolean ++gst_videocrop_transform_size (GstBaseTransform * trans, ++ GstPadDirection direction, GstCaps * caps, guint size, GstCaps * othercaps, ++ guint * othersize) ++{ ++ GstVideoCrop *vcrop = GST_VIDEO_CROP (trans); ++ guint inunitsize; ++ ++ if (!gst_video_crop_query_stride_supported (vcrop) || ++ direction == GST_PAD_SRC) { ++ guint outunitsize, units; ++ ++ if (!gst_video_crop_get_unit_size (trans, caps, &inunitsize)) ++ goto no_in_size; ++ ++ GST_DEBUG_OBJECT (vcrop, "input size %d, input unit size %d", size, ++ inunitsize); ++ ++ /* input size must be a multiple of the unit_size of the input caps */ ++ if (inunitsize == 0 || (size % inunitsize != 0)) ++ goto no_multiple; ++ ++ /* get the amount of units */ ++ units = size / inunitsize; ++ ++ /* now get the unit size of the output */ ++ if (!gst_video_crop_get_unit_size (trans, othercaps, &outunitsize)) ++ goto no_out_size; ++ ++ /* the output size is the unit_size times the amount of units on the ++ * input */ ++ *othersize = units * outunitsize; ++ } else { ++ guint sub_offset; ++ ++ /* Calculate a subbufer size for zero-copy cropping. The subbuffer is ++ created in prepare_output_buffer (). */ ++ if (vcrop->in.packing == VIDEO_CROP_PIXEL_FORMAT_PACKED_SIMPLE) { ++ sub_offset = (vcrop->crop_top * vcrop->in.stride) + ++ (vcrop->crop_left * vcrop->in.bytes_per_pixel); ++ } else if (vcrop->in.packing == VIDEO_CROP_PIXEL_FORMAT_PACKED_COMPLEX) { ++ sub_offset = (vcrop->crop_top * vcrop->in.stride) + ++ (ROUND_DOWN_2 (vcrop->crop_left) * vcrop->in.bytes_per_pixel); ++ } else if (vcrop->in.packing == VIDEO_CROP_PIXEL_FORMAT_SEMI_PLANAR) { ++ GstStructure *structure; ++ ++ structure = gst_caps_get_structure (caps, 0); ++ if (vcrop->interlaced) ++ sub_offset = (vcrop->crop_top / 2 * vcrop->in.stride) + ++ ROUND_DOWN_2 (vcrop->crop_left); ++ else ++ sub_offset = (vcrop->crop_top * vcrop->in.stride) + ++ ROUND_DOWN_2 (vcrop->crop_left); ++ } else { ++ GST_LOG_OBJECT (vcrop, ++ "can't do zero-copy cropping except for packed format"); ++ return FALSE; ++ } ++ ++ *othersize = vcrop->in.size - sub_offset; ++ } ++ ++ GST_DEBUG_OBJECT (vcrop, "transformed size to %d", *othersize); ++ ++ return TRUE; ++ ++ /* ERRORS */ ++no_in_size: ++ { ++ GST_DEBUG_OBJECT (vcrop, "could not get in_size"); ++ g_warning ("%s: could not get in_size", GST_ELEMENT_NAME (trans)); ++ return FALSE; ++ } ++no_multiple: ++ { ++ GST_DEBUG_OBJECT (vcrop, "Size %u is not a multiple of unit size %u", size, ++ inunitsize); ++ g_warning ("%s: size %u is not a multiple of unit size %u", ++ GST_ELEMENT_NAME (trans), size, inunitsize); ++ return FALSE; ++ } ++no_out_size: ++ { ++ GST_DEBUG_OBJECT (vcrop, "could not get out_size"); ++ g_warning ("%s: could not get out_size", GST_ELEMENT_NAME (trans)); ++ return FALSE; ++ } ++} ++ + static void + gst_video_crop_set_property (GObject * object, guint prop_id, + const GValue * value, GParamSpec * pspec) +-- +1.7.9.5 + |