ximage: reimplement buffer pooling with metadata

Use the buffer metadata to get back to the extra info we can use to optimize the
video rendering.
This commit is contained in:
Wim Taymans 2011-02-25 16:01:47 +01:00
parent 55c9ca592f
commit 08bfcad434
2 changed files with 33 additions and 38 deletions

View file

@ -1634,6 +1634,7 @@ static GstFlowReturn
gst_ximagesink_show_frame (GstVideoSink * vsink, GstBuffer * buf)
{
GstXImageSink *ximagesink;
GstMetaXImage *meta;
g_return_val_if_fail (buf != NULL, GST_FLOW_ERROR);
@ -1644,16 +1645,15 @@ gst_ximagesink_show_frame (GstVideoSink * vsink, GstBuffer * buf)
if (!ximagesink->xcontext)
return GST_FLOW_ERROR;
#if 0
meta = GST_META_XIMAGE_GET (buf, FALSE);
if (meta) {
/* If this buffer has been allocated using our buffer management we simply
put the ximage which is in the PRIVATE pointer */
if (GST_IS_XIMAGE_BUFFER (buf)) {
GST_LOG_OBJECT (ximagesink, "buffer from our pool, writing directly");
if (!gst_ximagesink_ximage_put (ximagesink, GST_XIMAGE_BUFFER (buf)))
if (!gst_ximagesink_ximage_put (ximagesink, buf))
goto no_window;
} else
#endif
{
} else {
/* Else we have to copy the data into our private image, */
/* if we have one... */
GST_LOG_OBJECT (ximagesink, "normal buffer, copying from it");
@ -1666,7 +1666,7 @@ gst_ximagesink_show_frame (GstVideoSink * vsink, GstBuffer * buf)
goto no_ximage;
if (GST_BUFFER_SIZE (ximagesink->ximage) < GST_BUFFER_SIZE (buf)) {
GstMetaXImage *meta = GST_META_XIMAGE_GET (ximagesink->ximage, FALSE);
meta = GST_META_XIMAGE_GET (ximagesink->ximage, FALSE);
GST_ELEMENT_ERROR (ximagesink, RESOURCE, WRITE,
("Failed to create output image buffer of %dx%d pixels",
@ -1733,7 +1733,6 @@ gst_ximagesink_event (GstBaseSink * sink, GstEvent * event)
return TRUE;
}
#if 0
/* Buffer management
*
* The buffer_alloc function must either return a buffer with given size and
@ -1749,7 +1748,8 @@ gst_ximagesink_buffer_alloc (GstBaseSink * bsink, guint64 offset, guint size,
GstCaps * caps, GstBuffer ** buf)
{
GstXImageSink *ximagesink;
GstXImageBuffer *ximage = NULL;
GstMetaXImage *meta = NULL;
GstBuffer *ximage = NULL;
GstStructure *structure = NULL;
GstFlowReturn ret = GST_FLOW_OK;
GstCaps *alloc_caps;
@ -1880,15 +1880,17 @@ alloc:
/* Inspect our buffer pool */
g_mutex_lock (ximagesink->pool_lock);
while (ximagesink->buffer_pool) {
ximage = (GstXImageBuffer *) ximagesink->buffer_pool->data;
ximage = ximagesink->buffer_pool->data;
if (ximage) {
meta = GST_META_XIMAGE_GET (ximage, FALSE);
/* Removing from the pool */
ximagesink->buffer_pool = g_slist_delete_link (ximagesink->buffer_pool,
ximagesink->buffer_pool);
/* If the ximage is invalid for our need, destroy */
if ((ximage->width != width) || (ximage->height != height)) {
if ((meta->width != width) || (meta->height != height)) {
gst_ximage_buffer_free (ximage);
ximage = NULL;
} else {
@ -1907,19 +1909,18 @@ alloc:
if (ximage) {
/* Make sure the buffer is cleared of any previously used flags */
GST_MINI_OBJECT_CAST (ximage)->flags = 0;
gst_buffer_set_caps (GST_BUFFER_CAST (ximage), alloc_caps);
gst_buffer_set_caps (ximage, alloc_caps);
}
/* could be our new reffed suggestion or the original unreffed caps */
if (alloc_unref)
gst_caps_unref (alloc_caps);
*buf = GST_BUFFER_CAST (ximage);
*buf = ximage;
beach:
return ret;
}
#endif
/* Interfaces stuff */
@ -2418,10 +2419,8 @@ gst_ximagesink_class_init (GstXImageSinkClass * klass)
gstbasesink_class->get_caps = GST_DEBUG_FUNCPTR (gst_ximagesink_getcaps);
gstbasesink_class->set_caps = GST_DEBUG_FUNCPTR (gst_ximagesink_setcaps);
#if 0
gstbasesink_class->buffer_alloc =
GST_DEBUG_FUNCPTR (gst_ximagesink_buffer_alloc);
#endif
gstbasesink_class->get_times = GST_DEBUG_FUNCPTR (gst_ximagesink_get_times);
gstbasesink_class->event = GST_DEBUG_FUNCPTR (gst_ximagesink_event);

View file

@ -2333,20 +2333,19 @@ static GstFlowReturn
gst_xvimagesink_show_frame (GstVideoSink * vsink, GstBuffer * buf)
{
GstXvImageSink *xvimagesink;
GstMetaXvImage *meta;
xvimagesink = GST_XVIMAGESINK (vsink);
#if 0
meta = GST_META_XVIMAGE_GET (buf, FALSE);
if (meta) {
/* If this buffer has been allocated using our buffer management we simply
put the ximage which is in the PRIVATE pointer */
if (GST_IS_XVIMAGE_BUFFER (buf)) {
GST_LOG_OBJECT (xvimagesink, "fast put of bufferpool buffer %p", buf);
if (!gst_xvimagesink_xvimage_put (xvimagesink,
GST_XVIMAGE_BUFFER_CAST (buf)))
if (!gst_xvimagesink_xvimage_put (xvimagesink, buf))
goto no_window;
} else
#endif
{
} else {
GST_CAT_LOG_OBJECT (GST_CAT_PERFORMANCE, xvimagesink,
"slow copy into bufferpool buffer %p", buf);
/* Else we have to copy the data into our private image, */
@ -2362,8 +2361,7 @@ gst_xvimagesink_show_frame (GstVideoSink * vsink, GstBuffer * buf)
goto no_image;
if (GST_BUFFER_SIZE (xvimagesink->xvimage) < GST_BUFFER_SIZE (buf)) {
GstMetaXvImage *meta =
GST_META_XVIMAGE_GET (xvimagesink->xvimage, FALSE);
meta = GST_META_XVIMAGE_GET (xvimagesink->xvimage, FALSE);
GST_ELEMENT_ERROR (xvimagesink, RESOURCE, WRITE,
("Failed to create output image buffer of %dx%d pixels",
@ -2432,9 +2430,7 @@ gst_xvimagesink_event (GstBaseSink * sink, GstEvent * event)
return TRUE;
}
#if 0
/* Buffer management */
static GstCaps *
gst_xvimage_sink_different_size_suggestion (GstXvImageSink * xvimagesink,
GstCaps * caps)
@ -2489,7 +2485,8 @@ gst_xvimagesink_buffer_alloc (GstBaseSink * bsink, guint64 offset, guint size,
{
GstFlowReturn ret = GST_FLOW_OK;
GstXvImageSink *xvimagesink;
GstMetaXvImage *xvimage = NULL;
GstBuffer *xvimage = NULL;
GstMetaXvImage *meta = NULL;
GstCaps *intersection = NULL;
GstStructure *structure = NULL;
gint width, height, image_format;
@ -2623,13 +2620,15 @@ reuse_last_caps:
xvimage = xvimagesink->image_pool->data;
if (xvimage) {
meta = GST_META_XVIMAGE_GET (xvimage, FALSE);
/* Removing from the pool */
xvimagesink->image_pool = g_slist_delete_link (xvimagesink->image_pool,
xvimagesink->image_pool);
/* We check for geometry or image format changes */
if ((xvimage->width != width) ||
(xvimage->height != height) || (xvimage->im_format != image_format)) {
if ((meta->width != width) ||
(meta->height != height) || (meta->im_format != image_format)) {
/* This image is unusable. Destroying... */
gst_xvimage_buffer_free (xvimage);
xvimage = NULL;
@ -2654,7 +2653,7 @@ reuse_last_caps:
gst_buffer_set_caps (GST_BUFFER_CAST (xvimage), intersection);
}
*buf = GST_BUFFER_CAST (xvimage);
*buf = xvimage;
beach:
if (intersection) {
@ -2690,7 +2689,6 @@ invalid_caps:
goto beach;
}
}
#endif
/* Interfaces stuff */
@ -3656,10 +3654,8 @@ gst_xvimagesink_class_init (GstXvImageSinkClass * klass)
gstbasesink_class->get_caps = GST_DEBUG_FUNCPTR (gst_xvimagesink_getcaps);
gstbasesink_class->set_caps = GST_DEBUG_FUNCPTR (gst_xvimagesink_setcaps);
#if 0
gstbasesink_class->buffer_alloc =
GST_DEBUG_FUNCPTR (gst_xvimagesink_buffer_alloc);
#endif
gstbasesink_class->get_times = GST_DEBUG_FUNCPTR (gst_xvimagesink_get_times);
gstbasesink_class->event = GST_DEBUG_FUNCPTR (gst_xvimagesink_event);