mirror of
https://gitlab.freedesktop.org/gstreamer/gstreamer.git
synced 2024-12-18 22:36:33 +00:00
mpegvideoparse: Export profile and level in caps
This exports profile and level in caps for MPEG 2 streams. https://bugzilla.gnome.org/show_bug.cgi?id=616078
This commit is contained in:
parent
49a85930c5
commit
bf586d7966
3 changed files with 60 additions and 2 deletions
|
@ -498,7 +498,6 @@ mpeg_util_parse_extension_packet (MPEGSeqHdr * hdr, guint8 * data, guint8 * end)
|
|||
case MPEG_PACKET_EXT_SEQUENCE:
|
||||
{
|
||||
/* Parse a Sequence Extension */
|
||||
guint8 profile_level;
|
||||
gboolean low_delay;
|
||||
guint8 chroma_format;
|
||||
guint8 horiz_size_ext, vert_size_ext;
|
||||
|
@ -508,7 +507,8 @@ mpeg_util_parse_extension_packet (MPEGSeqHdr * hdr, guint8 * data, guint8 * end)
|
|||
/* need at least 10 bytes, minus 4 for the start code 000001b5 */
|
||||
return FALSE;
|
||||
|
||||
profile_level = ((data[0] << 4) & 0xf0) | ((data[1]) >> 4);
|
||||
hdr->profile = data[0] & 0x0f; /* profile (0:2) + escape bit (3) */
|
||||
hdr->level = (data[1] >> 4) & 0x0f;
|
||||
hdr->progressive = data[1] & 0x08;
|
||||
chroma_format = (data[1] >> 2) & 0x03;
|
||||
horiz_size_ext = ((data[1] << 1) & 0x02) | ((data[2] >> 7) & 0x01);
|
||||
|
|
|
@ -78,6 +78,8 @@ struct MPEGSeqHdr
|
|||
gint fps_n, fps_d;
|
||||
/* Bitrate */
|
||||
guint bitrate;
|
||||
/* Profile and level */
|
||||
guint profile, level;
|
||||
|
||||
gboolean progressive;
|
||||
};
|
||||
|
|
|
@ -250,6 +250,17 @@ mpegvideoparse_handle_sequence (MpegVideoParse * mpegvideoparse,
|
|||
if (memcmp (&mpegvideoparse->seq_hdr, &new_hdr, sizeof (MPEGSeqHdr)) != 0) {
|
||||
GstCaps *caps;
|
||||
GstBuffer *seq_buf;
|
||||
/*
|
||||
* Profile indication - 1 => High, 2 => Spatially Scalable,
|
||||
* 3 => SNR Scalable, 4 => Main, 5 => Simple
|
||||
* 4:2:2 and Multi-view have profile = 0, with the escape bit set to 1
|
||||
*/
|
||||
const gchar *profiles[] = { "HP", "Spatial", "SNR", "MP", "SP" };
|
||||
/*
|
||||
* Level indication - 4 => High, 6 => High-1440, 8 => Main, 10 => Low,
|
||||
* except in the case of profile = 0
|
||||
*/
|
||||
const gchar *levels[] = { "HL", "H-14", "ML", "LL" };
|
||||
|
||||
/* Store the entire sequence header + sequence header extension
|
||||
for output as codec_data */
|
||||
|
@ -268,6 +279,51 @@ mpegvideoparse_handle_sequence (MpegVideoParse * mpegvideoparse,
|
|||
"interlaced", G_TYPE_BOOLEAN, !new_hdr.progressive,
|
||||
"codec_data", GST_TYPE_BUFFER, seq_buf, NULL);
|
||||
|
||||
if (new_hdr.mpeg_version == 2) {
|
||||
const gchar *profile = NULL, *level = NULL;
|
||||
|
||||
if (new_hdr.profile > 0 && new_hdr.profile < 6)
|
||||
profile = profiles[new_hdr.profile - 1];
|
||||
|
||||
if ((new_hdr.level > 3) && (new_hdr.level < 11) &&
|
||||
(new_hdr.level % 2 == 0))
|
||||
level = levels[(new_hdr.level >> 1) - 1];
|
||||
|
||||
if (new_hdr.profile == 8) {
|
||||
/* Non-hierarchical profile */
|
||||
switch (new_hdr.level) {
|
||||
case 2:
|
||||
level = levels[0];
|
||||
case 5:
|
||||
level = levels[2];
|
||||
profile = "422P";
|
||||
break;
|
||||
case 10:
|
||||
level = levels[0];
|
||||
case 11:
|
||||
level = levels[1];
|
||||
case 13:
|
||||
level = levels[2];
|
||||
case 14:
|
||||
level = levels[3];
|
||||
profile = "MVP";
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (profile)
|
||||
gst_caps_set_simple (caps, "profile", G_TYPE_STRING, profile, NULL);
|
||||
else
|
||||
GST_DEBUG ("Invalid profile - %u", new_hdr.profile);
|
||||
|
||||
if (level)
|
||||
gst_caps_set_simple (caps, "level", G_TYPE_STRING, level, NULL);
|
||||
else
|
||||
GST_DEBUG ("Invalid level - %u", new_hdr.level);
|
||||
}
|
||||
|
||||
GST_DEBUG ("New mpegvideoparse caps: %" GST_PTR_FORMAT, caps);
|
||||
if (!gst_pad_set_caps (mpegvideoparse->srcpad, caps)) {
|
||||
gst_caps_unref (caps);
|
||||
|
|
Loading…
Reference in a new issue