gst/: Make things work with --disable-parse as they do with
[platform/upstream/gstreamer.git] / gst / gstutils.c
1 /* GStreamer
2  * Copyright (C) 1999,2000 Erik Walthinsen <omega@cse.ogi.edu>
3  *                    2000 Wim Taymans <wtay@chello.be>
4  *                    2002 Thomas Vander Stichele <thomas@apestaart.org>
5  *
6  * gstutils.c: Utility functions: gtk_get_property stuff, etc.
7  *
8  * This library is free software; you can redistribute it and/or
9  * modify it under the terms of the GNU Library General Public
10  * License as published by the Free Software Foundation; either
11  * version 2 of the License, or (at your option) any later version.
12  *
13  * This library is distributed in the hope that it will be useful,
14  * but WITHOUT ANY WARRANTY; without even the implied warranty of
15  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
16  * Library General Public License for more details.
17  *
18  * You should have received a copy of the GNU Library General Public
19  * License along with this library; if not, write to the
20  * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
21  * Boston, MA 02111-1307, USA.
22  */
23
24 /**
25  * SECTION:gstutils
26  * @short_description: Various utility functions
27  *
28  * When defining own plugins, use the GST_BOILERPLATE ease gobject creation.
29  */
30
31 #include <stdio.h>
32 #include <string.h>
33
34 #include "gst_private.h"
35 #include "gstghostpad.h"
36 #include "gstutils.h"
37 #include "gstinfo.h"
38 #include "gstparse.h"
39 #include "gst-i18n-lib.h"
40
41
42 /**
43  * gst_util_dump_mem:
44  * @mem: a pointer to the memory to dump
45  * @size: the size of the memory block to dump
46  *
47  * Dumps the memory block into a hex representation. Useful for debugging.
48  */
49 void
50 gst_util_dump_mem (const guchar * mem, guint size)
51 {
52   guint i, j;
53   GString *string = g_string_sized_new (50);
54   GString *chars = g_string_sized_new (18);
55
56   i = j = 0;
57   while (i < size) {
58     if (g_ascii_isprint (mem[i]))
59       g_string_append_printf (chars, "%c", mem[i]);
60     else
61       g_string_append_printf (chars, ".");
62
63     g_string_append_printf (string, "%02x ", mem[i]);
64
65     j++;
66     i++;
67
68     if (j == 16 || i == size) {
69       g_print ("%08x (%p): %-48.48s %-16.16s\n", i - j, mem + i - j,
70           string->str, chars->str);
71       g_string_set_size (string, 0);
72       g_string_set_size (chars, 0);
73       j = 0;
74     }
75   }
76   g_string_free (string, TRUE);
77   g_string_free (chars, TRUE);
78 }
79
80
81 /**
82  * gst_util_set_value_from_string:
83  * @value: the value to set
84  * @value_str: the string to get the value from
85  *
86  * Converts the string to the type of the value and
87  * sets the value with it.
88  */
89 void
90 gst_util_set_value_from_string (GValue * value, const gchar * value_str)
91 {
92   gint sscanf_ret;
93
94   g_return_if_fail (value != NULL);
95   g_return_if_fail (value_str != NULL);
96
97   GST_CAT_DEBUG (GST_CAT_PARAMS, "parsing '%s' to type %s", value_str,
98       g_type_name (G_VALUE_TYPE (value)));
99
100   switch (G_VALUE_TYPE (value)) {
101     case G_TYPE_STRING:
102       g_value_set_string (value, g_strdup (value_str));
103       break;
104     case G_TYPE_ENUM:
105     case G_TYPE_INT:{
106       gint i;
107
108       sscanf_ret = sscanf (value_str, "%d", &i);
109       g_return_if_fail (sscanf_ret == 1);
110       g_value_set_int (value, i);
111       break;
112     }
113     case G_TYPE_UINT:{
114       guint i;
115
116       sscanf_ret = sscanf (value_str, "%u", &i);
117       g_return_if_fail (sscanf_ret == 1);
118       g_value_set_uint (value, i);
119       break;
120     }
121     case G_TYPE_LONG:{
122       glong i;
123
124       sscanf_ret = sscanf (value_str, "%ld", &i);
125       g_return_if_fail (sscanf_ret == 1);
126       g_value_set_long (value, i);
127       break;
128     }
129     case G_TYPE_ULONG:{
130       gulong i;
131
132       sscanf_ret = sscanf (value_str, "%lu", &i);
133       g_return_if_fail (sscanf_ret == 1);
134       g_value_set_ulong (value, i);
135       break;
136     }
137     case G_TYPE_BOOLEAN:{
138       gboolean i = FALSE;
139
140       if (!g_ascii_strncasecmp ("true", value_str, 4))
141         i = TRUE;
142       g_value_set_boolean (value, i);
143       break;
144     }
145     case G_TYPE_CHAR:{
146       gchar i;
147
148       sscanf_ret = sscanf (value_str, "%c", &i);
149       g_return_if_fail (sscanf_ret == 1);
150       g_value_set_char (value, i);
151       break;
152     }
153     case G_TYPE_UCHAR:{
154       guchar i;
155
156       sscanf_ret = sscanf (value_str, "%c", &i);
157       g_return_if_fail (sscanf_ret == 1);
158       g_value_set_uchar (value, i);
159       break;
160     }
161     case G_TYPE_FLOAT:{
162       gfloat i;
163
164       sscanf_ret = sscanf (value_str, "%f", &i);
165       g_return_if_fail (sscanf_ret == 1);
166       g_value_set_float (value, i);
167       break;
168     }
169     case G_TYPE_DOUBLE:{
170       gfloat i;
171
172       sscanf_ret = sscanf (value_str, "%g", &i);
173       g_return_if_fail (sscanf_ret == 1);
174       g_value_set_double (value, (gdouble) i);
175       break;
176     }
177     default:
178       break;
179   }
180 }
181
182 /**
183  * gst_util_set_object_arg:
184  * @object: the object to set the argument of
185  * @name: the name of the argument to set
186  * @value: the string value to set
187  *
188  * Convertes the string value to the type of the objects argument and
189  * sets the argument with it.
190  */
191 void
192 gst_util_set_object_arg (GObject * object, const gchar * name,
193     const gchar * value)
194 {
195   gboolean sscanf_ret;
196
197   if (name && value) {
198     GParamSpec *paramspec;
199
200     paramspec =
201         g_object_class_find_property (G_OBJECT_GET_CLASS (object), name);
202
203     if (!paramspec) {
204       return;
205     }
206
207     GST_DEBUG ("paramspec->flags is %d, paramspec->value_type is %d",
208         paramspec->flags, (gint) paramspec->value_type);
209
210     if (paramspec->flags & G_PARAM_WRITABLE) {
211       switch (paramspec->value_type) {
212         case G_TYPE_STRING:
213           g_object_set (G_OBJECT (object), name, value, NULL);
214           break;
215         case G_TYPE_ENUM:
216         case G_TYPE_INT:{
217           gint i;
218
219           sscanf_ret = sscanf (value, "%d", &i);
220           g_return_if_fail (sscanf_ret == 1);
221           g_object_set (G_OBJECT (object), name, i, NULL);
222           break;
223         }
224         case G_TYPE_UINT:{
225           guint i;
226
227           sscanf_ret = sscanf (value, "%u", &i);
228           g_return_if_fail (sscanf_ret == 1);
229           g_object_set (G_OBJECT (object), name, i, NULL);
230           break;
231         }
232         case G_TYPE_LONG:{
233           glong i;
234
235           sscanf_ret = sscanf (value, "%ld", &i);
236           g_return_if_fail (sscanf_ret == 1);
237           g_object_set (G_OBJECT (object), name, i, NULL);
238           break;
239         }
240         case G_TYPE_ULONG:{
241           gulong i;
242
243           sscanf_ret = sscanf (value, "%lu", &i);
244           g_return_if_fail (sscanf_ret == 1);
245           g_object_set (G_OBJECT (object), name, i, NULL);
246           break;
247         }
248         case G_TYPE_BOOLEAN:{
249           gboolean i = FALSE;
250
251           if (!g_ascii_strncasecmp ("true", value, 4))
252             i = TRUE;
253           g_object_set (G_OBJECT (object), name, i, NULL);
254           break;
255         }
256         case G_TYPE_CHAR:{
257           gchar i;
258
259           sscanf_ret = sscanf (value, "%c", &i);
260           g_return_if_fail (sscanf_ret == 1);
261           g_object_set (G_OBJECT (object), name, i, NULL);
262           break;
263         }
264         case G_TYPE_UCHAR:{
265           guchar i;
266
267           sscanf_ret = sscanf (value, "%c", &i);
268           g_return_if_fail (sscanf_ret == 1);
269           g_object_set (G_OBJECT (object), name, i, NULL);
270           break;
271         }
272         case G_TYPE_FLOAT:{
273           gfloat i;
274
275           sscanf_ret = sscanf (value, "%f", &i);
276           g_return_if_fail (sscanf_ret == 1);
277           g_object_set (G_OBJECT (object), name, i, NULL);
278           break;
279         }
280         case G_TYPE_DOUBLE:{
281           gfloat i;
282
283           sscanf_ret = sscanf (value, "%g", &i);
284           g_return_if_fail (sscanf_ret == 1);
285           g_object_set (G_OBJECT (object), name, (gdouble) i, NULL);
286           break;
287         }
288         default:
289           if (G_IS_PARAM_SPEC_ENUM (paramspec)) {
290             gint i;
291
292             sscanf_ret = sscanf (value, "%d", &i);
293             g_return_if_fail (sscanf_ret == 1);
294             g_object_set (G_OBJECT (object), name, i, NULL);
295           }
296           break;
297       }
298     }
299   }
300 }
301
302 /* work around error C2520: conversion from unsigned __int64 to double
303  * not implemented, use signed __int64
304  *
305  * These are implemented as functions because on some platforms a 64bit int to
306  * double conversion is not defined/implemented.
307  */
308
309 gdouble
310 gst_util_guint64_to_gdouble (guint64 value)
311 {
312   if (value & G_GINT64_CONSTANT (0x8000000000000000))
313     return (gdouble) ((gint64) value) + (gdouble) 18446744073709551616.;
314   else
315     return (gdouble) ((gint64) value);
316 }
317
318 guint64
319 gst_util_gdouble_to_guint64 (gdouble value)
320 {
321   if (value < (gdouble) 9223372036854775808.)   /* 1 << 63 */
322     return ((guint64) ((gint64) value));
323
324   value -= (gdouble) 18446744073709551616.;
325   return ((guint64) ((gint64) value));
326 }
327
328 /* convenience struct for getting high and low uint32 parts of
329  * a guint64 */
330 typedef union
331 {
332   guint64 ll;
333   struct
334   {
335 #if G_BYTE_ORDER == G_BIG_ENDIAN
336     guint32 high, low;
337 #else
338     guint32 low, high;
339 #endif
340   } l;
341 } GstUInt64;
342
343 /* based on Hacker's Delight p152 */
344 static guint64
345 gst_util_div128_64 (GstUInt64 c1, GstUInt64 c0, guint64 denom)
346 {
347   GstUInt64 q1, q0, rhat;
348   GstUInt64 v, cmp1, cmp2;
349   guint s;
350
351   v.ll = denom;
352
353   /* count number of leading zeroes, we know they must be in the high
354    * part of denom since denom > G_MAXUINT32. */
355   s = v.l.high | (v.l.high >> 1);
356   s |= (s >> 2);
357   s |= (s >> 4);
358   s |= (s >> 8);
359   s = ~(s | (s >> 16));
360   s = s - ((s >> 1) & 0x55555555);
361   s = (s & 0x33333333) + ((s >> 2) & 0x33333333);
362   s = (s + (s >> 4)) & 0x0f0f0f0f;
363   s += (s >> 8);
364   s = (s + (s >> 16)) & 0x3f;
365
366   if (s > 0) {
367     /* normalize divisor and dividend */
368     v.ll <<= s;
369     c1.ll = (c1.ll << s) | (c0.l.high >> (32 - s));
370     c0.ll <<= s;
371   }
372
373   q1.ll = c1.ll / v.l.high;
374   rhat.ll = c1.ll - q1.ll * v.l.high;
375
376   cmp1.l.high = rhat.l.low;
377   cmp1.l.low = c0.l.high;
378   cmp2.ll = q1.ll * v.l.low;
379
380   while (q1.l.high || cmp2.ll > cmp1.ll) {
381     q1.ll--;
382     rhat.ll += v.l.high;
383     if (rhat.l.high)
384       break;
385     cmp1.l.high = rhat.l.low;
386     cmp2.ll -= v.l.low;
387   }
388   c1.l.high = c1.l.low;
389   c1.l.low = c0.l.high;
390   c1.ll -= q1.ll * v.ll;
391   q0.ll = c1.ll / v.l.high;
392   rhat.ll = c1.ll - q0.ll * v.l.high;
393
394   cmp1.l.high = rhat.l.low;
395   cmp1.l.low = c0.l.low;
396   cmp2.ll = q0.ll * v.l.low;
397
398   while (q0.l.high || cmp2.ll > cmp1.ll) {
399     q0.ll--;
400     rhat.ll += v.l.high;
401     if (rhat.l.high)
402       break;
403     cmp1.l.high = rhat.l.low;
404     cmp2.ll -= v.l.low;
405   }
406   q0.l.high += q1.l.low;
407
408   return q0.ll;
409 }
410
411 static guint64
412 gst_util_uint64_scale_int64 (guint64 val, guint64 num, guint64 denom)
413 {
414   GstUInt64 a0, a1, b0, b1, c0, ct, c1, result;
415   GstUInt64 v, n;
416
417   /* prepare input */
418   v.ll = val;
419   n.ll = num;
420
421   /* do 128 bits multiply
422    *                   nh   nl
423    *                *  vh   vl
424    *                ----------
425    * a0 =              vl * nl
426    * a1 =         vl * nh
427    * b0 =         vh * nl
428    * b1 =  + vh * nh
429    *       -------------------
430    * c1,c0
431    */
432   a0.ll = (guint64) v.l.low * n.l.low;
433   a1.ll = (guint64) v.l.low * n.l.high;
434   b0.ll = (guint64) v.l.high * n.l.low;
435   b1.ll = (guint64) v.l.high * n.l.high;
436
437   /* and sum together with carry into 128 bits c1, c0 */
438   c0.l.low = a0.l.low;
439   ct.ll = (guint64) a0.l.high + a1.l.low + b0.l.low;
440   c0.l.high = ct.l.low;
441   c1.ll = (guint64) a1.l.high + b0.l.high + ct.l.high + b1.ll;
442
443   /* if high bits bigger than denom, we overflow */
444   if (c1.ll >= denom)
445     goto overflow;
446
447   /* shortcut for division by 1, c1.ll should be 0 because of the
448    * overflow check above. */
449   if (denom == 1)
450     return c0.ll;
451
452   /* and 128/64 bits division, result fits 64 bits */
453   if (denom <= G_MAXUINT32) {
454     guint32 den = (guint32) denom;
455
456     /* easy case, (c1,c0)128/(den)32 division */
457     c1.l.high %= den;
458     c1.l.high = c1.ll % den;
459     c1.l.low = c0.l.high;
460     c0.l.high = c1.ll % den;
461     result.l.high = c1.ll / den;
462     result.l.low = c0.ll / den;
463   } else {
464     result.ll = gst_util_div128_64 (c1, c0, denom);
465   }
466   return result.ll;
467
468 overflow:
469   {
470     return G_MAXUINT64;
471   }
472 }
473
474 /**
475  * gst_util_uint64_scale:
476  * @val: the number to scale
477  * @num: the numerator of the scale ratio
478  * @denom: the denominator of the scale ratio
479  *
480  * Scale @val by @num / @denom, trying to avoid overflows.
481  *
482  * This function can potentially be very slow if denom > G_MAXUINT32.
483  *
484  * Returns: @val * @num / @denom, trying to avoid overflows.
485  */
486 guint64
487 gst_util_uint64_scale (guint64 val, guint64 num, guint64 denom)
488 {
489   g_return_val_if_fail (denom != 0, G_MAXUINT64);
490
491   if (num == 0)
492     return 0;
493
494   if (num == 1 && denom == 1)
495     return val;
496
497   /* if the denom is high, we need to do a 64 muldiv */
498   if (denom > G_MAXINT32)
499     goto do_int64;
500
501   /* if num and denom are low we can do a 32 bit muldiv */
502   if (num <= G_MAXINT32)
503     goto do_int32;
504
505   /* val and num are high, we need 64 muldiv */
506   if (val > G_MAXINT32)
507     goto do_int64;
508
509   /* val is low and num is high, we can swap them and do 32 muldiv */
510   return gst_util_uint64_scale_int (num, (gint) val, (gint) denom);
511
512 do_int32:
513   return gst_util_uint64_scale_int (val, (gint) num, (gint) denom);
514
515 do_int64:
516   /* to the more heavy implementations... */
517   return gst_util_uint64_scale_int64 (val, num, denom);
518 }
519
520 /**
521  * gst_util_uint64_scale_int:
522  * @val: guint64 (such as a #GstClockTime) to scale.
523  * @num: numerator of the scale factor.
524  * @denom: denominator of the scale factor.
525  *
526  * Scale a guint64 by a factor expressed as a fraction (num/denom), avoiding
527  * overflows and loss of precision.
528  *
529  * @num and @denom must be positive integers. @denom cannot be 0.
530  *
531  * Returns: @val * @num / @denom, avoiding overflow and loss of precision
532  */
533 guint64
534 gst_util_uint64_scale_int (guint64 val, gint num, gint denom)
535 {
536   GstUInt64 result;
537   GstUInt64 low, high;
538
539   g_return_val_if_fail (denom > 0, G_MAXUINT64);
540   g_return_val_if_fail (num >= 0, G_MAXUINT64);
541
542   if (num == 0)
543     return 0;
544
545   if (num == 1 && denom == 1)
546     return val;
547
548   if (val <= G_MAXUINT32)
549     /* simple case */
550     return val * num / denom;
551
552   /* do 96 bits mult/div */
553   low.ll = val;
554   result.ll = ((guint64) low.l.low) * num;
555   high.ll = ((guint64) low.l.high) * num + (result.l.high);
556
557   low.ll = high.ll / denom;
558   result.l.high = high.ll % denom;
559   result.ll /= denom;
560
561   /* avoid overflow */
562   if (low.ll + result.l.high > G_MAXUINT32)
563     goto overflow;
564
565   result.l.high += low.l.low;
566
567   return result.ll;
568
569 overflow:
570   {
571     return G_MAXUINT64;
572   }
573 }
574
575 /* -----------------------------------------------------
576  *
577  *  The following code will be moved out of the main
578  * gstreamer library someday.
579  */
580
581 #include "gstpad.h"
582
583 static void
584 string_append_indent (GString * str, gint count)
585 {
586   gint xx;
587
588   for (xx = 0; xx < count; xx++)
589     g_string_append_c (str, ' ');
590 }
591
592 /**
593  * gst_print_pad_caps:
594  * @buf: the buffer to print the caps in
595  * @indent: initial indentation
596  * @pad: the pad to print the caps from
597  *
598  * Write the pad capabilities in a human readable format into
599  * the given GString.
600  */
601 void
602 gst_print_pad_caps (GString * buf, gint indent, GstPad * pad)
603 {
604   GstCaps *caps;
605
606   caps = pad->caps;
607
608   if (!caps) {
609     string_append_indent (buf, indent);
610     g_string_printf (buf, "%s:%s has no capabilities",
611         GST_DEBUG_PAD_NAME (pad));
612   } else {
613     char *s;
614
615     s = gst_caps_to_string (caps);
616     g_string_append (buf, s);
617     g_free (s);
618   }
619 }
620
621 /**
622  * gst_print_element_args:
623  * @buf: the buffer to print the args in
624  * @indent: initial indentation
625  * @element: the element to print the args of
626  *
627  * Print the element argument in a human readable format in the given
628  * GString.
629  */
630 void
631 gst_print_element_args (GString * buf, gint indent, GstElement * element)
632 {
633   guint width;
634   GValue value = { 0, };        /* the important thing is that value.type = 0 */
635   gchar *str = NULL;
636   GParamSpec *spec, **specs, **walk;
637
638   specs = g_object_class_list_properties (G_OBJECT_GET_CLASS (element), NULL);
639
640   width = 0;
641   for (walk = specs; *walk; walk++) {
642     spec = *walk;
643     if (width < strlen (spec->name))
644       width = strlen (spec->name);
645   }
646
647   for (walk = specs; *walk; walk++) {
648     spec = *walk;
649
650     if (spec->flags & G_PARAM_READABLE) {
651       g_value_init (&value, G_PARAM_SPEC_VALUE_TYPE (spec));
652       g_object_get_property (G_OBJECT (element), spec->name, &value);
653       str = g_strdup_value_contents (&value);
654       g_value_unset (&value);
655     } else {
656       str = g_strdup ("Parameter not readable.");
657     }
658
659     string_append_indent (buf, indent);
660     g_string_append (buf, spec->name);
661     string_append_indent (buf, 2 + width - strlen (spec->name));
662     g_string_append (buf, str);
663     g_string_append_c (buf, '\n');
664
665     g_free (str);
666   }
667
668   g_free (specs);
669 }
670
671 /**
672  * gst_element_create_all_pads:
673  * @element: a #GstElement to create pads for
674  *
675  * Creates a pad for each pad template that is always available.
676  * This function is only useful during object intialization of
677  * subclasses of #GstElement.
678  */
679 void
680 gst_element_create_all_pads (GstElement * element)
681 {
682   GList *padlist;
683
684   /* FIXME: lock element */
685
686   padlist =
687       gst_element_class_get_pad_template_list (GST_ELEMENT_CLASS
688       (G_OBJECT_GET_CLASS (element)));
689
690   while (padlist) {
691     GstPadTemplate *padtempl = (GstPadTemplate *) padlist->data;
692
693     if (padtempl->presence == GST_PAD_ALWAYS) {
694       GstPad *pad;
695
696       pad = gst_pad_new_from_template (padtempl, padtempl->name_template);
697
698       gst_element_add_pad (element, pad);
699     }
700     padlist = padlist->next;
701   }
702 }
703
704 /**
705  * gst_element_get_compatible_pad_template:
706  * @element: a #GstElement to get a compatible pad template for.
707  * @compattempl: the #GstPadTemplate to find a compatible template for.
708  *
709  * Retrieves a pad template from @element that is compatible with @compattempl.
710  * Pads from compatible templates can be linked together.
711  *
712  * Returns: a compatible #GstPadTemplate, or NULL if none was found. No
713  * unreferencing is necessary.
714  */
715 GstPadTemplate *
716 gst_element_get_compatible_pad_template (GstElement * element,
717     GstPadTemplate * compattempl)
718 {
719   GstPadTemplate *newtempl = NULL;
720   GList *padlist;
721   GstElementClass *class;
722
723   g_return_val_if_fail (element != NULL, NULL);
724   g_return_val_if_fail (GST_IS_ELEMENT (element), NULL);
725   g_return_val_if_fail (compattempl != NULL, NULL);
726
727   class = GST_ELEMENT_GET_CLASS (element);
728
729   padlist = gst_element_class_get_pad_template_list (class);
730
731   GST_CAT_DEBUG (GST_CAT_ELEMENT_PADS,
732       "Looking for a suitable pad template in %s out of %d templates...",
733       GST_ELEMENT_NAME (element), g_list_length (padlist));
734
735   while (padlist) {
736     GstPadTemplate *padtempl = (GstPadTemplate *) padlist->data;
737     GstCaps *intersection;
738
739     /* Ignore name
740      * Ignore presence
741      * Check direction (must be opposite)
742      * Check caps
743      */
744     GST_CAT_LOG (GST_CAT_CAPS,
745         "checking pad template %s", padtempl->name_template);
746     if (padtempl->direction != compattempl->direction) {
747       GST_CAT_DEBUG (GST_CAT_CAPS,
748           "compatible direction: found %s pad template \"%s\"",
749           padtempl->direction == GST_PAD_SRC ? "src" : "sink",
750           padtempl->name_template);
751
752       GST_CAT_DEBUG (GST_CAT_CAPS,
753           "intersecting %" GST_PTR_FORMAT, GST_PAD_TEMPLATE_CAPS (compattempl));
754       GST_CAT_DEBUG (GST_CAT_CAPS,
755           "..and %" GST_PTR_FORMAT, GST_PAD_TEMPLATE_CAPS (padtempl));
756
757       intersection = gst_caps_intersect (GST_PAD_TEMPLATE_CAPS (compattempl),
758           GST_PAD_TEMPLATE_CAPS (padtempl));
759
760       GST_CAT_DEBUG (GST_CAT_CAPS, "caps are %scompatible %" GST_PTR_FORMAT,
761           (intersection ? "" : "not "), intersection);
762
763       if (!gst_caps_is_empty (intersection))
764         newtempl = padtempl;
765       gst_caps_unref (intersection);
766       if (newtempl)
767         break;
768     }
769
770     padlist = g_list_next (padlist);
771   }
772   if (newtempl)
773     GST_CAT_DEBUG (GST_CAT_ELEMENT_PADS,
774         "Returning new pad template %p", newtempl);
775   else
776     GST_CAT_DEBUG (GST_CAT_ELEMENT_PADS, "No compatible pad template found");
777
778   return newtempl;
779 }
780
781 static GstPad *
782 gst_element_request_pad (GstElement * element, GstPadTemplate * templ,
783     const gchar * name)
784 {
785   GstPad *newpad = NULL;
786   GstElementClass *oclass;
787
788   oclass = GST_ELEMENT_GET_CLASS (element);
789
790   if (oclass->request_new_pad)
791     newpad = (oclass->request_new_pad) (element, templ, name);
792
793   if (newpad)
794     gst_object_ref (newpad);
795
796   return newpad;
797 }
798
799
800
801 /**
802  * gst_element_get_pad_from_template:
803  * @element: a #GstElement.
804  * @templ: a #GstPadTemplate belonging to @element.
805  *
806  * Gets a pad from @element described by @templ. If the presence of @templ is
807  * #GST_PAD_REQUEST, requests a new pad. Can return %NULL for #GST_PAD_SOMETIMES
808  * templates.
809  *
810  * Returns: the #GstPad, or NULL if one could not be found or created.
811  */
812 static GstPad *
813 gst_element_get_pad_from_template (GstElement * element, GstPadTemplate * templ)
814 {
815   GstPad *ret = NULL;
816   GstPadPresence presence;
817
818   /* If this function is ever exported, we need check the validity of `element'
819    * and `templ', and to make sure the template actually belongs to the
820    * element. */
821
822   presence = GST_PAD_TEMPLATE_PRESENCE (templ);
823
824   switch (presence) {
825     case GST_PAD_ALWAYS:
826     case GST_PAD_SOMETIMES:
827       ret = gst_element_get_static_pad (element, templ->name_template);
828       if (!ret && presence == GST_PAD_ALWAYS)
829         g_warning
830             ("Element %s has an ALWAYS template %s, but no pad of the same name",
831             GST_OBJECT_NAME (element), templ->name_template);
832       break;
833
834     case GST_PAD_REQUEST:
835       ret = gst_element_request_pad (element, templ, NULL);
836       break;
837   }
838
839   return ret;
840 }
841
842 /**
843  * gst_element_request_compatible_pad:
844  * @element: a #GstElement.
845  * @templ: the #GstPadTemplate to which the new pad should be able to link.
846  *
847  * Requests a pad from @element. The returned pad should be unlinked and
848  * compatible with @templ. Might return an existing pad, or request a new one.
849  *
850  * Returns: a #GstPad, or %NULL if one could not be found or created.
851  */
852 GstPad *
853 gst_element_request_compatible_pad (GstElement * element,
854     GstPadTemplate * templ)
855 {
856   GstPadTemplate *templ_new;
857   GstPad *pad = NULL;
858
859   g_return_val_if_fail (GST_IS_ELEMENT (element), NULL);
860   g_return_val_if_fail (GST_IS_PAD_TEMPLATE (templ), NULL);
861
862   /* FIXME: should really loop through the templates, testing each for
863    *      compatibility and pad availability. */
864   templ_new = gst_element_get_compatible_pad_template (element, templ);
865   if (templ_new)
866     pad = gst_element_get_pad_from_template (element, templ_new);
867
868   /* This can happen for non-request pads. No need to unref. */
869   if (pad && GST_PAD_PEER (pad))
870     pad = NULL;
871
872   return pad;
873 }
874
875 /**
876  * gst_element_get_compatible_pad:
877  * @element: a #GstElement in which the pad should be found.
878  * @pad: the #GstPad to find a compatible one for.
879  * @caps: the #GstCaps to use as a filter.
880  *
881  * Looks for an unlinked pad to which the given pad can link. It is not
882  * guaranteed that linking the pads will work, though it should work in most
883  * cases.
884  *
885  * Returns: the #GstPad to which a link can be made, or %NULL if one cannot be
886  * found.
887  */
888 GstPad *
889 gst_element_get_compatible_pad (GstElement * element, GstPad * pad,
890     const GstCaps * caps)
891 {
892   GstIterator *pads;
893   GstPadTemplate *templ;
894   GstCaps *templcaps;
895   GstPad *foundpad = NULL;
896   gboolean done;
897
898   /* FIXME check for caps compatibility */
899
900   g_return_val_if_fail (GST_IS_ELEMENT (element), NULL);
901   g_return_val_if_fail (GST_IS_PAD (pad), NULL);
902
903   GST_CAT_DEBUG (GST_CAT_ELEMENT_PADS,
904       "finding pad in %s compatible with %s:%s",
905       GST_ELEMENT_NAME (element), GST_DEBUG_PAD_NAME (pad));
906
907   g_return_val_if_fail (GST_PAD_PEER (pad) == NULL, NULL);
908
909   done = FALSE;
910   /* try to get an existing unlinked pad */
911   pads = gst_element_iterate_pads (element);
912   while (!done) {
913     gpointer padptr;
914
915     switch (gst_iterator_next (pads, &padptr)) {
916       case GST_ITERATOR_OK:
917       {
918         GstPad *peer;
919         GstPad *current;
920
921         current = GST_PAD (padptr);
922
923         GST_CAT_LOG (GST_CAT_ELEMENT_PADS, "examining pad %s:%s",
924             GST_DEBUG_PAD_NAME (current));
925
926         peer = gst_pad_get_peer (current);
927
928         if (peer == NULL && gst_pad_can_link (pad, current)) {
929
930           GST_CAT_DEBUG (GST_CAT_ELEMENT_PADS,
931               "found existing unlinked pad %s:%s",
932               GST_DEBUG_PAD_NAME (current));
933
934           gst_iterator_free (pads);
935
936           return current;
937         } else {
938           GST_CAT_DEBUG (GST_CAT_ELEMENT_PADS, "unreffing pads");
939
940           gst_object_unref (current);
941           if (peer)
942             gst_object_unref (peer);
943         }
944         break;
945       }
946       case GST_ITERATOR_DONE:
947         done = TRUE;
948         break;
949       case GST_ITERATOR_RESYNC:
950         gst_iterator_resync (pads);
951         break;
952       case GST_ITERATOR_ERROR:
953         g_assert_not_reached ();
954         break;
955     }
956   }
957   gst_iterator_free (pads);
958
959   /* try to create a new one */
960   /* requesting is a little crazy, we need a template. Let's create one */
961   templcaps = gst_pad_get_caps (pad);
962
963   templ = gst_pad_template_new ((gchar *) GST_PAD_NAME (pad),
964       GST_PAD_DIRECTION (pad), GST_PAD_ALWAYS, templcaps);
965   foundpad = gst_element_request_compatible_pad (element, templ);
966   gst_object_unref (templ);
967
968   if (foundpad) {
969     GST_CAT_DEBUG (GST_CAT_ELEMENT_PADS,
970         "found existing request pad %s:%s", GST_DEBUG_PAD_NAME (foundpad));
971     return foundpad;
972   }
973
974   GST_CAT_INFO_OBJECT (GST_CAT_ELEMENT_PADS, element,
975       "Could not find a compatible pad to link to %s:%s",
976       GST_DEBUG_PAD_NAME (pad));
977   return NULL;
978 }
979
980 /**
981  * gst_element_state_get_name:
982  * @state: a #GstState to get the name of.
983  *
984  * Gets a string representing the given state.
985  *
986  * Returns: a string with the name of the state.
987  */
988 const gchar *
989 gst_element_state_get_name (GstState state)
990 {
991   switch (state) {
992 #ifdef GST_DEBUG_COLOR
993     case GST_STATE_VOID_PENDING:
994       return "VOID_PENDING";
995       break;
996     case GST_STATE_NULL:
997       return "\033[01;34mNULL\033[00m";
998       break;
999     case GST_STATE_READY:
1000       return "\033[01;31mREADY\033[00m";
1001       break;
1002     case GST_STATE_PLAYING:
1003       return "\033[01;32mPLAYING\033[00m";
1004       break;
1005     case GST_STATE_PAUSED:
1006       return "\033[01;33mPAUSED\033[00m";
1007       break;
1008     default:
1009       /* This is a memory leak */
1010       return g_strdup_printf ("\033[01;35;41mUNKNOWN!\033[00m(%d)", state);
1011 #else
1012     case GST_STATE_VOID_PENDING:
1013       return "VOID_PENDING";
1014       break;
1015     case GST_STATE_NULL:
1016       return "NULL";
1017       break;
1018     case GST_STATE_READY:
1019       return "READY";
1020       break;
1021     case GST_STATE_PLAYING:
1022       return "PLAYING";
1023       break;
1024     case GST_STATE_PAUSED:
1025       return "PAUSED";
1026       break;
1027     default:
1028       /* This is a memory leak */
1029       return g_strdup_printf ("UNKNOWN!(%d)", state);
1030 #endif
1031   }
1032   return "";
1033 }
1034
1035 /**
1036  * gst_element_factory_can_src_caps :
1037  * @factory: factory to query
1038  * @caps: the caps to check
1039  *
1040  * Checks if the factory can source the given capability.
1041  *
1042  * Returns: true if it can src the capabilities
1043  */
1044 gboolean
1045 gst_element_factory_can_src_caps (GstElementFactory * factory,
1046     const GstCaps * caps)
1047 {
1048   GList *templates;
1049
1050   g_return_val_if_fail (factory != NULL, FALSE);
1051   g_return_val_if_fail (caps != NULL, FALSE);
1052
1053   templates = factory->staticpadtemplates;
1054
1055   while (templates) {
1056     GstStaticPadTemplate *template = (GstStaticPadTemplate *) templates->data;
1057
1058     if (template->direction == GST_PAD_SRC) {
1059       if (gst_caps_is_always_compatible (gst_static_caps_get (&template->
1060                   static_caps), caps))
1061         return TRUE;
1062     }
1063     templates = g_list_next (templates);
1064   }
1065
1066   return FALSE;
1067 }
1068
1069 /**
1070  * gst_element_factory_can_sink_caps :
1071  * @factory: factory to query
1072  * @caps: the caps to check
1073  *
1074  * Checks if the factory can sink the given capability.
1075  *
1076  * Returns: true if it can sink the capabilities
1077  */
1078 gboolean
1079 gst_element_factory_can_sink_caps (GstElementFactory * factory,
1080     const GstCaps * caps)
1081 {
1082   GList *templates;
1083
1084   g_return_val_if_fail (factory != NULL, FALSE);
1085   g_return_val_if_fail (caps != NULL, FALSE);
1086
1087   templates = factory->staticpadtemplates;
1088
1089   while (templates) {
1090     GstStaticPadTemplate *template = (GstStaticPadTemplate *) templates->data;
1091
1092     if (template->direction == GST_PAD_SINK) {
1093       if (gst_caps_is_always_compatible (caps,
1094               gst_static_caps_get (&template->static_caps)))
1095         return TRUE;
1096     }
1097     templates = g_list_next (templates);
1098   }
1099
1100   return FALSE;
1101 }
1102
1103
1104 /* if return val is true, *direct_child is a caller-owned ref on the direct
1105  * child of ancestor that is part of object's ancestry */
1106 static gboolean
1107 object_has_ancestor (GstObject * object, GstObject * ancestor,
1108     GstObject ** direct_child)
1109 {
1110   GstObject *child, *parent;
1111
1112   if (direct_child)
1113     *direct_child = NULL;
1114
1115   child = gst_object_ref (object);
1116   parent = gst_object_get_parent (object);
1117
1118   while (parent) {
1119     if (ancestor == parent) {
1120       if (direct_child)
1121         *direct_child = child;
1122       else
1123         gst_object_unref (child);
1124       gst_object_unref (parent);
1125       return TRUE;
1126     }
1127
1128     gst_object_unref (child);
1129     child = parent;
1130     parent = gst_object_get_parent (parent);
1131   }
1132
1133   gst_object_unref (child);
1134
1135   return FALSE;
1136 }
1137
1138 /* caller owns return */
1139 static GstObject *
1140 find_common_root (GstObject * o1, GstObject * o2)
1141 {
1142   GstObject *top = o1;
1143   GstObject *kid1, *kid2;
1144   GstObject *root = NULL;
1145
1146   while (GST_OBJECT_PARENT (top))
1147     top = GST_OBJECT_PARENT (top);
1148
1149   /* the itsy-bitsy spider... */
1150
1151   if (!object_has_ancestor (o2, top, &kid2))
1152     return NULL;
1153
1154   root = gst_object_ref (top);
1155   while (TRUE) {
1156     if (!object_has_ancestor (o1, kid2, &kid1)) {
1157       gst_object_unref (kid2);
1158       return root;
1159     }
1160     root = kid2;
1161     if (!object_has_ancestor (o2, kid1, &kid2)) {
1162       gst_object_unref (kid1);
1163       return root;
1164     }
1165     root = kid1;
1166   }
1167 }
1168
1169 /* caller does not own return */
1170 static GstPad *
1171 ghost_up (GstElement * e, GstPad * pad)
1172 {
1173   static gint ghost_pad_index = 0;
1174   GstPad *gpad;
1175   gchar *name;
1176   GstObject *parent = GST_OBJECT_PARENT (e);
1177
1178   name = g_strdup_printf ("ghost%d", ghost_pad_index++);
1179   gpad = gst_ghost_pad_new (name, pad);
1180   g_free (name);
1181
1182   if (!gst_element_add_pad ((GstElement *) parent, gpad)) {
1183     g_warning ("Pad named %s already exists in element %s\n",
1184         GST_OBJECT_NAME (gpad), GST_OBJECT_NAME (parent));
1185     gst_object_unref ((GstObject *) gpad);
1186     return NULL;
1187   }
1188
1189   return gpad;
1190 }
1191
1192 static void
1193 remove_pad (gpointer ppad, gpointer unused)
1194 {
1195   GstPad *pad = ppad;
1196
1197   if (!gst_element_remove_pad ((GstElement *) GST_OBJECT_PARENT (pad), pad))
1198     g_warning ("Couldn't remove pad %s from element %s",
1199         GST_OBJECT_NAME (pad), GST_OBJECT_NAME (GST_OBJECT_PARENT (pad)));
1200 }
1201
1202 static gboolean
1203 prepare_link_maybe_ghosting (GstPad ** src, GstPad ** sink,
1204     GSList ** pads_created)
1205 {
1206   GstObject *root;
1207   GstObject *e1, *e2;
1208   GSList *pads_created_local = NULL;
1209
1210   g_assert (pads_created);
1211
1212   e1 = GST_OBJECT_PARENT (*src);
1213   e2 = GST_OBJECT_PARENT (*sink);
1214
1215   if (GST_OBJECT_PARENT (e1) == GST_OBJECT_PARENT (e2)) {
1216     GST_CAT_INFO (GST_CAT_PADS, "%s and %s in same bin, no need for ghost pads",
1217         GST_OBJECT_NAME (e1), GST_OBJECT_NAME (e2));
1218     return TRUE;
1219   }
1220
1221   GST_CAT_INFO (GST_CAT_PADS, "%s and %s not in same bin, making ghost pads",
1222       GST_OBJECT_NAME (e1), GST_OBJECT_NAME (e2));
1223
1224   /* we need to setup some ghost pads */
1225   root = find_common_root (e1, e2);
1226   if (!root) {
1227     g_warning
1228         ("Trying to connect elements that don't share a common ancestor: %s and %s\n",
1229         GST_ELEMENT_NAME (e1), GST_ELEMENT_NAME (e2));
1230     return FALSE;
1231   }
1232
1233   while (GST_OBJECT_PARENT (e1) != root) {
1234     *src = ghost_up ((GstElement *) e1, *src);
1235     if (!*src)
1236       goto cleanup_fail;
1237     e1 = GST_OBJECT_PARENT (*src);
1238     pads_created_local = g_slist_prepend (pads_created_local, *src);
1239   }
1240   while (GST_OBJECT_PARENT (e2) != root) {
1241     *sink = ghost_up ((GstElement *) e2, *sink);
1242     if (!*sink)
1243       goto cleanup_fail;
1244     e2 = GST_OBJECT_PARENT (*sink);
1245     pads_created_local = g_slist_prepend (pads_created_local, *sink);
1246   }
1247
1248   gst_object_unref (root);
1249   *pads_created = g_slist_concat (*pads_created, pads_created_local);
1250   return TRUE;
1251
1252 cleanup_fail:
1253   gst_object_unref (root);
1254   g_slist_foreach (pads_created_local, remove_pad, NULL);
1255   g_slist_free (pads_created_local);
1256   return FALSE;
1257 }
1258
1259 static gboolean
1260 pad_link_maybe_ghosting (GstPad * src, GstPad * sink)
1261 {
1262   GSList *pads_created = NULL;
1263   gboolean ret;
1264
1265   if (!prepare_link_maybe_ghosting (&src, &sink, &pads_created)) {
1266     ret = FALSE;
1267   } else {
1268     ret = (gst_pad_link (src, sink) == GST_PAD_LINK_OK);
1269   }
1270
1271   if (!ret) {
1272     g_slist_foreach (pads_created, remove_pad, NULL);
1273   }
1274   g_slist_free (pads_created);
1275
1276   return ret;
1277 }
1278
1279 /**
1280  * gst_element_link_pads:
1281  * @src: a #GstElement containing the source pad.
1282  * @srcpadname: the name of the #GstPad in source element or NULL for any pad.
1283  * @dest: the #GstElement containing the destination pad.
1284  * @destpadname: the name of the #GstPad in destination element,
1285  * or NULL for any pad.
1286  *
1287  * Links the two named pads of the source and destination elements.
1288  * Side effect is that if one of the pads has no parent, it becomes a
1289  * child of the parent of the other element.  If they have different
1290  * parents, the link fails.
1291  *
1292  * Returns: TRUE if the pads could be linked, FALSE otherwise.
1293  */
1294 gboolean
1295 gst_element_link_pads (GstElement * src, const gchar * srcpadname,
1296     GstElement * dest, const gchar * destpadname)
1297 {
1298   const GList *srcpads, *destpads, *srctempls, *desttempls, *l;
1299   GstPad *srcpad, *destpad;
1300   GstPadTemplate *srctempl, *desttempl;
1301   GstElementClass *srcclass, *destclass;
1302
1303   /* checks */
1304   g_return_val_if_fail (GST_IS_ELEMENT (src), FALSE);
1305   g_return_val_if_fail (GST_IS_ELEMENT (dest), FALSE);
1306
1307   srcclass = GST_ELEMENT_GET_CLASS (src);
1308   destclass = GST_ELEMENT_GET_CLASS (dest);
1309
1310   GST_CAT_INFO (GST_CAT_ELEMENT_PADS,
1311       "trying to link element %s:%s to element %s:%s", GST_ELEMENT_NAME (src),
1312       srcpadname ? srcpadname : "(any)", GST_ELEMENT_NAME (dest),
1313       destpadname ? destpadname : "(any)");
1314
1315   /* get a src pad */
1316   if (srcpadname) {
1317     /* name specified, look it up */
1318     srcpad = gst_element_get_pad (src, srcpadname);
1319     if (!srcpad) {
1320       GST_CAT_DEBUG (GST_CAT_ELEMENT_PADS, "no pad %s:%s",
1321           GST_ELEMENT_NAME (src), srcpadname);
1322       return FALSE;
1323     } else {
1324       if (!(GST_PAD_DIRECTION (srcpad) == GST_PAD_SRC)) {
1325         GST_CAT_DEBUG (GST_CAT_ELEMENT_PADS, "pad %s:%s is no src pad",
1326             GST_DEBUG_PAD_NAME (srcpad));
1327         gst_object_unref (srcpad);
1328         return FALSE;
1329       }
1330       if (GST_PAD_PEER (srcpad) != NULL) {
1331         GST_CAT_DEBUG (GST_CAT_ELEMENT_PADS, "pad %s:%s is already linked",
1332             GST_DEBUG_PAD_NAME (srcpad));
1333         gst_object_unref (srcpad);
1334         return FALSE;
1335       }
1336     }
1337     srcpads = NULL;
1338   } else {
1339     /* no name given, get the first available pad */
1340     GST_OBJECT_LOCK (src);
1341     srcpads = GST_ELEMENT_PADS (src);
1342     srcpad = srcpads ? GST_PAD_CAST (srcpads->data) : NULL;
1343     if (srcpad)
1344       gst_object_ref (srcpad);
1345     GST_OBJECT_UNLOCK (src);
1346   }
1347
1348   /* get a destination pad */
1349   if (destpadname) {
1350     /* name specified, look it up */
1351     destpad = gst_element_get_pad (dest, destpadname);
1352     if (!destpad) {
1353       GST_CAT_DEBUG (GST_CAT_ELEMENT_PADS, "no pad %s:%s",
1354           GST_ELEMENT_NAME (dest), destpadname);
1355       return FALSE;
1356     } else {
1357       if (!(GST_PAD_DIRECTION (destpad) == GST_PAD_SINK)) {
1358         GST_CAT_DEBUG (GST_CAT_ELEMENT_PADS, "pad %s:%s is no sink pad",
1359             GST_DEBUG_PAD_NAME (destpad));
1360         gst_object_unref (destpad);
1361         return FALSE;
1362       }
1363       if (GST_PAD_PEER (destpad) != NULL) {
1364         GST_CAT_DEBUG (GST_CAT_ELEMENT_PADS, "pad %s:%s is already linked",
1365             GST_DEBUG_PAD_NAME (destpad));
1366         gst_object_unref (destpad);
1367         return FALSE;
1368       }
1369     }
1370     destpads = NULL;
1371   } else {
1372     /* no name given, get the first available pad */
1373     GST_OBJECT_LOCK (dest);
1374     destpads = GST_ELEMENT_PADS (dest);
1375     destpad = destpads ? GST_PAD_CAST (destpads->data) : NULL;
1376     if (destpad)
1377       gst_object_ref (destpad);
1378     GST_OBJECT_UNLOCK (dest);
1379   }
1380
1381   if (srcpadname && destpadname) {
1382     gboolean result;
1383
1384     /* two explicitly specified pads */
1385     result = pad_link_maybe_ghosting (srcpad, destpad);
1386
1387     gst_object_unref (srcpad);
1388     gst_object_unref (destpad);
1389
1390     return result;
1391   }
1392
1393   if (srcpad) {
1394     /* loop through the allowed pads in the source, trying to find a
1395      * compatible destination pad */
1396     GST_CAT_DEBUG (GST_CAT_ELEMENT_PADS,
1397         "looping through allowed src and dest pads");
1398     do {
1399       GST_CAT_DEBUG (GST_CAT_ELEMENT_PADS, "trying src pad %s:%s",
1400           GST_DEBUG_PAD_NAME (srcpad));
1401       if ((GST_PAD_DIRECTION (srcpad) == GST_PAD_SRC) &&
1402           (GST_PAD_PEER (srcpad) == NULL)) {
1403         GstPad *temp;
1404
1405         if (destpadname) {
1406           temp = destpad;
1407           gst_object_ref (temp);
1408         } else {
1409           temp = gst_element_get_compatible_pad (dest, srcpad, NULL);
1410         }
1411
1412         if (temp && pad_link_maybe_ghosting (srcpad, temp)) {
1413           GST_CAT_DEBUG (GST_CAT_ELEMENT_PADS, "linked pad %s:%s to pad %s:%s",
1414               GST_DEBUG_PAD_NAME (srcpad), GST_DEBUG_PAD_NAME (temp));
1415           if (destpad)
1416             gst_object_unref (destpad);
1417           gst_object_unref (srcpad);
1418           gst_object_unref (temp);
1419           return TRUE;
1420         }
1421
1422         if (temp) {
1423           gst_object_unref (temp);
1424         }
1425       }
1426       /* find a better way for this mess */
1427       if (srcpads) {
1428         srcpads = g_list_next (srcpads);
1429         if (srcpads) {
1430           gst_object_unref (srcpad);
1431           srcpad = GST_PAD_CAST (srcpads->data);
1432           gst_object_ref (srcpad);
1433         }
1434       }
1435     } while (srcpads);
1436   }
1437   if (srcpadname) {
1438     GST_CAT_DEBUG (GST_CAT_ELEMENT_PADS, "no link possible from %s:%s to %s",
1439         GST_DEBUG_PAD_NAME (srcpad), GST_ELEMENT_NAME (dest));
1440     if (srcpad)
1441       gst_object_unref (srcpad);
1442     srcpad = NULL;
1443     if (destpad)
1444       gst_object_unref (destpad);
1445     destpad = NULL;
1446   } else {
1447     if (srcpad)
1448       gst_object_unref (srcpad);
1449     srcpad = NULL;
1450   }
1451
1452   if (destpad) {
1453     /* loop through the existing pads in the destination */
1454     do {
1455       GST_CAT_DEBUG (GST_CAT_ELEMENT_PADS, "trying dest pad %s:%s",
1456           GST_DEBUG_PAD_NAME (destpad));
1457       if ((GST_PAD_DIRECTION (destpad) == GST_PAD_SINK) &&
1458           (GST_PAD_PEER (destpad) == NULL)) {
1459         GstPad *temp = gst_element_get_compatible_pad (src, destpad, NULL);
1460
1461         if (temp && pad_link_maybe_ghosting (temp, destpad)) {
1462           GST_CAT_DEBUG (GST_CAT_ELEMENT_PADS, "linked pad %s:%s to pad %s:%s",
1463               GST_DEBUG_PAD_NAME (temp), GST_DEBUG_PAD_NAME (destpad));
1464           gst_object_unref (temp);
1465           gst_object_unref (destpad);
1466           if (srcpad)
1467             gst_object_unref (srcpad);
1468           return TRUE;
1469         }
1470         if (temp) {
1471           gst_object_unref (temp);
1472         }
1473       }
1474       if (destpads) {
1475         destpads = g_list_next (destpads);
1476         if (destpads) {
1477           gst_object_unref (destpad);
1478           destpad = GST_PAD_CAST (destpads->data);
1479           gst_object_ref (destpad);
1480         }
1481       }
1482     } while (destpads);
1483   }
1484
1485   if (destpadname) {
1486     GST_CAT_DEBUG (GST_CAT_ELEMENT_PADS, "no link possible from %s to %s:%s",
1487         GST_ELEMENT_NAME (src), GST_DEBUG_PAD_NAME (destpad));
1488     gst_object_unref (destpad);
1489     if (srcpad)
1490       gst_object_unref (srcpad);
1491     return FALSE;
1492   } else {
1493     if (srcpad)
1494       gst_object_unref (srcpad);
1495     srcpad = NULL;
1496     if (destpad)
1497       gst_object_unref (destpad);
1498     destpad = NULL;
1499   }
1500
1501   GST_CAT_DEBUG (GST_CAT_ELEMENT_PADS,
1502       "we might have request pads on both sides, checking...");
1503   srctempls = gst_element_class_get_pad_template_list (srcclass);
1504   desttempls = gst_element_class_get_pad_template_list (destclass);
1505
1506   if (srctempls && desttempls) {
1507     while (srctempls) {
1508       srctempl = (GstPadTemplate *) srctempls->data;
1509       if (srctempl->presence == GST_PAD_REQUEST) {
1510         for (l = desttempls; l; l = l->next) {
1511           desttempl = (GstPadTemplate *) l->data;
1512           if (desttempl->presence == GST_PAD_REQUEST &&
1513               desttempl->direction != srctempl->direction) {
1514             if (gst_caps_is_always_compatible (gst_pad_template_get_caps
1515                     (srctempl), gst_pad_template_get_caps (desttempl))) {
1516               srcpad =
1517                   gst_element_get_request_pad (src, srctempl->name_template);
1518               destpad =
1519                   gst_element_get_request_pad (dest, desttempl->name_template);
1520               if (pad_link_maybe_ghosting (srcpad, destpad)) {
1521                 GST_CAT_DEBUG (GST_CAT_ELEMENT_PADS,
1522                     "linked pad %s:%s to pad %s:%s",
1523                     GST_DEBUG_PAD_NAME (srcpad), GST_DEBUG_PAD_NAME (destpad));
1524                 gst_object_unref (srcpad);
1525                 gst_object_unref (destpad);
1526                 return TRUE;
1527               }
1528               /* it failed, so we release the request pads */
1529               gst_element_release_request_pad (src, srcpad);
1530               gst_element_release_request_pad (dest, destpad);
1531             }
1532           }
1533         }
1534       }
1535       srctempls = srctempls->next;
1536     }
1537   }
1538
1539   GST_CAT_DEBUG (GST_CAT_ELEMENT_PADS, "no link possible from %s to %s",
1540       GST_ELEMENT_NAME (src), GST_ELEMENT_NAME (dest));
1541   return FALSE;
1542 }
1543
1544 /**
1545  * gst_element_link_pads_filtered:
1546  * @src: a #GstElement containing the source pad.
1547  * @srcpadname: the name of the #GstPad in source element or NULL for any pad.
1548  * @dest: the #GstElement containing the destination pad.
1549  * @destpadname: the name of the #GstPad in destination element or NULL for any pad.
1550  * @filter: the #GstCaps to filter the link, or #NULL for no filter.
1551  *
1552  * Links the two named pads of the source and destination elements. Side effect
1553  * is that if one of the pads has no parent, it becomes a child of the parent of
1554  * the other element. If they have different parents, the link fails. If @caps
1555  * is not #NULL, makes sure that the caps of the link is a subset of @caps.
1556  *
1557  * Returns: TRUE if the pads could be linked, FALSE otherwise.
1558  */
1559 gboolean
1560 gst_element_link_pads_filtered (GstElement * src, const gchar * srcpadname,
1561     GstElement * dest, const gchar * destpadname, GstCaps * filter)
1562 {
1563   /* checks */
1564   g_return_val_if_fail (GST_IS_ELEMENT (src), FALSE);
1565   g_return_val_if_fail (GST_IS_ELEMENT (dest), FALSE);
1566   g_return_val_if_fail (filter == NULL || GST_IS_CAPS (filter), FALSE);
1567
1568   if (filter) {
1569     GstElement *capsfilter;
1570     GstObject *parent;
1571     GstState state, pending;
1572
1573     capsfilter = gst_element_factory_make ("capsfilter", NULL);
1574     if (!capsfilter) {
1575       GST_ERROR ("Could not make a capsfilter");
1576       return FALSE;
1577     }
1578
1579     parent = gst_object_get_parent (GST_OBJECT (src));
1580     g_return_val_if_fail (GST_IS_BIN (parent), FALSE);
1581
1582     gst_element_get_state (GST_ELEMENT_CAST (parent), &state, &pending, 0);
1583
1584     if (!gst_bin_add (GST_BIN (parent), capsfilter)) {
1585       GST_ERROR ("Could not add capsfilter");
1586       gst_object_unref (capsfilter);
1587       gst_object_unref (parent);
1588       return FALSE;
1589     }
1590
1591     if (pending != GST_STATE_VOID_PENDING)
1592       state = pending;
1593
1594     gst_element_set_state (capsfilter, state);
1595
1596     gst_object_unref (parent);
1597
1598     g_object_set (capsfilter, "caps", filter, NULL);
1599
1600     if (gst_element_link_pads (src, srcpadname, capsfilter, "sink")
1601         && gst_element_link_pads (capsfilter, "src", dest, destpadname)) {
1602       return TRUE;
1603     } else {
1604       GST_INFO ("Could not link elements");
1605       gst_bin_remove (GST_BIN (GST_OBJECT_PARENT (capsfilter)), capsfilter);
1606       /* will unref and unlink as appropriate */
1607       return FALSE;
1608     }
1609   } else {
1610     return gst_element_link_pads (src, srcpadname, dest, destpadname);
1611   }
1612 }
1613
1614 /**
1615  * gst_element_link:
1616  * @src: a #GstElement containing the source pad.
1617  * @dest: the #GstElement containing the destination pad.
1618  *
1619  * Links @src to @dest. The link must be from source to
1620  * destination; the other direction will not be tried. The function looks for
1621  * existing pads that aren't linked yet. It will request new pads if necessary.
1622  * If multiple links are possible, only one is established.
1623  *
1624  * Returns: TRUE if the elements could be linked, FALSE otherwise.
1625  */
1626 gboolean
1627 gst_element_link (GstElement * src, GstElement * dest)
1628 {
1629   return gst_element_link_pads_filtered (src, NULL, dest, NULL, NULL);
1630 }
1631
1632 /**
1633  * gst_element_link_many:
1634  * @element_1: the first #GstElement in the link chain.
1635  * @element_2: the second #GstElement in the link chain.
1636  * @...: the NULL-terminated list of elements to link in order.
1637  *
1638  * Chain together a series of elements. Uses gst_element_link().
1639  *
1640  * Returns: TRUE on success, FALSE otherwise.
1641  */
1642 gboolean
1643 gst_element_link_many (GstElement * element_1, GstElement * element_2, ...)
1644 {
1645   va_list args;
1646
1647   g_return_val_if_fail (GST_IS_ELEMENT (element_1), FALSE);
1648   g_return_val_if_fail (GST_IS_ELEMENT (element_2), FALSE);
1649
1650   va_start (args, element_2);
1651
1652   while (element_2) {
1653     if (!gst_element_link (element_1, element_2))
1654       return FALSE;
1655
1656     element_1 = element_2;
1657     element_2 = va_arg (args, GstElement *);
1658   }
1659
1660   va_end (args);
1661
1662   return TRUE;
1663 }
1664
1665 /**
1666  * gst_element_link_filtered:
1667  * @src: a #GstElement containing the source pad.
1668  * @dest: the #GstElement containing the destination pad.
1669  * @filter: the #GstCaps to filter the link, or #NULL for no filter.
1670  *
1671  * Links @src to @dest using the given caps as filtercaps.
1672  * The link must be from source to
1673  * destination; the other direction will not be tried. The function looks for
1674  * existing pads that aren't linked yet. It will request new pads if necessary.
1675  * If multiple links are possible, only one is established.
1676  *
1677  * Returns: TRUE if the pads could be linked, FALSE otherwise.
1678  */
1679 gboolean
1680 gst_element_link_filtered (GstElement * src, GstElement * dest,
1681     GstCaps * filter)
1682 {
1683   return gst_element_link_pads_filtered (src, NULL, dest, NULL, filter);
1684 }
1685
1686 /**
1687  * gst_element_unlink_pads:
1688  * @src: a #GstElement containing the source pad.
1689  * @srcpadname: the name of the #GstPad in source element.
1690  * @dest: a #GstElement containing the destination pad.
1691  * @destpadname: the name of the #GstPad in destination element.
1692  *
1693  * Unlinks the two named pads of the source and destination elements.
1694  */
1695 void
1696 gst_element_unlink_pads (GstElement * src, const gchar * srcpadname,
1697     GstElement * dest, const gchar * destpadname)
1698 {
1699   GstPad *srcpad, *destpad;
1700
1701   g_return_if_fail (src != NULL);
1702   g_return_if_fail (GST_IS_ELEMENT (src));
1703   g_return_if_fail (srcpadname != NULL);
1704   g_return_if_fail (dest != NULL);
1705   g_return_if_fail (GST_IS_ELEMENT (dest));
1706   g_return_if_fail (destpadname != NULL);
1707
1708   /* obtain the pads requested */
1709   srcpad = gst_element_get_pad (src, srcpadname);
1710   if (srcpad == NULL) {
1711     GST_WARNING_OBJECT (src, "source element has no pad \"%s\"", srcpadname);
1712     return;
1713   }
1714   destpad = gst_element_get_pad (dest, destpadname);
1715   if (destpad == NULL) {
1716     GST_WARNING_OBJECT (dest, "destination element has no pad \"%s\"",
1717         destpadname);
1718     gst_object_unref (srcpad);
1719     return;
1720   }
1721
1722   /* we're satisified they can be unlinked, let's do it */
1723   gst_pad_unlink (srcpad, destpad);
1724   gst_object_unref (srcpad);
1725   gst_object_unref (destpad);
1726 }
1727
1728 /**
1729  * gst_element_unlink_many:
1730  * @element_1: the first #GstElement in the link chain.
1731  * @element_2: the second #GstElement in the link chain.
1732  * @...: the NULL-terminated list of elements to unlink in order.
1733  *
1734  * Unlinks a series of elements. Uses gst_element_unlink().
1735  */
1736 void
1737 gst_element_unlink_many (GstElement * element_1, GstElement * element_2, ...)
1738 {
1739   va_list args;
1740
1741   g_return_if_fail (element_1 != NULL && element_2 != NULL);
1742   g_return_if_fail (GST_IS_ELEMENT (element_1) && GST_IS_ELEMENT (element_2));
1743
1744   va_start (args, element_2);
1745
1746   while (element_2) {
1747     gst_element_unlink (element_1, element_2);
1748
1749     element_1 = element_2;
1750     element_2 = va_arg (args, GstElement *);
1751   }
1752
1753   va_end (args);
1754 }
1755
1756 /**
1757  * gst_element_unlink:
1758  * @src: the source #GstElement to unlink.
1759  * @dest: the sink #GstElement to unlink.
1760  *
1761  * Unlinks all source pads of the source element with all sink pads
1762  * of the sink element to which they are linked.
1763  */
1764 void
1765 gst_element_unlink (GstElement * src, GstElement * dest)
1766 {
1767   GstIterator *pads;
1768   gboolean done = FALSE;
1769
1770   g_return_if_fail (GST_IS_ELEMENT (src));
1771   g_return_if_fail (GST_IS_ELEMENT (dest));
1772
1773   GST_CAT_DEBUG (GST_CAT_ELEMENT_PADS, "unlinking \"%s\" and \"%s\"",
1774       GST_ELEMENT_NAME (src), GST_ELEMENT_NAME (dest));
1775
1776   pads = gst_element_iterate_pads (src);
1777   while (!done) {
1778     gpointer data;
1779
1780     switch (gst_iterator_next (pads, &data)) {
1781       case GST_ITERATOR_OK:
1782       {
1783         GstPad *pad = GST_PAD_CAST (data);
1784
1785         if (GST_PAD_IS_SRC (pad)) {
1786           GstPad *peerpad = gst_pad_get_peer (pad);
1787
1788           /* see if the pad is connected and is really a pad
1789            * of dest */
1790           if (peerpad) {
1791             GstElement *peerelem;
1792
1793             peerelem = gst_pad_get_parent_element (peerpad);
1794
1795             if (peerelem == dest) {
1796               gst_pad_unlink (pad, peerpad);
1797             }
1798             if (peerelem)
1799               gst_object_unref (peerelem);
1800
1801             gst_object_unref (peerpad);
1802           }
1803         }
1804         gst_object_unref (pad);
1805         break;
1806       }
1807       case GST_ITERATOR_RESYNC:
1808         gst_iterator_resync (pads);
1809         break;
1810       case GST_ITERATOR_DONE:
1811         done = TRUE;
1812         break;
1813       default:
1814         g_assert_not_reached ();
1815         break;
1816     }
1817   }
1818 }
1819
1820 /**
1821  * gst_element_query_position:
1822  * @element: a #GstElement to invoke the position query on.
1823  * @format: a pointer to the #GstFormat asked for.
1824  *          On return contains the #GstFormat used.
1825  * @cur: A location in which to store the current position, or NULL.
1826  *
1827  * Queries an element for the stream position.
1828  *
1829  * Returns: TRUE if the query could be performed.
1830  */
1831 gboolean
1832 gst_element_query_position (GstElement * element, GstFormat * format,
1833     gint64 * cur)
1834 {
1835   GstQuery *query;
1836   gboolean ret;
1837
1838   g_return_val_if_fail (GST_IS_ELEMENT (element), FALSE);
1839   g_return_val_if_fail (format != NULL, FALSE);
1840
1841   query = gst_query_new_position (*format);
1842   ret = gst_element_query (element, query);
1843
1844   if (ret)
1845     gst_query_parse_position (query, format, cur);
1846
1847   gst_query_unref (query);
1848
1849   return ret;
1850 }
1851
1852 /**
1853  * gst_element_query_duration:
1854  * @element: a #GstElement to invoke the duration query on.
1855  * @format: a pointer to the #GstFormat asked for.
1856  *          On return contains the #GstFormat used.
1857  * @duration: A location in which to store the total duration, or NULL.
1858  *
1859  * Queries an element for the total stream duration.
1860  *
1861  * Returns: TRUE if the query could be performed.
1862  */
1863 gboolean
1864 gst_element_query_duration (GstElement * element, GstFormat * format,
1865     gint64 * duration)
1866 {
1867   GstQuery *query;
1868   gboolean ret;
1869
1870   g_return_val_if_fail (GST_IS_ELEMENT (element), FALSE);
1871   g_return_val_if_fail (format != NULL, FALSE);
1872
1873   query = gst_query_new_duration (*format);
1874   ret = gst_element_query (element, query);
1875
1876   if (ret)
1877     gst_query_parse_duration (query, format, duration);
1878
1879   gst_query_unref (query);
1880
1881   return ret;
1882 }
1883
1884 /**
1885  * gst_element_query_convert:
1886  * @element: a #GstElement to invoke the convert query on.
1887  * @src_format: a #GstFormat to convert from.
1888  * @src_val: a value to convert.
1889  * @dest_format: a pointer to the #GstFormat to convert to.
1890  * @dest_val: a pointer to the result.
1891  *
1892  * Queries an element to convert @src_val in @src_format to @dest_format.
1893  *
1894  * Returns: TRUE if the query could be performed.
1895  */
1896 gboolean
1897 gst_element_query_convert (GstElement * element, GstFormat src_format,
1898     gint64 src_val, GstFormat * dest_format, gint64 * dest_val)
1899 {
1900   GstQuery *query;
1901   gboolean ret;
1902
1903   g_return_val_if_fail (GST_IS_ELEMENT (element), FALSE);
1904   g_return_val_if_fail (dest_format != NULL, FALSE);
1905   g_return_val_if_fail (dest_val != NULL, FALSE);
1906
1907   if (*dest_format == src_format) {
1908     *dest_val = src_val;
1909     return TRUE;
1910   }
1911
1912   query = gst_query_new_convert (src_format, src_val, *dest_format);
1913   ret = gst_element_query (element, query);
1914
1915   if (ret)
1916     gst_query_parse_convert (query, NULL, NULL, dest_format, dest_val);
1917
1918   gst_query_unref (query);
1919
1920   return ret;
1921 }
1922
1923 /**
1924  * gst_pad_can_link:
1925  * @srcpad: the source #GstPad to link.
1926  * @sinkpad: the sink #GstPad to link.
1927  *
1928  * Checks if the source pad and the sink pad can be linked.
1929  * Both @srcpad and @sinkpad must be unlinked.
1930  *
1931  * Returns: TRUE if the pads can be linked, FALSE otherwise.
1932  */
1933 gboolean
1934 gst_pad_can_link (GstPad * srcpad, GstPad * sinkpad)
1935 {
1936   /* FIXME This function is gross.  It's almost a direct copy of
1937    * gst_pad_link_filtered().  Any decent programmer would attempt
1938    * to merge the two functions, which I will do some day. --ds
1939    */
1940
1941   /* generic checks */
1942   g_return_val_if_fail (GST_IS_PAD (srcpad), FALSE);
1943   g_return_val_if_fail (GST_IS_PAD (sinkpad), FALSE);
1944
1945   GST_CAT_INFO (GST_CAT_PADS, "trying to link %s:%s and %s:%s",
1946       GST_DEBUG_PAD_NAME (srcpad), GST_DEBUG_PAD_NAME (sinkpad));
1947
1948   /* FIXME: shouldn't we convert this to g_return_val_if_fail? */
1949   if (GST_PAD_PEER (srcpad) != NULL) {
1950     GST_CAT_INFO (GST_CAT_PADS, "Source pad %s:%s has a peer, failed",
1951         GST_DEBUG_PAD_NAME (srcpad));
1952     return FALSE;
1953   }
1954   if (GST_PAD_PEER (sinkpad) != NULL) {
1955     GST_CAT_INFO (GST_CAT_PADS, "Sink pad %s:%s has a peer, failed",
1956         GST_DEBUG_PAD_NAME (sinkpad));
1957     return FALSE;
1958   }
1959   if (!GST_PAD_IS_SRC (srcpad)) {
1960     GST_CAT_INFO (GST_CAT_PADS, "Src pad %s:%s is not source pad, failed",
1961         GST_DEBUG_PAD_NAME (srcpad));
1962     return FALSE;
1963   }
1964   if (!GST_PAD_IS_SINK (sinkpad)) {
1965     GST_CAT_INFO (GST_CAT_PADS, "Sink pad %s:%s is not sink pad, failed",
1966         GST_DEBUG_PAD_NAME (sinkpad));
1967     return FALSE;
1968   }
1969   if (GST_PAD_PARENT (srcpad) == NULL) {
1970     GST_CAT_INFO (GST_CAT_PADS, "Src pad %s:%s has no parent, failed",
1971         GST_DEBUG_PAD_NAME (srcpad));
1972     return FALSE;
1973   }
1974   if (GST_PAD_PARENT (sinkpad) == NULL) {
1975     GST_CAT_INFO (GST_CAT_PADS, "Sink pad %s:%s has no parent, failed",
1976         GST_DEBUG_PAD_NAME (srcpad));
1977     return FALSE;
1978   }
1979
1980   return TRUE;
1981 }
1982
1983 /**
1984  * gst_pad_use_fixed_caps:
1985  * @pad: the pad to use
1986  *
1987  * A helper function you can use that sets the
1988  * @gst_pad_get_fixed_caps_func as the getcaps function for the
1989  * pad. This way the function will always return the negotiated caps
1990  * or in case the pad is not negotiated, the padtemplate caps.
1991  *
1992  * Use this function on a pad that, once _set_caps() has been called
1993  * on it, cannot be renegotiated to something else.
1994  */
1995 void
1996 gst_pad_use_fixed_caps (GstPad * pad)
1997 {
1998   gst_pad_set_getcaps_function (pad, gst_pad_get_fixed_caps_func);
1999 }
2000
2001 /**
2002  * gst_pad_get_fixed_caps_func:
2003  * @pad: the pad to use
2004  *
2005  * A helper function you can use as a GetCaps function that
2006  * will return the currently negotiated caps or the padtemplate
2007  * when NULL.
2008  *
2009  * Returns: The currently negotiated caps or the padtemplate.
2010  */
2011 GstCaps *
2012 gst_pad_get_fixed_caps_func (GstPad * pad)
2013 {
2014   GstCaps *result;
2015
2016   g_return_val_if_fail (GST_IS_PAD (pad), NULL);
2017
2018   if (GST_PAD_CAPS (pad)) {
2019     result = GST_PAD_CAPS (pad);
2020
2021     GST_CAT_DEBUG (GST_CAT_CAPS,
2022         "using pad caps %p %" GST_PTR_FORMAT, result, result);
2023
2024     result = gst_caps_ref (result);
2025     goto done;
2026   }
2027   if (GST_PAD_PAD_TEMPLATE (pad)) {
2028     GstPadTemplate *templ = GST_PAD_PAD_TEMPLATE (pad);
2029
2030     result = GST_PAD_TEMPLATE_CAPS (templ);
2031     GST_CAT_DEBUG (GST_CAT_CAPS,
2032         "using pad template %p with caps %p %" GST_PTR_FORMAT, templ, result,
2033         result);
2034
2035     result = gst_caps_ref (result);
2036     goto done;
2037   }
2038   GST_CAT_DEBUG (GST_CAT_CAPS, "pad has no caps");
2039   result = gst_caps_new_empty ();
2040
2041 done:
2042   return result;
2043 }
2044
2045 /**
2046  * gst_pad_get_parent_element:
2047  * @pad: a pad
2048  *
2049  * Gets the parent of @pad, cast to a #GstElement. If a @pad has no parent or
2050  * its parent is not an element, return NULL.
2051  *
2052  * Returns: The parent of the pad. The caller has a reference on the parent, so
2053  * unref when you're finished with it.
2054  *
2055  * MT safe.
2056  */
2057 GstElement *
2058 gst_pad_get_parent_element (GstPad * pad)
2059 {
2060   GstObject *p;
2061
2062   g_return_val_if_fail (GST_IS_PAD (pad), NULL);
2063
2064   p = gst_object_get_parent (GST_OBJECT_CAST (pad));
2065
2066   if (p && !GST_IS_ELEMENT (p)) {
2067     gst_object_unref (p);
2068     p = NULL;
2069   }
2070   return GST_ELEMENT_CAST (p);
2071 }
2072
2073 /**
2074  * gst_object_default_error:
2075  * @source: the #GstObject that initiated the error.
2076  * @error: the GError.
2077  * @debug: an additional debug information string, or NULL.
2078  *
2079  * A default error function.
2080  *
2081  * The default handler will simply print the error string using g_print.
2082  */
2083 void
2084 gst_object_default_error (GstObject * source, GError * error, gchar * debug)
2085 {
2086   gchar *name = gst_object_get_path_string (source);
2087
2088   g_print (_("ERROR: from element %s: %s\n"), name, error->message);
2089   if (debug)
2090     g_print (_("Additional debug info:\n%s\n"), debug);
2091
2092   g_free (name);
2093 }
2094
2095 /**
2096  * gst_bin_add_many:
2097  * @bin: a #GstBin
2098  * @element_1: the #GstElement element to add to the bin
2099  * @...: additional elements to add to the bin
2100  *
2101  * Adds a NULL-terminated list of elements to a bin.  This function is
2102  * equivalent to calling gst_bin_add() for each member of the list.
2103  */
2104 void
2105 gst_bin_add_many (GstBin * bin, GstElement * element_1, ...)
2106 {
2107   va_list args;
2108
2109   g_return_if_fail (GST_IS_BIN (bin));
2110   g_return_if_fail (GST_IS_ELEMENT (element_1));
2111
2112   va_start (args, element_1);
2113
2114   while (element_1) {
2115     gst_bin_add (bin, element_1);
2116
2117     element_1 = va_arg (args, GstElement *);
2118   }
2119
2120   va_end (args);
2121 }
2122
2123 /**
2124  * gst_bin_remove_many:
2125  * @bin: a #GstBin
2126  * @element_1: the first #GstElement to remove from the bin
2127  * @...: NULL-terminated list of elements to remove from the bin
2128  *
2129  * Remove a list of elements from a bin. This function is equivalent
2130  * to calling gst_bin_remove() with each member of the list.
2131  */
2132 void
2133 gst_bin_remove_many (GstBin * bin, GstElement * element_1, ...)
2134 {
2135   va_list args;
2136
2137   g_return_if_fail (GST_IS_BIN (bin));
2138   g_return_if_fail (GST_IS_ELEMENT (element_1));
2139
2140   va_start (args, element_1);
2141
2142   while (element_1) {
2143     gst_bin_remove (bin, element_1);
2144
2145     element_1 = va_arg (args, GstElement *);
2146   }
2147
2148   va_end (args);
2149 }
2150
2151 static void
2152 gst_element_populate_std_props (GObjectClass * klass, const gchar * prop_name,
2153     guint arg_id, GParamFlags flags)
2154 {
2155   GQuark prop_id = g_quark_from_string (prop_name);
2156   GParamSpec *pspec;
2157
2158   static GQuark fd_id = 0;
2159   static GQuark blocksize_id;
2160   static GQuark bytesperread_id;
2161   static GQuark dump_id;
2162   static GQuark filesize_id;
2163   static GQuark mmapsize_id;
2164   static GQuark location_id;
2165   static GQuark offset_id;
2166   static GQuark silent_id;
2167   static GQuark touch_id;
2168
2169   if (!fd_id) {
2170     fd_id = g_quark_from_static_string ("fd");
2171     blocksize_id = g_quark_from_static_string ("blocksize");
2172     bytesperread_id = g_quark_from_static_string ("bytesperread");
2173     dump_id = g_quark_from_static_string ("dump");
2174     filesize_id = g_quark_from_static_string ("filesize");
2175     mmapsize_id = g_quark_from_static_string ("mmapsize");
2176     location_id = g_quark_from_static_string ("location");
2177     offset_id = g_quark_from_static_string ("offset");
2178     silent_id = g_quark_from_static_string ("silent");
2179     touch_id = g_quark_from_static_string ("touch");
2180   }
2181
2182   if (prop_id == fd_id) {
2183     pspec = g_param_spec_int ("fd", "File-descriptor",
2184         "File-descriptor for the file being read", 0, G_MAXINT, 0, flags);
2185   } else if (prop_id == blocksize_id) {
2186     pspec = g_param_spec_ulong ("blocksize", "Block Size",
2187         "Block size to read per buffer", 0, G_MAXULONG, 4096, flags);
2188
2189   } else if (prop_id == bytesperread_id) {
2190     pspec = g_param_spec_int ("bytesperread", "Bytes per read",
2191         "Number of bytes to read per buffer", G_MININT, G_MAXINT, 0, flags);
2192
2193   } else if (prop_id == dump_id) {
2194     pspec = g_param_spec_boolean ("dump", "Dump",
2195         "Dump bytes to stdout", FALSE, flags);
2196
2197   } else if (prop_id == filesize_id) {
2198     pspec = g_param_spec_int64 ("filesize", "File Size",
2199         "Size of the file being read", 0, G_MAXINT64, 0, flags);
2200
2201   } else if (prop_id == mmapsize_id) {
2202     pspec = g_param_spec_ulong ("mmapsize", "mmap() Block Size",
2203         "Size in bytes of mmap()d regions", 0, G_MAXULONG, 4 * 1048576, flags);
2204
2205   } else if (prop_id == location_id) {
2206     pspec = g_param_spec_string ("location", "File Location",
2207         "Location of the file to read", NULL, flags);
2208
2209   } else if (prop_id == offset_id) {
2210     pspec = g_param_spec_int64 ("offset", "File Offset",
2211         "Byte offset of current read pointer", 0, G_MAXINT64, 0, flags);
2212
2213   } else if (prop_id == silent_id) {
2214     pspec = g_param_spec_boolean ("silent", "Silent", "Don't produce events",
2215         FALSE, flags);
2216
2217   } else if (prop_id == touch_id) {
2218     pspec = g_param_spec_boolean ("touch", "Touch read data",
2219         "Touch data to force disk read before " "push ()", TRUE, flags);
2220   } else {
2221     g_warning ("Unknown - 'standard' property '%s' id %d from klass %s",
2222         prop_name, arg_id, g_type_name (G_OBJECT_CLASS_TYPE (klass)));
2223     pspec = NULL;
2224   }
2225
2226   if (pspec) {
2227     g_object_class_install_property (klass, arg_id, pspec);
2228   }
2229 }
2230
2231 /**
2232  * gst_element_class_install_std_props:
2233  * @klass: the #GstElementClass to add the properties to.
2234  * @first_name: the name of the first property.
2235  * in a NULL terminated
2236  * @...: the id and flags of the first property, followed by
2237  * further 'name', 'id', 'flags' triplets and terminated by NULL.
2238  *
2239  * Adds a list of standardized properties with types to the @klass.
2240  * the id is for the property switch in your get_prop method, and
2241  * the flags determine readability / writeability.
2242  **/
2243 void
2244 gst_element_class_install_std_props (GstElementClass * klass,
2245     const gchar * first_name, ...)
2246 {
2247   const char *name;
2248
2249   va_list args;
2250
2251   g_return_if_fail (GST_IS_ELEMENT_CLASS (klass));
2252
2253   va_start (args, first_name);
2254
2255   name = first_name;
2256
2257   while (name) {
2258     int arg_id = va_arg (args, int);
2259     int flags = va_arg (args, int);
2260
2261     gst_element_populate_std_props ((GObjectClass *) klass, name, arg_id,
2262         flags);
2263
2264     name = va_arg (args, char *);
2265   }
2266
2267   va_end (args);
2268 }
2269
2270
2271 /**
2272  * gst_buffer_merge:
2273  * @buf1: the first source #GstBuffer to merge.
2274  * @buf2: the second source #GstBuffer to merge.
2275  *
2276  * Create a new buffer that is the concatenation of the two source
2277  * buffers.  The original source buffers will not be modified or
2278  * unref'd.  Make sure you unref the source buffers if they are not used
2279  * anymore afterwards.
2280  *
2281  * If the buffers point to contiguous areas of memory, the buffer
2282  * is created without copying the data.
2283  *
2284  * Returns: the new #GstBuffer which is the concatenation of the source buffers.
2285  */
2286 GstBuffer *
2287 gst_buffer_merge (GstBuffer * buf1, GstBuffer * buf2)
2288 {
2289   GstBuffer *result;
2290
2291   /* we're just a specific case of the more general gst_buffer_span() */
2292   result = gst_buffer_span (buf1, 0, buf2, buf1->size + buf2->size);
2293
2294   return result;
2295 }
2296
2297 /**
2298  * gst_buffer_join:
2299  * @buf1: the first source #GstBuffer.
2300  * @buf2: the second source #GstBuffer.
2301  *
2302  * Create a new buffer that is the concatenation of the two source
2303  * buffers, and unrefs the original source buffers.
2304  *
2305  * If the buffers point to contiguous areas of memory, the buffer
2306  * is created without copying the data.
2307  *
2308  * Returns: the new #GstBuffer which is the concatenation of the source buffers.
2309  */
2310 GstBuffer *
2311 gst_buffer_join (GstBuffer * buf1, GstBuffer * buf2)
2312 {
2313   GstBuffer *result;
2314
2315   result = gst_buffer_span (buf1, 0, buf2, buf1->size + buf2->size);
2316   gst_buffer_unref (buf1);
2317   gst_buffer_unref (buf2);
2318
2319   return result;
2320 }
2321
2322
2323 /**
2324  * gst_buffer_stamp:
2325  * @dest: buffer to stamp
2326  * @src: buffer to stamp from
2327  *
2328  * Copies additional information (the timestamp, duration, and offset start 
2329  * and end) from one buffer to the other.
2330  *
2331  * This function does not copy any buffer flags or caps.
2332  */
2333 void
2334 gst_buffer_stamp (GstBuffer * dest, const GstBuffer * src)
2335 {
2336   g_return_if_fail (dest != NULL);
2337   g_return_if_fail (src != NULL);
2338
2339   GST_BUFFER_TIMESTAMP (dest) = GST_BUFFER_TIMESTAMP (src);
2340   GST_BUFFER_DURATION (dest) = GST_BUFFER_DURATION (src);
2341   GST_BUFFER_OFFSET (dest) = GST_BUFFER_OFFSET (src);
2342   GST_BUFFER_OFFSET_END (dest) = GST_BUFFER_OFFSET_END (src);
2343 }
2344
2345 static gboolean
2346 intersect_caps_func (GstPad * pad, GValue * ret, GstPad * orig)
2347 {
2348   if (pad != orig) {
2349     GstCaps *peercaps, *existing;
2350
2351     existing = g_value_get_pointer (ret);
2352     peercaps = gst_pad_peer_get_caps (pad);
2353     if (peercaps == NULL)
2354       peercaps = gst_caps_new_any ();
2355     g_value_set_pointer (ret, gst_caps_intersect (existing, peercaps));
2356     gst_caps_unref (existing);
2357     gst_caps_unref (peercaps);
2358   }
2359   gst_object_unref (pad);
2360   return TRUE;
2361 }
2362
2363 /**
2364  * gst_pad_proxy_getcaps:
2365  * @pad: a #GstPad to proxy.
2366  *
2367  * Calls gst_pad_get_allowed_caps() for every other pad belonging to the
2368  * same element as @pad, and returns the intersection of the results.
2369  *
2370  * This function is useful as a default getcaps function for an element
2371  * that can handle any stream format, but requires all its pads to have
2372  * the same caps.  Two such elements are tee and aggregator.
2373  *
2374  * Returns: the intersection of the other pads' allowed caps.
2375  */
2376 GstCaps *
2377 gst_pad_proxy_getcaps (GstPad * pad)
2378 {
2379   GstElement *element;
2380   GstCaps *caps, *intersected;
2381   GstIterator *iter;
2382   GstIteratorResult res;
2383   GValue ret = { 0, };
2384
2385   g_return_val_if_fail (GST_IS_PAD (pad), NULL);
2386
2387   GST_DEBUG ("proxying getcaps for %s:%s", GST_DEBUG_PAD_NAME (pad));
2388
2389   element = gst_pad_get_parent_element (pad);
2390   if (element == NULL)
2391     return NULL;
2392
2393   iter = gst_element_iterate_pads (element);
2394
2395   g_value_init (&ret, G_TYPE_POINTER);
2396   g_value_set_pointer (&ret, gst_caps_new_any ());
2397
2398   res = gst_iterator_fold (iter, (GstIteratorFoldFunction) intersect_caps_func,
2399       &ret, pad);
2400   gst_iterator_free (iter);
2401
2402   if (res != GST_ITERATOR_DONE)
2403     goto pads_changed;
2404
2405   gst_object_unref (element);
2406
2407   caps = g_value_get_pointer (&ret);
2408   g_value_unset (&ret);
2409
2410   intersected = gst_caps_intersect (caps, gst_pad_get_pad_template_caps (pad));
2411   gst_caps_unref (caps);
2412
2413   return intersected;
2414
2415   /* ERRORS */
2416 pads_changed:
2417   {
2418     g_warning ("Pad list changed during capsnego for element %s",
2419         GST_ELEMENT_NAME (element));
2420     gst_object_unref (element);
2421     return NULL;
2422   }
2423 }
2424
2425 typedef struct
2426 {
2427   GstPad *orig;
2428   GstCaps *caps;
2429 } LinkData;
2430
2431 static gboolean
2432 link_fold_func (GstPad * pad, GValue * ret, LinkData * data)
2433 {
2434   gboolean success = TRUE;
2435
2436   if (pad != data->orig) {
2437     success = gst_pad_set_caps (pad, data->caps);
2438     g_value_set_boolean (ret, success);
2439   }
2440   gst_object_unref (pad);
2441
2442   return success;
2443 }
2444
2445 /**
2446  * gst_pad_proxy_setcaps
2447  * @pad: a #GstPad to proxy from
2448  * @caps: the #GstCaps to link with
2449  *
2450  * Calls gst_pad_set_caps() for every other pad belonging to the
2451  * same element as @pad.  If gst_pad_set_caps() fails on any pad,
2452  * the proxy setcaps fails. May be used only during negotiation.
2453  *
2454  * Returns: TRUE if sucessful
2455  */
2456 gboolean
2457 gst_pad_proxy_setcaps (GstPad * pad, GstCaps * caps)
2458 {
2459   GstElement *element;
2460   GstIterator *iter;
2461   GstIteratorResult res;
2462   GValue ret = { 0, };
2463   LinkData data;
2464
2465   g_return_val_if_fail (GST_IS_PAD (pad), FALSE);
2466   g_return_val_if_fail (caps != NULL, FALSE);
2467
2468   GST_DEBUG ("proxying pad link for %s:%s", GST_DEBUG_PAD_NAME (pad));
2469
2470   element = gst_pad_get_parent_element (pad);
2471   if (element == NULL)
2472     return FALSE;
2473
2474   iter = gst_element_iterate_pads (element);
2475
2476   g_value_init (&ret, G_TYPE_BOOLEAN);
2477   g_value_set_boolean (&ret, TRUE);
2478   data.orig = pad;
2479   data.caps = caps;
2480
2481   res = gst_iterator_fold (iter, (GstIteratorFoldFunction) link_fold_func,
2482       &ret, &data);
2483   gst_iterator_free (iter);
2484
2485   if (res != GST_ITERATOR_DONE)
2486     goto pads_changed;
2487
2488   gst_object_unref (element);
2489
2490   /* ok not to unset the gvalue */
2491   return g_value_get_boolean (&ret);
2492
2493   /* ERRORS */
2494 pads_changed:
2495   {
2496     g_warning ("Pad list changed during proxy_pad_link for element %s",
2497         GST_ELEMENT_NAME (element));
2498     gst_object_unref (element);
2499     return FALSE;
2500   }
2501 }
2502
2503 /**
2504  * gst_pad_query_position:
2505  * @pad: a #GstPad to invoke the position query on.
2506  * @format: a pointer to the #GstFormat asked for.
2507  *          On return contains the #GstFormat used.
2508  * @cur: A location in which to store the current position, or NULL.
2509  *
2510  * Queries a pad for the stream position.
2511  *
2512  * Returns: TRUE if the query could be performed.
2513  */
2514 gboolean
2515 gst_pad_query_position (GstPad * pad, GstFormat * format, gint64 * cur)
2516 {
2517   GstQuery *query;
2518   gboolean ret;
2519
2520   g_return_val_if_fail (GST_IS_PAD (pad), FALSE);
2521   g_return_val_if_fail (format != NULL, FALSE);
2522
2523   query = gst_query_new_position (*format);
2524   ret = gst_pad_query (pad, query);
2525
2526   if (ret)
2527     gst_query_parse_position (query, format, cur);
2528
2529   gst_query_unref (query);
2530
2531   return ret;
2532 }
2533
2534 /**
2535  * gst_pad_query_duration:
2536  * @pad: a #GstPad to invoke the duration query on.
2537  * @format: a pointer to the #GstFormat asked for.
2538  *          On return contains the #GstFormat used.
2539  * @duration: A location in which to store the total duration, or NULL.
2540  *
2541  * Queries a pad for the total stream duration.
2542  *
2543  * Returns: TRUE if the query could be performed.
2544  */
2545 gboolean
2546 gst_pad_query_duration (GstPad * pad, GstFormat * format, gint64 * duration)
2547 {
2548   GstQuery *query;
2549   gboolean ret;
2550
2551   g_return_val_if_fail (GST_IS_PAD (pad), FALSE);
2552   g_return_val_if_fail (format != NULL, FALSE);
2553
2554   query = gst_query_new_duration (*format);
2555   ret = gst_pad_query (pad, query);
2556
2557   if (ret)
2558     gst_query_parse_duration (query, format, duration);
2559
2560   gst_query_unref (query);
2561
2562   return ret;
2563 }
2564
2565 /**
2566  * gst_pad_query_convert:
2567  * @pad: a #GstPad to invoke the convert query on.
2568  * @src_format: a #GstFormat to convert from.
2569  * @src_val: a value to convert.
2570  * @dest_format: a pointer to the #GstFormat to convert to.
2571  * @dest_val: a pointer to the result.
2572  *
2573  * Queries a pad to convert @src_val in @src_format to @dest_format.
2574  *
2575  * Returns: TRUE if the query could be performed.
2576  */
2577 gboolean
2578 gst_pad_query_convert (GstPad * pad, GstFormat src_format, gint64 src_val,
2579     GstFormat * dest_format, gint64 * dest_val)
2580 {
2581   GstQuery *query;
2582   gboolean ret;
2583
2584   g_return_val_if_fail (GST_IS_PAD (pad), FALSE);
2585   g_return_val_if_fail (src_val >= 0, FALSE);
2586   g_return_val_if_fail (dest_format != NULL, FALSE);
2587   g_return_val_if_fail (dest_val != NULL, FALSE);
2588
2589   if (*dest_format == src_format) {
2590     *dest_val = src_val;
2591     return TRUE;
2592   }
2593
2594   query = gst_query_new_convert (src_format, src_val, *dest_format);
2595   ret = gst_pad_query (pad, query);
2596
2597   if (ret)
2598     gst_query_parse_convert (query, NULL, NULL, dest_format, dest_val);
2599
2600   gst_query_unref (query);
2601
2602   return ret;
2603 }
2604
2605 /**
2606  * gst_atomic_int_set:
2607  * @atomic_int: pointer to an atomic integer
2608  * @value: value to set
2609  *
2610  * Unconditionally sets the atomic integer to @value.
2611  */
2612 void
2613 gst_atomic_int_set (gint * atomic_int, gint value)
2614 {
2615   int ignore;
2616
2617   *atomic_int = value;
2618   /* read acts as a memory barrier */
2619   ignore = g_atomic_int_get (atomic_int);
2620 }
2621
2622 /**
2623  * gst_pad_add_data_probe:
2624  * @pad: pad to add the data probe handler to
2625  * @handler: function to call when data is passed over pad
2626  * @data: data to pass along with the handler
2627  *
2628  * Adds a "data probe" to a pad. This function will be called whenever data
2629  * passes through a pad. In this case data means both events and buffers. The
2630  * probe will be called with the data as an argument. Note that the data will
2631  * have a reference count greater than 1, so it will be immutable -- you must
2632  * not change it.
2633  *
2634  * For source pads, the probe will be called after the blocking function, if any
2635  * (see gst_pad_set_blocked_async()), but before looking up the peer to chain
2636  * to. For sink pads, the probe function will be called before configuring the
2637  * sink with new caps, if any, and before calling the pad's chain function.
2638  *
2639  * Your data probe should return TRUE to let the data continue to flow, or FALSE
2640  * to drop it. Dropping data is rarely useful, but occasionally comes in handy
2641  * with events.
2642  *
2643  * Although probes are implemented internally by connecting @handler to the
2644  * have-data signal on the pad, if you want to remove a probe it is insufficient
2645  * to only call g_signal_handler_disconnect on the returned handler id. To
2646  * remove a probe, use the appropriate function, such as
2647  * gst_pad_remove_data_probe().
2648  *
2649  * Returns: The handler id.
2650  */
2651 gulong
2652 gst_pad_add_data_probe (GstPad * pad, GCallback handler, gpointer data)
2653 {
2654   gulong sigid;
2655   gboolean was_ghost = FALSE;
2656
2657   g_return_val_if_fail (GST_IS_PAD (pad), 0);
2658   g_return_val_if_fail (handler != NULL, 0);
2659
2660   if (GST_IS_GHOST_PAD (pad)) {
2661     pad = gst_ghost_pad_get_target (GST_GHOST_PAD (pad));
2662     if (!pad) {
2663       return 0;
2664     }
2665     was_ghost = TRUE;
2666   }
2667
2668   GST_OBJECT_LOCK (pad);
2669   sigid = g_signal_connect (pad, "have-data", handler, data);
2670   GST_PAD_DO_EVENT_SIGNALS (pad)++;
2671   GST_PAD_DO_BUFFER_SIGNALS (pad)++;
2672   GST_DEBUG ("adding data probe to pad %s:%s, now %d data, %d event probes",
2673       GST_DEBUG_PAD_NAME (pad),
2674       GST_PAD_DO_BUFFER_SIGNALS (pad), GST_PAD_DO_EVENT_SIGNALS (pad));
2675   GST_OBJECT_UNLOCK (pad);
2676
2677   if (was_ghost) {
2678     gst_object_unref (pad);
2679   }
2680
2681   return sigid;
2682 }
2683
2684 /**
2685  * gst_pad_add_event_probe:
2686  * @pad: pad to add the event probe handler to
2687  * @handler: function to call when data is passed over pad
2688  * @data: data to pass along with the handler
2689  *
2690  * Adds a probe that will be called for all events passing through a pad. See
2691  * gst_pad_add_data_probe() for more information.
2692  *
2693  * Returns: The handler id
2694  */
2695 gulong
2696 gst_pad_add_event_probe (GstPad * pad, GCallback handler, gpointer data)
2697 {
2698   gulong sigid;
2699   gboolean was_ghost = FALSE;
2700
2701   g_return_val_if_fail (GST_IS_PAD (pad), 0);
2702   g_return_val_if_fail (handler != NULL, 0);
2703
2704   if (GST_IS_GHOST_PAD (pad)) {
2705     pad = gst_ghost_pad_get_target (GST_GHOST_PAD (pad));
2706     if (!pad) {
2707       return 0;
2708     }
2709     was_ghost = TRUE;
2710   }
2711
2712   GST_OBJECT_LOCK (pad);
2713   sigid = g_signal_connect (pad, "have-data::event", handler, data);
2714   GST_PAD_DO_EVENT_SIGNALS (pad)++;
2715   GST_DEBUG ("adding event probe to pad %s:%s, now %d probes",
2716       GST_DEBUG_PAD_NAME (pad), GST_PAD_DO_EVENT_SIGNALS (pad));
2717   GST_OBJECT_UNLOCK (pad);
2718
2719   if (was_ghost) {
2720     gst_object_unref (pad);
2721   }
2722
2723   return sigid;
2724 }
2725
2726 /**
2727  * gst_pad_add_buffer_probe:
2728  * @pad: pad to add the buffer probe handler to
2729  * @handler: function to call when data is passed over pad
2730  * @data: data to pass along with the handler
2731  *
2732  * Adds a probe that will be called for all buffers passing through a pad. See
2733  * gst_pad_add_data_probe() for more information.
2734  *
2735  * Returns: The handler id
2736  */
2737 gulong
2738 gst_pad_add_buffer_probe (GstPad * pad, GCallback handler, gpointer data)
2739 {
2740   gulong sigid;
2741   gboolean was_ghost = FALSE;
2742
2743   g_return_val_if_fail (GST_IS_PAD (pad), 0);
2744   g_return_val_if_fail (handler != NULL, 0);
2745
2746   if (GST_IS_GHOST_PAD (pad)) {
2747     pad = gst_ghost_pad_get_target (GST_GHOST_PAD (pad));
2748     if (!pad) {
2749       return 0;
2750     }
2751     was_ghost = TRUE;
2752   }
2753
2754   GST_OBJECT_LOCK (pad);
2755   sigid = g_signal_connect (pad, "have-data::buffer", handler, data);
2756   GST_PAD_DO_BUFFER_SIGNALS (pad)++;
2757   GST_DEBUG ("adding buffer probe to pad %s:%s, now %d probes",
2758       GST_DEBUG_PAD_NAME (pad), GST_PAD_DO_BUFFER_SIGNALS (pad));
2759   GST_OBJECT_UNLOCK (pad);
2760
2761   if (was_ghost) {
2762     gst_object_unref (pad);
2763   }
2764
2765   return sigid;
2766 }
2767
2768 /**
2769  * gst_pad_remove_data_probe:
2770  * @pad: pad to remove the data probe handler from
2771  * @handler_id: handler id returned from gst_pad_add_data_probe
2772  *
2773  * Removes a data probe from @pad.
2774  */
2775 void
2776 gst_pad_remove_data_probe (GstPad * pad, guint handler_id)
2777 {
2778   gboolean was_ghost = FALSE;
2779
2780   g_return_if_fail (GST_IS_PAD (pad));
2781   g_return_if_fail (handler_id > 0);
2782
2783   if (GST_IS_GHOST_PAD (pad)) {
2784     pad = gst_ghost_pad_get_target (GST_GHOST_PAD (pad));
2785     if (!pad) {
2786       return;
2787     }
2788     was_ghost = TRUE;
2789   }
2790
2791   GST_OBJECT_LOCK (pad);
2792   g_signal_handler_disconnect (pad, handler_id);
2793   GST_PAD_DO_BUFFER_SIGNALS (pad)--;
2794   GST_PAD_DO_EVENT_SIGNALS (pad)--;
2795   GST_DEBUG
2796       ("removed data probe from pad %s:%s, now %d event, %d buffer probes",
2797       GST_DEBUG_PAD_NAME (pad), GST_PAD_DO_EVENT_SIGNALS (pad),
2798       GST_PAD_DO_BUFFER_SIGNALS (pad));
2799   GST_OBJECT_UNLOCK (pad);
2800
2801   if (was_ghost) {
2802     gst_object_unref (pad);
2803   }
2804 }
2805
2806 /**
2807  * gst_pad_remove_event_probe:
2808  * @pad: pad to remove the event probe handler from
2809  * @handler_id: handler id returned from gst_pad_add_event_probe
2810  *
2811  * Removes an event probe from @pad.
2812  */
2813 void
2814 gst_pad_remove_event_probe (GstPad * pad, guint handler_id)
2815 {
2816   gboolean was_ghost = FALSE;
2817
2818   g_return_if_fail (GST_IS_PAD (pad));
2819   g_return_if_fail (handler_id > 0);
2820
2821   if (GST_IS_GHOST_PAD (pad)) {
2822     pad = gst_ghost_pad_get_target (GST_GHOST_PAD (pad));
2823     if (!pad) {
2824       return;
2825     }
2826     was_ghost = TRUE;
2827   }
2828
2829   GST_OBJECT_LOCK (pad);
2830   g_signal_handler_disconnect (pad, handler_id);
2831   GST_PAD_DO_EVENT_SIGNALS (pad)--;
2832   GST_DEBUG ("removed event probe from pad %s:%s, now %d event probes",
2833       GST_DEBUG_PAD_NAME (pad), GST_PAD_DO_EVENT_SIGNALS (pad));
2834   GST_OBJECT_UNLOCK (pad);
2835
2836   if (was_ghost) {
2837     gst_object_unref (pad);
2838   }
2839 }
2840
2841 /**
2842  * gst_pad_remove_buffer_probe:
2843  * @pad: pad to remove the buffer probe handler from
2844  * @handler_id: handler id returned from gst_pad_add_buffer_probe
2845  *
2846  * Removes a buffer probe from @pad.
2847  */
2848 void
2849 gst_pad_remove_buffer_probe (GstPad * pad, guint handler_id)
2850 {
2851   gboolean was_ghost = FALSE;
2852
2853   g_return_if_fail (GST_IS_PAD (pad));
2854   g_return_if_fail (handler_id > 0);
2855
2856   if (GST_IS_GHOST_PAD (pad)) {
2857     pad = gst_ghost_pad_get_target (GST_GHOST_PAD (pad));
2858     if (!pad) {
2859       return;
2860     }
2861     was_ghost = TRUE;
2862   }
2863
2864   GST_OBJECT_LOCK (pad);
2865   g_signal_handler_disconnect (pad, handler_id);
2866   GST_PAD_DO_BUFFER_SIGNALS (pad)--;
2867   GST_DEBUG ("removed buffer probe from pad %s:%s, now %d buffer probes",
2868       GST_DEBUG_PAD_NAME (pad), GST_PAD_DO_BUFFER_SIGNALS (pad));
2869   GST_OBJECT_UNLOCK (pad);
2870
2871   if (was_ghost) {
2872     gst_object_unref (pad);
2873   }
2874 }
2875
2876 /**
2877  * gst_element_found_tags_for_pad:
2878  * @element: element for which to post taglist to bus.
2879  * @pad: pad on which to push tag-event.
2880  * @list: the taglist to post on the bus and create event from.
2881  *
2882  * Posts a message to the bus that new tags were found and pushes the
2883  * tags as event. Takes ownership of the @list.
2884  *
2885  * This is a utility method for elements. Applications should use the
2886  * #GstTagSetter interface.
2887  */
2888 void
2889 gst_element_found_tags_for_pad (GstElement * element,
2890     GstPad * pad, GstTagList * list)
2891 {
2892   g_return_if_fail (element != NULL);
2893   g_return_if_fail (pad != NULL);
2894   g_return_if_fail (list != NULL);
2895
2896   gst_pad_push_event (pad, gst_event_new_tag (gst_tag_list_copy (list)));
2897   gst_element_post_message (element,
2898       gst_message_new_tag (GST_OBJECT (element), list));
2899 }
2900
2901 static void
2902 push_and_ref (GstPad * pad, GstEvent * event)
2903 {
2904   gst_pad_push_event (pad, gst_event_ref (event));
2905 }
2906
2907 /**
2908  * gst_element_found_tags:
2909  * @element: element for which we found the tags.
2910  * @list: list of tags.
2911  *
2912  * Posts a message to the bus that new tags were found, and pushes an event
2913  * to all sourcepads. Takes ownership of the @list.
2914  *
2915  * This is a utility method for elements. Applications should use the
2916  * #GstTagSetter interface.
2917  */
2918 void
2919 gst_element_found_tags (GstElement * element, GstTagList * list)
2920 {
2921   GstIterator *iter;
2922   GstEvent *event;
2923
2924   g_return_if_fail (element != NULL);
2925   g_return_if_fail (list != NULL);
2926
2927   iter = gst_element_iterate_src_pads (element);
2928   event = gst_event_new_tag (gst_tag_list_copy (list));
2929   gst_iterator_foreach (iter, (GFunc) push_and_ref, event);
2930   gst_iterator_free (iter);
2931   gst_event_unref (event);
2932
2933   gst_element_post_message (element,
2934       gst_message_new_tag (GST_OBJECT (element), list));
2935 }
2936
2937 static GstPad *
2938 element_find_unconnected_pad (GstElement * element, GstPadDirection direction)
2939 {
2940   GstIterator *iter;
2941   GstPad *unconnected_pad = NULL;
2942   gboolean done;
2943
2944   switch (direction) {
2945     case GST_PAD_SRC:
2946       iter = gst_element_iterate_src_pads (element);
2947       break;
2948     case GST_PAD_SINK:
2949       iter = gst_element_iterate_sink_pads (element);
2950       break;
2951     default:
2952       g_assert_not_reached ();
2953   }
2954
2955   done = FALSE;
2956   while (!done) {
2957     gpointer pad;
2958
2959     switch (gst_iterator_next (iter, &pad)) {
2960       case GST_ITERATOR_OK:{
2961         GstPad *peer;
2962
2963         GST_CAT_LOG (GST_CAT_ELEMENT_PADS, "examining pad %s:%s",
2964             GST_DEBUG_PAD_NAME (pad));
2965
2966         peer = gst_pad_get_peer (GST_PAD (pad));
2967         if (peer == NULL) {
2968           unconnected_pad = pad;
2969           done = TRUE;
2970           GST_CAT_DEBUG (GST_CAT_ELEMENT_PADS,
2971               "found existing unlinked pad %s:%s",
2972               GST_DEBUG_PAD_NAME (unconnected_pad));
2973         } else {
2974           gst_object_unref (pad);
2975           gst_object_unref (peer);
2976         }
2977         break;
2978       }
2979       case GST_ITERATOR_DONE:
2980         done = TRUE;
2981         break;
2982       case GST_ITERATOR_RESYNC:
2983         gst_iterator_resync (iter);
2984         break;
2985       case GST_ITERATOR_ERROR:
2986         g_return_val_if_reached (NULL);
2987         break;
2988     }
2989   }
2990
2991   gst_iterator_free (iter);
2992
2993   return unconnected_pad;
2994 }
2995
2996 /**
2997  * gst_bin_find_unconnected_pad:
2998  * @bin: bin in which to look for elements with unconnected pads
2999  * @direction: whether to look for an unconnected source or sink pad
3000  *
3001  * Recursively looks for elements with an unconnected pad of the given
3002  * direction within the specified bin and returns an unconnected pad
3003  * if one is found, or NULL otherwise. If a pad is found, the caller
3004  * owns a reference to it and should use gst_object_unref() on the
3005  * pad when it is not needed any longer.
3006  *
3007  * Returns: unconnected pad of the given direction, or NULL.
3008  *
3009  * Since: 0.10.3
3010  */
3011 GstPad *
3012 gst_bin_find_unconnected_pad (GstBin * bin, GstPadDirection direction)
3013 {
3014   GstIterator *iter;
3015   gboolean done;
3016   GstPad *pad = NULL;
3017
3018   g_return_val_if_fail (GST_IS_BIN (bin), NULL);
3019   g_return_val_if_fail (direction != GST_PAD_UNKNOWN, NULL);
3020
3021   done = FALSE;
3022   iter = gst_bin_iterate_recurse (bin);
3023   while (!done) {
3024     gpointer element;
3025
3026     switch (gst_iterator_next (iter, &element)) {
3027       case GST_ITERATOR_OK:
3028         pad = element_find_unconnected_pad (GST_ELEMENT (element), direction);
3029         gst_object_unref (element);
3030         if (pad != NULL)
3031           done = TRUE;
3032         break;
3033       case GST_ITERATOR_DONE:
3034         done = TRUE;
3035         break;
3036       case GST_ITERATOR_RESYNC:
3037         gst_iterator_resync (iter);
3038         break;
3039       case GST_ITERATOR_ERROR:
3040         g_return_val_if_reached (NULL);
3041         break;
3042     }
3043   }
3044
3045   gst_iterator_free (iter);
3046
3047   return pad;
3048 }
3049
3050 #ifndef GST_DISABLE_PARSE
3051 /**
3052  * gst_parse_bin_from_description:
3053  * @bin_description: command line describing the bin
3054  * @ghost_unconnected_pads: whether to automatically create ghost pads
3055  *                          for unconnected source or sink pads within
3056  *                          the bin
3057  * @err: where to store the error message in case of an error, or NULL
3058  *
3059  * This is a convenience wrapper around gst_parse_launch() to create a
3060  * #GstBin from a gst-launch-style pipeline description. See
3061  * gst_parse_launch() and the gst-launch man page for details about the
3062  * syntax. Ghost pads on the bin for unconnected source or sink pads
3063  * within the bin can automatically be created (but only a maximum of
3064  * one ghost pad for each direction will be created; if you expect
3065  * multiple unconnected source pads or multiple unconnected sink pads
3066  * and want them all ghosted, you will have to create the ghost pads
3067  * yourself).
3068  *
3069  * Returns: a newly-created bin, or NULL if an error occurred.
3070  *
3071  * Since: 0.10.3
3072  */
3073 GstElement *
3074 gst_parse_bin_from_description (const gchar * bin_description,
3075     gboolean ghost_unconnected_pads, GError ** err)
3076 {
3077   GstPad *pad = NULL;
3078   GstBin *bin;
3079   gchar *desc;
3080
3081   g_return_val_if_fail (bin_description != NULL, NULL);
3082   g_return_val_if_fail (err == NULL || *err == NULL, NULL);
3083
3084   GST_DEBUG ("Making bin from description '%s'", bin_description);
3085
3086   /* parse the pipeline to a bin */
3087   desc = g_strdup_printf ("bin.( %s )", bin_description);
3088   bin = (GstBin *) gst_parse_launch (desc, err);
3089   g_free (desc);
3090
3091   if (bin == NULL || (err && *err != NULL)) {
3092     if (bin)
3093       gst_object_unref (bin);
3094     return NULL;
3095   }
3096
3097   /* find pads and ghost them if necessary */
3098   if (ghost_unconnected_pads) {
3099     if ((pad = gst_bin_find_unconnected_pad (bin, GST_PAD_SRC))) {
3100       gst_element_add_pad (GST_ELEMENT (bin), gst_ghost_pad_new ("src", pad));
3101       gst_object_unref (pad);
3102     }
3103     if ((pad = gst_bin_find_unconnected_pad (bin, GST_PAD_SINK))) {
3104       gst_element_add_pad (GST_ELEMENT (bin), gst_ghost_pad_new ("sink", pad));
3105       gst_object_unref (pad);
3106     }
3107   }
3108
3109   return GST_ELEMENT (bin);
3110 }
3111 #endif