summaryrefslogtreecommitdiffstats
path: root/tests/check
diff options
context:
space:
mode:
Diffstat (limited to 'tests/check')
-rw-r--r--tests/check/Makefile.am33
-rw-r--r--tests/check/elements/.gitignore2
-rw-r--r--tests/check/elements/camerabin.c236
-rw-r--r--tests/check/elements/rtpbin_buffer_list.c331
-rw-r--r--tests/check/elements/shapewipe.c1
-rw-r--r--tests/check/pipelines/metadata.c6
6 files changed, 502 insertions, 107 deletions
diff --git a/tests/check/Makefile.am b/tests/check/Makefile.am
index cbc228e2..bf4f07ce 100644
--- a/tests/check/Makefile.am
+++ b/tests/check/Makefile.am
@@ -63,17 +63,9 @@ else
check_timidity=
endif
-if USE_X264
-check_x264enc=elements/x264enc
-else
-check_x264enc=
-endif
-
-
VALGRIND_TO_FIX = \
elements/mpeg2enc \
- elements/mplex \
- elements/x264enc
+ elements/mplex
# valgrind testing
VALGRIND_TESTS_DISABLE = \
@@ -86,13 +78,13 @@ check_PROGRAMS = \
$(check_neon) \
$(check_ofa) \
$(check_timidity) \
- $(check_x264enc) \
elements/aacparse \
elements/amrparse \
elements/camerabin \
elements/legacyresample \
elements/qtmux \
elements/rtpbin \
+ elements/rtpbin_buffer_list \
elements/selector \
elements/shapewipe \
elements/mxfdemux \
@@ -104,15 +96,26 @@ noinst_HEADERS = elements/mxfdemux.h elements/amrparse_data.h elements/aacparse_
TESTS = $(check_PROGRAMS)
-AM_CFLAGS = $(GST_OBJ_CFLAGS) $(GST_CHECK_CFLAGS) $(CHECK_CFLAGS) $(GST_OPTION_CFLAGS)
+AM_CFLAGS = $(GST_OBJ_CFLAGS) $(GST_CHECK_CFLAGS) $(CHECK_CFLAGS) $(GST_OPTION_CFLAGS)
LDADD = $(GST_OBJ_LIBS) $(GST_CHECK_LIBS) $(CHECK_LIBS)
-elements_camerabin_CFLAGS = $(GST_CFLAGS) $(GST_BASE_CFLAGS) $(GST_CHECK_CFLAGS)
-elements_camerabin_LDADD = $(GST_LIBS) $(GST_BASE_LIBS) $(GST_CHECK_LIBS) \
- -lgstinterfaces-@GST_MAJORMINOR@ \
- $(top_builddir)/gst-libs/gst/interfaces/libgstphotography-@GST_MAJORMINOR@.la
+elements_camerabin_CFLAGS = \
+ -I$(top_builddir)/gst-libs \
+ $(GST_CFLAGS) $(GST_BASE_CFLAGS) $(GST_CHECK_CFLAGS) \
+ -DGST_USE_UNSTABLE_API
+elements_camerabin_LDADD = \
+ $(top_builddir)/gst-libs/gst/interfaces/libgstphotography-@GST_MAJORMINOR@.la \
+ $(GST_LIBS) $(GST_BASE_LIBS) $(GST_CHECK_LIBS) \
+ -lgstinterfaces-@GST_MAJORMINOR@
elements_camerabin_SOURCES = elements/camerabin.c
+elements_rtpbin_buffer_list_CFLAGS = $(GST_PLUGINS_BASE_CFLAGS) $(GST_CFLAGS) \
+ $(ERROR_CFLAGS) $(GST_CHECK_CFLAGS)
+elements_rtpbin_buffer_list_LDADD = $(GST_PLUGINS_BASE_LIBS) \
+ -lgstnetbuffer-@GST_MAJORMINOR@ -lgstrtp-@GST_MAJORMINOR@ \
+ $(GST_BASE_LIBS) $(GST_LIBS_LIBS) $(GST_CHECK_LIBS)
+elements_rtpbin_buffer_list_SOURCES = elements/rtpbin_buffer_list.c
+
elements_timidity_CFLAGS = $(GST_BASE_CFLAGS) $(AM_CFLAGS)
elements_timidity_LDADD = $(GST_BASE_LIBS) $(LDADD)
diff --git a/tests/check/elements/.gitignore b/tests/check/elements/.gitignore
index 091fb4e5..5f268d3b 100644
--- a/tests/check/elements/.gitignore
+++ b/tests/check/elements/.gitignore
@@ -20,11 +20,11 @@ rglimiter
rgvolume
rtpbin
selector
+shapewipe
spectrum
timidity
videocrop
wavpackdec
wavpackenc
wavpackparse
-x264enc
y4menc
diff --git a/tests/check/elements/camerabin.c b/tests/check/elements/camerabin.c
index 7c6187d2..795fb4f0 100644
--- a/tests/check/elements/camerabin.c
+++ b/tests/check/elements/camerabin.c
@@ -27,10 +27,7 @@
#include <unistd.h>
#include <gst/gst.h>
#include <gst/check/gstcheck.h>
-
-#ifdef HAVE_GST_PHOTO_IFACE_H
#include <gst/interfaces/photography.h>
-#endif
#define SINGLE_IMAGE_FILENAME "image.cap"
#define BURST_IMAGE_FILENAME "burst_image.cap"
@@ -40,13 +37,11 @@
#define MAX_BURST_IMAGES 10
#define PHOTO_SETTING_DELAY_US 0
-static gboolean continuous = FALSE;
-static guint captured_images = 0;
-
static GstElement *camera;
static GCond *cam_cond;
static GMutex *cam_mutex;
-
+static GMainLoop *main_loop;
+static guint cycle_count = 0;
/* helper function for filenames */
static const gchar *
@@ -57,10 +52,12 @@ make_test_file_name (const gchar * base_name)
g_snprintf (file_name, 999, "%s" G_DIR_SEPARATOR_S "%s",
g_get_tmp_dir (), base_name);
- GST_INFO ("capturing to: %s", file_name);
+ GST_INFO ("capturing to: %s (cycle_count=%d)", file_name, cycle_count);
return file_name;
}
+/* burst capture is not supported in camerabin for the moment */
+#ifdef ENABLE_BURST_CAPTURE
static const gchar *
make_test_seq_file_name (const gchar * base_name)
{
@@ -72,30 +69,50 @@ make_test_seq_file_name (const gchar * base_name)
GST_INFO ("capturing to: %s", file_name);
return file_name;
}
-
+#endif
/* signal handlers */
static gboolean
-capture_done (GstElement * elem, const gchar * filename, gpointer user_data)
+handle_image_captured_cb (gpointer data)
{
- captured_images++;
-
- if (captured_images >= MAX_BURST_IMAGES) {
- /* release the shutter button */
- GST_DEBUG ("signal for img-done");
- g_mutex_lock (cam_mutex);
- g_cond_signal (cam_cond);
- g_mutex_unlock (cam_mutex);
- continuous = FALSE;
- }
+ GMainLoop *loop = (GMainLoop *) data;
+
+ GST_DEBUG ("handle_image_captured_cb, cycle: %d", cycle_count);
+ if (cycle_count == 0) {
+ g_main_loop_quit (loop);
+ } else {
+ /* Set video recording mode */
+ g_object_set (camera, "mode", 1,
+ "filename", make_test_file_name (CYCLE_VIDEO_FILENAME), NULL);
+ /* Record video */
+ g_signal_emit_by_name (camera, "user-start", NULL);
+ g_usleep (G_USEC_PER_SEC);
+ g_signal_emit_by_name (camera, "user-stop", NULL);
+ GST_DEBUG ("video captured");
- if (continuous) {
- /* Must set filename for new picture */
- g_object_set (G_OBJECT (elem), "filename",
- make_test_seq_file_name (BURST_IMAGE_FILENAME), NULL);
+ /* Set still image mode */
+ g_object_set (camera, "mode", 0,
+ "filename", make_test_file_name (CYCLE_IMAGE_FILENAME), NULL);
+ /* Take a picture */
+ g_signal_emit_by_name (camera, "user-start", NULL);
+
+ cycle_count--;
+ GST_DEBUG ("next cycle");
}
+ GST_DEBUG ("handle_image_captured_cb done");
+ return FALSE;
+}
- return continuous;
+static gboolean
+capture_done (GstElement * elem, const gchar * filename, gpointer user_data)
+{
+ GMainLoop *loop = (GMainLoop *) user_data;
+
+ g_idle_add ((GSourceFunc) handle_image_captured_cb, loop);
+
+ GST_DEBUG ("image saved");
+
+ return FALSE;
}
/* configuration */
@@ -103,17 +120,72 @@ capture_done (GstElement * elem, const gchar * filename, gpointer user_data)
static void
setup_camerabin_elements (GstElement * camera)
{
- GstElement *vfsink, *audiosrc, *videosrc;
+ GstElement *vfsink, *audiosrc, *videosrc, *audioenc, *videoenc, *imageenc,
+ *videomux;
/* Use fakesink for view finder */
vfsink = gst_element_factory_make ("fakesink", NULL);
+ g_object_set (vfsink, "sync", TRUE, NULL);
audiosrc = gst_element_factory_make ("audiotestsrc", NULL);
g_object_set (audiosrc, "is-live", TRUE, NULL);
videosrc = gst_element_factory_make ("videotestsrc", NULL);
g_object_set (videosrc, "is-live", TRUE, NULL);
+ audioenc = gst_element_factory_make ("vorbisenc", NULL);
+ videoenc = gst_element_factory_make ("theoraenc", NULL);
+ videomux = gst_element_factory_make ("oggmux", NULL);
+ imageenc = gst_element_factory_make ("jpegenc", NULL);
+
+ if (vfsink && audiosrc && videosrc && audioenc && videoenc && videomux
+ && imageenc) {
+ g_object_set (camera, "vfsink", vfsink, "audiosrc", audiosrc, "videosrc",
+ videosrc, "audioenc", audioenc, "videoenc", videoenc, "imageenc",
+ imageenc, "videomux", videomux, NULL);
+ } else {
+ GST_WARNING ("error setting up test plugins");
+ }
+}
+
+static gboolean
+capture_bus_cb (GstBus * bus, GstMessage * message, gpointer data)
+{
+ GMainLoop *loop = (GMainLoop *) data;
+ const GstStructure *st;
- g_object_set (camera, "vfsink", vfsink, "audiosrc", audiosrc,
- "videosrc", videosrc, NULL);
+ switch (GST_MESSAGE_TYPE (message)) {
+ case GST_MESSAGE_ERROR:{
+ GError *err = NULL;
+ gchar *debug = NULL;
+
+ gst_message_parse_error (message, &err, &debug);
+ GST_WARNING ("ERROR: %s [%s]", err->message, debug);
+ g_error_free (err);
+ g_free (debug);
+ fail_if (TRUE, "error while capturing");
+ g_main_loop_quit (loop);
+ break;
+ }
+ case GST_MESSAGE_WARNING:{
+ GError *err = NULL;
+ gchar *debug = NULL;
+
+ gst_message_parse_warning (message, &err, &debug);
+ GST_WARNING ("WARNING: %s [%s]", err->message, debug);
+ g_error_free (err);
+ g_free (debug);
+ break;
+ }
+ case GST_MESSAGE_EOS:
+ GST_DEBUG ("eos");
+ g_main_loop_quit (loop);
+ break;
+ default:
+ st = gst_message_get_structure (message);
+ if (st && gst_structure_has_name (st, "image-captured")) {
+ GST_INFO ("image-captured");
+ }
+ break;
+ }
+ return TRUE;
}
static void
@@ -121,6 +193,12 @@ setup (void)
{
GstTagSetter *setter;
gchar *desc_str;
+ GstCaps *filter_caps;
+ GstBus *bus;
+
+ GST_INFO ("init");
+
+ main_loop = g_main_loop_new (NULL, TRUE);
cam_cond = g_cond_new ();
cam_mutex = g_mutex_new ();
@@ -129,9 +207,19 @@ setup (void)
setup_camerabin_elements (camera);
- g_signal_connect (camera, "img-done", G_CALLBACK (capture_done), NULL);
+ g_signal_connect (camera, "img-done", G_CALLBACK (capture_done), main_loop);
+
+ bus = gst_pipeline_get_bus (GST_PIPELINE (camera));
+ gst_bus_add_watch (bus, (GstBusFunc) capture_bus_cb, main_loop);
+ gst_object_unref (bus);
+
+ filter_caps = gst_caps_from_string ("video/x-raw-yuv,format=(fourcc)I420");
+ g_object_set (G_OBJECT (camera), "filter-caps", filter_caps, NULL);
+ gst_caps_unref (filter_caps);
- captured_images = 0;
+ /* force a low framerate here to not timeout the tests because of the
+ * encoders */
+ g_signal_emit_by_name (camera, "user-res-fps", 320, 240, 5, 1, NULL);
/* Set some default tags */
setter = GST_TAG_SETTER (camera);
@@ -141,12 +229,14 @@ setup (void)
GST_TAG_DESCRIPTION, desc_str, NULL);
g_free (desc_str);
- if (gst_element_set_state (GST_ELEMENT (camera), GST_STATE_PLAYING) !=
- GST_STATE_CHANGE_SUCCESS) {
+ if (gst_element_set_state (GST_ELEMENT (camera), GST_STATE_PLAYING) ==
+ GST_STATE_CHANGE_FAILURE) {
+ GST_WARNING ("setting camerabin to PLAYING failed");
gst_element_set_state (GST_ELEMENT (camera), GST_STATE_NULL);
gst_object_unref (camera);
camera = NULL;
}
+ GST_INFO ("init finished");
}
static void
@@ -156,6 +246,8 @@ teardown (void)
g_cond_free (cam_cond);
if (camera)
gst_check_teardown_element (camera);
+
+ GST_INFO ("done");
}
static void
@@ -280,13 +372,13 @@ static gboolean
check_file_validity (const gchar * filename)
{
GstBus *bus;
- GMainLoop *loop = g_main_loop_new (NULL, TRUE);
+ GMainLoop *loop = g_main_loop_new (NULL, FALSE);
GstElement *playbin = gst_element_factory_make ("playbin2", NULL);
GstElement *fakevideo = gst_element_factory_make ("fakesink", NULL);
GstElement *fakeaudio = gst_element_factory_make ("fakesink", NULL);
gchar *uri = g_strconcat ("file://", make_test_file_name (filename), NULL);
- GST_DEBUG ("setting uri: %s", uri);
+ GST_DEBUG ("checking uri: %s", uri);
g_object_set (G_OBJECT (playbin), "uri", uri, "video-sink", fakevideo,
"audio-sink", fakeaudio, NULL);
@@ -294,7 +386,6 @@ check_file_validity (const gchar * filename)
gst_bus_add_watch (bus, (GstBusFunc) validity_bus_cb, loop);
gst_element_set_state (playbin, GST_STATE_PLAYING);
-
g_main_loop_run (loop);
gst_element_set_state (playbin, GST_STATE_NULL);
@@ -314,39 +405,14 @@ GST_START_TEST (test_single_image_capture)
g_object_set (camera, "mode", 0,
"filename", make_test_file_name (SINGLE_IMAGE_FILENAME), NULL);
- continuous = FALSE;
-
/* Test photography iface settings */
gst_element_get_state (GST_ELEMENT (camera), NULL, NULL, (2 * GST_SECOND));
test_photography_settings (camera);
- g_signal_emit_by_name (camera, "user-start", 0);
- g_signal_emit_by_name (camera, "user-stop", 0);
-}
-
-GST_END_TEST;
-
-GST_START_TEST (test_burst_image_capture)
-{
- if (!camera)
- return;
-
- /* set still image mode */
- g_object_set (camera, "mode", 0,
- "filename", make_test_seq_file_name (BURST_IMAGE_FILENAME), NULL);
-
- /* set burst mode */
- continuous = TRUE;
-
- g_signal_emit_by_name (camera, "user-start", 0);
-
- GST_DEBUG ("waiting for img-done");
- g_mutex_lock (cam_mutex);
- g_cond_wait (cam_cond, cam_mutex);
- g_mutex_unlock (cam_mutex);
- GST_DEBUG ("received img-done");
+ GST_INFO ("starting capture");
+ g_signal_emit_by_name (camera, "user-start", NULL);
- g_signal_emit_by_name (camera, "user-stop", 0);
+ g_main_loop_run (main_loop);
}
GST_END_TEST;
@@ -360,58 +426,47 @@ GST_START_TEST (test_video_recording)
g_object_set (camera, "mode", 1,
"filename", make_test_file_name (VIDEO_FILENAME), NULL);
- g_signal_emit_by_name (camera, "user-start", 0);
+ GST_INFO ("starting capture");
+ g_signal_emit_by_name (camera, "user-start", NULL);
/* Record for one seconds */
g_usleep (G_USEC_PER_SEC);
- g_signal_emit_by_name (camera, "user-stop", 0);
+ g_signal_emit_by_name (camera, "user-stop", NULL);
}
GST_END_TEST;
GST_START_TEST (test_image_video_cycle)
{
- guint i;
-
if (!camera)
return;
- continuous = FALSE;
-
- for (i = 0; i < 2; i++) {
- /* Set still image mode */
- g_object_set (camera, "mode", 0,
- "filename", make_test_file_name (CYCLE_IMAGE_FILENAME), NULL);
+ cycle_count = 2;
- /* Take a picture */
- g_signal_emit_by_name (camera, "user-start", 0);
- g_signal_emit_by_name (camera, "user-stop", 0);
- GST_DEBUG ("image captured");
+ /* set still image mode */
+ g_object_set (camera, "mode", 0,
+ "filename", make_test_file_name (CYCLE_IMAGE_FILENAME), NULL);
- /* Set video recording mode */
- g_object_set (camera, "mode", 1,
- "filename", make_test_file_name (CYCLE_VIDEO_FILENAME), NULL);
+ GST_INFO ("starting capture");
+ g_signal_emit_by_name (camera, "user-start", NULL);
- /* Record video */
- g_signal_emit_by_name (camera, "user-start", 0);
- g_usleep (G_USEC_PER_SEC);
- g_signal_emit_by_name (camera, "user-stop", 0);
- GST_DEBUG ("video captured");
- }
+ g_main_loop_run (main_loop);
}
GST_END_TEST;
GST_START_TEST (validate_captured_image_files)
{
- GString *filename;
- gint i;
-
if (!camera)
return;
/* validate single image */
check_file_validity (SINGLE_IMAGE_FILENAME);
+/* burst capture is not supported in camerabin for the moment */
+#ifdef ENABLE_BURST_CAPTURE
+ GString *filename;
+ gint i;
+
/* validate burst mode images */
filename = g_string_new ("");
for (i = 0; i < MAX_BURST_IMAGES; i++) {
@@ -419,7 +474,7 @@ GST_START_TEST (validate_captured_image_files)
check_file_validity (filename->str);
}
g_string_free (filename, TRUE);
-
+#endif
/* validate cycled image */
check_file_validity (CYCLE_IMAGE_FILENAME);
}
@@ -453,7 +508,6 @@ camerabin_suite (void)
tcase_set_timeout (tc_basic, 20);
tcase_add_checked_fixture (tc_basic, setup, teardown);
tcase_add_test (tc_basic, test_single_image_capture);
- tcase_add_test (tc_basic, test_burst_image_capture);
tcase_add_test (tc_basic, test_video_recording);
tcase_add_test (tc_basic, test_image_video_cycle);
diff --git a/tests/check/elements/rtpbin_buffer_list.c b/tests/check/elements/rtpbin_buffer_list.c
new file mode 100644
index 00000000..af4003dd
--- /dev/null
+++ b/tests/check/elements/rtpbin_buffer_list.c
@@ -0,0 +1,331 @@
+/* GStreamer
+ *
+ * Unit test for gstrtpbin sending rtp packets using GstBufferList.
+ * Copyright (C) 2009 Branko Subasic <branko dot subasic at axis dot com>
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Library General Public
+ * License as published by the Free Software Foundation; either
+ * version 2 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Library General Public License for more details.
+ *
+ * You should have received a copy of the GNU Library General Public
+ * License along with this library; if not, write to the
+ * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+ * Boston, MA 02111-1307, USA.
+ */
+
+#include <gst/check/gstcheck.h>
+
+#include <gst/rtp/gstrtpbuffer.h>
+
+
+
+/* This test makes sure that RTP packets sent as buffer lists are sent through
+ * the rtpbin as they are supposed to, and not corrupted in any way.
+ */
+
+
+#define TEST_CAPS \
+ "application/x-rtp, " \
+ "media=(string)video, " \
+ "clock-rate=(int)90000, " \
+ "encoding-name=(string)H264, " \
+ "profile-level-id=(string)4d4015, " \
+ "payload=(int)96, " \
+ "ssrc=(guint)2633237432, " \
+ "clock-base=(guint)1868267015, " \
+ "seqnum-base=(guint)54229"
+
+
+/* RTP headers and the first 2 bytes of the payload (FU indicator and FU header)
+ */
+static const guint8 rtp_header[2][14] = {
+ {0x80, 0x60, 0xbb, 0xb7, 0x5c, 0xe9, 0x09,
+ 0x0d, 0xf5, 0x9c, 0x43, 0x55, 0x1c, 0x86},
+ {0x80, 0x60, 0xbb, 0xb8, 0x5c, 0xe9, 0x09,
+ 0x0d, 0xf5, 0x9c, 0x43, 0x55, 0x1c, 0x46}
+};
+
+static const guint rtp_header_len[] = {
+ sizeof rtp_header[0],
+ sizeof rtp_header[1]
+};
+
+static GstBuffer *header_buffer[2] = { NULL, NULL };
+
+
+/* Some payload.
+ */
+static char *payload =
+ "0123456789ABSDEF0123456789ABSDEF0123456789ABSDEF0123456789ABSDEF0123456789ABSDEF"
+ "0123456789ABSDEF0123456789ABSDEF0123456789ABSDEF0123456789ABSDEF0123456789ABSDEF"
+ "0123456789ABSDEF0123456789ABSDEF0123456789ABSDEF0123456789ABSDEF0123456789ABSDEF"
+ "0123456789ABSDEF0123456789ABSDEF0123456789ABSDEF0123456789ABSDEF0123456789ABSDEF"
+ "0123456789ABSDEF0123456789ABSDEF0123456789ABSDEF0123456789ABSDEF0123456789ABSDEF"
+ "0123456789ABSDEF0123456789ABSDEF0123456789ABSDEF0123456789ABSDEF0123456789ABSDEF"
+ "0123456789ABSDEF0123456";
+
+static const guint payload_offset[] = {
+ 0, 498
+};
+
+static const guint payload_len[] = {
+ 498, 5
+};
+
+
+static GstBuffer *original_buffer = NULL;
+
+static GstStaticPadTemplate sinktemplate = GST_STATIC_PAD_TEMPLATE ("sink",
+ GST_PAD_SINK,
+ GST_PAD_ALWAYS,
+ GST_STATIC_CAPS ("application/x-rtp"));
+
+static GstStaticPadTemplate srctemplate = GST_STATIC_PAD_TEMPLATE ("src",
+ GST_PAD_SRC,
+ GST_PAD_ALWAYS,
+ GST_STATIC_CAPS ("application/x-rtp"));
+
+
+static GstBuffer *
+_create_original_buffer (void)
+{
+ GstCaps *caps;
+
+ if (original_buffer != NULL)
+ return original_buffer;
+
+ original_buffer = gst_buffer_new ();
+ fail_unless (original_buffer != NULL);
+
+ gst_buffer_set_data (original_buffer, (guint8 *) payload, strlen (payload));
+ GST_BUFFER_TIMESTAMP (original_buffer) =
+ gst_clock_get_internal_time (gst_system_clock_obtain ());
+
+ caps = gst_caps_from_string (TEST_CAPS);
+ fail_unless (caps != NULL);
+ gst_buffer_set_caps (original_buffer, caps);
+ gst_caps_unref (caps);
+
+ return original_buffer;
+}
+
+static GstBufferList *
+_create_buffer_list (void)
+{
+ GstBufferList *list;
+ GstBufferListIterator *it;
+ GstBuffer *orig_buffer;
+ GstBuffer *buffer;
+
+ orig_buffer = _create_original_buffer ();
+ fail_if (orig_buffer == NULL);
+
+ list = gst_buffer_list_new ();
+ fail_if (list == NULL);
+
+ it = gst_buffer_list_iterate (list);
+ fail_if (it == NULL);
+
+ /*** First group, i.e. first packet. **/
+ gst_buffer_list_iterator_add_group (it);
+
+ /* Create buffer with RTP header and add it to the 1st group */
+ buffer = gst_buffer_new ();
+ GST_BUFFER_MALLOCDATA (buffer) = g_memdup (&rtp_header[0], rtp_header_len[0]);
+ GST_BUFFER_DATA (buffer) = GST_BUFFER_MALLOCDATA (buffer);
+ GST_BUFFER_SIZE (buffer) = rtp_header_len[0];
+ gst_buffer_copy_metadata (buffer, orig_buffer, GST_BUFFER_COPY_ALL);
+ header_buffer[0] = buffer;
+ gst_buffer_list_iterator_add (it, buffer);
+
+ /* Create the payload buffer and add it to the 1st group
+ */
+ buffer =
+ gst_buffer_create_sub (orig_buffer, payload_offset[0], payload_len[0]);
+ fail_if (buffer == NULL);
+ gst_buffer_list_iterator_add (it, buffer);
+
+
+ /*** Second group, i.e. second packet. ***/
+
+ /* Create a new group to hold the rtp header and the payload */
+ gst_buffer_list_iterator_add_group (it);
+
+ /* Create buffer with RTP header and add it to the 2nd group */
+ buffer = gst_buffer_new ();
+ GST_BUFFER_MALLOCDATA (buffer) = g_memdup (&rtp_header[1], rtp_header_len[1]);
+ GST_BUFFER_DATA (buffer) = GST_BUFFER_MALLOCDATA (buffer);
+ GST_BUFFER_SIZE (buffer) = rtp_header_len[1];
+ gst_buffer_copy_metadata (buffer, orig_buffer, GST_BUFFER_COPY_ALL);
+ header_buffer[1] = buffer;
+
+ /* Add the rtp header to the buffer list */
+ gst_buffer_list_iterator_add (it, buffer);
+
+ /* Create the payload buffer and add it to the 2d group
+ */
+ buffer =
+ gst_buffer_create_sub (orig_buffer, payload_offset[1], payload_len[1]);
+ fail_if (buffer == NULL);
+ gst_buffer_list_iterator_add (it, buffer);
+
+ gst_buffer_list_iterator_free (it);
+
+ return list;
+}
+
+
+static void
+_check_header (GstBuffer * buffer, guint index)
+{
+ guint8 *data;
+
+ fail_if (buffer == NULL);
+ fail_unless (index < 2);
+
+ fail_unless (GST_BUFFER_SIZE (buffer) == rtp_header_len[index]);
+
+ /* Can't do a memcmp() on the whole header, cause the SSRC (bytes 8-11) will
+ * most likely be changed in gstrtpbin.
+ */
+ fail_unless ((data = GST_BUFFER_DATA (buffer)) != NULL);
+ fail_unless_equals_uint64 (*(guint64 *) data, *(guint64 *) rtp_header[index]);
+ fail_unless (*(guint16 *) (data + 12) ==
+ *(guint16 *) (rtp_header[index] + 12));
+}
+
+
+static void
+_check_payload (GstBuffer * buffer, guint index)
+{
+ fail_if (buffer == NULL);
+ fail_unless (index < 2);
+
+ fail_unless (GST_BUFFER_SIZE (buffer) == payload_len[index]);
+ fail_if (GST_BUFFER_DATA (buffer) !=
+ (gpointer) (payload + payload_offset[index]));
+ fail_if (memcmp (GST_BUFFER_DATA (buffer), payload + payload_offset[index],
+ payload_len[index]));
+}
+
+
+static void
+_check_group (GstBufferListIterator * it, guint index, GstCaps * caps)
+{
+ GstBuffer *buffer;
+
+ fail_unless (it != NULL);
+ fail_unless (gst_buffer_list_iterator_n_buffers (it) == 2);
+ fail_unless (caps != NULL);
+
+ fail_unless ((buffer = gst_buffer_list_iterator_next (it)) != NULL);
+
+ fail_unless (GST_BUFFER_TIMESTAMP (buffer) ==
+ GST_BUFFER_TIMESTAMP (original_buffer));
+
+ fail_unless (gst_caps_is_equal (GST_BUFFER_CAPS (original_buffer),
+ GST_BUFFER_CAPS (buffer)));
+
+ _check_header (buffer, index);
+
+ fail_unless ((buffer = gst_buffer_list_iterator_next (it)) != NULL);
+ _check_payload (buffer, index);
+}
+
+
+static GstFlowReturn
+_sink_chain_list (GstPad * pad, GstBufferList * list)
+{
+ GstCaps *caps;
+ GstBufferListIterator *it;
+
+ caps = gst_caps_from_string (TEST_CAPS);
+ fail_unless (caps != NULL);
+
+ fail_unless (GST_IS_BUFFER_LIST (list));
+ fail_unless (gst_buffer_list_n_groups (list) == 2);
+
+ it = gst_buffer_list_iterate (list);
+ fail_if (it == NULL);
+
+ fail_unless (gst_buffer_list_iterator_next_group (it));
+ _check_group (it, 0, caps);
+
+ fail_unless (gst_buffer_list_iterator_next_group (it));
+ _check_group (it, 1, caps);
+
+ gst_caps_unref (caps);
+ gst_buffer_list_iterator_free (it);
+
+ gst_buffer_list_unref (list);
+
+ return GST_FLOW_OK;
+}
+
+
+static void
+_set_chain_functions (GstPad * pad)
+{
+ gst_pad_set_chain_list_function (pad, _sink_chain_list);
+}
+
+
+GST_START_TEST (test_bufferlist)
+{
+ GstElement *rtpbin;
+ GstPad *sinkpad;
+ GstPad *srcpad;
+ GstBufferList *list;
+
+ list = _create_buffer_list ();
+ fail_unless (list != NULL);
+
+ rtpbin = gst_check_setup_element ("gstrtpbin");
+
+ srcpad =
+ gst_check_setup_src_pad_by_name (rtpbin, &srctemplate, "send_rtp_sink_0");
+ fail_if (srcpad == NULL);
+ sinkpad =
+ gst_check_setup_sink_pad_by_name (rtpbin, &sinktemplate,
+ "send_rtp_src_0");
+ fail_if (sinkpad == NULL);
+
+ _set_chain_functions (sinkpad);
+
+ gst_pad_set_active (sinkpad, TRUE);
+ gst_element_set_state (rtpbin, GST_STATE_PLAYING);
+ fail_unless (gst_pad_push_list (srcpad, list) == GST_FLOW_OK);
+ gst_pad_set_active (sinkpad, FALSE);
+
+ gst_check_teardown_pad_by_name (rtpbin, "send_rtp_src_0");
+ gst_check_teardown_pad_by_name (rtpbin, "send_rtp_sink_0");
+ gst_check_teardown_element (rtpbin);
+}
+
+GST_END_TEST;
+
+
+
+static Suite *
+bufferlist_suite (void)
+{
+ Suite *s = suite_create ("BufferList");
+
+ TCase *tc_chain = tcase_create ("general");
+
+ /* time out after 30s. */
+ tcase_set_timeout (tc_chain, 10);
+
+ suite_add_tcase (s, tc_chain);
+ tcase_add_test (tc_chain, test_bufferlist);
+
+ return s;
+}
+
+GST_CHECK_MAIN (bufferlist);
diff --git a/tests/check/elements/shapewipe.c b/tests/check/elements/shapewipe.c
index 6fcb0698..d0ec63f9 100644
--- a/tests/check/elements/shapewipe.c
+++ b/tests/check/elements/shapewipe.c
@@ -298,6 +298,7 @@ shapewipe_suite (void)
TCase *tc_chain = tcase_create ("general");
suite_add_tcase (s, tc_chain);
+ tcase_set_timeout (tc_chain, 180);
tcase_add_test (tc_chain, test_general);
return s;
diff --git a/tests/check/pipelines/metadata.c b/tests/check/pipelines/metadata.c
index a632df44..1a16a4a7 100644
--- a/tests/check/pipelines/metadata.c
+++ b/tests/check/pipelines/metadata.c
@@ -190,7 +190,13 @@ test_tags (const gchar * tag_str)
GST_START_TEST (test_common_tags)
{
+ /* The title tag will only work if the XMP backend is enabled.
+ * And since we don't have any programmatic feedback on whether
+ * a tag is properly handled or not... we need to do this kind
+ * of hack. */
+#if HAVE_XMP
test_tags ("taglist,title=\"test image\"");
+#endif
}
GST_END_TEST;