From f55b36e6aaca6be051a3b02f54ed24714121f00e Mon Sep 17 00:00:00 2001 From: He Junyan Date: Sun, 24 Apr 2022 23:19:00 +0800 Subject: [PATCH] videoscale: Fix the src video info error in transfer_colorimetry_from_input() Pipeline such as: gst-launch-1.0 -vf videotestsrc ! video/x-raw,format=NV12,colorimetry=\(string\)bt709 \ ! videoscale ! video/x-raw,format=I420 ! fakesink Always trigger a error: ERROR video-info video-info.c:556:gst_video_info_from_caps: no width property given Because it is called before the fixate_size(), the src caps' resolution may be absent or not fixed. That causes that the src video info can not be created correctly and we can not inherit the colorimetry and chroma-site from the input caps. Part-of: --- .../videoconvertscale/gstvideoconvertscale.c | 25 ++++++++++++++++--- 1 file changed, 21 insertions(+), 4 deletions(-) diff --git a/subprojects/gst-plugins-base/gst/videoconvertscale/gstvideoconvertscale.c b/subprojects/gst-plugins-base/gst/videoconvertscale/gstvideoconvertscale.c index 577a03c44a..fabc63c3ef 100644 --- a/subprojects/gst-plugins-base/gst/videoconvertscale/gstvideoconvertscale.c +++ b/subprojects/gst-plugins-base/gst/videoconvertscale/gstvideoconvertscale.c @@ -795,9 +795,9 @@ gst_video_convert_scale_set_info (GstVideoFilter * filter, GstCaps * in, tmp_info = *in_info; tmp_info.colorimetry.transfer = out_info->colorimetry.transfer; if (gst_video_info_is_equal (&tmp_info, out_info)) { - if (gst_video_transfer_function_is_equivalent (in_info-> - colorimetry.transfer, in_info->finfo->bits, - out_info->colorimetry.transfer, out_info->finfo->bits)) { + if (gst_video_transfer_function_is_equivalent (in_info->colorimetry. + transfer, in_info->finfo->bits, out_info->colorimetry.transfer, + out_info->finfo->bits)) { gst_base_transform_set_passthrough (GST_BASE_TRANSFORM (filter), TRUE); } } else { @@ -1164,17 +1164,34 @@ transfer_colorimetry_from_input (GstBaseTransform * trans, GstCaps * in_caps, GstVideoInfo in_info, out_info; const GValue *in_colorimetry = gst_structure_get_value (in_caps_s, "colorimetry"); + GstCaps *tmp_caps = NULL; + GstStructure *tmp_caps_s; if (!gst_video_info_from_caps (&in_info, in_caps)) { GST_WARNING_OBJECT (trans, "Failed to convert sink pad caps to video info"); return; } - if (!gst_video_info_from_caps (&out_info, out_caps)) { + + /* We are before fixate_size(), the width and height of + the output caps may be absent or not fixed. */ + tmp_caps = gst_caps_copy (out_caps); + tmp_caps = gst_caps_fixate (tmp_caps); + tmp_caps_s = gst_caps_get_structure (tmp_caps, 0); + if (!gst_structure_has_field (tmp_caps_s, "width")) + gst_structure_set_value (tmp_caps_s, "width", + gst_structure_get_value (in_caps_s, "width")); + if (!gst_structure_has_field (tmp_caps_s, "height")) + gst_structure_set_value (tmp_caps_s, "height", + gst_structure_get_value (in_caps_s, "height")); + + if (!gst_video_info_from_caps (&out_info, tmp_caps)) { + gst_clear_caps (&tmp_caps); GST_WARNING_OBJECT (trans, "Failed to convert src pad caps to video info"); return; } + gst_clear_caps (&tmp_caps); if (!have_colorimetry && in_colorimetry != NULL) { if ((GST_VIDEO_INFO_IS_YUV (&out_info)