mirror of
https://gitlab.freedesktop.org/gstreamer/gstreamer.git
synced 2025-04-26 06:54:49 +00:00
decoder: h264: fix tracking of DPB size changes.
Add support for MVC streams with multiple SPS and subset SPS headers emitted regularly, e.g. at around every I-frame. Track the maximum number of views in ensure_context() and really reset the DPB size to the expected value, always. i.e. even if it decreased. dpb_reset() only cares of ensuring the DPB allocation.
This commit is contained in:
parent
9169c520cb
commit
850d3d6a4d
1 changed files with 12 additions and 18 deletions
|
@ -985,9 +985,6 @@ dpb_reset(GstVaapiDecoderH264 *decoder, guint dpb_size)
|
||||||
{
|
{
|
||||||
GstVaapiDecoderH264Private * const priv = &decoder->priv;
|
GstVaapiDecoderH264Private * const priv = &decoder->priv;
|
||||||
|
|
||||||
if (dpb_size < priv->dpb_count)
|
|
||||||
return FALSE;
|
|
||||||
|
|
||||||
if (dpb_size > priv->dpb_size_max) {
|
if (dpb_size > priv->dpb_size_max) {
|
||||||
priv->dpb = g_try_realloc_n(priv->dpb, dpb_size, sizeof(*priv->dpb));
|
priv->dpb = g_try_realloc_n(priv->dpb, dpb_size, sizeof(*priv->dpb));
|
||||||
if (!priv->dpb)
|
if (!priv->dpb)
|
||||||
|
@ -996,11 +993,7 @@ dpb_reset(GstVaapiDecoderH264 *decoder, guint dpb_size)
|
||||||
(dpb_size - priv->dpb_size_max) * sizeof(*priv->dpb));
|
(dpb_size - priv->dpb_size_max) * sizeof(*priv->dpb));
|
||||||
priv->dpb_size_max = dpb_size;
|
priv->dpb_size_max = dpb_size;
|
||||||
}
|
}
|
||||||
|
priv->dpb_size = dpb_size;
|
||||||
if (priv->dpb_size < dpb_size)
|
|
||||||
priv->dpb_size = dpb_size;
|
|
||||||
else if (dpb_size < priv->dpb_count)
|
|
||||||
return FALSE;
|
|
||||||
|
|
||||||
GST_DEBUG("DPB size %u", priv->dpb_size);
|
GST_DEBUG("DPB size %u", priv->dpb_size);
|
||||||
return TRUE;
|
return TRUE;
|
||||||
|
@ -1300,7 +1293,13 @@ ensure_context(GstVaapiDecoderH264 *decoder, GstH264SPS *sps)
|
||||||
GstVaapiProfile profile;
|
GstVaapiProfile profile;
|
||||||
GstVaapiChromaType chroma_type;
|
GstVaapiChromaType chroma_type;
|
||||||
gboolean reset_context = FALSE;
|
gboolean reset_context = FALSE;
|
||||||
guint mb_width, mb_height, dpb_size;
|
guint mb_width, mb_height, dpb_size, num_views;
|
||||||
|
|
||||||
|
num_views = get_num_views(sps);
|
||||||
|
if (priv->max_views < num_views) {
|
||||||
|
priv->max_views = num_views;
|
||||||
|
GST_DEBUG("maximum number of views changed to %u", num_views);
|
||||||
|
}
|
||||||
|
|
||||||
dpb_size = get_max_dec_frame_buffering(sps);
|
dpb_size = get_max_dec_frame_buffering(sps);
|
||||||
if (priv->dpb_size < dpb_size) {
|
if (priv->dpb_size < dpb_size) {
|
||||||
|
@ -1495,9 +1494,6 @@ parse_sps(GstVaapiDecoderH264 *decoder, GstVaapiDecoderUnit *unit)
|
||||||
if (result != GST_H264_PARSER_OK)
|
if (result != GST_H264_PARSER_OK)
|
||||||
return get_status(result);
|
return get_status(result);
|
||||||
|
|
||||||
/* Reset defaults */
|
|
||||||
priv->max_views = 1;
|
|
||||||
|
|
||||||
priv->parser_state |= GST_H264_VIDEO_STATE_GOT_SPS;
|
priv->parser_state |= GST_H264_VIDEO_STATE_GOT_SPS;
|
||||||
return GST_VAAPI_DECODER_STATUS_SUCCESS;
|
return GST_VAAPI_DECODER_STATUS_SUCCESS;
|
||||||
}
|
}
|
||||||
|
@ -1577,7 +1573,6 @@ parse_slice(GstVaapiDecoderH264 *decoder, GstVaapiDecoderUnit *unit)
|
||||||
GstH264NalUnit * const nalu = &pi->nalu;
|
GstH264NalUnit * const nalu = &pi->nalu;
|
||||||
GstH264SPS *sps;
|
GstH264SPS *sps;
|
||||||
GstH264ParserResult result;
|
GstH264ParserResult result;
|
||||||
guint num_views;
|
|
||||||
|
|
||||||
GST_DEBUG("parse slice");
|
GST_DEBUG("parse slice");
|
||||||
|
|
||||||
|
@ -1625,11 +1620,6 @@ parse_slice(GstVaapiDecoderH264 *decoder, GstVaapiDecoderUnit *unit)
|
||||||
sps = slice_hdr->pps->sequence;
|
sps = slice_hdr->pps->sequence;
|
||||||
|
|
||||||
/* Update MVC data */
|
/* Update MVC data */
|
||||||
num_views = get_num_views(sps);
|
|
||||||
if (priv->max_views < num_views) {
|
|
||||||
priv->max_views = num_views;
|
|
||||||
GST_DEBUG("maximum number of views changed to %u", num_views);
|
|
||||||
}
|
|
||||||
pi->view_id = get_view_id(&pi->nalu);
|
pi->view_id = get_view_id(&pi->nalu);
|
||||||
pi->voc = get_view_order_index(sps, pi->view_id);
|
pi->voc = get_view_order_index(sps, pi->view_id);
|
||||||
|
|
||||||
|
@ -1679,6 +1669,7 @@ decode_pps(GstVaapiDecoderH264 *decoder, GstVaapiDecoderUnit *unit)
|
||||||
static GstVaapiDecoderStatus
|
static GstVaapiDecoderStatus
|
||||||
decode_sequence_end(GstVaapiDecoderH264 *decoder)
|
decode_sequence_end(GstVaapiDecoderH264 *decoder)
|
||||||
{
|
{
|
||||||
|
GstVaapiDecoderH264Private * const priv = &decoder->priv;
|
||||||
GstVaapiDecoderStatus status;
|
GstVaapiDecoderStatus status;
|
||||||
|
|
||||||
GST_DEBUG("decode sequence-end");
|
GST_DEBUG("decode sequence-end");
|
||||||
|
@ -1688,6 +1679,9 @@ decode_sequence_end(GstVaapiDecoderH264 *decoder)
|
||||||
return status;
|
return status;
|
||||||
|
|
||||||
dpb_flush(decoder, NULL);
|
dpb_flush(decoder, NULL);
|
||||||
|
|
||||||
|
/* Reset defaults, should there be a new sequence available next */
|
||||||
|
priv->max_views = 1;
|
||||||
return GST_VAAPI_DECODER_STATUS_SUCCESS;
|
return GST_VAAPI_DECODER_STATUS_SUCCESS;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Reference in a new issue