2 * Copyright (C) 2003 David A. Schleef <ds@schleef.org>
4 * gststructure.c: lists of { GQuark, GValue } tuples
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.
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.
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., 59 Temple Place - Suite 330,
19 * Boston, MA 02111-1307, USA.
28 #include "gst_private.h"
30 #include <gobject/gvaluecollector.h>
32 typedef struct _GstStructureField GstStructureField;
34 struct _GstStructureField
40 #define GST_STRUCTURE_FIELD(structure, index) \
41 &g_array_index((structure)->fields, GstStructureField, (index))
43 #define IS_MUTABLE(structure) \
44 (!(structure)->parent_refcount || \
45 g_atomic_int_get ((structure)->parent_refcount) == 1)
47 static void gst_structure_set_field (GstStructure * structure,
48 GstStructureField * field);
49 static GstStructureField *gst_structure_get_field (const GstStructure *
50 structure, const gchar * fieldname);
51 static GstStructureField *gst_structure_id_get_field (const GstStructure *
52 structure, GQuark field);
53 static void gst_structure_transform_to_string (const GValue * src_value,
55 static GstStructure *gst_structure_copy_conditional (const GstStructure *
57 static gboolean gst_structure_parse_value (gchar * str, gchar ** after,
58 GValue * value, GType default_type);
59 static gboolean gst_structure_parse_simple_string (gchar * s, gchar ** end);
62 gst_structure_get_type (void)
64 static GType gst_structure_type = 0;
66 if (!gst_structure_type) {
67 gst_structure_type = g_boxed_type_register_static ("GstStructure",
68 (GBoxedCopyFunc) gst_structure_copy_conditional,
69 (GBoxedFreeFunc) gst_structure_free);
71 g_value_register_transform_func (gst_structure_type, G_TYPE_STRING,
72 gst_structure_transform_to_string);
75 return gst_structure_type;
79 gst_structure_id_empty_new_with_size (GQuark quark, guint prealloc)
81 GstStructure *structure;
83 structure = g_new0 (GstStructure, 1);
84 structure->type = gst_structure_get_type ();
85 structure->name = quark;
87 g_array_sized_new (FALSE, TRUE, sizeof (GstStructureField), prealloc);
93 * gst_structure_id_empty_new:
94 * @quark: name of new structure
96 * Creates a new, empty #GstStructure with the given name.
98 * Returns: a new, empty #GstStructure
101 gst_structure_id_empty_new (GQuark quark)
103 g_return_val_if_fail (quark != 0, NULL);
105 return gst_structure_id_empty_new_with_size (quark, 0);
109 * gst_structure_empty_new:
110 * @name: name of new structure
112 * Creates a new, empty #GstStructure with the given name.
114 * Returns: a new, empty #GstStructure
117 gst_structure_empty_new (const gchar * name)
119 g_return_val_if_fail (name != NULL, NULL);
121 return gst_structure_id_empty_new_with_size (g_quark_from_string (name), 0);
126 * @name: name of new structure
127 * @firstfield: name of first field to set
128 * @...: additional arguments
130 * Creates a new #GstStructure with the given name. Parses the
131 * list of variable arguments and sets fields to the values listed.
132 * Variable arguments should be passed as field name, field type,
133 * and value. Last variable argument should be NULL.
135 * Returns: a new #GstStructure
138 gst_structure_new (const gchar * name, const gchar * firstfield, ...)
140 GstStructure *structure;
143 g_return_val_if_fail (name != NULL, NULL);
145 va_start (varargs, firstfield);
147 structure = gst_structure_new_valist (name, firstfield, varargs);
155 * gst_structure_new_valist:
156 * @name: name of new structure
157 * @firstfield: name of first field to set
158 * @varargs: variable argument list
160 * Creates a new #GstStructure with the given name. Structure fields
161 * are set according to the varargs in a manner similar to
162 * @gst_structure_new.
164 * Returns: a new #GstStructure
167 gst_structure_new_valist (const gchar * name,
168 const gchar * firstfield, va_list varargs)
170 GstStructure *structure;
172 g_return_val_if_fail (name != NULL, NULL);
174 structure = gst_structure_empty_new (name);
175 gst_structure_set_valist (structure, firstfield, varargs);
181 * gst_structure_set_parent_refcount:
182 * @structure: a #GstStructure
183 * @refcount: a pointer to the parent's refcount
185 * Sets the parent_refcount field of #GstStructure. This field is used to
186 * determine whether a structure is mutable or not. This function should only be
187 * called by code implementing parent objects of GstStructure, as described in
188 * the MT Refcounting section of the design documents.
190 * Returns: a new #GstStructure.
193 gst_structure_set_parent_refcount (GstStructure * structure, int *refcount)
195 g_return_if_fail (structure != NULL);
197 /* if we have a parent_refcount already, we can only clear
198 * if with a NULL refcount */
199 if (structure->parent_refcount)
200 g_return_if_fail (refcount == NULL);
202 g_return_if_fail (refcount != NULL);
204 structure->parent_refcount = refcount;
208 * gst_structure_copy:
209 * @structure: a #GstStructure to duplicate
211 * Duplicates a #GstStructure and all its fields and values.
213 * Returns: a new #GstStructure.
216 gst_structure_copy (const GstStructure * structure)
218 GstStructure *new_structure;
219 GstStructureField *field;
222 g_return_val_if_fail (structure != NULL, NULL);
225 gst_structure_id_empty_new_with_size (structure->name,
226 structure->fields->len);
228 for (i = 0; i < structure->fields->len; i++) {
229 GstStructureField new_field = { 0 };
231 field = GST_STRUCTURE_FIELD (structure, i);
233 new_field.name = field->name;
234 gst_value_init_and_copy (&new_field.value, &field->value);
235 g_array_append_val (new_structure->fields, new_field);
238 return new_structure;
242 * gst_structure_free:
243 * @structure: the #GstStructure to free
245 * Frees a #GstStructure and all its fields and values. The structure must not
246 * have a parent when this function is called.
249 gst_structure_free (GstStructure * structure)
251 GstStructureField *field;
254 g_return_if_fail (structure != NULL);
255 g_return_if_fail (structure->parent_refcount == NULL);
257 for (i = 0; i < structure->fields->len; i++) {
258 field = GST_STRUCTURE_FIELD (structure, i);
260 if (G_IS_VALUE (&field->value)) {
261 g_value_unset (&field->value);
264 g_array_free (structure->fields, TRUE);
266 memset (structure, 0xff, sizeof (GstStructure));
272 * gst_structure_get_name:
273 * @structure: a #GstStructure
277 * Returns: the name of the structure.
280 gst_structure_get_name (const GstStructure * structure)
282 g_return_val_if_fail (structure != NULL, NULL);
284 return g_quark_to_string (structure->name);
288 * gst_structure_has_name:
289 * @structure: a #GstStructure
290 * @name: structure name to check for
292 * Returns: TRUE if @name matches the name of the structure.
295 gst_structure_has_name (const GstStructure * structure, const gchar * name)
297 const gchar *structure_name;
299 g_return_val_if_fail (structure != NULL, FALSE);
300 g_return_val_if_fail (name != NULL, FALSE);
302 structure_name = g_quark_to_string (structure->name);
304 return (structure_name && strcmp (structure_name, name) == 0);
308 * gst_structure_get_name_id:
309 * @structure: a #GstStructure
313 * Returns: the quark representing the name of the structure.
316 gst_structure_get_name_id (const GstStructure * structure)
318 g_return_val_if_fail (structure != NULL, 0);
320 return structure->name;
324 * gst_structure_set_name:
325 * @structure: a #GstStructure
326 * @name: the new name of the structure
328 * Sets the name of the structure to the given name. The string
329 * provided is copied before being used.
332 gst_structure_set_name (GstStructure * structure, const gchar * name)
334 g_return_if_fail (structure != NULL);
335 g_return_if_fail (name != NULL);
336 g_return_if_fail (IS_MUTABLE (structure));
338 structure->name = g_quark_from_string (name);
342 * gst_structure_id_set_value:
343 * @structure: a #GstStructure
344 * @field: a #GQuark representing a field
345 * @value: the new value of the field
347 * Sets the field with the given ID to the provided value. If the field
348 * does not exist, it is created. If the field exists, the previous
352 gst_structure_id_set_value (GstStructure * structure,
353 GQuark field, const GValue * value)
355 GstStructureField gsfield = { 0, {0,} };
357 g_return_if_fail (structure != NULL);
358 g_return_if_fail (G_IS_VALUE (value));
359 g_return_if_fail (IS_MUTABLE (structure));
361 gsfield.name = field;
362 gst_value_init_and_copy (&gsfield.value, value);
364 gst_structure_set_field (structure, &gsfield);
368 * gst_structure_set_value:
369 * @structure: a #GstStructure
370 * @fieldname: the name of the field to set
371 * @value: the new value of the field
373 * Sets the field with the given name to the provided value. If the field
374 * does not exist, it is created. If the field exists, the previous
378 gst_structure_set_value (GstStructure * structure,
379 const gchar * fieldname, const GValue * value)
381 g_return_if_fail (structure != NULL);
382 g_return_if_fail (fieldname != NULL);
383 g_return_if_fail (G_IS_VALUE (value));
384 g_return_if_fail (IS_MUTABLE (structure));
386 gst_structure_id_set_value (structure, g_quark_from_string (fieldname),
392 * @structure: a #GstStructure
393 * @fieldname: the name of the field to set
394 * @...: variable arguments
396 * Parses the variable arguments and sets fields accordingly.
397 * Variable arguments should be in the form field name, field type
398 * (as a GType), value. The last variable argument should be NULL.
401 gst_structure_set (GstStructure * structure, const gchar * field, ...)
405 g_return_if_fail (structure != NULL);
407 va_start (varargs, field);
409 gst_structure_set_valist (structure, field, varargs);
415 * gst_structure_set_valist:
416 * @structure: a #GstStructure
417 * @fieldname: the name of the field to set
418 * @varargs: variable arguments
420 * va_list form of #gst_structure_set.
423 gst_structure_set_valist (GstStructure * structure,
424 const gchar * fieldname, va_list varargs)
429 g_return_if_fail (structure != NULL);
430 g_return_if_fail (IS_MUTABLE (structure));
433 GstStructureField field = { 0 };
435 field.name = g_quark_from_string (fieldname);
437 type = va_arg (varargs, GType);
438 g_value_init (&field.value, type);
439 G_VALUE_COLLECT (&field.value, varargs, 0, &err);
441 g_critical ("%s", err);
444 gst_structure_set_field (structure, &field);
446 fieldname = va_arg (varargs, gchar *);
450 /* If the structure currently contains a field with the same name, it is
451 * replaced with the provided field. Otherwise, the field is added to the
452 * structure. The field's value is not deeply copied.
455 gst_structure_set_field (GstStructure * structure, GstStructureField * field)
457 GstStructureField *f;
460 for (i = 0; i < structure->fields->len; i++) {
461 f = GST_STRUCTURE_FIELD (structure, i);
463 if (f->name == field->name) {
464 g_value_unset (&f->value);
465 memcpy (f, field, sizeof (GstStructureField));
470 g_array_append_val (structure->fields, *field);
473 /* If there is no field with the given ID, NULL is returned.
475 static GstStructureField *
476 gst_structure_id_get_field (const GstStructure * structure, GQuark field_id)
478 GstStructureField *field;
481 g_return_val_if_fail (structure != NULL, NULL);
483 for (i = 0; i < structure->fields->len; i++) {
484 field = GST_STRUCTURE_FIELD (structure, i);
486 if (field->name == field_id)
493 /* If there is no field with the given ID, NULL is returned.
495 static GstStructureField *
496 gst_structure_get_field (const GstStructure * structure,
497 const gchar * fieldname)
499 g_return_val_if_fail (structure != NULL, NULL);
500 g_return_val_if_fail (fieldname != NULL, NULL);
502 return gst_structure_id_get_field (structure,
503 g_quark_from_string (fieldname));
507 * gst_structure_get_value:
508 * @structure: a #GstStructure
509 * @fieldname: the name of the field to get
513 * Returns: the #GValue corresponding to the field with the given name.
516 gst_structure_get_value (const GstStructure * structure,
517 const gchar * fieldname)
519 GstStructureField *field;
521 g_return_val_if_fail (structure != NULL, NULL);
522 g_return_val_if_fail (fieldname != NULL, NULL);
524 field = gst_structure_get_field (structure, fieldname);
528 return &field->value;
532 * gst_structure_id_get_value:
533 * @structure: a #GstStructure
534 * @field: the #GQuark of the field to get
538 * Returns: the #GValue corresponding to the field with the given name
542 gst_structure_id_get_value (const GstStructure * structure, GQuark field)
544 GstStructureField *gsfield;
546 g_return_val_if_fail (structure != NULL, NULL);
548 gsfield = gst_structure_id_get_field (structure, field);
552 return &gsfield->value;
556 * gst_structure_remove_field:
557 * @structure: a #GstStructure
558 * @fieldname: the name of the field to remove
560 * Removes the field with the given name. If the field with the given
561 * name does not exist, the structure is unchanged.
564 gst_structure_remove_field (GstStructure * structure, const gchar * fieldname)
566 GstStructureField *field;
570 g_return_if_fail (structure != NULL);
571 g_return_if_fail (fieldname != NULL);
572 g_return_if_fail (IS_MUTABLE (structure));
574 id = g_quark_from_string (fieldname);
576 for (i = 0; i < structure->fields->len; i++) {
577 field = GST_STRUCTURE_FIELD (structure, i);
579 if (field->name == id) {
580 if (G_IS_VALUE (&field->value)) {
581 g_value_unset (&field->value);
583 structure->fields = g_array_remove_index (structure->fields, i);
590 * gst_structure_remove_fields:
591 * @structure: a #GstStructure
592 * @fieldname: the name of the field to remove
593 * @...: NULL-terminated list of more fieldnames to remove
595 * Removes the field with the given names. If a field does not exist, the
596 * argument is ignored.
599 gst_structure_remove_fields (GstStructure * structure,
600 const gchar * fieldname, ...)
604 g_return_if_fail (structure != NULL);
605 g_return_if_fail (fieldname != NULL);
606 /* mutability checked in remove_field */
608 va_start (varargs, fieldname);
610 gst_structure_remove_fields_valist (structure, fieldname, varargs);
616 * gst_structure_remove_fields_valist:
617 * @structure: a #GstStructure
618 * @fieldname: the name of the field to remove
619 * @varargs: NULL-terminated list of more fieldnames to remove
621 * Removes the field with the given names. If a field does not exist, the
622 * argument is ignored.
625 gst_structure_remove_fields_valist (GstStructure * structure,
626 const gchar * fieldname, va_list varargs)
628 gchar *field = (gchar *) fieldname;
630 g_return_if_fail (structure != NULL);
631 g_return_if_fail (fieldname != NULL);
632 /* mutability checked in remove_field */
635 gst_structure_remove_field (structure, field);
636 field = va_arg (varargs, char *);
641 * gst_structure_remove_all_fields:
642 * @structure: a #GstStructure
644 * Removes all fields in a GstStructure.
647 gst_structure_remove_all_fields (GstStructure * structure)
649 GstStructureField *field;
652 g_return_if_fail (structure != NULL);
653 g_return_if_fail (IS_MUTABLE (structure));
655 for (i = structure->fields->len - 1; i >= 0; i--) {
656 field = GST_STRUCTURE_FIELD (structure, i);
658 if (G_IS_VALUE (&field->value)) {
659 g_value_unset (&field->value);
661 structure->fields = g_array_remove_index (structure->fields, i);
666 * gst_structure_get_field_type:
667 * @structure: a #GstStructure
668 * @fieldname: the name of the field
670 * Finds the field with the given name, and returns the type of the
671 * value it contains. If the field is not found, G_TYPE_INVALID is
674 * Returns: the #GValue of the field
677 gst_structure_get_field_type (const GstStructure * structure,
678 const gchar * fieldname)
680 GstStructureField *field;
682 g_return_val_if_fail (structure != NULL, G_TYPE_INVALID);
683 g_return_val_if_fail (fieldname != NULL, G_TYPE_INVALID);
685 field = gst_structure_get_field (structure, fieldname);
687 return G_TYPE_INVALID;
689 return G_VALUE_TYPE (&field->value);
693 * gst_structure_n_fields:
694 * @structure: a #GstStructure
698 * Returns: the number of fields in the structure
701 gst_structure_n_fields (const GstStructure * structure)
703 g_return_val_if_fail (structure != NULL, 0);
705 return structure->fields->len;
709 * gst_structure_nth_field_name:
710 * @structure: a #GstStructure
712 * Returns: the name of the given field number, counting from 0 onwards.
715 gst_structure_nth_field_name (const GstStructure * structure, guint index)
717 GstStructureField *field;
719 field = GST_STRUCTURE_FIELD (structure, index);
720 return g_quark_to_string (field->name);
724 * gst_structure_foreach:
725 * @structure: a #GstStructure
726 * @func: a function to call for each field
727 * @user_data: private data
729 * Calls the provided function once for each field in the #GstStructure. The
730 * function must not modify the fields. Also see gst_structure_map_in_place().
732 * Returns: TRUE if the supplied function returns TRUE For each of the fields,
736 gst_structure_foreach (const GstStructure * structure,
737 GstStructureForeachFunc func, gpointer user_data)
740 GstStructureField *field;
743 g_return_val_if_fail (structure != NULL, FALSE);
745 for (i = 0; i < structure->fields->len; i++) {
746 field = GST_STRUCTURE_FIELD (structure, i);
748 ret = func (field->name, &field->value, user_data);
757 * gst_structure_map_in_place:
758 * @structure: a #GstStructure
759 * @func: a function to call for each field
760 * @user_data: private data
762 * Calls the provided function once for each field in the #GstStructure. In
763 * contrast to gst_structure_foreach(), the function may modify the fields. The
764 * structure must be mutable.
766 * Returns: TRUE if the supplied function returns TRUE For each of the fields,
770 gst_structure_map_in_place (GstStructure * structure,
771 GstStructureMapFunc func, gpointer user_data)
774 GstStructureField *field;
777 g_return_val_if_fail (structure != NULL, FALSE);
778 g_return_val_if_fail (IS_MUTABLE (structure), FALSE);
780 for (i = 0; i < structure->fields->len; i++) {
781 field = GST_STRUCTURE_FIELD (structure, i);
783 ret = func (field->name, &field->value, user_data);
792 * gst_structure_has_field:
793 * @structure: a #GstStructure
794 * @fieldname: the name of a field
798 * Returns: TRUE if the structure contains a field with the given name
801 gst_structure_has_field (const GstStructure * structure,
802 const gchar * fieldname)
804 GstStructureField *field;
806 g_return_val_if_fail (structure != NULL, 0);
807 g_return_val_if_fail (fieldname != NULL, 0);
809 field = gst_structure_get_field (structure, fieldname);
811 return (field != NULL);
815 * gst_structure_has_field_typed:
816 * @structure: a #GstStructure
817 * @fieldname: the name of a field
818 * @type: the type of a value
822 * Returns: TRUE if the structure contains a field with the given name and type
825 gst_structure_has_field_typed (const GstStructure * structure,
826 const gchar * fieldname, GType type)
828 GstStructureField *field;
830 g_return_val_if_fail (structure != NULL, 0);
831 g_return_val_if_fail (fieldname != NULL, 0);
833 field = gst_structure_get_field (structure, fieldname);
837 return (G_VALUE_TYPE (&field->value) == type);
841 /* utility functions */
844 * gst_structure_get_boolean:
845 * @structure: a #GstStructure
846 * @fieldname: the name of a field
847 * @value: a pointer to a #gboolean to set
849 * Sets the boolean pointed to by @value corresponding to the value of the
850 * given field. Caller is responsible for making sure the field exists
851 * and has the correct type.
853 * Returns: TRUE if the value could be set correctly
856 gst_structure_get_boolean (const GstStructure * structure,
857 const gchar * fieldname, gboolean * value)
859 GstStructureField *field;
861 g_return_val_if_fail (structure != NULL, FALSE);
862 g_return_val_if_fail (fieldname != NULL, FALSE);
864 field = gst_structure_get_field (structure, fieldname);
868 if (!G_VALUE_HOLDS_BOOLEAN (&field->value))
871 *value = g_value_get_boolean (&field->value);
877 * gst_structure_get_int:
878 * @structure: a #GstStructure
879 * @fieldname: the name of a field
880 * @value: a pointer to an int to set
882 * Sets the int pointed to by @value corresponding to the value of the
883 * given field. Caller is responsible for making sure the field exists
884 * and has the correct type.
886 * Returns: TRUE if the value could be set correctly
889 gst_structure_get_int (const GstStructure * structure,
890 const gchar * fieldname, gint * value)
892 GstStructureField *field;
894 g_return_val_if_fail (structure != NULL, FALSE);
895 g_return_val_if_fail (fieldname != NULL, FALSE);
896 g_return_val_if_fail (value != NULL, FALSE);
898 field = gst_structure_get_field (structure, fieldname);
902 if (!G_VALUE_HOLDS_INT (&field->value))
905 *value = g_value_get_int (&field->value);
911 * gst_structure_get_fourcc:
912 * @structure: a #GstStructure
913 * @fieldname: the name of a field
914 * @value: a pointer to a #GstFourcc to set
916 * Sets the #GstFourcc pointed to by @value corresponding to the value of the
917 * given field. Caller is responsible for making sure the field exists
918 * and has the correct type.
920 * Returns: TRUE if the value could be set correctly
923 gst_structure_get_fourcc (const GstStructure * structure,
924 const gchar * fieldname, guint32 * value)
926 GstStructureField *field;
928 g_return_val_if_fail (structure != NULL, FALSE);
929 g_return_val_if_fail (fieldname != NULL, FALSE);
930 g_return_val_if_fail (value != NULL, FALSE);
932 field = gst_structure_get_field (structure, fieldname);
936 if (!GST_VALUE_HOLDS_FOURCC (&field->value))
939 *value = gst_value_get_fourcc (&field->value);
945 * gst_structure_get_double:
946 * @structure: a #GstStructure
947 * @fieldname: the name of a field
948 * @value: a pointer to a #GstFourcc to set
950 * Sets the double pointed to by @value corresponding to the value of the
951 * given field. Caller is responsible for making sure the field exists
952 * and has the correct type.
954 * Returns: TRUE if the value could be set correctly
957 gst_structure_get_double (const GstStructure * structure,
958 const gchar * fieldname, gdouble * value)
960 GstStructureField *field;
962 g_return_val_if_fail (structure != NULL, FALSE);
963 g_return_val_if_fail (fieldname != NULL, FALSE);
964 g_return_val_if_fail (value != NULL, FALSE);
966 field = gst_structure_get_field (structure, fieldname);
970 if (!G_VALUE_HOLDS_DOUBLE (&field->value))
973 *value = g_value_get_double (&field->value);
979 * gst_structure_get_string:
980 * @structure: a #GstStructure
981 * @fieldname: the name of a field
983 * Finds the field corresponding to @fieldname, and returns the string
984 * contained in the field's value. Caller is responsible for making
985 * sure the field exists and has the correct type.
987 * The string should not be modified, and remains valid until the next
988 * call to a gst_structure_*() function with the given structure.
990 * Returns: a pointer to the string
993 gst_structure_get_string (const GstStructure * structure,
994 const gchar * fieldname)
996 GstStructureField *field;
998 g_return_val_if_fail (structure != NULL, NULL);
999 g_return_val_if_fail (fieldname != NULL, NULL);
1001 field = gst_structure_get_field (structure, fieldname);
1005 if (!G_VALUE_HOLDS_STRING (&field->value))
1008 return g_value_get_string (&field->value);
1011 typedef struct _GstStructureAbbreviation
1016 GstStructureAbbreviation;
1018 static GstStructureAbbreviation *
1019 gst_structure_get_abbrs (gint * n_abbrs)
1021 static GstStructureAbbreviation *abbrs = NULL;
1022 static gint num = 0;
1024 if (abbrs == NULL) {
1025 /* dynamically generate the array */
1026 GstStructureAbbreviation dyn_abbrs[] = {
1031 {"float", G_TYPE_FLOAT}
1035 {"double", G_TYPE_DOUBLE}
1037 {"d", G_TYPE_DOUBLE}
1039 {"buffer", GST_TYPE_BUFFER}
1041 {"fourcc", GST_TYPE_FOURCC}
1043 {"4", GST_TYPE_FOURCC}
1045 {"fraction", GST_TYPE_FRACTION}
1047 {"boolean", G_TYPE_BOOLEAN}
1049 {"bool", G_TYPE_BOOLEAN}
1051 {"b", G_TYPE_BOOLEAN}
1053 {"string", G_TYPE_STRING}
1055 {"str", G_TYPE_STRING}
1057 {"s", G_TYPE_STRING}
1059 num = G_N_ELEMENTS (dyn_abbrs);
1060 /* permanently allocate and copy the array now */
1061 abbrs = g_new0 (GstStructureAbbreviation, num);
1062 memcpy (abbrs, dyn_abbrs, sizeof (GstStructureAbbreviation) * num);
1070 gst_structure_from_abbr (const char *type_name)
1073 GstStructureAbbreviation *abbrs;
1076 g_return_val_if_fail (type_name != NULL, G_TYPE_INVALID);
1078 abbrs = gst_structure_get_abbrs (&n_abbrs);
1080 for (i = 0; i < n_abbrs; i++) {
1081 if (strcmp (type_name, abbrs[i].type_name) == 0) {
1082 return abbrs[i].type;
1086 /* this is the fallback */
1087 return g_type_from_name (type_name);
1091 gst_structure_to_abbr (GType type)
1094 GstStructureAbbreviation *abbrs;
1097 g_return_val_if_fail (type != G_TYPE_INVALID, NULL);
1099 abbrs = gst_structure_get_abbrs (&n_abbrs);
1101 for (i = 0; i < n_abbrs; i++) {
1102 if (type == abbrs[i].type) {
1103 return abbrs[i].type_name;
1107 return g_type_name (type);
1111 gst_structure_value_get_generic_type (GValue * val)
1113 if (G_VALUE_TYPE (val) == GST_TYPE_LIST
1114 || G_VALUE_TYPE (val) == GST_TYPE_ARRAY) {
1115 GArray *array = g_value_peek_pointer (val);
1117 if (array->len > 0) {
1118 GValue *value = &g_array_index (array, GValue, 0);
1120 return gst_structure_value_get_generic_type (value);
1124 } else if (G_VALUE_TYPE (val) == GST_TYPE_INT_RANGE) {
1126 } else if (G_VALUE_TYPE (val) == GST_TYPE_DOUBLE_RANGE) {
1127 return G_TYPE_DOUBLE;
1129 return G_VALUE_TYPE (val);
1132 #define GST_ASCII_IS_STRING(c) (g_ascii_isalnum((c)) || ((c) == '_') || \
1133 ((c) == '-') || ((c) == '+') || ((c) == '/') || ((c) == ':') || \
1137 * gst_structure_to_string:
1138 * @structure: a #GstStructure
1140 * Converts @structure to a human-readable representation.
1142 * Returns: a pointer to string allocated by g_malloc()
1145 gst_structure_to_string (const GstStructure * structure)
1147 GstStructureField *field;
1151 /* NOTE: This function is potentially called by the debug system,
1152 * so any calls to gst_log() (and GST_DEBUG(), GST_LOG(), etc.)
1153 * should be careful to avoid recursion. This includes any functions
1154 * called by gst_structure_to_string. In particular, calls should
1155 * not use the GST_PTR_FORMAT extension. */
1157 g_return_val_if_fail (structure != NULL, NULL);
1159 s = g_string_new ("");
1160 /* FIXME this string may need to be escaped */
1161 g_string_append_printf (s, "%s", g_quark_to_string (structure->name));
1162 for (i = 0; i < structure->fields->len; i++) {
1166 field = GST_STRUCTURE_FIELD (structure, i);
1168 t = gst_value_serialize (&field->value);
1169 type = gst_structure_value_get_generic_type (&field->value);
1171 g_string_append_printf (s, ", %s=(%s)%s", g_quark_to_string (field->name),
1172 gst_structure_to_abbr (type), t);
1175 return g_string_free (s, FALSE);
1179 * r will still point to the string. if end == next, the string will not be
1180 * null-terminated. In all other cases it will be.
1181 * end = pointer to char behind end of string, next = pointer to start of
1183 * THIS FUNCTION MODIFIES THE STRING AND DETECTS INSIDE A NONTERMINATED STRING
1186 gst_structure_parse_string (gchar * s, gchar ** end, gchar ** next)
1196 ret = gst_structure_parse_simple_string (s, end);
1225 gst_structure_parse_range (gchar * s, gchar ** after, GValue * value,
1228 GValue value1 = { 0 };
1229 GValue value2 = { 0 };
1238 ret = gst_structure_parse_value (s, &s, &value1, type);
1242 while (g_ascii_isspace (*s))
1249 while (g_ascii_isspace (*s))
1252 ret = gst_structure_parse_value (s, &s, &value2, type);
1256 while (g_ascii_isspace (*s))
1263 if (G_VALUE_TYPE (&value1) != G_VALUE_TYPE (&value2))
1266 if (G_VALUE_TYPE (&value1) == G_TYPE_DOUBLE) {
1267 range_type = GST_TYPE_DOUBLE_RANGE;
1268 } else if (G_VALUE_TYPE (&value1) == G_TYPE_INT) {
1269 range_type = GST_TYPE_INT_RANGE;
1274 g_value_init (value, range_type);
1275 if (range_type == GST_TYPE_DOUBLE_RANGE) {
1276 gst_value_set_double_range (value, g_value_get_double (&value1),
1277 g_value_get_double (&value2));
1279 gst_value_set_int_range (value, g_value_get_int (&value1),
1280 g_value_get_int (&value2));
1288 gst_structure_parse_any_list (gchar * s, gchar ** after, GValue * value,
1289 GType type, GType list_type, char begin, char end)
1291 GValue list_value = { 0 };
1295 g_value_init (value, list_type);
1296 array = g_value_peek_pointer (value);
1302 while (g_ascii_isspace (*s))
1310 ret = gst_structure_parse_value (s, &s, &list_value, type);
1314 g_array_append_val (array, list_value);
1316 while (g_ascii_isspace (*s))
1324 while (g_ascii_isspace (*s))
1327 memset (&list_value, 0, sizeof (list_value));
1328 ret = gst_structure_parse_value (s, &s, &list_value, type);
1332 g_array_append_val (array, list_value);
1333 while (g_ascii_isspace (*s))
1344 gst_structure_parse_list (gchar * s, gchar ** after, GValue * value, GType type)
1346 return gst_structure_parse_any_list (s, after, value, type, GST_TYPE_LIST,
1351 gst_structure_parse_array (gchar * s, gchar ** after, GValue * value,
1354 return gst_structure_parse_any_list (s, after, value, type,
1355 GST_TYPE_ARRAY, '<', '>');
1359 gst_structure_parse_simple_string (gchar * str, gchar ** end)
1363 while (GST_ASCII_IS_STRING (*s)) {
1373 gst_structure_parse_field (gchar * str,
1374 gchar ** after, GstStructureField * field)
1383 while (g_ascii_isspace (*s))
1386 if (!gst_structure_parse_simple_string (s, &name_end))
1390 while (g_ascii_isspace (*s))
1399 field->name = g_quark_from_string (name);
1402 if (!gst_structure_parse_value (s, &s, &field->value, G_TYPE_INVALID))
1410 gst_structure_parse_value (gchar * str,
1411 gchar ** after, GValue * value, GType default_type)
1420 GType type = default_type;
1424 while (g_ascii_isspace (*s))
1429 type = G_TYPE_INVALID;
1432 while (g_ascii_isspace (*s))
1435 if (!gst_structure_parse_simple_string (s, &type_end))
1438 while (g_ascii_isspace (*s))
1443 while (g_ascii_isspace (*s))
1448 type = gst_structure_from_abbr (type_name);
1451 if (type == G_TYPE_INVALID)
1455 while (g_ascii_isspace (*s))
1458 ret = gst_structure_parse_range (s, &s, value, type);
1459 } else if (*s == '{') {
1460 ret = gst_structure_parse_list (s, &s, value, type);
1461 } else if (*s == '<') {
1462 ret = gst_structure_parse_array (s, &s, value, type);
1465 if (!gst_structure_parse_string (s, &value_end, &s))
1470 if (type == G_TYPE_INVALID) {
1471 GType try_types[] = { G_TYPE_INT, G_TYPE_DOUBLE, G_TYPE_STRING };
1474 for (i = 0; i < 3; i++) {
1475 g_value_init (value, try_types[i]);
1476 ret = gst_value_deserialize (value, value_s);
1479 g_value_unset (value);
1482 g_value_init (value, type);
1484 ret = gst_value_deserialize (value, value_s);
1495 * gst_structure_from_string:
1496 * @string: a string representation of a #GstStructure.
1497 * @end: pointer to store the end of the string in.
1499 * Creates a #GstStructure from a string representation.
1500 * If end is not NULL, a pointer to the place inside the given string
1501 * where parsing ended will be returned.
1503 * Returns: a new #GstStructure
1506 gst_structure_from_string (const gchar * string, gchar ** end)
1513 GstStructure *structure = NULL;
1514 GstStructureField field = { 0 };
1516 g_return_val_if_fail (string != NULL, NULL);
1518 copy = g_strdup (string);
1522 if (!gst_structure_parse_string (r, &w, &r))
1525 while (g_ascii_isspace (*r))
1527 if (*r != 0 && *r != ';' && *r != ',')
1532 structure = gst_structure_empty_new (name);
1535 while (*r && (*r != ';')) {
1539 while (*r && g_ascii_isspace (*r))
1542 memset (&field, 0, sizeof (field));
1543 if (!gst_structure_parse_field (r, &r, &field))
1545 gst_structure_set_field (structure, &field);
1546 while (*r && g_ascii_isspace (*r))
1551 *end = (char *) string + (r - copy);
1558 gst_structure_free (structure);
1564 gst_structure_transform_to_string (const GValue * src_value,
1565 GValue * dest_value)
1567 g_return_if_fail (src_value != NULL);
1568 g_return_if_fail (dest_value != NULL);
1570 dest_value->data[0].v_pointer =
1571 gst_structure_to_string (src_value->data[0].v_pointer);
1574 static GstStructure *
1575 gst_structure_copy_conditional (const GstStructure * structure)
1578 return gst_structure_copy (structure);
1582 /* fixate utility functions */
1585 * gst_caps_structure_fixate_field_nearest_int:
1586 * @structure: a #GstStructure
1587 * @field_name: a field in @structure
1588 * @target: the target value of the fixation
1590 * Fixates a #GstStructure by changing the given field to the nearest
1591 * integer to @target that is a subset of the existing field.
1593 * Returns: TRUE if the structure could be fixated
1596 gst_caps_structure_fixate_field_nearest_int (GstStructure * structure,
1597 const char *field_name, int target)
1599 const GValue *value;
1601 g_return_val_if_fail (gst_structure_has_field (structure, field_name), FALSE);
1602 g_return_val_if_fail (IS_MUTABLE (structure), FALSE);
1604 value = gst_structure_get_value (structure, field_name);
1606 if (G_VALUE_TYPE (value) == G_TYPE_INT) {
1609 } else if (G_VALUE_TYPE (value) == GST_TYPE_INT_RANGE) {
1612 x = gst_value_get_int_range_min (value);
1615 x = gst_value_get_int_range_max (value);
1618 gst_structure_set (structure, field_name, G_TYPE_INT, target, NULL);
1620 } else if (G_VALUE_TYPE (value) == GST_TYPE_LIST) {
1621 const GValue *list_value;
1624 int best_index = -1;
1626 n = gst_value_list_get_size (value);
1627 for (i = 0; i < n; i++) {
1628 list_value = gst_value_list_get_value (value, i);
1629 if (G_VALUE_TYPE (list_value) == G_TYPE_INT) {
1630 int x = g_value_get_int (list_value);
1632 if (best_index == -1 || (ABS (target - x) < ABS (target - best))) {
1638 if (best_index != -1) {
1639 gst_structure_set (structure, field_name, G_TYPE_INT, best, NULL);
1649 * gst_caps_structure_fixate_field_nearest_double:
1650 * @structure: a #GstStructure
1651 * @field_name: a field in @structure
1652 * @target: the target value of the fixation
1654 * Fixates a #GstStructure by changing the given field to the nearest
1655 * double to @target that is a subset of the existing field.
1657 * Returns: TRUE if the structure could be fixated
1660 gst_caps_structure_fixate_field_nearest_double (GstStructure * structure,
1661 const char *field_name, double target)
1663 const GValue *value;
1665 g_return_val_if_fail (gst_structure_has_field (structure, field_name), FALSE);
1666 g_return_val_if_fail (IS_MUTABLE (structure), FALSE);
1668 value = gst_structure_get_value (structure, field_name);
1670 if (G_VALUE_TYPE (value) == G_TYPE_DOUBLE) {
1673 } else if (G_VALUE_TYPE (value) == GST_TYPE_DOUBLE_RANGE) {
1676 x = gst_value_get_double_range_min (value);
1679 x = gst_value_get_double_range_max (value);
1682 gst_structure_set (structure, field_name, G_TYPE_DOUBLE, target, NULL);
1684 } else if (G_VALUE_TYPE (value) == GST_TYPE_LIST) {
1685 const GValue *list_value;
1688 int best_index = -1;
1690 n = gst_value_list_get_size (value);
1691 for (i = 0; i < n; i++) {
1692 list_value = gst_value_list_get_value (value, i);
1693 if (G_VALUE_TYPE (list_value) == G_TYPE_DOUBLE) {
1694 double x = g_value_get_double (list_value);
1696 if (best_index == -1 || (ABS (target - x) < ABS (target - best))) {
1702 if (best_index != -1) {
1703 gst_structure_set (structure, field_name, G_TYPE_DOUBLE, best, NULL);