nvdec: Use interlace info in input caps
... instead of relying on only parsed values from bitstream. Also parses HEVC specific interlace information Part-of: <https://gitlab.freedesktop.org/gstreamer/gstreamer/-/merge_requests/9170>
This commit is contained in:
parent
3b896cd4ea
commit
712203163e
@ -1988,11 +1988,22 @@ gst_nv_decoder_negotiate (GstNvDecoder * decoder,
|
||||
}
|
||||
#endif
|
||||
|
||||
state = gst_video_decoder_set_interlaced_output_state (videodec,
|
||||
state = gst_video_decoder_set_output_state (videodec,
|
||||
GST_VIDEO_INFO_FORMAT (&decoder->output_info),
|
||||
GST_VIDEO_INFO_INTERLACE_MODE (&decoder->output_info),
|
||||
GST_VIDEO_INFO_WIDTH (&decoder->output_info),
|
||||
GST_VIDEO_INFO_HEIGHT (&decoder->output_info), input_state);
|
||||
|
||||
if (GST_VIDEO_INFO_IS_INTERLACED (&decoder->info)) {
|
||||
auto in_s = gst_caps_get_structure (input_state->caps, 0);
|
||||
if (!gst_structure_has_field (in_s, "interlace-mode")) {
|
||||
/* Use our parsed info if missed in upstream */
|
||||
GST_VIDEO_INFO_INTERLACE_MODE (&state->info) =
|
||||
GST_VIDEO_INFO_INTERLACE_MODE (&decoder->info);
|
||||
GST_VIDEO_INFO_FIELD_ORDER (&state->info) =
|
||||
GST_VIDEO_INFO_FIELD_ORDER (&decoder->info);
|
||||
}
|
||||
}
|
||||
|
||||
state->caps = gst_video_info_to_caps (&state->info);
|
||||
|
||||
switch (decoder->output_type) {
|
||||
|
@ -153,6 +153,7 @@ typedef struct _GstNvH265Dec
|
||||
gint max_display_delay;
|
||||
|
||||
GstVideoFormat out_format;
|
||||
GstVideoInterlaceMode interlace_mode;
|
||||
} GstNvH265Dec;
|
||||
|
||||
typedef struct _GstNvH265DecClass
|
||||
@ -193,6 +194,7 @@ static void gst_nv_h265_dec_set_context (GstElement * element,
|
||||
GstContext * context);
|
||||
static gboolean gst_nv_h265_dec_open (GstVideoDecoder * decoder);
|
||||
static gboolean gst_nv_h265_dec_close (GstVideoDecoder * decoder);
|
||||
static gboolean gst_nv_h265_dec_start (GstVideoDecoder * decoder);
|
||||
static gboolean gst_nv_h265_dec_stop (GstVideoDecoder * decoder);
|
||||
static gboolean gst_nv_h265_dec_negotiate (GstVideoDecoder * decoder);
|
||||
static gboolean gst_nv_h265_dec_decide_allocation (GstVideoDecoder *
|
||||
@ -334,6 +336,7 @@ gst_nv_h265_dec_class_init (GstNvH265DecClass * klass,
|
||||
|
||||
decoder_class->open = GST_DEBUG_FUNCPTR (gst_nv_h265_dec_open);
|
||||
decoder_class->close = GST_DEBUG_FUNCPTR (gst_nv_h265_dec_close);
|
||||
decoder_class->start = GST_DEBUG_FUNCPTR (gst_nv_h265_dec_start);
|
||||
decoder_class->stop = GST_DEBUG_FUNCPTR (gst_nv_h265_dec_stop);
|
||||
decoder_class->negotiate = GST_DEBUG_FUNCPTR (gst_nv_h265_dec_negotiate);
|
||||
decoder_class->decide_allocation =
|
||||
@ -489,6 +492,23 @@ gst_nv_h265_dec_close (GstVideoDecoder * decoder)
|
||||
return gst_nv_decoder_close (self->decoder);
|
||||
}
|
||||
|
||||
static gboolean
|
||||
gst_nv_h265_dec_start (GstVideoDecoder * decoder)
|
||||
{
|
||||
GstNvH265Dec *self = GST_NV_H265_DEC (decoder);
|
||||
|
||||
self->width = 0;
|
||||
self->height = 0;
|
||||
self->coded_width = 0;
|
||||
self->coded_height = 0;
|
||||
self->interlace_mode = GST_VIDEO_INTERLACE_MODE_PROGRESSIVE;
|
||||
self->chroma_format_idc = 0;
|
||||
self->bitdepth = 0;
|
||||
self->max_dpb_size = 0;
|
||||
|
||||
return GST_VIDEO_DECODER_CLASS (parent_class)->start (decoder);
|
||||
}
|
||||
|
||||
static gboolean
|
||||
gst_nv_h265_dec_stop (GstVideoDecoder * decoder)
|
||||
{
|
||||
@ -581,6 +601,7 @@ gst_nv_h265_dec_new_sequence (GstH265Decoder * decoder, const GstH265SPS * sps,
|
||||
gboolean modified = FALSE;
|
||||
guint max_width, max_height;
|
||||
GstVideoFormat out_format = GST_VIDEO_FORMAT_UNKNOWN;
|
||||
GstVideoInterlaceMode interlace_mode = GST_VIDEO_INTERLACE_MODE_PROGRESSIVE;
|
||||
gboolean is_gbr = FALSE;
|
||||
const GstH265VUIParams *vui = &sps->vui_params;
|
||||
|
||||
@ -630,6 +651,26 @@ gst_nv_h265_dec_new_sequence (GstH265Decoder * decoder, const GstH265SPS * sps,
|
||||
is_gbr = TRUE;
|
||||
}
|
||||
|
||||
if (sps->vui_parameters_present_flag && sps->vui_params.field_seq_flag) {
|
||||
GST_ELEMENT_WARNING (self, STREAM, NOT_IMPLEMENTED, (nullptr),
|
||||
("alternate interlace mode is not properly supported. Output might have wrong aspect ratio"));
|
||||
} else {
|
||||
/* 7.4.4 Profile, tier and level sementics */
|
||||
if (sps->profile_tier_level.progressive_source_flag &&
|
||||
!sps->profile_tier_level.interlaced_source_flag) {
|
||||
interlace_mode = GST_VIDEO_INTERLACE_MODE_PROGRESSIVE;
|
||||
} else {
|
||||
interlace_mode = GST_VIDEO_INTERLACE_MODE_MIXED;
|
||||
}
|
||||
}
|
||||
|
||||
if (self->interlace_mode != interlace_mode) {
|
||||
GST_INFO_OBJECT (self, "Interlace mode change %d -> %d",
|
||||
self->interlace_mode, interlace_mode);
|
||||
self->interlace_mode = interlace_mode;
|
||||
modified = TRUE;
|
||||
}
|
||||
|
||||
switch (self->bitdepth) {
|
||||
case 8:
|
||||
if (self->chroma_format_idc == 1)
|
||||
@ -677,8 +718,8 @@ gst_nv_h265_dec_new_sequence (GstH265Decoder * decoder, const GstH265SPS * sps,
|
||||
if (modified || !gst_nv_decoder_is_configured (self->decoder)) {
|
||||
GstVideoInfo info;
|
||||
|
||||
gst_video_info_set_format (&info,
|
||||
self->out_format, self->width, self->height);
|
||||
gst_video_info_set_interlaced_format (&info,
|
||||
self->out_format, self->interlace_mode, self->width, self->height);
|
||||
|
||||
self->max_dpb_size = max_dpb_size;
|
||||
max_width = gst_nv_decoder_get_max_output_size (self->coded_width,
|
||||
|
Loading…
x
Reference in New Issue
Block a user