element: Add gst_element_call_async()
[platform/upstream/gstreamer.git] / gst / gstelement.c
1 /* GStreamer
2  * Copyright (C) 1999,2000 Erik Walthinsen <omega@cse.ogi.edu>
3  *                    2004 Wim Taymans <wim@fluendo.com>
4  *
5  * gstelement.c: The base element, all elements derive from this
6  *
7  * This library is free software; you can redistribute it and/or
8  * modify it under the terms of the GNU Library General Public
9  * License as published by the Free Software Foundation; either
10  * version 2 of the License, or (at your option) any later version.
11  *
12  * This library is distributed in the hope that it will be useful,
13  * but WITHOUT ANY WARRANTY; without even the implied warranty of
14  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
15  * Library General Public License for more details.
16  *
17  * You should have received a copy of the GNU Library General Public
18  * License along with this library; if not, write to the
19  * Free Software Foundation, Inc., 51 Franklin St, Fifth Floor,
20  * Boston, MA 02110-1301, USA.
21  */
22
23 /**
24  * SECTION:gstelement
25  * @short_description: Abstract base class for all pipeline elements
26  * @see_also: #GstElementFactory, #GstPad
27  *
28  * GstElement is the abstract base class needed to construct an element that
29  * can be used in a GStreamer pipeline. Please refer to the plugin writers
30  * guide for more information on creating #GstElement subclasses.
31  *
32  * The name of a #GstElement can be get with gst_element_get_name() and set with
33  * gst_element_set_name().  For speed, GST_ELEMENT_NAME() can be used in the
34  * core when using the appropriate locking. Do not use this in plug-ins or
35  * applications in order to retain ABI compatibility.
36  *
37  * Elements can have pads (of the type #GstPad).  These pads link to pads on
38  * other elements.  #GstBuffer flow between these linked pads.
39  * A #GstElement has a #GList of #GstPad structures for all their input (or sink)
40  * and output (or source) pads.
41  * Core and plug-in writers can add and remove pads with gst_element_add_pad()
42  * and gst_element_remove_pad().
43  *
44  * An existing pad of an element can be retrieved by name with
45  * gst_element_get_static_pad(). A new dynamic pad can be created using
46  * gst_element_request_pad() with a #GstPadTemplate.
47  * An iterator of all pads can be retrieved with gst_element_iterate_pads().
48  *
49  * Elements can be linked through their pads.
50  * If the link is straightforward, use the gst_element_link()
51  * convenience function to link two elements, or gst_element_link_many()
52  * for more elements in a row.
53  * Use gst_element_link_filtered() to link two elements constrained by
54  * a specified set of #GstCaps.
55  * For finer control, use gst_element_link_pads() and
56  * gst_element_link_pads_filtered() to specify the pads to link on
57  * each element by name.
58  *
59  * Each element has a state (see #GstState).  You can get and set the state
60  * of an element with gst_element_get_state() and gst_element_set_state().
61  * Setting a state triggers a #GstStateChange. To get a string representation
62  * of a #GstState, use gst_element_state_get_name().
63  *
64  * You can get and set a #GstClock on an element using gst_element_get_clock()
65  * and gst_element_set_clock().
66  * Some elements can provide a clock for the pipeline if
67  * the #GST_ELEMENT_FLAG_PROVIDE_CLOCK flag is set. With the
68  * gst_element_provide_clock() method one can retrieve the clock provided by
69  * such an element.
70  * Not all elements require a clock to operate correctly. If the
71  * #GST_ELEMENT_FLAG_REQUIRE_CLOCK() flag is set, a clock should be set on the
72  * element with gst_element_set_clock().
73  *
74  * Note that clock selection and distribution is normally handled by the
75  * toplevel #GstPipeline so the clock functions are only to be used in very
76  * specific situations.
77  */
78
79 #include "gst_private.h"
80 #include <glib.h>
81 #include <stdarg.h>
82 #include <gobject/gvaluecollector.h>
83
84 #include "gstelement.h"
85 #include "gstelementmetadata.h"
86 #include "gstenumtypes.h"
87 #include "gstbus.h"
88 #include "gsterror.h"
89 #include "gstevent.h"
90 #include "gstutils.h"
91 #include "gstinfo.h"
92 #include "gstquark.h"
93 #include "gsttracerutils.h"
94 #include "gstvalue.h"
95 #include "gst-i18n-lib.h"
96 #include "glib-compat-private.h"
97
98 #ifndef GST_DISABLE_GST_DEBUG
99 #include "printf/printf.h"
100 #endif
101
102 /* Element signals and args */
103 enum
104 {
105   PAD_ADDED,
106   PAD_REMOVED,
107   NO_MORE_PADS,
108   /* add more above */
109   LAST_SIGNAL
110 };
111
112 enum
113 {
114   ARG_0
115       /* FILL ME */
116 };
117
118 static void gst_element_class_init (GstElementClass * klass);
119 static void gst_element_init (GstElement * element);
120 static void gst_element_base_class_init (gpointer g_class);
121 static void gst_element_base_class_finalize (gpointer g_class);
122
123 static void gst_element_constructed (GObject * object);
124 static void gst_element_dispose (GObject * object);
125 static void gst_element_finalize (GObject * object);
126
127 static GstStateChangeReturn gst_element_change_state_func (GstElement * element,
128     GstStateChange transition);
129 static GstStateChangeReturn gst_element_get_state_func (GstElement * element,
130     GstState * state, GstState * pending, GstClockTime timeout);
131 static GstStateChangeReturn gst_element_set_state_func (GstElement * element,
132     GstState state);
133 static gboolean gst_element_set_clock_func (GstElement * element,
134     GstClock * clock);
135 static void gst_element_set_bus_func (GstElement * element, GstBus * bus);
136 static gboolean gst_element_post_message_default (GstElement * element,
137     GstMessage * message);
138 static void gst_element_set_context_default (GstElement * element,
139     GstContext * context);
140
141 static gboolean gst_element_default_send_event (GstElement * element,
142     GstEvent * event);
143 static gboolean gst_element_default_query (GstElement * element,
144     GstQuery * query);
145
146 static GstPadTemplate
147     * gst_element_class_get_request_pad_template (GstElementClass *
148     element_class, const gchar * name);
149
150 static void gst_element_call_async_func (gpointer data, gpointer user_data);
151
152 static GstObjectClass *parent_class = NULL;
153 static guint gst_element_signals[LAST_SIGNAL] = { 0 };
154
155 static GThreadPool *gst_element_pool = NULL;
156
157 /* this is used in gstelementfactory.c:gst_element_register() */
158 GQuark __gst_elementclass_factory = 0;
159
160 GType
161 gst_element_get_type (void)
162 {
163   static volatile gsize gst_element_type = 0;
164
165   if (g_once_init_enter (&gst_element_type)) {
166     GType _type;
167     static const GTypeInfo element_info = {
168       sizeof (GstElementClass),
169       gst_element_base_class_init,
170       gst_element_base_class_finalize,
171       (GClassInitFunc) gst_element_class_init,
172       NULL,
173       NULL,
174       sizeof (GstElement),
175       0,
176       (GInstanceInitFunc) gst_element_init,
177       NULL
178     };
179
180     _type = g_type_register_static (GST_TYPE_OBJECT, "GstElement",
181         &element_info, G_TYPE_FLAG_ABSTRACT);
182
183     __gst_elementclass_factory =
184         g_quark_from_static_string ("GST_ELEMENTCLASS_FACTORY");
185     g_once_init_leave (&gst_element_type, _type);
186   }
187   return gst_element_type;
188 }
189
190 static void
191 gst_element_class_init (GstElementClass * klass)
192 {
193   GObjectClass *gobject_class;
194   GError *err = NULL;
195
196   gobject_class = (GObjectClass *) klass;
197
198   parent_class = g_type_class_peek_parent (klass);
199
200   /**
201    * GstElement::pad-added:
202    * @gstelement: the object which received the signal
203    * @new_pad: the pad that has been added
204    *
205    * a new #GstPad has been added to the element. Note that this signal will
206    * usually be emitted from the context of the streaming thread. Also keep in
207    * mind that if you add new elements to the pipeline in the signal handler
208    * you will need to set them to the desired target state with
209    * gst_element_set_state() or gst_element_sync_state_with_parent().
210    */
211   gst_element_signals[PAD_ADDED] =
212       g_signal_new ("pad-added", G_TYPE_FROM_CLASS (klass), G_SIGNAL_RUN_LAST,
213       G_STRUCT_OFFSET (GstElementClass, pad_added), NULL, NULL,
214       g_cclosure_marshal_generic, G_TYPE_NONE, 1, GST_TYPE_PAD);
215   /**
216    * GstElement::pad-removed:
217    * @gstelement: the object which received the signal
218    * @old_pad: the pad that has been removed
219    *
220    * a #GstPad has been removed from the element
221    */
222   gst_element_signals[PAD_REMOVED] =
223       g_signal_new ("pad-removed", G_TYPE_FROM_CLASS (klass), G_SIGNAL_RUN_LAST,
224       G_STRUCT_OFFSET (GstElementClass, pad_removed), NULL, NULL,
225       g_cclosure_marshal_generic, G_TYPE_NONE, 1, GST_TYPE_PAD);
226   /**
227    * GstElement::no-more-pads:
228    * @gstelement: the object which received the signal
229    *
230    * This signals that the element will not generate more dynamic pads.
231    * Note that this signal will usually be emitted from the context of
232    * the streaming thread.
233    */
234   gst_element_signals[NO_MORE_PADS] =
235       g_signal_new ("no-more-pads", G_TYPE_FROM_CLASS (klass),
236       G_SIGNAL_RUN_LAST, G_STRUCT_OFFSET (GstElementClass, no_more_pads), NULL,
237       NULL, g_cclosure_marshal_generic, G_TYPE_NONE, 0);
238
239   gobject_class->dispose = gst_element_dispose;
240   gobject_class->finalize = gst_element_finalize;
241   gobject_class->constructed = gst_element_constructed;
242
243   klass->change_state = GST_DEBUG_FUNCPTR (gst_element_change_state_func);
244   klass->set_state = GST_DEBUG_FUNCPTR (gst_element_set_state_func);
245   klass->get_state = GST_DEBUG_FUNCPTR (gst_element_get_state_func);
246   klass->set_clock = GST_DEBUG_FUNCPTR (gst_element_set_clock_func);
247   klass->set_bus = GST_DEBUG_FUNCPTR (gst_element_set_bus_func);
248   klass->query = GST_DEBUG_FUNCPTR (gst_element_default_query);
249   klass->send_event = GST_DEBUG_FUNCPTR (gst_element_default_send_event);
250   klass->numpadtemplates = 0;
251   klass->post_message = GST_DEBUG_FUNCPTR (gst_element_post_message_default);
252   klass->set_context = GST_DEBUG_FUNCPTR (gst_element_set_context_default);
253
254   klass->elementfactory = NULL;
255
256   GST_DEBUG ("creating element thread pool");
257   gst_element_pool =
258       g_thread_pool_new ((GFunc) gst_element_call_async_func, NULL, -1, FALSE,
259       &err);
260   if (err != NULL) {
261     g_critical ("could not alloc threadpool %s", err->message);
262     g_clear_error (&err);
263   }
264 }
265
266 static void
267 gst_element_base_class_init (gpointer g_class)
268 {
269   GstElementClass *element_class = GST_ELEMENT_CLASS (g_class);
270   GList *node, *padtemplates;
271
272   /* Copy the element details here so elements can inherit the
273    * details from their base class and classes only need to set
274    * the details in class_init instead of base_init */
275   element_class->metadata =
276       element_class->metadata ? gst_structure_copy (element_class->metadata) :
277       gst_structure_new_empty ("metadata");
278
279   /* Copy the pad templates so elements inherit them
280    * from their base class but elements can add pad templates in class_init
281    * instead of base_init.
282    */
283   padtemplates = g_list_copy (element_class->padtemplates);
284   for (node = padtemplates; node != NULL; node = node->next) {
285     GstPadTemplate *tmpl = (GstPadTemplate *) node->data;
286     gst_object_ref (tmpl);
287   }
288   element_class->padtemplates = padtemplates;
289
290   /* set the factory, see gst_element_register() */
291   element_class->elementfactory =
292       g_type_get_qdata (G_TYPE_FROM_CLASS (element_class),
293       __gst_elementclass_factory);
294   GST_CAT_DEBUG (GST_CAT_ELEMENT_PADS, "type %s : factory %p",
295       G_OBJECT_CLASS_NAME (element_class), element_class->elementfactory);
296 }
297
298 static void
299 gst_element_base_class_finalize (gpointer g_class)
300 {
301   GstElementClass *klass = GST_ELEMENT_CLASS (g_class);
302
303   g_list_foreach (klass->padtemplates, (GFunc) gst_object_unref, NULL);
304   g_list_free (klass->padtemplates);
305
306   gst_structure_free (klass->metadata);
307 }
308
309 static void
310 gst_element_init (GstElement * element)
311 {
312   GST_STATE (element) = GST_STATE_NULL;
313   GST_STATE_TARGET (element) = GST_STATE_NULL;
314   GST_STATE_NEXT (element) = GST_STATE_VOID_PENDING;
315   GST_STATE_PENDING (element) = GST_STATE_VOID_PENDING;
316   GST_STATE_RETURN (element) = GST_STATE_CHANGE_SUCCESS;
317
318   g_rec_mutex_init (&element->state_lock);
319   g_cond_init (&element->state_cond);
320 }
321
322 static void
323 gst_element_constructed (GObject * object)
324 {
325   GST_TRACER_ELEMENT_NEW (GST_ELEMENT_CAST (object));
326   G_OBJECT_CLASS (parent_class)->constructed (object);
327 }
328
329 /**
330  * gst_element_release_request_pad:
331  * @element: a #GstElement to release the request pad of.
332  * @pad: the #GstPad to release.
333  *
334  * Makes the element free the previously requested pad as obtained
335  * with gst_element_request_pad().
336  *
337  * This does not unref the pad. If the pad was created by using
338  * gst_element_request_pad(), gst_element_release_request_pad() needs to be
339  * followed by gst_object_unref() to free the @pad.
340  *
341  * MT safe.
342  */
343 void
344 gst_element_release_request_pad (GstElement * element, GstPad * pad)
345 {
346   GstElementClass *oclass;
347
348   g_return_if_fail (GST_IS_ELEMENT (element));
349   g_return_if_fail (GST_IS_PAD (pad));
350   g_return_if_fail (GST_PAD_PAD_TEMPLATE (pad) == NULL ||
351       GST_PAD_TEMPLATE_PRESENCE (GST_PAD_PAD_TEMPLATE (pad)) ==
352       GST_PAD_REQUEST);
353
354   oclass = GST_ELEMENT_GET_CLASS (element);
355
356   /* if the element implements a custom release function we call that, else we
357    * simply remove the pad from the element */
358   if (oclass->release_pad)
359     oclass->release_pad (element, pad);
360   else
361     gst_element_remove_pad (element, pad);
362 }
363
364 /**
365  * gst_element_provide_clock:
366  * @element: a #GstElement to query
367  *
368  * Get the clock provided by the given element.
369  * <note>An element is only required to provide a clock in the PAUSED
370  * state. Some elements can provide a clock in other states.</note>
371  *
372  * Returns: (transfer full) (nullable): the GstClock provided by the
373  * element or %NULL if no clock could be provided.  Unref after usage.
374  *
375  * MT safe.
376  */
377 GstClock *
378 gst_element_provide_clock (GstElement * element)
379 {
380   GstClock *result = NULL;
381   GstElementClass *oclass;
382
383   g_return_val_if_fail (GST_IS_ELEMENT (element), NULL);
384
385   oclass = GST_ELEMENT_GET_CLASS (element);
386
387   if (oclass->provide_clock)
388     result = oclass->provide_clock (element);
389
390   return result;
391 }
392
393 static gboolean
394 gst_element_set_clock_func (GstElement * element, GstClock * clock)
395 {
396   GstClock **clock_p;
397
398   GST_OBJECT_LOCK (element);
399   clock_p = &element->clock;
400   gst_object_replace ((GstObject **) clock_p, (GstObject *) clock);
401   GST_OBJECT_UNLOCK (element);
402
403   return TRUE;
404 }
405
406 /**
407  * gst_element_set_clock:
408  * @element: a #GstElement to set the clock for.
409  * @clock: the #GstClock to set for the element.
410  *
411  * Sets the clock for the element. This function increases the
412  * refcount on the clock. Any previously set clock on the object
413  * is unreffed.
414  *
415  * Returns: %TRUE if the element accepted the clock. An element can refuse a
416  * clock when it, for example, is not able to slave its internal clock to the
417  * @clock or when it requires a specific clock to operate.
418  *
419  * MT safe.
420  */
421 gboolean
422 gst_element_set_clock (GstElement * element, GstClock * clock)
423 {
424   GstElementClass *oclass;
425   gboolean res = FALSE;
426
427   g_return_val_if_fail (GST_IS_ELEMENT (element), FALSE);
428   g_return_val_if_fail (clock == NULL || GST_IS_CLOCK (clock), FALSE);
429
430   oclass = GST_ELEMENT_GET_CLASS (element);
431
432   GST_CAT_DEBUG_OBJECT (GST_CAT_CLOCK, element, "setting clock %p", clock);
433
434   if (oclass->set_clock)
435     res = oclass->set_clock (element, clock);
436
437   return res;
438 }
439
440 /**
441  * gst_element_get_clock:
442  * @element: a #GstElement to get the clock of.
443  *
444  * Gets the currently configured clock of the element. This is the clock as was
445  * last set with gst_element_set_clock().
446  *
447  * Elements in a pipeline will only have their clock set when the
448  * pipeline is in the PLAYING state.
449  *
450  * Returns: (transfer full): the #GstClock of the element. unref after usage.
451  *
452  * MT safe.
453  */
454 GstClock *
455 gst_element_get_clock (GstElement * element)
456 {
457   GstClock *result;
458
459   g_return_val_if_fail (GST_IS_ELEMENT (element), NULL);
460
461   GST_OBJECT_LOCK (element);
462   if ((result = element->clock))
463     gst_object_ref (result);
464   GST_OBJECT_UNLOCK (element);
465
466   return result;
467 }
468
469 /**
470  * gst_element_set_base_time:
471  * @element: a #GstElement.
472  * @time: the base time to set.
473  *
474  * Set the base time of an element. See gst_element_get_base_time().
475  *
476  * MT safe.
477  */
478 void
479 gst_element_set_base_time (GstElement * element, GstClockTime time)
480 {
481   GstClockTime old;
482
483   g_return_if_fail (GST_IS_ELEMENT (element));
484
485   GST_OBJECT_LOCK (element);
486   old = element->base_time;
487   element->base_time = time;
488   GST_OBJECT_UNLOCK (element);
489
490   GST_CAT_DEBUG_OBJECT (GST_CAT_CLOCK, element,
491       "set base_time=%" GST_TIME_FORMAT ", old %" GST_TIME_FORMAT,
492       GST_TIME_ARGS (time), GST_TIME_ARGS (old));
493 }
494
495 /**
496  * gst_element_get_base_time:
497  * @element: a #GstElement.
498  *
499  * Returns the base time of the element. The base time is the
500  * absolute time of the clock when this element was last put to
501  * PLAYING. Subtracting the base time from the clock time gives
502  * the running time of the element.
503  *
504  * Returns: the base time of the element.
505  *
506  * MT safe.
507  */
508 GstClockTime
509 gst_element_get_base_time (GstElement * element)
510 {
511   GstClockTime result;
512
513   g_return_val_if_fail (GST_IS_ELEMENT (element), GST_CLOCK_TIME_NONE);
514
515   GST_OBJECT_LOCK (element);
516   result = element->base_time;
517   GST_OBJECT_UNLOCK (element);
518
519   return result;
520 }
521
522 /**
523  * gst_element_set_start_time:
524  * @element: a #GstElement.
525  * @time: the base time to set.
526  *
527  * Set the start time of an element. The start time of the element is the
528  * running time of the element when it last went to the PAUSED state. In READY
529  * or after a flushing seek, it is set to 0.
530  *
531  * Toplevel elements like #GstPipeline will manage the start_time and
532  * base_time on its children. Setting the start_time to #GST_CLOCK_TIME_NONE
533  * on such a toplevel element will disable the distribution of the base_time to
534  * the children and can be useful if the application manages the base_time
535  * itself, for example if you want to synchronize capture from multiple
536  * pipelines, and you can also ensure that the pipelines have the same clock.
537  *
538  * MT safe.
539  */
540 void
541 gst_element_set_start_time (GstElement * element, GstClockTime time)
542 {
543   GstClockTime old;
544
545   g_return_if_fail (GST_IS_ELEMENT (element));
546
547   GST_OBJECT_LOCK (element);
548   old = GST_ELEMENT_START_TIME (element);
549   GST_ELEMENT_START_TIME (element) = time;
550   GST_OBJECT_UNLOCK (element);
551
552   GST_CAT_DEBUG_OBJECT (GST_CAT_CLOCK, element,
553       "set start_time=%" GST_TIME_FORMAT ", old %" GST_TIME_FORMAT,
554       GST_TIME_ARGS (time), GST_TIME_ARGS (old));
555 }
556
557 /**
558  * gst_element_get_start_time:
559  * @element: a #GstElement.
560  *
561  * Returns the start time of the element. The start time is the
562  * running time of the clock when this element was last put to PAUSED.
563  *
564  * Usually the start_time is managed by a toplevel element such as
565  * #GstPipeline.
566  *
567  * MT safe.
568  *
569  * Returns: the start time of the element.
570  */
571 GstClockTime
572 gst_element_get_start_time (GstElement * element)
573 {
574   GstClockTime result;
575
576   g_return_val_if_fail (GST_IS_ELEMENT (element), GST_CLOCK_TIME_NONE);
577
578   GST_OBJECT_LOCK (element);
579   result = GST_ELEMENT_START_TIME (element);
580   GST_OBJECT_UNLOCK (element);
581
582   return result;
583 }
584
585 #if 0
586 /**
587  * gst_element_set_index:
588  * @element: a #GstElement.
589  * @index: (transfer none): a #GstIndex.
590  *
591  * Set @index on the element. The refcount of the index
592  * will be increased, any previously set index is unreffed.
593  *
594  * MT safe.
595  */
596 void
597 gst_element_set_index (GstElement * element, GstIndex * index)
598 {
599   GstElementClass *oclass;
600
601   g_return_if_fail (GST_IS_ELEMENT (element));
602   g_return_if_fail (index == NULL || GST_IS_INDEX (index));
603
604   oclass = GST_ELEMENT_GET_CLASS (element);
605
606   if (oclass->set_index)
607     oclass->set_index (element, index);
608 }
609
610 /**
611  * gst_element_get_index:
612  * @element: a #GstElement.
613  *
614  * Gets the index from the element.
615  *
616  * Returns: (transfer full) (nullable): a #GstIndex or %NULL when no
617  * index was set on the element. unref after usage.
618  *
619  * MT safe.
620  */
621 GstIndex *
622 gst_element_get_index (GstElement * element)
623 {
624   GstElementClass *oclass;
625   GstIndex *result = NULL;
626
627   g_return_val_if_fail (GST_IS_ELEMENT (element), NULL);
628
629   oclass = GST_ELEMENT_GET_CLASS (element);
630
631   if (oclass->get_index)
632     result = oclass->get_index (element);
633
634   return result;
635 }
636 #endif
637
638 /**
639  * gst_element_add_pad:
640  * @element: a #GstElement to add the pad to.
641  * @pad: (transfer full): the #GstPad to add to the element.
642  *
643  * Adds a pad (link point) to @element. @pad's parent will be set to @element;
644  * see gst_object_set_parent() for refcounting information.
645  *
646  * Pads are not automatically activated so elements should perform the needed
647  * steps to activate the pad in case this pad is added in the PAUSED or PLAYING
648  * state. See gst_pad_set_active() for more information about activating pads.
649  *
650  * The pad and the element should be unlocked when calling this function.
651  *
652  * This function will emit the #GstElement::pad-added signal on the element.
653  *
654  * Returns: %TRUE if the pad could be added. This function can fail when
655  * a pad with the same name already existed or the pad already had another
656  * parent.
657  *
658  * MT safe.
659  */
660 gboolean
661 gst_element_add_pad (GstElement * element, GstPad * pad)
662 {
663   gchar *pad_name;
664   gboolean active;
665
666   g_return_val_if_fail (GST_IS_ELEMENT (element), FALSE);
667   g_return_val_if_fail (GST_IS_PAD (pad), FALSE);
668
669   /* locking pad to look at the name */
670   GST_OBJECT_LOCK (pad);
671   pad_name = g_strdup (GST_PAD_NAME (pad));
672   GST_CAT_INFO_OBJECT (GST_CAT_ELEMENT_PADS, element, "adding pad '%s'",
673       GST_STR_NULL (pad_name));
674   active = GST_PAD_IS_ACTIVE (pad);
675   GST_OBJECT_FLAG_SET (pad, GST_PAD_FLAG_NEED_PARENT);
676   GST_OBJECT_UNLOCK (pad);
677
678   /* then check to see if there's already a pad by that name here */
679   GST_OBJECT_LOCK (element);
680   if (G_UNLIKELY (!gst_object_check_uniqueness (element->pads, pad_name)))
681     goto name_exists;
682
683   /* try to set the pad's parent */
684   if (G_UNLIKELY (!gst_object_set_parent (GST_OBJECT_CAST (pad),
685               GST_OBJECT_CAST (element))))
686     goto had_parent;
687
688   /* check for active pads */
689   if (!active && (GST_STATE (element) > GST_STATE_READY ||
690           GST_STATE_NEXT (element) == GST_STATE_PAUSED)) {
691     g_warning ("adding inactive pad '%s' to running element '%s', you need to "
692         "use gst_pad_set_active(pad,TRUE) before adding it.",
693         GST_STR_NULL (pad_name), GST_ELEMENT_NAME (element));
694     gst_pad_set_active (pad, TRUE);
695   }
696
697   g_free (pad_name);
698
699   /* add it to the list */
700   switch (gst_pad_get_direction (pad)) {
701     case GST_PAD_SRC:
702       element->srcpads = g_list_append (element->srcpads, pad);
703       element->numsrcpads++;
704       break;
705     case GST_PAD_SINK:
706       element->sinkpads = g_list_append (element->sinkpads, pad);
707       element->numsinkpads++;
708       break;
709     default:
710       goto no_direction;
711   }
712   element->pads = g_list_append (element->pads, pad);
713   element->numpads++;
714   element->pads_cookie++;
715   GST_OBJECT_UNLOCK (element);
716
717   /* emit the PAD_ADDED signal */
718   g_signal_emit (element, gst_element_signals[PAD_ADDED], 0, pad);
719   GST_TRACER_ELEMENT_ADD_PAD (element, pad);
720   return TRUE;
721
722   /* ERROR cases */
723 name_exists:
724   {
725     g_critical ("Padname %s is not unique in element %s, not adding",
726         pad_name, GST_ELEMENT_NAME (element));
727     GST_OBJECT_UNLOCK (element);
728     g_free (pad_name);
729     return FALSE;
730   }
731 had_parent:
732   {
733     g_critical
734         ("Pad %s already has parent when trying to add to element %s",
735         pad_name, GST_ELEMENT_NAME (element));
736     GST_OBJECT_UNLOCK (element);
737     g_free (pad_name);
738     return FALSE;
739   }
740 no_direction:
741   {
742     GST_OBJECT_LOCK (pad);
743     g_critical
744         ("Trying to add pad %s to element %s, but it has no direction",
745         GST_OBJECT_NAME (pad), GST_ELEMENT_NAME (element));
746     GST_OBJECT_UNLOCK (pad);
747     GST_OBJECT_UNLOCK (element);
748     return FALSE;
749   }
750 }
751
752 /**
753  * gst_element_remove_pad:
754  * @element: a #GstElement to remove pad from.
755  * @pad: (transfer full): the #GstPad to remove from the element.
756  *
757  * Removes @pad from @element. @pad will be destroyed if it has not been
758  * referenced elsewhere using gst_object_unparent().
759  *
760  * This function is used by plugin developers and should not be used
761  * by applications. Pads that were dynamically requested from elements
762  * with gst_element_request_pad() should be released with the
763  * gst_element_release_request_pad() function instead.
764  *
765  * Pads are not automatically deactivated so elements should perform the needed
766  * steps to deactivate the pad in case this pad is removed in the PAUSED or
767  * PLAYING state. See gst_pad_set_active() for more information about
768  * deactivating pads.
769  *
770  * The pad and the element should be unlocked when calling this function.
771  *
772  * This function will emit the #GstElement::pad-removed signal on the element.
773  *
774  * Returns: %TRUE if the pad could be removed. Can return %FALSE if the
775  * pad does not belong to the provided element.
776  *
777  * MT safe.
778  */
779 gboolean
780 gst_element_remove_pad (GstElement * element, GstPad * pad)
781 {
782   GstPad *peer;
783
784   g_return_val_if_fail (GST_IS_ELEMENT (element), FALSE);
785   g_return_val_if_fail (GST_IS_PAD (pad), FALSE);
786
787   /* locking pad to look at the name and parent */
788   GST_OBJECT_LOCK (pad);
789   GST_CAT_INFO_OBJECT (GST_CAT_ELEMENT_PADS, element, "removing pad '%s'",
790       GST_STR_NULL (GST_PAD_NAME (pad)));
791
792   if (G_UNLIKELY (GST_PAD_PARENT (pad) != element))
793     goto not_our_pad;
794   GST_OBJECT_UNLOCK (pad);
795
796   /* unlink */
797   if ((peer = gst_pad_get_peer (pad))) {
798     /* window for MT unsafeness, someone else could unlink here
799      * and then we call unlink with wrong pads. The unlink
800      * function would catch this and safely return failed. */
801     if (GST_PAD_IS_SRC (pad))
802       gst_pad_unlink (pad, peer);
803     else
804       gst_pad_unlink (peer, pad);
805
806     gst_object_unref (peer);
807   }
808
809   GST_OBJECT_LOCK (element);
810   /* remove it from the list */
811   switch (gst_pad_get_direction (pad)) {
812     case GST_PAD_SRC:
813       element->srcpads = g_list_remove (element->srcpads, pad);
814       element->numsrcpads--;
815       break;
816     case GST_PAD_SINK:
817       element->sinkpads = g_list_remove (element->sinkpads, pad);
818       element->numsinkpads--;
819       break;
820     default:
821       g_critical ("Removing pad without direction???");
822       break;
823   }
824   element->pads = g_list_remove (element->pads, pad);
825   element->numpads--;
826   element->pads_cookie++;
827   GST_OBJECT_UNLOCK (element);
828
829   /* emit the PAD_REMOVED signal before unparenting and losing the last ref. */
830   g_signal_emit (element, gst_element_signals[PAD_REMOVED], 0, pad);
831   GST_TRACER_ELEMENT_REMOVE_PAD (element, pad);
832   gst_object_unparent (GST_OBJECT_CAST (pad));
833
834   return TRUE;
835
836   /* ERRORS */
837 not_our_pad:
838   {
839     /* locking order is element > pad */
840     GST_OBJECT_UNLOCK (pad);
841
842     GST_OBJECT_LOCK (element);
843     GST_OBJECT_LOCK (pad);
844     g_critical ("Padname %s:%s does not belong to element %s when removing",
845         GST_DEBUG_PAD_NAME (pad), GST_ELEMENT_NAME (element));
846     GST_OBJECT_UNLOCK (pad);
847     GST_OBJECT_UNLOCK (element);
848     return FALSE;
849   }
850 }
851
852 /**
853  * gst_element_no_more_pads:
854  * @element: a #GstElement
855  *
856  * Use this function to signal that the element does not expect any more pads
857  * to show up in the current pipeline. This function should be called whenever
858  * pads have been added by the element itself. Elements with #GST_PAD_SOMETIMES
859  * pad templates use this in combination with autopluggers to figure out that
860  * the element is done initializing its pads.
861  *
862  * This function emits the #GstElement::no-more-pads signal.
863  *
864  * MT safe.
865  */
866 void
867 gst_element_no_more_pads (GstElement * element)
868 {
869   g_return_if_fail (GST_IS_ELEMENT (element));
870
871   g_signal_emit (element, gst_element_signals[NO_MORE_PADS], 0);
872 }
873
874 static gint
875 pad_compare_name (GstPad * pad1, const gchar * name)
876 {
877   gint result;
878
879   GST_OBJECT_LOCK (pad1);
880   result = strcmp (GST_PAD_NAME (pad1), name);
881   GST_OBJECT_UNLOCK (pad1);
882
883   return result;
884 }
885
886 /**
887  * gst_element_get_static_pad:
888  * @element: a #GstElement to find a static pad of.
889  * @name: the name of the static #GstPad to retrieve.
890  *
891  * Retrieves a pad from @element by name. This version only retrieves
892  * already-existing (i.e. 'static') pads.
893  *
894  * Returns: (transfer full) (nullable): the requested #GstPad if
895  *     found, otherwise %NULL.  unref after usage.
896  *
897  * MT safe.
898  */
899 GstPad *
900 gst_element_get_static_pad (GstElement * element, const gchar * name)
901 {
902   GList *find;
903   GstPad *result = NULL;
904
905   g_return_val_if_fail (GST_IS_ELEMENT (element), NULL);
906   g_return_val_if_fail (name != NULL, NULL);
907
908   GST_OBJECT_LOCK (element);
909   find =
910       g_list_find_custom (element->pads, name, (GCompareFunc) pad_compare_name);
911   if (find) {
912     result = GST_PAD_CAST (find->data);
913     gst_object_ref (result);
914   }
915
916   if (result == NULL) {
917     GST_CAT_INFO (GST_CAT_ELEMENT_PADS, "no such pad '%s' in element \"%s\"",
918         name, GST_ELEMENT_NAME (element));
919   } else {
920     GST_CAT_INFO (GST_CAT_ELEMENT_PADS, "found pad %s:%s",
921         GST_ELEMENT_NAME (element), name);
922   }
923   GST_OBJECT_UNLOCK (element);
924
925   return result;
926 }
927
928 static GstPad *
929 _gst_element_request_pad (GstElement * element, GstPadTemplate * templ,
930     const gchar * name, const GstCaps * caps)
931 {
932   GstPad *newpad = NULL;
933   GstElementClass *oclass;
934
935   oclass = GST_ELEMENT_GET_CLASS (element);
936
937 #ifndef G_DISABLE_CHECKS
938   /* Some sanity checking here */
939   if (name) {
940     GstPad *pad;
941
942     /* Is this the template name? */
943     if (strstr (name, "%") || !strchr (templ->name_template, '%')) {
944       g_return_val_if_fail (strcmp (name, templ->name_template) == 0, NULL);
945     } else {
946       const gchar *str, *data;
947       gchar *endptr;
948
949       /* Otherwise check if it's a valid name for the name template */
950       str = strchr (templ->name_template, '%');
951       g_return_val_if_fail (str != NULL, NULL);
952       g_return_val_if_fail (strncmp (templ->name_template, name,
953               str - templ->name_template) == 0, NULL);
954       g_return_val_if_fail (strlen (name) > str - templ->name_template, NULL);
955
956       data = name + (str - templ->name_template);
957
958       /* Can either be %s or %d or %u, do sanity checking for %d */
959       if (*(str + 1) == 'd') {
960         gint64 tmp;
961
962         /* it's an int */
963         tmp = g_ascii_strtoll (data, &endptr, 10);
964         g_return_val_if_fail (tmp >= G_MININT && tmp <= G_MAXINT
965             && *endptr == '\0', NULL);
966       } else if (*(str + 1) == 'u') {
967         guint64 tmp;
968
969         /* it's an int */
970         tmp = g_ascii_strtoull (data, &endptr, 10);
971         g_return_val_if_fail (tmp <= G_MAXUINT && *endptr == '\0', NULL);
972       }
973     }
974
975     pad = gst_element_get_static_pad (element, name);
976     if (pad) {
977       gst_object_unref (pad);
978       /* FIXME 2.0: Change this to g_return_val_if_fail() */
979       g_critical ("Element %s already has a pad named %s, the behaviour of "
980           " gst_element_get_request_pad() for existing pads is undefined!",
981           GST_ELEMENT_NAME (element), name);
982     }
983   }
984 #endif
985
986   if (oclass->request_new_pad)
987     newpad = (oclass->request_new_pad) (element, templ, name, caps);
988
989   if (newpad)
990     gst_object_ref (newpad);
991
992   return newpad;
993 }
994
995 /**
996  * gst_element_get_request_pad:
997  * @element: a #GstElement to find a request pad of.
998  * @name: the name of the request #GstPad to retrieve.
999  *
1000  * Retrieves a pad from the element by name (e.g. "src_\%d"). This version only
1001  * retrieves request pads. The pad should be released with
1002  * gst_element_release_request_pad().
1003  *
1004  * This method is slower than manually getting the pad template and calling
1005  * gst_element_request_pad() if the pads should have a specific name (e.g.
1006  * @name is "src_1" instead of "src_\%u").
1007  *
1008  * Returns: (transfer full) (nullable): requested #GstPad if found,
1009  *     otherwise %NULL.  Release after usage.
1010  */
1011 GstPad *
1012 gst_element_get_request_pad (GstElement * element, const gchar * name)
1013 {
1014   GstPadTemplate *templ = NULL;
1015   GstPad *pad;
1016   const gchar *req_name = NULL;
1017   gboolean templ_found = FALSE;
1018   GList *list;
1019   const gchar *data;
1020   gchar *str, *endptr = NULL;
1021   GstElementClass *class;
1022
1023   g_return_val_if_fail (GST_IS_ELEMENT (element), NULL);
1024   g_return_val_if_fail (name != NULL, NULL);
1025
1026   class = GST_ELEMENT_GET_CLASS (element);
1027
1028   /* if the name contains a %, we assume it's the complete template name. Get
1029    * the template and try to get a pad */
1030   if (strstr (name, "%")) {
1031     templ = gst_element_class_get_request_pad_template (class, name);
1032     req_name = NULL;
1033     if (templ)
1034       templ_found = TRUE;
1035   } else {
1036     /* there is no % in the name, try to find a matching template */
1037     list = class->padtemplates;
1038     while (!templ_found && list) {
1039       templ = (GstPadTemplate *) list->data;
1040       if (templ->presence == GST_PAD_REQUEST) {
1041         GST_CAT_DEBUG (GST_CAT_PADS, "comparing %s to %s", name,
1042             templ->name_template);
1043         /* see if we find an exact match */
1044         if (strcmp (name, templ->name_template) == 0) {
1045           templ_found = TRUE;
1046           req_name = name;
1047           break;
1048         }
1049         /* Because of sanity checks in gst_pad_template_new(), we know that %s
1050            and %d and %u, occurring at the end of the name_template, are the only
1051            possibilities. */
1052         else if ((str = strchr (templ->name_template, '%'))
1053             && strncmp (templ->name_template, name,
1054                 str - templ->name_template) == 0
1055             && strlen (name) > str - templ->name_template) {
1056           data = name + (str - templ->name_template);
1057           if (*(str + 1) == 'd') {
1058             glong tmp;
1059
1060             /* it's an int */
1061             tmp = strtol (data, &endptr, 10);
1062             if (tmp != G_MINLONG && tmp != G_MAXLONG && endptr &&
1063                 *endptr == '\0') {
1064               templ_found = TRUE;
1065               req_name = name;
1066               break;
1067             }
1068           } else if (*(str + 1) == 'u') {
1069             gulong tmp;
1070
1071             /* it's an int */
1072             tmp = strtoul (data, &endptr, 10);
1073             if (tmp != G_MAXULONG && endptr && *endptr == '\0') {
1074               templ_found = TRUE;
1075               req_name = name;
1076               break;
1077             }
1078           } else {
1079             /* it's a string */
1080             templ_found = TRUE;
1081             req_name = name;
1082             break;
1083           }
1084         }
1085       }
1086       list = list->next;
1087     }
1088   }
1089
1090   if (!templ_found)
1091     return NULL;
1092
1093   pad = _gst_element_request_pad (element, templ, req_name, NULL);
1094
1095   return pad;
1096 }
1097
1098 /**
1099  * gst_element_request_pad: (virtual request_new_pad)
1100  * @element: a #GstElement to find a request pad of.
1101  * @templ: a #GstPadTemplate of which we want a pad of.
1102  * @name: (transfer none) (allow-none): the name of the request #GstPad
1103  * to retrieve. Can be %NULL.
1104  * @caps: (transfer none) (allow-none): the caps of the pad we want to
1105  * request. Can be %NULL.
1106  *
1107  * Retrieves a request pad from the element according to the provided template.
1108  * Pad templates can be looked up using
1109  * gst_element_factory_get_static_pad_templates().
1110  *
1111  * The pad should be released with gst_element_release_request_pad().
1112  *
1113  * Returns: (transfer full) (nullable): requested #GstPad if found,
1114  *     otherwise %NULL.  Release after usage.
1115  */
1116 GstPad *
1117 gst_element_request_pad (GstElement * element,
1118     GstPadTemplate * templ, const gchar * name, const GstCaps * caps)
1119 {
1120   g_return_val_if_fail (GST_IS_ELEMENT (element), NULL);
1121   g_return_val_if_fail (templ != NULL, NULL);
1122   g_return_val_if_fail (templ->presence == GST_PAD_REQUEST, NULL);
1123
1124   return _gst_element_request_pad (element, templ, name, caps);
1125 }
1126
1127 static GstIterator *
1128 gst_element_iterate_pad_list (GstElement * element, GList ** padlist)
1129 {
1130   GstIterator *result;
1131
1132   GST_OBJECT_LOCK (element);
1133   result = gst_iterator_new_list (GST_TYPE_PAD,
1134       GST_OBJECT_GET_LOCK (element),
1135       &element->pads_cookie, padlist, (GObject *) element, NULL);
1136   GST_OBJECT_UNLOCK (element);
1137
1138   return result;
1139 }
1140
1141 /**
1142  * gst_element_iterate_pads:
1143  * @element: a #GstElement to iterate pads of.
1144  *
1145  * Retrieves an iterator of @element's pads. The iterator should
1146  * be freed after usage. Also more specialized iterators exists such as
1147  * gst_element_iterate_src_pads() or gst_element_iterate_sink_pads().
1148  *
1149  * The order of pads returned by the iterator will be the order in which
1150  * the pads were added to the element.
1151  *
1152  * Returns: (transfer full): the #GstIterator of #GstPad.
1153  *
1154  * MT safe.
1155  */
1156 GstIterator *
1157 gst_element_iterate_pads (GstElement * element)
1158 {
1159   g_return_val_if_fail (GST_IS_ELEMENT (element), NULL);
1160
1161   return gst_element_iterate_pad_list (element, &element->pads);
1162 }
1163
1164 /**
1165  * gst_element_iterate_src_pads:
1166  * @element: a #GstElement.
1167  *
1168  * Retrieves an iterator of @element's source pads.
1169  *
1170  * The order of pads returned by the iterator will be the order in which
1171  * the pads were added to the element.
1172  *
1173  * Returns: (transfer full): the #GstIterator of #GstPad.
1174  *
1175  * MT safe.
1176  */
1177 GstIterator *
1178 gst_element_iterate_src_pads (GstElement * element)
1179 {
1180   g_return_val_if_fail (GST_IS_ELEMENT (element), NULL);
1181
1182   return gst_element_iterate_pad_list (element, &element->srcpads);
1183 }
1184
1185 /**
1186  * gst_element_iterate_sink_pads:
1187  * @element: a #GstElement.
1188  *
1189  * Retrieves an iterator of @element's sink pads.
1190  *
1191  * The order of pads returned by the iterator will be the order in which
1192  * the pads were added to the element.
1193  *
1194  * Returns: (transfer full): the #GstIterator of #GstPad.
1195  *
1196  * MT safe.
1197  */
1198 GstIterator *
1199 gst_element_iterate_sink_pads (GstElement * element)
1200 {
1201   g_return_val_if_fail (GST_IS_ELEMENT (element), NULL);
1202
1203   return gst_element_iterate_pad_list (element, &element->sinkpads);
1204 }
1205
1206 /**
1207  * gst_element_class_add_pad_template:
1208  * @klass: the #GstElementClass to add the pad template to.
1209  * @templ: (transfer full): a #GstPadTemplate to add to the element class.
1210  *
1211  * Adds a padtemplate to an element class. This is mainly used in the _class_init
1212  * functions of classes. If a pad template with the same name as an already
1213  * existing one is added the old one is replaced by the new one.
1214  *
1215  */
1216 void
1217 gst_element_class_add_pad_template (GstElementClass * klass,
1218     GstPadTemplate * templ)
1219 {
1220   GList *template_list = klass->padtemplates;
1221
1222   g_return_if_fail (GST_IS_ELEMENT_CLASS (klass));
1223   g_return_if_fail (GST_IS_PAD_TEMPLATE (templ));
1224
1225   /* If we already have a pad template with the same name replace the
1226    * old one. */
1227   while (template_list) {
1228     GstPadTemplate *padtempl = (GstPadTemplate *) template_list->data;
1229
1230     /* Found pad with the same name, replace and return */
1231     if (strcmp (templ->name_template, padtempl->name_template) == 0) {
1232       gst_object_unref (padtempl);
1233       template_list->data = templ;
1234       return;
1235     }
1236     template_list = g_list_next (template_list);
1237   }
1238
1239   /* Take ownership of the floating ref */
1240   gst_object_ref_sink (templ);
1241
1242   klass->padtemplates = g_list_append (klass->padtemplates, templ);
1243   klass->numpadtemplates++;
1244 }
1245
1246 /**
1247  * gst_element_class_add_static_pad_template:
1248  * @klass: the #GstElementClass to add the pad template to.
1249  * @static_templ: #GstStaticPadTemplate to add as pad template to the element class.
1250  *
1251  * Adds a pad template to an element class based on the static pad template
1252  * @templ. This is mainly used in the _class_init functions of element
1253  * implementations. If a pad template with the same name already exists,
1254  * the old one is replaced by the new one.
1255  *
1256  * Since: 1.8
1257  */
1258 void
1259 gst_element_class_add_static_pad_template (GstElementClass * klass,
1260     GstStaticPadTemplate * static_templ)
1261 {
1262   gst_element_class_add_pad_template (klass,
1263       gst_static_pad_template_get (static_templ));
1264 }
1265
1266 /**
1267  * gst_element_class_add_metadata:
1268  * @klass: class to set metadata for
1269  * @key: the key to set
1270  * @value: the value to set
1271  *
1272  * Set @key with @value as metadata in @klass.
1273  */
1274 void
1275 gst_element_class_add_metadata (GstElementClass * klass,
1276     const gchar * key, const gchar * value)
1277 {
1278   g_return_if_fail (GST_IS_ELEMENT_CLASS (klass));
1279   g_return_if_fail (key != NULL);
1280   g_return_if_fail (value != NULL);
1281
1282   gst_structure_set ((GstStructure *) klass->metadata,
1283       key, G_TYPE_STRING, value, NULL);
1284 }
1285
1286 /**
1287  * gst_element_class_add_static_metadata:
1288  * @klass: class to set metadata for
1289  * @key: the key to set
1290  * @value: the value to set
1291  *
1292  * Set @key with @value as metadata in @klass.
1293  *
1294  * Same as gst_element_class_add_metadata(), but @value must be a static string
1295  * or an inlined string, as it will not be copied. (GStreamer plugins will
1296  * be made resident once loaded, so this function can be used even from
1297  * dynamically loaded plugins.)
1298  */
1299 void
1300 gst_element_class_add_static_metadata (GstElementClass * klass,
1301     const gchar * key, const gchar * value)
1302 {
1303   GValue val = G_VALUE_INIT;
1304
1305   g_return_if_fail (GST_IS_ELEMENT_CLASS (klass));
1306   g_return_if_fail (key != NULL);
1307   g_return_if_fail (value != NULL);
1308
1309   g_value_init (&val, G_TYPE_STRING);
1310   g_value_set_static_string (&val, value);
1311   gst_structure_take_value ((GstStructure *) klass->metadata, key, &val);
1312 }
1313
1314 /**
1315  * gst_element_class_set_metadata:
1316  * @klass: class to set metadata for
1317  * @longname: The long English name of the element. E.g. "File Sink"
1318  * @classification: String describing the type of element, as an unordered list
1319  * separated with slashes ('/'). See draft-klass.txt of the design docs
1320  * for more details and common types. E.g: "Sink/File"
1321  * @description: Sentence describing the purpose of the element.
1322  * E.g: "Write stream to a file"
1323  * @author: Name and contact details of the author(s). Use \n to separate
1324  * multiple author metadata. E.g: "Joe Bloggs &lt;joe.blogs at foo.com&gt;"
1325  *
1326  * Sets the detailed information for a #GstElementClass.
1327  * <note>This function is for use in _class_init functions only.</note>
1328  */
1329 void
1330 gst_element_class_set_metadata (GstElementClass * klass,
1331     const gchar * longname, const gchar * classification,
1332     const gchar * description, const gchar * author)
1333 {
1334   g_return_if_fail (GST_IS_ELEMENT_CLASS (klass));
1335   g_return_if_fail (longname != NULL && *longname != '\0');
1336   g_return_if_fail (classification != NULL && *classification != '\0');
1337   g_return_if_fail (description != NULL && *description != '\0');
1338   g_return_if_fail (author != NULL && *author != '\0');
1339
1340   gst_structure_id_set ((GstStructure *) klass->metadata,
1341       GST_QUARK (ELEMENT_METADATA_LONGNAME), G_TYPE_STRING, longname,
1342       GST_QUARK (ELEMENT_METADATA_KLASS), G_TYPE_STRING, classification,
1343       GST_QUARK (ELEMENT_METADATA_DESCRIPTION), G_TYPE_STRING, description,
1344       GST_QUARK (ELEMENT_METADATA_AUTHOR), G_TYPE_STRING, author, NULL);
1345 }
1346
1347 /**
1348  * gst_element_class_set_static_metadata:
1349  * @klass: class to set metadata for
1350  * @longname: The long English name of the element. E.g. "File Sink"
1351  * @classification: String describing the type of element, as an unordered list
1352  * separated with slashes ('/'). See draft-klass.txt of the design docs
1353  * for more details and common types. E.g: "Sink/File"
1354  * @description: Sentence describing the purpose of the element.
1355  * E.g: "Write stream to a file"
1356  * @author: Name and contact details of the author(s). Use \n to separate
1357  * multiple author metadata. E.g: "Joe Bloggs &lt;joe.blogs at foo.com&gt;"
1358  *
1359  * Sets the detailed information for a #GstElementClass.
1360  * <note>This function is for use in _class_init functions only.</note>
1361  *
1362  * Same as gst_element_class_set_metadata(), but @longname, @classification,
1363  * @description, and @author must be static strings or inlined strings, as
1364  * they will not be copied. (GStreamer plugins will be made resident once
1365  * loaded, so this function can be used even from dynamically loaded plugins.)
1366  */
1367 void
1368 gst_element_class_set_static_metadata (GstElementClass * klass,
1369     const gchar * longname, const gchar * classification,
1370     const gchar * description, const gchar * author)
1371 {
1372   GstStructure *s = (GstStructure *) klass->metadata;
1373   GValue val = G_VALUE_INIT;
1374
1375   g_return_if_fail (GST_IS_ELEMENT_CLASS (klass));
1376   g_return_if_fail (longname != NULL && *longname != '\0');
1377   g_return_if_fail (classification != NULL && *classification != '\0');
1378   g_return_if_fail (description != NULL && *description != '\0');
1379   g_return_if_fail (author != NULL && *author != '\0');
1380
1381   g_value_init (&val, G_TYPE_STRING);
1382
1383   g_value_set_static_string (&val, longname);
1384   gst_structure_id_set_value (s, GST_QUARK (ELEMENT_METADATA_LONGNAME), &val);
1385
1386   g_value_set_static_string (&val, classification);
1387   gst_structure_id_set_value (s, GST_QUARK (ELEMENT_METADATA_KLASS), &val);
1388
1389   g_value_set_static_string (&val, description);
1390   gst_structure_id_set_value (s, GST_QUARK (ELEMENT_METADATA_DESCRIPTION),
1391       &val);
1392
1393   g_value_set_static_string (&val, author);
1394   gst_structure_id_take_value (s, GST_QUARK (ELEMENT_METADATA_AUTHOR), &val);
1395 }
1396
1397 /**
1398  * gst_element_class_get_metadata:
1399  * @klass: class to get metadata for
1400  * @key: the key to get
1401  *
1402  * Get metadata with @key in @klass.
1403  *
1404  * Returns: the metadata for @key.
1405  */
1406 const gchar *
1407 gst_element_class_get_metadata (GstElementClass * klass, const gchar * key)
1408 {
1409   g_return_val_if_fail (GST_IS_ELEMENT_CLASS (klass), NULL);
1410   g_return_val_if_fail (key != NULL, NULL);
1411
1412   return gst_structure_get_string ((GstStructure *) klass->metadata, key);
1413 }
1414
1415 /**
1416  * gst_element_class_get_pad_template_list:
1417  * @element_class: a #GstElementClass to get pad templates of.
1418  *
1419  * Retrieves a list of the pad templates associated with @element_class. The
1420  * list must not be modified by the calling code.
1421  * <note>If you use this function in the #GInstanceInitFunc of an object class
1422  * that has subclasses, make sure to pass the g_class parameter of the
1423  * #GInstanceInitFunc here.</note>
1424  *
1425  * Returns: (transfer none) (element-type Gst.PadTemplate): the #GList of
1426  *     pad templates.
1427  */
1428 GList *
1429 gst_element_class_get_pad_template_list (GstElementClass * element_class)
1430 {
1431   g_return_val_if_fail (GST_IS_ELEMENT_CLASS (element_class), NULL);
1432
1433   return element_class->padtemplates;
1434 }
1435
1436 /**
1437  * gst_element_class_get_pad_template:
1438  * @element_class: a #GstElementClass to get the pad template of.
1439  * @name: the name of the #GstPadTemplate to get.
1440  *
1441  * Retrieves a padtemplate from @element_class with the given name.
1442  * <note>If you use this function in the #GInstanceInitFunc of an object class
1443  * that has subclasses, make sure to pass the g_class parameter of the
1444  * #GInstanceInitFunc here.</note>
1445  *
1446  * Returns: (transfer none) (nullable): the #GstPadTemplate with the
1447  *     given name, or %NULL if none was found. No unreferencing is
1448  *     necessary.
1449  */
1450 GstPadTemplate *
1451 gst_element_class_get_pad_template (GstElementClass *
1452     element_class, const gchar * name)
1453 {
1454   GList *padlist;
1455
1456   g_return_val_if_fail (GST_IS_ELEMENT_CLASS (element_class), NULL);
1457   g_return_val_if_fail (name != NULL, NULL);
1458
1459   padlist = element_class->padtemplates;
1460
1461   while (padlist) {
1462     GstPadTemplate *padtempl = (GstPadTemplate *) padlist->data;
1463
1464     if (strcmp (padtempl->name_template, name) == 0)
1465       return padtempl;
1466
1467     padlist = g_list_next (padlist);
1468   }
1469
1470   return NULL;
1471 }
1472
1473 static GstPadTemplate *
1474 gst_element_class_get_request_pad_template (GstElementClass *
1475     element_class, const gchar * name)
1476 {
1477   GstPadTemplate *tmpl;
1478
1479   tmpl = gst_element_class_get_pad_template (element_class, name);
1480   if (tmpl != NULL && tmpl->presence == GST_PAD_REQUEST)
1481     return tmpl;
1482
1483   return NULL;
1484 }
1485
1486 /* get a random pad on element of the given direction.
1487  * The pad is random in a sense that it is the first pad that is (optionaly) linked.
1488  */
1489 static GstPad *
1490 gst_element_get_random_pad (GstElement * element,
1491     gboolean need_linked, GstPadDirection dir)
1492 {
1493   GstPad *result = NULL;
1494   GList *pads;
1495
1496   GST_CAT_DEBUG (GST_CAT_ELEMENT_PADS, "getting a random pad");
1497
1498   switch (dir) {
1499     case GST_PAD_SRC:
1500       GST_OBJECT_LOCK (element);
1501       pads = element->srcpads;
1502       break;
1503     case GST_PAD_SINK:
1504       GST_OBJECT_LOCK (element);
1505       pads = element->sinkpads;
1506       break;
1507     default:
1508       goto wrong_direction;
1509   }
1510   for (; pads; pads = g_list_next (pads)) {
1511     GstPad *pad = GST_PAD_CAST (pads->data);
1512
1513     GST_OBJECT_LOCK (pad);
1514     GST_CAT_DEBUG (GST_CAT_ELEMENT_PADS, "checking pad %s:%s",
1515         GST_DEBUG_PAD_NAME (pad));
1516
1517     if (need_linked && !GST_PAD_IS_LINKED (pad)) {
1518       /* if we require a linked pad, and it is not linked, continue the
1519        * search */
1520       GST_CAT_DEBUG (GST_CAT_ELEMENT_PADS, "pad %s:%s is not linked",
1521           GST_DEBUG_PAD_NAME (pad));
1522       GST_OBJECT_UNLOCK (pad);
1523       continue;
1524     } else {
1525       /* found a pad, stop search */
1526       GST_CAT_DEBUG (GST_CAT_ELEMENT_PADS, "found pad %s:%s",
1527           GST_DEBUG_PAD_NAME (pad));
1528       GST_OBJECT_UNLOCK (pad);
1529       result = pad;
1530       break;
1531     }
1532   }
1533   if (result)
1534     gst_object_ref (result);
1535
1536   GST_OBJECT_UNLOCK (element);
1537
1538   return result;
1539
1540   /* ERROR handling */
1541 wrong_direction:
1542   {
1543     g_warning ("unknown pad direction %d", dir);
1544     return NULL;
1545   }
1546 }
1547
1548 static gboolean
1549 gst_element_default_send_event (GstElement * element, GstEvent * event)
1550 {
1551   gboolean result = FALSE;
1552   GstPad *pad;
1553
1554   pad = GST_EVENT_IS_DOWNSTREAM (event) ?
1555       gst_element_get_random_pad (element, TRUE, GST_PAD_SINK) :
1556       gst_element_get_random_pad (element, TRUE, GST_PAD_SRC);
1557
1558   if (pad) {
1559     GST_CAT_DEBUG (GST_CAT_ELEMENT_PADS,
1560         "pushing %s event to random %s pad %s:%s",
1561         GST_EVENT_TYPE_NAME (event),
1562         (GST_PAD_DIRECTION (pad) == GST_PAD_SRC ? "src" : "sink"),
1563         GST_DEBUG_PAD_NAME (pad));
1564
1565     result = gst_pad_send_event (pad, event);
1566     gst_object_unref (pad);
1567   } else {
1568     GST_CAT_INFO (GST_CAT_ELEMENT_PADS, "can't send %s event on element %s",
1569         GST_EVENT_TYPE_NAME (event), GST_ELEMENT_NAME (element));
1570     gst_event_unref (event);
1571   }
1572   return result;
1573 }
1574
1575 /**
1576  * gst_element_send_event:
1577  * @element: a #GstElement to send the event to.
1578  * @event: (transfer full): the #GstEvent to send to the element.
1579  *
1580  * Sends an event to an element. If the element doesn't implement an
1581  * event handler, the event will be pushed on a random linked sink pad for
1582  * downstream events or a random linked source pad for upstream events.
1583  *
1584  * This function takes ownership of the provided event so you should
1585  * gst_event_ref() it if you want to reuse the event after this call.
1586  *
1587  * MT safe.
1588  *
1589  * Returns: %TRUE if the event was handled. Events that trigger a preroll (such
1590  * as flushing seeks and steps) will emit %GST_MESSAGE_ASYNC_DONE.
1591  */
1592 gboolean
1593 gst_element_send_event (GstElement * element, GstEvent * event)
1594 {
1595   GstElementClass *oclass;
1596   gboolean result = FALSE;
1597
1598   g_return_val_if_fail (GST_IS_ELEMENT (element), FALSE);
1599   g_return_val_if_fail (event != NULL, FALSE);
1600
1601   oclass = GST_ELEMENT_GET_CLASS (element);
1602
1603   GST_STATE_LOCK (element);
1604   if (oclass->send_event) {
1605     GST_CAT_DEBUG (GST_CAT_ELEMENT_PADS, "send %s event on element %s",
1606         GST_EVENT_TYPE_NAME (event), GST_ELEMENT_NAME (element));
1607     result = oclass->send_event (element, event);
1608   } else {
1609     gst_event_unref (event);
1610   }
1611   GST_STATE_UNLOCK (element);
1612
1613   return result;
1614 }
1615
1616 /**
1617  * gst_element_seek:
1618  * @element: a #GstElement to send the event to.
1619  * @rate: The new playback rate
1620  * @format: The format of the seek values
1621  * @flags: The optional seek flags.
1622  * @start_type: The type and flags for the new start position
1623  * @start: The value of the new start position
1624  * @stop_type: The type and flags for the new stop position
1625  * @stop: The value of the new stop position
1626  *
1627  * Sends a seek event to an element. See gst_event_new_seek() for the details of
1628  * the parameters. The seek event is sent to the element using
1629  * gst_element_send_event().
1630  *
1631  * MT safe.
1632  *
1633  * Returns: %TRUE if the event was handled. Flushing seeks will trigger a
1634  * preroll, which will emit %GST_MESSAGE_ASYNC_DONE.
1635  */
1636 gboolean
1637 gst_element_seek (GstElement * element, gdouble rate, GstFormat format,
1638     GstSeekFlags flags, GstSeekType start_type, gint64 start,
1639     GstSeekType stop_type, gint64 stop)
1640 {
1641   GstEvent *event;
1642   gboolean result;
1643
1644   g_return_val_if_fail (GST_IS_ELEMENT (element), FALSE);
1645
1646   event =
1647       gst_event_new_seek (rate, format, flags, start_type, start, stop_type,
1648       stop);
1649   result = gst_element_send_event (element, event);
1650
1651   return result;
1652 }
1653
1654 static gboolean
1655 gst_element_default_query (GstElement * element, GstQuery * query)
1656 {
1657   gboolean result = FALSE;
1658   GstPad *pad;
1659
1660   pad = gst_element_get_random_pad (element, FALSE, GST_PAD_SRC);
1661   if (pad) {
1662     result = gst_pad_query (pad, query);
1663
1664     gst_object_unref (pad);
1665   } else {
1666     pad = gst_element_get_random_pad (element, TRUE, GST_PAD_SINK);
1667     if (pad) {
1668       GstPad *peer = gst_pad_get_peer (pad);
1669
1670       if (peer) {
1671         result = gst_pad_query (peer, query);
1672
1673         gst_object_unref (peer);
1674       }
1675       gst_object_unref (pad);
1676     }
1677   }
1678   return result;
1679 }
1680
1681 /**
1682  * gst_element_query:
1683  * @element: a #GstElement to perform the query on.
1684  * @query: (transfer none): the #GstQuery.
1685  *
1686  * Performs a query on the given element.
1687  *
1688  * For elements that don't implement a query handler, this function
1689  * forwards the query to a random srcpad or to the peer of a
1690  * random linked sinkpad of this element.
1691  *
1692  * Please note that some queries might need a running pipeline to work.
1693  *
1694  * Returns: %TRUE if the query could be performed.
1695  *
1696  * MT safe.
1697  */
1698 gboolean
1699 gst_element_query (GstElement * element, GstQuery * query)
1700 {
1701   GstElementClass *klass;
1702   gboolean res = FALSE;
1703
1704   g_return_val_if_fail (GST_IS_ELEMENT (element), FALSE);
1705   g_return_val_if_fail (query != NULL, FALSE);
1706
1707   GST_TRACER_ELEMENT_QUERY_PRE (element, query);
1708
1709   klass = GST_ELEMENT_GET_CLASS (element);
1710   if (klass->query) {
1711     GST_CAT_DEBUG (GST_CAT_ELEMENT_PADS, "send query on element %s",
1712         GST_ELEMENT_NAME (element));
1713     res = klass->query (element, query);
1714   }
1715
1716   GST_TRACER_ELEMENT_QUERY_POST (element, query, res);
1717   return res;
1718 }
1719
1720 static gboolean
1721 gst_element_post_message_default (GstElement * element, GstMessage * message)
1722 {
1723   GstBus *bus;
1724   gboolean result = FALSE;
1725
1726   g_return_val_if_fail (GST_IS_ELEMENT (element), FALSE);
1727   g_return_val_if_fail (message != NULL, FALSE);
1728
1729   GST_OBJECT_LOCK (element);
1730   bus = element->bus;
1731
1732   if (G_UNLIKELY (bus == NULL))
1733     goto no_bus;
1734
1735   gst_object_ref (bus);
1736   GST_OBJECT_UNLOCK (element);
1737
1738   /* we release the element lock when posting the message so that any
1739    * (synchronous) message handlers can operate on the element */
1740   result = gst_bus_post (bus, message);
1741   gst_object_unref (bus);
1742
1743   return result;
1744
1745   /* ERRORS */
1746 no_bus:
1747   {
1748     GST_CAT_DEBUG_OBJECT (GST_CAT_MESSAGE, element,
1749         "not posting message %p: no bus", message);
1750     GST_OBJECT_UNLOCK (element);
1751     gst_message_unref (message);
1752     return FALSE;
1753   }
1754 }
1755
1756 /**
1757  * gst_element_post_message:
1758  * @element: a #GstElement posting the message
1759  * @message: (transfer full): a #GstMessage to post
1760  *
1761  * Post a message on the element's #GstBus. This function takes ownership of the
1762  * message; if you want to access the message after this call, you should add an
1763  * additional reference before calling.
1764  *
1765  * Returns: %TRUE if the message was successfully posted. The function returns
1766  * %FALSE if the element did not have a bus.
1767  *
1768  * MT safe.
1769  */
1770 gboolean
1771 gst_element_post_message (GstElement * element, GstMessage * message)
1772 {
1773   GstElementClass *klass;
1774   gboolean res = FALSE;
1775
1776   g_return_val_if_fail (GST_IS_ELEMENT (element), FALSE);
1777   g_return_val_if_fail (message != NULL, FALSE);
1778
1779   GST_TRACER_ELEMENT_POST_MESSAGE_PRE (element, message);
1780
1781   klass = GST_ELEMENT_GET_CLASS (element);
1782   if (klass->post_message)
1783     res = klass->post_message (element, message);
1784   else
1785     gst_message_unref (message);
1786
1787   GST_TRACER_ELEMENT_POST_MESSAGE_POST (element, res);
1788   return res;
1789 }
1790
1791 /**
1792  * _gst_element_error_printf:
1793  * @format: (allow-none): the printf-like format to use, or %NULL
1794  *
1795  * This function is only used internally by the gst_element_error() macro.
1796  *
1797  * Returns: (transfer full) (nullable): a newly allocated string, or
1798  *     %NULL if the format was %NULL or ""
1799  *
1800  * MT safe.
1801  */
1802 gchar *
1803 _gst_element_error_printf (const gchar * format, ...)
1804 {
1805   va_list args;
1806   gchar *buffer;
1807   int len;
1808
1809   if (format == NULL)
1810     return NULL;
1811   if (format[0] == 0)
1812     return NULL;
1813
1814   va_start (args, format);
1815
1816   len = __gst_vasprintf (&buffer, format, args);
1817
1818   va_end (args);
1819
1820   if (len < 0)
1821     buffer = NULL;
1822
1823   return buffer;
1824 }
1825
1826 /**
1827  * gst_element_message_full:
1828  * @element:  a #GstElement to send message from
1829  * @type:     the #GstMessageType
1830  * @domain:   the GStreamer GError domain this message belongs to
1831  * @code:     the GError code belonging to the domain
1832  * @text:     (allow-none) (transfer full): an allocated text string to be used
1833  *            as a replacement for the default message connected to code,
1834  *            or %NULL
1835  * @debug:    (allow-none) (transfer full): an allocated debug message to be
1836  *            used as a replacement for the default debugging information,
1837  *            or %NULL
1838  * @file:     the source code file where the error was generated
1839  * @function: the source code function where the error was generated
1840  * @line:     the source code line where the error was generated
1841  *
1842  * Post an error, warning or info message on the bus from inside an element.
1843  *
1844  * @type must be of #GST_MESSAGE_ERROR, #GST_MESSAGE_WARNING or
1845  * #GST_MESSAGE_INFO.
1846  *
1847  * MT safe.
1848  */
1849 void gst_element_message_full
1850     (GstElement * element, GstMessageType type,
1851     GQuark domain, gint code, gchar * text,
1852     gchar * debug, const gchar * file, const gchar * function, gint line)
1853 {
1854   GError *gerror = NULL;
1855   gchar *name;
1856   gchar *sent_text;
1857   gchar *sent_debug;
1858   gboolean has_debug = TRUE;
1859   GstMessage *message = NULL;
1860
1861   /* checks */
1862   GST_CAT_DEBUG_OBJECT (GST_CAT_MESSAGE, element, "start");
1863   g_return_if_fail (GST_IS_ELEMENT (element));
1864   g_return_if_fail ((type == GST_MESSAGE_ERROR) ||
1865       (type == GST_MESSAGE_WARNING) || (type == GST_MESSAGE_INFO));
1866
1867   /* check if we send the given text or the default error text */
1868   if ((text == NULL) || (text[0] == 0)) {
1869     /* text could have come from g_strdup_printf (""); */
1870     g_free (text);
1871     sent_text = gst_error_get_message (domain, code);
1872   } else
1873     sent_text = text;
1874
1875   /* construct a sent_debug with extra information from source */
1876   if ((debug == NULL) || (debug[0] == 0)) {
1877     /* debug could have come from g_strdup_printf (""); */
1878     has_debug = FALSE;
1879   }
1880
1881   name = gst_object_get_path_string (GST_OBJECT_CAST (element));
1882   if (has_debug)
1883     sent_debug = g_strdup_printf ("%s(%d): %s (): %s:\n%s",
1884         file, line, function, name, debug);
1885   else
1886     sent_debug = g_strdup_printf ("%s(%d): %s (): %s",
1887         file, line, function, name);
1888   g_free (name);
1889   g_free (debug);
1890
1891   /* create gerror and post message */
1892   GST_CAT_INFO_OBJECT (GST_CAT_ERROR_SYSTEM, element, "posting message: %s",
1893       sent_text);
1894   gerror = g_error_new_literal (domain, code, sent_text);
1895
1896   switch (type) {
1897     case GST_MESSAGE_ERROR:
1898       message =
1899           gst_message_new_error (GST_OBJECT_CAST (element), gerror, sent_debug);
1900       break;
1901     case GST_MESSAGE_WARNING:
1902       message = gst_message_new_warning (GST_OBJECT_CAST (element), gerror,
1903           sent_debug);
1904       break;
1905     case GST_MESSAGE_INFO:
1906       message = gst_message_new_info (GST_OBJECT_CAST (element), gerror,
1907           sent_debug);
1908       break;
1909     default:
1910       g_assert_not_reached ();
1911       break;
1912   }
1913   gst_element_post_message (element, message);
1914
1915   GST_CAT_INFO_OBJECT (GST_CAT_ERROR_SYSTEM, element, "posted %s message: %s",
1916       (type == GST_MESSAGE_ERROR ? "error" : "warning"), sent_text);
1917
1918   /* cleanup */
1919   g_error_free (gerror);
1920   g_free (sent_debug);
1921   g_free (sent_text);
1922 }
1923
1924 /**
1925  * gst_element_is_locked_state:
1926  * @element: a #GstElement.
1927  *
1928  * Checks if the state of an element is locked.
1929  * If the state of an element is locked, state changes of the parent don't
1930  * affect the element.
1931  * This way you can leave currently unused elements inside bins. Just lock their
1932  * state before changing the state from #GST_STATE_NULL.
1933  *
1934  * MT safe.
1935  *
1936  * Returns: %TRUE, if the element's state is locked.
1937  */
1938 gboolean
1939 gst_element_is_locked_state (GstElement * element)
1940 {
1941   gboolean result;
1942
1943   g_return_val_if_fail (GST_IS_ELEMENT (element), FALSE);
1944
1945   GST_OBJECT_LOCK (element);
1946   result = GST_ELEMENT_IS_LOCKED_STATE (element);
1947   GST_OBJECT_UNLOCK (element);
1948
1949   return result;
1950 }
1951
1952 /**
1953  * gst_element_set_locked_state:
1954  * @element: a #GstElement
1955  * @locked_state: %TRUE to lock the element's state
1956  *
1957  * Locks the state of an element, so state changes of the parent don't affect
1958  * this element anymore.
1959  *
1960  * MT safe.
1961  *
1962  * Returns: %TRUE if the state was changed, %FALSE if bad parameters were given
1963  * or the elements state-locking needed no change.
1964  */
1965 gboolean
1966 gst_element_set_locked_state (GstElement * element, gboolean locked_state)
1967 {
1968   gboolean old;
1969
1970   g_return_val_if_fail (GST_IS_ELEMENT (element), FALSE);
1971
1972   GST_OBJECT_LOCK (element);
1973   old = GST_ELEMENT_IS_LOCKED_STATE (element);
1974
1975   if (G_UNLIKELY (old == locked_state))
1976     goto was_ok;
1977
1978   if (locked_state) {
1979     GST_CAT_DEBUG (GST_CAT_STATES, "locking state of element %s",
1980         GST_ELEMENT_NAME (element));
1981     GST_OBJECT_FLAG_SET (element, GST_ELEMENT_FLAG_LOCKED_STATE);
1982   } else {
1983     GST_CAT_DEBUG (GST_CAT_STATES, "unlocking state of element %s",
1984         GST_ELEMENT_NAME (element));
1985     GST_OBJECT_FLAG_UNSET (element, GST_ELEMENT_FLAG_LOCKED_STATE);
1986   }
1987   GST_OBJECT_UNLOCK (element);
1988
1989   return TRUE;
1990
1991 was_ok:
1992   {
1993     GST_CAT_DEBUG (GST_CAT_STATES,
1994         "elements %s was already in locked state %d",
1995         GST_ELEMENT_NAME (element), old);
1996     GST_OBJECT_UNLOCK (element);
1997
1998     return FALSE;
1999   }
2000 }
2001
2002 /**
2003  * gst_element_sync_state_with_parent:
2004  * @element: a #GstElement.
2005  *
2006  * Tries to change the state of the element to the same as its parent.
2007  * If this function returns %FALSE, the state of element is undefined.
2008  *
2009  * Returns: %TRUE, if the element's state could be synced to the parent's state.
2010  *
2011  * MT safe.
2012  */
2013 gboolean
2014 gst_element_sync_state_with_parent (GstElement * element)
2015 {
2016   GstElement *parent;
2017   GstState target;
2018   GstStateChangeReturn ret;
2019
2020   g_return_val_if_fail (GST_IS_ELEMENT (element), FALSE);
2021
2022   if ((parent = GST_ELEMENT_CAST (gst_element_get_parent (element)))) {
2023     GstState parent_current, parent_pending;
2024
2025     GST_OBJECT_LOCK (parent);
2026     parent_current = GST_STATE (parent);
2027     parent_pending = GST_STATE_PENDING (parent);
2028     GST_OBJECT_UNLOCK (parent);
2029
2030     /* set to pending if there is one, else we set it to the current state of
2031      * the parent */
2032     if (parent_pending != GST_STATE_VOID_PENDING)
2033       target = parent_pending;
2034     else
2035       target = parent_current;
2036
2037     GST_CAT_DEBUG_OBJECT (GST_CAT_STATES, element,
2038         "syncing state (%s) to parent %s %s (%s, %s)",
2039         gst_element_state_get_name (GST_STATE (element)),
2040         GST_ELEMENT_NAME (parent), gst_element_state_get_name (target),
2041         gst_element_state_get_name (parent_current),
2042         gst_element_state_get_name (parent_pending));
2043
2044     ret = gst_element_set_state (element, target);
2045     if (ret == GST_STATE_CHANGE_FAILURE)
2046       goto failed;
2047
2048     gst_object_unref (parent);
2049
2050     return TRUE;
2051   } else {
2052     GST_CAT_DEBUG_OBJECT (GST_CAT_STATES, element, "element has no parent");
2053   }
2054   return FALSE;
2055
2056   /* ERROR */
2057 failed:
2058   {
2059     GST_CAT_DEBUG_OBJECT (GST_CAT_STATES, element,
2060         "syncing state failed (%s)",
2061         gst_element_state_change_return_get_name (ret));
2062     gst_object_unref (parent);
2063     return FALSE;
2064   }
2065 }
2066
2067 /* MT safe */
2068 static GstStateChangeReturn
2069 gst_element_get_state_func (GstElement * element,
2070     GstState * state, GstState * pending, GstClockTime timeout)
2071 {
2072   GstStateChangeReturn ret = GST_STATE_CHANGE_FAILURE;
2073   GstState old_pending;
2074
2075   GST_CAT_DEBUG_OBJECT (GST_CAT_STATES, element, "getting state, timeout %"
2076       GST_TIME_FORMAT, GST_TIME_ARGS (timeout));
2077
2078   GST_OBJECT_LOCK (element);
2079   ret = GST_STATE_RETURN (element);
2080   GST_CAT_DEBUG_OBJECT (GST_CAT_STATES, element, "RETURN is %s",
2081       gst_element_state_change_return_get_name (ret));
2082
2083   /* we got an error, report immediately */
2084   if (ret == GST_STATE_CHANGE_FAILURE)
2085     goto done;
2086
2087   /* we got no_preroll, report immediately */
2088   if (ret == GST_STATE_CHANGE_NO_PREROLL)
2089     goto done;
2090
2091   /* no need to wait async if we are not async */
2092   if (ret != GST_STATE_CHANGE_ASYNC)
2093     goto done;
2094
2095   old_pending = GST_STATE_PENDING (element);
2096   if (old_pending != GST_STATE_VOID_PENDING) {
2097     gboolean signaled;
2098     guint32 cookie;
2099
2100     /* get cookie to detect state changes during waiting */
2101     cookie = element->state_cookie;
2102
2103     GST_CAT_INFO_OBJECT (GST_CAT_STATES, element,
2104         "waiting for element to commit state");
2105
2106     /* we have a pending state change, wait for it to complete */
2107     if (timeout != GST_CLOCK_TIME_NONE) {
2108       gint64 end_time;
2109       /* make timeout absolute */
2110       end_time = g_get_monotonic_time () + (timeout / 1000);
2111       signaled = GST_STATE_WAIT_UNTIL (element, end_time);
2112     } else {
2113       GST_STATE_WAIT (element);
2114       signaled = TRUE;
2115     }
2116
2117     if (!signaled) {
2118       GST_CAT_INFO_OBJECT (GST_CAT_STATES, element, "timed out");
2119       /* timeout triggered */
2120       ret = GST_STATE_CHANGE_ASYNC;
2121     } else {
2122       if (cookie != element->state_cookie)
2123         goto interrupted;
2124
2125       /* could be success or failure */
2126       if (old_pending == GST_STATE (element)) {
2127         GST_CAT_DEBUG_OBJECT (GST_CAT_STATES, element, "got success");
2128         ret = GST_STATE_CHANGE_SUCCESS;
2129       } else {
2130         GST_CAT_DEBUG_OBJECT (GST_CAT_STATES, element, "got failure");
2131         ret = GST_STATE_CHANGE_FAILURE;
2132       }
2133     }
2134     /* if nothing is pending anymore we can return SUCCESS */
2135     if (GST_STATE_PENDING (element) == GST_STATE_VOID_PENDING) {
2136       GST_CAT_LOG_OBJECT (GST_CAT_STATES, element, "nothing pending");
2137       ret = GST_STATE_CHANGE_SUCCESS;
2138     }
2139   }
2140
2141 done:
2142   if (state)
2143     *state = GST_STATE (element);
2144   if (pending)
2145     *pending = GST_STATE_PENDING (element);
2146
2147   GST_CAT_DEBUG_OBJECT (GST_CAT_STATES, element,
2148       "state current: %s, pending: %s, result: %s",
2149       gst_element_state_get_name (GST_STATE (element)),
2150       gst_element_state_get_name (GST_STATE_PENDING (element)),
2151       gst_element_state_change_return_get_name (ret));
2152   GST_OBJECT_UNLOCK (element);
2153
2154   return ret;
2155
2156 interrupted:
2157   {
2158     if (state)
2159       *state = GST_STATE_VOID_PENDING;
2160     if (pending)
2161       *pending = GST_STATE_VOID_PENDING;
2162
2163     GST_CAT_INFO_OBJECT (GST_CAT_STATES, element, "interruped");
2164
2165     GST_OBJECT_UNLOCK (element);
2166
2167     return GST_STATE_CHANGE_FAILURE;
2168   }
2169 }
2170
2171 /**
2172  * gst_element_get_state:
2173  * @element: a #GstElement to get the state of.
2174  * @state: (out) (allow-none): a pointer to #GstState to hold the state.
2175  *     Can be %NULL.
2176  * @pending: (out) (allow-none): a pointer to #GstState to hold the pending
2177  *     state. Can be %NULL.
2178  * @timeout: a #GstClockTime to specify the timeout for an async
2179  *           state change or %GST_CLOCK_TIME_NONE for infinite timeout.
2180  *
2181  * Gets the state of the element.
2182  *
2183  * For elements that performed an ASYNC state change, as reported by
2184  * gst_element_set_state(), this function will block up to the
2185  * specified timeout value for the state change to complete.
2186  * If the element completes the state change or goes into
2187  * an error, this function returns immediately with a return value of
2188  * %GST_STATE_CHANGE_SUCCESS or %GST_STATE_CHANGE_FAILURE respectively.
2189  *
2190  * For elements that did not return %GST_STATE_CHANGE_ASYNC, this function
2191  * returns the current and pending state immediately.
2192  *
2193  * This function returns %GST_STATE_CHANGE_NO_PREROLL if the element
2194  * successfully changed its state but is not able to provide data yet.
2195  * This mostly happens for live sources that only produce data in
2196  * %GST_STATE_PLAYING. While the state change return is equivalent to
2197  * %GST_STATE_CHANGE_SUCCESS, it is returned to the application to signal that
2198  * some sink elements might not be able to complete their state change because
2199  * an element is not producing data to complete the preroll. When setting the
2200  * element to playing, the preroll will complete and playback will start.
2201  *
2202  * Returns: %GST_STATE_CHANGE_SUCCESS if the element has no more pending state
2203  *          and the last state change succeeded, %GST_STATE_CHANGE_ASYNC if the
2204  *          element is still performing a state change or
2205  *          %GST_STATE_CHANGE_FAILURE if the last state change failed.
2206  *
2207  * MT safe.
2208  */
2209 GstStateChangeReturn
2210 gst_element_get_state (GstElement * element,
2211     GstState * state, GstState * pending, GstClockTime timeout)
2212 {
2213   GstElementClass *oclass;
2214   GstStateChangeReturn result = GST_STATE_CHANGE_FAILURE;
2215
2216   g_return_val_if_fail (GST_IS_ELEMENT (element), GST_STATE_CHANGE_FAILURE);
2217
2218   oclass = GST_ELEMENT_GET_CLASS (element);
2219
2220   if (oclass->get_state)
2221     result = (oclass->get_state) (element, state, pending, timeout);
2222
2223   return result;
2224 }
2225
2226 /**
2227  * gst_element_abort_state:
2228  * @element: a #GstElement to abort the state of.
2229  *
2230  * Abort the state change of the element. This function is used
2231  * by elements that do asynchronous state changes and find out
2232  * something is wrong.
2233  *
2234  * This function should be called with the STATE_LOCK held.
2235  *
2236  * MT safe.
2237  */
2238 void
2239 gst_element_abort_state (GstElement * element)
2240 {
2241   GstState pending;
2242
2243 #ifndef GST_DISABLE_GST_DEBUG
2244   GstState old_state;
2245 #endif
2246
2247   g_return_if_fail (GST_IS_ELEMENT (element));
2248
2249   GST_OBJECT_LOCK (element);
2250   pending = GST_STATE_PENDING (element);
2251
2252   if (pending == GST_STATE_VOID_PENDING ||
2253       GST_STATE_RETURN (element) == GST_STATE_CHANGE_FAILURE)
2254     goto nothing_aborted;
2255
2256 #ifndef GST_DISABLE_GST_DEBUG
2257   old_state = GST_STATE (element);
2258
2259   GST_CAT_INFO_OBJECT (GST_CAT_STATES, element,
2260       "aborting state from %s to %s", gst_element_state_get_name (old_state),
2261       gst_element_state_get_name (pending));
2262 #endif
2263
2264   /* flag error */
2265   GST_STATE_RETURN (element) = GST_STATE_CHANGE_FAILURE;
2266
2267   GST_STATE_BROADCAST (element);
2268   GST_OBJECT_UNLOCK (element);
2269
2270   return;
2271
2272 nothing_aborted:
2273   {
2274     GST_OBJECT_UNLOCK (element);
2275     return;
2276   }
2277 }
2278
2279 /* Not static because GstBin has manual state handling too */
2280 void
2281 _priv_gst_element_state_changed (GstElement * element, GstState oldstate,
2282     GstState newstate, GstState pending)
2283 {
2284   GstElementClass *klass = GST_ELEMENT_GET_CLASS (element);
2285   GstMessage *message;
2286
2287   GST_CAT_INFO_OBJECT (GST_CAT_STATES, element,
2288       "notifying about state-changed %s to %s (%s pending)",
2289       gst_element_state_get_name (oldstate),
2290       gst_element_state_get_name (newstate),
2291       gst_element_state_get_name (pending));
2292
2293   if (klass->state_changed)
2294     klass->state_changed (element, oldstate, newstate, pending);
2295
2296   message = gst_message_new_state_changed (GST_OBJECT_CAST (element),
2297       oldstate, newstate, pending);
2298   gst_element_post_message (element, message);
2299 }
2300
2301 /**
2302  * gst_element_continue_state:
2303  * @element: a #GstElement to continue the state change of.
2304  * @ret: The previous state return value
2305  *
2306  * Commit the state change of the element and proceed to the next
2307  * pending state if any. This function is used
2308  * by elements that do asynchronous state changes.
2309  * The core will normally call this method automatically when an
2310  * element returned %GST_STATE_CHANGE_SUCCESS from the state change function.
2311  *
2312  * If after calling this method the element still has not reached
2313  * the pending state, the next state change is performed.
2314  *
2315  * This method is used internally and should normally not be called by plugins
2316  * or applications.
2317  *
2318  * Returns: The result of the commit state change.
2319  *
2320  * MT safe.
2321  */
2322 GstStateChangeReturn
2323 gst_element_continue_state (GstElement * element, GstStateChangeReturn ret)
2324 {
2325   GstStateChangeReturn old_ret;
2326   GstState old_state, old_next;
2327   GstState current, next, pending;
2328   GstStateChange transition;
2329
2330   GST_OBJECT_LOCK (element);
2331   old_ret = GST_STATE_RETURN (element);
2332   GST_STATE_RETURN (element) = ret;
2333   pending = GST_STATE_PENDING (element);
2334
2335   /* check if there is something to commit */
2336   if (pending == GST_STATE_VOID_PENDING)
2337     goto nothing_pending;
2338
2339   old_state = GST_STATE (element);
2340   /* this is the state we should go to next */
2341   old_next = GST_STATE_NEXT (element);
2342   /* update current state */
2343   current = GST_STATE (element) = old_next;
2344
2345   /* see if we reached the final state */
2346   if (pending == current)
2347     goto complete;
2348
2349   next = GST_STATE_GET_NEXT (current, pending);
2350   transition = (GstStateChange) GST_STATE_TRANSITION (current, next);
2351
2352   GST_STATE_NEXT (element) = next;
2353   /* mark busy */
2354   GST_STATE_RETURN (element) = GST_STATE_CHANGE_ASYNC;
2355   GST_OBJECT_UNLOCK (element);
2356
2357   GST_CAT_INFO_OBJECT (GST_CAT_STATES, element,
2358       "committing state from %s to %s, pending %s, next %s",
2359       gst_element_state_get_name (old_state),
2360       gst_element_state_get_name (old_next),
2361       gst_element_state_get_name (pending), gst_element_state_get_name (next));
2362
2363   _priv_gst_element_state_changed (element, old_state, old_next, pending);
2364
2365   GST_CAT_INFO_OBJECT (GST_CAT_STATES, element,
2366       "continue state change %s to %s, final %s",
2367       gst_element_state_get_name (current),
2368       gst_element_state_get_name (next), gst_element_state_get_name (pending));
2369
2370   ret = gst_element_change_state (element, transition);
2371
2372   return ret;
2373
2374 nothing_pending:
2375   {
2376     GST_CAT_INFO_OBJECT (GST_CAT_STATES, element, "nothing pending");
2377     GST_OBJECT_UNLOCK (element);
2378     return ret;
2379   }
2380 complete:
2381   {
2382     GST_STATE_PENDING (element) = GST_STATE_VOID_PENDING;
2383     GST_STATE_NEXT (element) = GST_STATE_VOID_PENDING;
2384
2385     GST_CAT_INFO_OBJECT (GST_CAT_STATES, element,
2386         "completed state change to %s", gst_element_state_get_name (pending));
2387     GST_OBJECT_UNLOCK (element);
2388
2389     /* don't post silly messages with the same state. This can happen
2390      * when an element state is changed to what it already was. For bins
2391      * this can be the result of a lost state, which we check with the
2392      * previous return value.
2393      * We do signal the cond though as a _get_state() might be blocking
2394      * on it. */
2395     if (old_state != old_next || old_ret == GST_STATE_CHANGE_ASYNC)
2396       _priv_gst_element_state_changed (element, old_state, old_next,
2397           GST_STATE_VOID_PENDING);
2398
2399     GST_STATE_BROADCAST (element);
2400
2401     return ret;
2402   }
2403 }
2404
2405 /**
2406  * gst_element_lost_state:
2407  * @element: a #GstElement the state is lost of
2408  *
2409  * Brings the element to the lost state. The current state of the
2410  * element is copied to the pending state so that any call to
2411  * gst_element_get_state() will return %GST_STATE_CHANGE_ASYNC.
2412  *
2413  * An ASYNC_START message is posted. If the element was PLAYING, it will
2414  * go to PAUSED. The element will be restored to its PLAYING state by
2415  * the parent pipeline when it prerolls again.
2416  *
2417  * This is mostly used for elements that lost their preroll buffer
2418  * in the %GST_STATE_PAUSED or %GST_STATE_PLAYING state after a flush,
2419  * they will go to their pending state again when a new preroll buffer is
2420  * queued. This function can only be called when the element is currently
2421  * not in error or an async state change.
2422  *
2423  * This function is used internally and should normally not be called from
2424  * plugins or applications.
2425  */
2426 void
2427 gst_element_lost_state (GstElement * element)
2428 {
2429   GstState old_state, new_state;
2430   GstMessage *message;
2431
2432   g_return_if_fail (GST_IS_ELEMENT (element));
2433
2434   GST_OBJECT_LOCK (element);
2435   if (GST_STATE_RETURN (element) == GST_STATE_CHANGE_FAILURE)
2436     goto nothing_lost;
2437
2438   if (GST_STATE_PENDING (element) != GST_STATE_VOID_PENDING)
2439     goto only_async_start;
2440
2441   old_state = GST_STATE (element);
2442
2443   /* when we were PLAYING, the new state is PAUSED. We will also not
2444    * automatically go to PLAYING but let the parent bin(s) set us to PLAYING
2445    * when we preroll. */
2446   if (old_state > GST_STATE_PAUSED)
2447     new_state = GST_STATE_PAUSED;
2448   else
2449     new_state = old_state;
2450
2451   GST_CAT_DEBUG_OBJECT (GST_CAT_STATES, element,
2452       "lost state of %s to %s", gst_element_state_get_name (old_state),
2453       gst_element_state_get_name (new_state));
2454
2455   GST_STATE (element) = new_state;
2456   GST_STATE_NEXT (element) = new_state;
2457   GST_STATE_PENDING (element) = new_state;
2458   GST_STATE_RETURN (element) = GST_STATE_CHANGE_ASYNC;
2459   GST_OBJECT_UNLOCK (element);
2460
2461   _priv_gst_element_state_changed (element, new_state, new_state, new_state);
2462
2463   message = gst_message_new_async_start (GST_OBJECT_CAST (element));
2464   gst_element_post_message (element, message);
2465
2466   return;
2467
2468 nothing_lost:
2469   {
2470     GST_OBJECT_UNLOCK (element);
2471     return;
2472   }
2473 only_async_start:
2474   {
2475     GST_OBJECT_UNLOCK (element);
2476
2477     message = gst_message_new_async_start (GST_OBJECT_CAST (element));
2478     gst_element_post_message (element, message);
2479     return;
2480   }
2481 }
2482
2483 /**
2484  * gst_element_set_state:
2485  * @element: a #GstElement to change state of.
2486  * @state: the element's new #GstState.
2487  *
2488  * Sets the state of the element. This function will try to set the
2489  * requested state by going through all the intermediary states and calling
2490  * the class's state change function for each.
2491  *
2492  * This function can return #GST_STATE_CHANGE_ASYNC, in which case the
2493  * element will perform the remainder of the state change asynchronously in
2494  * another thread.
2495  * An application can use gst_element_get_state() to wait for the completion
2496  * of the state change or it can wait for a %GST_MESSAGE_ASYNC_DONE or
2497  * %GST_MESSAGE_STATE_CHANGED on the bus.
2498  *
2499  * State changes to %GST_STATE_READY or %GST_STATE_NULL never return
2500  * #GST_STATE_CHANGE_ASYNC.
2501  *
2502  * Returns: Result of the state change using #GstStateChangeReturn.
2503  *
2504  * MT safe.
2505  */
2506 GstStateChangeReturn
2507 gst_element_set_state (GstElement * element, GstState state)
2508 {
2509   GstElementClass *oclass;
2510   GstStateChangeReturn result = GST_STATE_CHANGE_FAILURE;
2511
2512   g_return_val_if_fail (GST_IS_ELEMENT (element), GST_STATE_CHANGE_FAILURE);
2513
2514   oclass = GST_ELEMENT_GET_CLASS (element);
2515
2516   if (oclass->set_state)
2517     result = (oclass->set_state) (element, state);
2518
2519   return result;
2520 }
2521
2522 /*
2523  * default set state function, calculates the next state based
2524  * on current state and calls the change_state function
2525  */
2526 static GstStateChangeReturn
2527 gst_element_set_state_func (GstElement * element, GstState state)
2528 {
2529   GstState current, next, old_pending;
2530   GstStateChangeReturn ret;
2531   GstStateChange transition;
2532   GstStateChangeReturn old_ret;
2533
2534   g_return_val_if_fail (GST_IS_ELEMENT (element), GST_STATE_CHANGE_FAILURE);
2535
2536   GST_CAT_DEBUG_OBJECT (GST_CAT_STATES, element, "set_state to %s",
2537       gst_element_state_get_name (state));
2538
2539   /* state lock is taken to protect the set_state() and get_state()
2540    * procedures, it does not lock any variables. */
2541   GST_STATE_LOCK (element);
2542
2543   /* now calculate how to get to the new state */
2544   GST_OBJECT_LOCK (element);
2545   old_ret = GST_STATE_RETURN (element);
2546   /* previous state change returned an error, remove all pending
2547    * and next states */
2548   if (old_ret == GST_STATE_CHANGE_FAILURE) {
2549     GST_STATE_NEXT (element) = GST_STATE_VOID_PENDING;
2550     GST_STATE_PENDING (element) = GST_STATE_VOID_PENDING;
2551     GST_STATE_RETURN (element) = GST_STATE_CHANGE_SUCCESS;
2552   }
2553
2554   current = GST_STATE (element);
2555   next = GST_STATE_NEXT (element);
2556   old_pending = GST_STATE_PENDING (element);
2557
2558   /* this is the (new) state we should go to. TARGET is the last state we set on
2559    * the element. */
2560   if (state != GST_STATE_TARGET (element)) {
2561     GST_CAT_DEBUG_OBJECT (GST_CAT_STATES, element,
2562         "setting target state to %s", gst_element_state_get_name (state));
2563     GST_STATE_TARGET (element) = state;
2564     /* increment state cookie so that we can track each state change. We only do
2565      * this if this is actually a new state change. */
2566     element->state_cookie++;
2567   }
2568   GST_STATE_PENDING (element) = state;
2569
2570   GST_CAT_DEBUG_OBJECT (GST_CAT_STATES, element,
2571       "current %s, old_pending %s, next %s, old return %s",
2572       gst_element_state_get_name (current),
2573       gst_element_state_get_name (old_pending),
2574       gst_element_state_get_name (next),
2575       gst_element_state_change_return_get_name (old_ret));
2576
2577   /* if the element was busy doing a state change, we just update the
2578    * target state, it'll get to it async then. */
2579   if (old_pending != GST_STATE_VOID_PENDING) {
2580     /* upwards state change will happen ASYNC */
2581     if (old_pending <= state)
2582       goto was_busy;
2583     /* element is going to this state already */
2584     else if (next == state)
2585       goto was_busy;
2586     /* element was performing an ASYNC upward state change and
2587      * we request to go downward again. Start from the next pending
2588      * state then. */
2589     else if (next > state
2590         && GST_STATE_RETURN (element) == GST_STATE_CHANGE_ASYNC) {
2591       current = next;
2592     }
2593   }
2594   next = GST_STATE_GET_NEXT (current, state);
2595   /* now we store the next state */
2596   GST_STATE_NEXT (element) = next;
2597   /* mark busy, we need to check that there is actually a state change
2598    * to be done else we could accidentally override SUCCESS/NO_PREROLL and
2599    * the default element change_state function has no way to know what the
2600    * old value was... could consider this a FIXME...*/
2601   if (current != next)
2602     GST_STATE_RETURN (element) = GST_STATE_CHANGE_ASYNC;
2603
2604   transition = (GstStateChange) GST_STATE_TRANSITION (current, next);
2605
2606   GST_CAT_DEBUG_OBJECT (GST_CAT_STATES, element,
2607       "%s: setting state from %s to %s",
2608       (next != state ? "intermediate" : "final"),
2609       gst_element_state_get_name (current), gst_element_state_get_name (next));
2610
2611   /* now signal any waiters, they will error since the cookie was incremented */
2612   GST_STATE_BROADCAST (element);
2613
2614   GST_OBJECT_UNLOCK (element);
2615
2616   ret = gst_element_change_state (element, transition);
2617
2618   GST_STATE_UNLOCK (element);
2619
2620   GST_CAT_DEBUG_OBJECT (GST_CAT_STATES, element, "returned %s",
2621       gst_element_state_change_return_get_name (ret));
2622
2623   return ret;
2624
2625 was_busy:
2626   {
2627     GST_STATE_RETURN (element) = GST_STATE_CHANGE_ASYNC;
2628     GST_CAT_DEBUG_OBJECT (GST_CAT_STATES, element,
2629         "element was busy with async state change");
2630     GST_OBJECT_UNLOCK (element);
2631
2632     GST_STATE_UNLOCK (element);
2633
2634     return GST_STATE_CHANGE_ASYNC;
2635   }
2636 }
2637
2638 /**
2639  * gst_element_change_state:
2640  * @element: a #GstElement
2641  * @transition: the requested transition
2642  *
2643  * Perform @transition on @element.
2644  *
2645  * This function must be called with STATE_LOCK held and is mainly used
2646  * internally.
2647  *
2648  * Returns: the #GstStateChangeReturn of the state transition.
2649  */
2650 GstStateChangeReturn
2651 gst_element_change_state (GstElement * element, GstStateChange transition)
2652 {
2653   GstElementClass *oclass;
2654   GstStateChangeReturn ret = GST_STATE_CHANGE_SUCCESS;
2655
2656   oclass = GST_ELEMENT_GET_CLASS (element);
2657
2658   GST_TRACER_ELEMENT_CHANGE_STATE_PRE (element, transition);
2659
2660   /* call the state change function so it can set the state */
2661   if (oclass->change_state)
2662     ret = (oclass->change_state) (element, transition);
2663   else
2664     ret = GST_STATE_CHANGE_FAILURE;
2665
2666   GST_TRACER_ELEMENT_CHANGE_STATE_POST (element, transition, ret);
2667
2668   switch (ret) {
2669     case GST_STATE_CHANGE_FAILURE:
2670       GST_CAT_INFO_OBJECT (GST_CAT_STATES, element,
2671           "have FAILURE change_state return");
2672       /* state change failure */
2673       gst_element_abort_state (element);
2674       break;
2675     case GST_STATE_CHANGE_ASYNC:
2676     {
2677       GstState target;
2678
2679       GST_CAT_DEBUG_OBJECT (GST_CAT_STATES, element,
2680           "element will change state ASYNC");
2681
2682       target = GST_STATE_TARGET (element);
2683
2684       if (target > GST_STATE_READY)
2685         goto async;
2686
2687       /* else we just continue the state change downwards */
2688       GST_CAT_INFO_OBJECT (GST_CAT_STATES, element,
2689           "forcing commit state %s <= %s",
2690           gst_element_state_get_name (target),
2691           gst_element_state_get_name (GST_STATE_READY));
2692
2693       ret = gst_element_continue_state (element, GST_STATE_CHANGE_SUCCESS);
2694       break;
2695     }
2696     case GST_STATE_CHANGE_SUCCESS:
2697       GST_CAT_DEBUG_OBJECT (GST_CAT_STATES, element,
2698           "element changed state SUCCESS");
2699       /* we can commit the state now which will proceeed to
2700        * the next state */
2701       ret = gst_element_continue_state (element, ret);
2702       break;
2703     case GST_STATE_CHANGE_NO_PREROLL:
2704       GST_CAT_DEBUG_OBJECT (GST_CAT_STATES, element,
2705           "element changed state NO_PREROLL");
2706       /* we can commit the state now which will proceeed to
2707        * the next state */
2708       ret = gst_element_continue_state (element, ret);
2709       break;
2710     default:
2711       goto invalid_return;
2712   }
2713
2714   GST_CAT_LOG_OBJECT (GST_CAT_STATES, element, "exit state change %d", ret);
2715
2716   return ret;
2717
2718 async:
2719   GST_CAT_LOG_OBJECT (GST_CAT_STATES, element, "exit async state change %d",
2720       ret);
2721
2722   return ret;
2723
2724   /* ERROR */
2725 invalid_return:
2726   {
2727     GST_OBJECT_LOCK (element);
2728     /* somebody added a GST_STATE_ and forgot to do stuff here ! */
2729     g_critical ("%s: unknown return value %d from a state change function",
2730         GST_ELEMENT_NAME (element), ret);
2731
2732     /* we are in error now */
2733     ret = GST_STATE_CHANGE_FAILURE;
2734     GST_STATE_RETURN (element) = ret;
2735     GST_OBJECT_UNLOCK (element);
2736
2737     return ret;
2738   }
2739 }
2740
2741 /* gst_iterator_fold functions for pads_activate
2742  * Stop the iterator if activating one pad failed, but only if that pad
2743  * has not been removed from the element. */
2744 static gboolean
2745 activate_pads (const GValue * vpad, GValue * ret, gboolean * active)
2746 {
2747   GstPad *pad = g_value_get_object (vpad);
2748   gboolean cont = TRUE;
2749
2750   if (!gst_pad_set_active (pad, *active)) {
2751     if (GST_PAD_PARENT (pad) != NULL) {
2752       cont = FALSE;
2753       g_value_set_boolean (ret, FALSE);
2754     }
2755   }
2756
2757   return cont;
2758 }
2759
2760 /* returns false on error or early cutout of the fold, true if all
2761  * pads in @iter were (de)activated successfully. */
2762 static gboolean
2763 iterator_activate_fold_with_resync (GstIterator * iter,
2764     GstIteratorFoldFunction func, gpointer user_data)
2765 {
2766   GstIteratorResult ires;
2767   GValue ret = { 0 };
2768
2769   /* no need to unset this later, it's just a boolean */
2770   g_value_init (&ret, G_TYPE_BOOLEAN);
2771   g_value_set_boolean (&ret, TRUE);
2772
2773   while (1) {
2774     ires = gst_iterator_fold (iter, func, &ret, user_data);
2775     switch (ires) {
2776       case GST_ITERATOR_RESYNC:
2777         /* need to reset the result again */
2778         g_value_set_boolean (&ret, TRUE);
2779         gst_iterator_resync (iter);
2780         break;
2781       case GST_ITERATOR_DONE:
2782         /* all pads iterated, return collected value */
2783         goto done;
2784       default:
2785         /* iterator returned _ERROR or premature end with _OK,
2786          * mark an error and exit */
2787         g_value_set_boolean (&ret, FALSE);
2788         goto done;
2789     }
2790   }
2791 done:
2792   /* return collected value */
2793   return g_value_get_boolean (&ret);
2794 }
2795
2796 /* is called with STATE_LOCK
2797  *
2798  * Pads are activated from source pads to sinkpads.
2799  */
2800 static gboolean
2801 gst_element_pads_activate (GstElement * element, gboolean active)
2802 {
2803   GstIterator *iter;
2804   gboolean res;
2805
2806   GST_CAT_DEBUG_OBJECT (GST_CAT_ELEMENT_PADS, element,
2807       "%s pads", active ? "activate" : "deactivate");
2808
2809   iter = gst_element_iterate_src_pads (element);
2810   res =
2811       iterator_activate_fold_with_resync (iter,
2812       (GstIteratorFoldFunction) activate_pads, &active);
2813   gst_iterator_free (iter);
2814   if (G_UNLIKELY (!res))
2815     goto src_failed;
2816
2817   iter = gst_element_iterate_sink_pads (element);
2818   res =
2819       iterator_activate_fold_with_resync (iter,
2820       (GstIteratorFoldFunction) activate_pads, &active);
2821   gst_iterator_free (iter);
2822   if (G_UNLIKELY (!res))
2823     goto sink_failed;
2824
2825   GST_CAT_DEBUG_OBJECT (GST_CAT_ELEMENT_PADS, element,
2826       "pad %sactivation successful", active ? "" : "de");
2827
2828   return TRUE;
2829
2830   /* ERRORS */
2831 src_failed:
2832   {
2833     GST_CAT_DEBUG_OBJECT (GST_CAT_ELEMENT_PADS, element,
2834         "pad %sactivation failed", active ? "" : "de");
2835     return FALSE;
2836   }
2837 sink_failed:
2838   {
2839     GST_CAT_DEBUG_OBJECT (GST_CAT_ELEMENT_PADS, element,
2840         "sink pads_activate failed");
2841     return FALSE;
2842   }
2843 }
2844
2845 /* is called with STATE_LOCK */
2846 static GstStateChangeReturn
2847 gst_element_change_state_func (GstElement * element, GstStateChange transition)
2848 {
2849   GstState state, next;
2850   GstStateChangeReturn result = GST_STATE_CHANGE_SUCCESS;
2851
2852   g_return_val_if_fail (GST_IS_ELEMENT (element), GST_STATE_CHANGE_FAILURE);
2853
2854   state = (GstState) GST_STATE_TRANSITION_CURRENT (transition);
2855   next = GST_STATE_TRANSITION_NEXT (transition);
2856
2857   /* if the element already is in the given state, we just return success */
2858   if (next == GST_STATE_VOID_PENDING || state == next)
2859     goto was_ok;
2860
2861   GST_CAT_LOG_OBJECT (GST_CAT_STATES, element,
2862       "default handler tries setting state from %s to %s (%04x)",
2863       gst_element_state_get_name (state),
2864       gst_element_state_get_name (next), transition);
2865
2866   switch (transition) {
2867     case GST_STATE_CHANGE_NULL_TO_READY:
2868       break;
2869     case GST_STATE_CHANGE_READY_TO_PAUSED:
2870       if (!gst_element_pads_activate (element, TRUE)) {
2871         result = GST_STATE_CHANGE_FAILURE;
2872       }
2873       break;
2874     case GST_STATE_CHANGE_PAUSED_TO_PLAYING:
2875       break;
2876     case GST_STATE_CHANGE_PLAYING_TO_PAUSED:
2877       break;
2878     case GST_STATE_CHANGE_PAUSED_TO_READY:
2879     case GST_STATE_CHANGE_READY_TO_NULL:{
2880       GList *l;
2881
2882       /* deactivate pads in both cases, since they are activated on
2883          ready->paused but the element might not have made it to paused */
2884       if (!gst_element_pads_activate (element, FALSE)) {
2885         result = GST_STATE_CHANGE_FAILURE;
2886       }
2887
2888       /* Remove all non-persistent contexts */
2889       GST_OBJECT_LOCK (element);
2890       for (l = element->contexts; l;) {
2891         GstContext *context = l->data;
2892
2893         if (!gst_context_is_persistent (context)) {
2894           GList *next;
2895
2896           gst_context_unref (context);
2897           next = l->next;
2898           element->contexts = g_list_delete_link (element->contexts, l);
2899           l = next;
2900         } else {
2901           l = l->next;
2902         }
2903       }
2904       GST_OBJECT_UNLOCK (element);
2905       break;
2906     }
2907     default:
2908       /* this will catch real but unhandled state changes;
2909        * can only be caused by:
2910        * - a new state was added
2911        * - somehow the element was asked to jump across an intermediate state
2912        */
2913       g_warning ("Unhandled state change from %s to %s",
2914           gst_element_state_get_name (state),
2915           gst_element_state_get_name (next));
2916       break;
2917   }
2918   return result;
2919
2920 was_ok:
2921   {
2922     GST_OBJECT_LOCK (element);
2923     result = GST_STATE_RETURN (element);
2924     GST_CAT_DEBUG_OBJECT (GST_CAT_STATES, element,
2925         "element is already in the %s state",
2926         gst_element_state_get_name (state));
2927     GST_OBJECT_UNLOCK (element);
2928
2929     return result;
2930   }
2931 }
2932
2933 /**
2934  * gst_element_get_factory:
2935  * @element: a #GstElement to request the element factory of.
2936  *
2937  * Retrieves the factory that was used to create this element.
2938  *
2939  * Returns: (transfer none): the #GstElementFactory used for creating this
2940  *     element. no refcounting is needed.
2941  */
2942 GstElementFactory *
2943 gst_element_get_factory (GstElement * element)
2944 {
2945   g_return_val_if_fail (GST_IS_ELEMENT (element), NULL);
2946
2947   return GST_ELEMENT_GET_CLASS (element)->elementfactory;
2948 }
2949
2950 static void
2951 gst_element_dispose (GObject * object)
2952 {
2953   GstElement *element = GST_ELEMENT_CAST (object);
2954   GstClock **clock_p;
2955   GstBus **bus_p;
2956   GstElementClass *oclass;
2957   GList *walk;
2958
2959   oclass = GST_ELEMENT_GET_CLASS (element);
2960
2961   GST_CAT_INFO_OBJECT (GST_CAT_REFCOUNTING, element, "%p dispose", element);
2962
2963   if (GST_STATE (element) != GST_STATE_NULL)
2964     goto not_null;
2965
2966   /* start by releasing all request pads, this might also remove some dynamic
2967    * pads */
2968   walk = element->pads;
2969   while (walk) {
2970     GstPad *pad = GST_PAD_CAST (walk->data);
2971
2972     walk = walk->next;
2973
2974     if (oclass->release_pad && GST_PAD_PAD_TEMPLATE (pad) &&
2975         GST_PAD_TEMPLATE_PRESENCE (GST_PAD_PAD_TEMPLATE (pad))
2976         == GST_PAD_REQUEST) {
2977       GST_CAT_DEBUG_OBJECT (GST_CAT_ELEMENT_PADS, element,
2978           "removing request pad %s:%s", GST_DEBUG_PAD_NAME (pad));
2979       oclass->release_pad (element, pad);
2980
2981       /* in case the release_pad function removed the next pad too */
2982       if (walk && g_list_position (element->pads, walk) == -1)
2983         walk = element->pads;
2984     }
2985   }
2986   /* remove the remaining pads */
2987   while (element->pads) {
2988     GstPad *pad = GST_PAD_CAST (element->pads->data);
2989     GST_CAT_DEBUG_OBJECT (GST_CAT_ELEMENT_PADS, element,
2990         "removing pad %s:%s", GST_DEBUG_PAD_NAME (pad));
2991     if (!gst_element_remove_pad (element, pad)) {
2992       /* only happens when someone unparented our pad.. */
2993       g_critical ("failed to remove pad %s:%s", GST_DEBUG_PAD_NAME (pad));
2994       break;
2995     }
2996   }
2997
2998   GST_OBJECT_LOCK (element);
2999   clock_p = &element->clock;
3000   bus_p = &element->bus;
3001   gst_object_replace ((GstObject **) clock_p, NULL);
3002   gst_object_replace ((GstObject **) bus_p, NULL);
3003   g_list_free_full (element->contexts, (GDestroyNotify) gst_context_unref);
3004   GST_OBJECT_UNLOCK (element);
3005
3006   GST_CAT_INFO_OBJECT (GST_CAT_REFCOUNTING, element, "%p parent class dispose",
3007       element);
3008
3009   G_OBJECT_CLASS (parent_class)->dispose (object);
3010
3011   return;
3012
3013   /* ERRORS */
3014 not_null:
3015   {
3016     gboolean is_locked;
3017
3018     is_locked = GST_ELEMENT_IS_LOCKED_STATE (element);
3019     g_critical
3020         ("\nTrying to dispose element %s, but it is in %s%s instead of the NULL"
3021         " state.\n"
3022         "You need to explicitly set elements to the NULL state before\n"
3023         "dropping the final reference, to allow them to clean up.\n"
3024         "This problem may also be caused by a refcounting bug in the\n"
3025         "application or some element.\n",
3026         GST_OBJECT_NAME (element),
3027         gst_element_state_get_name (GST_STATE (element)),
3028         is_locked ? " (locked)" : "");
3029     return;
3030   }
3031 }
3032
3033 static void
3034 gst_element_finalize (GObject * object)
3035 {
3036   GstElement *element = GST_ELEMENT_CAST (object);
3037
3038   GST_CAT_INFO_OBJECT (GST_CAT_REFCOUNTING, element, "%p finalize", element);
3039
3040   g_cond_clear (&element->state_cond);
3041   g_rec_mutex_clear (&element->state_lock);
3042
3043   GST_CAT_INFO_OBJECT (GST_CAT_REFCOUNTING, element, "%p finalize parent",
3044       element);
3045
3046   G_OBJECT_CLASS (parent_class)->finalize (object);
3047 }
3048
3049 static void
3050 gst_element_set_bus_func (GstElement * element, GstBus * bus)
3051 {
3052   GstBus **bus_p;
3053
3054   g_return_if_fail (GST_IS_ELEMENT (element));
3055
3056   GST_CAT_DEBUG_OBJECT (GST_CAT_PARENTAGE, element, "setting bus to %p", bus);
3057
3058   GST_OBJECT_LOCK (element);
3059   bus_p = &GST_ELEMENT_BUS (element);
3060   gst_object_replace ((GstObject **) bus_p, GST_OBJECT_CAST (bus));
3061   GST_OBJECT_UNLOCK (element);
3062 }
3063
3064 /**
3065  * gst_element_set_bus:
3066  * @element: a #GstElement to set the bus of.
3067  * @bus: (transfer none): the #GstBus to set.
3068  *
3069  * Sets the bus of the element. Increases the refcount on the bus.
3070  * For internal use only, unless you're testing elements.
3071  *
3072  * MT safe.
3073  */
3074 void
3075 gst_element_set_bus (GstElement * element, GstBus * bus)
3076 {
3077   GstElementClass *oclass;
3078
3079   g_return_if_fail (GST_IS_ELEMENT (element));
3080
3081   oclass = GST_ELEMENT_GET_CLASS (element);
3082
3083   if (oclass->set_bus)
3084     oclass->set_bus (element, bus);
3085 }
3086
3087 /**
3088  * gst_element_get_bus:
3089  * @element: a #GstElement to get the bus of.
3090  *
3091  * Returns the bus of the element. Note that only a #GstPipeline will provide a
3092  * bus for the application.
3093  *
3094  * Returns: (transfer full): the element's #GstBus. unref after usage.
3095  *
3096  * MT safe.
3097  */
3098 GstBus *
3099 gst_element_get_bus (GstElement * element)
3100 {
3101   GstBus *result = NULL;
3102
3103   g_return_val_if_fail (GST_IS_ELEMENT (element), result);
3104
3105   GST_OBJECT_LOCK (element);
3106   if ((result = GST_ELEMENT_BUS (element)))
3107     gst_object_ref (result);
3108   GST_OBJECT_UNLOCK (element);
3109
3110   GST_CAT_DEBUG_OBJECT (GST_CAT_BUS, element, "got bus %" GST_PTR_FORMAT,
3111       result);
3112
3113   return result;
3114 }
3115
3116 static void
3117 gst_element_set_context_default (GstElement * element, GstContext * context)
3118 {
3119   const gchar *context_type;
3120   GList *l;
3121
3122   GST_OBJECT_LOCK (element);
3123   context_type = gst_context_get_context_type (context);
3124   for (l = element->contexts; l; l = l->next) {
3125     GstContext *tmp = l->data;
3126     const gchar *tmp_type = gst_context_get_context_type (tmp);
3127
3128     /* Always store newest context but never replace
3129      * a persistent one by a non-persistent one */
3130     if (strcmp (context_type, tmp_type) == 0 &&
3131         (gst_context_is_persistent (context) ||
3132             !gst_context_is_persistent (tmp))) {
3133       gst_context_replace ((GstContext **) & l->data, context);
3134       break;
3135     }
3136   }
3137   /* Not found? Add */
3138   if (l == NULL) {
3139     element->contexts =
3140         g_list_prepend (element->contexts, gst_context_ref (context));
3141   }
3142   GST_OBJECT_UNLOCK (element);
3143 }
3144
3145 /**
3146  * gst_element_set_context:
3147  * @element: a #GstElement to set the context of.
3148  * @context: (transfer none): the #GstContext to set.
3149  *
3150  * Sets the context of the element. Increases the refcount of the context.
3151  *
3152  * MT safe.
3153  */
3154 void
3155 gst_element_set_context (GstElement * element, GstContext * context)
3156 {
3157   GstElementClass *oclass;
3158
3159   g_return_if_fail (GST_IS_ELEMENT (element));
3160
3161   oclass = GST_ELEMENT_GET_CLASS (element);
3162
3163   GST_CAT_DEBUG_OBJECT (GST_CAT_CONTEXT, element,
3164       "set context %p %" GST_PTR_FORMAT, context,
3165       gst_context_get_structure (context));
3166
3167   if (oclass->set_context)
3168     oclass->set_context (element, context);
3169 }
3170
3171 /**
3172  * gst_element_get_contexts:
3173  * @element: a #GstElement to set the context of.
3174  *
3175  * Gets the contexts set on the element.
3176  *
3177  * MT safe.
3178  *
3179  * Returns: (element-type Gst.Context) (transfer full): List of #GstContext
3180  *
3181  * Since: 1.8
3182  */
3183 GList *
3184 gst_element_get_contexts (GstElement * element)
3185 {
3186   GList *ret;
3187
3188   g_return_val_if_fail (GST_IS_ELEMENT (element), NULL);
3189
3190   GST_OBJECT_LOCK (element);
3191   ret = g_list_copy_deep (element->contexts, (GCopyFunc) gst_context_ref, NULL);
3192   GST_OBJECT_UNLOCK (element);
3193
3194   return ret;
3195 }
3196
3197 static gint
3198 _match_context_type (GstContext * c1, const gchar * context_type)
3199 {
3200   const gchar *c1_type;
3201
3202   c1_type = gst_context_get_context_type (c1);
3203
3204   return g_strcmp0 (c1_type, context_type);
3205 }
3206
3207 /**
3208  * gst_element_get_context_unlocked:
3209  * @element: a #GstElement to get the context of.
3210  * @context_type: a name of a context to retrieve
3211  *
3212  * Gets the context with @context_type set on the element or NULL.
3213  *
3214  * Returns: (transfer full): A #GstContext or NULL
3215  *
3216  * Since: 1.8
3217  */
3218 GstContext *
3219 gst_element_get_context_unlocked (GstElement * element,
3220     const gchar * context_type)
3221 {
3222   GstContext *ret = NULL;
3223   GList *node;
3224
3225   g_return_val_if_fail (GST_IS_ELEMENT (element), NULL);
3226
3227   node =
3228       g_list_find_custom (element->contexts, context_type,
3229       (GCompareFunc) _match_context_type);
3230   if (node && node->data)
3231     ret = gst_context_ref (node->data);
3232
3233   return ret;
3234 }
3235
3236 /**
3237  * gst_element_get_context:
3238  * @element: a #GstElement to get the context of.
3239  * @context_type: a name of a context to retrieve
3240  *
3241  * Gets the context with @context_type set on the element or NULL.
3242  *
3243  * MT safe.
3244  *
3245  * Returns: (transfer full): A #GstContext or NULL
3246  *
3247  * Since: 1.8
3248  */
3249 GstContext *
3250 gst_element_get_context (GstElement * element, const gchar * context_type)
3251 {
3252   GstContext *ret = NULL;
3253
3254   g_return_val_if_fail (GST_IS_ELEMENT (element), NULL);
3255
3256   GST_OBJECT_LOCK (element);
3257   ret = gst_element_get_context_unlocked (element, context_type);
3258   GST_OBJECT_UNLOCK (element);
3259
3260   return ret;
3261 }
3262
3263 static void
3264 gst_element_property_post_notify_msg (GstElement * element, GObject * obj,
3265     GParamSpec * pspec, gboolean include_value)
3266 {
3267   GValue val = G_VALUE_INIT;
3268   GValue *v;
3269
3270   GST_LOG_OBJECT (element, "property '%s' of object %" GST_PTR_FORMAT " has "
3271       "changed, posting message with%s value", pspec->name, obj,
3272       include_value ? "" : "out");
3273
3274   if (include_value && (pspec->flags & G_PARAM_READABLE) != 0) {
3275     g_value_init (&val, pspec->value_type);
3276     g_object_get_property (obj, pspec->name, &val);
3277     v = &val;
3278   } else {
3279     v = NULL;
3280   }
3281   gst_element_post_message (element,
3282       gst_message_new_property_notify (GST_OBJECT_CAST (obj), pspec->name, v));
3283 }
3284
3285 static void
3286 gst_element_property_deep_notify_cb (GstElement * element, GObject * prop_obj,
3287     GParamSpec * pspec, gpointer user_data)
3288 {
3289   gboolean include_value = GPOINTER_TO_INT (user_data);
3290
3291   gst_element_property_post_notify_msg (element, prop_obj, pspec,
3292       include_value);
3293 }
3294
3295 static void
3296 gst_element_property_notify_cb (GObject * obj, GParamSpec * pspec,
3297     gpointer user_data)
3298 {
3299   gboolean include_value = GPOINTER_TO_INT (user_data);
3300
3301   gst_element_property_post_notify_msg (GST_ELEMENT_CAST (obj), obj, pspec,
3302       include_value);
3303 }
3304
3305 /**
3306  * gst_element_add_property_notify_watch:
3307  * @element: a #GstElement to watch for property changes
3308  * @property_name: (allow-none): name of property to watch for changes, or
3309  *     NULL to watch all properties
3310  * @include_value: whether to include the new property value in the message
3311  *
3312  * Returns: a watch id, which can be used in connection with
3313  *     gst_element_remove_property_notify_watch() to remove the watch again.
3314  *
3315  * Since: 1.10
3316  */
3317 gulong
3318 gst_element_add_property_notify_watch (GstElement * element,
3319     const gchar * property_name, gboolean include_value)
3320 {
3321   const gchar *sep;
3322   gchar *signal_name;
3323   gulong id;
3324
3325   g_return_val_if_fail (GST_IS_ELEMENT (element), 0);
3326
3327   sep = (property_name != NULL) ? "::" : NULL;
3328   signal_name = g_strconcat ("notify", sep, property_name, NULL);
3329   id = g_signal_connect (element, signal_name,
3330       G_CALLBACK (gst_element_property_notify_cb),
3331       GINT_TO_POINTER (include_value));
3332   g_free (signal_name);
3333
3334   return id;
3335 }
3336
3337 /**
3338  * gst_element_add_property_deep_notify_watch:
3339  * @element: a #GstElement to watch (recursively) for property changes
3340  * @property_name: (allow-none): name of property to watch for changes, or
3341  *     NULL to watch all properties
3342  * @include_value: whether to include the new property value in the message
3343  *
3344  * Returns: a watch id, which can be used in connection with
3345  *     gst_element_remove_property_notify_watch() to remove the watch again.
3346  *
3347  * Since: 1.10
3348  */
3349 gulong
3350 gst_element_add_property_deep_notify_watch (GstElement * element,
3351     const gchar * property_name, gboolean include_value)
3352 {
3353   const gchar *sep;
3354   gchar *signal_name;
3355   gulong id;
3356
3357   g_return_val_if_fail (GST_IS_ELEMENT (element), 0);
3358
3359   sep = (property_name != NULL) ? "::" : NULL;
3360   signal_name = g_strconcat ("deep-notify", sep, property_name, NULL);
3361   id = g_signal_connect (element, signal_name,
3362       G_CALLBACK (gst_element_property_deep_notify_cb),
3363       GINT_TO_POINTER (include_value));
3364   g_free (signal_name);
3365
3366   return id;
3367 }
3368
3369 /**
3370  * gst_element_remove_property_notify_watch:
3371  * @element: a #GstElement being watched for property changes
3372  * @watch_id: watch id to remove
3373  *
3374  * Since: 1.10
3375  */
3376 void
3377 gst_element_remove_property_notify_watch (GstElement * element, gulong watch_id)
3378 {
3379   g_signal_handler_disconnect (element, watch_id);
3380 }
3381
3382 typedef struct
3383 {
3384   GstElement *element;
3385   GstElementCallAsyncFunc func;
3386   gpointer user_data;
3387   GDestroyNotify destroy_notify;
3388 } GstElementCallAsyncData;
3389
3390 static void
3391 gst_element_call_async_func (gpointer data, gpointer user_data)
3392 {
3393   GstElementCallAsyncData *async_data = data;
3394
3395   async_data->func (async_data->element, async_data->user_data);
3396   if (async_data->destroy_notify)
3397     async_data->destroy_notify (async_data->user_data);
3398   gst_object_unref (async_data->element);
3399   g_free (async_data);
3400 }
3401
3402 /**
3403  * gst_element_call_async:
3404  * @element: a #GstElement
3405  * @func: Function to call asynchronously from another thread
3406  * @user_data: Data to pass to @func
3407  * @destroy_notify: GDestroyNotify for @user_data
3408  *
3409  * Calls @func from another thread and passes @user_data to it. This is to be
3410  * used for cases when a state change has to be performed from a streaming
3411  * thread, directly via gst_element_set_state() or indirectly e.g. via SEEK
3412  * events.
3413  *
3414  * Calling those functions directly from the streaming thread will cause
3415  * deadlocks in many situations, as they might involve waiting for the
3416  * streaming thread to shut down from this very streaming thread.
3417  *
3418  * MT safe.
3419  *
3420  * Since: 1.10
3421  */
3422 void
3423 gst_element_call_async (GstElement * element, GstElementCallAsyncFunc func,
3424     gpointer user_data, GDestroyNotify destroy_notify)
3425 {
3426   GstElementCallAsyncData *async_data;
3427
3428   g_return_if_fail (GST_IS_ELEMENT (element));
3429
3430   async_data = g_new0 (GstElementCallAsyncData, 1);
3431   async_data->element = gst_object_ref (element);
3432   async_data->func = func;
3433   async_data->user_data = user_data;
3434   async_data->destroy_notify = destroy_notify;
3435
3436   g_thread_pool_push (gst_element_pool, async_data, NULL);
3437 }