mirror of
https://gitlab.freedesktop.org/gstreamer/gstreamer.git
synced 2024-11-27 04:01:08 +00:00
mpeg2: allocate dummy picture for first field based I-frame.
In P-pictures, prediction shall be made from the two most recently decoded reference fields. However, when the first I-frame is a field, the next field of the current picture could be a P-picture but only a single field was decoded so far. In this case, create a dummy picture with POC = -1 that will be used as reference. Some VA drivers would error out if P-pictures don't have a forward reference picture. This is true in general but not in this very specific initial case.
This commit is contained in:
parent
99932049e4
commit
5975def8ab
3 changed files with 45 additions and 0 deletions
|
@ -238,6 +238,14 @@ gst_vaapi_dpb_add(GstVaapiDpb *dpb, GstVaapiPicture *picture)
|
|||
return klass->add(dpb, picture);
|
||||
}
|
||||
|
||||
guint
|
||||
gst_vaapi_dpb_size(GstVaapiDpb *dpb)
|
||||
{
|
||||
g_return_val_if_fail(GST_VAAPI_IS_DPB(dpb), 0);
|
||||
|
||||
return dpb->num_pictures;
|
||||
}
|
||||
|
||||
/* ------------------------------------------------------------------------- */
|
||||
/* --- MPEG-2 Decoded Picture Buffer --- */
|
||||
/* ------------------------------------------------------------------------- */
|
||||
|
|
|
@ -103,6 +103,10 @@ gboolean
|
|||
gst_vaapi_dpb_add(GstVaapiDpb *dpb, GstVaapiPicture *picture)
|
||||
attribute_hidden;
|
||||
|
||||
guint
|
||||
gst_vaapi_dpb_size(GstVaapiDpb *dpb)
|
||||
attribute_hidden;
|
||||
|
||||
static inline gpointer
|
||||
gst_vaapi_dpb_ref(gpointer ptr)
|
||||
{
|
||||
|
|
|
@ -700,6 +700,39 @@ decode_picture_ext(GstVaapiDecoderMpeg2 *decoder, guchar *buf, guint buf_size)
|
|||
picture->structure = GST_VAAPI_PICTURE_STRUCTURE_FRAME;
|
||||
break;
|
||||
}
|
||||
|
||||
/* Allocate dummy picture for first field based I-frame */
|
||||
if (picture->type == GST_VAAPI_PICTURE_TYPE_I &&
|
||||
!GST_VAAPI_PICTURE_IS_FRAME(picture) &&
|
||||
gst_vaapi_dpb_size(priv->dpb) == 0) {
|
||||
GstVaapiPicture *dummy_picture;
|
||||
gboolean success;
|
||||
|
||||
dummy_picture = GST_VAAPI_PICTURE_NEW(MPEG2, decoder);
|
||||
if (!dummy_picture) {
|
||||
GST_ERROR("failed to allocate dummy picture");
|
||||
return GST_VAAPI_DECODER_STATUS_ERROR_ALLOCATION_FAILED;
|
||||
}
|
||||
|
||||
dummy_picture->type = GST_VAAPI_PICTURE_TYPE_I;
|
||||
dummy_picture->pts = GST_CLOCK_TIME_NONE;
|
||||
dummy_picture->poc = -1;
|
||||
dummy_picture->structure = GST_VAAPI_PICTURE_STRUCTURE_FRAME;
|
||||
|
||||
GST_VAAPI_PICTURE_FLAG_SET(
|
||||
dummy_picture,
|
||||
(GST_VAAPI_PICTURE_FLAG_SKIPPED |
|
||||
GST_VAAPI_PICTURE_FLAG_REFERENCE)
|
||||
);
|
||||
|
||||
success = gst_vaapi_dpb_add(priv->dpb, dummy_picture);
|
||||
gst_vaapi_picture_unref(dummy_picture);
|
||||
if (!success) {
|
||||
GST_ERROR("failed to add dummy picture into DPB");
|
||||
return GST_VAAPI_DECODER_STATUS_ERROR_UNKNOWN;
|
||||
}
|
||||
GST_INFO("allocated dummy picture for first field based I-frame");
|
||||
}
|
||||
return GST_VAAPI_DECODER_STATUS_SUCCESS;
|
||||
}
|
||||
|
||||
|
|
Loading…
Reference in a new issue