From 04fa67937d8ea9a915461fc344f14325b4ba219c Mon Sep 17 00:00:00 2001 From: Wim Taymans Date: Tue, 17 May 2005 17:41:32 +0000 Subject: [PATCH] Leak fixes in oggdemux. Original commit message from CVS: * ext/ogg/gstoggdemux.c: (gst_ogg_pad_internal_chain), (gst_ogg_demux_submit_buffer), (gst_ogg_demux_get_data), (gst_ogg_demux_chain_unlocked): * gst/audioconvert/gstaudioconvert.c: (gst_audio_convert_chain), (gst_audio_convert_caps_remove_format_info), (gst_audio_convert_getcaps), (gst_audio_convert_setcaps), (gst_audio_convert_fixate), (gst_audio_convert_change_state): * gst/ffmpegcolorspace/gstffmpegcolorspace.c: (gst_ffmpegcsp_getcaps), (gst_ffmpegcsp_configure_context), (gst_ffmpegcsp_setcaps), (gst_ffmpegcsp_init), (gst_ffmpegcsp_bufferalloc), (gst_ffmpegcsp_chain), (gst_ffmpegcsp_change_state), (gst_ffmpegcsp_set_property), (gst_ffmpegcsp_get_property): * sys/xvimage/xvimagesink.c: (gst_xvimage_buffer_destroy), (gst_xvimage_buffer_finalize), (gst_xvimage_buffer_free), (gst_xvimage_buffer_class_init), (gst_xvimage_buffer_get_type), (gst_xvimagesink_check_xshm_calls), (gst_xvimagesink_xvimage_new), (gst_xvimagesink_xvimage_put), (gst_xvimagesink_imagepool_clear), (gst_xvimagesink_setcaps), (gst_xvimagesink_change_state), (gst_xvimagesink_show_frame), (gst_xvimagesink_buffer_free), (gst_xvimagesink_buffer_alloc), (gst_xvimagesink_set_xwindow_id): Leak fixes in oggdemux. Some cleanups in audioconvert. Make passthrough work along with buffer_alloc etc. Make buffer_alloc and buffer recycling actually work in xvimagesink. --- ChangeLog | 29 ++++ ext/ogg/gstoggdemux.c | 5 +- gst/audioconvert/gstaudioconvert.c | 22 ++- gst/ffmpegcolorspace/gstffmpegcolorspace.c | 159 ++++++++++++++------- sys/xvimage/xvimagesink.c | 122 ++++++++++------ 5 files changed, 236 insertions(+), 101 deletions(-) diff --git a/ChangeLog b/ChangeLog index cef9a11f9e..7ddaaad12c 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,32 @@ +2005-05-17 Wim Taymans + + * ext/ogg/gstoggdemux.c: (gst_ogg_pad_internal_chain), + (gst_ogg_demux_submit_buffer), (gst_ogg_demux_get_data), + (gst_ogg_demux_chain_unlocked): + * gst/audioconvert/gstaudioconvert.c: (gst_audio_convert_chain), + (gst_audio_convert_caps_remove_format_info), + (gst_audio_convert_getcaps), (gst_audio_convert_setcaps), + (gst_audio_convert_fixate), (gst_audio_convert_change_state): + * gst/ffmpegcolorspace/gstffmpegcolorspace.c: + (gst_ffmpegcsp_getcaps), (gst_ffmpegcsp_configure_context), + (gst_ffmpegcsp_setcaps), (gst_ffmpegcsp_init), + (gst_ffmpegcsp_bufferalloc), (gst_ffmpegcsp_chain), + (gst_ffmpegcsp_change_state), (gst_ffmpegcsp_set_property), + (gst_ffmpegcsp_get_property): + * sys/xvimage/xvimagesink.c: (gst_xvimage_buffer_destroy), + (gst_xvimage_buffer_finalize), (gst_xvimage_buffer_free), + (gst_xvimage_buffer_class_init), (gst_xvimage_buffer_get_type), + (gst_xvimagesink_check_xshm_calls), (gst_xvimagesink_xvimage_new), + (gst_xvimagesink_xvimage_put), (gst_xvimagesink_imagepool_clear), + (gst_xvimagesink_setcaps), (gst_xvimagesink_change_state), + (gst_xvimagesink_show_frame), (gst_xvimagesink_buffer_free), + (gst_xvimagesink_buffer_alloc), (gst_xvimagesink_set_xwindow_id): + Leak fixes in oggdemux. + Some cleanups in audioconvert. + Make passthrough work along with buffer_alloc etc. + Make buffer_alloc and buffer recycling actually work in + xvimagesink. + 2005-05-17 Thomas Vander Stichele * gst/subparse/gstsubparse.c: (parse_subrip), (parse_mpsub): diff --git a/ext/ogg/gstoggdemux.c b/ext/ogg/gstoggdemux.c index d3735cd54b..6bcb39018d 100644 --- a/ext/ogg/gstoggdemux.c +++ b/ext/ogg/gstoggdemux.c @@ -512,6 +512,8 @@ gst_ogg_pad_internal_chain (GstPad * pad, GstBuffer * buffer) if (oggpad->start_time == -1) oggpad->start_time = timestamp; + gst_buffer_unref (buffer); + return GST_FLOW_OK; } @@ -981,6 +983,7 @@ gst_ogg_demux_submit_buffer (GstOggDemux * ogg, GstBuffer * buffer) oggbuffer = ogg_sync_buffer (&ogg->sync, size); memcpy (oggbuffer, data, size); ogg_sync_wrote (&ogg->sync, size); + gst_buffer_unref (buffer); return size; } @@ -1019,7 +1022,6 @@ gst_ogg_demux_get_data (GstOggDemux * ogg) return -1; size = gst_ogg_demux_submit_buffer (ogg, buffer); - gst_buffer_unref (buffer); return size; } @@ -1862,7 +1864,6 @@ gst_ogg_demux_chain_unlocked (GstPad * pad, GstBuffer * buffer) } } } - gst_buffer_unref (buffer); return result; } diff --git a/gst/audioconvert/gstaudioconvert.c b/gst/audioconvert/gstaudioconvert.c index f9ade6121d..7a1676f529 100644 --- a/gst/audioconvert/gstaudioconvert.c +++ b/gst/audioconvert/gstaudioconvert.c @@ -616,24 +616,32 @@ gst_audio_convert_fixate (GstPad * pad, GstCaps * caps) static GstElementStateReturn gst_audio_convert_change_state (GstElement * element) { + GstElementStateReturn ret; GstAudioConvert *this = GST_AUDIO_CONVERT (element); + gint transition; - switch (GST_STATE_TRANSITION (element)) { + transition = GST_STATE_TRANSITION (element); + + switch (transition) { + default: + break; + } + + ret = parent_class->change_state (element); + + switch (transition) { case GST_STATE_PAUSED_TO_READY: GST_STREAM_LOCK (this->sink); this->convert_internal = NULL; gst_audio_convert_unset_matrix (this); + gst_caps_replace (&GST_RPAD_CAPS (this->sink), NULL); + gst_caps_replace (&GST_RPAD_CAPS (this->src), NULL); GST_STREAM_UNLOCK (this->sink); break; default: break; } - - if (parent_class->change_state) { - return parent_class->change_state (element); - } else { - return GST_STATE_SUCCESS; - } + return ret; } /* return a writable buffer of size which ideally is the same as before diff --git a/gst/ffmpegcolorspace/gstffmpegcolorspace.c b/gst/ffmpegcolorspace/gstffmpegcolorspace.c index 61c388d72a..fd4a4bd511 100644 --- a/gst/ffmpegcolorspace/gstffmpegcolorspace.c +++ b/gst/ffmpegcolorspace/gstffmpegcolorspace.c @@ -98,6 +98,8 @@ static void gst_ffmpegcsp_set_property (GObject * object, static void gst_ffmpegcsp_get_property (GObject * object, guint prop_id, GValue * value, GParamSpec * pspec); +static GstBuffer *gst_ffmpegcsp_bufferalloc (GstPad * pad, guint64 offset, + guint size, GstCaps * caps); static GstFlowReturn gst_ffmpegcsp_chain (GstPad * pad, GstBuffer * buffer); static GstElementStateReturn gst_ffmpegcsp_change_state (GstElement * element); @@ -247,15 +249,17 @@ gst_ffmpegcsp_setcaps (GstPad * pad, GstCaps * caps) par = gst_structure_get_value (structure, "pixel-aspect-ratio"); if (!gst_ffmpegcsp_configure_context (pad, caps, width, height)) - goto configure_error; + goto configure_error_source; - *prefered = caps; + gst_caps_replace (prefered, caps); otherpeer = gst_pad_get_peer (otherpad); if (otherpeer) { /* check passthrough */ if (gst_pad_accept_caps (otherpeer, caps)) { - *other_prefered = gst_caps_ref (caps); + if (!gst_ffmpegcsp_configure_context (otherpad, caps, width, height)) + goto configure_error_target; + gst_caps_replace (other_prefered, caps); } else { GstCaps *othercaps; @@ -277,7 +281,13 @@ gst_ffmpegcsp_setcaps (GstPad * pad, GstCaps * caps) gst_value_get_fraction_numerator (par), gst_value_get_fraction_denominator (par), NULL); } - *other_prefered = targetcaps; + if (!gst_ffmpegcsp_configure_context (otherpad, targetcaps, width, + height)) { + gst_caps_unref (targetcaps); + goto configure_error_target; + } + gst_caps_replace (other_prefered, targetcaps); + gst_caps_unref (targetcaps); } } gst_object_unref (GST_OBJECT (otherpeer)); @@ -288,9 +298,15 @@ gst_ffmpegcsp_setcaps (GstPad * pad, GstCaps * caps) return TRUE; -configure_error: +configure_error_source: { - GST_DEBUG ("could not configure context"); + GST_DEBUG ("could not configure context for source"); + return FALSE; + } +configure_error_target: + { + gst_object_unref (GST_OBJECT (otherpeer)); + GST_DEBUG ("could not configure context for target"); return FALSE; } } @@ -357,6 +373,7 @@ gst_ffmpegcsp_init (GstFFMpegCsp * space) gst_pad_set_getcaps_function (space->sinkpad, gst_ffmpegcsp_getcaps); gst_pad_set_setcaps_function (space->sinkpad, gst_ffmpegcsp_setcaps); gst_pad_set_chain_function (space->sinkpad, gst_ffmpegcsp_chain); + gst_pad_set_bufferalloc_function (space->sinkpad, gst_ffmpegcsp_bufferalloc); gst_element_add_pad (GST_ELEMENT (space), space->sinkpad); space->srcpad = gst_pad_new_from_template (srctempl, "src"); @@ -368,83 +385,126 @@ gst_ffmpegcsp_init (GstFFMpegCsp * space) space->palette = NULL; } -static GstFlowReturn -gst_ffmpegcsp_chain (GstPad * pad, GstBuffer * buffer) +static GstBuffer * +gst_ffmpegcsp_bufferalloc (GstPad * pad, guint64 offset, guint size, + GstCaps * caps) { - GstBuffer *inbuf = GST_BUFFER (buffer); + GstBuffer *buf; GstFFMpegCsp *space; - GstBuffer *outbuf = NULL; - - //GstCaps *outcaps; space = GST_FFMPEGCSP (GST_PAD_PARENT (pad)); - if (!GST_PAD_IS_USABLE (space->srcpad)) { - gst_buffer_unref (inbuf); - return GST_FLOW_ERROR; - } + buf = gst_pad_alloc_buffer (space->srcpad, offset, size, caps); + return buf; +} - /* asume passthrough */ - guint size = - avpicture_get_size (space->from_pixfmt, space->width, space->height); +static GstFlowReturn +gst_ffmpegcsp_chain (GstPad * pad, GstBuffer * buffer) +{ + GstFFMpegCsp *space; + GstFlowReturn res; + GstBuffer *outbuf = NULL; - outbuf = gst_pad_alloc_buffer (space->srcpad, GST_BUFFER_OFFSET_NONE, size, - space->src_prefered); - if (outbuf == NULL) { - return GST_FLOW_ERROR; - } + space = GST_FFMPEGCSP (GST_PAD_PARENT (pad)); - if (space->from_pixfmt == PIX_FMT_NB || space->to_pixfmt == PIX_FMT_NB) { - GST_ELEMENT_ERROR (space, CORE, NOT_IMPLEMENTED, (NULL), - ("attempting to convert colorspaces between unknown formats")); - gst_buffer_unref (inbuf); - return GST_FLOW_NOT_NEGOTIATED; - } + GST_STREAM_LOCK (pad); + + if (space->from_pixfmt == PIX_FMT_NB || space->to_pixfmt == PIX_FMT_NB) + goto unkown_format; if (space->from_pixfmt == space->to_pixfmt) { - GST_DEBUG ("passthrough conversion %" GST_PTR_FORMAT, - GST_PAD_CAPS (space->srcpad)); - outbuf = inbuf; + GST_DEBUG ("passthrough conversion"); + /* use input as output buffer */ + outbuf = buffer; } else { - /* convert */ + /* get size of our suggested output format */ + guint size = + avpicture_get_size (space->to_pixfmt, space->width, space->height); + + /* get buffer in prefered format, setcaps will be called when it is different */ + outbuf = gst_pad_alloc_buffer (space->srcpad, GST_BUFFER_OFFSET_NONE, size, + space->src_prefered); + if (outbuf == NULL) + goto no_buffer; + + /* fill from from with source data */ gst_ffmpegcsp_avpicture_fill (&space->from_frame, - GST_BUFFER_DATA (inbuf), + GST_BUFFER_DATA (buffer), space->from_pixfmt, space->width, space->height); + + /* fill optional palette */ if (space->palette) space->from_frame.data[1] = (uint8_t *) space->palette; + + /* fill target frame */ gst_ffmpegcsp_avpicture_fill (&space->to_frame, GST_BUFFER_DATA (outbuf), space->to_pixfmt, space->width, space->height); + + /* and convert */ img_convert (&space->to_frame, space->to_pixfmt, &space->from_frame, space->from_pixfmt, space->width, space->height); - GST_BUFFER_TIMESTAMP (outbuf) = GST_BUFFER_TIMESTAMP (inbuf); - GST_BUFFER_DURATION (outbuf) = GST_BUFFER_DURATION (inbuf); - gst_buffer_unref (inbuf); + /* copy timestamps */ + GST_BUFFER_TIMESTAMP (outbuf) = GST_BUFFER_TIMESTAMP (buffer); + GST_BUFFER_DURATION (outbuf) = GST_BUFFER_DURATION (buffer); + + /* we don't need source anymore */ + gst_buffer_unref (buffer); } - return gst_pad_push (space->srcpad, outbuf); + res = gst_pad_push (space->srcpad, outbuf); + GST_STREAM_UNLOCK (pad); + + return res; + + /* ERRORS */ +no_buffer: + { + GST_STREAM_UNLOCK (pad); + gst_buffer_unref (buffer); + return GST_FLOW_ERROR; + } +unkown_format: + { + GST_STREAM_UNLOCK (pad); + GST_ELEMENT_ERROR (space, CORE, NOT_IMPLEMENTED, (NULL), + ("attempting to convert colorspaces between unknown formats")); + gst_buffer_unref (buffer); + return GST_FLOW_NOT_NEGOTIATED; + } } static GstElementStateReturn gst_ffmpegcsp_change_state (GstElement * element) { GstFFMpegCsp *space; + GstElementStateReturn ret; + gint transition; space = GST_FFMPEGCSP (element); + transition = GST_STATE_TRANSITION (element); - switch (GST_STATE_TRANSITION (element)) { - case GST_STATE_PAUSED_TO_READY: - if (space->palette) - av_free (space->palette); - space->palette = NULL; + switch (transition) { + default: break; } - if (parent_class->change_state) - return parent_class->change_state (element); + ret = parent_class->change_state (element); - return GST_STATE_SUCCESS; + switch (transition) { + case GST_STATE_PAUSED_TO_READY: + GST_STREAM_LOCK (space->sinkpad); + if (space->palette) + av_free (space->palette); + space->palette = NULL; + GST_STREAM_UNLOCK (space->sinkpad); + break; + default: + break; + } + + return ret; } static void @@ -453,12 +513,11 @@ gst_ffmpegcsp_set_property (GObject * object, { GstFFMpegCsp *space; - /* it's not null if we got it, but it might not be ours */ - g_return_if_fail (GST_IS_FFMPEGCSP (object)); space = GST_FFMPEGCSP (object); switch (prop_id) { default: + G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec); break; } } @@ -469,8 +528,6 @@ gst_ffmpegcsp_get_property (GObject * object, { GstFFMpegCsp *space; - /* it's not null if we got it, but it might not be ours */ - g_return_if_fail (GST_IS_FFMPEGCSP (object)); space = GST_FFMPEGCSP (object); switch (prop_id) { diff --git a/sys/xvimage/xvimagesink.c b/sys/xvimage/xvimagesink.c index 8633b76aa4..2761b892fa 100644 --- a/sys/xvimage/xvimagesink.c +++ b/sys/xvimage/xvimagesink.c @@ -103,16 +103,13 @@ static gboolean error_caught = FALSE; /* This function destroys a GstXvImage handling XShm availability */ static void -gst_xvimage_buffer_finalize (GstXvImageBuffer * xvimage) +gst_xvimage_buffer_destroy (GstXvImageBuffer * xvimage) { GstXvImageSink *xvimagesink; - g_return_if_fail (xvimage != NULL); - - if (xvimage->xvimagesink == NULL) - return; - xvimagesink = xvimage->xvimagesink; + if (xvimagesink == NULL) + goto no_sink; g_return_if_fail (GST_IS_XVIMAGESINK (xvimagesink)); @@ -147,8 +144,59 @@ gst_xvimage_buffer_finalize (GstXvImageBuffer * xvimage) XSync (xvimagesink->xcontext->disp, FALSE); g_mutex_unlock (xvimagesink->x_lock); + + return; + +no_sink: + { + GST_WARNING ("no sink found"); + return; + } } +static void +gst_xvimage_buffer_finalize (GstXvImageBuffer * xvimage) +{ + GstXvImageSink *xvimagesink; + + xvimagesink = xvimage->xvimagesink; + if (xvimagesink == NULL) + goto no_sink; + + /* If our geometry changed we can't reuse that image. */ + if ((xvimage->width != xvimagesink->video_width) || + (xvimage->height != xvimagesink->video_height)) { + GST_DEBUG ("destroy image as its size changed %dx%d vs current %dx%d", + xvimage->width, xvimage->height, + xvimagesink->video_width, xvimagesink->video_height); + gst_xvimage_buffer_destroy (xvimage); + } else { + /* In that case we can reuse the image and add it to our image pool. */ + GST_DEBUG ("recycling image in pool"); + /* need to increment the refcount again to recycle */ + gst_buffer_ref (GST_BUFFER (xvimage)); + g_mutex_lock (xvimagesink->pool_lock); + xvimagesink->image_pool = g_slist_prepend (xvimagesink->image_pool, + xvimage); + g_mutex_unlock (xvimagesink->pool_lock); + } + return; + +no_sink: + { + GST_WARNING ("no sink found"); + return; + } +} + +static void +gst_xvimage_buffer_free (GstXvImageBuffer * xvimage) +{ + /* make sure it is not recycled */ + xvimage->width = -1; + xvimage->height = -1; + gst_buffer_unref (GST_BUFFER (xvimage)); +} static void gst_xvimage_buffer_init (GTypeInstance * instance, gpointer g_class) @@ -270,7 +318,7 @@ gst_xvimagesink_check_xshm_calls (GstXContext * xcontext) beach: XSetErrorHandler (handler); - gst_buffer_unref (GST_BUFFER (xvimage)); + gst_xvimage_buffer_free (xvimage); XSync (xcontext->disp, FALSE); return result; #endif /* HAVE_XSHM */ @@ -363,7 +411,7 @@ gst_xvimagesink_xvimage_new (GstXvImageSink * xvimagesink, beach: if (!succeeded) { - gst_buffer_unref (GST_BUFFER (xvimage)); + gst_xvimage_buffer_free (xvimage); xvimage = NULL; } @@ -1164,7 +1212,7 @@ gst_xvimagesink_imagepool_clear (GstXvImageSink * xvimagesink) xvimagesink->image_pool = g_slist_delete_link (xvimagesink->image_pool, xvimagesink->image_pool); - gst_buffer_unref (GST_BUFFER (xvimage)); + gst_xvimage_buffer_free (xvimage); } g_mutex_unlock (xvimagesink->pool_lock); @@ -1363,7 +1411,7 @@ gst_xvimagesink_setcaps (GstBaseSink * bsink, GstCaps * caps) GST_FOURCC_ARGS (xvimagesink->xcontext->im_format), GST_FOURCC_ARGS (im_format)); GST_DEBUG_OBJECT (xvimagesink, "renewing xvimage"); - gst_buffer_unref (GST_BUFFER (xvimagesink->xvimage)); + gst_xvimage_buffer_free (xvimagesink->xvimage); xvimagesink->xvimage = NULL; } @@ -1415,7 +1463,7 @@ gst_xvimagesink_change_state (GstElement * element) break; case GST_STATE_READY_TO_NULL: if (xvimagesink->xvimage) { - gst_buffer_unref (GST_BUFFER (xvimagesink->xvimage)); + gst_xvimage_buffer_free (xvimagesink->xvimage); xvimagesink->xvimage = NULL; } @@ -1467,32 +1515,42 @@ gst_xvimagesink_show_frame (GstBaseSink * bsink, GstBuffer * buf) /* 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_DEBUG ("fast put of bufferpool buffer"); gst_xvimagesink_xvimage_put (xvimagesink, GST_XVIMAGE_BUFFER (buf)); } else { + GST_DEBUG ("slow copy into bufferpool buffer"); /* Else we have to copy the data into our private image, */ /* if we have one... */ if (!xvimagesink->xvimage) { GST_DEBUG_OBJECT (xvimagesink, "creating our xvimage"); + xvimagesink->xvimage = gst_xvimagesink_xvimage_new (xvimagesink, xvimagesink->video_width, xvimagesink->video_height); - if (!xvimagesink->xvimage) { - /* No image available. That's very bad ! */ - gst_buffer_unref (buf); - GST_ELEMENT_ERROR (xvimagesink, CORE, NEGOTIATION, (NULL), - ("Failed creating an XvImage in xvimagesink chain function.")); - return GST_FLOW_ERROR; - } + + if (!xvimagesink->xvimage) + goto no_image; } memcpy (xvimagesink->xvimage->xvimage->data, GST_BUFFER_DATA (buf), MIN (GST_BUFFER_SIZE (buf), xvimagesink->xvimage->size)); + gst_xvimagesink_xvimage_put (xvimagesink, xvimagesink->xvimage); } gst_xvimagesink_handle_xevents (xvimagesink, GST_VIDEOSINK_PAD (xvimagesink)); return GST_FLOW_OK; + + /* ERRORS */ +no_image: + { + /* No image available. That's very bad ! */ + gst_buffer_unref (buf); + GST_ELEMENT_ERROR (xvimagesink, CORE, NEGOTIATION, (NULL), + ("Failed creating an XvImage in xvimagesink chain function.")); + return GST_FLOW_ERROR; + } } /* Buffer management */ @@ -1501,25 +1559,6 @@ gst_xvimagesink_show_frame (GstBaseSink * bsink, GstBuffer * buf) static void gst_xvimagesink_buffer_free (GstBuffer * buffer) { - GstXvImageSink *xvimagesink; - GstXvImageBuffer *xvimage; - - xvimage = GST_BUFFER_PRIVATE (buffer); - - g_assert (GST_IS_XVIMAGESINK (xvimage->xvimagesink)); - xvimagesink = xvimage->xvimagesink; - - /* If our geometry changed we can't reuse that image. */ - if ((xvimage->width != GST_VIDEOSINK_WIDTH (xvimagesink)) || - (xvimage->height != GST_VIDEOSINK_HEIGHT (xvimagesink))) - gst_xvimagesink_xvimage_destroy (xvimagesink, xvimage); - else { - /* In that case we can reuse the image and add it to our image pool. */ - g_mutex_lock (xvimagesink->pool_lock); - xvimagesink->image_pool = g_slist_prepend (xvimagesink->image_pool, - xvimage); - g_mutex_unlock (xvimagesink->pool_lock); - } } #endif @@ -1553,14 +1592,15 @@ gst_xvimagesink_buffer_alloc (GstBaseSink * bsink, guint64 offset, guint size, xvimagesink->image_pool); /* We check for geometry or image format changes */ - if ((xvimage->width != GST_VIDEOSINK_WIDTH (xvimagesink)) || - (xvimage->height != GST_VIDEOSINK_HEIGHT (xvimagesink)) || + if ((xvimage->width != xvimagesink->video_width) || + (xvimage->height != xvimagesink->video_height) || (xvimage->im_format != xvimagesink->xcontext->im_format)) { /* This image is unusable. Destroying... */ - gst_buffer_unref (GST_BUFFER (xvimage)); + gst_xvimage_buffer_free (xvimage); xvimage = NULL; } else { /* We found a suitable image */ + GST_DEBUG_OBJECT (xvimagesink, "found usable image in pool"); break; } } @@ -1707,7 +1747,7 @@ gst_xvimagesink_set_xwindow_id (GstXOverlay * overlay, XID xwindow_id) /* Clear the xvimage */ if (xvimagesink->xvimage) { - gst_buffer_unref (GST_BUFFER (xvimagesink->xvimage)); + gst_xvimage_buffer_free (xvimagesink->xvimage); xvimagesink->xvimage = NULL; }