From f19bb850acb3863ce1ed26407593d9ea42b78c8f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Sebastian=20Dr=C3=B6ge?= Date: Wed, 16 Mar 2011 18:19:11 +0100 Subject: [PATCH 01/34] inputselector: Return GST_FLOW_OK until the selected pad pushed something downstream This makes sure that during switches at no point in time all pads have returned not-linked, which can happen when playing an audio-only file with playbin2 and switching between the streams for example. Fixes bug #644935. --- plugins/elements/gstinputselector.c | 11 +++++++++-- 1 file changed, 9 insertions(+), 2 deletions(-) diff --git a/plugins/elements/gstinputselector.c b/plugins/elements/gstinputselector.c index 7ef7be2be3..2a67584100 100644 --- a/plugins/elements/gstinputselector.c +++ b/plugins/elements/gstinputselector.c @@ -137,6 +137,7 @@ struct _GstSelectorPad GstPad parent; gboolean active; /* when buffer have passed the pad */ + gboolean pushed; /* when buffer was pushed downstream since activation */ gboolean eos; /* when EOS has been received */ gboolean discont; /* after switching we create a discont */ gboolean always_ok; @@ -329,6 +330,7 @@ gst_selector_pad_reset (GstSelectorPad * pad) { GST_OBJECT_LOCK (pad); pad->active = FALSE; + pad->pushed = FALSE; pad->eos = FALSE; pad->segment_pending = FALSE; pad->discont = FALSE; @@ -542,7 +544,7 @@ not_active: /* unselected pad, perform fallback alloc or return unlinked when * asked */ GST_OBJECT_LOCK (selpad); - if (selpad->always_ok) { + if (selpad->always_ok || !GST_SELECTOR_PAD_CAST (active_sinkpad)->pushed) { GST_DEBUG_OBJECT (pad, "Not selected, performing fallback allocation"); *buf = NULL; result = GST_FLOW_OK; @@ -675,6 +677,7 @@ gst_selector_pad_chain (GstPad * pad, GstBuffer * buf) } res = gst_pad_push (sel->srcpad, buf); + selpad->pushed = TRUE; done: gst_object_unref (sel); @@ -691,7 +694,7 @@ ignore: /* figure out what to return upstream */ GST_OBJECT_LOCK (selpad); - if (selpad->always_ok) + if (selpad->always_ok || !GST_SELECTOR_PAD_CAST (active_sinkpad)->pushed) res = GST_FLOW_OK; else res = GST_FLOW_NOT_LINKED; @@ -1032,6 +1035,8 @@ gst_input_selector_set_active_pad (GstInputSelector * self, gst_segment_set_stop (&self->segment, stop_time); self->pending_close = TRUE; } + if (old) + old->pushed = FALSE; if (new && new->active && start_time >= 0) { GST_DEBUG_OBJECT (self, "setting start_time to %" GST_TIME_FORMAT, @@ -1040,6 +1045,8 @@ gst_input_selector_set_active_pad (GstInputSelector * self, gst_segment_set_start (&new->segment, start_time); new->segment_pending = TRUE; } + if (new) + new->pushed = FALSE; active_pad_p = &self->active_sinkpad; gst_object_replace ((GstObject **) active_pad_p, GST_OBJECT_CAST (pad)); From 5e60a80268e239be8bf1a678a0113a21a49a4a05 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Sebastian=20Dr=C3=B6ge?= Date: Thu, 17 Mar 2011 14:10:49 +0100 Subject: [PATCH 02/34] inputselector: Make sure that EOS is always sent downstream for the active pad It can happen that the currently active pad got the EOS event before it was activated and the previously active pad got the EOS event after it was deactivated. In that case we have to send the EOS event from an inactive pad downstream. --- plugins/elements/gstinputselector.c | 21 +++++++++++++++++++++ 1 file changed, 21 insertions(+) diff --git a/plugins/elements/gstinputselector.c b/plugins/elements/gstinputselector.c index 2a67584100..dbb3b22ada 100644 --- a/plugins/elements/gstinputselector.c +++ b/plugins/elements/gstinputselector.c @@ -139,6 +139,7 @@ struct _GstSelectorPad gboolean active; /* when buffer have passed the pad */ gboolean pushed; /* when buffer was pushed downstream since activation */ gboolean eos; /* when EOS has been received */ + gboolean eos_sent; /* when EOS was sent downstream */ gboolean discont; /* after switching we create a discont */ gboolean always_ok; GstSegment segment; /* the current segment on the pad */ @@ -332,6 +333,7 @@ gst_selector_pad_reset (GstSelectorPad * pad) pad->active = FALSE; pad->pushed = FALSE; pad->eos = FALSE; + pad->eos_sent = FALSE; pad->segment_pending = FALSE; pad->discont = FALSE; gst_segment_init (&pad->segment, GST_FORMAT_UNDEFINED); @@ -450,6 +452,25 @@ gst_selector_pad_event (GstPad * pad, GstEvent * event) } case GST_EVENT_EOS: selpad->eos = TRUE; + + if (forward) { + selpad->eos_sent = TRUE; + } else { + GstSelectorPad *tmp; + + /* If the active sinkpad is in EOS state but EOS + * was not sent downstream this means that the pad + * got EOS before it was set as active pad and that + * the previously active pad got EOS after it was + * active + */ + GST_INPUT_SELECTOR_LOCK (sel); + active_sinkpad = gst_input_selector_activate_sinkpad (sel, pad); + tmp = GST_SELECTOR_PAD (active_sinkpad); + forward = (tmp->eos && !tmp->eos_sent); + tmp->eos_sent = TRUE; + GST_INPUT_SELECTOR_UNLOCK (sel); + } GST_DEBUG_OBJECT (pad, "received EOS"); break; default: From c8ecd6e9ebc6529d1cabc60d75bb30c392b2a82d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Sebastian=20Dr=C3=B6ge?= Date: Thu, 17 Mar 2011 14:21:17 +0100 Subject: [PATCH 03/34] inputselector: Hold the selector lock while reading properties of the active pad --- plugins/elements/gstinputselector.c | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) diff --git a/plugins/elements/gstinputselector.c b/plugins/elements/gstinputselector.c index dbb3b22ada..0995e67db1 100644 --- a/plugins/elements/gstinputselector.c +++ b/plugins/elements/gstinputselector.c @@ -560,12 +560,14 @@ done: /* ERRORS */ not_active: { + gboolean active_pad_pushed = GST_SELECTOR_PAD_CAST (active_sinkpad)->pushed; + GST_INPUT_SELECTOR_UNLOCK (sel); /* unselected pad, perform fallback alloc or return unlinked when * asked */ GST_OBJECT_LOCK (selpad); - if (selpad->always_ok || !GST_SELECTOR_PAD_CAST (active_sinkpad)->pushed) { + if (selpad->always_ok || !active_pad_pushed) { GST_DEBUG_OBJECT (pad, "Not selected, performing fallback allocation"); *buf = NULL; result = GST_FLOW_OK; @@ -707,6 +709,8 @@ done: /* dropped buffers */ ignore: { + gboolean active_pad_pushed = GST_SELECTOR_PAD_CAST (active_sinkpad)->pushed; + GST_DEBUG_OBJECT (pad, "Pad not active, discard buffer %p", buf); /* when we drop a buffer, we're creating a discont on this pad */ selpad->discont = TRUE; @@ -715,7 +719,7 @@ ignore: /* figure out what to return upstream */ GST_OBJECT_LOCK (selpad); - if (selpad->always_ok || !GST_SELECTOR_PAD_CAST (active_sinkpad)->pushed) + if (selpad->always_ok || !active_pad_pushed) res = GST_FLOW_OK; else res = GST_FLOW_NOT_LINKED; From 02d27de048ae7f30114f7a76ff964143413d0edf Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Tim-Philipp=20M=C3=BCller?= Date: Thu, 17 Mar 2011 23:42:48 +0000 Subject: [PATCH 04/34] task: fix GST_TASK_BROADCAST MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Surprisingly enough, you can't "breadcast" on a GCond. Spotted by Rune Sætre. https://bugzilla.gnome.org/show_bug.cgi?id=645022 --- gst/gsttask.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/gst/gsttask.h b/gst/gsttask.h index 279d530f7a..2081815231 100644 --- a/gst/gsttask.h +++ b/gst/gsttask.h @@ -99,7 +99,7 @@ typedef enum { * * Send a broadcast signal to all waiting task conds */ -#define GST_TASK_BROADCAST(task) g_cond_breadcast(GST_TASK_GET_COND (task)) +#define GST_TASK_BROADCAST(task) g_cond_broadcast(GST_TASK_GET_COND (task)) /** * GST_TASK_GET_LOCK: From d41fe48ce3b4626849f6cfb5187b116e9811d38f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Sebastian=20Dr=C3=B6ge?= Date: Sat, 19 Mar 2011 08:50:06 +0100 Subject: [PATCH 05/34] inputselector: Move locking and signalling macros from the header to the source file --- plugins/elements/gstinputselector.c | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/plugins/elements/gstinputselector.c b/plugins/elements/gstinputselector.c index 0995e67db1..33f2ce1bb1 100644 --- a/plugins/elements/gstinputselector.c +++ b/plugins/elements/gstinputselector.c @@ -70,6 +70,14 @@ static GStaticRecMutex notify_mutex = G_STATIC_REC_MUTEX_INIT; #define NOTIFY_MUTEX_UNLOCK() g_static_rec_mutex_unlock (¬ify_mutex) #endif +#define GST_INPUT_SELECTOR_GET_LOCK(sel) (((GstInputSelector*)(sel))->lock) +#define GST_INPUT_SELECTOR_GET_COND(sel) (((GstInputSelector*)(sel))->cond) +#define GST_INPUT_SELECTOR_LOCK(sel) (g_mutex_lock (GST_INPUT_SELECTOR_GET_LOCK(sel))) +#define GST_INPUT_SELECTOR_UNLOCK(sel) (g_mutex_unlock (GST_INPUT_SELECTOR_GET_LOCK(sel))) +#define GST_INPUT_SELECTOR_WAIT(sel) (g_cond_wait (GST_INPUT_SELECTOR_GET_COND(sel), \ + GST_INPUT_SELECTOR_GET_LOCK(sel))) +#define GST_INPUT_SELECTOR_BROADCAST(sel) (g_cond_broadcast (GST_INPUT_SELECTOR_GET_COND(sel))) + static GstStaticPadTemplate gst_input_selector_sink_factory = GST_STATIC_PAD_TEMPLATE ("sink%d", GST_PAD_SINK, From 69e81448c164d844358815322408c352e697ded2 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Sebastian=20Dr=C3=B6ge?= Date: Sat, 19 Mar 2011 08:55:57 +0100 Subject: [PATCH 06/34] inputselector: Stop waiting for a pad switch when the pad is flushing --- plugins/elements/gstinputselector.c | 15 +++++++++++---- 1 file changed, 11 insertions(+), 4 deletions(-) diff --git a/plugins/elements/gstinputselector.c b/plugins/elements/gstinputselector.c index 33f2ce1bb1..ffe825e460 100644 --- a/plugins/elements/gstinputselector.c +++ b/plugins/elements/gstinputselector.c @@ -5,6 +5,7 @@ * Copyright (C) 2007 Wim Taymans * Copyright (C) 2007 Andy Wingo * Copyright (C) 2008 Nokia Corporation. (contact ) + * Copyright (C) 2011 Sebastian Dröge * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Library General Public @@ -149,6 +150,7 @@ struct _GstSelectorPad gboolean eos; /* when EOS has been received */ gboolean eos_sent; /* when EOS was sent downstream */ gboolean discont; /* after switching we create a discont */ + gboolean flushing; /* set after flush-start and before flush-stop */ gboolean always_ok; GstSegment segment; /* the current segment on the pad */ GstTagList *tags; /* last tags received on the pad */ @@ -344,6 +346,7 @@ gst_selector_pad_reset (GstSelectorPad * pad) pad->eos_sent = FALSE; pad->segment_pending = FALSE; pad->discont = FALSE; + pad->flushing = FALSE; gst_segment_init (&pad->segment, GST_FORMAT_UNDEFINED); GST_OBJECT_UNLOCK (pad); } @@ -397,7 +400,11 @@ gst_selector_pad_event (GstPad * pad, GstEvent * event) switch (GST_EVENT_TYPE (event)) { case GST_EVENT_FLUSH_START: - /* FIXME, flush out the waiter */ + /* Unblock the pad if it's waiting */ + GST_INPUT_SELECTOR_LOCK (sel); + selpad->flushing = TRUE; + GST_INPUT_SELECTOR_BROADCAST (sel); + GST_INPUT_SELECTOR_UNLOCK (sel); break; case GST_EVENT_FLUSH_STOP: GST_INPUT_SELECTOR_LOCK (sel); @@ -592,9 +599,9 @@ not_active: /* must be called with the SELECTOR_LOCK, will block while the pad is blocked * or return TRUE when flushing */ static gboolean -gst_input_selector_wait (GstInputSelector * self, GstPad * pad) +gst_input_selector_wait (GstInputSelector * self, GstSelectorPad * pad) { - while (self->blocked && !self->flushing) { + while (self->blocked && !self->flushing && !pad->flushing) { /* we can be unlocked here when we are shutting down (flushing) or when we * get unblocked */ GST_INPUT_SELECTOR_WAIT (self); @@ -621,7 +628,7 @@ gst_selector_pad_chain (GstPad * pad, GstBuffer * buf) GST_INPUT_SELECTOR_LOCK (sel); /* wait or check for flushing */ - if (gst_input_selector_wait (sel, pad)) + if (gst_input_selector_wait (sel, selpad)) goto flushing; GST_LOG_OBJECT (pad, "getting active pad"); From 27c0a2b9b12c93c6a7940c3a97d466ba3afbb9ae Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Sebastian=20Dr=C3=B6ge?= Date: Sat, 19 Mar 2011 10:39:28 +0100 Subject: [PATCH 07/34] event: Add since marker to GST_EVENT_SINK_MESSAGE --- gst/gstevent.h | 1 + 1 file changed, 1 insertion(+) diff --git a/gst/gstevent.h b/gst/gstevent.h index 34983b679b..cf61369877 100644 --- a/gst/gstevent.h +++ b/gst/gstevent.h @@ -93,6 +93,7 @@ typedef enum { * @GST_EVENT_SINK_MESSAGE: An event that sinks turn into a message. Used to * send messages that should be emitted in sync with * rendering. + * Since: 0.10.26 * @GST_EVENT_QOS: A quality message. Used to indicate to upstream elements * that the downstream elements should adjust their processing * rate. From a789096c04a661cf34df833be8ee927388aa12de Mon Sep 17 00:00:00 2001 From: "Jason D. Clinton" Date: Sat, 19 Mar 2011 17:06:12 -0500 Subject: [PATCH 08/34] build: fix build with -Werror with GCC 4.6.0 This touches three areas of code, removes unused variables and discards return values from two functions with (void). https://bugzilla.gnome.org/show_bug.cgi?id=645267 --- gst/gstpoll.c | 3 +-- libs/gst/controller/gstinterpolation.c | 3 +-- plugins/elements/gstfilesrc.c | 4 ++-- 3 files changed, 4 insertions(+), 6 deletions(-) diff --git a/gst/gstpoll.c b/gst/gstpoll.c index cbc3904d94..ba9fdc8bca 100644 --- a/gst/gstpoll.c +++ b/gst/gstpoll.c @@ -200,7 +200,6 @@ release_wakeup (GstPoll * set) static inline gint release_all_wakeup (GstPoll * set) { - gboolean result; gint old; while (TRUE) { @@ -211,7 +210,7 @@ release_all_wakeup (GstPoll * set) /* try to remove all pending control messages */ if (g_atomic_int_compare_and_exchange (&set->control_pending, old, 0)) { /* we managed to remove all messages, read the control socket */ - result = RELEASE_EVENT (set); + (void) RELEASE_EVENT (set); break; } } diff --git a/libs/gst/controller/gstinterpolation.c b/libs/gst/controller/gstinterpolation.c index c3a427482d..54ff60e1a0 100644 --- a/libs/gst/controller/gstinterpolation.c +++ b/libs/gst/controller/gstinterpolation.c @@ -573,7 +573,7 @@ _interpolate_cubic_update_cache_##vtype (GstInterpolationControlSource *self) \ \ GSequenceIter *iter; \ GstControlPoint *cp; \ - GstClockTime x_prev, x, x_next; \ + GstClockTime x, x_next; \ g##vtype y_prev, y, y_next; \ \ /* Fill linear system of equations */ \ @@ -592,7 +592,6 @@ _interpolate_cubic_update_cache_##vtype (GstInterpolationControlSource *self) \ \ for (i = 1; i < n-1; i++) { \ /* Shuffle x and y values */ \ - x_prev = x; \ y_prev = y; \ x = x_next; \ y = y_next; \ diff --git a/plugins/elements/gstfilesrc.c b/plugins/elements/gstfilesrc.c index 16a3e0300f..cc07a72a02 100644 --- a/plugins/elements/gstfilesrc.c +++ b/plugins/elements/gstfilesrc.c @@ -763,11 +763,11 @@ gst_file_src_create_mmap (GstFileSrc * src, guint64 offset, guint length, /* if we need to touch the buffer (to bring it into memory), do so */ if (src->touch) { - volatile guchar *p = GST_BUFFER_DATA (buf), c; + volatile guchar *p = GST_BUFFER_DATA (buf); /* read first byte of each page */ for (i = 0; i < GST_BUFFER_SIZE (buf); i += src->pagesize) - c = p[i]; + (void) p[i]; } /* we're done, return the buffer */ From 14eb517849e4d1cb3506ac2f7ec16452dec8a8a5 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Sebastian=20Dr=C3=B6ge?= Date: Mon, 21 Mar 2011 16:28:37 +0100 Subject: [PATCH 09/34] multiqueue: Exit loop function if the pad is flushing Fixes possible deadlocks when flushing an unlinked pad that waits for other pads to advance. --- plugins/elements/gstmultiqueue.c | 17 +++++++++++++++++ 1 file changed, 17 insertions(+) diff --git a/plugins/elements/gstmultiqueue.c b/plugins/elements/gstmultiqueue.c index f21a2aa6db..4a0f351ff0 100644 --- a/plugins/elements/gstmultiqueue.c +++ b/plugins/elements/gstmultiqueue.c @@ -148,6 +148,7 @@ struct _GstSingleQueue GstDataQueueSize max_size, extra_size; GstClockTime cur_time; gboolean is_eos; + gboolean flushing; /* Protected by global lock */ guint32 nextid; /* ID of the next object waiting to be pushed */ @@ -661,6 +662,8 @@ gst_single_queue_flush (GstMultiQueue * mq, GstSingleQueue * sq, gboolean flush) sq->srcresult = GST_FLOW_WRONG_STATE; gst_data_queue_set_flushing (sq->queue, TRUE); + sq->flushing = TRUE; + /* wake up non-linked task */ GST_LOG_OBJECT (mq, "SingleQueue %d : waking up eventually waiting task", sq->id); @@ -685,6 +688,8 @@ gst_single_queue_flush (GstMultiQueue * mq, GstSingleQueue * sq, gboolean flush) sq->last_oldid = G_MAXUINT32; gst_data_queue_set_flushing (sq->queue, FALSE); + sq->flushing = FALSE; + GST_LOG_OBJECT (mq, "SingleQueue %d : starting task", sq->id); result = gst_pad_start_task (sq->srcpad, (GstTaskFunction) gst_multi_queue_loop, @@ -1025,6 +1030,9 @@ gst_multi_queue_loop (GstPad * pad) GST_DEBUG_OBJECT (mq, "SingleQueue %d : trying to pop an object", sq->id); + if (sq->flushing) + goto out_flushing; + /* Get something from the queue, blocking until that happens, or we get * flushed */ if (!(gst_data_queue_pop (sq->queue, &sitem))) @@ -1077,6 +1085,11 @@ gst_multi_queue_loop (GstPad * pad) g_cond_wait (sq->turn, mq->qlock); mq->numwaiting--; + if (sq->flushing) { + GST_MULTI_QUEUE_MUTEX_UNLOCK (mq); + goto out_flushing; + } + GST_DEBUG_OBJECT (mq, "queue %d woken from sleeping for not-linked " "wakeup with newid %u and highid %u", sq->id, newid, mq->highid); } @@ -1094,6 +1107,9 @@ gst_multi_queue_loop (GstPad * pad) GST_MULTI_QUEUE_MUTEX_UNLOCK (mq); } + if (sq->flushing) + goto out_flushing; + GST_LOG_OBJECT (mq, "BEFORE PUSHING sq->srcresult: %s", gst_flow_get_name (sq->srcresult)); @@ -1664,6 +1680,7 @@ gst_single_queue_new (GstMultiQueue * mqueue) (GstDataQueueFullCallback) single_queue_overrun_cb, (GstDataQueueEmptyCallback) single_queue_underrun_cb, sq); sq->is_eos = FALSE; + sq->flushing = FALSE; gst_segment_init (&sq->sink_segment, GST_FORMAT_TIME); gst_segment_init (&sq->src_segment, GST_FORMAT_TIME); From 5b48fd5b24e08584b4ca70539e3abee00928387e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Sebastian=20Dr=C3=B6ge?= Date: Mon, 21 Mar 2011 12:39:34 +0100 Subject: [PATCH 10/34] multiqueue: Remove unused variable --- plugins/elements/gstmultiqueue.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/plugins/elements/gstmultiqueue.c b/plugins/elements/gstmultiqueue.c index 4a0f351ff0..9fa3304e0d 100644 --- a/plugins/elements/gstmultiqueue.c +++ b/plugins/elements/gstmultiqueue.c @@ -2,6 +2,7 @@ * Copyright (C) 2006 Edward Hervey * Copyright (C) 2007 Jan Schmidt * Copyright (C) 2007 Wim Taymans + * Copyright (C) 2011 Sebastian Dröge * * gstmultiqueue.c: * @@ -421,7 +422,6 @@ gst_multi_queue_init (GstMultiQueue * mqueue, GstMultiQueueClass * klass) mqueue->counter = 1; mqueue->highid = -1; - mqueue->nextnotlinked = -1; mqueue->qlock = g_mutex_new (); } From 9e36a51bac990a5caba278caeef8ecb2937de4ff Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Sebastian=20Dr=C3=B6ge?= Date: Mon, 21 Mar 2011 17:17:22 +0100 Subject: [PATCH 11/34] multiqueue: Unblock all waiting pads when shutting down --- plugins/elements/gstmultiqueue.c | 54 ++++++++++++++++++++++++++++++++ 1 file changed, 54 insertions(+) diff --git a/plugins/elements/gstmultiqueue.c b/plugins/elements/gstmultiqueue.c index 9fa3304e0d..f1956dae9e 100644 --- a/plugins/elements/gstmultiqueue.c +++ b/plugins/elements/gstmultiqueue.c @@ -256,6 +256,8 @@ static void gst_multi_queue_get_property (GObject * object, static GstPad *gst_multi_queue_request_new_pad (GstElement * element, GstPadTemplate * temp, const gchar * name); static void gst_multi_queue_release_pad (GstElement * element, GstPad * pad); +static GstStateChangeReturn gst_multi_queue_change_state (GstElement * + element, GstStateChange transition); static void gst_multi_queue_loop (GstPad * pad); @@ -400,6 +402,8 @@ gst_multi_queue_class_init (GstMultiQueueClass * klass) GST_DEBUG_FUNCPTR (gst_multi_queue_request_new_pad); gstelement_class->release_pad = GST_DEBUG_FUNCPTR (gst_multi_queue_release_pad); + gstelement_class->change_state = + GST_DEBUG_FUNCPTR (gst_multi_queue_change_state); } static void @@ -650,6 +654,56 @@ gst_multi_queue_release_pad (GstElement * element, GstPad * pad) gst_single_queue_free (sq); } +static GstStateChangeReturn +gst_multi_queue_change_state (GstElement * element, GstStateChange transition) +{ + GstMultiQueue *mqueue = GST_MULTI_QUEUE (element); + GstSingleQueue *sq = NULL; + GstStateChangeReturn result; + + switch (transition) { + case GST_STATE_CHANGE_READY_TO_PAUSED:{ + GList *tmp; + + /* Set all pads to non-flushing */ + GST_MULTI_QUEUE_MUTEX_LOCK (mqueue); + for (tmp = mqueue->queues; tmp; tmp = g_list_next (tmp)) { + sq = (GstSingleQueue *) tmp->data; + sq->flushing = FALSE; + } + GST_MULTI_QUEUE_MUTEX_UNLOCK (mqueue); + break; + } + case GST_STATE_CHANGE_PAUSED_TO_READY:{ + GList *tmp; + + /* Un-wait all waiting pads */ + GST_MULTI_QUEUE_MUTEX_LOCK (mqueue); + for (tmp = mqueue->queues; tmp; tmp = g_list_next (tmp)) { + sq = (GstSingleQueue *) tmp->data; + sq->flushing = TRUE; + g_cond_signal (sq->turn); + } + GST_MULTI_QUEUE_MUTEX_UNLOCK (mqueue); + break; + } + default: + break; + } + + result = GST_ELEMENT_CLASS (parent_class)->change_state (element, transition); + + switch (transition) { + default: + break; + } + + return result; + + + +} + static gboolean gst_single_queue_flush (GstMultiQueue * mq, GstSingleQueue * sq, gboolean flush) { From 383cac91b103fa4b133428cc6196f35a1cd7904d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Sebastian=20Dr=C3=B6ge?= Date: Mon, 21 Mar 2011 17:52:13 +0100 Subject: [PATCH 12/34] multiqueue: Increment unique item counter with atomic operations Before it was only protected by the stream lock but every pad has its own stream lock, making the protection rather useless. --- plugins/elements/gstmultiqueue.c | 7 +++---- plugins/elements/gstmultiqueue.h | 2 +- 2 files changed, 4 insertions(+), 5 deletions(-) diff --git a/plugins/elements/gstmultiqueue.c b/plugins/elements/gstmultiqueue.c index f1956dae9e..3f1eef5705 100644 --- a/plugins/elements/gstmultiqueue.c +++ b/plugins/elements/gstmultiqueue.c @@ -1229,7 +1229,7 @@ gst_multi_queue_chain (GstPad * pad, GstBuffer * buffer) goto was_eos; /* Get a unique incrementing id */ - curid = mq->counter++; + curid = g_atomic_int_exchange_and_add ((gint *) & mq->counter, 1); GST_LOG_OBJECT (mq, "SingleQueue %d : about to enqueue buffer %p with id %d", sq->id, buffer, curid); @@ -1334,9 +1334,8 @@ gst_multi_queue_sink_event (GstPad * pad, GstEvent * event) if (sq->is_eos) goto was_eos; - /* Get an unique incrementing id. protected with the STREAM_LOCK, unserialized - * events already got pushed and don't end up in the queue. */ - curid = mq->counter++; + /* Get an unique incrementing id. */ + curid = g_atomic_int_exchange_and_add ((gint *) & mq->counter, 1); item = gst_multi_queue_event_item_new ((GstMiniObject *) event, curid); diff --git a/plugins/elements/gstmultiqueue.h b/plugins/elements/gstmultiqueue.h index ec47601d08..60262b7c13 100644 --- a/plugins/elements/gstmultiqueue.h +++ b/plugins/elements/gstmultiqueue.h @@ -63,7 +63,7 @@ struct _GstMultiQueue { gboolean buffering; gint percent; - guint32 counter; /* incoming object counter, protected with STREAM_LOCK */ + guint32 counter; /* incoming object counter, use atomic accesses */ guint32 highid; /* contains highest id of last outputted object */ GMutex * qlock; /* Global queue lock (vs object lock or individual */ From 65fbc9398a33c4e9d22b8d216bc49e4ff992d263 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Sebastian=20Dr=C3=B6ge?= Date: Mon, 21 Mar 2011 17:54:10 +0100 Subject: [PATCH 13/34] multiqueue: Really remove unused variable --- plugins/elements/gstmultiqueue.h | 2 -- 1 file changed, 2 deletions(-) diff --git a/plugins/elements/gstmultiqueue.h b/plugins/elements/gstmultiqueue.h index 60262b7c13..b9c28cd442 100644 --- a/plugins/elements/gstmultiqueue.h +++ b/plugins/elements/gstmultiqueue.h @@ -70,8 +70,6 @@ struct _GstMultiQueue { /* queues lock). Protects nbqueues, queues, global */ /* GstMultiQueueSize, counter and highid */ - gint nextnotlinked; /* ID of the next queue not linked (-1 : none) */ - gint numwaiting; /* number of not-linked pads waiting */ }; From 489b94444e96b8ea43aa929eac615471fcb9778e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Sebastian=20Dr=C3=B6ge?= Date: Tue, 22 Mar 2011 11:04:20 +0100 Subject: [PATCH 14/34] multiqueue: Don't leak objects when flushing after dequeueing and before pushing the object --- plugins/elements/gstmultiqueue.c | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/plugins/elements/gstmultiqueue.c b/plugins/elements/gstmultiqueue.c index 3f1eef5705..f2850831f8 100644 --- a/plugins/elements/gstmultiqueue.c +++ b/plugins/elements/gstmultiqueue.c @@ -1075,7 +1075,7 @@ gst_multi_queue_loop (GstPad * pad) GstMultiQueueItem *item; GstDataQueueItem *sitem; GstMultiQueue *mq; - GstMiniObject *object; + GstMiniObject *object = NULL; guint32 newid; GstFlowReturn result; @@ -1170,6 +1170,7 @@ gst_multi_queue_loop (GstPad * pad) /* Try to push out the new object */ result = gst_single_queue_push_one (mq, sq, object); sq->srcresult = result; + object = NULL; if (result != GST_FLOW_OK && result != GST_FLOW_NOT_LINKED && result != GST_FLOW_UNEXPECTED) @@ -1183,6 +1184,9 @@ gst_multi_queue_loop (GstPad * pad) out_flushing: { + if (object) + gst_mini_object_unref (object); + /* Need to make sure wake up any sleeping pads when we exit */ GST_MULTI_QUEUE_MUTEX_LOCK (mq); compute_high_id (mq); From 1be2076922db6ca8089756a81434617af6a3dec2 Mon Sep 17 00:00:00 2001 From: Luis de Bethencourt Date: Fri, 18 Mar 2011 19:34:57 +0100 Subject: [PATCH 15/34] autogen: wingo signed comment --- autogen.sh | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/autogen.sh b/autogen.sh index fd523618f4..c0cd19e54c 100755 --- a/autogen.sh +++ b/autogen.sh @@ -84,7 +84,7 @@ tool_run "$libtoolize" "--copy --force" tool_run "$aclocal" "-I m4 -I common/m4 $ACLOCAL_FLAGS" tool_run "$autoheader" -# touch the stamp-h.in build stamp so we don't re-run autoheader in maintainer mode -- wingo +# touch the stamp-h.in build stamp so we don't re-run autoheader in maintainer mode echo timestamp > stamp-h.in 2> /dev/null tool_run "$autoconf" From 4b322b215aadf33f114afd7054a7cecaa853c4e0 Mon Sep 17 00:00:00 2001 From: Thiago Santos Date: Fri, 18 Mar 2011 08:22:23 -0300 Subject: [PATCH 16/34] tagsetter: Removing unused debug category tagsetter's debug category had a typo and was unused. Removing it. --- gst/gsttagsetter.c | 6 ------ 1 file changed, 6 deletions(-) diff --git a/gst/gsttagsetter.c b/gst/gsttagsetter.c index 05dbbab439..5a5f967f48 100644 --- a/gst/gsttagsetter.c +++ b/gst/gsttagsetter.c @@ -77,9 +77,6 @@ #include #include -GST_DEBUG_CATEGORY_STATIC (gst_tag_interface_debug); -#define GST_CAT_DEFAULT tag_tag_interface_debug - static GQuark gst_tag_key; typedef struct @@ -108,9 +105,6 @@ gst_tag_setter_get_type (void) NULL }; - GST_DEBUG_CATEGORY_INIT (gst_tag_interface_debug, "GstTagInterface", 0, - "interfaces for tagging"); - _type = g_type_register_static (G_TYPE_INTERFACE, "GstTagSetter", &tag_setter_info, 0); From 2f0dab0f44dcb5260285b980feac569a10acfd33 Mon Sep 17 00:00:00 2001 From: Thiago Santos Date: Tue, 22 Mar 2011 16:26:56 -0300 Subject: [PATCH 17/34] gstelement: Fix typo in the docs GST_ELEMENT_INFO will post a INFO message, not a WARNING --- gst/gstelement.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/gst/gstelement.h b/gst/gstelement.h index b026dff249..622f05f0f2 100644 --- a/gst/gstelement.h +++ b/gst/gstelement.h @@ -459,7 +459,7 @@ G_STMT_START { \ * * Utility function that elements can use in case they want to inform * the application of something noteworthy that is not an error. - * The pipeline will post a warning message and the + * The pipeline will post a info message and the * application will be informed. * * Since: 0.10.12 From 5300a5e73b1c20958e3a348003e750d5be50930c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Tim-Philipp=20M=C3=BCller?= Date: Sat, 12 Mar 2011 16:58:01 +0000 Subject: [PATCH 18/34] bytereader, bytewriter: fix up inline functions to make g++ happy MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit gstbytereader.h: In function ‘guint8* gst_byte_reader_dup_data_unchecked(GstByteReader*, guint)’: gstbytereader.h:249:75: error: invalid conversion from ‘void*’ to ‘guint8*’ gstbytewriter.h: In function ‘gboolean _gst_byte_writer_ensure_free_space_inline(GstByteWriter*, guint)’: gstbytewriter.h:196:75: error: invalid conversion from ‘void*’ to ‘guint8*’ https://bugzilla.gnome.org/show_bug.cgi?id=645595 --- libs/gst/base/gstbytereader.h | 3 ++- libs/gst/base/gstbytewriter.h | 4 ++-- 2 files changed, 4 insertions(+), 3 deletions(-) diff --git a/libs/gst/base/gstbytereader.h b/libs/gst/base/gstbytereader.h index f25c3b54ef..8ce76df334 100644 --- a/libs/gst/base/gstbytereader.h +++ b/libs/gst/base/gstbytereader.h @@ -246,7 +246,8 @@ gst_byte_reader_get_data_unchecked (GstByteReader * reader, guint size) static inline guint8 * gst_byte_reader_dup_data_unchecked (GstByteReader * reader, guint size) { - return g_memdup (gst_byte_reader_get_data_unchecked (reader, size), size); + gconstpointer data = gst_byte_reader_get_data_unchecked (reader, size); + return (guint8 *) g_memdup (data, size); } /* Unchecked variants that should not be used */ diff --git a/libs/gst/base/gstbytewriter.h b/libs/gst/base/gstbytewriter.h index 186480d6cd..8fcd53da6f 100644 --- a/libs/gst/base/gstbytewriter.h +++ b/libs/gst/base/gstbytewriter.h @@ -183,7 +183,7 @@ _gst_byte_writer_next_pow2 (guint n) static inline gboolean _gst_byte_writer_ensure_free_space_inline (GstByteWriter * writer, guint size) { - guint8 *data; + gpointer data; if (G_LIKELY (size <= writer->alloc_size - writer->parent.byte)) return TRUE; @@ -197,7 +197,7 @@ _gst_byte_writer_ensure_free_space_inline (GstByteWriter * writer, guint size) if (G_UNLIKELY (data == NULL)) return FALSE; - writer->parent.data = data; + writer->parent.data = (guint8 *) data; return TRUE; } From f9558b163fab74d97a747823d2abede31f343871 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Tim-Philipp=20M=C3=BCller?= Date: Sat, 12 Mar 2011 17:01:39 +0000 Subject: [PATCH 19/34] tests: add libscpp unit test to make sure g++ likes our library headers --- tests/check/Makefile.am | 4 +- tests/check/libs/.gitignore | 1 + tests/check/libs/gstlibscpp.cc | 75 ++++++++++++++++++++++++++++++++++ 3 files changed, 79 insertions(+), 1 deletion(-) create mode 100644 tests/check/libs/gstlibscpp.cc diff --git a/tests/check/Makefile.am b/tests/check/Makefile.am index 83e38aa49a..d006bc7f67 100644 --- a/tests/check/Makefile.am +++ b/tests/check/Makefile.am @@ -44,7 +44,7 @@ endif endif if HAVE_CXX -CXX_CHECKS = gst/gstcpp +CXX_CHECKS = gst/gstcpp libs/gstlibscpp else CXX_CHECKS = endif @@ -166,6 +166,8 @@ LDADD = $(top_builddir)/libs/gst/check/libgstcheck-@GST_MAJORMINOR@.la \ gst_gstcpp_SOURCES = gst/gstcpp.cc +libs_gstlibscpp_SOURCES = libs/gstlibscpp.cc + gst_gstutils_LDADD = $(LDADD) $(GSL_LIBS) $(GMP_LIBS) libs_gdp_SOURCES = \ diff --git a/tests/check/libs/.gitignore b/tests/check/libs/.gitignore index 64540fdb34..8eb96b413b 100644 --- a/tests/check/libs/.gitignore +++ b/tests/check/libs/.gitignore @@ -8,6 +8,7 @@ bytewriter gdp collectpads controller +gstlibscpp gstnetclientclock gstnettimeprovider libsabi diff --git a/tests/check/libs/gstlibscpp.cc b/tests/check/libs/gstlibscpp.cc new file mode 100644 index 0000000000..23079e8666 --- /dev/null +++ b/tests/check/libs/gstlibscpp.cc @@ -0,0 +1,75 @@ +/* GStreamer + * Copyright (C) 2011 Tim-Philipp Müller + * + * 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. + */ + +#ifdef HAVE_CONFIG_H +#include +#endif + +#include +#include + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#include +#include +#include +#include +#include +#include +#include + +#include + +#include +#include +#include +#include + +/* we mostly just want to make sure that our library headers don't + * contain anything a C++ compiler might not like */ +GST_START_TEST (test_nothing) +{ + gst_init (NULL, NULL); +} + +GST_END_TEST; + +static Suite * +libscpp_suite (void) +{ + Suite *s = suite_create ("GstLibsCpp"); + TCase *tc_chain = tcase_create ("C++ libs header tests"); + + suite_add_tcase (s, tc_chain); + tcase_add_test (tc_chain, test_nothing); + + return s; +} + +GST_CHECK_MAIN (libscpp); From 09d83e589ab24becbe9171407e8b5a865f7d898d Mon Sep 17 00:00:00 2001 From: Edward Hervey Date: Fri, 25 Feb 2011 08:50:12 -0300 Subject: [PATCH 20/34] gstcaps: new API : gst_caps_intersect_full Just like gst_caps_intersect, but adds a new parameter 'mode' that allows selecting the intersection algorithm to use. Currently we have GST_CAPS_INTERSECT_MODE_ZIG_ZAG (default) and GST_CAPS_INTERSECT_MODE_FIRST. API: gst_caps_intersect_full API: GstCapsIntersectMode API: GST_CAPS_INTERSECT_MODE_ZIG_ZAG API: GST_CAPS_INTERSECT_MODE_FIRST https://bugzilla.gnome.org/show_bug.cgi?id=617045 --- gst/gst.c | 2 + gst/gstcaps.c | 120 +++++++++++++++++++++++++++++----- gst/gstcaps.h | 34 ++++++++++ win32/common/libgstreamer.def | 2 + 4 files changed, 143 insertions(+), 15 deletions(-) diff --git a/gst/gst.c b/gst/gst.c index cf27a6662d..adf22396be 100644 --- a/gst/gst.c +++ b/gst/gst.c @@ -747,6 +747,7 @@ init_post (GOptionContext * context, GOptionGroup * group, gpointer data, g_type_class_ref (gst_parse_flags_get_type ()); g_type_class_ref (gst_search_mode_get_type ()); g_type_class_ref (gst_progress_type_get_type ()); + g_type_class_ref (gst_caps_intersect_mode_get_type ()); gst_structure_get_type (); _gst_value_initialize (); @@ -1112,6 +1113,7 @@ gst_deinit (void) g_type_class_unref (g_type_class_peek (gst_parse_error_get_type ())); g_type_class_unref (g_type_class_peek (gst_param_spec_fraction_get_type ())); g_type_class_unref (g_type_class_peek (gst_progress_type_get_type ())); + g_type_class_unref (g_type_class_peek (gst_caps_intersect_mode_get_type ())); gst_deinitialized = TRUE; GST_INFO ("deinitialized GStreamer"); diff --git a/gst/gstcaps.c b/gst/gstcaps.c index 0ac7a7e100..5d8912c4d3 100644 --- a/gst/gstcaps.c +++ b/gst/gstcaps.c @@ -1416,18 +1416,8 @@ gst_caps_can_intersect (const GstCaps * caps1, const GstCaps * caps2) return FALSE; } -/** - * gst_caps_intersect: - * @caps1: a #GstCaps to intersect - * @caps2: a #GstCaps to intersect - * - * Creates a new #GstCaps that contains all the formats that are common - * to both @caps1 and @caps2. - * - * Returns: the new #GstCaps - */ -GstCaps * -gst_caps_intersect (const GstCaps * caps1, const GstCaps * caps2) +static GstCaps * +gst_caps_intersect_zig_zag (const GstCaps * caps1, const GstCaps * caps2) { guint64 i; /* index can be up to 2 * G_MAX_UINT */ guint j, k, len1, len2; @@ -1437,9 +1427,6 @@ gst_caps_intersect (const GstCaps * caps1, const GstCaps * caps2) GstCaps *dest; GstStructure *istruct; - g_return_val_if_fail (GST_IS_CAPS (caps1), NULL); - g_return_val_if_fail (GST_IS_CAPS (caps2), NULL); - /* caps are exactly the same pointers, just copy one caps */ if (G_UNLIKELY (caps1 == caps2)) return gst_caps_copy (caps1); @@ -1500,6 +1487,109 @@ gst_caps_intersect (const GstCaps * caps1, const GstCaps * caps2) return dest; } +/** + * gst_caps_intersect_first: + * @caps1: a #GstCaps to intersect + * @caps2: a #GstCaps to intersect + * + * Creates a new #GstCaps that contains all the formats that are common + * to both @caps1 and @caps2. + * + * Unlike @gst_caps_intersect, the returned caps will be ordered in a similar + * fashion as @caps1. + * + * Returns: the new #GstCaps + */ +static GstCaps * +gst_caps_intersect_first (const GstCaps * caps1, const GstCaps * caps2) +{ + guint64 i; /* index can be up to 2 * G_MAX_UINT */ + guint j, len1, len2; + + GstStructure *struct1; + GstStructure *struct2; + GstCaps *dest; + GstStructure *istruct; + + /* caps are exactly the same pointers, just copy one caps */ + if (G_UNLIKELY (caps1 == caps2)) + return gst_caps_copy (caps1); + + /* empty caps on either side, return empty */ + if (G_UNLIKELY (CAPS_IS_EMPTY (caps1) || CAPS_IS_EMPTY (caps2))) + return gst_caps_new_empty (); + + /* one of the caps is any, just copy the other caps */ + if (G_UNLIKELY (CAPS_IS_ANY (caps1))) + return gst_caps_copy (caps2); + if (G_UNLIKELY (CAPS_IS_ANY (caps2))) + return gst_caps_copy (caps1); + + dest = gst_caps_new_empty (); + + len1 = caps1->structs->len; + len2 = caps2->structs->len; + for (i = 0; i < len1; i++) { + struct1 = gst_caps_get_structure_unchecked (caps1, i); + for (j = 0; j < len2; j++) { + struct2 = gst_caps_get_structure_unchecked (caps2, j); + istruct = gst_caps_structure_intersect (struct1, struct2); + if (istruct) + gst_caps_append_structure (dest, istruct); + } + } + + return dest; +} + +/** + * gst_caps_intersect_full: + * @caps1: a #GstCaps to intersect + * @caps2: a #GstCaps to intersect + * @mode: The intersection algorithm/mode to use + * + * Creates a new #GstCaps that contains all the formats that are common + * to both @caps1 and @caps2, the order is defined by the #GstCapsIntersectMode + * used. + * + * Returns: the new #GstCaps + * Since: 0.10.33 + */ +GstCaps * +gst_caps_intersect_full (const GstCaps * caps1, const GstCaps * caps2, + GstCapsIntersectMode mode) +{ + g_return_val_if_fail (GST_IS_CAPS (caps1), NULL); + g_return_val_if_fail (GST_IS_CAPS (caps2), NULL); + + switch (mode) { + case GST_CAPS_INTERSECT_FIRST: + return gst_caps_intersect_first (caps1, caps2); + default: + g_warning ("Unknown caps intersect mode: %d", mode); + /* fallthrough */ + case GST_CAPS_INTERSECT_ZIG_ZAG: + return gst_caps_intersect_zig_zag (caps1, caps2); + } +} + +/** + * gst_caps_intersect: + * @caps1: a #GstCaps to intersect + * @caps2: a #GstCaps to intersect + * + * Creates a new #GstCaps that contains all the formats that are common + * to both @caps1 and @caps2. Defaults to %GST_CAPS_INTERSECT_ZIG_ZAG mode. + * + * Returns: the new #GstCaps + */ +GstCaps * +gst_caps_intersect (const GstCaps * caps1, const GstCaps * caps2) +{ + return gst_caps_intersect_full (caps1, caps2, GST_CAPS_INTERSECT_ZIG_ZAG); +} + + /* subtract operation */ typedef struct diff --git a/gst/gstcaps.h b/gst/gstcaps.h index 47d10326d6..398fa3fcbf 100644 --- a/gst/gstcaps.h +++ b/gst/gstcaps.h @@ -43,6 +43,37 @@ typedef enum { GST_CAPS_FLAGS_ANY = (1 << 0) } GstCapsFlags; +/** + * GstCapsIntersectMode: + * @GST_CAPS_INTERSECT_ZIG_ZAG : Zig-zags over both caps. + * @GST_CAPS_INTERSECT_FIRST : Keeps the first caps order. + * + * Modes of caps intersection + * + * #GST_CAPS_INTERSECT_ZIG_ZAG tries to preserve overall order of both caps + * by iterating on the caps' structures as the following matrix shows: + * caps1 + * +------------- + * | 1 2 4 7 + * caps2 | 3 5 8 10 + * | 6 9 11 12 + * + * Used when there is no explicit precedence of one caps over the other. e.g. + * tee's sink pad getcaps function, it will probe its src pad peers' for their + * caps and intersect them with this mode. + * + * #GST_CAPS_INTERSECT_FIRST is useful when an element wants to preserve + * another element's caps priority order when intersecting with its own caps. + * Example: If caps1 is [A, B, C] and caps2 is [E, B, D, A], the result + * would be [A, B], maintaining the first caps priority on the intersection. + * + * Since: 0.10.33 + */ +typedef enum { + GST_CAPS_INTERSECT_ZIG_ZAG = 0, + GST_CAPS_INTERSECT_FIRST = 1 +} GstCapsIntersectMode; + /** * GST_CAPS_ANY: * @@ -237,6 +268,9 @@ gboolean gst_caps_can_intersect (const GstCaps * caps1, /* operations */ GstCaps * gst_caps_intersect (const GstCaps *caps1, const GstCaps *caps2); +GstCaps * gst_caps_intersect_full (const GstCaps *caps1, + const GstCaps *caps2, + GstCapsIntersectMode mode); GstCaps * gst_caps_subtract (const GstCaps *minuend, const GstCaps *subtrahend); GstCaps * gst_caps_union (const GstCaps *caps1, diff --git a/win32/common/libgstreamer.def b/win32/common/libgstreamer.def index a679ce5269..c6da075d50 100644 --- a/win32/common/libgstreamer.def +++ b/win32/common/libgstreamer.def @@ -162,6 +162,8 @@ EXPORTS gst_caps_get_structure gst_caps_get_type gst_caps_intersect + gst_caps_intersect_full + gst_caps_intersect_mode_get_type gst_caps_is_always_compatible gst_caps_is_any gst_caps_is_empty From 0e1a56146728563e84e95521c856425bebf78506 Mon Sep 17 00:00:00 2001 From: Thiago Santos Date: Fri, 25 Feb 2011 10:25:26 -0300 Subject: [PATCH 21/34] tests: caps: Tests for the new caps intersection mode Adds test cases for the caps 'first' intersect mode Adds another test for the 'zigzag' mode Fixes #617045 --- tests/check/gst/gstcaps.c | 87 +++++++++++++++++++++++++++++++++++++++ 1 file changed, 87 insertions(+) diff --git a/tests/check/gst/gstcaps.c b/tests/check/gst/gstcaps.c index d1bbe4bedc..fa160d91dd 100644 --- a/tests/check/gst/gstcaps.c +++ b/tests/check/gst/gstcaps.c @@ -728,6 +728,90 @@ GST_START_TEST (test_intersect2) GST_END_TEST; + +GST_START_TEST (test_intersect_zigzag) +{ + GstCaps *caps1, *caps2, *icaps, *result; + + /* tests if caps order is maintained */ + caps1 = gst_caps_from_string ("format/A; format/B; format/C; format/D"); + caps2 = gst_caps_from_string ("format/D; format/A; format/B; format/C"); + + icaps = gst_caps_intersect_full (caps1, caps2, GST_CAPS_INTERSECT_ZIG_ZAG); + result = gst_caps_from_string ("format/B; format/A; format/D; format/C"); + GST_LOG ("intersected caps: %" GST_PTR_FORMAT, icaps); + fail_if (gst_caps_is_empty (icaps)); + fail_unless (gst_caps_is_equal (icaps, result)); + gst_caps_unref (icaps); + gst_caps_unref (result); + + icaps = gst_caps_intersect_full (caps2, caps1, GST_CAPS_INTERSECT_FIRST); + result = gst_caps_from_string ("format/A; format/B; format/D; format/C"); + GST_LOG ("intersected caps: %" GST_PTR_FORMAT, icaps); + fail_if (gst_caps_is_empty (icaps)); + fail_unless (gst_caps_is_equal (icaps, result)); + gst_caps_unref (icaps); + gst_caps_unref (result); + + gst_caps_unref (caps1); + gst_caps_unref (caps2); +} + +GST_END_TEST; + + +GST_START_TEST (test_intersect_first) +{ + GstCaps *caps1, *caps2, *icaps, *result; + + /* tests if caps order is maintained */ + caps1 = gst_caps_from_string ("format/A; format/B; format/C; format/D"); + caps2 = gst_caps_from_string ("format/C; format/D; format/A"); + icaps = gst_caps_intersect_full (caps1, caps2, GST_CAPS_INTERSECT_FIRST); + result = gst_caps_from_string ("format/A; format/C; format/D"); + GST_LOG ("intersected caps: %" GST_PTR_FORMAT, icaps); + fail_if (gst_caps_is_empty (icaps)); + fail_unless (gst_caps_is_equal (icaps, result)); + gst_caps_unref (caps1); + gst_caps_unref (caps2); + gst_caps_unref (icaps); + gst_caps_unref (result); +} + +GST_END_TEST; + + +GST_START_TEST (test_intersect_first2) +{ + GstCaps *caps1, *caps2, *icaps, *result; + + /* tests if caps order is maintained */ + caps1 = gst_caps_from_string ("format/A; format/B; format/C; format/D"); + caps2 = gst_caps_from_string ("format/D; format/A; format/B; format/C"); + + icaps = gst_caps_intersect_full (caps1, caps2, GST_CAPS_INTERSECT_FIRST); + result = gst_caps_from_string ("format/A; format/B; format/C; format/D"); + GST_LOG ("intersected caps: %" GST_PTR_FORMAT, icaps); + fail_if (gst_caps_is_empty (icaps)); + fail_unless (gst_caps_is_equal (icaps, result)); + gst_caps_unref (icaps); + gst_caps_unref (result); + + icaps = gst_caps_intersect_full (caps2, caps1, GST_CAPS_INTERSECT_FIRST); + result = gst_caps_from_string ("format/D; format/A; format/B; format/C"); + GST_LOG ("intersected caps: %" GST_PTR_FORMAT, icaps); + fail_if (gst_caps_is_empty (icaps)); + fail_unless (gst_caps_is_equal (icaps, result)); + gst_caps_unref (icaps); + gst_caps_unref (result); + + gst_caps_unref (caps1); + gst_caps_unref (caps2); +} + +GST_END_TEST; + + static gboolean _caps_is_fixed_foreach (GQuark field_id, const GValue * value, gpointer unused) { @@ -834,6 +918,9 @@ gst_caps_suite (void) tcase_add_test (tc_chain, test_merge_subset); tcase_add_test (tc_chain, test_intersect); tcase_add_test (tc_chain, test_intersect2); + tcase_add_test (tc_chain, test_intersect_zigzag); + tcase_add_test (tc_chain, test_intersect_first); + tcase_add_test (tc_chain, test_intersect_first2); tcase_add_test (tc_chain, test_normalize); tcase_add_test (tc_chain, test_broken); From 0f0a62f316aff3a135ca4bcfe98964f1d053be73 Mon Sep 17 00:00:00 2001 From: Edward Hervey Date: Mon, 19 Apr 2010 20:40:56 +0200 Subject: [PATCH 22/34] basetransform: Retain caps order when getting caps If the element gave us caps in a specific order, let's retain that by intersecting against the template but retaining the order given by the element. https://bugzilla.gnome.org/show_bug.cgi?id=617045 --- libs/gst/base/gstbasetransform.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/libs/gst/base/gstbasetransform.c b/libs/gst/base/gstbasetransform.c index db4f963109..76fec60465 100644 --- a/libs/gst/base/gstbasetransform.c +++ b/libs/gst/base/gstbasetransform.c @@ -686,7 +686,8 @@ gst_base_transform_getcaps (GstPad * pad) /* and filter against the template of this pad */ templ = gst_pad_get_pad_template_caps (pad); GST_DEBUG_OBJECT (pad, "our template %" GST_PTR_FORMAT, templ); - temp = gst_caps_intersect (caps, templ); + /* We keep the caps sorted like the returned caps */ + temp = gst_caps_intersect_full (caps, templ, GST_CAPS_INTERSECT_FIRST); GST_DEBUG_OBJECT (pad, "intersected %" GST_PTR_FORMAT, temp); gst_caps_unref (caps); /* this is what we can do */ From d979eb3e9e8590da66f8948273ba276e700b97fc Mon Sep 17 00:00:00 2001 From: Edward Hervey Date: Mon, 19 Apr 2010 20:39:53 +0200 Subject: [PATCH 23/34] basesrc: Keep downstream caps order when fixating This allows use to use the first intersecting format prefered by downstream. https://bugzilla.gnome.org/show_bug.cgi?id=617045 --- libs/gst/base/gstbasesrc.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/libs/gst/base/gstbasesrc.c b/libs/gst/base/gstbasesrc.c index c4502236b6..f67335554c 100644 --- a/libs/gst/base/gstbasesrc.c +++ b/libs/gst/base/gstbasesrc.c @@ -2614,7 +2614,7 @@ gst_base_src_default_negotiate (GstBaseSrc * basesrc) GST_DEBUG_OBJECT (basesrc, "caps of peer: %" GST_PTR_FORMAT, peercaps); if (peercaps) { /* get intersection */ - caps = gst_caps_intersect (thiscaps, peercaps); + caps = gst_caps_intersect_full (peercaps, thiscaps, GST_CAPS_INTERSECT_FIRST); GST_DEBUG_OBJECT (basesrc, "intersect: %" GST_PTR_FORMAT, caps); gst_caps_unref (peercaps); } else { From 3e475c4d338fe454cbfd35aad891ab3f7099891f Mon Sep 17 00:00:00 2001 From: Stefan Kost Date: Wed, 23 Mar 2011 17:13:58 +0200 Subject: [PATCH 24/34] docs: do xrefs for non installed books too Get the xrefs from the builddir for the books in the same packages. This fixes the cross references if one does not have the docs already installed. --- docs/libs/Makefile.am | 3 ++- docs/plugins/Makefile.am | 4 +++- 2 files changed, 5 insertions(+), 2 deletions(-) diff --git a/docs/libs/Makefile.am b/docs/libs/Makefile.am index 4172285e7c..2cda7f51c5 100644 --- a/docs/libs/Makefile.am +++ b/docs/libs/Makefile.am @@ -54,7 +54,8 @@ SCAN_OPTIONS=--deprecated-guards="GST_DISABLE_DEPRECATED" MKDB_OPTIONS=--sgml-mode --output-format=xml # Extra options to supply to gtkdoc-fixref. -FIXXREF_OPTIONS=--extra-dir=$(GLIB_PREFIX)/share/gtk-doc/html \ +FIXXREF_OPTIONS=--extra-dir=$(top_builddir)/docs/gst/html \ + --extra-dir=$(GLIB_PREFIX)/share/gtk-doc/html \ --extra-dir=$(datadir)/gtk-doc/html # Used for dependencies. diff --git a/docs/plugins/Makefile.am b/docs/plugins/Makefile.am index 0e44c57f2a..9fa051f680 100644 --- a/docs/plugins/Makefile.am +++ b/docs/plugins/Makefile.am @@ -52,7 +52,9 @@ SCAN_OPTIONS= MKDB_OPTIONS=--sgml-mode # Extra options to supply to gtkdoc-fixref. -FIXXREF_OPTIONS=--extra-dir=$(GLIB_PREFIX)/share/gtk-doc/html \ +FIXXREF_OPTIONS=--extra-dir=$(top_builddir)/docs/gst/html \ + --extra-dir=$(top_builddir)/docs/libs/html \ + --extra-dir=$(GLIB_PREFIX)/share/gtk-doc/html \ --extra-dir=$(datadir)/gtk-doc/html # Used for dependencies. From 71dcd52cc0e4dc312e9995a7f4b4ee70510a2632 Mon Sep 17 00:00:00 2001 From: Stefan Kost Date: Wed, 23 Mar 2011 16:42:24 +0200 Subject: [PATCH 25/34] basesink: print flow return as a name in debug log --- libs/gst/base/gstbasesink.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/libs/gst/base/gstbasesink.c b/libs/gst/base/gstbasesink.c index 040c25f82c..01900eda57 100644 --- a/libs/gst/base/gstbasesink.c +++ b/libs/gst/base/gstbasesink.c @@ -2343,7 +2343,7 @@ gst_base_sink_do_preroll (GstBaseSink * sink, GstMiniObject * obj) /* ERRORS */ preroll_failed: { - GST_DEBUG_OBJECT (sink, "preroll failed %d", ret); + GST_DEBUG_OBJECT (sink, "preroll failed: %s", gst_flow_get_name (ret)); return ret; } } From 02eda0e3d9cb559ddeffe4babc38158fdc662f6b Mon Sep 17 00:00:00 2001 From: Stefan Kost Date: Thu, 24 Mar 2011 13:22:57 +0200 Subject: [PATCH 26/34] docs: cleanup and xref fixes Deal with the hints from gtk-doc and fix the xrefs. Apply a work-around for () precedence over @. Move "MT Safe" text to doc body in many places. Trim eol whitespaces. --- libs/gst/base/gstbasesrc.c | 4 +- libs/gst/base/gstbasesrc.h | 4 +- libs/gst/base/gstbasetransform.h | 3 +- libs/gst/base/gstcollectpads.c | 78 ++++++++++++++++---------------- 4 files changed, 45 insertions(+), 44 deletions(-) diff --git a/libs/gst/base/gstbasesrc.c b/libs/gst/base/gstbasesrc.c index f67335554c..dc97580b27 100644 --- a/libs/gst/base/gstbasesrc.c +++ b/libs/gst/base/gstbasesrc.c @@ -59,7 +59,7 @@ * #GstBaseSrcClass.is_seekable() returns %TRUE. * * - * #GstBaseSrc:Class.query() can convert all supported seek formats to the + * #GstBaseSrcClass.query() can convert all supported seek formats to the * internal format as set with gst_base_src_set_format(). * * @@ -565,7 +565,7 @@ gst_base_src_is_live (GstBaseSrc * src) * for sending NEW_SEGMENT events and for performing seeks. * * If a format of GST_FORMAT_BYTES is set, the element will be able to - * operate in pull mode if the #GstBaseSrc.is_seekable() returns TRUE. + * operate in pull mode if the #GstBaseSrcClass.is_seekable() returns TRUE. * * This function must only be called in states < %GST_STATE_PAUSED. * diff --git a/libs/gst/base/gstbasesrc.h b/libs/gst/base/gstbasesrc.h index 9715972052..2a3caecdbb 100644 --- a/libs/gst/base/gstbasesrc.h +++ b/libs/gst/base/gstbasesrc.h @@ -133,8 +133,8 @@ struct _GstBaseSrc { * @unlock: Unlock any pending access to the resource. Subclasses should * unblock any blocked function ASAP. In particular, any create() function in * progress should be unblocked and should return GST_FLOW_WRONG_STATE. Any - * future create() function call should also return GST_FLOW_WRONG_STATE - * until the unlock_stop() function has been called. + * future @create() function call should also return GST_FLOW_WRONG_STATE + * until the @unlock_stop() function has been called. * @unlock_stop: Clear the previous unlock request. Subclasses should clear * any state they set during unlock(), such as clearing command queues. * @event: Override this to implement custom event handling. diff --git a/libs/gst/base/gstbasetransform.h b/libs/gst/base/gstbasetransform.h index 33f971baa6..72c2b2a9de 100644 --- a/libs/gst/base/gstbasetransform.h +++ b/libs/gst/base/gstbasetransform.h @@ -143,6 +143,7 @@ struct _GstBaseTransform { /** * GstBaseTransformClass: + * @parent_class: Element parent class * @transform_caps: Optional. Given the pad in this direction and the given * caps, what caps are allowed on the other pad in this * element ? @@ -170,7 +171,7 @@ struct _GstBaseTransform { * Transform the incoming buffer in-place. * @event: Optional. * Event handler on the sink pad. This function should return - * TRUE if the base class should forward the event. + * TRUE if the base class should forward the event. * @src_event: Optional. * Event handler on the source pad. * @passthrough_on_same_caps: If set to TRUE, passthrough mode will be diff --git a/libs/gst/base/gstcollectpads.c b/libs/gst/base/gstcollectpads.c index 8d0aa14d96..004508d321 100644 --- a/libs/gst/base/gstcollectpads.c +++ b/libs/gst/base/gstcollectpads.c @@ -28,7 +28,7 @@ * * * Collectpads are created with gst_collect_pads_new(). A callback should then - * be installed with gst_collect_pads_set_function (). + * be installed with gst_collect_pads_set_function (). * * * Pads are added to the collection with gst_collect_pads_add_pad()/ @@ -52,7 +52,7 @@ * event itself. * * - * Data can also be dequeued in byte units using the gst_collect_pads_available(), + * Data can also be dequeued in byte units using the gst_collect_pads_available(), * gst_collect_pads_read() and gst_collect_pads_flush() calls. * * @@ -166,9 +166,9 @@ gst_collect_pads_finalize (GObject * object) * * Create a new instance of #GstCollectPads. * - * Returns: (transfer full): a new #GstCollectPads, or NULL in case of an error. - * * MT safe. + * + * Returns: (transfer full): a new #GstCollectPads, or NULL in case of an error. */ GstCollectPads * gst_collect_pads_new (void) @@ -262,10 +262,10 @@ unref_data (GstCollectData * data) * This function calls gst_collect_pads_add_pad_full() passing a value of NULL * for destroy_notify. * + * MT safe. + * * Returns: a new #GstCollectData to identify the new pad. Or NULL * if wrong parameters are supplied. - * - * MT safe. */ GstCollectData * gst_collect_pads_add_pad (GstCollectPads * pads, GstPad * pad, guint size) @@ -297,12 +297,12 @@ gst_collect_pads_add_pad (GstCollectPads * pads, GstPad * pad, guint size) * The pad will be automatically activated in push mode when @pads is * started. * + * MT safe. + * * Since: 0.10.12 * * Returns: a new #GstCollectData to identify the new pad. Or NULL * if wrong parameters are supplied. - * - * MT safe. */ GstCollectData * gst_collect_pads_add_pad_full (GstCollectPads * pads, GstPad * pad, guint size, @@ -365,7 +365,7 @@ find_pad (GstCollectData * data, GstPad * pad) * @user_data: (closure): user data to pass to @clip_func * * Install a clipping function that is called right after a buffer is received - * on a pad managed by @pads. See #GstCollectDataClipFunction for more info. + * on a pad managed by @pads. See #GstCollectPadsClipFunction for more info. * * Since: 0.10.26 */ @@ -390,14 +390,14 @@ gst_collect_pads_set_clip_function (GstCollectPads * pads, * @pad: (transfer none): the pad to remove * * Remove a pad from the collection of collect pads. This function will also - * free the #GstCollectData and all the resources that were allocated with + * free the #GstCollectData and all the resources that were allocated with * gst_collect_pads_add_pad(). * * The pad will be deactivated automatically when @pads is stopped. * - * Returns: %TRUE if the pad could be removed. - * * MT safe. + * + * Returns: %TRUE if the pad could be removed. */ gboolean gst_collect_pads_remove_pad (GstCollectPads * pads, GstPad * pad) @@ -480,9 +480,9 @@ unknown_pad: * * This function is currently not implemented. * - * Returns: %TRUE if the pad is active. - * * MT safe. + * + * Returns: %TRUE if the pad is active. */ gboolean gst_collect_pads_is_active (GstCollectPads * pads, GstPad * pad) @@ -502,13 +502,13 @@ gst_collect_pads_is_active (GstCollectPads * pads, GstPad * pad) * @pads: the collectspads to use * * Collect data on all pads. This function is usually called - * from a #GstTask function in an element. + * from a #GstTask function in an element. * * This function is currently not implemented. * - * Returns: #GstFlowReturn of the operation. - * * MT safe. + * + * Returns: #GstFlowReturn of the operation. */ GstFlowReturn gst_collect_pads_collect (GstCollectPads * pads) @@ -528,13 +528,13 @@ gst_collect_pads_collect (GstCollectPads * pads) * @length: the length to collect * * Collect data with @offset and @length on all pads. This function - * is typically called in the getrange function of an element. + * is typically called in the getrange function of an element. * * This function is currently not implemented. * - * Returns: #GstFlowReturn of the operation. - * * MT safe. + * + * Returns: #GstFlowReturn of the operation. */ GstFlowReturn gst_collect_pads_collect_range (GstCollectPads * pads, guint64 offset, @@ -607,7 +607,7 @@ gst_collect_pads_set_flushing_unlocked (GstCollectPads * pads, } } /* Setting the pads to flushing means that we changed the values which - * are 'protected' by the cookie. We therefore update it to force a + * are 'protected' by the cookie. We therefore update it to force a * recalculation of the current pad status. */ pads->abidata.ABI.pad_cookie++; } @@ -741,10 +741,10 @@ gst_collect_pads_stop (GstCollectPads * pads) * should be called with the @pads LOCK held, such as in the callback * handler. * + * MT safe. + * * Returns: (transfer full): The buffer in @data or NULL if no buffer is queued. * should unref the buffer after usage. - * - * MT safe. */ GstBuffer * gst_collect_pads_peek (GstCollectPads * pads, GstCollectData * data) @@ -775,10 +775,10 @@ gst_collect_pads_peek (GstCollectPads * pads, GstCollectData * data) * * Free-function: gst_buffer_unref * + * MT safe. + * * Returns: (transfer full): The buffer in @data or NULL if no buffer was * queued. You should unref the buffer after usage. - * - * MT safe. */ GstBuffer * gst_collect_pads_pop (GstCollectPads * pads, GstCollectData * data) @@ -826,10 +826,10 @@ gst_collect_pads_clear (GstCollectPads * pads, GstCollectData * data) * This function should be called with @pads LOCK held, such as * in the callback. * + * MT safe. + * * Returns: The maximum number of bytes queued on all pads. This function * returns 0 if a pad has no queued buffer. - * - * MT safe. */ /* FIXME, we can do this in the _chain functions */ guint @@ -894,11 +894,11 @@ not_filled: * This function should be called with @pads LOCK held, such as * in the callback. * + * MT safe. + * * Returns: The number of bytes available for consumption in the * memory pointed to by @bytes. This can be less than @size and * is 0 if the pad is end-of-stream. - * - * MT safe. */ guint gst_collect_pads_read (GstCollectPads * pads, GstCollectData * data, @@ -939,9 +939,9 @@ gst_collect_pads_read (GstCollectPads * pads, GstCollectData * data, * that requested. A return of NULL signals that the pad is end-of-stream. * Unref the buffer with gst_buffer_unref() after use. * - * Since: 0.10.18 - * * MT safe. + * + * Since: 0.10.18 */ GstBuffer * gst_collect_pads_read_buffer (GstCollectPads * pads, GstCollectData * data, @@ -981,13 +981,13 @@ gst_collect_pads_read_buffer (GstCollectPads * pads, GstCollectData * data, * * Free-function: gst_buffer_unref * + * MT safe. + * * Returns: (transfer full): a #GstBuffer. The size of the buffer can be less * that requested. A return of NULL signals that the pad is end-of-stream. * Unref the buffer after use. * * Since: 0.10.18 - * - * MT safe. */ GstBuffer * gst_collect_pads_take_buffer (GstCollectPads * pads, GstCollectData * data, @@ -1012,10 +1012,10 @@ gst_collect_pads_take_buffer (GstCollectPads * pads, GstCollectData * data, * This function should be called with @pads LOCK held, such as * in the callback. * + * MT safe. + * * Returns: The number of bytes flushed. This can be less than @size and * is 0 if the pad was end-of-stream. - * - * MT safe. */ guint gst_collect_pads_flush (GstCollectPads * pads, GstCollectData * data, @@ -1186,7 +1186,7 @@ gst_collect_pads_event (GstPad * pad, GstEvent * event) gst_pad_event_default (pad, event); /* now unblock the chain function. - * no cond per pad, so they all unblock, + * no cond per pad, so they all unblock, * non-flushing block again */ GST_OBJECT_LOCK (pads); data->abidata.ABI.flushing = TRUE; @@ -1260,7 +1260,7 @@ gst_collect_pads_event (GstPad * pad, GstEvent * event) data->abidata.ABI.new_segment = TRUE; - /* we must not forward this event since multiple segments will be + /* we must not forward this event since multiple segments will be * accumulated and this is certainly not what we want. */ gst_event_unref (event); /* FIXME: collect-pads based elements need to create their own newsegment @@ -1302,7 +1302,7 @@ pad_removed: * and if so we call the collected function. When this is done we check if * data has been unqueued. If data is still queued we wait holding the stream * lock to make sure no EOS event can happen while we are ready to be - * collected + * collected */ static GstFlowReturn gst_collect_pads_chain (GstPad * pad, GstBuffer * buffer) @@ -1392,7 +1392,7 @@ gst_collect_pads_chain (GstPad * pad, GstBuffer * buffer) /* wait to be collected, this must happen from another thread triggered * by the _chain function of another pad. We release the lock so we * can get stopped or flushed as well. We can however not get EOS - * because we still hold the STREAM_LOCK. + * because we still hold the STREAM_LOCK. */ GST_COLLECT_PADS_WAIT (pads); From 1177a968cca55222479fdce6aa39fe9b7ecaa864 Mon Sep 17 00:00:00 2001 From: Stefan Kost Date: Thu, 24 Mar 2011 18:25:08 +0200 Subject: [PATCH 27/34] queue2: set max value for to the matching one for the datatype The property is guint64, so use G_MAXUINT64 instead of G_MAXUINT. --- plugins/elements/gstqueue2.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/plugins/elements/gstqueue2.c b/plugins/elements/gstqueue2.c index ab55cbbc22..9c8c838c58 100644 --- a/plugins/elements/gstqueue2.c +++ b/plugins/elements/gstqueue2.c @@ -369,7 +369,7 @@ gst_queue2_class_init (GstQueue2Class * klass) g_param_spec_uint64 ("ring-buffer-max-size", "Max. ring buffer size (bytes)", "Max. amount of data in the ring buffer (bytes, 0 = disabled", - 0, G_MAXUINT, DEFAULT_RING_BUFFER_MAX_SIZE, + 0, G_MAXUINT64, DEFAULT_RING_BUFFER_MAX_SIZE, G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS)); /* set several parent class virtual functions */ @@ -766,7 +766,7 @@ apply_buffer (GstQueue2 * queue, GstBuffer * buffer, GstSegment * segment, timestamp = GST_BUFFER_TIMESTAMP (buffer); duration = GST_BUFFER_DURATION (buffer); - /* if no timestamp is set, assume it's continuous with the previous + /* if no timestamp is set, assume it's continuous with the previous * time */ if (timestamp == GST_CLOCK_TIME_NONE) timestamp = segment->last_stop; From 84eafff61b7e2d086439cc63365909a1c4ea6cd5 Mon Sep 17 00:00:00 2001 From: Stefan Kost Date: Thu, 24 Mar 2011 18:27:09 +0200 Subject: [PATCH 28/34] docs: fix some gtk-doc warnings Document the queue leaky enums. --- docs/plugins/gstreamer-plugins-sections.txt | 1 + plugins/elements/gstqueue.h | 25 ++++++++++++++------- 2 files changed, 18 insertions(+), 8 deletions(-) diff --git a/docs/plugins/gstreamer-plugins-sections.txt b/docs/plugins/gstreamer-plugins-sections.txt index 1854112140..742fdf9dad 100644 --- a/docs/plugins/gstreamer-plugins-sections.txt +++ b/docs/plugins/gstreamer-plugins-sections.txt @@ -149,6 +149,7 @@ GST_INPUT_SELECTOR_WAIT element-queue queue GstQueue +GstQueueLeaky GstQueueClass GST_QUEUE diff --git a/plugins/elements/gstqueue.h b/plugins/elements/gstqueue.h index c72bcb790c..6ab861706f 100644 --- a/plugins/elements/gstqueue.h +++ b/plugins/elements/gstqueue.h @@ -39,17 +39,26 @@ G_BEGIN_DECLS #define GST_IS_QUEUE_CLASS(klass) \ (G_TYPE_CHECK_CLASS_TYPE((klass),GST_TYPE_QUEUE)) -enum { +typedef struct _GstQueue GstQueue; +typedef struct _GstQueueSize GstQueueSize; +typedef enum _GstQueueLeaky GstQueueLeaky; +typedef struct _GstQueueClass GstQueueClass; + +/** + * GstQueueLeaky: + * @GST_QUEUE_NO_LEAK: Not Leaky + * @GST_QUEUE_LEAK_UPSTREAM: Leaky on upstream (new buffers) + * @GST_QUEUE_LEAK_DOWNSTREAM: Leaky on downstream (old buffers) + * + * Buffer dropping scheme to avoid the queue to block when full. + */ +enum _GstQueueLeaky { GST_QUEUE_NO_LEAK = 0, GST_QUEUE_LEAK_UPSTREAM = 1, GST_QUEUE_LEAK_DOWNSTREAM = 2 }; -typedef struct _GstQueue GstQueue; -typedef struct _GstQueueSize GstQueueSize; -typedef struct _GstQueueClass GstQueueClass; - -/** +/* * GstQueueSize: * @buffers: number of buffers * @bytes: number of bytes @@ -115,8 +124,8 @@ struct _GstQueue { gboolean head_needs_discont, tail_needs_discont; gboolean push_newsegment; - - gboolean silent; /* don't emit signals */ + + gboolean silent; /* don't emit signals */ /* whether the first new segment has been applied to src */ gboolean newseg_applied_to_src; From 54792a3a09a7de6273b7d2bfcc43c70b54e46689 Mon Sep 17 00:00:00 2001 From: Stefan Kost Date: Thu, 24 Mar 2011 18:48:41 +0200 Subject: [PATCH 29/34] Automatic update of common submodule From 6aec6b9 to 6aaa286 --- common | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/common b/common index 6aec6b9716..6aaa286970 160000 --- a/common +++ b/common @@ -1 +1 @@ -Subproject commit 6aec6b9716c184c60c4bc6a5916a2471cfa8c8cd +Subproject commit 6aaa286970e59ed89bd69544f2ee10551f377cb6 From fc6a47a6f64f8272f69f04a04925e0d2aeb403f5 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Sebastian=20Dr=C3=B6ge?= Date: Fri, 25 Mar 2011 08:59:37 +0100 Subject: [PATCH 30/34] Automatic update of common submodule From 6aaa286 to d8814b6 --- common | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/common b/common index 6aaa286970..d8814b6c7f 160000 --- a/common +++ b/common @@ -1 +1 @@ -Subproject commit 6aaa286970e59ed89bd69544f2ee10551f377cb6 +Subproject commit d8814b6c7fb8e037bd19bff6a2698f55ddb2b311 From 3e4a080e078450f87f9655f671d666cab435ab3d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Sebastian=20Dr=C3=B6ge?= Date: Fri, 25 Mar 2011 09:27:58 +0100 Subject: [PATCH 31/34] Automatic update of common submodule From d8814b6 to b77e2bf --- common | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/common b/common index d8814b6c7f..b77e2bfbb7 160000 --- a/common +++ b/common @@ -1 +1 @@ -Subproject commit d8814b6c7fb8e037bd19bff6a2698f55ddb2b311 +Subproject commit b77e2bfbb78e1093d39b7714572ed364e46df53c From 18db9981895c463d6b2ff7816f51a7932c065f14 Mon Sep 17 00:00:00 2001 From: Stefan Kost Date: Fri, 25 Mar 2011 14:55:39 +0200 Subject: [PATCH 32/34] Automatic update of common submodule From b77e2bf to 193b717 --- common | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/common b/common index b77e2bfbb7..193b7176e6 160000 --- a/common +++ b/common @@ -1 +1 @@ -Subproject commit b77e2bfbb78e1093d39b7714572ed364e46df53c +Subproject commit 193b7176e61160d78a967884f1b20af76d1c7379 From 33c86b93dd83f537096ada0283db34ccc4820e76 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Sebastian=20Dr=C3=B6ge?= Date: Fri, 25 Mar 2011 22:08:41 +0100 Subject: [PATCH 33/34] Automatic update of common submodule From 193b717 to 1ccbe09 --- common | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/common b/common index 193b7176e6..1ccbe098d6 160000 --- a/common +++ b/common @@ -1 +1 @@ -Subproject commit 193b7176e61160d78a967884f1b20af76d1c7379 +Subproject commit 1ccbe098d6379612fcef09f4000da23585af980a From bae67f116c2d3f6a8f6e68386cc31e6a4e0e85db Mon Sep 17 00:00:00 2001 From: Arun Raghavan Date: Mon, 28 Mar 2011 21:21:00 +0530 Subject: [PATCH 34/34] basesrc: Return FALSE if we don't handle an event basesrc's default event handler returns TRUE regardless of whether the event is handled or not. This fixes the handler to conform with the expected behaviour (which is to only return TRUE when the event has actually benn handled). gst_bin_do_latency_func() depended on this (incorrect) behaviour, and is now modified as well. (Remaining 1-liner change in gstbasesrc.c is to keep gst-indent happy) --- gst/gstbin.c | 5 +---- libs/gst/base/gstbasesrc.c | 5 +++-- 2 files changed, 4 insertions(+), 6 deletions(-) diff --git a/gst/gstbin.c b/gst/gstbin.c index 770fb56f03..73758213e9 100644 --- a/gst/gstbin.c +++ b/gst/gstbin.c @@ -2376,11 +2376,8 @@ gst_bin_do_latency_func (GstBin * bin) GST_TIME_ARGS (min_latency)); } else { GST_WARNING_OBJECT (element, - "failed to configure latency of %" GST_TIME_FORMAT, + "did not really configure latency of %" GST_TIME_FORMAT, GST_TIME_ARGS (min_latency)); - GST_ELEMENT_WARNING (element, CORE, CLOCK, (NULL), - ("Failed to configure latency of %" GST_TIME_FORMAT, - GST_TIME_ARGS (min_latency))); } } else { /* this is not a real problem, we just don't configure any latency. */ diff --git a/libs/gst/base/gstbasesrc.c b/libs/gst/base/gstbasesrc.c index dc97580b27..fb1679bdd1 100644 --- a/libs/gst/base/gstbasesrc.c +++ b/libs/gst/base/gstbasesrc.c @@ -1737,7 +1737,7 @@ gst_base_src_default_event (GstBaseSrc * src, GstEvent * event) break; } default: - result = TRUE; + result = FALSE; break; } return result; @@ -2614,7 +2614,8 @@ gst_base_src_default_negotiate (GstBaseSrc * basesrc) GST_DEBUG_OBJECT (basesrc, "caps of peer: %" GST_PTR_FORMAT, peercaps); if (peercaps) { /* get intersection */ - caps = gst_caps_intersect_full (peercaps, thiscaps, GST_CAPS_INTERSECT_FIRST); + caps = + gst_caps_intersect_full (peercaps, thiscaps, GST_CAPS_INTERSECT_FIRST); GST_DEBUG_OBJECT (basesrc, "intersect: %" GST_PTR_FORMAT, caps); gst_caps_unref (peercaps); } else {