mirror of
https://gitlab.freedesktop.org/gstreamer/gstreamer.git
synced 2025-02-20 04:56:24 +00:00
omxbufferpool: use gst_video_meta_set_alignment()
Tell buffer consumer about our paddings. v4l2src can now uses these paddings information when trying to import buffers to configure the v4l2 driver accordingly.
This commit is contained in:
parent
611f37c2ae
commit
800cc4bd67
3 changed files with 105 additions and 1 deletions
|
@ -26,6 +26,7 @@
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#include "gstomxbufferpool.h"
|
#include "gstomxbufferpool.h"
|
||||||
|
#include "gstomxvideo.h"
|
||||||
|
|
||||||
#include <gst/allocators/gstdmabuf.h>
|
#include <gst/allocators/gstdmabuf.h>
|
||||||
|
|
||||||
|
@ -410,11 +411,18 @@ gst_omx_buffer_pool_alloc_buffer (GstBufferPool * bpool,
|
||||||
/* We always add the videometa. It's the job of the user
|
/* We always add the videometa. It's the job of the user
|
||||||
* to copy the buffer if pool->need_copy is TRUE
|
* to copy the buffer if pool->need_copy is TRUE
|
||||||
*/
|
*/
|
||||||
gst_buffer_add_video_meta_full (buf, GST_VIDEO_FRAME_FLAG_NONE,
|
GstVideoMeta *meta;
|
||||||
|
GstVideoAlignment align;
|
||||||
|
|
||||||
|
meta = gst_buffer_add_video_meta_full (buf, GST_VIDEO_FRAME_FLAG_NONE,
|
||||||
GST_VIDEO_INFO_FORMAT (&pool->video_info),
|
GST_VIDEO_INFO_FORMAT (&pool->video_info),
|
||||||
GST_VIDEO_INFO_WIDTH (&pool->video_info),
|
GST_VIDEO_INFO_WIDTH (&pool->video_info),
|
||||||
GST_VIDEO_INFO_HEIGHT (&pool->video_info),
|
GST_VIDEO_INFO_HEIGHT (&pool->video_info),
|
||||||
GST_VIDEO_INFO_N_PLANES (&pool->video_info), offset, stride);
|
GST_VIDEO_INFO_N_PLANES (&pool->video_info), offset, stride);
|
||||||
|
|
||||||
|
if (gst_omx_video_get_port_padding (pool->port, &pool->video_info,
|
||||||
|
&align))
|
||||||
|
gst_video_meta_set_alignment (meta, align);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -254,3 +254,96 @@ gst_omx_video_is_equal_framerate_q16 (OMX_U32 q16_a, OMX_U32 q16_b)
|
||||||
* an unnecessary re-negotiation. */
|
* an unnecessary re-negotiation. */
|
||||||
return fabs (((gdouble) q16_a) - ((gdouble) q16_b)) / (gdouble) q16_b < 0.01;
|
return fabs (((gdouble) q16_a) - ((gdouble) q16_b)) / (gdouble) q16_b < 0.01;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
gboolean
|
||||||
|
gst_omx_video_get_port_padding (GstOMXPort * port, GstVideoInfo * info_orig,
|
||||||
|
GstVideoAlignment * align)
|
||||||
|
{
|
||||||
|
guint nstride;
|
||||||
|
guint nslice_height;
|
||||||
|
GstVideoInfo info;
|
||||||
|
gsize plane_size[GST_VIDEO_MAX_PLANES];
|
||||||
|
|
||||||
|
gst_video_alignment_reset (align);
|
||||||
|
|
||||||
|
/* Create a copy of @info_orig without any offset/stride as we need a
|
||||||
|
* 'standard' version to compute the paddings. */
|
||||||
|
gst_video_info_init (&info);
|
||||||
|
gst_video_info_set_interlaced_format (&info,
|
||||||
|
GST_VIDEO_INFO_FORMAT (info_orig),
|
||||||
|
GST_VIDEO_INFO_INTERLACE_MODE (info_orig),
|
||||||
|
GST_VIDEO_INFO_WIDTH (info_orig), GST_VIDEO_INFO_HEIGHT (info_orig));
|
||||||
|
|
||||||
|
/* Retrieve the plane sizes */
|
||||||
|
if (!gst_video_info_align_full (&info, align, plane_size)) {
|
||||||
|
GST_WARNING_OBJECT (port->comp->parent, "Failed to retrieve plane sizes");
|
||||||
|
return FALSE;
|
||||||
|
}
|
||||||
|
|
||||||
|
nstride = port->port_def.format.video.nStride;
|
||||||
|
nslice_height = port->port_def.format.video.nSliceHeight;
|
||||||
|
|
||||||
|
if (nstride > GST_VIDEO_INFO_PLANE_STRIDE (&info, 0)) {
|
||||||
|
align->padding_right = nstride - GST_VIDEO_INFO_PLANE_STRIDE (&info, 0);
|
||||||
|
|
||||||
|
if (GST_VIDEO_FORMAT_INFO_IS_COMPLEX (info.finfo)) {
|
||||||
|
/* Stride is in bytes while padding is in pixels so we need to do manual
|
||||||
|
* conversions for complex formats. */
|
||||||
|
switch (GST_VIDEO_INFO_FORMAT (&info)) {
|
||||||
|
case GST_VIDEO_FORMAT_NV12_10LE32:
|
||||||
|
case GST_VIDEO_FORMAT_NV16_10LE32:
|
||||||
|
/* Need ((width + 2) / 3) 32-bits words to store one row,
|
||||||
|
* see unpack_NV12_10LE32 in -base.
|
||||||
|
*
|
||||||
|
* So let's say:
|
||||||
|
* - W = the width, in pixels
|
||||||
|
* - S = the stride, in bytes
|
||||||
|
* - P = the padding, in bytes
|
||||||
|
* - Δ = the padding, in pixels
|
||||||
|
*
|
||||||
|
* we then have:
|
||||||
|
* S = ((W+2)/3) * 4
|
||||||
|
* S+P = ((W+2+Δ)/3) * 4
|
||||||
|
*
|
||||||
|
* By solving this system we get:
|
||||||
|
* Δ = (3/4) * P
|
||||||
|
*/
|
||||||
|
align->padding_right *= 0.75;
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
GST_FIXME_OBJECT (port->comp->parent,
|
||||||
|
"Stride conversion is not supported for format %s",
|
||||||
|
GST_VIDEO_INFO_NAME (&info));
|
||||||
|
return FALSE;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
GST_LOG_OBJECT (port->comp->parent,
|
||||||
|
"OMX stride (%d) is higher than standard (%d) for port %u; right padding: %d",
|
||||||
|
nstride, GST_VIDEO_INFO_PLANE_STRIDE (&info, 0), port->index,
|
||||||
|
align->padding_right);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (nslice_height > GST_VIDEO_INFO_PLANE_HEIGHT (&info, 0, plane_size)) {
|
||||||
|
align->padding_bottom =
|
||||||
|
nslice_height - GST_VIDEO_INFO_PLANE_HEIGHT (&info, 0, plane_size);
|
||||||
|
|
||||||
|
if (GST_VIDEO_INFO_INTERLACE_MODE (&info) ==
|
||||||
|
GST_VIDEO_INTERLACE_MODE_ALTERNATE) {
|
||||||
|
/* GstVideoAlignment defines the alignment for the full frame while
|
||||||
|
* OMX gives us the slice height for a single field, so we have to
|
||||||
|
* double the vertical padding. */
|
||||||
|
GST_DEBUG_OBJECT (port->comp->parent,
|
||||||
|
"Double bottom padding because of alternate stream");
|
||||||
|
align->padding_bottom *= 2;
|
||||||
|
}
|
||||||
|
|
||||||
|
GST_LOG_OBJECT (port->comp->parent,
|
||||||
|
"OMX slice height (%d) is higher than standard (%" G_GSIZE_FORMAT
|
||||||
|
") for port %u; vertical padding: %d", nslice_height,
|
||||||
|
GST_VIDEO_INFO_PLANE_HEIGHT (&info, 0, plane_size), port->index,
|
||||||
|
align->padding_bottom);
|
||||||
|
}
|
||||||
|
|
||||||
|
return TRUE;
|
||||||
|
}
|
||||||
|
|
|
@ -63,6 +63,9 @@ OMX_U32 gst_omx_video_calculate_framerate_q16 (GstVideoInfo * info);
|
||||||
|
|
||||||
gboolean gst_omx_video_is_equal_framerate_q16 (OMX_U32 q16_a, OMX_U32 q16_b);
|
gboolean gst_omx_video_is_equal_framerate_q16 (OMX_U32 q16_a, OMX_U32 q16_b);
|
||||||
|
|
||||||
|
gboolean gst_omx_video_get_port_padding (GstOMXPort * port, GstVideoInfo * info_orig,
|
||||||
|
GstVideoAlignment * align);
|
||||||
|
|
||||||
G_END_DECLS
|
G_END_DECLS
|
||||||
|
|
||||||
#endif /* __GST_OMX_VIDEO_H__ */
|
#endif /* __GST_OMX_VIDEO_H__ */
|
||||||
|
|
Loading…
Reference in a new issue