diff options
author | Sebastian Dröge <slomo@circular-chaos.org> | 2013-05-24 16:51:17 +0200 |
---|---|---|
committer | Sebastian Dröge <slomo@circular-chaos.org> | 2013-05-24 16:54:46 +0200 |
commit | 0c2c909497f5f97074cf1b0d26bd14939f892b6f (patch) | |
tree | d0e873ed447aa522c29e6f2304e1967378c6f219 | |
parent | fa7ad8743c47ec9256cf4f6e16c1bb8c57d91db7 (diff) |
video: Always provide a buffer in gst_video_(enc|dec)oder_allocate_output_buffer()
We have no way of tell the caller of the exact error (e.g. if we're flushing),
so will have to wait until the caller uses API that returns a GstFlowReturn,
for example when pushing this buffer.
https://bugzilla.gnome.org/show_bug.cgi?id=700006
-rw-r--r-- | gst-libs/gst/video/gstvideodecoder.c | 32 | ||||
-rw-r--r-- | gst-libs/gst/video/gstvideoencoder.c | 26 |
2 files changed, 44 insertions, 14 deletions
diff --git a/gst-libs/gst/video/gstvideodecoder.c b/gst-libs/gst/video/gstvideodecoder.c index e6ebc73c8..5f0bf20d1 100644 --- a/gst-libs/gst/video/gstvideodecoder.c +++ b/gst-libs/gst/video/gstvideodecoder.c @@ -3128,6 +3128,7 @@ gst_video_decoder_negotiate (GstVideoDecoder * decoder) gboolean ret = TRUE; g_return_val_if_fail (GST_IS_VIDEO_DECODER (decoder), FALSE); + g_return_val_if_fail (decoder->priv->output_state, FALSE); klass = GST_VIDEO_DECODER_GET_CLASS (decoder); @@ -3156,25 +3157,38 @@ GstBuffer * gst_video_decoder_allocate_output_buffer (GstVideoDecoder * decoder) { GstFlowReturn flow; - GstBuffer *buffer; + GstBuffer *buffer = NULL; + + g_return_val_if_fail (decoder->priv->output_state, NULL); GST_DEBUG ("alloc src buffer"); GST_VIDEO_DECODER_STREAM_LOCK (decoder); if (G_UNLIKELY (decoder->priv->output_state_changed - || (decoder->priv->output_state - && gst_pad_check_reconfigure (decoder->srcpad)))) - gst_video_decoder_negotiate (decoder); + || gst_pad_check_reconfigure (decoder->srcpad))) { + if (!gst_video_decoder_negotiate (decoder)) { + GST_DEBUG_OBJECT (decoder, "Failed to negotiate, fallback allocation"); + goto fallback; + } + } flow = gst_buffer_pool_acquire_buffer (decoder->priv->pool, &buffer, NULL); - GST_VIDEO_DECODER_STREAM_UNLOCK (decoder); - if (flow != GST_FLOW_OK) { GST_INFO_OBJECT (decoder, "couldn't allocate output buffer, flow %s", gst_flow_get_name (flow)); - buffer = NULL; + goto fallback; } + GST_VIDEO_DECODER_STREAM_UNLOCK (decoder); + + return buffer; + +fallback: + buffer = + gst_buffer_new_allocate (NULL, decoder->priv->output_state->info.size, + NULL); + + GST_VIDEO_DECODER_STREAM_UNLOCK (decoder); return buffer; } @@ -3201,6 +3215,7 @@ gst_video_decoder_allocate_output_frame (GstVideoDecoder * GstVideoCodecState *state; int num_bytes; + g_return_val_if_fail (decoder->priv->output_state, GST_FLOW_NOT_NEGOTIATED); g_return_val_if_fail (frame->output_buffer == NULL, GST_FLOW_ERROR); GST_VIDEO_DECODER_STREAM_LOCK (decoder); @@ -3217,8 +3232,7 @@ gst_video_decoder_allocate_output_frame (GstVideoDecoder * } if (G_UNLIKELY (decoder->priv->output_state_changed - || (decoder->priv->output_state - && gst_pad_check_reconfigure (decoder->srcpad)))) + || gst_pad_check_reconfigure (decoder->srcpad))) gst_video_decoder_negotiate (decoder); GST_LOG_OBJECT (decoder, "alloc buffer size %d", num_bytes); diff --git a/gst-libs/gst/video/gstvideoencoder.c b/gst-libs/gst/video/gstvideoencoder.c index 155173a1f..6f92493b9 100644 --- a/gst-libs/gst/video/gstvideoencoder.c +++ b/gst-libs/gst/video/gstvideoencoder.c @@ -1573,6 +1573,7 @@ gst_video_encoder_negotiate (GstVideoEncoder * encoder) gboolean ret = TRUE; g_return_val_if_fail (GST_IS_VIDEO_ENCODER (encoder), FALSE); + g_return_val_if_fail (encoder->priv->output_state, FALSE); klass = GST_VIDEO_ENCODER_GET_CLASS (encoder); @@ -1599,19 +1600,34 @@ gst_video_encoder_allocate_output_buffer (GstVideoEncoder * encoder, gsize size) { GstBuffer *buffer; + g_return_val_if_fail (encoder->priv->output_state, NULL); g_return_val_if_fail (size > 0, NULL); GST_DEBUG ("alloc src buffer"); GST_VIDEO_ENCODER_STREAM_LOCK (encoder); if (G_UNLIKELY (encoder->priv->output_state_changed - || (encoder->priv->output_state - && gst_pad_check_reconfigure (encoder->srcpad)))) - gst_video_encoder_negotiate (encoder); + || gst_pad_check_reconfigure (encoder->srcpad))) { + if (!gst_video_encoder_negotiate (encoder)) { + GST_DEBUG_OBJECT (encoder, "Failed to negotiate, fallback allocation"); + goto fallback; + } + } buffer = gst_buffer_new_allocate (encoder->priv->allocator, size, &encoder->priv->params); + if (!buffer) { + GST_INFO_OBJECT (encoder, "couldn't allocate output buffer"); + goto fallback; + } + + GST_VIDEO_ENCODER_STREAM_UNLOCK (encoder); + + return buffer; + +fallback: + buffer = gst_buffer_new_allocate (NULL, size, NULL); GST_VIDEO_ENCODER_STREAM_UNLOCK (encoder); @@ -1638,11 +1654,11 @@ gst_video_encoder_allocate_output_frame (GstVideoEncoder * encoder, GstVideoCodecFrame * frame, gsize size) { g_return_val_if_fail (frame->output_buffer == NULL, GST_FLOW_ERROR); + g_return_val_if_fail (encoder->priv->output_state, GST_FLOW_NOT_NEGOTIATED); GST_VIDEO_ENCODER_STREAM_LOCK (encoder); if (G_UNLIKELY (encoder->priv->output_state_changed - || (encoder->priv->output_state - && gst_pad_check_reconfigure (encoder->srcpad)))) + || gst_pad_check_reconfigure (encoder->srcpad))) gst_video_encoder_negotiate (encoder); GST_LOG_OBJECT (encoder, "alloc buffer size %" G_GSIZE_FORMAT, size); |