From 240b0ac9f6bbf6439ddea24ca30702de255de97f Mon Sep 17 00:00:00 2001 From: Havard Graff Date: Wed, 23 Sep 2015 13:50:52 +0200 Subject: [PATCH] flvdemux: output speex vorbiscomment as a GstTagList This is what speexdec expects. https://bugzilla.gnome.org/show_bug.cgi?id=755478 --- gst/flv/Makefile.am | 2 +- gst/flv/gstflvdemux.c | 7 +- tests/check/Makefile.am | 2 + tests/check/elements/flvdemux.c | 154 ++++++++++++++++++++++++++++++++ 4 files changed, 163 insertions(+), 2 deletions(-) diff --git a/gst/flv/Makefile.am b/gst/flv/Makefile.am index b396743805..b205999a09 100644 --- a/gst/flv/Makefile.am +++ b/gst/flv/Makefile.am @@ -2,7 +2,7 @@ plugin_LTLIBRARIES = libgstflv.la libgstflv_la_CFLAGS = $(GST_PLUGINS_BASE_CFLAGS) $(GST_BASE_CFLAGS) $(GST_CFLAGS) libgstflv_la_LIBADD = -lgstpbutils-@GST_API_VERSION@ -lgstaudio-@GST_API_VERSION@ \ - -lgstvideo-@GST_API_VERSION@ \ + -lgstvideo-@GST_API_VERSION@ -lgsttag-$(GST_API_VERSION) \ $(GST_PLUGINS_BASE_LIBS) $(GST_BASE_LIBS) $(GST_LIBS) libgstflv_la_LDFLAGS = ${GST_PLUGIN_LDFLAGS} libgstflv_la_SOURCES = gstflvdemux.c gstflvmux.c diff --git a/gst/flv/gstflvdemux.c b/gst/flv/gstflvdemux.c index 95263f13b3..8d523f3078 100644 --- a/gst/flv/gstflvdemux.c +++ b/gst/flv/gstflvdemux.c @@ -44,6 +44,7 @@ #include #include #include +#include /* FIXME: don't rely on own GstIndex */ #include "gstindex.c" @@ -749,6 +750,7 @@ gst_flv_demux_audio_negotiate (GstFlvDemux * demux, guint32 codec_tag, GstByteWriter w; GstStructure *structure; GstBuffer *buf; + GstTagList *tags; caps = gst_caps_new_empty_simple ("audio/x-speex"); structure = gst_caps_get_structure (caps, 0); @@ -785,7 +787,10 @@ gst_flv_demux_audio_negotiate (GstFlvDemux * demux, guint32 codec_tag, /* comment part */ g_value_init (&value, GST_TYPE_BUFFER); - buf = gst_buffer_new_wrapped (g_memdup ("No comments", 12), 12); + tags = gst_tag_list_new_empty (); + buf = gst_tag_list_to_vorbiscomment_buffer (tags, NULL, + 0, "No comments"); + gst_tag_list_unref (tags); g_value_take_boxed (&value, buf); gst_value_array_append_value (&streamheader, &value); g_value_unset (&value); diff --git a/tests/check/Makefile.am b/tests/check/Makefile.am index 097edf2475..613911e82f 100644 --- a/tests/check/Makefile.am +++ b/tests/check/Makefile.am @@ -424,6 +424,8 @@ elements_amrparse_LDADD = libparser.la $(LDADD) elements_flacparse_LDADD = libparser.la $(LDADD) +elements_flvdemux_LDADD = -lgsttag-$(GST_API_VERSION) $(LDADD) + elements_mpegaudioparse_LDADD = libparser.la $(LDADD) elements_aspectratiocrop_LDADD = $(LDADD) diff --git a/tests/check/elements/flvdemux.c b/tests/check/elements/flvdemux.c index c9d156dda7..2d8d1a7c69 100644 --- a/tests/check/elements/flvdemux.c +++ b/tests/check/elements/flvdemux.c @@ -19,8 +19,10 @@ */ #include +#include #include +#include static void pad_added_cb (GstElement * flvdemux, GstPad * pad, GstBin * pipeline) @@ -166,6 +168,156 @@ GST_START_TEST (test_reuse_push) GST_END_TEST; +static GstBuffer * +create_buffer (guint8 * data, gsize size) +{ + GstBuffer * buf = gst_buffer_new_wrapped_full (GST_MEMORY_FLAG_READONLY, + data, size, 0, size, NULL, NULL); + GST_BUFFER_PTS (buf) = GST_CLOCK_TIME_NONE; + GST_BUFFER_DTS (buf) = GST_CLOCK_TIME_NONE; + GST_BUFFER_DURATION (buf) = GST_CLOCK_TIME_NONE; + GST_BUFFER_OFFSET (buf) = GST_BUFFER_OFFSET_NONE; + GST_BUFFER_OFFSET_END (buf) = GST_BUFFER_OFFSET_NONE; + return buf; +} + +static void +flvdemux_pad_added (GstElement * flvdemux, GstPad * srcpad, GstHarness * h) +{ + (void)flvdemux; + gst_harness_add_element_src_pad (h, srcpad); +} + +GST_START_TEST (test_speex) +{ + guint8 flv_header0[] = { + 0x46, 0x4c, 0x56, 0x01, 0x04, 0x00, 0x00, 0x00, + 0x09, 0x00, 0x00, 0x00, 0x00 + }; + + guint8 flv_header1[] = { + 0x12, 0x00, 0x00, 0x7c, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x02, 0x00, 0x0a, 0x6f, 0x6e, + 0x4d, 0x65, 0x74, 0x61, 0x44, 0x61, 0x74, 0x61, + 0x08, 0x00, 0x00, 0x00, 0x04, 0x00, 0x0c, 0x61, + 0x75, 0x64, 0x69, 0x6f, 0x63, 0x6f, 0x64, 0x65, + 0x63, 0x69, 0x64, 0x00, 0x40, 0x26, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x0f, 0x6d, 0x65, + 0x74, 0x61, 0x64, 0x61, 0x74, 0x61, 0x63, 0x72, + 0x65, 0x61, 0x74, 0x6f, 0x72, 0x02, 0x00, 0x13, + 0x47, 0x53, 0x74, 0x72, 0x65, 0x61, 0x6d, 0x65, + 0x72, 0x20, 0x46, 0x4c, 0x56, 0x20, 0x6d, 0x75, + 0x78, 0x65, 0x72, 0x00, 0x0c, 0x63, 0x72, 0x65, + 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x64, 0x61, 0x74, + 0x65, 0x02, 0x00, 0x18, 0x57, 0x65, 0x64, 0x20, + 0x53, 0x65, 0x70, 0x20, 0x32, 0x33, 0x20, 0x31, + 0x30, 0x3a, 0x34, 0x39, 0x3a, 0x35, 0x36, 0x20, + 0x32, 0x30, 0x31, 0x35, 0x00, 0x00, 0x09, 0x00, + 0x00, 0x00, 0x87, + }; + + guint8 speex_header0[] = { + 0x08, 0x00, 0x00, 0x51, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0xb2, 0x53, 0x70, 0x65, 0x65, + 0x78, 0x20, 0x20, 0x20, 0x31, 0x2e, 0x32, 0x72, + 0x63, 0x31, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x01, 0x00, 0x00, 0x00, 0x50, 0x00, 0x00, 0x00, + 0x80, 0x3e, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, + 0x04, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, + 0xff, 0xff, 0xff, 0xff, 0x40, 0x01, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x5c, + }; + + guint8 speex_header1[] = { + 0x08, 0x00, 0x00, 0x29, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0xb2, 0x1f, 0x00, 0x00, 0x00, + 0x45, 0x6e, 0x63, 0x6f, 0x64, 0x65, 0x64, 0x20, + 0x77, 0x69, 0x74, 0x68, 0x20, 0x47, 0x53, 0x74, + 0x72, 0x65, 0x61, 0x6d, 0x65, 0x72, 0x20, 0x53, + 0x70, 0x65, 0x65, 0x78, 0x65, 0x6e, 0x63, 0x00, + 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x34, + }; + + guint8 buffer[] = { + 0x08, 0x00, 0x00, 0x47, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0xb2, 0x36, 0x9d, 0x1b, 0x9a, + 0x20, 0x00, 0x01, 0x68, 0xe8, 0xe8, 0xe8, 0xe8, + 0xe8, 0xe8, 0xe8, 0x84, 0x00, 0xb4, 0x74, 0x74, + 0x74, 0x74, 0x74, 0x74, 0x74, 0x42, 0x00, 0x5a, + 0x3a, 0x3a, 0x3a, 0x3a, 0x3a, 0x3a, 0x3a, 0x21, + 0x00, 0x2d, 0x1d, 0x1d, 0x1d, 0x1d, 0x1d, 0x1d, + 0x1d, 0x1b, 0x3b, 0x60, 0xab, 0xab, 0xab, 0xab, + 0xab, 0x0a, 0xba, 0xba, 0xba, 0xba, 0xb0, 0xab, + 0xab, 0xab, 0xab, 0xab, 0x0a, 0xba, 0xba, 0xba, + 0xba, 0xb7, 0x00, 0x00, 0x00, 0x52, + }; + + GstHarness * h = gst_harness_new_with_padnames ("flvdemux", "sink", NULL); + gst_harness_set_src_caps_str (h, "video/x-flv"); + + g_signal_connect (h->element, "pad-added", + G_CALLBACK (flvdemux_pad_added), h); + + gst_harness_push (h, create_buffer (flv_header0, sizeof (flv_header0))); + gst_harness_push (h, create_buffer (flv_header1, sizeof (flv_header1))); + gst_harness_push (h, create_buffer (speex_header0, sizeof (speex_header0))); + gst_harness_push (h, create_buffer (speex_header1, sizeof (speex_header1))); + gst_harness_push (h, create_buffer (buffer, sizeof (buffer))); + + { + GstCaps * caps; + const GstStructure * s; + const GValue *streamheader; + const GValue *header; + const GValue *vorbiscomment; + GstBuffer *buf; + GstTagList *list; + gint rate; + gint channels; + + caps = gst_pad_get_current_caps (h->sinkpad); + s = gst_caps_get_structure (caps, 0); + + fail_unless (gst_structure_has_name (s, "audio/x-speex")); + + streamheader = gst_structure_get_value (s, "streamheader"); + fail_unless (streamheader != NULL); + fail_unless (G_VALUE_HOLDS (streamheader, GST_TYPE_ARRAY)); + fail_unless_equals_int (2, gst_value_array_get_size (streamheader)); + + header = gst_value_array_get_value (streamheader, 0); + fail_unless (header != NULL); + fail_unless (G_VALUE_HOLDS (header, GST_TYPE_BUFFER)); + buf = gst_value_get_buffer (header); + + vorbiscomment = gst_value_array_get_value (streamheader, 1); + fail_unless (header != NULL); + fail_unless (G_VALUE_HOLDS (header, GST_TYPE_BUFFER)); + buf = gst_value_get_buffer (vorbiscomment); + list = gst_tag_list_from_vorbiscomment_buffer (buf, NULL, 0, NULL); + fail_unless (list != NULL); + gst_tag_list_unref (list); + + gst_structure_get_int (s, "rate", &rate); + fail_unless_equals_int (16000, rate); + + gst_structure_get_int (s, "channels", &channels); + fail_unless_equals_int (1, channels); + + gst_caps_unref (caps); + } + + /* we should have gotten 2x speex-headers, and one encoded buffer */ + fail_unless_equals_int (3, gst_harness_buffers_in_queue (h)); + + gst_harness_teardown (h); +} + +GST_END_TEST; + static Suite * flvdemux_suite (void) { @@ -176,6 +328,8 @@ flvdemux_suite (void) tcase_add_test (tc_chain, test_reuse_push); tcase_add_test (tc_chain, test_reuse_pull); + tcase_add_test (tc_chain, test_speex); + return s; }