element: Enforce that elements created by gst_element_factory_create/make() are floating
[platform/upstream/gstreamer.git] / gst / gststructure.c
1 /* GStreamer
2  * Copyright (C) 2003 David A. Schleef <ds@schleef.org>
3  *
4  * gststructure.c: lists of { GQuark, GValue } tuples
5  *
6  * This library is free software; you can redistribute it and/or
7  * modify it under the terms of the GNU Library General Public
8  * License as published by the Free Software Foundation; either
9  * version 2 of the License, or (at your option) any later version.
10  *
11  * This library is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
14  * Library General Public License for more details.
15  *
16  * You should have received a copy of the GNU Library General Public
17  * License along with this library; if not, write to the
18  * Free Software Foundation, Inc., 51 Franklin St, Fifth Floor,
19  * Boston, MA 02110-1301, USA.
20  */
21
22 /**
23  * SECTION:gststructure
24  * @title: GstStructure
25  * @short_description: Generic structure containing fields of names and values
26  * @see_also: #GstCaps, #GstMessage, #GstEvent, #GstQuery
27  *
28  * A #GstStructure is a collection of key/value pairs. The keys are expressed
29  * as GQuarks and the values can be of any GType.
30  *
31  * In addition to the key/value pairs, a #GstStructure also has a name. The name
32  * starts with a letter and can be filled by letters, numbers and any of "/-_.:".
33  *
34  * #GstStructure is used by various GStreamer subsystems to store information
35  * in a flexible and extensible way. A #GstStructure does not have a refcount
36  * because it usually is part of a higher level object such as #GstCaps,
37  * #GstMessage, #GstEvent, #GstQuery. It provides a means to enforce mutability
38  * using the refcount of the parent with the gst_structure_set_parent_refcount()
39  * method.
40  *
41  * A #GstStructure can be created with gst_structure_new_empty() or
42  * gst_structure_new(), which both take a name and an optional set of
43  * key/value pairs along with the types of the values.
44  *
45  * Field values can be changed with gst_structure_set_value() or
46  * gst_structure_set().
47  *
48  * Field values can be retrieved with gst_structure_get_value() or the more
49  * convenient gst_structure_get_*() functions.
50  *
51  * Fields can be removed with gst_structure_remove_field() or
52  * gst_structure_remove_fields().
53  *
54  * Strings in structures must be ASCII or UTF-8 encoded. Other encodings are
55  * not allowed. Strings may be %NULL however.
56  *
57  * Be aware that the current #GstCaps / #GstStructure serialization into string
58  * has limited support for nested #GstCaps / #GstStructure fields. It can only
59  * support one level of nesting. Using more levels will lead to unexpected
60  * behavior when using serialization features, such as gst_caps_to_string() or
61  * gst_value_serialize() and their counterparts.
62  */
63
64 #ifdef HAVE_CONFIG_H
65 #include "config.h"
66 #endif
67
68 /* FIXME 2.0: suppress warnings for deprecated API such as GValueArray
69  * with newer GLib versions (>= 2.31.0) */
70 #define GLIB_DISABLE_DEPRECATION_WARNINGS
71
72 #include <string.h>
73
74 #include "gst_private.h"
75 #include "gstquark.h"
76 #include <gst/gst.h>
77 #include <gobject/gvaluecollector.h>
78
79 GST_DEBUG_CATEGORY_STATIC (gst_structure_debug);
80 #define GST_CAT_DEFAULT gst_structure_debug
81
82 typedef struct _GstStructureField GstStructureField;
83
84 struct _GstStructureField
85 {
86   GQuark name;
87   GValue value;
88 };
89
90 typedef struct
91 {
92   GstStructure s;
93
94   /* owned by parent structure, NULL if no parent */
95   gint *parent_refcount;
96
97   GArray *fields;
98 } GstStructureImpl;
99
100 #define GST_STRUCTURE_REFCOUNT(s) (((GstStructureImpl*)(s))->parent_refcount)
101 #define GST_STRUCTURE_FIELDS(s) (((GstStructureImpl*)(s))->fields)
102
103 #define GST_STRUCTURE_FIELD(structure, index) \
104     &g_array_index(GST_STRUCTURE_FIELDS(structure), GstStructureField, (index))
105
106 #define IS_MUTABLE(structure) \
107     (!GST_STRUCTURE_REFCOUNT(structure) || \
108      g_atomic_int_get (GST_STRUCTURE_REFCOUNT(structure)) == 1)
109
110 #define IS_TAGLIST(structure) \
111     (structure->name == GST_QUARK (TAGLIST))
112
113 static void gst_structure_set_field (GstStructure * structure,
114     GstStructureField * field);
115 static GstStructureField *gst_structure_get_field (const GstStructure *
116     structure, const gchar * fieldname);
117 static GstStructureField *gst_structure_id_get_field (const GstStructure *
118     structure, GQuark field);
119 static void gst_structure_transform_to_string (const GValue * src_value,
120     GValue * dest_value);
121 static GstStructure *gst_structure_copy_conditional (const GstStructure *
122     structure);
123
124 GType _gst_structure_type = 0;
125
126
127 G_DEFINE_BOXED_TYPE (GstStructure, gst_structure,
128     gst_structure_copy_conditional, gst_structure_free);
129
130 void
131 _priv_gst_structure_initialize (void)
132 {
133   _gst_structure_type = gst_structure_get_type ();
134
135   g_value_register_transform_func (_gst_structure_type, G_TYPE_STRING,
136       gst_structure_transform_to_string);
137
138   GST_DEBUG_CATEGORY_INIT (gst_structure_debug, "structure", 0,
139       "GstStructure debug");
140 }
141
142 static GstStructure *
143 gst_structure_new_id_empty_with_size (GQuark quark, guint prealloc)
144 {
145   GstStructureImpl *structure;
146
147   structure = g_slice_new (GstStructureImpl);
148   ((GstStructure *) structure)->type = _gst_structure_type;
149   ((GstStructure *) structure)->name = quark;
150   GST_STRUCTURE_REFCOUNT (structure) = NULL;
151   GST_STRUCTURE_FIELDS (structure) =
152       g_array_sized_new (FALSE, FALSE, sizeof (GstStructureField), prealloc);
153
154   GST_TRACE ("created structure %p", structure);
155
156   return GST_STRUCTURE_CAST (structure);
157 }
158
159 /**
160  * gst_structure_new_id_empty:
161  * @quark: name of new structure
162  *
163  * Creates a new, empty #GstStructure with the given name as a GQuark.
164  *
165  * Free-function: gst_structure_free
166  *
167  * Returns: (transfer full): a new, empty #GstStructure
168  */
169 GstStructure *
170 gst_structure_new_id_empty (GQuark quark)
171 {
172   g_return_val_if_fail (quark != 0, NULL);
173
174   return gst_structure_new_id_empty_with_size (quark, 0);
175 }
176
177 #ifndef G_DISABLE_CHECKS
178 static gboolean
179 gst_structure_validate_name (const gchar * name)
180 {
181   const gchar *s;
182
183   g_return_val_if_fail (name != NULL, FALSE);
184
185   if (G_UNLIKELY (!g_ascii_isalpha (*name))) {
186     GST_WARNING ("Invalid character '%c' at offset 0 in structure name: %s",
187         *name, name);
188     return FALSE;
189   }
190
191   /* FIXME: test name string more */
192   s = &name[1];
193   while (*s && (g_ascii_isalnum (*s) || strchr ("/-_.:+", *s) != NULL))
194     s++;
195   if (G_UNLIKELY (*s != '\0')) {
196     GST_WARNING ("Invalid character '%c' at offset %" G_GUINTPTR_FORMAT " in"
197         " structure name: %s", *s, ((guintptr) s - (guintptr) name), name);
198     return FALSE;
199   }
200
201   if (strncmp (name, "video/x-raw-", 12) == 0) {
202     g_warning ("0.10-style raw video caps are being created. Should be "
203         "video/x-raw,format=(string).. now.");
204   } else if (strncmp (name, "audio/x-raw-", 12) == 0) {
205     g_warning ("0.10-style raw audio caps are being created. Should be "
206         "audio/x-raw,format=(string).. now.");
207   }
208
209   return TRUE;
210 }
211 #endif
212
213 /**
214  * gst_structure_new_empty:
215  * @name: name of new structure
216  *
217  * Creates a new, empty #GstStructure with the given @name.
218  *
219  * See gst_structure_set_name() for constraints on the @name parameter.
220  *
221  * Free-function: gst_structure_free
222  *
223  * Returns: (transfer full): a new, empty #GstStructure
224  */
225 GstStructure *
226 gst_structure_new_empty (const gchar * name)
227 {
228   g_return_val_if_fail (gst_structure_validate_name (name), NULL);
229
230   return gst_structure_new_id_empty_with_size (g_quark_from_string (name), 0);
231 }
232
233 /**
234  * gst_structure_new:
235  * @name: name of new structure
236  * @firstfield: name of first field to set
237  * @...: additional arguments
238  *
239  * Creates a new #GstStructure with the given name.  Parses the
240  * list of variable arguments and sets fields to the values listed.
241  * Variable arguments should be passed as field name, field type,
242  * and value.  Last variable argument should be %NULL.
243  *
244  * Free-function: gst_structure_free
245  *
246  * Returns: (transfer full): a new #GstStructure
247  */
248 GstStructure *
249 gst_structure_new (const gchar * name, const gchar * firstfield, ...)
250 {
251   GstStructure *structure;
252   va_list varargs;
253
254   va_start (varargs, firstfield);
255   structure = gst_structure_new_valist (name, firstfield, varargs);
256   va_end (varargs);
257
258   return structure;
259 }
260
261 /**
262  * gst_structure_new_valist:
263  * @name: name of new structure
264  * @firstfield: name of first field to set
265  * @varargs: variable argument list
266  *
267  * Creates a new #GstStructure with the given @name.  Structure fields
268  * are set according to the varargs in a manner similar to
269  * gst_structure_new().
270  *
271  * See gst_structure_set_name() for constraints on the @name parameter.
272  *
273  * Free-function: gst_structure_free
274  *
275  * Returns: (transfer full): a new #GstStructure
276  */
277 GstStructure *
278 gst_structure_new_valist (const gchar * name,
279     const gchar * firstfield, va_list varargs)
280 {
281   GstStructure *structure;
282
283   structure = gst_structure_new_empty (name);
284
285   if (structure)
286     gst_structure_set_valist (structure, firstfield, varargs);
287
288   return structure;
289 }
290
291 /**
292  * gst_structure_set_parent_refcount:
293  * @structure: a #GstStructure
294  * @refcount: (in): a pointer to the parent's refcount
295  *
296  * Sets the parent_refcount field of #GstStructure. This field is used to
297  * determine whether a structure is mutable or not. This function should only be
298  * called by code implementing parent objects of #GstStructure, as described in
299  * the MT Refcounting section of the design documents.
300  *
301  * Returns: %TRUE if the parent refcount could be set.
302  */
303 gboolean
304 gst_structure_set_parent_refcount (GstStructure * structure, gint * refcount)
305 {
306   g_return_val_if_fail (structure != NULL, FALSE);
307
308   /* if we have a parent_refcount already, we can only clear
309    * if with a NULL refcount */
310   if (GST_STRUCTURE_REFCOUNT (structure)) {
311     if (refcount != NULL) {
312       g_return_val_if_fail (refcount == NULL, FALSE);
313       return FALSE;
314     }
315   } else {
316     if (refcount == NULL) {
317       g_return_val_if_fail (refcount != NULL, FALSE);
318       return FALSE;
319     }
320   }
321
322   GST_STRUCTURE_REFCOUNT (structure) = refcount;
323
324   return TRUE;
325 }
326
327 /**
328  * gst_structure_copy:
329  * @structure: a #GstStructure to duplicate
330  *
331  * Duplicates a #GstStructure and all its fields and values.
332  *
333  * Free-function: gst_structure_free
334  *
335  * Returns: (transfer full): a new #GstStructure.
336  */
337 GstStructure *
338 gst_structure_copy (const GstStructure * structure)
339 {
340   GstStructure *new_structure;
341   GstStructureField *field;
342   guint i, len;
343
344   g_return_val_if_fail (structure != NULL, NULL);
345
346   len = GST_STRUCTURE_FIELDS (structure)->len;
347   new_structure = gst_structure_new_id_empty_with_size (structure->name, len);
348
349   for (i = 0; i < len; i++) {
350     GstStructureField new_field = { 0 };
351
352     field = GST_STRUCTURE_FIELD (structure, i);
353
354     new_field.name = field->name;
355     gst_value_init_and_copy (&new_field.value, &field->value);
356     g_array_append_val (GST_STRUCTURE_FIELDS (new_structure), new_field);
357   }
358   GST_CAT_TRACE (GST_CAT_PERFORMANCE, "doing copy %p -> %p",
359       structure, new_structure);
360
361   return new_structure;
362 }
363
364 /**
365  * gst_structure_free:
366  * @structure: (in) (transfer full): the #GstStructure to free
367  *
368  * Frees a #GstStructure and all its fields and values. The structure must not
369  * have a parent when this function is called.
370  */
371 void
372 gst_structure_free (GstStructure * structure)
373 {
374   GstStructureField *field;
375   guint i, len;
376
377   g_return_if_fail (structure != NULL);
378   g_return_if_fail (GST_STRUCTURE_REFCOUNT (structure) == NULL);
379
380   len = GST_STRUCTURE_FIELDS (structure)->len;
381   for (i = 0; i < len; i++) {
382     field = GST_STRUCTURE_FIELD (structure, i);
383
384     if (G_IS_VALUE (&field->value)) {
385       g_value_unset (&field->value);
386     }
387   }
388   g_array_free (GST_STRUCTURE_FIELDS (structure), TRUE);
389 #ifdef USE_POISONING
390   memset (structure, 0xff, sizeof (GstStructure));
391 #endif
392   GST_TRACE ("free structure %p", structure);
393
394   g_slice_free1 (sizeof (GstStructureImpl), structure);
395 }
396
397 /**
398  * gst_clear_structure: (skip)
399  * @structure_ptr: a pointer to a #GstStructure reference
400  *
401  * Clears a reference to a #GstStructure.
402  *
403  * @structure_ptr must not be %NULL.
404  *
405  * If the reference is %NULL then this function does nothing.
406  * Otherwise, the structure is free'd using gst_structure_free() and the
407  * pointer is set to %NULL.
408  *
409  * A macro is also included that allows this function to be used without
410  * pointer casts.
411  *
412  * Since: 1.16
413  **/
414 #undef gst_clear_structure
415 void
416 gst_clear_structure (GstStructure ** structure_ptr)
417 {
418   g_clear_pointer (structure_ptr, gst_structure_free);
419 }
420
421 /**
422  * gst_structure_get_name:
423  * @structure: a #GstStructure
424  *
425  * Get the name of @structure as a string.
426  *
427  * Returns: the name of the structure.
428  */
429 const gchar *
430 gst_structure_get_name (const GstStructure * structure)
431 {
432   g_return_val_if_fail (structure != NULL, NULL);
433
434   return g_quark_to_string (structure->name);
435 }
436
437 /**
438  * gst_structure_has_name:
439  * @structure: a #GstStructure
440  * @name: structure name to check for
441  *
442  * Checks if the structure has the given name
443  *
444  * Returns: %TRUE if @name matches the name of the structure.
445  */
446 gboolean
447 gst_structure_has_name (const GstStructure * structure, const gchar * name)
448 {
449   const gchar *structure_name;
450
451   g_return_val_if_fail (structure != NULL, FALSE);
452   g_return_val_if_fail (name != NULL, FALSE);
453
454   /* getting the string is cheap and comparing short strings is too
455    * should be faster than getting the quark for name and comparing the quarks
456    */
457   structure_name = g_quark_to_string (structure->name);
458
459   return (structure_name && strcmp (structure_name, name) == 0);
460 }
461
462 /**
463  * gst_structure_get_name_id:
464  * @structure: a #GstStructure
465  *
466  * Get the name of @structure as a GQuark.
467  *
468  * Returns: the quark representing the name of the structure.
469  */
470 GQuark
471 gst_structure_get_name_id (const GstStructure * structure)
472 {
473   g_return_val_if_fail (structure != NULL, 0);
474
475   return structure->name;
476 }
477
478 /**
479  * gst_structure_set_name:
480  * @structure: a #GstStructure
481  * @name: the new name of the structure
482  *
483  * Sets the name of the structure to the given @name.  The string
484  * provided is copied before being used. It must not be empty, start with a
485  * letter and can be followed by letters, numbers and any of "/-_.:".
486  */
487 void
488 gst_structure_set_name (GstStructure * structure, const gchar * name)
489 {
490   g_return_if_fail (structure != NULL);
491   g_return_if_fail (IS_MUTABLE (structure));
492   g_return_if_fail (gst_structure_validate_name (name));
493
494   structure->name = g_quark_from_string (name);
495 }
496
497 static inline void
498 gst_structure_id_set_value_internal (GstStructure * structure, GQuark field,
499     const GValue * value)
500 {
501   GstStructureField gsfield = { 0, {0,} };
502
503   gsfield.name = field;
504   gst_value_init_and_copy (&gsfield.value, value);
505
506   gst_structure_set_field (structure, &gsfield);
507 }
508
509 /**
510  * gst_structure_id_set_value:
511  * @structure: a #GstStructure
512  * @field: a #GQuark representing a field
513  * @value: the new value of the field
514  *
515  * Sets the field with the given GQuark @field to @value.  If the field
516  * does not exist, it is created.  If the field exists, the previous
517  * value is replaced and freed.
518  */
519 void
520 gst_structure_id_set_value (GstStructure * structure,
521     GQuark field, const GValue * value)
522 {
523
524   g_return_if_fail (structure != NULL);
525   g_return_if_fail (G_IS_VALUE (value));
526   g_return_if_fail (IS_MUTABLE (structure));
527
528   gst_structure_id_set_value_internal (structure, field, value);
529 }
530
531 /**
532  * gst_structure_set_value:
533  * @structure: a #GstStructure
534  * @fieldname: the name of the field to set
535  * @value: the new value of the field
536  *
537  * Sets the field with the given name @field to @value.  If the field
538  * does not exist, it is created.  If the field exists, the previous
539  * value is replaced and freed.
540  */
541 void
542 gst_structure_set_value (GstStructure * structure,
543     const gchar * fieldname, const GValue * value)
544 {
545   g_return_if_fail (structure != NULL);
546   g_return_if_fail (fieldname != NULL);
547   g_return_if_fail (G_IS_VALUE (value));
548   g_return_if_fail (IS_MUTABLE (structure));
549
550   gst_structure_id_set_value_internal (structure,
551       g_quark_from_string (fieldname), value);
552 }
553
554 static inline void
555 gst_structure_id_take_value_internal (GstStructure * structure, GQuark field,
556     GValue * value)
557 {
558   GstStructureField gsfield = { 0, {0,} };
559
560   gsfield.name = field;
561   gsfield.value = *value;
562
563   gst_structure_set_field (structure, &gsfield);
564
565   /* we took ownership */
566 #ifdef USE_POISONING
567   memset (value, 0, sizeof (GValue));
568 #else
569   value->g_type = G_TYPE_INVALID;
570 #endif
571 }
572
573 /**
574  * gst_structure_id_take_value:
575  * @structure: a #GstStructure
576  * @field: a #GQuark representing a field
577  * @value: (transfer full): the new value of the field
578  *
579  * Sets the field with the given GQuark @field to @value.  If the field
580  * does not exist, it is created.  If the field exists, the previous
581  * value is replaced and freed.
582  */
583 void
584 gst_structure_id_take_value (GstStructure * structure, GQuark field,
585     GValue * value)
586 {
587   g_return_if_fail (structure != NULL);
588   g_return_if_fail (G_IS_VALUE (value));
589   g_return_if_fail (IS_MUTABLE (structure));
590
591   gst_structure_id_take_value_internal (structure, field, value);
592 }
593
594 /**
595  * gst_structure_take_value:
596  * @structure: a #GstStructure
597  * @fieldname: the name of the field to set
598  * @value: (transfer full): the new value of the field
599  *
600  * Sets the field with the given name @field to @value.  If the field
601  * does not exist, it is created.  If the field exists, the previous
602  * value is replaced and freed. The function will take ownership of @value.
603  */
604 void
605 gst_structure_take_value (GstStructure * structure, const gchar * fieldname,
606     GValue * value)
607 {
608   g_return_if_fail (structure != NULL);
609   g_return_if_fail (fieldname != NULL);
610   g_return_if_fail (G_IS_VALUE (value));
611   g_return_if_fail (IS_MUTABLE (structure));
612
613   gst_structure_id_take_value_internal (structure,
614       g_quark_from_string (fieldname), value);
615 }
616
617 static void
618 gst_structure_set_valist_internal (GstStructure * structure,
619     const gchar * fieldname, va_list varargs)
620 {
621   gchar *err = NULL;
622   GType type;
623
624   while (fieldname) {
625     GstStructureField field = { 0 };
626
627     field.name = g_quark_from_string (fieldname);
628
629     type = va_arg (varargs, GType);
630
631     G_VALUE_COLLECT_INIT (&field.value, type, varargs, 0, &err);
632     if (G_UNLIKELY (err)) {
633       g_critical ("%s", err);
634       g_free (err);
635       return;
636     }
637     gst_structure_set_field (structure, &field);
638
639     fieldname = va_arg (varargs, gchar *);
640   }
641 }
642
643 /**
644  * gst_structure_set:
645  * @structure: a #GstStructure
646  * @fieldname: the name of the field to set
647  * @...: variable arguments
648  *
649  * Parses the variable arguments and sets fields accordingly. Fields that
650  * weren't already part of the structure are added as needed.
651  * Variable arguments should be in the form field name, field type
652  * (as a GType), value(s).  The last variable argument should be %NULL.
653  */
654 void
655 gst_structure_set (GstStructure * structure, const gchar * field, ...)
656 {
657   va_list varargs;
658
659   g_return_if_fail (structure != NULL);
660   g_return_if_fail (IS_MUTABLE (structure) || field == NULL);
661
662   va_start (varargs, field);
663   gst_structure_set_valist_internal (structure, field, varargs);
664   va_end (varargs);
665 }
666
667 /**
668  * gst_structure_set_valist:
669  * @structure: a #GstStructure
670  * @fieldname: the name of the field to set
671  * @varargs: variable arguments
672  *
673  * va_list form of gst_structure_set().
674  */
675 void
676 gst_structure_set_valist (GstStructure * structure,
677     const gchar * fieldname, va_list varargs)
678 {
679   g_return_if_fail (structure != NULL);
680   g_return_if_fail (IS_MUTABLE (structure));
681
682   gst_structure_set_valist_internal (structure, fieldname, varargs);
683 }
684
685 static void
686 gst_structure_id_set_valist_internal (GstStructure * structure,
687     GQuark fieldname, va_list varargs)
688 {
689   gchar *err = NULL;
690   GType type;
691
692   while (fieldname) {
693     GstStructureField field = { 0 };
694
695     field.name = fieldname;
696     type = va_arg (varargs, GType);
697
698     G_VALUE_COLLECT_INIT (&field.value, type, varargs, 0, &err);
699     if (G_UNLIKELY (err)) {
700       g_critical ("%s", err);
701       g_free (err);
702       return;
703     }
704     gst_structure_set_field (structure, &field);
705
706     fieldname = va_arg (varargs, GQuark);
707   }
708 }
709
710 /**
711  * gst_structure_id_set:
712  * @structure: a #GstStructure
713  * @fieldname: the GQuark for the name of the field to set
714  * @...: variable arguments
715  *
716  * Identical to gst_structure_set, except that field names are
717  * passed using the GQuark for the field name. This allows more efficient
718  * setting of the structure if the caller already knows the associated
719  * quark values.
720  * The last variable argument must be %NULL.
721  */
722 void
723 gst_structure_id_set (GstStructure * structure, GQuark field, ...)
724 {
725   va_list varargs;
726
727   g_return_if_fail (structure != NULL);
728
729   va_start (varargs, field);
730   gst_structure_id_set_valist_internal (structure, field, varargs);
731   va_end (varargs);
732 }
733
734 /**
735  * gst_structure_id_set_valist:
736  * @structure: a #GstStructure
737  * @fieldname: the name of the field to set
738  * @varargs: variable arguments
739  *
740  * va_list form of gst_structure_id_set().
741  */
742 void
743 gst_structure_id_set_valist (GstStructure * structure,
744     GQuark fieldname, va_list varargs)
745 {
746   g_return_if_fail (structure != NULL);
747   g_return_if_fail (IS_MUTABLE (structure));
748
749   gst_structure_id_set_valist_internal (structure, fieldname, varargs);
750 }
751
752 /**
753  * gst_structure_new_id:
754  * @name_quark: name of new structure
755  * @field_quark: the GQuark for the name of the field to set
756  * @...: variable arguments
757  *
758  * Creates a new #GstStructure with the given name as a GQuark, followed by
759  * fieldname quark, GType, argument(s) "triplets" in the same format as
760  * gst_structure_id_set(). Basically a convenience wrapper around
761  * gst_structure_new_id_empty() and gst_structure_id_set().
762  *
763  * The last variable argument must be %NULL (or 0).
764  *
765  * Free-function: gst_structure_free
766  *
767  * Returns: (transfer full): a new #GstStructure
768  */
769 GstStructure *
770 gst_structure_new_id (GQuark name_quark, GQuark field_quark, ...)
771 {
772   GstStructure *s;
773   va_list varargs;
774
775   g_return_val_if_fail (name_quark != 0, NULL);
776   g_return_val_if_fail (field_quark != 0, NULL);
777
778   s = gst_structure_new_id_empty (name_quark);
779
780   va_start (varargs, field_quark);
781   gst_structure_id_set_valist_internal (s, field_quark, varargs);
782   va_end (varargs);
783
784   return s;
785 }
786
787 #if GST_VERSION_NANO == 1
788 #define GIT_G_WARNING g_warning
789 #else
790 #define GIT_G_WARNING GST_WARNING
791 #endif
792
793 /* If the structure currently contains a field with the same name, it is
794  * replaced with the provided field. Otherwise, the field is added to the
795  * structure. The field's value is not deeply copied.
796  */
797 static void
798 gst_structure_set_field (GstStructure * structure, GstStructureField * field)
799 {
800   GstStructureField *f;
801   GType field_value_type;
802   guint i, len;
803
804   len = GST_STRUCTURE_FIELDS (structure)->len;
805
806   field_value_type = G_VALUE_TYPE (&field->value);
807   if (field_value_type == G_TYPE_STRING) {
808     const gchar *s;
809
810     s = g_value_get_string (&field->value);
811     /* only check for NULL strings in taglists, as they are allowed in message
812      * structs, e.g. error message debug strings */
813     if (G_UNLIKELY (IS_TAGLIST (structure) && (s == NULL || *s == '\0'))) {
814       if (s == NULL) {
815         GIT_G_WARNING ("Trying to set NULL string on field '%s' on taglist. "
816             "Please file a bug.", g_quark_to_string (field->name));
817         g_value_unset (&field->value);
818         return;
819       } else {
820         /* empty strings never make sense */
821         GIT_G_WARNING ("Trying to set empty string on taglist field '%s'. "
822             "Please file a bug.", g_quark_to_string (field->name));
823         g_value_unset (&field->value);
824         return;
825       }
826     } else if (G_UNLIKELY (s != NULL && !g_utf8_validate (s, -1, NULL))) {
827       g_warning ("Trying to set string on %s field '%s', but string is not "
828           "valid UTF-8. Please file a bug.",
829           IS_TAGLIST (structure) ? "taglist" : "structure",
830           g_quark_to_string (field->name));
831       g_value_unset (&field->value);
832       return;
833     }
834   } else if (G_UNLIKELY (field_value_type == G_TYPE_DATE)) {
835     const GDate *d;
836
837     d = g_value_get_boxed (&field->value);
838     /* only check for NULL GDates in taglists, as they might make sense
839      * in other, generic structs */
840     if (G_UNLIKELY ((IS_TAGLIST (structure) && d == NULL))) {
841       GIT_G_WARNING ("Trying to set NULL GDate on field '%s' on taglist. "
842           "Please file a bug.", g_quark_to_string (field->name));
843       g_value_unset (&field->value);
844       return;
845     } else if (G_UNLIKELY (d != NULL && !g_date_valid (d))) {
846       g_warning
847           ("Trying to set invalid GDate on %s field '%s'. Please file a bug.",
848           IS_TAGLIST (structure) ? "taglist" : "structure",
849           g_quark_to_string (field->name));
850       g_value_unset (&field->value);
851       return;
852     }
853   }
854
855   for (i = 0; i < len; i++) {
856     f = GST_STRUCTURE_FIELD (structure, i);
857
858     if (G_UNLIKELY (f->name == field->name)) {
859       g_value_unset (&f->value);
860       memcpy (f, field, sizeof (GstStructureField));
861       return;
862     }
863   }
864
865   g_array_append_val (GST_STRUCTURE_FIELDS (structure), *field);
866 }
867
868 /* If there is no field with the given ID, NULL is returned.
869  */
870 static GstStructureField *
871 gst_structure_id_get_field (const GstStructure * structure, GQuark field_id)
872 {
873   GstStructureField *field;
874   guint i, len;
875
876   len = GST_STRUCTURE_FIELDS (structure)->len;
877
878   for (i = 0; i < len; i++) {
879     field = GST_STRUCTURE_FIELD (structure, i);
880
881     if (G_UNLIKELY (field->name == field_id))
882       return field;
883   }
884
885   return NULL;
886 }
887
888 /* If there is no field with the given ID, NULL is returned.
889  */
890 static GstStructureField *
891 gst_structure_get_field (const GstStructure * structure,
892     const gchar * fieldname)
893 {
894   g_return_val_if_fail (structure != NULL, NULL);
895   g_return_val_if_fail (fieldname != NULL, NULL);
896
897   return gst_structure_id_get_field (structure,
898       g_quark_from_string (fieldname));
899 }
900
901 /**
902  * gst_structure_get_value:
903  * @structure: a #GstStructure
904  * @fieldname: the name of the field to get
905  *
906  * Get the value of the field with name @fieldname.
907  *
908  * Returns: (nullable): the #GValue corresponding to the field with the given
909  * name.
910  */
911 const GValue *
912 gst_structure_get_value (const GstStructure * structure,
913     const gchar * fieldname)
914 {
915   GstStructureField *field;
916
917   g_return_val_if_fail (structure != NULL, NULL);
918   g_return_val_if_fail (fieldname != NULL, NULL);
919
920   field = gst_structure_get_field (structure, fieldname);
921   if (field == NULL)
922     return NULL;
923
924   return &field->value;
925 }
926
927 /**
928  * gst_structure_id_get_value:
929  * @structure: a #GstStructure
930  * @field: the #GQuark of the field to get
931  *
932  * Get the value of the field with GQuark @field.
933  *
934  * Returns: (nullable): the #GValue corresponding to the field with the given
935  * name identifier.
936  */
937 const GValue *
938 gst_structure_id_get_value (const GstStructure * structure, GQuark field)
939 {
940   GstStructureField *gsfield;
941
942   g_return_val_if_fail (structure != NULL, NULL);
943
944   gsfield = gst_structure_id_get_field (structure, field);
945   if (gsfield == NULL)
946     return NULL;
947
948   return &gsfield->value;
949 }
950
951 /**
952  * gst_structure_remove_field:
953  * @structure: a #GstStructure
954  * @fieldname: the name of the field to remove
955  *
956  * Removes the field with the given name.  If the field with the given
957  * name does not exist, the structure is unchanged.
958  */
959 void
960 gst_structure_remove_field (GstStructure * structure, const gchar * fieldname)
961 {
962   GstStructureField *field;
963   GQuark id;
964   guint i, len;
965
966   g_return_if_fail (structure != NULL);
967   g_return_if_fail (fieldname != NULL);
968   g_return_if_fail (IS_MUTABLE (structure));
969
970   id = g_quark_from_string (fieldname);
971   len = GST_STRUCTURE_FIELDS (structure)->len;
972
973   for (i = 0; i < len; i++) {
974     field = GST_STRUCTURE_FIELD (structure, i);
975
976     if (field->name == id) {
977       if (G_IS_VALUE (&field->value)) {
978         g_value_unset (&field->value);
979       }
980       GST_STRUCTURE_FIELDS (structure) =
981           g_array_remove_index (GST_STRUCTURE_FIELDS (structure), i);
982       return;
983     }
984   }
985 }
986
987 /**
988  * gst_structure_remove_fields:
989  * @structure: a #GstStructure
990  * @fieldname: the name of the field to remove
991  * @...: %NULL-terminated list of more fieldnames to remove
992  *
993  * Removes the fields with the given names. If a field does not exist, the
994  * argument is ignored.
995  */
996 void
997 gst_structure_remove_fields (GstStructure * structure,
998     const gchar * fieldname, ...)
999 {
1000   va_list varargs;
1001
1002   g_return_if_fail (structure != NULL);
1003   g_return_if_fail (fieldname != NULL);
1004   /* mutability checked in remove_field */
1005
1006   va_start (varargs, fieldname);
1007   gst_structure_remove_fields_valist (structure, fieldname, varargs);
1008   va_end (varargs);
1009 }
1010
1011 /**
1012  * gst_structure_remove_fields_valist:
1013  * @structure: a #GstStructure
1014  * @fieldname: the name of the field to remove
1015  * @varargs: %NULL-terminated list of more fieldnames to remove
1016  *
1017  * va_list form of gst_structure_remove_fields().
1018  */
1019 void
1020 gst_structure_remove_fields_valist (GstStructure * structure,
1021     const gchar * fieldname, va_list varargs)
1022 {
1023   gchar *field = (gchar *) fieldname;
1024
1025   g_return_if_fail (structure != NULL);
1026   g_return_if_fail (fieldname != NULL);
1027   /* mutability checked in remove_field */
1028
1029   while (field) {
1030     gst_structure_remove_field (structure, field);
1031     field = va_arg (varargs, char *);
1032   }
1033 }
1034
1035 /**
1036  * gst_structure_remove_all_fields:
1037  * @structure: a #GstStructure
1038  *
1039  * Removes all fields in a GstStructure.
1040  */
1041 void
1042 gst_structure_remove_all_fields (GstStructure * structure)
1043 {
1044   GstStructureField *field;
1045   int i;
1046
1047   g_return_if_fail (structure != NULL);
1048   g_return_if_fail (IS_MUTABLE (structure));
1049
1050   for (i = GST_STRUCTURE_FIELDS (structure)->len - 1; i >= 0; i--) {
1051     field = GST_STRUCTURE_FIELD (structure, i);
1052
1053     if (G_IS_VALUE (&field->value)) {
1054       g_value_unset (&field->value);
1055     }
1056     GST_STRUCTURE_FIELDS (structure) =
1057         g_array_remove_index (GST_STRUCTURE_FIELDS (structure), i);
1058   }
1059 }
1060
1061 /**
1062  * gst_structure_get_field_type:
1063  * @structure: a #GstStructure
1064  * @fieldname: the name of the field
1065  *
1066  * Finds the field with the given name, and returns the type of the
1067  * value it contains.  If the field is not found, G_TYPE_INVALID is
1068  * returned.
1069  *
1070  * Returns: the #GValue of the field
1071  */
1072 GType
1073 gst_structure_get_field_type (const GstStructure * structure,
1074     const gchar * fieldname)
1075 {
1076   GstStructureField *field;
1077
1078   g_return_val_if_fail (structure != NULL, G_TYPE_INVALID);
1079   g_return_val_if_fail (fieldname != NULL, G_TYPE_INVALID);
1080
1081   field = gst_structure_get_field (structure, fieldname);
1082   if (field == NULL)
1083     return G_TYPE_INVALID;
1084
1085   return G_VALUE_TYPE (&field->value);
1086 }
1087
1088 /**
1089  * gst_structure_n_fields:
1090  * @structure: a #GstStructure
1091  *
1092  * Get the number of fields in the structure.
1093  *
1094  * Returns: the number of fields in the structure
1095  */
1096 gint
1097 gst_structure_n_fields (const GstStructure * structure)
1098 {
1099   g_return_val_if_fail (structure != NULL, 0);
1100
1101   return GST_STRUCTURE_FIELDS (structure)->len;
1102 }
1103
1104 /**
1105  * gst_structure_nth_field_name:
1106  * @structure: a #GstStructure
1107  * @index: the index to get the name of
1108  *
1109  * Get the name of the given field number, counting from 0 onwards.
1110  *
1111  * Returns: the name of the given field number
1112  */
1113 const gchar *
1114 gst_structure_nth_field_name (const GstStructure * structure, guint index)
1115 {
1116   GstStructureField *field;
1117
1118   g_return_val_if_fail (structure != NULL, NULL);
1119   g_return_val_if_fail (index < GST_STRUCTURE_FIELDS (structure)->len, NULL);
1120
1121   field = GST_STRUCTURE_FIELD (structure, index);
1122
1123   return g_quark_to_string (field->name);
1124 }
1125
1126 /**
1127  * gst_structure_foreach:
1128  * @structure: a #GstStructure
1129  * @func: (scope call): a function to call for each field
1130  * @user_data: (closure): private data
1131  *
1132  * Calls the provided function once for each field in the #GstStructure. The
1133  * function must not modify the fields. Also see gst_structure_map_in_place()
1134  * and gst_structure_filter_and_map_in_place().
1135  *
1136  * Returns: %TRUE if the supplied function returns %TRUE For each of the fields,
1137  * %FALSE otherwise.
1138  */
1139 gboolean
1140 gst_structure_foreach (const GstStructure * structure,
1141     GstStructureForeachFunc func, gpointer user_data)
1142 {
1143   guint i, len;
1144   GstStructureField *field;
1145   gboolean ret;
1146
1147   g_return_val_if_fail (structure != NULL, FALSE);
1148   g_return_val_if_fail (func != NULL, FALSE);
1149
1150   len = GST_STRUCTURE_FIELDS (structure)->len;
1151
1152   for (i = 0; i < len; i++) {
1153     field = GST_STRUCTURE_FIELD (structure, i);
1154
1155     ret = func (field->name, &field->value, user_data);
1156     if (G_UNLIKELY (!ret))
1157       return FALSE;
1158   }
1159
1160   return TRUE;
1161 }
1162
1163 /**
1164  * gst_structure_map_in_place:
1165  * @structure: a #GstStructure
1166  * @func: (scope call): a function to call for each field
1167  * @user_data: (closure): private data
1168  *
1169  * Calls the provided function once for each field in the #GstStructure. In
1170  * contrast to gst_structure_foreach(), the function may modify but not delete the
1171  * fields. The structure must be mutable.
1172  *
1173  * Returns: %TRUE if the supplied function returns %TRUE For each of the fields,
1174  * %FALSE otherwise.
1175  */
1176 gboolean
1177 gst_structure_map_in_place (GstStructure * structure,
1178     GstStructureMapFunc func, gpointer user_data)
1179 {
1180   guint i, len;
1181   GstStructureField *field;
1182   gboolean ret;
1183
1184   g_return_val_if_fail (structure != NULL, FALSE);
1185   g_return_val_if_fail (IS_MUTABLE (structure), FALSE);
1186   g_return_val_if_fail (func != NULL, FALSE);
1187   len = GST_STRUCTURE_FIELDS (structure)->len;
1188
1189   for (i = 0; i < len; i++) {
1190     field = GST_STRUCTURE_FIELD (structure, i);
1191
1192     ret = func (field->name, &field->value, user_data);
1193     if (!ret)
1194       return FALSE;
1195   }
1196
1197   return TRUE;
1198 }
1199
1200 /**
1201  * gst_structure_filter_and_map_in_place:
1202  * @structure: a #GstStructure
1203  * @func: (scope call): a function to call for each field
1204  * @user_data: (closure): private data
1205  *
1206  * Calls the provided function once for each field in the #GstStructure. In
1207  * contrast to gst_structure_foreach(), the function may modify the fields.
1208  * In contrast to gst_structure_map_in_place(), the field is removed from
1209  * the structure if %FALSE is returned from the function.
1210  * The structure must be mutable.
1211  *
1212  * Since: 1.6
1213  */
1214 void
1215 gst_structure_filter_and_map_in_place (GstStructure * structure,
1216     GstStructureFilterMapFunc func, gpointer user_data)
1217 {
1218   guint i, len;
1219   GstStructureField *field;
1220   gboolean ret;
1221
1222   g_return_if_fail (structure != NULL);
1223   g_return_if_fail (IS_MUTABLE (structure));
1224   g_return_if_fail (func != NULL);
1225   len = GST_STRUCTURE_FIELDS (structure)->len;
1226
1227   for (i = 0; i < len;) {
1228     field = GST_STRUCTURE_FIELD (structure, i);
1229
1230     ret = func (field->name, &field->value, user_data);
1231
1232     if (!ret) {
1233       if (G_IS_VALUE (&field->value)) {
1234         g_value_unset (&field->value);
1235       }
1236       GST_STRUCTURE_FIELDS (structure) =
1237           g_array_remove_index (GST_STRUCTURE_FIELDS (structure), i);
1238       len = GST_STRUCTURE_FIELDS (structure)->len;
1239     } else {
1240       i++;
1241     }
1242   }
1243 }
1244
1245 /**
1246  * gst_structure_id_has_field:
1247  * @structure: a #GstStructure
1248  * @field: #GQuark of the field name
1249  *
1250  * Check if @structure contains a field named @field.
1251  *
1252  * Returns: %TRUE if the structure contains a field with the given name
1253  */
1254 gboolean
1255 gst_structure_id_has_field (const GstStructure * structure, GQuark field)
1256 {
1257   GstStructureField *f;
1258
1259   g_return_val_if_fail (structure != NULL, FALSE);
1260   g_return_val_if_fail (field != 0, FALSE);
1261
1262   f = gst_structure_id_get_field (structure, field);
1263
1264   return (f != NULL);
1265 }
1266
1267 /**
1268  * gst_structure_has_field:
1269  * @structure: a #GstStructure
1270  * @fieldname: the name of a field
1271  *
1272  * Check if @structure contains a field named @fieldname.
1273  *
1274  * Returns: %TRUE if the structure contains a field with the given name
1275  */
1276 gboolean
1277 gst_structure_has_field (const GstStructure * structure,
1278     const gchar * fieldname)
1279 {
1280   g_return_val_if_fail (structure != NULL, FALSE);
1281   g_return_val_if_fail (fieldname != NULL, FALSE);
1282
1283   return gst_structure_id_has_field (structure,
1284       g_quark_from_string (fieldname));
1285 }
1286
1287 /**
1288  * gst_structure_id_has_field_typed:
1289  * @structure: a #GstStructure
1290  * @field: #GQuark of the field name
1291  * @type: the type of a value
1292  *
1293  * Check if @structure contains a field named @field and with GType @type.
1294  *
1295  * Returns: %TRUE if the structure contains a field with the given name and type
1296  */
1297 gboolean
1298 gst_structure_id_has_field_typed (const GstStructure * structure,
1299     GQuark field, GType type)
1300 {
1301   GstStructureField *f;
1302
1303   g_return_val_if_fail (structure != NULL, FALSE);
1304   g_return_val_if_fail (field != 0, FALSE);
1305
1306   f = gst_structure_id_get_field (structure, field);
1307   if (f == NULL)
1308     return FALSE;
1309
1310   return (G_VALUE_TYPE (&f->value) == type);
1311 }
1312
1313 /**
1314  * gst_structure_has_field_typed:
1315  * @structure: a #GstStructure
1316  * @fieldname: the name of a field
1317  * @type: the type of a value
1318  *
1319  * Check if @structure contains a field named @fieldname and with GType @type.
1320  *
1321  * Returns: %TRUE if the structure contains a field with the given name and type
1322  */
1323 gboolean
1324 gst_structure_has_field_typed (const GstStructure * structure,
1325     const gchar * fieldname, GType type)
1326 {
1327   g_return_val_if_fail (structure != NULL, FALSE);
1328   g_return_val_if_fail (fieldname != NULL, FALSE);
1329
1330   return gst_structure_id_has_field_typed (structure,
1331       g_quark_from_string (fieldname), type);
1332 }
1333
1334 /* utility functions */
1335
1336 /**
1337  * gst_structure_get_boolean:
1338  * @structure: a #GstStructure
1339  * @fieldname: the name of a field
1340  * @value: (out): a pointer to a #gboolean to set
1341  *
1342  * Sets the boolean pointed to by @value corresponding to the value of the
1343  * given field.  Caller is responsible for making sure the field exists
1344  * and has the correct type.
1345  *
1346  * Returns: %TRUE if the value could be set correctly. If there was no field
1347  * with @fieldname or the existing field did not contain a boolean, this
1348  * function returns %FALSE.
1349  */
1350 gboolean
1351 gst_structure_get_boolean (const GstStructure * structure,
1352     const gchar * fieldname, gboolean * value)
1353 {
1354   GstStructureField *field;
1355
1356   g_return_val_if_fail (structure != NULL, FALSE);
1357   g_return_val_if_fail (fieldname != NULL, FALSE);
1358
1359   field = gst_structure_get_field (structure, fieldname);
1360
1361   if (field == NULL || G_VALUE_TYPE (&field->value) != G_TYPE_BOOLEAN)
1362     return FALSE;
1363
1364   *value = gst_g_value_get_boolean_unchecked (&field->value);
1365
1366   return TRUE;
1367 }
1368
1369 /**
1370  * gst_structure_get_int:
1371  * @structure: a #GstStructure
1372  * @fieldname: the name of a field
1373  * @value: (out): a pointer to an int to set
1374  *
1375  * Sets the int pointed to by @value corresponding to the value of the
1376  * given field.  Caller is responsible for making sure the field exists
1377  * and has the correct type.
1378  *
1379  * Returns: %TRUE if the value could be set correctly. If there was no field
1380  * with @fieldname or the existing field did not contain an int, this function
1381  * returns %FALSE.
1382  */
1383 gboolean
1384 gst_structure_get_int (const GstStructure * structure,
1385     const gchar * fieldname, gint * value)
1386 {
1387   GstStructureField *field;
1388
1389   g_return_val_if_fail (structure != NULL, FALSE);
1390   g_return_val_if_fail (fieldname != NULL, FALSE);
1391   g_return_val_if_fail (value != NULL, FALSE);
1392
1393   field = gst_structure_get_field (structure, fieldname);
1394
1395   if (field == NULL || G_VALUE_TYPE (&field->value) != G_TYPE_INT)
1396     return FALSE;
1397
1398   *value = gst_g_value_get_int_unchecked (&field->value);
1399
1400   return TRUE;
1401 }
1402
1403 /**
1404  * gst_structure_get_uint:
1405  * @structure: a #GstStructure
1406  * @fieldname: the name of a field
1407  * @value: (out): a pointer to a uint to set
1408  *
1409  * Sets the uint pointed to by @value corresponding to the value of the
1410  * given field.  Caller is responsible for making sure the field exists
1411  * and has the correct type.
1412  *
1413  * Returns: %TRUE if the value could be set correctly. If there was no field
1414  * with @fieldname or the existing field did not contain a uint, this function
1415  * returns %FALSE.
1416  */
1417 gboolean
1418 gst_structure_get_uint (const GstStructure * structure,
1419     const gchar * fieldname, guint * value)
1420 {
1421   GstStructureField *field;
1422
1423   g_return_val_if_fail (structure != NULL, FALSE);
1424   g_return_val_if_fail (fieldname != NULL, FALSE);
1425   g_return_val_if_fail (value != NULL, FALSE);
1426
1427   field = gst_structure_get_field (structure, fieldname);
1428
1429   if (field == NULL || G_VALUE_TYPE (&field->value) != G_TYPE_UINT)
1430     return FALSE;
1431
1432   *value = gst_g_value_get_uint_unchecked (&field->value);
1433
1434   return TRUE;
1435 }
1436
1437 /**
1438  * gst_structure_get_int64:
1439  * @structure: a #GstStructure
1440  * @fieldname: the name of a field
1441  * @value: (out): a pointer to a #gint64 to set
1442  *
1443  * Sets the #gint64 pointed to by @value corresponding to the value of the
1444  * given field. Caller is responsible for making sure the field exists
1445  * and has the correct type.
1446  *
1447  * Returns: %TRUE if the value could be set correctly. If there was no field
1448  * with @fieldname or the existing field did not contain a #gint64, this function
1449  * returns %FALSE.
1450  *
1451  * Since: 1.4
1452  */
1453 gboolean
1454 gst_structure_get_int64 (const GstStructure * structure,
1455     const gchar * fieldname, gint64 * value)
1456 {
1457   GstStructureField *field;
1458
1459   g_return_val_if_fail (structure != NULL, FALSE);
1460   g_return_val_if_fail (fieldname != NULL, FALSE);
1461   g_return_val_if_fail (value != NULL, FALSE);
1462
1463   field = gst_structure_get_field (structure, fieldname);
1464
1465   if (field == NULL || G_VALUE_TYPE (&field->value) != G_TYPE_INT64)
1466     return FALSE;
1467
1468   *value = gst_g_value_get_int64_unchecked (&field->value);
1469
1470   return TRUE;
1471 }
1472
1473 /**
1474  * gst_structure_get_uint64:
1475  * @structure: a #GstStructure
1476  * @fieldname: the name of a field
1477  * @value: (out): a pointer to a #guint64 to set
1478  *
1479  * Sets the #guint64 pointed to by @value corresponding to the value of the
1480  * given field. Caller is responsible for making sure the field exists
1481  * and has the correct type.
1482  *
1483  * Returns: %TRUE if the value could be set correctly. If there was no field
1484  * with @fieldname or the existing field did not contain a #guint64, this function
1485  * returns %FALSE.
1486  *
1487  * Since: 1.4
1488  */
1489 gboolean
1490 gst_structure_get_uint64 (const GstStructure * structure,
1491     const gchar * fieldname, guint64 * value)
1492 {
1493   GstStructureField *field;
1494
1495   g_return_val_if_fail (structure != NULL, FALSE);
1496   g_return_val_if_fail (fieldname != NULL, FALSE);
1497   g_return_val_if_fail (value != NULL, FALSE);
1498
1499   field = gst_structure_get_field (structure, fieldname);
1500
1501   if (field == NULL || G_VALUE_TYPE (&field->value) != G_TYPE_UINT64)
1502     return FALSE;
1503
1504   *value = gst_g_value_get_uint64_unchecked (&field->value);
1505
1506   return TRUE;
1507 }
1508
1509 /**
1510  * gst_structure_get_date:
1511  * @structure: a #GstStructure
1512  * @fieldname: the name of a field
1513  * @value: (out callee-allocates): a pointer to a #GDate to set
1514  *
1515  * Sets the date pointed to by @value corresponding to the date of the
1516  * given field.  Caller is responsible for making sure the field exists
1517  * and has the correct type.
1518  *
1519  * On success @value will point to a newly-allocated copy of the date which
1520  * should be freed with g_date_free() when no longer needed (note: this is
1521  * inconsistent with e.g. gst_structure_get_string() which doesn't return a
1522  * copy of the string).
1523  *
1524  * Returns: %TRUE if the value could be set correctly. If there was no field
1525  * with @fieldname or the existing field did not contain a data, this function
1526  * returns %FALSE.
1527  */
1528 gboolean
1529 gst_structure_get_date (const GstStructure * structure, const gchar * fieldname,
1530     GDate ** value)
1531 {
1532   GstStructureField *field;
1533
1534   g_return_val_if_fail (structure != NULL, FALSE);
1535   g_return_val_if_fail (fieldname != NULL, FALSE);
1536   g_return_val_if_fail (value != NULL, FALSE);
1537
1538   field = gst_structure_get_field (structure, fieldname);
1539
1540   if (field == NULL || G_VALUE_TYPE (&field->value) != G_TYPE_DATE)
1541     return FALSE;
1542
1543   /* FIXME: 2.0 g_value_dup_boxed() -> g_value_get_boxed() */
1544   *value = g_value_dup_boxed (&field->value);
1545
1546   return TRUE;
1547 }
1548
1549 /**
1550  * gst_structure_get_date_time:
1551  * @structure: a #GstStructure
1552  * @fieldname: the name of a field
1553  * @value: (out callee-allocates): a pointer to a #GstDateTime to set
1554  *
1555  * Sets the datetime pointed to by @value corresponding to the datetime of the
1556  * given field. Caller is responsible for making sure the field exists
1557  * and has the correct type.
1558  *
1559  * On success @value will point to a reference of the datetime which
1560  * should be unreffed with gst_date_time_unref() when no longer needed
1561  * (note: this is inconsistent with e.g. gst_structure_get_string()
1562  * which doesn't return a copy of the string).
1563  *
1564  * Returns: %TRUE if the value could be set correctly. If there was no field
1565  * with @fieldname or the existing field did not contain a data, this function
1566  * returns %FALSE.
1567  */
1568 gboolean
1569 gst_structure_get_date_time (const GstStructure * structure,
1570     const gchar * fieldname, GstDateTime ** value)
1571 {
1572   GstStructureField *field;
1573
1574   g_return_val_if_fail (structure != NULL, FALSE);
1575   g_return_val_if_fail (fieldname != NULL, FALSE);
1576   g_return_val_if_fail (value != NULL, FALSE);
1577
1578   field = gst_structure_get_field (structure, fieldname);
1579
1580   if (field == NULL)
1581     return FALSE;
1582   if (!GST_VALUE_HOLDS_DATE_TIME (&field->value))
1583     return FALSE;
1584
1585   /* FIXME 2.0: g_value_dup_boxed() -> g_value_get_boxed() */
1586   *value = g_value_dup_boxed (&field->value);
1587
1588   return TRUE;
1589 }
1590
1591 /**
1592  * gst_structure_get_clock_time:
1593  * @structure: a #GstStructure
1594  * @fieldname: the name of a field
1595  * @value: (out): a pointer to a #GstClockTime to set
1596  *
1597  * Sets the clock time pointed to by @value corresponding to the clock time
1598  * of the given field.  Caller is responsible for making sure the field exists
1599  * and has the correct type.
1600  *
1601  * Returns: %TRUE if the value could be set correctly. If there was no field
1602  * with @fieldname or the existing field did not contain a #GstClockTime, this
1603  * function returns %FALSE.
1604  */
1605 gboolean
1606 gst_structure_get_clock_time (const GstStructure * structure,
1607     const gchar * fieldname, GstClockTime * value)
1608 {
1609   return gst_structure_get_uint64 (structure, fieldname, value);
1610 }
1611
1612 /**
1613  * gst_structure_get_double:
1614  * @structure: a #GstStructure
1615  * @fieldname: the name of a field
1616  * @value: (out): a pointer to a gdouble to set
1617  *
1618  * Sets the double pointed to by @value corresponding to the value of the
1619  * given field.  Caller is responsible for making sure the field exists
1620  * and has the correct type.
1621  *
1622  * Returns: %TRUE if the value could be set correctly. If there was no field
1623  * with @fieldname or the existing field did not contain a double, this
1624  * function returns %FALSE.
1625  */
1626 gboolean
1627 gst_structure_get_double (const GstStructure * structure,
1628     const gchar * fieldname, gdouble * value)
1629 {
1630   GstStructureField *field;
1631
1632   g_return_val_if_fail (structure != NULL, FALSE);
1633   g_return_val_if_fail (fieldname != NULL, FALSE);
1634   g_return_val_if_fail (value != NULL, FALSE);
1635
1636   field = gst_structure_get_field (structure, fieldname);
1637
1638   if (field == NULL || G_VALUE_TYPE (&field->value) != G_TYPE_DOUBLE)
1639     return FALSE;
1640
1641   *value = gst_g_value_get_double_unchecked (&field->value);
1642
1643   return TRUE;
1644 }
1645
1646 /**
1647  * gst_structure_get_string:
1648  * @structure: a #GstStructure
1649  * @fieldname: the name of a field
1650  *
1651  * Finds the field corresponding to @fieldname, and returns the string
1652  * contained in the field's value.  Caller is responsible for making
1653  * sure the field exists and has the correct type.
1654  *
1655  * The string should not be modified, and remains valid until the next
1656  * call to a gst_structure_*() function with the given structure.
1657  *
1658  * Returns: (nullable): a pointer to the string or %NULL when the
1659  * field did not exist or did not contain a string.
1660  */
1661 const gchar *
1662 gst_structure_get_string (const GstStructure * structure,
1663     const gchar * fieldname)
1664 {
1665   GstStructureField *field;
1666
1667   g_return_val_if_fail (structure != NULL, NULL);
1668   g_return_val_if_fail (fieldname != NULL, NULL);
1669
1670   field = gst_structure_get_field (structure, fieldname);
1671
1672   if (field == NULL || G_VALUE_TYPE (&field->value) != G_TYPE_STRING)
1673     return NULL;
1674
1675   return gst_g_value_get_string_unchecked (&field->value);
1676 }
1677
1678 /**
1679  * gst_structure_get_enum:
1680  * @structure: a #GstStructure
1681  * @fieldname: the name of a field
1682  * @enumtype: the enum type of a field
1683  * @value: (out): a pointer to an int to set
1684  *
1685  * Sets the int pointed to by @value corresponding to the value of the
1686  * given field.  Caller is responsible for making sure the field exists,
1687  * has the correct type and that the enumtype is correct.
1688  *
1689  * Returns: %TRUE if the value could be set correctly. If there was no field
1690  * with @fieldname or the existing field did not contain an enum of the given
1691  * type, this function returns %FALSE.
1692  */
1693 gboolean
1694 gst_structure_get_enum (const GstStructure * structure,
1695     const gchar * fieldname, GType enumtype, gint * value)
1696 {
1697   GstStructureField *field;
1698
1699   g_return_val_if_fail (structure != NULL, FALSE);
1700   g_return_val_if_fail (fieldname != NULL, FALSE);
1701   g_return_val_if_fail (enumtype != G_TYPE_INVALID, FALSE);
1702   g_return_val_if_fail (value != NULL, FALSE);
1703
1704   field = gst_structure_get_field (structure, fieldname);
1705
1706   if (field == NULL)
1707     return FALSE;
1708   if (!G_TYPE_CHECK_VALUE_TYPE (&field->value, enumtype))
1709     return FALSE;
1710
1711   *value = g_value_get_enum (&field->value);
1712
1713   return TRUE;
1714 }
1715
1716 /**
1717  * gst_structure_get_fraction:
1718  * @structure: a #GstStructure
1719  * @fieldname: the name of a field
1720  * @value_numerator: (out): a pointer to an int to set
1721  * @value_denominator: (out): a pointer to an int to set
1722  *
1723  * Sets the integers pointed to by @value_numerator and @value_denominator
1724  * corresponding to the value of the given field.  Caller is responsible
1725  * for making sure the field exists and has the correct type.
1726  *
1727  * Returns: %TRUE if the values could be set correctly. If there was no field
1728  * with @fieldname or the existing field did not contain a GstFraction, this
1729  * function returns %FALSE.
1730  */
1731 gboolean
1732 gst_structure_get_fraction (const GstStructure * structure,
1733     const gchar * fieldname, gint * value_numerator, gint * value_denominator)
1734 {
1735   GstStructureField *field;
1736
1737   g_return_val_if_fail (structure != NULL, FALSE);
1738   g_return_val_if_fail (fieldname != NULL, FALSE);
1739   g_return_val_if_fail (value_numerator != NULL, FALSE);
1740   g_return_val_if_fail (value_denominator != NULL, FALSE);
1741
1742   field = gst_structure_get_field (structure, fieldname);
1743
1744   if (field == NULL || G_VALUE_TYPE (&field->value) != GST_TYPE_FRACTION)
1745     return FALSE;
1746
1747   *value_numerator = gst_value_get_fraction_numerator (&field->value);
1748   *value_denominator = gst_value_get_fraction_denominator (&field->value);
1749
1750   return TRUE;
1751 }
1752
1753 /**
1754  * gst_structure_get_flagset:
1755  * @structure: a #GstStructure
1756  * @fieldname: the name of a field
1757  * @value_flags: (out) (allow-none): a pointer to a guint for the flags field
1758  * @value_mask: (out) (allow-none): a pointer to a guint for the mask field
1759  *
1760  * Read the GstFlagSet flags and mask out of the structure into the
1761  * provided pointers.
1762  *
1763  * Returns: %TRUE if the values could be set correctly. If there was no field
1764  * with @fieldname or the existing field did not contain a GstFlagSet, this
1765  * function returns %FALSE.
1766  *
1767  * Since: 1.6
1768  */
1769 gboolean
1770 gst_structure_get_flagset (const GstStructure * structure,
1771     const gchar * fieldname, guint * value_flags, guint * value_mask)
1772 {
1773   GstStructureField *field;
1774
1775   g_return_val_if_fail (structure != NULL, FALSE);
1776   g_return_val_if_fail (fieldname != NULL, FALSE);
1777
1778   field = gst_structure_get_field (structure, fieldname);
1779
1780   if (field == NULL || !GST_VALUE_HOLDS_FLAG_SET (&field->value))
1781     return FALSE;
1782
1783   if (value_flags)
1784     *value_flags = gst_value_get_flagset_flags (&field->value);
1785   if (value_mask)
1786     *value_mask = gst_value_get_flagset_mask (&field->value);
1787
1788   return TRUE;
1789 }
1790
1791 static GType
1792 gst_structure_value_get_generic_type (const GValue * val)
1793 {
1794   if (G_VALUE_TYPE (val) == GST_TYPE_LIST
1795       || G_VALUE_TYPE (val) == GST_TYPE_ARRAY) {
1796     GArray *array = g_value_peek_pointer (val);
1797
1798     if (array->len > 0) {
1799       GValue *value = &g_array_index (array, GValue, 0);
1800
1801       return gst_structure_value_get_generic_type (value);
1802     } else {
1803       return G_TYPE_INT;
1804     }
1805   } else if (G_VALUE_TYPE (val) == GST_TYPE_INT_RANGE) {
1806     return G_TYPE_INT;
1807   } else if (G_VALUE_TYPE (val) == GST_TYPE_INT64_RANGE) {
1808     return G_TYPE_INT64;
1809   } else if (G_VALUE_TYPE (val) == GST_TYPE_DOUBLE_RANGE) {
1810     return G_TYPE_DOUBLE;
1811   } else if (G_VALUE_TYPE (val) == GST_TYPE_FRACTION_RANGE) {
1812     return GST_TYPE_FRACTION;
1813   }
1814   return G_VALUE_TYPE (val);
1815 }
1816
1817 gboolean
1818 priv_gst_structure_append_to_gstring (const GstStructure * structure,
1819     GString * s)
1820 {
1821   GstStructureField *field;
1822   guint i, len;
1823
1824   g_return_val_if_fail (s != NULL, FALSE);
1825
1826   len = GST_STRUCTURE_FIELDS (structure)->len;
1827   for (i = 0; i < len; i++) {
1828     char *t;
1829     GType type;
1830
1831     field = GST_STRUCTURE_FIELD (structure, i);
1832
1833     if (G_VALUE_TYPE (&field->value) == GST_TYPE_ARRAY) {
1834       t = _priv_gst_value_serialize_any_list (&field->value, "< ", " >", FALSE);
1835     } else if (G_VALUE_TYPE (&field->value) == GST_TYPE_LIST) {
1836       t = _priv_gst_value_serialize_any_list (&field->value, "{ ", " }", FALSE);
1837     } else {
1838       t = gst_value_serialize (&field->value);
1839     }
1840
1841     type = gst_structure_value_get_generic_type (&field->value);
1842
1843     g_string_append_len (s, ", ", 2);
1844     /* FIXME: do we need to escape fieldnames? */
1845     g_string_append (s, g_quark_to_string (field->name));
1846     g_string_append_len (s, "=(", 2);
1847     g_string_append (s, _priv_gst_value_gtype_to_abbr (type));
1848     g_string_append_c (s, ')');
1849     if (t) {
1850       g_string_append (s, t);
1851       g_free (t);
1852     } else if (G_TYPE_CHECK_VALUE_TYPE (&field->value, G_TYPE_POINTER)) {
1853       gpointer ptr = g_value_get_pointer (&field->value);
1854
1855       if (!ptr)
1856         g_string_append (s, "NULL");
1857       else
1858         g_string_append_printf (s, "%p", ptr);
1859     } else {
1860       if (!G_TYPE_CHECK_VALUE_TYPE (&field->value, G_TYPE_STRING))
1861         GST_WARNING ("No value transform to serialize field '%s' of type '%s'",
1862             g_quark_to_string (field->name),
1863             _priv_gst_value_gtype_to_abbr (type));
1864       /* TODO(ensonic): don't print NULL if field->value is not empty */
1865       g_string_append (s, "NULL");
1866     }
1867   }
1868
1869   g_string_append_c (s, ';');
1870   return TRUE;
1871 }
1872
1873 gboolean
1874 priv__gst_structure_append_template_to_gstring (GQuark field_id,
1875     const GValue * value, gpointer user_data)
1876 {
1877   GType type = gst_structure_value_get_generic_type (value);
1878   GString *s = (GString *) user_data;
1879
1880   g_string_append_len (s, ", ", 2);
1881   /* FIXME: do we need to escape fieldnames? */
1882   g_string_append (s, g_quark_to_string (field_id));
1883   g_string_append_len (s, "=(", 2);
1884   g_string_append (s, _priv_gst_value_gtype_to_abbr (type));
1885   g_string_append_c (s, ')');
1886
1887   //TODO(ensonic): table like GstStructureAbbreviation (or extend it)
1888   if (type == G_TYPE_INT) {
1889     g_string_append_len (s, "%i", 2);
1890   } else if (type == G_TYPE_UINT) {
1891     g_string_append_len (s, "%u", 2);
1892   } else if (type == G_TYPE_FLOAT) {
1893     g_string_append_len (s, "%f", 2);
1894   } else if (type == G_TYPE_DOUBLE) {
1895     g_string_append_len (s, "%lf", 3);
1896   } else if (type == G_TYPE_STRING) {
1897     g_string_append_len (s, "%s", 2);
1898   } else if (type == G_TYPE_BOOLEAN) {
1899     /* we normally store this as a string, but can parse it also from an int */
1900     g_string_append_len (s, "%i", 2);
1901   } else if (type == G_TYPE_INT64) {
1902     g_string_append (s, "%" G_GINT64_FORMAT);
1903   } else if (type == G_TYPE_UINT64) {
1904     g_string_append (s, "%" G_GUINT64_FORMAT);
1905   } else if (type == GST_TYPE_STRUCTURE) {
1906     g_string_append (s, "%" GST_WRAPPED_PTR_FORMAT);
1907   } else if (g_type_is_a (type, G_TYPE_ENUM)
1908       || g_type_is_a (type, G_TYPE_FLAGS)) {
1909     g_string_append_len (s, "%i", 2);
1910   } else if (type == G_TYPE_GTYPE) {
1911     g_string_append_len (s, "%s", 2);
1912   } else if (type == G_TYPE_POINTER) {
1913     g_string_append_len (s, "%p", 2);
1914   } else {
1915     GST_WARNING ("unhandled type: %s", g_type_name (type));
1916     g_string_append (s, "%" GST_WRAPPED_PTR_FORMAT);
1917   }
1918
1919   return TRUE;
1920 }
1921
1922 /**
1923  * gst_structure_to_string:
1924  * @structure: a #GstStructure
1925  *
1926  * Converts @structure to a human-readable string representation.
1927  *
1928  * For debugging purposes its easier to do something like this:
1929  * |[<!-- language="C" -->
1930  * GST_LOG ("structure is %" GST_PTR_FORMAT, structure);
1931  * ]|
1932  * This prints the structure in human readable form.
1933  *
1934  * The current implementation of serialization will lead to unexpected results
1935  * when there are nested #GstCaps / #GstStructure deeper than one level.
1936  *
1937  * Free-function: g_free
1938  *
1939  * Returns: (transfer full): a pointer to string allocated by g_malloc().
1940  *     g_free() after usage.
1941  */
1942 gchar *
1943 gst_structure_to_string (const GstStructure * structure)
1944 {
1945   GString *s;
1946
1947   /* NOTE:  This function is potentially called by the debug system,
1948    * so any calls to gst_log() (and GST_DEBUG(), GST_LOG(), etc.)
1949    * should be careful to avoid recursion.  This includes any functions
1950    * called by gst_structure_to_string.  In particular, calls should
1951    * not use the GST_PTR_FORMAT extension.  */
1952
1953   g_return_val_if_fail (structure != NULL, NULL);
1954
1955   /* we estimate a minimum size based on the number of fields in order to
1956    * avoid unnecessary reallocs within GString */
1957   s = g_string_sized_new (STRUCTURE_ESTIMATED_STRING_LEN (structure));
1958   g_string_append (s, g_quark_to_string (structure->name));
1959   priv_gst_structure_append_to_gstring (structure, s);
1960   return g_string_free (s, FALSE);
1961 }
1962
1963 static gboolean
1964 gst_structure_parse_field (gchar * str,
1965     gchar ** after, GstStructureField * field)
1966 {
1967   gchar *name;
1968   gchar *name_end;
1969   gchar *s;
1970   gchar c;
1971
1972   s = str;
1973
1974   while (g_ascii_isspace (*s) || (s[0] == '\\' && g_ascii_isspace (s[1])))
1975     s++;
1976   name = s;
1977   if (G_UNLIKELY (!_priv_gst_value_parse_simple_string (s, &name_end))) {
1978     GST_WARNING ("failed to parse simple string, str=%s", str);
1979     return FALSE;
1980   }
1981
1982   s = name_end;
1983   while (g_ascii_isspace (*s) || (s[0] == '\\' && g_ascii_isspace (s[1])))
1984     s++;
1985
1986   if (G_UNLIKELY (*s != '=')) {
1987     GST_WARNING ("missing assignment operator in the field, str=%s", str);
1988     return FALSE;
1989   }
1990   s++;
1991
1992   c = *name_end;
1993   *name_end = '\0';
1994   field->name = g_quark_from_string (name);
1995   GST_DEBUG ("trying field name '%s'", name);
1996   *name_end = c;
1997
1998   if (G_UNLIKELY (!_priv_gst_value_parse_value (s, &s, &field->value,
1999               G_TYPE_INVALID))) {
2000     GST_WARNING ("failed to parse value %s", str);
2001     return FALSE;
2002   }
2003
2004   *after = s;
2005   return TRUE;
2006 }
2007
2008 gboolean
2009 priv_gst_structure_parse_name (gchar * str, gchar ** start, gchar ** end,
2010     gchar ** next)
2011 {
2012   char *w;
2013   char *r;
2014
2015   r = str;
2016
2017   /* skip spaces (FIXME: _isspace treats tabs and newlines as space!) */
2018   while (*r && (g_ascii_isspace (*r) || (r[0] == '\\'
2019               && g_ascii_isspace (r[1]))))
2020     r++;
2021
2022   *start = r;
2023
2024   if (G_UNLIKELY (!_priv_gst_value_parse_string (r, &w, &r, TRUE))) {
2025     GST_WARNING ("Failed to parse structure string '%s'", str);
2026     return FALSE;
2027   }
2028
2029   *end = w;
2030   *next = r;
2031
2032   return TRUE;
2033 }
2034
2035 gboolean
2036 priv_gst_structure_parse_fields (gchar * str, gchar ** end,
2037     GstStructure * structure)
2038 {
2039   gchar *r;
2040   GstStructureField field;
2041
2042   r = str;
2043
2044   do {
2045     while (*r && (g_ascii_isspace (*r) || (r[0] == '\\'
2046                 && g_ascii_isspace (r[1]))))
2047       r++;
2048     if (*r == ';') {
2049       /* end of structure, get the next char and finish */
2050       r++;
2051       break;
2052     }
2053     if (*r == '\0') {
2054       /* accept \0 as end delimiter */
2055       break;
2056     }
2057     if (G_UNLIKELY (*r != ',')) {
2058       GST_WARNING ("Failed to find delimiter, r=%s", r);
2059       return FALSE;
2060     }
2061     r++;
2062     while (*r && (g_ascii_isspace (*r) || (r[0] == '\\'
2063                 && g_ascii_isspace (r[1]))))
2064       r++;
2065
2066     memset (&field, 0, sizeof (field));
2067     if (G_UNLIKELY (!gst_structure_parse_field (r, &r, &field))) {
2068       GST_WARNING ("Failed to parse field, r=%s", r);
2069       return FALSE;
2070     }
2071     gst_structure_set_field (structure, &field);
2072   } while (TRUE);
2073
2074   *end = r;
2075
2076   return TRUE;
2077 }
2078
2079 /**
2080  * gst_structure_new_from_string:
2081  * @string: a string representation of a #GstStructure
2082  *
2083  * Creates a #GstStructure from a string representation.
2084  * If end is not %NULL, a pointer to the place inside the given string
2085  * where parsing ended will be returned.
2086  *
2087  * The current implementation of serialization will lead to unexpected results
2088  * when there are nested #GstCaps / #GstStructure deeper than one level.
2089  *
2090  * Free-function: gst_structure_free
2091  *
2092  * Returns: (transfer full) (nullable): a new #GstStructure or %NULL
2093  *     when the string could not be parsed. Free with
2094  *     gst_structure_free() after use.
2095  *
2096  * Since: 1.2
2097  */
2098 GstStructure *
2099 gst_structure_new_from_string (const gchar * string)
2100 {
2101   return gst_structure_from_string (string, NULL);
2102 }
2103
2104 /**
2105  * gst_structure_from_string:
2106  * @string: a string representation of a #GstStructure.
2107  * @end: (out) (allow-none) (transfer none) (skip): pointer to store the end of the string in.
2108  *
2109  * Creates a #GstStructure from a string representation.
2110  * If end is not %NULL, a pointer to the place inside the given string
2111  * where parsing ended will be returned.
2112  *
2113  * Free-function: gst_structure_free
2114  *
2115  * Returns: (transfer full) (nullable): a new #GstStructure or %NULL
2116  *     when the string could not be parsed. Free with
2117  *     gst_structure_free() after use.
2118  */
2119 GstStructure *
2120 gst_structure_from_string (const gchar * string, gchar ** end)
2121 {
2122   char *name;
2123   char *copy;
2124   char *w;
2125   char *r;
2126   char save;
2127   GstStructure *structure = NULL;
2128
2129   g_return_val_if_fail (string != NULL, NULL);
2130
2131   copy = g_strdup (string);
2132   r = copy;
2133
2134   if (!priv_gst_structure_parse_name (r, &name, &w, &r))
2135     goto error;
2136
2137   save = *w;
2138   *w = '\0';
2139   structure = gst_structure_new_empty (name);
2140   *w = save;
2141
2142   if (G_UNLIKELY (structure == NULL))
2143     goto error;
2144
2145   if (!priv_gst_structure_parse_fields (r, &r, structure))
2146     goto error;
2147
2148   if (end)
2149     *end = (char *) string + (r - copy);
2150   else if (*r)
2151     g_warning ("gst_structure_from_string did not consume whole string,"
2152         " but caller did not provide end pointer (\"%s\")", string);
2153
2154   g_free (copy);
2155   return structure;
2156
2157 error:
2158   if (structure)
2159     gst_structure_free (structure);
2160   g_free (copy);
2161   return NULL;
2162 }
2163
2164 static void
2165 gst_structure_transform_to_string (const GValue * src_value,
2166     GValue * dest_value)
2167 {
2168   g_return_if_fail (src_value != NULL);
2169   g_return_if_fail (dest_value != NULL);
2170
2171   dest_value->data[0].v_pointer =
2172       gst_structure_to_string (src_value->data[0].v_pointer);
2173 }
2174
2175 static GstStructure *
2176 gst_structure_copy_conditional (const GstStructure * structure)
2177 {
2178   if (structure)
2179     return gst_structure_copy (structure);
2180   return NULL;
2181 }
2182
2183 /* fixate utility functions */
2184
2185 /**
2186  * gst_structure_fixate_field_nearest_int:
2187  * @structure: a #GstStructure
2188  * @field_name: a field in @structure
2189  * @target: the target value of the fixation
2190  *
2191  * Fixates a #GstStructure by changing the given field to the nearest
2192  * integer to @target that is a subset of the existing field.
2193  *
2194  * Returns: %TRUE if the structure could be fixated
2195  */
2196 gboolean
2197 gst_structure_fixate_field_nearest_int (GstStructure * structure,
2198     const char *field_name, int target)
2199 {
2200   const GValue *value;
2201
2202   g_return_val_if_fail (gst_structure_has_field (structure, field_name), FALSE);
2203   g_return_val_if_fail (IS_MUTABLE (structure), FALSE);
2204
2205   value = gst_structure_get_value (structure, field_name);
2206
2207   if (G_VALUE_TYPE (value) == G_TYPE_INT) {
2208     /* already fixed */
2209     return FALSE;
2210   } else if (G_VALUE_TYPE (value) == GST_TYPE_INT_RANGE) {
2211     int min, max, step;
2212
2213     min = gst_value_get_int_range_min (value);
2214     max = gst_value_get_int_range_max (value);
2215     step = gst_value_get_int_range_step (value);
2216
2217     target = CLAMP (target, min, max);
2218     if (G_UNLIKELY (step != 1)) {
2219       gint rem = target % step;
2220       target -= rem;
2221       if (rem > step / 2)
2222         target += step;
2223     }
2224
2225     gst_structure_set (structure, field_name, G_TYPE_INT, target, NULL);
2226     return TRUE;
2227   } else if (G_VALUE_TYPE (value) == GST_TYPE_LIST) {
2228     const GValue *list_value;
2229     int i, n;
2230     int best = 0;
2231     int best_index = -1;
2232
2233     n = gst_value_list_get_size (value);
2234     for (i = 0; i < n; i++) {
2235       list_value = gst_value_list_get_value (value, i);
2236       if (G_VALUE_TYPE (list_value) == G_TYPE_INT) {
2237         int x = gst_g_value_get_int_unchecked (list_value);
2238
2239         if (best_index == -1 || (ABS (target - x) < ABS (target - best))) {
2240           best_index = i;
2241           best = x;
2242         }
2243       }
2244     }
2245     if (best_index != -1) {
2246       gst_structure_set (structure, field_name, G_TYPE_INT, best, NULL);
2247       return TRUE;
2248     }
2249     return FALSE;
2250   }
2251
2252   return FALSE;
2253 }
2254
2255 /**
2256  * gst_structure_fixate_field_nearest_double:
2257  * @structure: a #GstStructure
2258  * @field_name: a field in @structure
2259  * @target: the target value of the fixation
2260  *
2261  * Fixates a #GstStructure by changing the given field to the nearest
2262  * double to @target that is a subset of the existing field.
2263  *
2264  * Returns: %TRUE if the structure could be fixated
2265  */
2266 gboolean
2267 gst_structure_fixate_field_nearest_double (GstStructure * structure,
2268     const char *field_name, double target)
2269 {
2270   const GValue *value;
2271
2272   g_return_val_if_fail (gst_structure_has_field (structure, field_name), FALSE);
2273   g_return_val_if_fail (IS_MUTABLE (structure), FALSE);
2274
2275   value = gst_structure_get_value (structure, field_name);
2276
2277   if (G_VALUE_TYPE (value) == G_TYPE_DOUBLE) {
2278     /* already fixed */
2279     return FALSE;
2280   } else if (G_VALUE_TYPE (value) == GST_TYPE_DOUBLE_RANGE) {
2281     double x;
2282
2283     x = gst_value_get_double_range_min (value);
2284     if (target < x)
2285       target = x;
2286     x = gst_value_get_double_range_max (value);
2287     if (target > x)
2288       target = x;
2289     gst_structure_set (structure, field_name, G_TYPE_DOUBLE, target, NULL);
2290     return TRUE;
2291   } else if (G_VALUE_TYPE (value) == GST_TYPE_LIST) {
2292     const GValue *list_value;
2293     int i, n;
2294     double best = 0;
2295     int best_index = -1;
2296
2297     n = gst_value_list_get_size (value);
2298     for (i = 0; i < n; i++) {
2299       list_value = gst_value_list_get_value (value, i);
2300       if (G_VALUE_TYPE (list_value) == G_TYPE_DOUBLE) {
2301         double x = gst_g_value_get_double_unchecked (list_value);
2302
2303         if (best_index == -1 || (ABS (target - x) < ABS (target - best))) {
2304           best_index = i;
2305           best = x;
2306         }
2307       }
2308     }
2309     if (best_index != -1) {
2310       gst_structure_set (structure, field_name, G_TYPE_DOUBLE, best, NULL);
2311       return TRUE;
2312     }
2313     return FALSE;
2314   }
2315
2316   return FALSE;
2317
2318 }
2319
2320 /**
2321  * gst_structure_fixate_field_boolean:
2322  * @structure: a #GstStructure
2323  * @field_name: a field in @structure
2324  * @target: the target value of the fixation
2325  *
2326  * Fixates a #GstStructure by changing the given @field_name field to the given
2327  * @target boolean if that field is not fixed yet.
2328  *
2329  * Returns: %TRUE if the structure could be fixated
2330  */
2331 gboolean
2332 gst_structure_fixate_field_boolean (GstStructure * structure,
2333     const char *field_name, gboolean target)
2334 {
2335   const GValue *value;
2336
2337   g_return_val_if_fail (gst_structure_has_field (structure, field_name), FALSE);
2338   g_return_val_if_fail (IS_MUTABLE (structure), FALSE);
2339
2340   value = gst_structure_get_value (structure, field_name);
2341
2342   if (G_VALUE_TYPE (value) == G_TYPE_BOOLEAN) {
2343     /* already fixed */
2344     return FALSE;
2345   } else if (G_VALUE_TYPE (value) == GST_TYPE_LIST) {
2346     const GValue *list_value;
2347     int i, n;
2348     int best = 0;
2349     int best_index = -1;
2350
2351     n = gst_value_list_get_size (value);
2352     for (i = 0; i < n; i++) {
2353       list_value = gst_value_list_get_value (value, i);
2354       if (G_VALUE_TYPE (list_value) == G_TYPE_BOOLEAN) {
2355         gboolean x = gst_g_value_get_boolean_unchecked (list_value);
2356
2357         if (best_index == -1 || x == target) {
2358           best_index = i;
2359           best = x;
2360         }
2361       }
2362     }
2363     if (best_index != -1) {
2364       gst_structure_set (structure, field_name, G_TYPE_BOOLEAN, best, NULL);
2365       return TRUE;
2366     }
2367     return FALSE;
2368   }
2369
2370   return FALSE;
2371 }
2372
2373 /**
2374  * gst_structure_fixate_field_string:
2375  * @structure: a #GstStructure
2376  * @field_name: a field in @structure
2377  * @target: the target value of the fixation
2378  *
2379  * Fixates a #GstStructure by changing the given @field_name field to the given
2380  * @target string if that field is not fixed yet.
2381  *
2382  * Returns: %TRUE if the structure could be fixated
2383  */
2384 gboolean
2385 gst_structure_fixate_field_string (GstStructure * structure,
2386     const gchar * field_name, const gchar * target)
2387 {
2388   const GValue *value;
2389
2390   g_return_val_if_fail (gst_structure_has_field (structure, field_name), FALSE);
2391   g_return_val_if_fail (IS_MUTABLE (structure), FALSE);
2392
2393   value = gst_structure_get_value (structure, field_name);
2394
2395   if (G_VALUE_TYPE (value) == G_TYPE_STRING) {
2396     /* already fixed */
2397     return FALSE;
2398   } else if (G_VALUE_TYPE (value) == GST_TYPE_LIST) {
2399     const GValue *list_value;
2400     int i, n;
2401     const gchar *best = NULL;
2402     int best_index = -1;
2403
2404     n = gst_value_list_get_size (value);
2405     for (i = 0; i < n; i++) {
2406       list_value = gst_value_list_get_value (value, i);
2407       if (G_VALUE_TYPE (list_value) == G_TYPE_STRING) {
2408         const gchar *x = g_value_get_string (list_value);
2409
2410         if (best_index == -1 || g_str_equal (x, target)) {
2411           best_index = i;
2412           best = x;
2413         }
2414       }
2415     }
2416     if (best_index != -1) {
2417       gst_structure_set (structure, field_name, G_TYPE_STRING, best, NULL);
2418       return TRUE;
2419     }
2420     return FALSE;
2421   }
2422
2423   return FALSE;
2424 }
2425
2426 /**
2427  * gst_structure_fixate_field_nearest_fraction:
2428  * @structure: a #GstStructure
2429  * @field_name: a field in @structure
2430  * @target_numerator: The numerator of the target value of the fixation
2431  * @target_denominator: The denominator of the target value of the fixation
2432  *
2433  * Fixates a #GstStructure by changing the given field to the nearest
2434  * fraction to @target_numerator/@target_denominator that is a subset
2435  * of the existing field.
2436  *
2437  * Returns: %TRUE if the structure could be fixated
2438  */
2439 gboolean
2440 gst_structure_fixate_field_nearest_fraction (GstStructure * structure,
2441     const char *field_name, const gint target_numerator,
2442     const gint target_denominator)
2443 {
2444   const GValue *value;
2445
2446   g_return_val_if_fail (gst_structure_has_field (structure, field_name), FALSE);
2447   g_return_val_if_fail (IS_MUTABLE (structure), FALSE);
2448   g_return_val_if_fail (target_denominator != 0, FALSE);
2449
2450   value = gst_structure_get_value (structure, field_name);
2451
2452   if (G_VALUE_TYPE (value) == GST_TYPE_FRACTION) {
2453     /* already fixed */
2454     return FALSE;
2455   } else if (G_VALUE_TYPE (value) == GST_TYPE_FRACTION_RANGE) {
2456     const GValue *x, *new_value;
2457     GValue target = { 0 };
2458     g_value_init (&target, GST_TYPE_FRACTION);
2459     gst_value_set_fraction (&target, target_numerator, target_denominator);
2460
2461     new_value = &target;
2462     x = gst_value_get_fraction_range_min (value);
2463     if (gst_value_compare (&target, x) == GST_VALUE_LESS_THAN)
2464       new_value = x;
2465     x = gst_value_get_fraction_range_max (value);
2466     if (gst_value_compare (&target, x) == GST_VALUE_GREATER_THAN)
2467       new_value = x;
2468
2469     gst_structure_set_value (structure, field_name, new_value);
2470     g_value_unset (&target);
2471     return TRUE;
2472   } else if (G_VALUE_TYPE (value) == GST_TYPE_LIST) {
2473     const GValue *list_value;
2474     int i, n;
2475     const GValue *best = NULL;
2476     gdouble target;
2477     gdouble cur_diff;
2478     gdouble best_diff = G_MAXDOUBLE;
2479
2480     target = (gdouble) target_numerator / (gdouble) target_denominator;
2481
2482     GST_DEBUG ("target %g, best %g", target, best_diff);
2483
2484     best = NULL;
2485
2486     n = gst_value_list_get_size (value);
2487     for (i = 0; i < n; i++) {
2488       list_value = gst_value_list_get_value (value, i);
2489       if (G_VALUE_TYPE (list_value) == GST_TYPE_FRACTION) {
2490         gint num, denom;
2491         gdouble list_double;
2492
2493         num = gst_value_get_fraction_numerator (list_value);
2494         denom = gst_value_get_fraction_denominator (list_value);
2495
2496         list_double = ((gdouble) num / (gdouble) denom);
2497         cur_diff = target - list_double;
2498
2499         GST_DEBUG ("curr diff %g, list %g", cur_diff, list_double);
2500
2501         if (cur_diff < 0)
2502           cur_diff = -cur_diff;
2503
2504         if (!best || cur_diff < best_diff) {
2505           GST_DEBUG ("new best %g", list_double);
2506           best = list_value;
2507           best_diff = cur_diff;
2508         }
2509       }
2510     }
2511     if (best != NULL) {
2512       gst_structure_set_value (structure, field_name, best);
2513       return TRUE;
2514     }
2515   }
2516
2517   return FALSE;
2518 }
2519
2520 static gboolean
2521 default_fixate (GQuark field_id, const GValue * value, gpointer data)
2522 {
2523   GstStructure *s = data;
2524   GValue v = { 0 };
2525
2526   if (gst_value_fixate (&v, value)) {
2527     gst_structure_id_take_value (s, field_id, &v);
2528   }
2529   return TRUE;
2530 }
2531
2532 /**
2533  * gst_structure_fixate_field:
2534  * @structure: a #GstStructure
2535  * @field_name: a field in @structure
2536  *
2537  * Fixates a #GstStructure by changing the given field with its fixated value.
2538  *
2539  * Returns: %TRUE if the structure field could be fixated
2540  */
2541 gboolean
2542 gst_structure_fixate_field (GstStructure * structure, const char *field_name)
2543 {
2544   GstStructureField *field;
2545
2546   g_return_val_if_fail (structure != NULL, FALSE);
2547   g_return_val_if_fail (IS_MUTABLE (structure), FALSE);
2548
2549   if (!(field = gst_structure_get_field (structure, field_name)))
2550     return FALSE;
2551
2552   return default_fixate (field->name, &field->value, structure);
2553 }
2554
2555 /* our very own version of G_VALUE_LCOPY that allows NULL return locations
2556  * (useful for message parsing functions where the return location is user
2557  * supplied and the user may pass %NULL if the value isn't of interest) */
2558 #define GST_VALUE_LCOPY(value, var_args, flags, __error, fieldname)           \
2559 G_STMT_START {                                                                \
2560   const GValue *_value = (value);                                             \
2561   guint _flags = (flags);                                                     \
2562   GType _value_type = G_VALUE_TYPE (_value);                                  \
2563   GTypeValueTable *_vtable = g_type_value_table_peek (_value_type);           \
2564   const gchar *_lcopy_format = _vtable->lcopy_format;                         \
2565   GTypeCValue _cvalues[G_VALUE_COLLECT_FORMAT_MAX_LENGTH] = { { 0, }, };      \
2566   guint _n_values = 0;                                                        \
2567                                                                               \
2568   while (*_lcopy_format != '\0') {                                            \
2569     g_assert (*_lcopy_format == G_VALUE_COLLECT_POINTER);                     \
2570     _cvalues[_n_values++].v_pointer = va_arg ((var_args), gpointer);          \
2571     _lcopy_format++;                                                          \
2572   }                                                                           \
2573   if (_n_values == 2 && !!_cvalues[0].v_pointer != !!_cvalues[1].v_pointer) { \
2574     *(__error) = g_strdup_printf ("either all or none of the return "         \
2575         "locations for field '%s' need to be NULL", fieldname);               \
2576   } else if (_cvalues[0].v_pointer != NULL) {                                 \
2577     *(__error) = _vtable->lcopy_value (_value, _n_values, _cvalues, _flags);  \
2578   }                                                                           \
2579 } G_STMT_END
2580
2581 /**
2582  * gst_structure_get_valist:
2583  * @structure: a #GstStructure
2584  * @first_fieldname: the name of the first field to read
2585  * @args: variable arguments
2586  *
2587  * Parses the variable arguments and reads fields from @structure accordingly.
2588  * valist-variant of gst_structure_get(). Look at the documentation of
2589  * gst_structure_get() for more details.
2590  *
2591  * Returns: %TRUE, or %FALSE if there was a problem reading any of the fields
2592  */
2593 gboolean
2594 gst_structure_get_valist (const GstStructure * structure,
2595     const char *first_fieldname, va_list args)
2596 {
2597   const char *field_name;
2598   GType expected_type = G_TYPE_INVALID;
2599
2600   g_return_val_if_fail (GST_IS_STRUCTURE (structure), FALSE);
2601   g_return_val_if_fail (first_fieldname != NULL, FALSE);
2602
2603   field_name = first_fieldname;
2604   while (field_name) {
2605     const GValue *val = NULL;
2606     gchar *err = NULL;
2607
2608     expected_type = va_arg (args, GType);
2609
2610     val = gst_structure_get_value (structure, field_name);
2611
2612     if (val == NULL)
2613       goto no_such_field;
2614
2615     if (G_VALUE_TYPE (val) != expected_type)
2616       goto wrong_type;
2617
2618     GST_VALUE_LCOPY (val, args, 0, &err, field_name);
2619     if (err) {
2620       g_warning ("%s: %s", G_STRFUNC, err);
2621       g_free (err);
2622       return FALSE;
2623     }
2624
2625     field_name = va_arg (args, const gchar *);
2626   }
2627
2628   return TRUE;
2629
2630 /* ERRORS */
2631 no_such_field:
2632   {
2633     GST_INFO ("Expected field '%s' in structure: %" GST_PTR_FORMAT,
2634         field_name, structure);
2635     return FALSE;
2636   }
2637 wrong_type:
2638   {
2639     GST_INFO ("Expected field '%s' in structure to be of type '%s', but "
2640         "field was of type '%s': %" GST_PTR_FORMAT, field_name,
2641         GST_STR_NULL (g_type_name (expected_type)),
2642         G_VALUE_TYPE_NAME (gst_structure_get_value (structure, field_name)),
2643         structure);
2644     return FALSE;
2645   }
2646 }
2647
2648 /**
2649  * gst_structure_id_get_valist:
2650  * @structure: a #GstStructure
2651  * @first_field_id: the quark of the first field to read
2652  * @args: variable arguments
2653  *
2654  * Parses the variable arguments and reads fields from @structure accordingly.
2655  * valist-variant of gst_structure_id_get(). Look at the documentation of
2656  * gst_structure_id_get() for more details.
2657  *
2658  * Returns: %TRUE, or %FALSE if there was a problem reading any of the fields
2659  */
2660 gboolean
2661 gst_structure_id_get_valist (const GstStructure * structure,
2662     GQuark first_field_id, va_list args)
2663 {
2664   GQuark field_id;
2665   GType expected_type = G_TYPE_INVALID;
2666
2667   g_return_val_if_fail (GST_IS_STRUCTURE (structure), FALSE);
2668   g_return_val_if_fail (first_field_id != 0, FALSE);
2669
2670   field_id = first_field_id;
2671   while (field_id) {
2672     const GValue *val = NULL;
2673     gchar *err = NULL;
2674
2675     expected_type = va_arg (args, GType);
2676
2677     val = gst_structure_id_get_value (structure, field_id);
2678
2679     if (val == NULL)
2680       goto no_such_field;
2681
2682     if (G_VALUE_TYPE (val) != expected_type)
2683       goto wrong_type;
2684
2685     GST_VALUE_LCOPY (val, args, 0, &err, g_quark_to_string (field_id));
2686     if (err) {
2687       g_warning ("%s: %s", G_STRFUNC, err);
2688       g_free (err);
2689       return FALSE;
2690     }
2691
2692     field_id = va_arg (args, GQuark);
2693   }
2694
2695   return TRUE;
2696
2697 /* ERRORS */
2698 no_such_field:
2699   {
2700     GST_DEBUG ("Expected field '%s' in structure: %" GST_PTR_FORMAT,
2701         GST_STR_NULL (g_quark_to_string (field_id)), structure);
2702     return FALSE;
2703   }
2704 wrong_type:
2705   {
2706     GST_DEBUG ("Expected field '%s' in structure to be of type '%s', but "
2707         "field was of type '%s': %" GST_PTR_FORMAT,
2708         g_quark_to_string (field_id),
2709         GST_STR_NULL (g_type_name (expected_type)),
2710         G_VALUE_TYPE_NAME (gst_structure_id_get_value (structure, field_id)),
2711         structure);
2712     return FALSE;
2713   }
2714 }
2715
2716 /**
2717  * gst_structure_get:
2718  * @structure: a #GstStructure
2719  * @first_fieldname: the name of the first field to read
2720  * @...: variable arguments
2721  *
2722  * Parses the variable arguments and reads fields from @structure accordingly.
2723  * Variable arguments should be in the form field name, field type
2724  * (as a GType), pointer(s) to a variable(s) to hold the return value(s).
2725  * The last variable argument should be %NULL.
2726  *
2727  * For refcounted (mini)objects you will receive a new reference which
2728  * you must release with a suitable _unref() when no longer needed. For
2729  * strings and boxed types you will receive a copy which you will need to
2730  * release with either g_free() or the suitable function for the boxed type.
2731  *
2732  * Returns: %FALSE if there was a problem reading any of the fields (e.g.
2733  *     because the field requested did not exist, or was of a type other
2734  *     than the type specified), otherwise %TRUE.
2735  */
2736 gboolean
2737 gst_structure_get (const GstStructure * structure, const char *first_fieldname,
2738     ...)
2739 {
2740   gboolean ret;
2741   va_list args;
2742
2743   g_return_val_if_fail (GST_IS_STRUCTURE (structure), FALSE);
2744   g_return_val_if_fail (first_fieldname != NULL, FALSE);
2745
2746   va_start (args, first_fieldname);
2747   ret = gst_structure_get_valist (structure, first_fieldname, args);
2748   va_end (args);
2749
2750   return ret;
2751 }
2752
2753 /**
2754  * gst_structure_id_get:
2755  * @structure: a #GstStructure
2756  * @first_field_id: the quark of the first field to read
2757  * @...: variable arguments
2758  *
2759  * Parses the variable arguments and reads fields from @structure accordingly.
2760  * Variable arguments should be in the form field id quark, field type
2761  * (as a GType), pointer(s) to a variable(s) to hold the return value(s).
2762  * The last variable argument should be %NULL (technically it should be a
2763  * 0 quark, but we require %NULL so compilers that support it can check for
2764  * the %NULL terminator and warn if it's not there).
2765  *
2766  * This function is just like gst_structure_get() only that it is slightly
2767  * more efficient since it saves the string-to-quark lookup in the global
2768  * quark hashtable.
2769  *
2770  * For refcounted (mini)objects you will receive a new reference which
2771  * you must release with a suitable _unref() when no longer needed. For
2772  * strings and boxed types you will receive a copy which you will need to
2773  * release with either g_free() or the suitable function for the boxed type.
2774  *
2775  * Returns: %FALSE if there was a problem reading any of the fields (e.g.
2776  *     because the field requested did not exist, or was of a type other
2777  *     than the type specified), otherwise %TRUE.
2778  */
2779 gboolean
2780 gst_structure_id_get (const GstStructure * structure, GQuark first_field_id,
2781     ...)
2782 {
2783   gboolean ret;
2784   va_list args;
2785
2786   g_return_val_if_fail (GST_IS_STRUCTURE (structure), FALSE);
2787   g_return_val_if_fail (first_field_id != 0, FALSE);
2788
2789   va_start (args, first_field_id);
2790   ret = gst_structure_id_get_valist (structure, first_field_id, args);
2791   va_end (args);
2792
2793   return ret;
2794 }
2795
2796 static gboolean
2797 gst_structure_is_equal_foreach (GQuark field_id, const GValue * val2,
2798     gpointer data)
2799 {
2800   const GstStructure *struct1 = (const GstStructure *) data;
2801   const GValue *val1 = gst_structure_id_get_value (struct1, field_id);
2802
2803   if (G_UNLIKELY (val1 == NULL))
2804     return FALSE;
2805   if (gst_value_compare (val1, val2) == GST_VALUE_EQUAL) {
2806     return TRUE;
2807   }
2808
2809   return FALSE;
2810 }
2811
2812 /**
2813  * gst_structure_is_equal:
2814  * @structure1: a #GstStructure.
2815  * @structure2: a #GstStructure.
2816  *
2817  * Tests if the two #GstStructure are equal.
2818  *
2819  * Returns: %TRUE if the two structures have the same name and field.
2820  **/
2821 gboolean
2822 gst_structure_is_equal (const GstStructure * structure1,
2823     const GstStructure * structure2)
2824 {
2825   g_return_val_if_fail (GST_IS_STRUCTURE (structure1), FALSE);
2826   g_return_val_if_fail (GST_IS_STRUCTURE (structure2), FALSE);
2827
2828   if (G_UNLIKELY (structure1 == structure2))
2829     return TRUE;
2830
2831   if (structure1->name != structure2->name) {
2832     return FALSE;
2833   }
2834   if (GST_STRUCTURE_FIELDS (structure1)->len !=
2835       GST_STRUCTURE_FIELDS (structure2)->len) {
2836     return FALSE;
2837   }
2838
2839   return gst_structure_foreach (structure1, gst_structure_is_equal_foreach,
2840       (gpointer) structure2);
2841 }
2842
2843
2844 typedef struct
2845 {
2846   GstStructure *dest;
2847   const GstStructure *intersect;
2848 }
2849 IntersectData;
2850
2851 static gboolean
2852 gst_structure_intersect_field1 (GQuark id, const GValue * val1, gpointer data)
2853 {
2854   IntersectData *idata = (IntersectData *) data;
2855   const GValue *val2 = gst_structure_id_get_value (idata->intersect, id);
2856
2857   if (G_UNLIKELY (val2 == NULL)) {
2858     gst_structure_id_set_value (idata->dest, id, val1);
2859   } else {
2860     GValue dest_value = { 0 };
2861     if (gst_value_intersect (&dest_value, val1, val2)) {
2862       gst_structure_id_take_value (idata->dest, id, &dest_value);
2863     } else {
2864       return FALSE;
2865     }
2866   }
2867   return TRUE;
2868 }
2869
2870 static gboolean
2871 gst_structure_intersect_field2 (GQuark id, const GValue * val1, gpointer data)
2872 {
2873   IntersectData *idata = (IntersectData *) data;
2874   const GValue *val2 = gst_structure_id_get_value (idata->intersect, id);
2875
2876   if (G_UNLIKELY (val2 == NULL)) {
2877     gst_structure_id_set_value (idata->dest, id, val1);
2878   }
2879   return TRUE;
2880 }
2881
2882 /**
2883  * gst_structure_intersect:
2884  * @struct1: a #GstStructure
2885  * @struct2: a #GstStructure
2886  *
2887  * Intersects @struct1 and @struct2 and returns the intersection.
2888  *
2889  * Returns: (nullable): Intersection of @struct1 and @struct2
2890  */
2891 GstStructure *
2892 gst_structure_intersect (const GstStructure * struct1,
2893     const GstStructure * struct2)
2894 {
2895   IntersectData data;
2896
2897   g_assert (struct1 != NULL);
2898   g_assert (struct2 != NULL);
2899
2900   if (G_UNLIKELY (struct1->name != struct2->name))
2901     return NULL;
2902
2903   /* copy fields from struct1 which we have not in struct2 to target
2904    * intersect if we have the field in both */
2905   data.dest = gst_structure_new_id_empty (struct1->name);
2906   data.intersect = struct2;
2907   if (G_UNLIKELY (!gst_structure_foreach ((GstStructure *) struct1,
2908               gst_structure_intersect_field1, &data)))
2909     goto error;
2910
2911   /* copy fields from struct2 which we have not in struct1 to target */
2912   data.intersect = struct1;
2913   if (G_UNLIKELY (!gst_structure_foreach ((GstStructure *) struct2,
2914               gst_structure_intersect_field2, &data)))
2915     goto error;
2916
2917   return data.dest;
2918
2919 error:
2920   gst_structure_free (data.dest);
2921   return NULL;
2922 }
2923
2924 static gboolean
2925 gst_caps_structure_can_intersect_field (GQuark id, const GValue * val1,
2926     gpointer data)
2927 {
2928   GstStructure *other = (GstStructure *) data;
2929   const GValue *val2 = gst_structure_id_get_value (other, id);
2930
2931   if (G_LIKELY (val2)) {
2932     if (!gst_value_can_intersect (val1, val2)) {
2933       return FALSE;
2934     } else {
2935       gint eq = gst_value_compare (val1, val2);
2936
2937       if (eq == GST_VALUE_UNORDERED) {
2938         /* we need to try interseting */
2939         if (!gst_value_intersect (NULL, val1, val2)) {
2940           return FALSE;
2941         }
2942       } else if (eq != GST_VALUE_EQUAL) {
2943         return FALSE;
2944       }
2945     }
2946   }
2947   return TRUE;
2948 }
2949
2950 /**
2951  * gst_structure_can_intersect:
2952  * @struct1: a #GstStructure
2953  * @struct2: a #GstStructure
2954  *
2955  * Tries intersecting @struct1 and @struct2 and reports whether the result
2956  * would not be empty.
2957  *
2958  * Returns: %TRUE if intersection would not be empty
2959  */
2960 gboolean
2961 gst_structure_can_intersect (const GstStructure * struct1,
2962     const GstStructure * struct2)
2963 {
2964   g_return_val_if_fail (GST_IS_STRUCTURE (struct1), FALSE);
2965   g_return_val_if_fail (GST_IS_STRUCTURE (struct2), FALSE);
2966
2967   if (G_UNLIKELY (struct1->name != struct2->name))
2968     return FALSE;
2969
2970   /* tries to intersect if we have the field in both */
2971   return gst_structure_foreach ((GstStructure *) struct1,
2972       gst_caps_structure_can_intersect_field, (gpointer) struct2);
2973 }
2974
2975 static gboolean
2976 gst_caps_structure_is_superset_field (GQuark field_id, const GValue * value,
2977     gpointer user_data)
2978 {
2979   GstStructure *subset = user_data;
2980   const GValue *other;
2981   int comparison;
2982
2983   if (!(other = gst_structure_id_get_value (subset, field_id)))
2984     /* field is missing in the subset => no subset */
2985     return FALSE;
2986
2987   comparison = gst_value_compare (value, other);
2988
2989   /* equal values are subset */
2990   if (comparison == GST_VALUE_EQUAL)
2991     return TRUE;
2992
2993   /* ordered, but unequal, values are not */
2994   if (comparison != GST_VALUE_UNORDERED)
2995     return FALSE;
2996
2997   return gst_value_is_subset (other, value);
2998 }
2999
3000 /**
3001  * gst_structure_is_subset:
3002  * @subset: a #GstStructure
3003  * @superset: a potentially greater #GstStructure
3004  *
3005  * Checks if @subset is a subset of @superset, i.e. has the same
3006  * structure name and for all fields that are existing in @superset,
3007  * @subset has a value that is a subset of the value in @superset.
3008  *
3009  * Returns: %TRUE if @subset is a subset of @superset
3010  */
3011 gboolean
3012 gst_structure_is_subset (const GstStructure * subset,
3013     const GstStructure * superset)
3014 {
3015   if ((superset->name != subset->name) ||
3016       (gst_structure_n_fields (superset) > gst_structure_n_fields (subset)))
3017     return FALSE;
3018
3019   return gst_structure_foreach ((GstStructure *) superset,
3020       gst_caps_structure_is_superset_field, (gpointer) subset);
3021 }
3022
3023
3024 /**
3025  * gst_structure_fixate:
3026  * @structure: a #GstStructure
3027  *
3028  * Fixate all values in @structure using gst_value_fixate().
3029  * @structure will be modified in-place and should be writable.
3030  */
3031 void
3032 gst_structure_fixate (GstStructure * structure)
3033 {
3034   g_return_if_fail (GST_IS_STRUCTURE (structure));
3035
3036   gst_structure_foreach (structure, default_fixate, structure);
3037 }
3038
3039 static gboolean
3040 _gst_structure_get_any_list (GstStructure * structure, GType type,
3041     const gchar * fieldname, GValueArray ** array)
3042 {
3043   GstStructureField *field;
3044   GValue val = G_VALUE_INIT;
3045
3046   g_return_val_if_fail (structure != NULL, FALSE);
3047   g_return_val_if_fail (fieldname != NULL, FALSE);
3048   g_return_val_if_fail (array != NULL, FALSE);
3049
3050   field = gst_structure_get_field (structure, fieldname);
3051
3052   if (field == NULL || G_VALUE_TYPE (&field->value) != type)
3053     return FALSE;
3054
3055   g_value_init (&val, G_TYPE_VALUE_ARRAY);
3056
3057   if (g_value_transform (&field->value, &val)) {
3058     *array = g_value_get_boxed (&val);
3059     return TRUE;
3060   }
3061
3062   g_value_unset (&val);
3063   return FALSE;
3064 }
3065
3066 /**
3067  * gst_structure_get_array:
3068  * @structure: a #GstStructure
3069  * @fieldname: the name of a field
3070  * @array: (out): a pointer to a #GValueArray
3071  *
3072  * This is useful in language bindings where unknown #GValue types are not
3073  * supported. This function will convert the %GST_TYPE_ARRAY into a newly
3074  * allocated #GValueArray and return it through @array. Be aware that this is
3075  * slower then getting the #GValue directly.
3076  *
3077  * Returns: %TRUE if the value could be set correctly. If there was no field
3078  * with @fieldname or the existing field did not contain a %GST_TYPE_ARRAY,
3079  * this function returns %FALSE.
3080  */
3081 gboolean
3082 gst_structure_get_array (GstStructure * structure, const gchar * fieldname,
3083     GValueArray ** array)
3084 {
3085   return _gst_structure_get_any_list (structure, GST_TYPE_ARRAY, fieldname,
3086       array);
3087 }
3088
3089 /**
3090  * gst_structure_get_list:
3091  * @structure: a #GstStructure
3092  * @fieldname: the name of a field
3093  * @array: (out): a pointer to a #GValueArray
3094  *
3095  * This is useful in language bindings where unknown #GValue types are not
3096  * supported. This function will convert the %GST_TYPE_LIST into a newly
3097  * allocated GValueArray and return it through @array. Be aware that this is
3098  * slower then getting the #GValue directly.
3099  *
3100  * Returns: %TRUE if the value could be set correctly. If there was no field
3101  * with @fieldname or the existing field did not contain a %GST_TYPE_LIST, this
3102  * function returns %FALSE.
3103  *
3104  * Since: 1.12
3105  */
3106 gboolean
3107 gst_structure_get_list (GstStructure * structure, const gchar * fieldname,
3108     GValueArray ** array)
3109 {
3110   return _gst_structure_get_any_list (structure, GST_TYPE_LIST, fieldname,
3111       array);
3112 }
3113
3114 static void
3115 _gst_structure_set_any_list (GstStructure * structure, GType type,
3116     const gchar * fieldname, const GValueArray * array)
3117 {
3118   GValue arval = G_VALUE_INIT;
3119   GValue value = G_VALUE_INIT;
3120
3121   g_return_if_fail (structure != NULL);
3122   g_return_if_fail (fieldname != NULL);
3123   g_return_if_fail (array != NULL);
3124   g_return_if_fail (IS_MUTABLE (structure));
3125
3126   g_value_init (&value, type);
3127   g_value_init (&arval, G_TYPE_VALUE_ARRAY);
3128   g_value_set_static_boxed (&arval, array);
3129
3130   if (g_value_transform (&arval, &value)) {
3131     gst_structure_id_set_value_internal (structure,
3132         g_quark_from_string (fieldname), &value);
3133   } else {
3134     g_warning ("Failed to convert a GValueArray");
3135   }
3136
3137   g_value_unset (&arval);
3138   g_value_unset (&value);
3139 }
3140
3141 /**
3142  * gst_structure_set_array:
3143  * @structure: a #GstStructure
3144  * @fieldname: the name of a field
3145  * @array: a pointer to a #GValueArray
3146  *
3147  * This is useful in language bindings where unknown GValue types are not
3148  * supported. This function will convert a @array to %GST_TYPE_ARRAY and set
3149  * the field specified by @fieldname.  Be aware that this is slower then using
3150  * %GST_TYPE_ARRAY in a #GValue directly.
3151  *
3152  * Since: 1.12
3153  */
3154 void
3155 gst_structure_set_array (GstStructure * structure, const gchar * fieldname,
3156     const GValueArray * array)
3157 {
3158   _gst_structure_set_any_list (structure, GST_TYPE_ARRAY, fieldname, array);
3159 }
3160
3161 /**
3162  * gst_structure_set_list:
3163  * @structure: a #GstStructure
3164  * @fieldname: the name of a field
3165  * @array: a pointer to a #GValueArray
3166  *
3167  * This is useful in language bindings where unknown GValue types are not
3168  * supported. This function will convert a @array to %GST_TYPE_LIST and set
3169  * the field specified by @fieldname. Be aware that this is slower then using
3170  * %GST_TYPE_LIST in a #GValue directly.
3171  *
3172  * Since: 1.12
3173  */
3174 void
3175 gst_structure_set_list (GstStructure * structure, const gchar * fieldname,
3176     const GValueArray * array)
3177 {
3178   _gst_structure_set_any_list (structure, GST_TYPE_LIST, fieldname, array);
3179 }