summaryrefslogtreecommitdiff
path: root/omx/gstomxh264dec.c
diff options
context:
space:
mode:
Diffstat (limited to 'omx/gstomxh264dec.c')
-rw-r--r--omx/gstomxh264dec.c36
1 files changed, 30 insertions, 6 deletions
diff --git a/omx/gstomxh264dec.c b/omx/gstomxh264dec.c
index 9608f65..32b5757 100644
--- a/omx/gstomxh264dec.c
+++ b/omx/gstomxh264dec.c
@@ -50,6 +50,21 @@ enum
G_DEFINE_TYPE_WITH_CODE (GstOMXH264Dec, gst_omx_h264_dec,
GST_TYPE_OMX_VIDEO_DEC, DEBUG_INIT);
+#define MAKE_CAPS(alignment) \
+ "video/x-h264, " \
+ "alignment=(string) " alignment ", " \
+ "stream-format=(string) byte-stream, " \
+ "width=(int) [1,MAX], height=(int) [1,MAX]"
+
+/* The Zynq supports decoding subframes, though we want "au" to be the
+ * default, so we keep it prepended. This is the only way that it works with
+ * rtph264depay. */
+#ifdef USE_OMX_TARGET_ZYNQ_USCALE_PLUS
+#define SINK_CAPS MAKE_CAPS ("au") ";" MAKE_CAPS ("nal")
+#else
+#define SINK_CAPS MAKE_CAPS ("au")
+#endif
+
static void
gst_omx_h264_dec_class_init (GstOMXH264DecClass * klass)
{
@@ -60,10 +75,7 @@ gst_omx_h264_dec_class_init (GstOMXH264DecClass * klass)
GST_DEBUG_FUNCPTR (gst_omx_h264_dec_is_format_change);
videodec_class->set_format = GST_DEBUG_FUNCPTR (gst_omx_h264_dec_set_format);
- videodec_class->cdata.default_sink_template_caps = "video/x-h264, "
- "alignment=(string) au, "
- "stream-format=(string) byte-stream, "
- "width=(int) [1,MAX], " "height=(int) [1,MAX]";
+ videodec_class->cdata.default_sink_template_caps = SINK_CAPS;
gst_element_class_set_static_metadata (element_class,
"OpenMAX H.264 Video Decoder",
@@ -86,7 +98,8 @@ gst_omx_h264_dec_is_format_change (GstOMXVideoDec * dec,
GstCaps *old_caps = NULL;
GstCaps *new_caps = state->caps;
GstStructure *old_structure, *new_structure;
- const gchar *old_profile, *old_level, *new_profile, *new_level;
+ const gchar *old_profile, *old_level, *old_alignment, *new_profile,
+ *new_level, *new_alignment;
if (dec->input_state) {
old_caps = dec->input_state->caps;
@@ -100,11 +113,14 @@ gst_omx_h264_dec_is_format_change (GstOMXVideoDec * dec,
new_structure = gst_caps_get_structure (new_caps, 0);
old_profile = gst_structure_get_string (old_structure, "profile");
old_level = gst_structure_get_string (old_structure, "level");
+ old_alignment = gst_structure_get_string (old_structure, "alignment");
new_profile = gst_structure_get_string (new_structure, "profile");
new_level = gst_structure_get_string (new_structure, "level");
+ new_alignment = gst_structure_get_string (new_structure, "alignment");
if (g_strcmp0 (old_profile, new_profile) != 0
- || g_strcmp0 (old_level, new_level) != 0) {
+ || g_strcmp0 (old_level, new_level) != 0
+ || g_strcmp0 (old_alignment, new_alignment) != 0) {
return TRUE;
}
@@ -176,6 +192,7 @@ gst_omx_h264_dec_set_format (GstOMXVideoDec * dec, GstOMXPort * port,
GstOMXVideoDecClass *klass = GST_OMX_VIDEO_DEC_GET_CLASS (dec);
OMX_PARAM_PORTDEFINITIONTYPE port_def;
OMX_ERRORTYPE err;
+ const GstStructure *s;
gst_omx_port_get_port_definition (port, &port_def);
port_def.format.video.eCompressionFormat = OMX_VIDEO_CodingAVC;
@@ -188,5 +205,12 @@ gst_omx_h264_dec_set_format (GstOMXVideoDec * dec, GstOMXPort * port,
return FALSE;
}
+ /* Enable subframe mode if NAL aligned */
+ s = gst_caps_get_structure (state->caps, 0);
+ if (!g_strcmp0 (gst_structure_get_string (s, "alignment"), "nal")
+ && gst_omx_port_set_subframe (dec->dec_in_port, TRUE)) {
+ gst_video_decoder_set_subframe_mode (GST_VIDEO_DECODER (dec), TRUE);
+ }
+
return TRUE;
}