va: Use the GstVaSurfaceCopy of the allocator atomically.
The mem_copy() of the allocator can be called simultaneously from different threads. We should use atomic pointer operations to create and use the GstVaSurfaceCopy of the allocator. Part-of: <https://gitlab.freedesktop.org/gstreamer/gstreamer/-/merge_requests/1373>
This commit is contained in:
parent
7f31dcf084
commit
954f7cf88c
@ -258,6 +258,27 @@ struct _GstVaDmabufAllocator
|
|||||||
G_DEFINE_TYPE_WITH_CODE (GstVaDmabufAllocator, gst_va_dmabuf_allocator,
|
G_DEFINE_TYPE_WITH_CODE (GstVaDmabufAllocator, gst_va_dmabuf_allocator,
|
||||||
GST_TYPE_DMABUF_ALLOCATOR, _init_debug_category ());
|
GST_TYPE_DMABUF_ALLOCATOR, _init_debug_category ());
|
||||||
|
|
||||||
|
static GstVaSurfaceCopy *
|
||||||
|
_ensure_surface_copy (GstVaSurfaceCopy ** old, GstVaDisplay * display,
|
||||||
|
GstVideoInfo * info)
|
||||||
|
{
|
||||||
|
GstVaSurfaceCopy *surface_copy;
|
||||||
|
|
||||||
|
surface_copy = g_atomic_pointer_get (old);
|
||||||
|
if (!surface_copy) {
|
||||||
|
surface_copy = gst_va_surface_copy_new (display, info);
|
||||||
|
|
||||||
|
/* others create a new one and set it before us */
|
||||||
|
if (surface_copy &&
|
||||||
|
!g_atomic_pointer_compare_and_exchange (old, NULL, surface_copy)) {
|
||||||
|
gst_va_surface_copy_free (surface_copy);
|
||||||
|
surface_copy = g_atomic_pointer_get (old);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return surface_copy;
|
||||||
|
}
|
||||||
|
|
||||||
/* If a buffer contains multiple memories (dmabuf objects) its very
|
/* If a buffer contains multiple memories (dmabuf objects) its very
|
||||||
* difficult to provide a realiable way to fast-copy single memories:
|
* difficult to provide a realiable way to fast-copy single memories:
|
||||||
* While VA API sees surfaces with dependant dmabufs, GStreamer only
|
* While VA API sees surfaces with dependant dmabufs, GStreamer only
|
||||||
@ -294,6 +315,7 @@ gst_va_dmabuf_mem_copy (GstMemory * gmem, gssize offset, gssize size)
|
|||||||
if (offset == 0 && size == mem_size && buf->n_mems == 1) {
|
if (offset == 0 && size == mem_size && buf->n_mems == 1) {
|
||||||
GstVaBufferSurface *buf_copy = NULL;
|
GstVaBufferSurface *buf_copy = NULL;
|
||||||
GstMemory *copy;
|
GstMemory *copy;
|
||||||
|
GstVaSurfaceCopy *copy_func;
|
||||||
|
|
||||||
GST_VA_MEMORY_POOL_LOCK (&self->pool);
|
GST_VA_MEMORY_POOL_LOCK (&self->pool);
|
||||||
copy = gst_va_memory_pool_pop (&self->pool);
|
copy = gst_va_memory_pool_pop (&self->pool);
|
||||||
@ -325,9 +347,8 @@ gst_va_dmabuf_mem_copy (GstMemory * gmem, gssize offset, gssize size)
|
|||||||
|
|
||||||
g_assert (buf_copy->n_mems == 1);
|
g_assert (buf_copy->n_mems == 1);
|
||||||
|
|
||||||
if (!self->copy)
|
copy_func = _ensure_surface_copy (&self->copy, self->display, &self->info);
|
||||||
self->copy = gst_va_surface_copy_new (self->display, &self->info);
|
if (copy_func && gst_va_surface_copy (copy_func, buf_copy->surface,
|
||||||
if (self->copy && gst_va_surface_copy (self->copy, buf_copy->surface,
|
|
||||||
buf->surface))
|
buf->surface))
|
||||||
return copy;
|
return copy;
|
||||||
|
|
||||||
@ -1283,16 +1304,14 @@ _va_copy (GstMemory * mem, gssize offset, gssize size)
|
|||||||
size = mem_size > offset ? mem_size - offset : 0;
|
size = mem_size > offset ? mem_size - offset : 0;
|
||||||
|
|
||||||
if (offset == 0 && size == mem_size) {
|
if (offset == 0 && size == mem_size) {
|
||||||
if (!va_allocator->copy) {
|
GstVaSurfaceCopy *copy_func;
|
||||||
va_allocator->copy =
|
|
||||||
gst_va_surface_copy_new (va_allocator->display, &va_allocator->info);
|
copy_func = _ensure_surface_copy (&va_allocator->copy,
|
||||||
}
|
va_allocator->display, &va_allocator->info);
|
||||||
if (va_allocator->copy
|
if (copy_func
|
||||||
&& gst_va_surface_copy (va_allocator->copy, va_copy->surface,
|
&& gst_va_surface_copy (copy_func, va_copy->surface, va_mem->surface))
|
||||||
va_mem->surface)) {
|
|
||||||
return copy;
|
return copy;
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
if (!gst_memory_map (mem, &sinfo, GST_MAP_READ)) {
|
if (!gst_memory_map (mem, &sinfo, GST_MAP_READ)) {
|
||||||
GST_WARNING ("failed to map memory to copy");
|
GST_WARNING ("failed to map memory to copy");
|
||||||
|
Loading…
x
Reference in New Issue
Block a user