mirror of
https://gitlab.freedesktop.org/gstreamer/gstreamer.git
synced 2024-11-24 02:31:03 +00:00
va: allocator: add a memory pool object helper
Since both allocators use a memory pool, with its mutex and cond, this patch refactors it into a single internal object, implementing a generic GstMemory pool. Part-of: <https://gitlab.freedesktop.org/gstreamer/gst-plugins-bad/-/merge_requests/1815>
This commit is contained in:
parent
8c128ead6d
commit
8e6ad8267f
1 changed files with 144 additions and 96 deletions
|
@ -358,14 +358,54 @@ gst_va_buffer_surface_new (VASurfaceID surface, GstVideoFormat format,
|
||||||
return buf;
|
return buf;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/*=========================== GstVaMemoryPool ================================*/
|
||||||
|
|
||||||
|
/* queue for disposed surfaces */
|
||||||
|
typedef struct _GstVaMemoryPool GstVaMemoryPool;
|
||||||
|
struct _GstVaMemoryPool
|
||||||
|
{
|
||||||
|
GstAtomicQueue *queue;
|
||||||
|
gint surface_count;
|
||||||
|
|
||||||
|
GMutex lock;
|
||||||
|
GCond cond;
|
||||||
|
|
||||||
|
gboolean flushing;
|
||||||
|
};
|
||||||
|
|
||||||
|
#define GST_VA_MEMORY_POOL_CAST(obj) ((GstVaMemoryPool *)obj)
|
||||||
|
#define GST_VA_MEMORY_POOL_LOCK(obj) g_mutex_lock (&GST_VA_MEMORY_POOL_CAST(obj)->lock)
|
||||||
|
#define GST_VA_MEMORY_POOL_UNLOCK(obj) g_mutex_unlock (&GST_VA_MEMORY_POOL_CAST(obj)->lock)
|
||||||
|
|
||||||
static void
|
static void
|
||||||
_available_mems_flush (GstVaDisplay * display, GstAtomicQueue * available_mems,
|
gst_va_memory_pool_init (GstVaMemoryPool * self)
|
||||||
gint * surface_count)
|
{
|
||||||
|
self->queue = gst_atomic_queue_new (2);
|
||||||
|
|
||||||
|
g_mutex_init (&self->lock);
|
||||||
|
g_cond_init (&self->cond);
|
||||||
|
|
||||||
|
self->flushing = FALSE;
|
||||||
|
self->surface_count = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
gst_va_memory_pool_finalize (GstVaMemoryPool * self)
|
||||||
|
{
|
||||||
|
g_mutex_clear (&self->lock);
|
||||||
|
g_cond_clear (&self->cond);
|
||||||
|
|
||||||
|
gst_atomic_queue_unref (self->queue);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
gst_va_memory_pool_flush_unlocked (GstVaMemoryPool * self,
|
||||||
|
GstVaDisplay * display)
|
||||||
{
|
{
|
||||||
GstMemory *mem;
|
GstMemory *mem;
|
||||||
GstVaBufferSurface *buf;
|
GstVaBufferSurface *buf;
|
||||||
|
|
||||||
while ((mem = gst_atomic_queue_pop (available_mems))) {
|
while ((mem = gst_atomic_queue_pop (self->queue))) {
|
||||||
/* destroy the surface */
|
/* destroy the surface */
|
||||||
buf = gst_mini_object_get_qdata (GST_MINI_OBJECT (mem),
|
buf = gst_mini_object_get_qdata (GST_MINI_OBJECT (mem),
|
||||||
gst_va_buffer_surface_quark ());
|
gst_va_buffer_surface_quark ());
|
||||||
|
@ -373,11 +413,11 @@ _available_mems_flush (GstVaDisplay * display, GstAtomicQueue * available_mems,
|
||||||
if (g_atomic_int_dec_and_test (&buf->ref_count)) {
|
if (g_atomic_int_dec_and_test (&buf->ref_count)) {
|
||||||
GST_LOG ("Destroying surface %#x", buf->surface);
|
GST_LOG ("Destroying surface %#x", buf->surface);
|
||||||
_destroy_surfaces (display, &buf->surface, 1);
|
_destroy_surfaces (display, &buf->surface, 1);
|
||||||
*surface_count -= 1; /* GstVaDmabufAllocator */
|
self->surface_count -= 1; /* GstVaDmabufAllocator */
|
||||||
g_slice_free (GstVaBufferSurface, buf);
|
g_slice_free (GstVaBufferSurface, buf);
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
*surface_count -= 1; /* GstVaAllocator */
|
self->surface_count -= 1; /* GstVaAllocator */
|
||||||
}
|
}
|
||||||
|
|
||||||
GST_MINI_OBJECT_CAST (mem)->dispose = NULL;
|
GST_MINI_OBJECT_CAST (mem)->dispose = NULL;
|
||||||
|
@ -389,27 +429,78 @@ _available_mems_flush (GstVaDisplay * display, GstAtomicQueue * available_mems,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
gst_va_memory_pool_flush (GstVaMemoryPool * self, GstVaDisplay * display)
|
||||||
|
{
|
||||||
|
GST_VA_MEMORY_POOL_LOCK (self);
|
||||||
|
|
||||||
|
self->flushing = TRUE;
|
||||||
|
gst_va_memory_pool_flush_unlocked (self, display);
|
||||||
|
self->flushing = FALSE;
|
||||||
|
|
||||||
|
g_cond_broadcast (&self->cond);
|
||||||
|
|
||||||
|
GST_VA_MEMORY_POOL_UNLOCK (self);
|
||||||
|
}
|
||||||
|
|
||||||
|
static inline void
|
||||||
|
gst_va_memory_pool_push (GstVaMemoryPool * self, GstMemory * mem)
|
||||||
|
{
|
||||||
|
GST_VA_MEMORY_POOL_LOCK (self);
|
||||||
|
|
||||||
|
gst_atomic_queue_push (self->queue, gst_memory_ref (mem));
|
||||||
|
g_cond_signal (&self->cond);
|
||||||
|
|
||||||
|
GST_VA_MEMORY_POOL_UNLOCK (self);
|
||||||
|
}
|
||||||
|
|
||||||
|
static inline GstMemory *
|
||||||
|
gst_va_memory_pool_pop (GstVaMemoryPool * self)
|
||||||
|
{
|
||||||
|
return gst_atomic_queue_pop (self->queue);
|
||||||
|
}
|
||||||
|
|
||||||
|
static inline GstMemory *
|
||||||
|
gst_va_memory_pool_peek (GstVaMemoryPool * self)
|
||||||
|
{
|
||||||
|
return gst_atomic_queue_peek (self->queue);
|
||||||
|
}
|
||||||
|
|
||||||
|
static gboolean
|
||||||
|
gst_va_memory_pool_wait_unlocked (GstVaMemoryPool * self)
|
||||||
|
{
|
||||||
|
while (gst_atomic_queue_length (self->queue) == 0 && !self->flushing)
|
||||||
|
g_cond_wait (&self->cond, &self->lock);
|
||||||
|
|
||||||
|
return !self->flushing;
|
||||||
|
}
|
||||||
|
|
||||||
|
static inline guint
|
||||||
|
gst_va_memory_pool_surface_count (GstVaMemoryPool * self)
|
||||||
|
{
|
||||||
|
return g_atomic_int_get (&self->surface_count);
|
||||||
|
}
|
||||||
|
|
||||||
|
static inline void
|
||||||
|
gst_va_memory_pool_surface_inc (GstVaMemoryPool * self)
|
||||||
|
{
|
||||||
|
g_atomic_int_inc (&self->surface_count);
|
||||||
|
}
|
||||||
|
|
||||||
/*=========================== GstVaDmabufAllocator ===========================*/
|
/*=========================== GstVaDmabufAllocator ===========================*/
|
||||||
|
|
||||||
struct _GstVaDmabufAllocator
|
struct _GstVaDmabufAllocator
|
||||||
{
|
{
|
||||||
GstDmaBufAllocator parent;
|
GstDmaBufAllocator parent;
|
||||||
|
|
||||||
/* queue for disposed surfaces */
|
|
||||||
GstAtomicQueue *available_mems;
|
|
||||||
gint surface_count;
|
|
||||||
|
|
||||||
GstVaDisplay *display;
|
GstVaDisplay *display;
|
||||||
|
|
||||||
GstMemoryMapFunction parent_map;
|
GstMemoryMapFunction parent_map;
|
||||||
|
|
||||||
GMutex buffer_lock;
|
|
||||||
GCond buffer_cond;
|
|
||||||
|
|
||||||
GstVideoInfo info;
|
GstVideoInfo info;
|
||||||
guint usage_hint;
|
guint usage_hint;
|
||||||
|
|
||||||
gboolean flushing;
|
GstVaMemoryPool pool;
|
||||||
};
|
};
|
||||||
|
|
||||||
#define gst_va_dmabuf_allocator_parent_class dmabuf_parent_class
|
#define gst_va_dmabuf_allocator_parent_class dmabuf_parent_class
|
||||||
|
@ -445,10 +536,8 @@ gst_va_dmabuf_allocator_finalize (GObject * object)
|
||||||
{
|
{
|
||||||
GstVaDmabufAllocator *self = GST_VA_DMABUF_ALLOCATOR (object);
|
GstVaDmabufAllocator *self = GST_VA_DMABUF_ALLOCATOR (object);
|
||||||
|
|
||||||
gst_atomic_queue_unref (self->available_mems);
|
gst_va_memory_pool_finalize (&self->pool);
|
||||||
gst_clear_object (&self->display);
|
gst_clear_object (&self->display);
|
||||||
g_mutex_clear (&self->buffer_lock);
|
|
||||||
g_cond_clear (&self->buffer_cond);
|
|
||||||
|
|
||||||
G_OBJECT_CLASS (dmabuf_parent_class)->finalize (object);
|
G_OBJECT_CLASS (dmabuf_parent_class)->finalize (object);
|
||||||
}
|
}
|
||||||
|
@ -458,10 +547,11 @@ gst_va_dmabuf_allocator_dispose (GObject * object)
|
||||||
{
|
{
|
||||||
GstVaDmabufAllocator *self = GST_VA_DMABUF_ALLOCATOR (object);
|
GstVaDmabufAllocator *self = GST_VA_DMABUF_ALLOCATOR (object);
|
||||||
|
|
||||||
_available_mems_flush (self->display, self->available_mems,
|
gst_va_memory_pool_flush_unlocked (&self->pool, self->display);
|
||||||
&self->surface_count);
|
if (gst_va_memory_pool_surface_count (&self->pool) != 0) {
|
||||||
if (self->surface_count != 0)
|
GST_WARNING_OBJECT (self, "Surfaces leaked: %d",
|
||||||
GST_WARNING_OBJECT (self, "Surfaces leaked: %d", self->surface_count);
|
gst_va_memory_pool_surface_count (&self->pool));
|
||||||
|
}
|
||||||
|
|
||||||
G_OBJECT_CLASS (dmabuf_parent_class)->dispose (object);
|
G_OBJECT_CLASS (dmabuf_parent_class)->dispose (object);
|
||||||
}
|
}
|
||||||
|
@ -478,10 +568,7 @@ gst_va_dmabuf_allocator_class_init (GstVaDmabufAllocatorClass * klass)
|
||||||
static void
|
static void
|
||||||
gst_va_dmabuf_allocator_init (GstVaDmabufAllocator * self)
|
gst_va_dmabuf_allocator_init (GstVaDmabufAllocator * self)
|
||||||
{
|
{
|
||||||
self->available_mems = gst_atomic_queue_new (2);
|
gst_va_memory_pool_init (&self->pool);
|
||||||
g_mutex_init (&self->buffer_lock);
|
|
||||||
g_cond_init (&self->buffer_cond);
|
|
||||||
|
|
||||||
self->parent_map = GST_ALLOCATOR (self)->mem_map;
|
self->parent_map = GST_ALLOCATOR (self)->mem_map;
|
||||||
GST_ALLOCATOR (self)->mem_map = gst_va_dmabuf_mem_map;
|
GST_ALLOCATOR (self)->mem_map = gst_va_dmabuf_mem_map;
|
||||||
}
|
}
|
||||||
|
@ -513,11 +600,7 @@ gst_va_dmabuf_memory_release (GstMiniObject * mini_object)
|
||||||
GstVaDmabufAllocator *self = GST_VA_DMABUF_ALLOCATOR (mem->allocator);
|
GstVaDmabufAllocator *self = GST_VA_DMABUF_ALLOCATOR (mem->allocator);
|
||||||
|
|
||||||
GST_LOG ("releasing %p", mem);
|
GST_LOG ("releasing %p", mem);
|
||||||
|
gst_va_memory_pool_push (&self->pool, mem);
|
||||||
g_mutex_lock (&self->buffer_lock);
|
|
||||||
gst_atomic_queue_push (self->available_mems, gst_memory_ref (mem));
|
|
||||||
g_cond_signal (&self->buffer_cond);
|
|
||||||
g_mutex_unlock (&self->buffer_lock);
|
|
||||||
|
|
||||||
/* Keep last in case we are holding on the last allocator ref */
|
/* Keep last in case we are holding on the last allocator ref */
|
||||||
gst_object_unref (mem->allocator);
|
gst_object_unref (mem->allocator);
|
||||||
|
@ -628,7 +711,7 @@ gst_va_dmabuf_allocator_setup_buffer_full (GstAllocator * allocator,
|
||||||
GST_VIDEO_INFO_PLANE_STRIDE (info, i) = desc.layers[i].pitch[0];
|
GST_VIDEO_INFO_PLANE_STRIDE (info, i) = desc.layers[i].pitch[0];
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
g_atomic_int_inc (&self->surface_count);
|
gst_va_memory_pool_surface_inc (&self->pool);
|
||||||
}
|
}
|
||||||
|
|
||||||
GST_LOG_OBJECT (self, "Created surface %#x [%dx%d] size %" G_GSIZE_FORMAT,
|
GST_LOG_OBJECT (self, "Created surface %#x [%dx%d] size %" G_GSIZE_FORMAT,
|
||||||
|
@ -659,7 +742,7 @@ gst_va_dmabuf_allocator_prepare_buffer_unlocked (GstVaDmabufAllocator * self,
|
||||||
VASurfaceID surface;
|
VASurfaceID surface;
|
||||||
gint j, idx = 1;
|
gint j, idx = 1;
|
||||||
|
|
||||||
mem[0] = gst_atomic_queue_pop (self->available_mems);
|
mem[0] = gst_va_memory_pool_pop (&self->pool);
|
||||||
if (!mem[0])
|
if (!mem[0])
|
||||||
return VA_INVALID_ID;
|
return VA_INVALID_ID;
|
||||||
|
|
||||||
|
@ -668,7 +751,7 @@ gst_va_dmabuf_allocator_prepare_buffer_unlocked (GstVaDmabufAllocator * self,
|
||||||
GstMemory *pmem;
|
GstMemory *pmem;
|
||||||
VASurfaceID psurface;
|
VASurfaceID psurface;
|
||||||
|
|
||||||
pmem = gst_atomic_queue_peek (self->available_mems);
|
pmem = gst_va_memory_pool_peek (&self->pool);
|
||||||
if (!pmem)
|
if (!pmem)
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
@ -676,7 +759,7 @@ gst_va_dmabuf_allocator_prepare_buffer_unlocked (GstVaDmabufAllocator * self,
|
||||||
if (psurface != surface)
|
if (psurface != surface)
|
||||||
break;
|
break;
|
||||||
|
|
||||||
mem[idx++] = gst_atomic_queue_pop (self->available_mems);
|
mem[idx++] = gst_va_memory_pool_pop (&self->pool);
|
||||||
};
|
};
|
||||||
|
|
||||||
/* append them in reverse order */
|
/* append them in reverse order */
|
||||||
|
@ -695,9 +778,9 @@ gst_va_dmabuf_allocator_prepare_buffer (GstAllocator * allocator,
|
||||||
GstVaDmabufAllocator *self = GST_VA_DMABUF_ALLOCATOR (allocator);
|
GstVaDmabufAllocator *self = GST_VA_DMABUF_ALLOCATOR (allocator);
|
||||||
VASurfaceID surface;
|
VASurfaceID surface;
|
||||||
|
|
||||||
g_mutex_lock (&self->buffer_lock);
|
GST_VA_MEMORY_POOL_LOCK (&self->pool);
|
||||||
surface = gst_va_dmabuf_allocator_prepare_buffer_unlocked (self, buffer);
|
surface = gst_va_dmabuf_allocator_prepare_buffer_unlocked (self, buffer);
|
||||||
g_mutex_unlock (&self->buffer_lock);
|
GST_VA_MEMORY_POOL_UNLOCK (&self->pool);
|
||||||
|
|
||||||
if (surface != VA_INVALID_ID) {
|
if (surface != VA_INVALID_ID) {
|
||||||
GST_TRACE_OBJECT (self, "Prepared surface %#x in buffer %p", surface,
|
GST_TRACE_OBJECT (self, "Prepared surface %#x in buffer %p", surface,
|
||||||
|
@ -714,17 +797,13 @@ gst_va_dmabuf_allocator_wait_for_memory (GstAllocator * allocator,
|
||||||
GstVaDmabufAllocator *self = GST_VA_DMABUF_ALLOCATOR (allocator);
|
GstVaDmabufAllocator *self = GST_VA_DMABUF_ALLOCATOR (allocator);
|
||||||
VASurfaceID surface;
|
VASurfaceID surface;
|
||||||
|
|
||||||
g_mutex_lock (&self->buffer_lock);
|
GST_VA_MEMORY_POOL_LOCK (&self->pool);
|
||||||
while (gst_atomic_queue_length (self->available_mems) == 0 && !self->flushing)
|
if (!gst_va_memory_pool_wait_unlocked (&self->pool)) {
|
||||||
g_cond_wait (&self->buffer_cond, &self->buffer_lock);
|
GST_VA_MEMORY_POOL_LOCK (&self->pool);
|
||||||
|
|
||||||
if (self->flushing) {
|
|
||||||
g_mutex_unlock (&self->buffer_lock);
|
|
||||||
return FALSE;
|
return FALSE;
|
||||||
}
|
}
|
||||||
|
|
||||||
surface = gst_va_dmabuf_allocator_prepare_buffer_unlocked (self, buffer);
|
surface = gst_va_dmabuf_allocator_prepare_buffer_unlocked (self, buffer);
|
||||||
g_mutex_unlock (&self->buffer_lock);
|
GST_VA_MEMORY_POOL_UNLOCK (&self->pool);
|
||||||
|
|
||||||
if (surface != VA_INVALID_ID) {
|
if (surface != VA_INVALID_ID) {
|
||||||
GST_TRACE_OBJECT (self, "Prepared surface %#x in buffer %p", surface,
|
GST_TRACE_OBJECT (self, "Prepared surface %#x in buffer %p", surface,
|
||||||
|
@ -739,13 +818,7 @@ gst_va_dmabuf_allocator_flush (GstAllocator * allocator)
|
||||||
{
|
{
|
||||||
GstVaDmabufAllocator *self = GST_VA_DMABUF_ALLOCATOR (allocator);
|
GstVaDmabufAllocator *self = GST_VA_DMABUF_ALLOCATOR (allocator);
|
||||||
|
|
||||||
g_mutex_lock (&self->buffer_lock);
|
gst_va_memory_pool_flush (&self->pool, self->display);
|
||||||
self->flushing = TRUE;
|
|
||||||
_available_mems_flush (self->display, self->available_mems,
|
|
||||||
&self->surface_count);
|
|
||||||
self->flushing = FALSE;
|
|
||||||
g_cond_broadcast (&self->buffer_cond);
|
|
||||||
g_mutex_unlock (&self->buffer_lock);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static gboolean
|
static gboolean
|
||||||
|
@ -778,7 +851,7 @@ gst_va_dmabuf_allocator_set_format (GstAllocator * allocator,
|
||||||
|
|
||||||
self = GST_VA_DMABUF_ALLOCATOR (allocator);
|
self = GST_VA_DMABUF_ALLOCATOR (allocator);
|
||||||
|
|
||||||
if (self->surface_count != 0) {
|
if (gst_va_memory_pool_surface_count (&self->pool) != 0) {
|
||||||
if (GST_VIDEO_INFO_FORMAT (info) == GST_VIDEO_INFO_FORMAT (&self->info)
|
if (GST_VIDEO_INFO_FORMAT (info) == GST_VIDEO_INFO_FORMAT (&self->info)
|
||||||
&& GST_VIDEO_INFO_WIDTH (info) == GST_VIDEO_INFO_WIDTH (&self->info)
|
&& GST_VIDEO_INFO_WIDTH (info) == GST_VIDEO_INFO_WIDTH (&self->info)
|
||||||
&& GST_VIDEO_INFO_HEIGHT (info) == GST_VIDEO_INFO_HEIGHT (&self->info)
|
&& GST_VIDEO_INFO_HEIGHT (info) == GST_VIDEO_INFO_HEIGHT (&self->info)
|
||||||
|
@ -890,10 +963,6 @@ struct _GstVaAllocator
|
||||||
{
|
{
|
||||||
GstAllocator parent;
|
GstAllocator parent;
|
||||||
|
|
||||||
/* queue for disposed surfaces */
|
|
||||||
GstAtomicQueue *available_mems;
|
|
||||||
gint surface_count;
|
|
||||||
|
|
||||||
GstVaDisplay *display;
|
GstVaDisplay *display;
|
||||||
|
|
||||||
gboolean use_derived;
|
gboolean use_derived;
|
||||||
|
@ -904,13 +973,10 @@ struct _GstVaAllocator
|
||||||
guint32 fourcc;
|
guint32 fourcc;
|
||||||
guint32 rt_format;
|
guint32 rt_format;
|
||||||
|
|
||||||
GMutex buffer_lock;
|
|
||||||
GCond buffer_cond;
|
|
||||||
|
|
||||||
GstVideoInfo info;
|
GstVideoInfo info;
|
||||||
guint usage_hint;
|
guint usage_hint;
|
||||||
|
|
||||||
gboolean flushing;
|
GstVaMemoryPool pool;
|
||||||
};
|
};
|
||||||
|
|
||||||
typedef struct _GstVaMemory GstVaMemory;
|
typedef struct _GstVaMemory GstVaMemory;
|
||||||
|
@ -941,11 +1007,9 @@ gst_va_allocator_finalize (GObject * object)
|
||||||
{
|
{
|
||||||
GstVaAllocator *self = GST_VA_ALLOCATOR (object);
|
GstVaAllocator *self = GST_VA_ALLOCATOR (object);
|
||||||
|
|
||||||
gst_atomic_queue_unref (self->available_mems);
|
gst_va_memory_pool_finalize (&self->pool);
|
||||||
gst_clear_object (&self->display);
|
|
||||||
g_clear_pointer (&self->surface_formats, g_array_unref);
|
g_clear_pointer (&self->surface_formats, g_array_unref);
|
||||||
g_mutex_clear (&self->buffer_lock);
|
gst_clear_object (&self->display);
|
||||||
g_cond_clear (&self->buffer_cond);
|
|
||||||
|
|
||||||
G_OBJECT_CLASS (gst_va_allocator_parent_class)->finalize (object);
|
G_OBJECT_CLASS (gst_va_allocator_parent_class)->finalize (object);
|
||||||
}
|
}
|
||||||
|
@ -955,10 +1019,11 @@ gst_va_allocator_dispose (GObject * object)
|
||||||
{
|
{
|
||||||
GstVaAllocator *self = GST_VA_ALLOCATOR (object);
|
GstVaAllocator *self = GST_VA_ALLOCATOR (object);
|
||||||
|
|
||||||
_available_mems_flush (self->display, self->available_mems,
|
gst_va_memory_pool_flush_unlocked (&self->pool, self->display);
|
||||||
&self->surface_count);
|
if (gst_va_memory_pool_surface_count (&self->pool) != 0) {
|
||||||
if (self->surface_count != 0)
|
GST_WARNING_OBJECT (self, "Surfaces leaked: %d",
|
||||||
GST_WARNING_OBJECT (self, "Surfaces leaked: %d", self->surface_count);
|
gst_va_memory_pool_surface_count (&self->pool));
|
||||||
|
}
|
||||||
|
|
||||||
G_OBJECT_CLASS (gst_va_allocator_parent_class)->dispose (object);
|
G_OBJECT_CLASS (gst_va_allocator_parent_class)->dispose (object);
|
||||||
}
|
}
|
||||||
|
@ -1250,8 +1315,6 @@ gst_va_allocator_init (GstVaAllocator * self)
|
||||||
{
|
{
|
||||||
GstAllocator *allocator = GST_ALLOCATOR (self);
|
GstAllocator *allocator = GST_ALLOCATOR (self);
|
||||||
|
|
||||||
self->available_mems = gst_atomic_queue_new (2);
|
|
||||||
|
|
||||||
allocator->mem_type = GST_ALLOCATOR_VASURFACE;
|
allocator->mem_type = GST_ALLOCATOR_VASURFACE;
|
||||||
allocator->mem_map = (GstMemoryMapFunction) _va_map;
|
allocator->mem_map = (GstMemoryMapFunction) _va_map;
|
||||||
allocator->mem_unmap = (GstMemoryUnmapFunction) _va_unmap;
|
allocator->mem_unmap = (GstMemoryUnmapFunction) _va_unmap;
|
||||||
|
@ -1259,8 +1322,7 @@ gst_va_allocator_init (GstVaAllocator * self)
|
||||||
|
|
||||||
self->use_derived = TRUE;
|
self->use_derived = TRUE;
|
||||||
|
|
||||||
g_mutex_init (&self->buffer_lock);
|
gst_va_memory_pool_init (&self->pool);
|
||||||
g_cond_init (&self->buffer_cond);
|
|
||||||
|
|
||||||
GST_OBJECT_FLAG_SET (self, GST_ALLOCATOR_FLAG_CUSTOM_ALLOC);
|
GST_OBJECT_FLAG_SET (self, GST_ALLOCATOR_FLAG_CUSTOM_ALLOC);
|
||||||
}
|
}
|
||||||
|
@ -1272,11 +1334,7 @@ gst_va_memory_release (GstMiniObject * mini_object)
|
||||||
GstVaAllocator *self = GST_VA_ALLOCATOR (mem->allocator);
|
GstVaAllocator *self = GST_VA_ALLOCATOR (mem->allocator);
|
||||||
|
|
||||||
GST_LOG ("releasing %p", mem);
|
GST_LOG ("releasing %p", mem);
|
||||||
|
gst_va_memory_pool_push (&self->pool, mem);
|
||||||
g_mutex_lock (&self->buffer_lock);
|
|
||||||
gst_atomic_queue_push (self->available_mems, gst_memory_ref (mem));
|
|
||||||
g_cond_signal (&self->buffer_cond);
|
|
||||||
g_mutex_unlock (&self->buffer_lock);
|
|
||||||
|
|
||||||
/* Keep last in case we are holding on the last allocator ref */
|
/* Keep last in case we are holding on the last allocator ref */
|
||||||
gst_object_unref (mem->allocator);
|
gst_object_unref (mem->allocator);
|
||||||
|
@ -1312,7 +1370,7 @@ gst_va_allocator_alloc (GstAllocator * allocator)
|
||||||
_reset_mem (mem, allocator, GST_VIDEO_INFO_SIZE (&self->info));
|
_reset_mem (mem, allocator, GST_VIDEO_INFO_SIZE (&self->info));
|
||||||
|
|
||||||
GST_MINI_OBJECT (mem)->dispose = gst_va_memory_release;
|
GST_MINI_OBJECT (mem)->dispose = gst_va_memory_release;
|
||||||
g_atomic_int_inc (&self->surface_count);
|
gst_va_memory_pool_surface_inc (&self->pool);
|
||||||
|
|
||||||
GST_LOG_OBJECT (self, "Created surface %#x [%dx%d]", mem->surface,
|
GST_LOG_OBJECT (self, "Created surface %#x [%dx%d]", mem->surface,
|
||||||
GST_VIDEO_INFO_WIDTH (&self->info), GST_VIDEO_INFO_HEIGHT (&self->info));
|
GST_VIDEO_INFO_WIDTH (&self->info), GST_VIDEO_INFO_HEIGHT (&self->info));
|
||||||
|
@ -1342,7 +1400,7 @@ gst_va_allocator_prepare_buffer_unlocked (GstVaAllocator * self,
|
||||||
GstMemory *mem;
|
GstMemory *mem;
|
||||||
VASurfaceID surface;
|
VASurfaceID surface;
|
||||||
|
|
||||||
mem = gst_atomic_queue_pop (self->available_mems);
|
mem = gst_va_memory_pool_pop (&self->pool);
|
||||||
if (!mem)
|
if (!mem)
|
||||||
return VA_INVALID_ID;
|
return VA_INVALID_ID;
|
||||||
|
|
||||||
|
@ -1359,9 +1417,9 @@ gst_va_allocator_prepare_buffer (GstAllocator * allocator, GstBuffer * buffer)
|
||||||
GstVaAllocator *self = GST_VA_ALLOCATOR (allocator);
|
GstVaAllocator *self = GST_VA_ALLOCATOR (allocator);
|
||||||
VASurfaceID surface;
|
VASurfaceID surface;
|
||||||
|
|
||||||
g_mutex_lock (&self->buffer_lock);
|
GST_VA_MEMORY_POOL_LOCK (&self->pool);
|
||||||
surface = gst_va_allocator_prepare_buffer_unlocked (self, buffer);
|
surface = gst_va_allocator_prepare_buffer_unlocked (self, buffer);
|
||||||
g_mutex_unlock (&self->buffer_lock);
|
GST_VA_MEMORY_POOL_UNLOCK (&self->pool);
|
||||||
|
|
||||||
if (surface != VA_INVALID_ID) {
|
if (surface != VA_INVALID_ID) {
|
||||||
GST_TRACE_OBJECT (self, "Prepared surface %#x in buffer %p", surface,
|
GST_TRACE_OBJECT (self, "Prepared surface %#x in buffer %p", surface,
|
||||||
|
@ -1377,17 +1435,13 @@ gst_va_allocator_wait_for_memory (GstAllocator * allocator, GstBuffer * buffer)
|
||||||
GstVaAllocator *self = GST_VA_ALLOCATOR (allocator);
|
GstVaAllocator *self = GST_VA_ALLOCATOR (allocator);
|
||||||
VASurfaceID surface;
|
VASurfaceID surface;
|
||||||
|
|
||||||
g_mutex_lock (&self->buffer_lock);
|
GST_VA_MEMORY_POOL_LOCK (&self->pool);
|
||||||
while (gst_atomic_queue_length (self->available_mems) == 0 && !self->flushing)
|
if (!gst_va_memory_pool_wait_unlocked (&self->pool)) {
|
||||||
g_cond_wait (&self->buffer_cond, &self->buffer_lock);
|
GST_VA_MEMORY_POOL_LOCK (&self->pool);
|
||||||
|
|
||||||
if (self->flushing) {
|
|
||||||
g_mutex_unlock (&self->buffer_lock);
|
|
||||||
return FALSE;
|
return FALSE;
|
||||||
}
|
}
|
||||||
|
|
||||||
surface = gst_va_allocator_prepare_buffer_unlocked (self, buffer);
|
surface = gst_va_allocator_prepare_buffer_unlocked (self, buffer);
|
||||||
g_mutex_unlock (&self->buffer_lock);
|
GST_VA_MEMORY_POOL_LOCK (&self->pool);
|
||||||
|
|
||||||
if (surface != VA_INVALID_ID) {
|
if (surface != VA_INVALID_ID) {
|
||||||
GST_TRACE_OBJECT (self, "Prepared surface %#x in buffer %p", surface,
|
GST_TRACE_OBJECT (self, "Prepared surface %#x in buffer %p", surface,
|
||||||
|
@ -1402,13 +1456,7 @@ gst_va_allocator_flush (GstAllocator * allocator)
|
||||||
{
|
{
|
||||||
GstVaAllocator *self = GST_VA_ALLOCATOR (allocator);
|
GstVaAllocator *self = GST_VA_ALLOCATOR (allocator);
|
||||||
|
|
||||||
g_mutex_lock (&self->buffer_lock);
|
gst_va_memory_pool_flush (&self->pool, self->display);
|
||||||
self->flushing = TRUE;
|
|
||||||
_available_mems_flush (self->display, self->available_mems,
|
|
||||||
&self->surface_count);
|
|
||||||
self->flushing = FALSE;
|
|
||||||
g_cond_broadcast (&self->buffer_cond);
|
|
||||||
g_mutex_unlock (&self->buffer_lock);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static gboolean
|
static gboolean
|
||||||
|
@ -1467,7 +1515,7 @@ gst_va_allocator_set_format (GstAllocator * allocator, GstVideoInfo * info,
|
||||||
|
|
||||||
self = GST_VA_ALLOCATOR (allocator);
|
self = GST_VA_ALLOCATOR (allocator);
|
||||||
|
|
||||||
if (self->surface_count != 0) {
|
if (gst_va_memory_pool_surface_count (&self->pool) != 0) {
|
||||||
if (GST_VIDEO_INFO_FORMAT (info) == GST_VIDEO_INFO_FORMAT (&self->info)
|
if (GST_VIDEO_INFO_FORMAT (info) == GST_VIDEO_INFO_FORMAT (&self->info)
|
||||||
&& GST_VIDEO_INFO_WIDTH (info) == GST_VIDEO_INFO_WIDTH (&self->info)
|
&& GST_VIDEO_INFO_WIDTH (info) == GST_VIDEO_INFO_WIDTH (&self->info)
|
||||||
&& GST_VIDEO_INFO_HEIGHT (info) == GST_VIDEO_INFO_HEIGHT (&self->info)
|
&& GST_VIDEO_INFO_HEIGHT (info) == GST_VIDEO_INFO_HEIGHT (&self->info)
|
||||||
|
|
Loading…
Reference in a new issue