pleorasrc: fix handling of strides that aren't 32-bit aligned

For example, a Mono8 642x482 would have failed to work, as GStreamer
expects the stride to be a multiple of 4-bytes, that is 644 bytes in
this example, while Pleora doesn't do this alignment. This incurs a copy
unfortunately, and there might be a way with memory meta to avoid this,
however eventually most elements will need to have the data 4-byte
aligned.
This commit is contained in:
Joshua M. Doe 2019-08-29 14:56:18 -04:00
parent 64866758a2
commit e364cfe4d5
2 changed files with 36 additions and 11 deletions

View File

@ -804,8 +804,6 @@ static gboolean
gst_pleorasrc_start (GstBaseSrc * bsrc)
{
GstPleoraSrc *src = GST_PLEORA_SRC (bsrc);
guint32 width, height, bpp, stride;
GstVideoInfo vinfo;
PvResult pvRes;
GST_DEBUG_OBJECT (src, "start");
@ -953,7 +951,9 @@ gst_pleorasrc_set_caps (GstBaseSrc * bsrc, GstCaps * caps)
gst_video_info_from_caps (&vinfo, caps);
if (GST_VIDEO_INFO_FORMAT (&vinfo) != GST_VIDEO_FORMAT_UNKNOWN) {
src->height = GST_VIDEO_INFO_HEIGHT (&vinfo);
src->gst_stride = GST_VIDEO_INFO_COMP_STRIDE (&vinfo, 0);
src->pleora_stride = GST_VIDEO_INFO_WIDTH (&vinfo) * GST_VIDEO_INFO_COMP_PSTRIDE (&vinfo, 0);
} else {
goto unsupported_caps;
}
@ -1112,16 +1112,41 @@ gst_pleorasrc_create (GstPushSrc * psrc, GstBuffer ** buf)
return GST_FLOW_ERROR;
}
VideoFrame *vf = g_new0 (VideoFrame, 1);
vf->src = src;
vf->buffer = pvbuffer;
gpointer data = pvimage->GetDataPointer ();
gsize data_size = pvimage->GetImageSize ();
*buf =
gst_buffer_new_wrapped_full ((GstMemoryFlags) GST_MEMORY_FLAG_READONLY,
(gpointer) data, data_size, 0, data_size, vf,
(GDestroyNotify) pvbuffer_release);
if (src->pleora_stride == src->gst_stride) {
VideoFrame *vf = g_new0 (VideoFrame, 1);
vf->src = src;
vf->buffer = pvbuffer;
gsize data_size = pvimage->GetImageSize ();
*buf =
gst_buffer_new_wrapped_full ((GstMemoryFlags) GST_MEMORY_FLAG_READONLY,
(gpointer) data, data_size, 0, data_size, vf,
(GDestroyNotify) pvbuffer_release);
} else {
GstMapInfo minfo;
GST_LOG_OBJECT (src,
"Row stride not aligned, copying %d -> %d",
src->pleora_stride, src->gst_stride);
*buf = gst_buffer_new_and_alloc (src->height * src->gst_stride);
guint8 *s = (guint8*)data;
guint8 *d;
gst_buffer_map (*buf, &minfo, GST_MAP_WRITE);
d = minfo.data;
g_assert (minfo.size >= src->pleora_stride * src->height);
for (int i = 0; i < src->height; i++)
memcpy (d + i * src->gst_stride, s + i * src->pleora_stride,
src->pleora_stride);
gst_buffer_unmap (*buf, &minfo);
src->pipeline->ReleaseBuffer (pvbuffer);
}
clock = gst_element_get_clock (GST_ELEMENT (src));
clock_time = gst_clock_get_time (clock);
gst_object_unref (clock);

View File

@ -62,7 +62,7 @@ struct _GstPleoraSrc
GstCaps *caps;
gint height;
gint gst_stride;
gint bf_stride;
gint pleora_stride;
gboolean stop_requested;
};