v4l2codecs: h264: retrieve interlaced information

Lets the decoder knows if the frames are interlaced or not.
Provide this information to the driver while filling reference
pictures fields in slice params structure

Part-of: <https://gitlab.freedesktop.org/gstreamer/gst-plugins-bad/-/merge_requests/1624>
This commit is contained in:
Benjamin Gaignard 2021-02-16 11:23:17 +01:00 committed by GStreamer Merge Bot
parent 84daea6be2
commit 5e8daa1c5c

View file

@ -75,6 +75,7 @@ struct _GstV4l2CodecH264Dec
gint min_pool_size;
gboolean has_videometa;
gboolean need_negotiation;
gboolean interlaced;
gboolean need_sequence;
gboolean copy_frames;
gboolean scaling_matrix_present;
@ -372,6 +373,9 @@ gst_v4l2_codec_h264_dec_negotiate (GstVideoDecoder * decoder)
self->vinfo.finfo->format, self->display_width,
self->display_height, h264dec->input_state);
if (self->interlaced)
self->output_state->info.interlace_mode = GST_VIDEO_INTERLACE_MODE_MIXED;
self->output_state->caps = gst_video_info_to_caps (&self->output_state->info);
if (GST_VIDEO_DECODER_CLASS (parent_class)->negotiate (decoder)) {
@ -715,7 +719,10 @@ gst_v4l2_codec_h264_dec_fill_references (GstV4l2CodecH264Dec * self,
GArray * ref_pic_list0, GArray * ref_pic_list1)
{
struct v4l2_ctrl_h264_slice_params *slice_params;
gint i;
gint i, fields = V4L2_H264_FRAME_REF;
if (self->interlaced)
fields = 0;
slice_params = &g_array_index (self->slice_params,
struct v4l2_ctrl_h264_slice_params, 0);
@ -730,7 +737,7 @@ gst_v4l2_codec_h264_dec_fill_references (GstV4l2CodecH264Dec * self,
g_array_index (ref_pic_list0, GstH264Picture *, i);
slice_params->ref_pic_list0[i].index =
lookup_dpb_index (self->decode_params.dpb, ref_pic);
slice_params->ref_pic_list0[i].fields = 0;
slice_params->ref_pic_list0[i].fields = fields;
}
for (i = 0; i < ref_pic_list1->len; i++) {
@ -738,7 +745,7 @@ gst_v4l2_codec_h264_dec_fill_references (GstV4l2CodecH264Dec * self,
g_array_index (ref_pic_list1, GstH264Picture *, i);
slice_params->ref_pic_list1[i].index =
lookup_dpb_index (self->decode_params.dpb, ref_pic);
slice_params->ref_pic_list1[i].fields = 0;
slice_params->ref_pic_list1[i].fields = fields;
}
}
@ -750,6 +757,7 @@ gst_v4l2_codec_h264_dec_new_sequence (GstH264Decoder * decoder,
gint crop_width = sps->width;
gint crop_height = sps->height;
gboolean negotiation_needed = FALSE;
gboolean interlaced;
if (self->vinfo.finfo->format == GST_VIDEO_FORMAT_UNKNOWN)
negotiation_needed = TRUE;
@ -778,6 +786,14 @@ gst_v4l2_codec_h264_dec_new_sequence (GstH264Decoder * decoder,
self->coded_width, self->coded_height);
}
interlaced = !sps->frame_mbs_only_flag;
if (self->interlaced != interlaced) {
self->interlaced = interlaced;
negotiation_needed = TRUE;
GST_INFO_OBJECT (self, "Interlaced mode changed to %d", interlaced);
}
if (self->bitdepth != sps->bit_depth_luma_minus8 + 8) {
self->bitdepth = sps->bit_depth_luma_minus8 + 8;
negotiation_needed = TRUE;