mirror of
https://gitlab.freedesktop.org/gstreamer/gstreamer.git
synced 2024-12-23 08:46:40 +00:00
qsvh265dec: Add support for GBR decoding
Use GBR equivalent output formats if RGB colorspace is detected Part-of: <https://gitlab.freedesktop.org/gstreamer/gstreamer/-/merge_requests/5706>
This commit is contained in:
parent
e4729e5784
commit
865d7a1351
7 changed files with 50 additions and 8 deletions
|
@ -149,6 +149,8 @@ gst_qsv_allocator_init (GstQsvAllocator * self)
|
||||||
{
|
{
|
||||||
GstQsvAllocatorPrivate *priv;
|
GstQsvAllocatorPrivate *priv;
|
||||||
|
|
||||||
|
self->is_gbr = FALSE;
|
||||||
|
|
||||||
priv = self->priv = (GstQsvAllocatorPrivate *)
|
priv = self->priv = (GstQsvAllocatorPrivate *)
|
||||||
gst_qsv_allocator_get_instance_private (self);
|
gst_qsv_allocator_get_instance_private (self);
|
||||||
|
|
||||||
|
@ -199,7 +201,7 @@ gst_qsv_allocator_alloc_default (GstQsvAllocator * self, gboolean dummy_alloc,
|
||||||
return MFX_ERR_UNSUPPORTED;
|
return MFX_ERR_UNSUPPORTED;
|
||||||
}
|
}
|
||||||
|
|
||||||
format = gst_qsv_frame_info_format_to_gst (&request->Info);
|
format = gst_qsv_frame_info_format_to_gst (&request->Info, self->is_gbr);
|
||||||
if (format == GST_VIDEO_FORMAT_UNKNOWN) {
|
if (format == GST_VIDEO_FORMAT_UNKNOWN) {
|
||||||
GST_ERROR_OBJECT (self, "Unknown MFX format fourcc %" GST_FOURCC_FORMAT,
|
GST_ERROR_OBJECT (self, "Unknown MFX format fourcc %" GST_FOURCC_FORMAT,
|
||||||
GST_FOURCC_ARGS (request->Info.FourCC));
|
GST_FOURCC_ARGS (request->Info.FourCC));
|
||||||
|
@ -406,15 +408,18 @@ gst_qsv_allocator_lock (mfxHDL pthis, mfxMemId mid, mfxFrameData * ptr)
|
||||||
ptr->V16 = ptr->Y16 + 3;
|
ptr->V16 = ptr->Y16 + 3;
|
||||||
break;
|
break;
|
||||||
case GST_VIDEO_FORMAT_VUYA:
|
case GST_VIDEO_FORMAT_VUYA:
|
||||||
|
case GST_VIDEO_FORMAT_RBGA:
|
||||||
ptr->V = (mfxU8 *) GST_VIDEO_FRAME_PLANE_DATA (&frame->frame, 0);
|
ptr->V = (mfxU8 *) GST_VIDEO_FRAME_PLANE_DATA (&frame->frame, 0);
|
||||||
ptr->U = ptr->V + 1;
|
ptr->U = ptr->V + 1;
|
||||||
ptr->Y = ptr->V + 2;
|
ptr->Y = ptr->V + 2;
|
||||||
ptr->A = ptr->V + 3;
|
ptr->A = ptr->V + 3;
|
||||||
break;
|
break;
|
||||||
case GST_VIDEO_FORMAT_Y410:
|
case GST_VIDEO_FORMAT_Y410:
|
||||||
|
case GST_VIDEO_FORMAT_BGR10A2_LE:
|
||||||
ptr->Y410 = (mfxY410 *) GST_VIDEO_FRAME_PLANE_DATA (&frame->frame, 0);
|
ptr->Y410 = (mfxY410 *) GST_VIDEO_FRAME_PLANE_DATA (&frame->frame, 0);
|
||||||
break;
|
break;
|
||||||
case GST_VIDEO_FORMAT_Y412_LE:
|
case GST_VIDEO_FORMAT_Y412_LE:
|
||||||
|
case GST_VIDEO_FORMAT_BGRA64_LE:
|
||||||
ptr->U = (mfxU8 *) GST_VIDEO_FRAME_PLANE_DATA (&frame->frame, 0);
|
ptr->U = (mfxU8 *) GST_VIDEO_FRAME_PLANE_DATA (&frame->frame, 0);
|
||||||
ptr->Y = ptr->Y + 2;
|
ptr->Y = ptr->Y + 2;
|
||||||
ptr->V = ptr->Y + 4;
|
ptr->V = ptr->Y + 4;
|
||||||
|
|
|
@ -83,6 +83,7 @@ typedef enum
|
||||||
struct _GstQsvAllocator
|
struct _GstQsvAllocator
|
||||||
{
|
{
|
||||||
GstObject parent;
|
GstObject parent;
|
||||||
|
gboolean is_gbr;
|
||||||
|
|
||||||
GstQsvAllocatorPrivate *priv;
|
GstQsvAllocatorPrivate *priv;
|
||||||
};
|
};
|
||||||
|
|
|
@ -99,7 +99,7 @@ gst_qsv_d3d11_allocator_alloc (GstQsvAllocator * allocator,
|
||||||
return MFX_ERR_UNSUPPORTED;
|
return MFX_ERR_UNSUPPORTED;
|
||||||
}
|
}
|
||||||
|
|
||||||
format = gst_qsv_frame_info_format_to_gst (&request->Info);
|
format = gst_qsv_frame_info_format_to_gst (&request->Info, allocator->is_gbr);
|
||||||
|
|
||||||
if (format == GST_VIDEO_FORMAT_UNKNOWN &&
|
if (format == GST_VIDEO_FORMAT_UNKNOWN &&
|
||||||
request->Info.FourCC != MFX_FOURCC_P8) {
|
request->Info.FourCC != MFX_FOURCC_P8) {
|
||||||
|
|
|
@ -81,6 +81,8 @@ struct _GstQsvDecoderPrivate
|
||||||
|
|
||||||
mfxSession session;
|
mfxSession session;
|
||||||
mfxVideoParam video_param;
|
mfxVideoParam video_param;
|
||||||
|
mfxExtVideoSignalInfo signal_info;
|
||||||
|
mfxExtBuffer *video_param_ext[1];
|
||||||
|
|
||||||
/* holding allocated GstQsvFrame, should be cleared via
|
/* holding allocated GstQsvFrame, should be cleared via
|
||||||
* mfxFrameAllocator::Free() */
|
* mfxFrameAllocator::Free() */
|
||||||
|
@ -888,6 +890,10 @@ gst_qsv_decoder_set_format (GstVideoDecoder * decoder,
|
||||||
|
|
||||||
memset (&priv->video_param, 0, sizeof (mfxVideoParam));
|
memset (&priv->video_param, 0, sizeof (mfxVideoParam));
|
||||||
priv->video_param.mfx.CodecId = klass->codec_id;
|
priv->video_param.mfx.CodecId = klass->codec_id;
|
||||||
|
priv->signal_info.Header.BufferId = MFX_EXTBUFF_VIDEO_SIGNAL_INFO;
|
||||||
|
priv->signal_info.Header.BufferSz = sizeof (mfxExtVideoSignalInfo);
|
||||||
|
priv->video_param_ext[0] = (mfxExtBuffer *) & priv->signal_info;
|
||||||
|
priv->video_param.ExtParam = priv->video_param_ext;
|
||||||
|
|
||||||
/* If upstream is live, we will use single async-depth for low-latency
|
/* If upstream is live, we will use single async-depth for low-latency
|
||||||
* decoding */
|
* decoding */
|
||||||
|
@ -1199,6 +1205,7 @@ gst_qsv_decoder_negotiate (GstVideoDecoder * decoder)
|
||||||
mfxFrameInfo *frame_info = ¶m->mfx.FrameInfo;
|
mfxFrameInfo *frame_info = ¶m->mfx.FrameInfo;
|
||||||
GstVideoFormat format = GST_VIDEO_FORMAT_UNKNOWN;
|
GstVideoFormat format = GST_VIDEO_FORMAT_UNKNOWN;
|
||||||
GstVideoInterlaceMode interlace_mode = GST_VIDEO_INTERLACE_MODE_PROGRESSIVE;
|
GstVideoInterlaceMode interlace_mode = GST_VIDEO_INTERLACE_MODE_PROGRESSIVE;
|
||||||
|
gboolean is_gbr = FALSE;
|
||||||
|
|
||||||
width = coded_width = frame_info->Width;
|
width = coded_width = frame_info->Width;
|
||||||
height = coded_height = frame_info->Height;
|
height = coded_height = frame_info->Height;
|
||||||
|
@ -1208,6 +1215,16 @@ gst_qsv_decoder_negotiate (GstVideoDecoder * decoder)
|
||||||
height = frame_info->CropH;
|
height = frame_info->CropH;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (klass->codec_id == MFX_CODEC_HEVC &&
|
||||||
|
priv->signal_info.ColourDescriptionPresent &&
|
||||||
|
gst_video_color_matrix_from_iso (priv->signal_info.MatrixCoefficients) ==
|
||||||
|
GST_VIDEO_COLOR_MATRIX_RGB) {
|
||||||
|
is_gbr = TRUE;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (priv->allocator)
|
||||||
|
priv->allocator->is_gbr = is_gbr;
|
||||||
|
|
||||||
if (klass->codec_id == MFX_CODEC_JPEG) {
|
if (klass->codec_id == MFX_CODEC_JPEG) {
|
||||||
if (param->mfx.JPEGChromaFormat == MFX_CHROMAFORMAT_YUV422) {
|
if (param->mfx.JPEGChromaFormat == MFX_CHROMAFORMAT_YUV422) {
|
||||||
format = GST_VIDEO_FORMAT_YUY2;
|
format = GST_VIDEO_FORMAT_YUY2;
|
||||||
|
@ -1219,7 +1236,7 @@ gst_qsv_decoder_negotiate (GstVideoDecoder * decoder)
|
||||||
frame_info->ChromaFormat = MFX_CHROMAFORMAT_YUV444;
|
frame_info->ChromaFormat = MFX_CHROMAFORMAT_YUV444;
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
format = gst_qsv_frame_info_format_to_gst (frame_info);
|
format = gst_qsv_frame_info_format_to_gst (frame_info, is_gbr);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (format == GST_VIDEO_FORMAT_UNKNOWN) {
|
if (format == GST_VIDEO_FORMAT_UNKNOWN) {
|
||||||
|
@ -1452,8 +1469,11 @@ gst_qsv_decoder_handle_frame (GstVideoDecoder * decoder,
|
||||||
|
|
||||||
new_sequence:
|
new_sequence:
|
||||||
if (!priv->decoder) {
|
if (!priv->decoder) {
|
||||||
|
if (klass->codec_id == MFX_CODEC_HEVC)
|
||||||
|
priv->video_param.NumExtParam = 1;
|
||||||
status = MFXVideoDECODE_DecodeHeader (priv->session,
|
status = MFXVideoDECODE_DecodeHeader (priv->session,
|
||||||
&bs, &priv->video_param);
|
&bs, &priv->video_param);
|
||||||
|
priv->video_param.NumExtParam = 0;
|
||||||
|
|
||||||
if (status != MFX_ERR_NONE) {
|
if (status != MFX_ERR_NONE) {
|
||||||
if (status == MFX_ERR_MORE_DATA) {
|
if (status == MFX_ERR_MORE_DATA) {
|
||||||
|
|
|
@ -558,6 +558,7 @@ gst_qsv_h265_dec_register (GstPlugin * plugin, guint rank, guint impl_index,
|
||||||
if (MFXVideoDECODE_Query (session, ¶m, ¶m) == MFX_ERR_NONE) {
|
if (MFXVideoDECODE_Query (session, ¶m, ¶m) == MFX_ERR_NONE) {
|
||||||
supported_profiles.push_back ("main-444");
|
supported_profiles.push_back ("main-444");
|
||||||
supported_formats.push_back ("VUYA");
|
supported_formats.push_back ("VUYA");
|
||||||
|
supported_formats.push_back ("RBGA");
|
||||||
}
|
}
|
||||||
|
|
||||||
/* main-444-10 */
|
/* main-444-10 */
|
||||||
|
@ -566,6 +567,7 @@ gst_qsv_h265_dec_register (GstPlugin * plugin, guint rank, guint impl_index,
|
||||||
if (MFXVideoDECODE_Query (session, ¶m, ¶m) == MFX_ERR_NONE) {
|
if (MFXVideoDECODE_Query (session, ¶m, ¶m) == MFX_ERR_NONE) {
|
||||||
supported_profiles.push_back ("main-444-10");
|
supported_profiles.push_back ("main-444-10");
|
||||||
supported_formats.push_back ("Y410");
|
supported_formats.push_back ("Y410");
|
||||||
|
supported_formats.push_back ("BGR10A2_LE");
|
||||||
}
|
}
|
||||||
|
|
||||||
/* main-444-12 */
|
/* main-444-12 */
|
||||||
|
@ -574,6 +576,7 @@ gst_qsv_h265_dec_register (GstPlugin * plugin, guint rank, guint impl_index,
|
||||||
if (MFXVideoDECODE_Query (session, ¶m, ¶m) == MFX_ERR_NONE) {
|
if (MFXVideoDECODE_Query (session, ¶m, ¶m) == MFX_ERR_NONE) {
|
||||||
supported_profiles.push_back ("main-444-12");
|
supported_profiles.push_back ("main-444-12");
|
||||||
supported_formats.push_back ("Y412_LE");
|
supported_formats.push_back ("Y412_LE");
|
||||||
|
supported_formats.push_back ("BGRA64_LE");
|
||||||
}
|
}
|
||||||
|
|
||||||
/* To cover both landscape and portrait,
|
/* To cover both landscape and portrait,
|
||||||
|
|
|
@ -200,7 +200,7 @@ gst_qsv_status_to_string (mfxStatus status)
|
||||||
}
|
}
|
||||||
|
|
||||||
GstVideoFormat
|
GstVideoFormat
|
||||||
gst_qsv_frame_info_format_to_gst (const mfxFrameInfo * info)
|
gst_qsv_frame_info_format_to_gst (const mfxFrameInfo * info, gboolean is_gbr)
|
||||||
{
|
{
|
||||||
GstVideoFormat format = GST_VIDEO_FORMAT_UNKNOWN;
|
GstVideoFormat format = GST_VIDEO_FORMAT_UNKNOWN;
|
||||||
|
|
||||||
|
@ -228,12 +228,21 @@ gst_qsv_frame_info_format_to_gst (const mfxFrameInfo * info)
|
||||||
break;
|
break;
|
||||||
break;
|
break;
|
||||||
case MFX_FOURCC_AYUV:
|
case MFX_FOURCC_AYUV:
|
||||||
|
if (is_gbr)
|
||||||
|
format = GST_VIDEO_FORMAT_RBGA;
|
||||||
|
else
|
||||||
format = GST_VIDEO_FORMAT_VUYA;
|
format = GST_VIDEO_FORMAT_VUYA;
|
||||||
break;
|
break;
|
||||||
case MFX_FOURCC_Y410:
|
case MFX_FOURCC_Y410:
|
||||||
|
if (is_gbr)
|
||||||
|
format = GST_VIDEO_FORMAT_BGR10A2_LE;
|
||||||
|
else
|
||||||
format = GST_VIDEO_FORMAT_Y410;
|
format = GST_VIDEO_FORMAT_Y410;
|
||||||
break;
|
break;
|
||||||
case MFX_FOURCC_Y416:
|
case MFX_FOURCC_Y416:
|
||||||
|
if (is_gbr)
|
||||||
|
format = GST_VIDEO_FORMAT_BGRA64_LE;
|
||||||
|
else
|
||||||
format = GST_VIDEO_FORMAT_Y412_LE;
|
format = GST_VIDEO_FORMAT_Y412_LE;
|
||||||
break;
|
break;
|
||||||
case MFX_FOURCC_RGB4:
|
case MFX_FOURCC_RGB4:
|
||||||
|
@ -300,6 +309,7 @@ gst_qsv_frame_info_set_format (mfxFrameInfo * info, GstVideoFormat format)
|
||||||
info->Shift = 1;
|
info->Shift = 1;
|
||||||
break;
|
break;
|
||||||
case GST_VIDEO_FORMAT_VUYA:
|
case GST_VIDEO_FORMAT_VUYA:
|
||||||
|
case GST_VIDEO_FORMAT_RBGA:
|
||||||
info->FourCC = MFX_FOURCC_AYUV;
|
info->FourCC = MFX_FOURCC_AYUV;
|
||||||
info->ChromaFormat = MFX_CHROMAFORMAT_YUV444;
|
info->ChromaFormat = MFX_CHROMAFORMAT_YUV444;
|
||||||
info->BitDepthLuma = 8;
|
info->BitDepthLuma = 8;
|
||||||
|
@ -307,6 +317,7 @@ gst_qsv_frame_info_set_format (mfxFrameInfo * info, GstVideoFormat format)
|
||||||
info->Shift = 0;
|
info->Shift = 0;
|
||||||
break;
|
break;
|
||||||
case GST_VIDEO_FORMAT_Y410:
|
case GST_VIDEO_FORMAT_Y410:
|
||||||
|
case GST_VIDEO_FORMAT_BGR10A2_LE:
|
||||||
info->FourCC = MFX_FOURCC_Y410;
|
info->FourCC = MFX_FOURCC_Y410;
|
||||||
info->ChromaFormat = MFX_CHROMAFORMAT_YUV444;
|
info->ChromaFormat = MFX_CHROMAFORMAT_YUV444;
|
||||||
info->BitDepthLuma = 10;
|
info->BitDepthLuma = 10;
|
||||||
|
@ -314,6 +325,7 @@ gst_qsv_frame_info_set_format (mfxFrameInfo * info, GstVideoFormat format)
|
||||||
info->Shift = 0;
|
info->Shift = 0;
|
||||||
break;
|
break;
|
||||||
case GST_VIDEO_FORMAT_Y412_LE:
|
case GST_VIDEO_FORMAT_Y412_LE:
|
||||||
|
case GST_VIDEO_FORMAT_BGRA64_LE:
|
||||||
info->FourCC = MFX_FOURCC_Y416;
|
info->FourCC = MFX_FOURCC_Y416;
|
||||||
info->ChromaFormat = MFX_CHROMAFORMAT_YUV444;
|
info->ChromaFormat = MFX_CHROMAFORMAT_YUV444;
|
||||||
info->BitDepthLuma = 12;
|
info->BitDepthLuma = 12;
|
||||||
|
|
|
@ -76,7 +76,8 @@ static const GstQsvResolution gst_qsv_resolutions[] = {
|
||||||
{7680, 4320}, {8192, 4320}, {15360, 8640}, {16384, 8640}
|
{7680, 4320}, {8192, 4320}, {15360, 8640}, {16384, 8640}
|
||||||
};
|
};
|
||||||
|
|
||||||
GstVideoFormat gst_qsv_frame_info_format_to_gst (const mfxFrameInfo * info);
|
GstVideoFormat gst_qsv_frame_info_format_to_gst (const mfxFrameInfo * info,
|
||||||
|
gboolean is_gbr);
|
||||||
|
|
||||||
gboolean gst_qsv_frame_info_set_format (mfxFrameInfo * info,
|
gboolean gst_qsv_frame_info_set_format (mfxFrameInfo * info,
|
||||||
GstVideoFormat format);
|
GstVideoFormat format);
|
||||||
|
|
Loading…
Reference in a new issue