gstvalue: Fix comparision of double range
[platform/upstream/gstreamer.git] / tests / check / gst / gstvalue.c
1 /* GStreamer
2  * Copyright (C) <2004> David Schleef <david at schleef dot org>
3  * Copyright (C) <2005> Thomas Vander Stichele <thomas at apestaart dot org>
4  *
5  * gstvalue.c: Unit tests for GstValue
6  *
7  * This library is free software; you can redistribute it and/or
8  * modify it under the terms of the GNU Library General Public
9  * License as published by the Free Software Foundation; either
10  * version 2 of the License, or (at your option) any later version.
11  *
12  * This library is distributed in the hope that it will be useful,
13  * but WITHOUT ANY WARRANTY; without even the implied warranty of
14  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
15  * Library General Public License for more details.
16  *
17  * You should have received a copy of the GNU Library General Public
18  * License along with this library; if not, write to the
19  * Free Software Foundation, Inc., 51 Franklin St, Fifth Floor,
20  * Boston, MA 02110-1301, USA.
21  */
22
23
24 #include <gst/check/gstcheck.h>
25
26
27 GST_START_TEST (test_deserialize_buffer)
28 {
29   GValue value = { 0 };
30   GstBuffer *buf;
31
32   g_value_init (&value, GST_TYPE_BUFFER);
33   fail_unless (gst_value_deserialize (&value, "1234567890abcdef"));
34   /* does not increase the refcount */
35   buf = GST_BUFFER (g_value_get_boxed (&value));
36   ASSERT_MINI_OBJECT_REFCOUNT (buf, "buffer", 1);
37
38   /* does not increase the refcount */
39   buf = gst_value_get_buffer (&value);
40   ASSERT_MINI_OBJECT_REFCOUNT (buf, "buffer", 1);
41
42   /* cleanup */
43   g_value_unset (&value);
44 }
45
46 GST_END_TEST;
47
48 /* create and serialize a buffer */
49 GST_START_TEST (test_serialize_buffer)
50 {
51   GValue value = { 0 };
52   GstBuffer *buf;
53   gchar *serialized;
54   static const char *buf_data = "1234567890abcdef";
55   gint len;
56
57   len = strlen (buf_data);
58   buf = gst_buffer_new_and_alloc (len);
59
60   gst_buffer_fill (buf, 0, buf_data, len);
61
62   ASSERT_MINI_OBJECT_REFCOUNT (buf, "buffer", 1);
63
64   /* and assign buffer to mini object */
65   g_value_init (&value, GST_TYPE_BUFFER);
66   gst_value_take_buffer (&value, buf);
67   ASSERT_MINI_OBJECT_REFCOUNT (buf, "buffer", 1);
68
69   /* now serialize it */
70   serialized = gst_value_serialize (&value);
71   GST_DEBUG ("serialized buffer to %s", serialized);
72   fail_unless (serialized != NULL);
73
74   /* refcount should not change */
75   ASSERT_MINI_OBJECT_REFCOUNT (buf, "buffer", 1);
76
77   /* cleanup */
78   g_free (serialized);
79   g_value_unset (&value);
80
81   /* take NULL buffer */
82   g_value_init (&value, GST_TYPE_BUFFER);
83   GST_DEBUG ("setting NULL buffer");
84   gst_value_take_buffer (&value, NULL);
85
86   /* now serialize it */
87   GST_DEBUG ("serializing NULL buffer");
88   serialized = gst_value_serialize (&value);
89   /* should return NULL */
90   fail_unless (serialized == NULL);
91
92   g_free (serialized);
93   g_value_unset (&value);
94 }
95
96 GST_END_TEST;
97
98 GST_START_TEST (test_deserialize_gint64)
99 {
100   GValue value = { 0 };
101   const char *strings[] = {
102     "12345678901",
103     "-12345678901",
104     "1152921504606846976",
105     "-1152921504606846976",
106   };
107   gint64 results[] = {
108     12345678901LL,
109     -12345678901LL,
110     1152921504606846976LL,
111     -1152921504606846976LL,
112   };
113   int i;
114
115   g_value_init (&value, G_TYPE_INT64);
116
117   for (i = 0; i < G_N_ELEMENTS (strings); ++i) {
118     fail_unless (gst_value_deserialize (&value, strings[i]),
119         "could not deserialize %s (%d)", strings[i], i);
120     fail_unless (g_value_get_int64 (&value) == results[i],
121         "resulting value is %" G_GINT64_FORMAT ", not %" G_GINT64_FORMAT
122         ", for string %s (%d)", g_value_get_int64 (&value),
123         results[i], strings[i], i);
124   }
125 }
126
127 GST_END_TEST;
128
129 GST_START_TEST (test_deserialize_guint64)
130 {
131   GValue value = { 0 };
132   const char *strings[] = {
133     "0xffffffffffffffff",
134     "9223372036854775810",
135     "-9223372036854775810",
136     "-1",
137     "1",
138     "-0",
139   };
140   guint64 results[] = {
141     0xffffffffffffffffULL,
142     9223372036854775810ULL,
143     9223372036854775806ULL,
144     (guint64) - 1,
145     1,
146     0,
147   };
148   int i;
149
150   g_value_init (&value, G_TYPE_UINT64);
151
152   for (i = 0; i < G_N_ELEMENTS (strings); ++i) {
153     fail_unless (gst_value_deserialize (&value, strings[i]),
154         "could not deserialize %s (%d)", strings[i], i);
155     fail_unless (g_value_get_uint64 (&value) == results[i],
156         "resulting value is %" G_GUINT64_FORMAT ", not %" G_GUINT64_FORMAT
157         ", for string %s (%d)", g_value_get_uint64 (&value),
158         results[i], strings[i], i);
159   }
160 }
161
162 GST_END_TEST;
163
164 GST_START_TEST (test_deserialize_guchar)
165 {
166   GValue value = { 0 };
167   const char *strings[] = {
168     "0xff",
169     "255",
170     "-1",
171     "1",
172     "-0",
173   };
174   guchar results[] = {
175     0xff,
176     255,
177     (guchar) - 1,
178     1,
179     0,
180   };
181   int i;
182
183   g_value_init (&value, G_TYPE_UCHAR);
184
185   for (i = 0; i < G_N_ELEMENTS (strings); ++i) {
186     fail_unless (gst_value_deserialize (&value, strings[i]),
187         "could not deserialize %s (%d)", strings[i], i);
188     fail_unless (g_value_get_uchar (&value) == results[i],
189         "resulting value is %u not %u, for string %s (%d)",
190         g_value_get_uchar (&value), results[i], strings[i], i);
191   }
192
193   /* test serialisation as well while we're at it */
194   {
195     gchar *str;
196     GValue value = { 0 };
197     g_value_init (&value, G_TYPE_UCHAR);
198
199     g_value_set_uchar (&value, 255);
200     str = gst_value_serialize (&value);
201
202     fail_unless_equals_string (str, "255");
203     g_free (str);
204   }
205 }
206
207 GST_END_TEST;
208
209 GST_START_TEST (test_deserialize_gstfraction)
210 {
211   GValue value = { 0 };
212   const char *strings[] = {
213     "4/5",
214     "-8/9"
215   };
216   gint64 result_numers[] = {
217     4,
218     -8
219   };
220   gint64 result_denoms[] = {
221     5,
222     9
223   };
224
225   int i;
226
227   g_value_init (&value, GST_TYPE_FRACTION);
228   for (i = 0; i < G_N_ELEMENTS (strings); ++i) {
229     fail_unless (gst_value_deserialize (&value, strings[i]),
230         "could not deserialize %s (%d)", strings[i], i);
231     fail_unless (gst_value_get_fraction_numerator (&value) == result_numers[i],
232         "resulting numerator value is %d, not %d"
233         ", for string %s (%d)", gst_value_get_fraction_numerator (&value),
234         result_numers[i], strings[i], i);
235     fail_unless (gst_value_get_fraction_denominator (&value) ==
236         result_denoms[i], "resulting denominator value is %d, not %d"
237         ", for string %s (%d)", gst_value_get_fraction_denominator (&value),
238         result_denoms[i], strings[i], i);
239   }
240 }
241
242 GST_END_TEST;
243
244 GST_START_TEST (test_deserialize_gint)
245 {
246   GValue value = { 0 };
247   const char *strings[] = {
248     "123456",
249     "-123456",
250     "0xFFFF",
251     "0x0000FFFF",
252     /* a positive long long, serializing to highest possible positive sint */
253     "0x7FFFFFFF",
254     /* a positive long long, serializing to lowest possible negative sint */
255     "0x80000000",
256     /* a negative long long, serializing to lowest possible negative sint */
257     "0xFFFFFFFF80000000",
258     "0xFF000000",
259     /* a positive long long serializing to -1 */
260     "0xFFFFFFFF",
261     "0xFFFFFFFF",
262     /* a negative long long serializing to -1 */
263     "0xFFFFFFFFFFFFFFFF",
264     "0xFFFFFFFFFFFFFFFF",
265     "0xEFFFFFFF",
266   };
267   /* some casts need to be explicit because of unsigned -> signed */
268   gint results[] = {
269     123456,
270     -123456,
271     0xFFFF,
272     0xFFFF,
273     0x7FFFFFFF,
274     (gint) 0x80000000,
275     (gint) 0x80000000,
276     (gint) 0xFF000000,
277     -1,
278     (gint) 0xFFFFFFFF,
279     -1,
280     (gint) 0xFFFFFFFFFFFFFFFFLL,
281     (gint) 0xEFFFFFFF,
282   };
283   int i;
284
285   g_value_init (&value, G_TYPE_INT);
286
287   for (i = 0; i < G_N_ELEMENTS (strings); ++i) {
288     fail_unless (gst_value_deserialize (&value, strings[i]),
289         "could not deserialize %s (%d)", strings[i], i);
290     fail_unless (g_value_get_int (&value) == results[i],
291         "resulting value is %d, not %d, for string %s (%d)",
292         g_value_get_int (&value), results[i], strings[i], i);
293   }
294 }
295
296 GST_END_TEST;
297
298 GST_START_TEST (test_deserialize_gint_failures)
299 {
300   GValue value = { 0 };
301   const char *strings[] = {
302     "-",                        /* not a complete number */
303     "- TEST",                   /* not a complete number */
304     "0x0000000100000000",       /* lowest long long that cannot fit in 32 bits */
305     "0xF000000000000000",
306     "0xFFFFFFF000000000",
307     "0xFFFFFFFF00000000",
308     "0x10000000000000000",      /* first number too long to fit into a long long */
309     /* invent a new processor first before trying to make this one pass */
310     "0x10000000000000000000000000000000000000000000",
311   };
312   int i;
313
314   g_value_init (&value, G_TYPE_INT);
315
316   for (i = 0; i < G_N_ELEMENTS (strings); ++i) {
317     fail_if (gst_value_deserialize (&value, strings[i]),
318         "deserialized %s (%d), while it should have failed", strings[i], i);
319   }
320 }
321
322 GST_END_TEST;
323
324 GST_START_TEST (test_deserialize_guint)
325 {
326   GValue value = { 0 };
327   const char *strings[] = {
328     "123456",
329     "-123456",
330     "0xFFFF",
331     "0x0000FFFF",
332     /* a positive long long, serializing to highest possible positive sint */
333     "0x7FFFFFFF",
334     /* a positive long long, serializing to lowest possible negative sint */
335     "0x80000000",
336     "2147483648",
337     /* a negative long long, serializing to lowest possible negative sint */
338     "0xFFFFFFFF80000000",
339     /* a value typically used for rgb masks */
340     "0xFF000000",
341     /* a positive long long serializing to highest possible positive uint */
342     "0xFFFFFFFF",
343     "0xFFFFFFFF",
344     /* a negative long long serializing to highest possible positive uint */
345     "0xFFFFFFFFFFFFFFFF",
346     "0xEFFFFFFF",
347   };
348   guint results[] = {
349     123456,
350     (guint) - 123456,
351     0xFFFF,
352     0xFFFF,
353     0x7FFFFFFF,
354     0x80000000,
355     (guint) 2147483648LL,
356     0x80000000,
357     0xFF000000,
358     0xFFFFFFFF,
359     G_MAXUINT,
360     (guint) 0xFFFFFFFFFFFFFFFFLL,
361     0xEFFFFFFF,
362   };
363   int i;
364
365   g_value_init (&value, G_TYPE_UINT);
366
367   for (i = 0; i < G_N_ELEMENTS (strings); ++i) {
368     fail_unless (gst_value_deserialize (&value, strings[i]),
369         "could not deserialize %s (%d)", strings[i], i);
370     fail_unless (g_value_get_uint (&value) == results[i],
371         "resulting value is %d, not %d, for string %s (%d)",
372         g_value_get_uint (&value), results[i], strings[i], i);
373   }
374 }
375
376 GST_END_TEST;
377
378 GST_START_TEST (test_deserialize_guint_failures)
379 {
380   GValue value = { 0 };
381   const char *strings[] = {
382     "-",                        /* not a complete number */
383     "- TEST",                   /* not a complete number */
384 #if 0
385 /* FIXME: these values should not be deserializable, since they overflow
386  * the target format */
387     "0x0000000100000000",       /* lowest long long that cannot fit in 32 bits */
388     "0xF000000000000000",
389     "0xFFFFFFF000000000",
390     "0xFFFFFFFF00000000",
391     "0x10000000000000000",      /* first number too long to fit into a long long */
392     /* invent a new processor first before trying to make this one pass */
393     "0x10000000000000000000000000000000000000000000",
394 #endif
395   };
396   int i;
397
398   g_value_init (&value, G_TYPE_UINT);
399
400   for (i = 0; i < G_N_ELEMENTS (strings); ++i) {
401     fail_if (gst_value_deserialize (&value, strings[i]),
402         "deserialized %s (%d), while it should have failed", strings[i], i);
403   }
404 }
405
406 GST_END_TEST;
407
408 GST_START_TEST (test_serialize_flags)
409 {
410   GValue value = { 0 };
411   gchar *string;
412   GstSeekFlags flags[] = {
413     0,
414     GST_SEEK_FLAG_NONE,
415     GST_SEEK_FLAG_FLUSH,
416     GST_SEEK_FLAG_FLUSH | GST_SEEK_FLAG_ACCURATE,
417   };
418   const char *results[] = {
419     "GST_SEEK_FLAG_NONE",
420     "GST_SEEK_FLAG_NONE",
421     "GST_SEEK_FLAG_FLUSH",
422     "GST_SEEK_FLAG_FLUSH+GST_SEEK_FLAG_ACCURATE",
423   };
424   int i;
425
426   g_value_init (&value, GST_TYPE_SEEK_FLAGS);
427
428   for (i = 0; i < G_N_ELEMENTS (flags); ++i) {
429     g_value_set_flags (&value, flags[i]);
430     string = gst_value_serialize (&value);
431     fail_if (string == NULL, "could not serialize flags %d", i);
432     fail_unless (strcmp (string, results[i]) == 0,
433         "resulting value is %s, not %s, for flags #%d", string, results[i], i);
434     g_free (string);
435   }
436 }
437
438 GST_END_TEST;
439
440
441 GST_START_TEST (test_deserialize_flags)
442 {
443   GValue value = { 0 };
444   const char *strings[] = {
445     "",
446     "0",
447     "GST_SEEK_FLAG_NONE",
448     "GST_SEEK_FLAG_FLUSH",
449     "GST_SEEK_FLAG_FLUSH+GST_SEEK_FLAG_ACCURATE",
450   };
451   GstSeekFlags results[] = {
452     GST_SEEK_FLAG_NONE,
453     GST_SEEK_FLAG_NONE,
454     GST_SEEK_FLAG_NONE,
455     GST_SEEK_FLAG_FLUSH,
456     GST_SEEK_FLAG_FLUSH | GST_SEEK_FLAG_ACCURATE,
457   };
458   int i;
459
460   g_value_init (&value, GST_TYPE_SEEK_FLAGS);
461
462   for (i = 0; i < G_N_ELEMENTS (strings); ++i) {
463     fail_unless (gst_value_deserialize (&value, strings[i]),
464         "could not deserialize %s (%d)", strings[i], i);
465     fail_unless (g_value_get_flags (&value) == results[i],
466         "resulting value is %d, not %d, for string %s (%d)",
467         g_value_get_flags (&value), results[i], strings[i], i);
468   }
469 }
470
471 GST_END_TEST;
472
473 GST_START_TEST (test_deserialize_bitmask)
474 {
475   GValue value = { 0 };
476   const char *strings[] = {
477     "0xffffffffffffffff",
478     "0x1234567890ABCDEF",
479   };
480   guint64 results[] = {
481     0xffffffffffffffffULL,
482     0x1234567890ABCDEFULL,
483   };
484   int i;
485
486   g_value_init (&value, GST_TYPE_BITMASK);
487
488   for (i = 0; i < G_N_ELEMENTS (strings); ++i) {
489     fail_unless (gst_value_deserialize (&value, strings[i]),
490         "could not deserialize %s (%d)", strings[i], i);
491     fail_unless (gst_value_get_bitmask (&value) == results[i],
492         "resulting value is 0x%016" G_GINT64_MODIFIER "x, not 0x%016"
493         G_GINT64_MODIFIER "x, for string %s (%d)",
494         gst_value_get_bitmask (&value), results[i], strings[i], i);
495   }
496 }
497
498 GST_END_TEST;
499
500 GST_START_TEST (test_string)
501 {
502   const gchar *try[] = {
503     "Dude",
504     "Hi, I'm a string",
505     "tüüüt!",
506     "\"\""                      /* Empty string */
507   };
508   gchar *tmp;
509   GValue v = { 0, };
510   guint i;
511
512   g_value_init (&v, G_TYPE_STRING);
513   for (i = 0; i < G_N_ELEMENTS (try); i++) {
514     g_value_set_string (&v, try[i]);
515     tmp = gst_value_serialize (&v);
516     fail_if (tmp == NULL, "couldn't serialize: %s\n", try[i]);
517     fail_unless (gst_value_deserialize (&v, tmp),
518         "couldn't deserialize: %s\n", tmp);
519     g_free (tmp);
520
521     fail_unless (g_str_equal (g_value_get_string (&v), try[i]),
522         "\nserialized  : %s\ndeserialized: %s", try[i],
523         g_value_get_string (&v));
524   }
525   /* NULL strings should not be serializable */
526   g_value_set_string (&v, NULL);
527   fail_unless (gst_value_serialize (&v) == NULL);
528   g_value_unset (&v);
529 }
530
531 GST_END_TEST;
532
533 GST_START_TEST (test_deserialize_string)
534 {
535   struct
536   {
537     const gchar *from;
538     const gchar *to;
539   } tests[] = {
540     {
541     "", ""},                    /* empty strings */
542     {
543     "\"\"", ""},                /* quoted empty string -> empty string */
544         /* Expected FAILURES: */
545     {
546     "\"", NULL},                /* missing second quote */
547     {
548     "\"Hello\\ World", NULL},   /* missing second quote */
549     {
550     "\"\\", NULL},              /* quote at end, missing second quote */
551     {
552     "\"\\0", NULL},             /* missing second quote */
553     {
554     "\"\\0\"", NULL},           /* unfinished escaped character */
555     {
556     "\" \"", NULL},             /* spaces must be escaped */
557 #if 0
558         /* FIXME 0.9: this test should fail, but it doesn't */
559     {
560     "tüüt", NULL}             /* string with special chars must be escaped */
561 #endif
562   };
563   guint i;
564   GValue v = { 0, };
565
566   g_value_init (&v, G_TYPE_STRING);
567   for (i = 0; i < G_N_ELEMENTS (tests); i++) {
568     if (gst_value_deserialize (&v, tests[i].from)) {
569       fail_if (tests[i].to == NULL,
570           "I got %s instead of a failure", g_value_get_string (&v));
571       fail_unless (g_str_equal (g_value_get_string (&v), tests[i].to),
572           "\nwanted: %s\ngot    : %s", tests[i].to, g_value_get_string (&v));
573     } else {
574       fail_if (tests[i].to != NULL, "failed, but wanted: %s", tests[i].to);
575     }
576   }
577   g_value_unset (&v);
578 }
579
580 GST_END_TEST;
581
582 GST_START_TEST (test_value_compare)
583 {
584   GValue value1 = { 0 };
585   GValue value2 = { 0 };
586   GValue tmp = { 0 };
587
588   g_value_init (&value1, G_TYPE_INT);
589   g_value_set_int (&value1, 10);
590   g_value_init (&value2, G_TYPE_INT);
591   g_value_set_int (&value2, 20);
592   fail_unless (gst_value_compare (&value1, &value2) == GST_VALUE_LESS_THAN);
593   fail_unless (gst_value_compare (&value2, &value1) == GST_VALUE_GREATER_THAN);
594   fail_unless (gst_value_compare (&value1, &value1) == GST_VALUE_EQUAL);
595   g_value_unset (&value1);
596   g_value_unset (&value2);
597
598   g_value_init (&value1, G_TYPE_DOUBLE);
599   g_value_set_double (&value1, 10);
600   g_value_init (&value2, G_TYPE_DOUBLE);
601   g_value_set_double (&value2, 20);
602   fail_unless (gst_value_compare (&value1, &value2) == GST_VALUE_LESS_THAN);
603   fail_unless (gst_value_compare (&value2, &value1) == GST_VALUE_GREATER_THAN);
604   fail_unless (gst_value_compare (&value1, &value1) == GST_VALUE_EQUAL);
605   g_value_unset (&value1);
606   g_value_unset (&value2);
607
608   g_value_init (&value1, G_TYPE_STRING);
609   g_value_set_string (&value1, "a");
610   g_value_init (&value2, G_TYPE_STRING);
611   g_value_set_string (&value2, "b");
612   fail_unless (gst_value_compare (&value1, &value2) == GST_VALUE_LESS_THAN);
613   fail_unless (gst_value_compare (&value2, &value1) == GST_VALUE_GREATER_THAN);
614   fail_unless (gst_value_compare (&value1, &value1) == GST_VALUE_EQUAL);
615   /* Test some NULL string comparisons */
616   g_value_set_string (&value2, NULL);
617   fail_unless (gst_value_compare (&value1, &value2) == GST_VALUE_UNORDERED);
618   fail_unless (gst_value_compare (&value2, &value1) == GST_VALUE_UNORDERED);
619   fail_unless (gst_value_compare (&value2, &value2) == GST_VALUE_EQUAL);
620
621   g_value_unset (&value1);
622   g_value_unset (&value2);
623
624   /* comparing 2/3 with 3/4 */
625   g_value_init (&value1, GST_TYPE_FRACTION);
626   gst_value_set_fraction (&value1, 2, 3);
627   g_value_init (&value2, GST_TYPE_FRACTION);
628   gst_value_set_fraction (&value2, 3, 4);
629   fail_unless (gst_value_compare (&value1, &value2) == GST_VALUE_LESS_THAN);
630   fail_unless (gst_value_compare (&value2, &value1) == GST_VALUE_GREATER_THAN);
631   fail_unless (gst_value_compare (&value1, &value1) == GST_VALUE_EQUAL);
632   g_value_unset (&value1);
633   g_value_unset (&value2);
634
635   /* comparing -4/5 with 2/-3 */
636   g_value_init (&value1, GST_TYPE_FRACTION);
637   gst_value_set_fraction (&value1, -4, 5);
638   g_value_init (&value2, GST_TYPE_FRACTION);
639   gst_value_set_fraction (&value2, 2, -3);
640   fail_unless (gst_value_compare (&value1, &value2) == GST_VALUE_LESS_THAN);
641   fail_unless (gst_value_compare (&value2, &value1) == GST_VALUE_GREATER_THAN);
642   fail_unless (gst_value_compare (&value1, &value1) == GST_VALUE_EQUAL);
643   g_value_unset (&value1);
644   g_value_unset (&value2);
645
646   /* comparing 10/100 with 200/2000 */
647   g_value_init (&value1, GST_TYPE_FRACTION);
648   gst_value_set_fraction (&value1, 10, 100);
649   g_value_init (&value2, GST_TYPE_FRACTION);
650   gst_value_set_fraction (&value2, 200, 2000);
651   fail_unless (gst_value_compare (&value1, &value2) == GST_VALUE_EQUAL);
652   g_value_unset (&value1);
653   g_value_unset (&value2);
654
655   /* comparing -4/5 with 2/-3 */
656   g_value_init (&value1, GST_TYPE_FRACTION);
657   gst_value_set_fraction (&value1, -4, 5);
658   g_value_init (&value2, GST_TYPE_FRACTION);
659   gst_value_set_fraction (&value2, 2, -3);
660   fail_unless (gst_value_compare (&value1, &value2) == GST_VALUE_LESS_THAN);
661   fail_unless (gst_value_compare (&value2, &value1) == GST_VALUE_GREATER_THAN);
662   fail_unless (gst_value_compare (&value1, &value1) == GST_VALUE_EQUAL);
663   g_value_unset (&value1);
664   g_value_unset (&value2);
665
666   /* Check that lists are equal regardless of order */
667   g_value_init (&value1, GST_TYPE_LIST);
668   g_value_init (&tmp, G_TYPE_INT);
669   g_value_set_int (&tmp, 1);
670   gst_value_list_append_value (&value1, &tmp);
671   g_value_set_int (&tmp, 2);
672   gst_value_list_append_value (&value1, &tmp);
673   g_value_set_int (&tmp, 3);
674   gst_value_list_append_value (&value1, &tmp);
675   g_value_set_int (&tmp, 4);
676   gst_value_list_append_value (&value1, &tmp);
677
678   g_value_init (&value2, GST_TYPE_LIST);
679   g_value_set_int (&tmp, 4);
680   gst_value_list_append_value (&value2, &tmp);
681   g_value_set_int (&tmp, 3);
682   gst_value_list_append_value (&value2, &tmp);
683   g_value_set_int (&tmp, 2);
684   gst_value_list_append_value (&value2, &tmp);
685   g_value_set_int (&tmp, 1);
686   gst_value_list_append_value (&value2, &tmp);
687
688   fail_unless (gst_value_compare (&value1, &value2) == GST_VALUE_EQUAL,
689       "value lists with different order were not equal when they should be");
690   fail_unless (gst_value_compare (&value1, &value1) == GST_VALUE_EQUAL,
691       "value lists with same order were not equal when they should be");
692   fail_unless (gst_value_compare (&value2, &value2) == GST_VALUE_EQUAL,
693       "value lists with same order were not equal when they should be");
694
695   /* Carry over the lists to this next check: */
696   /* Lists with different sizes are unequal */
697   g_value_set_int (&tmp, 1);
698   gst_value_list_append_value (&value2, &tmp);
699
700   fail_if (gst_value_compare (&value1, &value2) == GST_VALUE_EQUAL,
701       "Value lists with different size were equal when they shouldn't be");
702
703   /* Carry over the lists to this next check: */
704   /* Lists with same size but list1 contains one more element not in list2 */
705   g_value_set_int (&tmp, 5);
706   gst_value_list_append_value (&value1, &tmp);
707
708   fail_if (gst_value_compare (&value1, &value2) == GST_VALUE_EQUAL,
709       "Value lists with different elements were equal when they shouldn't be");
710   fail_if (gst_value_compare (&value2, &value1) == GST_VALUE_EQUAL,
711       "Value lists with different elements were equal when they shouldn't be");
712
713   g_value_unset (&value1);
714   g_value_unset (&value2);
715   g_value_unset (&tmp);
716
717   /* Arrays are only equal when in the same order */
718   g_value_init (&value1, GST_TYPE_ARRAY);
719   g_value_init (&tmp, G_TYPE_INT);
720   g_value_set_int (&tmp, 1);
721   gst_value_array_append_value (&value1, &tmp);
722   g_value_set_int (&tmp, 2);
723   gst_value_array_append_value (&value1, &tmp);
724   g_value_set_int (&tmp, 3);
725   gst_value_array_append_value (&value1, &tmp);
726   g_value_set_int (&tmp, 4);
727   gst_value_array_append_value (&value1, &tmp);
728
729   g_value_init (&value2, GST_TYPE_ARRAY);
730   g_value_set_int (&tmp, 4);
731   gst_value_array_append_value (&value2, &tmp);
732   g_value_set_int (&tmp, 3);
733   gst_value_array_append_value (&value2, &tmp);
734   g_value_set_int (&tmp, 2);
735   gst_value_array_append_value (&value2, &tmp);
736   g_value_set_int (&tmp, 1);
737   gst_value_array_append_value (&value2, &tmp);
738
739   fail_if (gst_value_compare (&value1, &value2) == GST_VALUE_EQUAL,
740       "Value arrays with different order were equal when they shouldn't be");
741   fail_unless (gst_value_compare (&value1, &value1) == GST_VALUE_EQUAL,
742       "Identical value arrays were not equal when they should be");
743   fail_unless (gst_value_compare (&value2, &value2) == GST_VALUE_EQUAL,
744       "Identical value arrays were not equal when they should be");
745
746   /* Carry over the arrays to this next check: */
747   /* Arrays with different sizes are unequal */
748   g_value_unset (&value2);
749   g_value_init (&value2, GST_TYPE_ARRAY);
750   g_value_copy (&value1, &value2);
751
752   g_value_set_int (&tmp, 1);
753   gst_value_array_append_value (&value2, &tmp);
754
755   fail_if (gst_value_compare (&value1, &value2) == GST_VALUE_EQUAL,
756       "Value arrays with different size were equal when they shouldn't be");
757   /* order should not matter */
758   fail_if (gst_value_compare (&value2, &value1) == GST_VALUE_EQUAL,
759       "Value arrays with different size were equal when they shouldn't be");
760
761   g_value_unset (&value1);
762   g_value_unset (&value2);
763   g_value_unset (&tmp);
764
765   g_value_init (&value1, GST_TYPE_BITMASK);
766   gst_value_set_bitmask (&value1, 0x123);
767   g_value_init (&value2, GST_TYPE_BITMASK);
768   gst_value_set_bitmask (&value2, 0x321);
769   fail_unless (gst_value_compare (&value1, &value2) == GST_VALUE_UNORDERED);
770   fail_unless (gst_value_compare (&value2, &value1) == GST_VALUE_UNORDERED);
771   fail_unless (gst_value_compare (&value1, &value1) == GST_VALUE_EQUAL);
772   g_value_unset (&value1);
773   g_value_unset (&value2);
774 }
775
776 GST_END_TEST;
777
778 GST_START_TEST (test_value_intersect)
779 {
780   GValue dest = { 0 };
781   GValue src1 = { 0 };
782   GValue src2 = { 0 };
783   GValue item = { 0 };
784   gboolean ret;
785
786   g_value_init (&src1, G_TYPE_INT);
787   g_value_set_int (&src1, 10);
788   g_value_init (&src2, G_TYPE_INT);
789   g_value_set_int (&src2, 20);
790   ret = gst_value_intersect (&dest, &src1, &src2);
791   fail_unless (ret == FALSE);
792   g_value_unset (&src1);
793   g_value_unset (&src2);
794
795   g_value_init (&src1, G_TYPE_STRING);
796   g_value_set_static_string (&src1, "YUY2");
797   g_value_init (&src2, GST_TYPE_LIST);
798   g_value_init (&item, G_TYPE_STRING);
799   g_value_set_static_string (&item, "YUY2");
800   gst_value_list_append_value (&src2, &item);
801   g_value_set_static_string (&item, "I420");
802   gst_value_list_append_value (&src2, &item);
803   g_value_set_static_string (&item, "ABCD");
804   gst_value_list_append_value (&src2, &item);
805
806   fail_unless (gst_value_intersect (&dest, &src1, &src2));
807   fail_unless (G_VALUE_HOLDS_STRING (&dest));
808   fail_unless (g_str_equal (g_value_get_string (&dest), "YUY2"));
809
810   g_value_unset (&src1);
811   g_value_unset (&src2);
812   g_value_unset (&dest);
813 }
814
815 GST_END_TEST;
816
817
818 GST_START_TEST (test_value_subtract_int)
819 {
820   GValue dest = { 0 };
821   GValue src1 = { 0 };
822   GValue src2 = { 0 };
823   const GValue *tmp;
824   gboolean ret;
825
826   /*  int <-> int
827    */
828   g_value_init (&src1, G_TYPE_INT);
829   g_value_set_int (&src1, 10);
830   g_value_init (&src2, G_TYPE_INT);
831   g_value_set_int (&src2, 20);
832   /* subtract as in sets, result is 10 */
833   ret = gst_value_subtract (&dest, &src1, &src2);
834   fail_unless (ret == TRUE);
835   fail_unless (gst_value_compare (&dest, &src1) == GST_VALUE_EQUAL);
836   g_value_unset (&dest);
837
838   /* same values, yields empty set */
839   ret = gst_value_subtract (&dest, &src1, &src1);
840   fail_unless (ret == FALSE);
841   g_value_unset (&src1);
842   g_value_unset (&src2);
843
844   /*  int <-> int_range
845    */
846
847   /* would yield an empty set */
848   g_value_init (&src1, G_TYPE_INT);
849   g_value_set_int (&src1, 10);
850   g_value_init (&src2, GST_TYPE_INT_RANGE);
851   gst_value_set_int_range (&src2, 0, 20);
852   ret = gst_value_subtract (&dest, &src1, &src2);
853   fail_unless (ret == FALSE);
854
855   /* and the other way around, should create a list of two ranges. */
856   ret = gst_value_subtract (&dest, &src2, &src1);
857   fail_unless (ret == TRUE);
858   fail_unless (GST_VALUE_HOLDS_LIST (&dest) == TRUE);
859   tmp = gst_value_list_get_value (&dest, 0);
860   fail_unless (GST_VALUE_HOLDS_INT_RANGE (tmp) == TRUE);
861   fail_unless (gst_value_get_int_range_min (tmp) == 0);
862   fail_unless (gst_value_get_int_range_max (tmp) == 9);
863   tmp = gst_value_list_get_value (&dest, 1);
864   fail_unless (GST_VALUE_HOLDS_INT_RANGE (tmp) == TRUE);
865   fail_unless (gst_value_get_int_range_min (tmp) == 11);
866   fail_unless (gst_value_get_int_range_max (tmp) == 20);
867   g_value_unset (&dest);
868   g_value_unset (&src1);
869   g_value_unset (&src2);
870
871   /* border case 1, empty set */
872   g_value_init (&src1, G_TYPE_INT);
873   g_value_set_int (&src1, 10);
874   g_value_init (&src2, GST_TYPE_INT_RANGE);
875   gst_value_set_int_range (&src2, 10, 20);
876   ret = gst_value_subtract (&dest, &src1, &src2);
877   fail_unless (ret == FALSE);
878
879   /* and the other way around, should create a new range. */
880   ret = gst_value_subtract (&dest, &src2, &src1);
881   fail_unless (ret == TRUE);
882   fail_unless (GST_VALUE_HOLDS_INT_RANGE (&dest) == TRUE);
883   fail_unless (gst_value_get_int_range_min (&dest) == 11);
884   fail_unless (gst_value_get_int_range_max (&dest) == 20);
885   g_value_unset (&dest);
886   g_value_unset (&src1);
887   g_value_unset (&src2);
888
889   /* border case 2, empty set */
890   g_value_init (&src1, G_TYPE_INT);
891   g_value_set_int (&src1, 20);
892   g_value_init (&src2, GST_TYPE_INT_RANGE);
893   gst_value_set_int_range (&src2, 10, 20);
894   ret = gst_value_subtract (&dest, &src1, &src2);
895   fail_unless (ret == FALSE);
896
897   /* and the other way around, should create a new range. */
898   ret = gst_value_subtract (&dest, &src2, &src1);
899   fail_unless (ret == TRUE);
900   fail_unless (GST_VALUE_HOLDS_INT_RANGE (&dest) == TRUE);
901   fail_unless (gst_value_get_int_range_min (&dest) == 10);
902   fail_unless (gst_value_get_int_range_max (&dest) == 19);
903   g_value_unset (&dest);
904   g_value_unset (&src1);
905   g_value_unset (&src2);
906
907   /* case 3, valid set */
908   g_value_init (&src1, G_TYPE_INT);
909   g_value_set_int (&src1, 0);
910   g_value_init (&src2, GST_TYPE_INT_RANGE);
911   gst_value_set_int_range (&src2, 10, 20);
912   ret = gst_value_subtract (&dest, &src1, &src2);
913   fail_unless (ret == TRUE);
914   fail_unless (G_VALUE_HOLDS_INT (&dest) == TRUE);
915   fail_unless (gst_value_compare (&dest, &src1) == GST_VALUE_EQUAL);
916   g_value_unset (&dest);
917
918   /* and the other way around, should keep the range. */
919   ret = gst_value_subtract (&dest, &src2, &src1);
920   fail_unless (ret == TRUE);
921   fail_unless (GST_VALUE_HOLDS_INT_RANGE (&dest) == TRUE);
922   fail_unless (gst_value_get_int_range_min (&dest) == 10);
923   fail_unless (gst_value_get_int_range_max (&dest) == 20);
924   g_value_unset (&dest);
925   g_value_unset (&src1);
926   g_value_unset (&src2);
927
928   /*  int_range <-> int_range
929    */
930
931   /* same range, empty set */
932   g_value_init (&src1, GST_TYPE_INT_RANGE);
933   gst_value_set_int_range (&src1, 10, 20);
934   g_value_init (&src2, GST_TYPE_INT_RANGE);
935   gst_value_set_int_range (&src2, 10, 20);
936   ret = gst_value_subtract (&dest, &src1, &src2);
937   fail_unless (ret == FALSE);
938   ret = gst_value_subtract (&dest, &src2, &src1);
939   fail_unless (ret == FALSE);
940   g_value_unset (&src1);
941   g_value_unset (&src2);
942
943   /* non overlapping ranges */
944   g_value_init (&src1, GST_TYPE_INT_RANGE);
945   gst_value_set_int_range (&src1, 10, 20);
946   g_value_init (&src2, GST_TYPE_INT_RANGE);
947   gst_value_set_int_range (&src2, 30, 40);
948   ret = gst_value_subtract (&dest, &src1, &src2);
949   fail_unless (ret == TRUE);
950   fail_unless (GST_VALUE_HOLDS_INT_RANGE (&dest) == TRUE);
951   fail_unless (gst_value_get_int_range_min (&dest) == 10);
952   fail_unless (gst_value_get_int_range_max (&dest) == 20);
953   g_value_unset (&dest);
954   /* the other way */
955   ret = gst_value_subtract (&dest, &src2, &src1);
956   fail_unless (ret == TRUE);
957   fail_unless (GST_VALUE_HOLDS_INT_RANGE (&dest) == TRUE);
958   fail_unless (gst_value_get_int_range_min (&dest) == 30);
959   fail_unless (gst_value_get_int_range_max (&dest) == 40);
960   g_value_unset (&dest);
961   g_value_unset (&src1);
962   g_value_unset (&src2);
963
964   /* completely overlapping ranges */
965   g_value_init (&src1, GST_TYPE_INT_RANGE);
966   gst_value_set_int_range (&src1, 10, 20);
967   g_value_init (&src2, GST_TYPE_INT_RANGE);
968   gst_value_set_int_range (&src2, 10, 30);
969   ret = gst_value_subtract (&dest, &src1, &src2);
970   fail_unless (ret == FALSE);
971   /* the other way */
972   ret = gst_value_subtract (&dest, &src2, &src1);
973   fail_unless (ret == TRUE);
974   fail_unless (GST_VALUE_HOLDS_INT_RANGE (&dest) == TRUE);
975   fail_unless (gst_value_get_int_range_min (&dest) == 21);
976   fail_unless (gst_value_get_int_range_max (&dest) == 30);
977   g_value_unset (&dest);
978   g_value_unset (&src1);
979   g_value_unset (&src2);
980
981   /* partially overlapping ranges */
982   g_value_init (&src1, GST_TYPE_INT_RANGE);
983   gst_value_set_int_range (&src1, 10, 20);
984   g_value_init (&src2, GST_TYPE_INT_RANGE);
985   gst_value_set_int_range (&src2, 15, 30);
986   ret = gst_value_subtract (&dest, &src1, &src2);
987   fail_unless (ret == TRUE);
988   fail_unless (GST_VALUE_HOLDS_INT_RANGE (&dest) == TRUE);
989   fail_unless (gst_value_get_int_range_min (&dest) == 10);
990   fail_unless (gst_value_get_int_range_max (&dest) == 14);
991   g_value_unset (&dest);
992   /* the other way */
993   ret = gst_value_subtract (&dest, &src2, &src1);
994   fail_unless (ret == TRUE);
995   fail_unless (GST_VALUE_HOLDS_INT_RANGE (&dest) == TRUE);
996   fail_unless (gst_value_get_int_range_min (&dest) == 21);
997   fail_unless (gst_value_get_int_range_max (&dest) == 30);
998   g_value_unset (&dest);
999   g_value_unset (&src1);
1000   g_value_unset (&src2);
1001
1002   /* create a hole { int_range, int_range } */
1003   g_value_init (&src1, GST_TYPE_INT_RANGE);
1004   gst_value_set_int_range (&src1, 10, 30);
1005   g_value_init (&src2, GST_TYPE_INT_RANGE);
1006   gst_value_set_int_range (&src2, 15, 20);
1007   ret = gst_value_subtract (&dest, &src1, &src2);
1008   fail_unless (ret == TRUE);
1009   fail_unless (GST_VALUE_HOLDS_LIST (&dest) == TRUE);
1010   tmp = gst_value_list_get_value (&dest, 0);
1011   fail_unless (GST_VALUE_HOLDS_INT_RANGE (tmp) == TRUE);
1012   fail_unless (gst_value_get_int_range_min (tmp) == 10);
1013   fail_unless (gst_value_get_int_range_max (tmp) == 14);
1014   tmp = gst_value_list_get_value (&dest, 1);
1015   fail_unless (GST_VALUE_HOLDS_INT_RANGE (tmp) == TRUE);
1016   fail_unless (gst_value_get_int_range_min (tmp) == 21);
1017   fail_unless (gst_value_get_int_range_max (tmp) == 30);
1018   g_value_unset (&dest);
1019   /* the other way */
1020   ret = gst_value_subtract (&dest, &src2, &src1);
1021   fail_unless (ret == FALSE);
1022   g_value_unset (&src1);
1023   g_value_unset (&src2);
1024
1025   /* create a hole, { int, int } */
1026   g_value_init (&src1, GST_TYPE_INT_RANGE);
1027   gst_value_set_int_range (&src1, 10, 30);
1028   g_value_init (&src2, GST_TYPE_INT_RANGE);
1029   gst_value_set_int_range (&src2, 11, 29);
1030   ret = gst_value_subtract (&dest, &src1, &src2);
1031   fail_unless (ret == TRUE);
1032   fail_unless (GST_VALUE_HOLDS_LIST (&dest) == TRUE);
1033   tmp = gst_value_list_get_value (&dest, 0);
1034   fail_unless (G_VALUE_HOLDS_INT (tmp) == TRUE);
1035   fail_unless (g_value_get_int (tmp) == 10);
1036   tmp = gst_value_list_get_value (&dest, 1);
1037   fail_unless (G_VALUE_HOLDS_INT (tmp) == TRUE);
1038   fail_unless (g_value_get_int (tmp) == 30);
1039   g_value_unset (&dest);
1040   /* the other way */
1041   ret = gst_value_subtract (&dest, &src2, &src1);
1042   fail_unless (ret == FALSE);
1043   g_value_unset (&src1);
1044   g_value_unset (&src2);
1045
1046   /* create a hole, { int, int_range } */
1047   g_value_init (&src1, GST_TYPE_INT_RANGE);
1048   gst_value_set_int_range (&src1, 10, 30);
1049   g_value_init (&src2, GST_TYPE_INT_RANGE);
1050   gst_value_set_int_range (&src2, 11, 28);
1051   ret = gst_value_subtract (&dest, &src1, &src2);
1052   fail_unless (ret == TRUE);
1053   fail_unless (GST_VALUE_HOLDS_LIST (&dest) == TRUE);
1054   tmp = gst_value_list_get_value (&dest, 0);
1055   fail_unless (G_VALUE_HOLDS_INT (tmp) == TRUE);
1056   fail_unless (g_value_get_int (tmp) == 10);
1057   tmp = gst_value_list_get_value (&dest, 1);
1058   fail_unless (GST_VALUE_HOLDS_INT_RANGE (tmp) == TRUE);
1059   fail_unless (gst_value_get_int_range_min (tmp) == 29);
1060   fail_unless (gst_value_get_int_range_max (tmp) == 30);
1061   g_value_unset (&dest);
1062   /* the other way */
1063   ret = gst_value_subtract (&dest, &src2, &src1);
1064   fail_unless (ret == FALSE);
1065   g_value_unset (&src1);
1066   g_value_unset (&src2);
1067
1068   /* create a hole, { int_range, int } */
1069   g_value_init (&src1, GST_TYPE_INT_RANGE);
1070   gst_value_set_int_range (&src1, 10, 30);
1071   g_value_init (&src2, GST_TYPE_INT_RANGE);
1072   gst_value_set_int_range (&src2, 12, 29);
1073   ret = gst_value_subtract (&dest, &src1, &src2);
1074   fail_unless (ret == TRUE);
1075   fail_unless (GST_VALUE_HOLDS_LIST (&dest) == TRUE);
1076   tmp = gst_value_list_get_value (&dest, 0);
1077   fail_unless (GST_VALUE_HOLDS_INT_RANGE (tmp) == TRUE);
1078   fail_unless (gst_value_get_int_range_min (tmp) == 10);
1079   fail_unless (gst_value_get_int_range_max (tmp) == 11);
1080   tmp = gst_value_list_get_value (&dest, 1);
1081   fail_unless (G_VALUE_HOLDS_INT (tmp) == TRUE);
1082   fail_unless (g_value_get_int (tmp) == 30);
1083   g_value_unset (&dest);
1084   /* the other way */
1085   ret = gst_value_subtract (&dest, &src2, &src1);
1086   fail_unless (ret == FALSE);
1087   g_value_unset (&src1);
1088   g_value_unset (&src2);
1089 }
1090
1091 GST_END_TEST;
1092
1093 GST_START_TEST (test_value_subtract_int64)
1094 {
1095   GValue dest = { 0 };
1096   GValue src1 = { 0 };
1097   GValue src2 = { 0 };
1098   const GValue *tmp;
1099   gboolean ret;
1100
1101   /*  int64 <-> int64
1102    */
1103   g_value_init (&src1, G_TYPE_INT64);
1104   g_value_set_int64 (&src1, 10);
1105   g_value_init (&src2, G_TYPE_INT64);
1106   g_value_set_int64 (&src2, 20);
1107   /* subtract as in sets, result is 10 */
1108   ret = gst_value_subtract (&dest, &src1, &src2);
1109   fail_unless (ret == TRUE);
1110   fail_unless (gst_value_compare (&dest, &src1) == GST_VALUE_EQUAL);
1111   g_value_unset (&dest);
1112
1113   /* same values, yields empty set */
1114   ret = gst_value_subtract (&dest, &src1, &src1);
1115   fail_unless (ret == FALSE);
1116   g_value_unset (&src1);
1117   g_value_unset (&src2);
1118
1119   /*  int64 <-> int64_range
1120    */
1121
1122   /* would yield an empty set */
1123   g_value_init (&src1, G_TYPE_INT64);
1124   g_value_set_int64 (&src1, 10);
1125   g_value_init (&src2, GST_TYPE_INT64_RANGE);
1126   gst_value_set_int64_range (&src2, 0, 20);
1127   ret = gst_value_subtract (&dest, &src1, &src2);
1128   fail_unless (ret == FALSE);
1129
1130   /* and the other way around, should create a list of two ranges. */
1131   ret = gst_value_subtract (&dest, &src2, &src1);
1132   fail_unless (ret == TRUE);
1133   fail_unless (GST_VALUE_HOLDS_LIST (&dest) == TRUE);
1134   tmp = gst_value_list_get_value (&dest, 0);
1135   fail_unless (GST_VALUE_HOLDS_INT64_RANGE (tmp) == TRUE);
1136   fail_unless (gst_value_get_int64_range_min (tmp) == 0);
1137   fail_unless (gst_value_get_int64_range_max (tmp) == 9);
1138   tmp = gst_value_list_get_value (&dest, 1);
1139   fail_unless (GST_VALUE_HOLDS_INT64_RANGE (tmp) == TRUE);
1140   fail_unless (gst_value_get_int64_range_min (tmp) == 11);
1141   fail_unless (gst_value_get_int64_range_max (tmp) == 20);
1142   g_value_unset (&dest);
1143   g_value_unset (&src1);
1144   g_value_unset (&src2);
1145
1146   /* border case 1, empty set */
1147   g_value_init (&src1, G_TYPE_INT64);
1148   g_value_set_int64 (&src1, 10);
1149   g_value_init (&src2, GST_TYPE_INT64_RANGE);
1150   gst_value_set_int64_range (&src2, 10, 20);
1151   ret = gst_value_subtract (&dest, &src1, &src2);
1152   fail_unless (ret == FALSE);
1153
1154   /* and the other way around, should create a new range. */
1155   ret = gst_value_subtract (&dest, &src2, &src1);
1156   fail_unless (ret == TRUE);
1157   fail_unless (GST_VALUE_HOLDS_INT64_RANGE (&dest) == TRUE);
1158   fail_unless (gst_value_get_int64_range_min (&dest) == 11);
1159   fail_unless (gst_value_get_int64_range_max (&dest) == 20);
1160   g_value_unset (&dest);
1161   g_value_unset (&src1);
1162   g_value_unset (&src2);
1163
1164   /* border case 2, empty set */
1165   g_value_init (&src1, G_TYPE_INT64);
1166   g_value_set_int64 (&src1, 20);
1167   g_value_init (&src2, GST_TYPE_INT64_RANGE);
1168   gst_value_set_int64_range (&src2, 10, 20);
1169   ret = gst_value_subtract (&dest, &src1, &src2);
1170   fail_unless (ret == FALSE);
1171
1172   /* and the other way around, should create a new range. */
1173   ret = gst_value_subtract (&dest, &src2, &src1);
1174   fail_unless (ret == TRUE);
1175   fail_unless (GST_VALUE_HOLDS_INT64_RANGE (&dest) == TRUE);
1176   fail_unless (gst_value_get_int64_range_min (&dest) == 10);
1177   fail_unless (gst_value_get_int64_range_max (&dest) == 19);
1178   g_value_unset (&dest);
1179   g_value_unset (&src1);
1180   g_value_unset (&src2);
1181
1182   /* case 3, valid set */
1183   g_value_init (&src1, G_TYPE_INT64);
1184   g_value_set_int64 (&src1, 0);
1185   g_value_init (&src2, GST_TYPE_INT64_RANGE);
1186   gst_value_set_int64_range (&src2, 10, 20);
1187   ret = gst_value_subtract (&dest, &src1, &src2);
1188   fail_unless (ret == TRUE);
1189   fail_unless (G_VALUE_HOLDS_INT64 (&dest) == TRUE);
1190   fail_unless (gst_value_compare (&dest, &src1) == GST_VALUE_EQUAL);
1191   g_value_unset (&dest);
1192
1193   /* and the other way around, should keep the range. */
1194   ret = gst_value_subtract (&dest, &src2, &src1);
1195   fail_unless (ret == TRUE);
1196   fail_unless (GST_VALUE_HOLDS_INT64_RANGE (&dest) == TRUE);
1197   fail_unless (gst_value_get_int64_range_min (&dest) == 10);
1198   fail_unless (gst_value_get_int64_range_max (&dest) == 20);
1199   g_value_unset (&dest);
1200   g_value_unset (&src1);
1201   g_value_unset (&src2);
1202
1203   /*  int64_range <-> int64_range
1204    */
1205
1206   /* same range, empty set */
1207   g_value_init (&src1, GST_TYPE_INT64_RANGE);
1208   gst_value_set_int64_range (&src1, 10, 20);
1209   g_value_init (&src2, GST_TYPE_INT64_RANGE);
1210   gst_value_set_int64_range (&src2, 10, 20);
1211   ret = gst_value_subtract (&dest, &src1, &src2);
1212   fail_unless (ret == FALSE);
1213   ret = gst_value_subtract (&dest, &src2, &src1);
1214   fail_unless (ret == FALSE);
1215   g_value_unset (&src1);
1216   g_value_unset (&src2);
1217
1218   /* non overlapping ranges */
1219   g_value_init (&src1, GST_TYPE_INT64_RANGE);
1220   gst_value_set_int64_range (&src1, 10, 20);
1221   g_value_init (&src2, GST_TYPE_INT64_RANGE);
1222   gst_value_set_int64_range (&src2, 30, 40);
1223   ret = gst_value_subtract (&dest, &src1, &src2);
1224   fail_unless (ret == TRUE);
1225   fail_unless (GST_VALUE_HOLDS_INT64_RANGE (&dest) == TRUE);
1226   fail_unless (gst_value_get_int64_range_min (&dest) == 10);
1227   fail_unless (gst_value_get_int64_range_max (&dest) == 20);
1228   g_value_unset (&dest);
1229   /* the other way */
1230   ret = gst_value_subtract (&dest, &src2, &src1);
1231   fail_unless (ret == TRUE);
1232   fail_unless (GST_VALUE_HOLDS_INT64_RANGE (&dest) == TRUE);
1233   fail_unless (gst_value_get_int64_range_min (&dest) == 30);
1234   fail_unless (gst_value_get_int64_range_max (&dest) == 40);
1235   g_value_unset (&dest);
1236   g_value_unset (&src1);
1237   g_value_unset (&src2);
1238
1239   /* completely overlapping ranges */
1240   g_value_init (&src1, GST_TYPE_INT64_RANGE);
1241   gst_value_set_int64_range (&src1, 10, 20);
1242   g_value_init (&src2, GST_TYPE_INT64_RANGE);
1243   gst_value_set_int64_range (&src2, 10, 30);
1244   ret = gst_value_subtract (&dest, &src1, &src2);
1245   fail_unless (ret == FALSE);
1246   /* the other way */
1247   ret = gst_value_subtract (&dest, &src2, &src1);
1248   fail_unless (ret == TRUE);
1249   fail_unless (GST_VALUE_HOLDS_INT64_RANGE (&dest) == TRUE);
1250   fail_unless (gst_value_get_int64_range_min (&dest) == 21);
1251   fail_unless (gst_value_get_int64_range_max (&dest) == 30);
1252   g_value_unset (&dest);
1253   g_value_unset (&src1);
1254   g_value_unset (&src2);
1255
1256   /* partially overlapping ranges */
1257   g_value_init (&src1, GST_TYPE_INT64_RANGE);
1258   gst_value_set_int64_range (&src1, 10, 20);
1259   g_value_init (&src2, GST_TYPE_INT64_RANGE);
1260   gst_value_set_int64_range (&src2, 15, 30);
1261   ret = gst_value_subtract (&dest, &src1, &src2);
1262   fail_unless (ret == TRUE);
1263   fail_unless (GST_VALUE_HOLDS_INT64_RANGE (&dest) == TRUE);
1264   fail_unless (gst_value_get_int64_range_min (&dest) == 10);
1265   fail_unless (gst_value_get_int64_range_max (&dest) == 14);
1266   g_value_unset (&dest);
1267   /* the other way */
1268   ret = gst_value_subtract (&dest, &src2, &src1);
1269   fail_unless (ret == TRUE);
1270   fail_unless (GST_VALUE_HOLDS_INT64_RANGE (&dest) == TRUE);
1271   fail_unless (gst_value_get_int64_range_min (&dest) == 21);
1272   fail_unless (gst_value_get_int64_range_max (&dest) == 30);
1273   g_value_unset (&dest);
1274   g_value_unset (&src1);
1275   g_value_unset (&src2);
1276
1277   /* create a hole { int64_range, int64_range } */
1278   g_value_init (&src1, GST_TYPE_INT64_RANGE);
1279   gst_value_set_int64_range (&src1, 10, 30);
1280   g_value_init (&src2, GST_TYPE_INT64_RANGE);
1281   gst_value_set_int64_range (&src2, 15, 20);
1282   ret = gst_value_subtract (&dest, &src1, &src2);
1283   fail_unless (ret == TRUE);
1284   fail_unless (GST_VALUE_HOLDS_LIST (&dest) == TRUE);
1285   tmp = gst_value_list_get_value (&dest, 0);
1286   fail_unless (GST_VALUE_HOLDS_INT64_RANGE (tmp) == TRUE);
1287   fail_unless (gst_value_get_int64_range_min (tmp) == 10);
1288   fail_unless (gst_value_get_int64_range_max (tmp) == 14);
1289   tmp = gst_value_list_get_value (&dest, 1);
1290   fail_unless (GST_VALUE_HOLDS_INT64_RANGE (tmp) == TRUE);
1291   fail_unless (gst_value_get_int64_range_min (tmp) == 21);
1292   fail_unless (gst_value_get_int64_range_max (tmp) == 30);
1293   g_value_unset (&dest);
1294   /* the other way */
1295   ret = gst_value_subtract (&dest, &src2, &src1);
1296   fail_unless (ret == FALSE);
1297   g_value_unset (&src1);
1298   g_value_unset (&src2);
1299
1300   /* create a hole, { int64, int64 } */
1301   g_value_init (&src1, GST_TYPE_INT64_RANGE);
1302   gst_value_set_int64_range (&src1, 10, 30);
1303   g_value_init (&src2, GST_TYPE_INT64_RANGE);
1304   gst_value_set_int64_range (&src2, 11, 29);
1305   ret = gst_value_subtract (&dest, &src1, &src2);
1306   fail_unless (ret == TRUE);
1307   fail_unless (GST_VALUE_HOLDS_LIST (&dest) == TRUE);
1308   tmp = gst_value_list_get_value (&dest, 0);
1309   fail_unless (G_VALUE_HOLDS_INT64 (tmp) == TRUE);
1310   fail_unless (g_value_get_int64 (tmp) == 10);
1311   tmp = gst_value_list_get_value (&dest, 1);
1312   fail_unless (G_VALUE_HOLDS_INT64 (tmp) == TRUE);
1313   fail_unless (g_value_get_int64 (tmp) == 30);
1314   g_value_unset (&dest);
1315   /* the other way */
1316   ret = gst_value_subtract (&dest, &src2, &src1);
1317   fail_unless (ret == FALSE);
1318   g_value_unset (&src1);
1319   g_value_unset (&src2);
1320
1321   /* create a hole, { int64, int64_range } */
1322   g_value_init (&src1, GST_TYPE_INT64_RANGE);
1323   gst_value_set_int64_range (&src1, 10, 30);
1324   g_value_init (&src2, GST_TYPE_INT64_RANGE);
1325   gst_value_set_int64_range (&src2, 11, 28);
1326   ret = gst_value_subtract (&dest, &src1, &src2);
1327   fail_unless (ret == TRUE);
1328   fail_unless (GST_VALUE_HOLDS_LIST (&dest) == TRUE);
1329   tmp = gst_value_list_get_value (&dest, 0);
1330   fail_unless (G_VALUE_HOLDS_INT64 (tmp) == TRUE);
1331   fail_unless (g_value_get_int64 (tmp) == 10);
1332   tmp = gst_value_list_get_value (&dest, 1);
1333   fail_unless (GST_VALUE_HOLDS_INT64_RANGE (tmp) == TRUE);
1334   fail_unless (gst_value_get_int64_range_min (tmp) == 29);
1335   fail_unless (gst_value_get_int64_range_max (tmp) == 30);
1336   g_value_unset (&dest);
1337   /* the other way */
1338   ret = gst_value_subtract (&dest, &src2, &src1);
1339   fail_unless (ret == FALSE);
1340   g_value_unset (&src1);
1341   g_value_unset (&src2);
1342
1343   /* create a hole, { int64_range, int64 } */
1344   g_value_init (&src1, GST_TYPE_INT64_RANGE);
1345   gst_value_set_int64_range (&src1, 10, 30);
1346   g_value_init (&src2, GST_TYPE_INT64_RANGE);
1347   gst_value_set_int64_range (&src2, 12, 29);
1348   ret = gst_value_subtract (&dest, &src1, &src2);
1349   fail_unless (ret == TRUE);
1350   fail_unless (GST_VALUE_HOLDS_LIST (&dest) == TRUE);
1351   tmp = gst_value_list_get_value (&dest, 0);
1352   fail_unless (GST_VALUE_HOLDS_INT64_RANGE (tmp) == TRUE);
1353   fail_unless (gst_value_get_int64_range_min (tmp) == 10);
1354   fail_unless (gst_value_get_int64_range_max (tmp) == 11);
1355   tmp = gst_value_list_get_value (&dest, 1);
1356   fail_unless (G_VALUE_HOLDS_INT64 (tmp) == TRUE);
1357   fail_unless (g_value_get_int64 (tmp) == 30);
1358   g_value_unset (&dest);
1359   /* the other way */
1360   ret = gst_value_subtract (&dest, &src2, &src1);
1361   fail_unless (ret == FALSE);
1362   g_value_unset (&src1);
1363   g_value_unset (&src2);
1364 }
1365
1366 GST_END_TEST;
1367
1368 GST_START_TEST (test_value_subtract_double)
1369 {
1370   GValue dest = { 0 };
1371   GValue src1 = { 0 };
1372   GValue src2 = { 0 };
1373   const GValue *tmp;
1374   gboolean ret;
1375
1376   /*  double <-> double
1377    */
1378   g_value_init (&src1, G_TYPE_DOUBLE);
1379   g_value_set_double (&src1, 10.0);
1380   g_value_init (&src2, G_TYPE_DOUBLE);
1381   g_value_set_double (&src2, 20.0);
1382   /* subtract as in sets, result is 10 */
1383   ret = gst_value_subtract (&dest, &src1, &src2);
1384   fail_unless (ret == TRUE);
1385   fail_unless (gst_value_compare (&dest, &src1) == GST_VALUE_EQUAL);
1386   g_value_unset (&dest);
1387
1388   /* same values, yields empty set */
1389   ret = gst_value_subtract (&dest, &src1, &src1);
1390   fail_unless (ret == FALSE);
1391   g_value_unset (&src1);
1392   g_value_unset (&src2);
1393
1394   /*  double <-> double_range
1395    */
1396
1397   /* would yield an empty set */
1398   g_value_init (&src1, G_TYPE_DOUBLE);
1399   g_value_set_double (&src1, 10.0);
1400   g_value_init (&src2, GST_TYPE_DOUBLE_RANGE);
1401   gst_value_set_double_range (&src2, 0.0, 20.0);
1402   ret = gst_value_subtract (&dest, &src1, &src2);
1403   fail_unless (ret == FALSE);
1404
1405   /* and the other way around, we cannot create open ranges
1406    * so the result is the range again */
1407   ret = gst_value_subtract (&dest, &src2, &src1);
1408   fail_unless (ret == TRUE);
1409   fail_unless (GST_VALUE_HOLDS_DOUBLE_RANGE (&dest) == TRUE);
1410   fail_unless (gst_value_get_double_range_min (&dest) == 0.0);
1411   fail_unless (gst_value_get_double_range_max (&dest) == 20.0);
1412   g_value_unset (&dest);
1413   g_value_unset (&src1);
1414   g_value_unset (&src2);
1415
1416   /* border case 1, empty set */
1417   g_value_init (&src1, G_TYPE_DOUBLE);
1418   g_value_set_double (&src1, 10.0);
1419   g_value_init (&src2, GST_TYPE_DOUBLE_RANGE);
1420   gst_value_set_double_range (&src2, 10.0, 20.0);
1421   ret = gst_value_subtract (&dest, &src1, &src2);
1422   fail_unless (ret == FALSE);
1423
1424   /* and the other way around, should keep same range as
1425    * we don't have open ranges. */
1426   ret = gst_value_subtract (&dest, &src2, &src1);
1427   fail_unless (ret == TRUE);
1428   fail_unless (GST_VALUE_HOLDS_DOUBLE_RANGE (&dest) == TRUE);
1429   fail_unless (gst_value_get_double_range_min (&dest) == 10.0);
1430   fail_unless (gst_value_get_double_range_max (&dest) == 20.0);
1431   g_value_unset (&dest);
1432   g_value_unset (&src1);
1433   g_value_unset (&src2);
1434
1435   /* border case 2, empty set */
1436   g_value_init (&src1, G_TYPE_DOUBLE);
1437   g_value_set_double (&src1, 20.0);
1438   g_value_init (&src2, GST_TYPE_DOUBLE_RANGE);
1439   gst_value_set_double_range (&src2, 10.0, 20.0);
1440   ret = gst_value_subtract (&dest, &src1, &src2);
1441   fail_unless (ret == FALSE);
1442
1443   /* and the other way around, should keep same range as
1444    * we don't have open ranges. */
1445   ret = gst_value_subtract (&dest, &src2, &src1);
1446   fail_unless (ret == TRUE);
1447   fail_unless (GST_VALUE_HOLDS_DOUBLE_RANGE (&dest) == TRUE);
1448   fail_unless (gst_value_get_double_range_min (&dest) == 10.0);
1449   fail_unless (gst_value_get_double_range_max (&dest) == 20.0);
1450   g_value_unset (&dest);
1451   g_value_unset (&src1);
1452   g_value_unset (&src2);
1453
1454   /* case 3, valid set */
1455   g_value_init (&src1, G_TYPE_DOUBLE);
1456   g_value_set_double (&src1, 0.0);
1457   g_value_init (&src2, GST_TYPE_DOUBLE_RANGE);
1458   gst_value_set_double_range (&src2, 10.0, 20.0);
1459   ret = gst_value_subtract (&dest, &src1, &src2);
1460   fail_unless (ret == TRUE);
1461   fail_unless (G_VALUE_HOLDS_DOUBLE (&dest) == TRUE);
1462   fail_unless (gst_value_compare (&dest, &src1) == GST_VALUE_EQUAL);
1463   g_value_unset (&dest);
1464
1465   /* and the other way around, should keep the range. */
1466   ret = gst_value_subtract (&dest, &src2, &src1);
1467   fail_unless (ret == TRUE);
1468   fail_unless (GST_VALUE_HOLDS_DOUBLE_RANGE (&dest) == TRUE);
1469   fail_unless (gst_value_get_double_range_min (&dest) == 10.0);
1470   fail_unless (gst_value_get_double_range_max (&dest) == 20.0);
1471   g_value_unset (&dest);
1472   g_value_unset (&src1);
1473   g_value_unset (&src2);
1474
1475   /*  double_range <-> double_range
1476    */
1477
1478   /* Check equality */
1479   g_value_init (&src1, GST_TYPE_DOUBLE_RANGE);
1480   gst_value_set_double_range (&src1, 10.0, 20.0);
1481   g_value_init (&src2, GST_TYPE_DOUBLE_RANGE);
1482   gst_value_set_double_range (&src2, 10.0, 15.0);
1483   /* They are not equal (higher bound is different */
1484   fail_if (gst_value_compare (&src1, &src2) == GST_VALUE_EQUAL);
1485   g_value_unset (&src1);
1486   /* They are not equal (lower bound is different */
1487   g_value_init (&src1, GST_TYPE_DOUBLE_RANGE);
1488   gst_value_set_double_range (&src1, 5.0, 15.0);
1489   fail_if (gst_value_compare (&src1, &src2) == GST_VALUE_EQUAL);
1490   g_value_unset (&src1);
1491   /* And finally check equality */
1492   g_value_init (&src1, GST_TYPE_DOUBLE_RANGE);
1493   gst_value_set_double_range (&src1, 10.0, 15.0);
1494   fail_unless (gst_value_compare (&src1, &src2) == GST_VALUE_EQUAL);
1495   g_value_unset (&src1);
1496   g_value_unset (&src2);
1497
1498   /* same range, empty set */
1499   g_value_init (&src1, GST_TYPE_DOUBLE_RANGE);
1500   gst_value_set_double_range (&src1, 10.0, 20.0);
1501   g_value_init (&src2, GST_TYPE_DOUBLE_RANGE);
1502   gst_value_set_double_range (&src2, 10.0, 20.0);
1503   ret = gst_value_subtract (&dest, &src1, &src2);
1504   fail_unless (ret == FALSE);
1505   ret = gst_value_subtract (&dest, &src2, &src1);
1506   fail_unless (ret == FALSE);
1507   g_value_unset (&src1);
1508   g_value_unset (&src2);
1509
1510   /* non overlapping ranges */
1511   g_value_init (&src1, GST_TYPE_DOUBLE_RANGE);
1512   gst_value_set_double_range (&src1, 10.0, 20.0);
1513   g_value_init (&src2, GST_TYPE_DOUBLE_RANGE);
1514   gst_value_set_double_range (&src2, 30.0, 40.0);
1515   ret = gst_value_subtract (&dest, &src1, &src2);
1516   fail_unless (ret == TRUE);
1517   fail_unless (GST_VALUE_HOLDS_DOUBLE_RANGE (&dest) == TRUE);
1518   fail_unless (gst_value_get_double_range_min (&dest) == 10.0);
1519   fail_unless (gst_value_get_double_range_max (&dest) == 20.0);
1520   g_value_unset (&dest);
1521   /* the other way */
1522   ret = gst_value_subtract (&dest, &src2, &src1);
1523   fail_unless (ret == TRUE);
1524   fail_unless (GST_VALUE_HOLDS_DOUBLE_RANGE (&dest) == TRUE);
1525   fail_unless (gst_value_get_double_range_min (&dest) == 30.0);
1526   fail_unless (gst_value_get_double_range_max (&dest) == 40.0);
1527   g_value_unset (&dest);
1528   g_value_unset (&src1);
1529   g_value_unset (&src2);
1530
1531   /* completely overlapping ranges */
1532   g_value_init (&src1, GST_TYPE_DOUBLE_RANGE);
1533   gst_value_set_double_range (&src1, 10.0, 20.0);
1534   g_value_init (&src2, GST_TYPE_DOUBLE_RANGE);
1535   gst_value_set_double_range (&src2, 10.0, 30.0);
1536   ret = gst_value_subtract (&dest, &src1, &src2);
1537   fail_unless (ret == FALSE);
1538   /* the other way */
1539   ret = gst_value_subtract (&dest, &src2, &src1);
1540   fail_unless (ret == TRUE);
1541   fail_unless (GST_VALUE_HOLDS_DOUBLE_RANGE (&dest) == TRUE);
1542   fail_unless (gst_value_get_double_range_min (&dest) == 20.0);
1543   fail_unless (gst_value_get_double_range_max (&dest) == 30.0);
1544   g_value_unset (&dest);
1545   g_value_unset (&src1);
1546   g_value_unset (&src2);
1547
1548   /* partially overlapping ranges */
1549   g_value_init (&src1, GST_TYPE_DOUBLE_RANGE);
1550   gst_value_set_double_range (&src1, 10.0, 20.0);
1551   g_value_init (&src2, GST_TYPE_DOUBLE_RANGE);
1552   gst_value_set_double_range (&src2, 15.0, 30.0);
1553   ret = gst_value_subtract (&dest, &src1, &src2);
1554   fail_unless (ret == TRUE);
1555   fail_unless (GST_VALUE_HOLDS_DOUBLE_RANGE (&dest) == TRUE);
1556   fail_unless (gst_value_get_double_range_min (&dest) == 10.0);
1557   fail_unless (gst_value_get_double_range_max (&dest) == 15.0);
1558   g_value_unset (&dest);
1559   /* the other way */
1560   ret = gst_value_subtract (&dest, &src2, &src1);
1561   fail_unless (ret == TRUE);
1562   fail_unless (GST_VALUE_HOLDS_DOUBLE_RANGE (&dest) == TRUE);
1563   fail_unless (gst_value_get_double_range_min (&dest) == 20.0);
1564   fail_unless (gst_value_get_double_range_max (&dest) == 30.0);
1565   g_value_unset (&dest);
1566   g_value_unset (&src1);
1567   g_value_unset (&src2);
1568
1569   /* create a hole { double_range, double_range } */
1570   g_value_init (&src1, GST_TYPE_DOUBLE_RANGE);
1571   gst_value_set_double_range (&src1, 10.0, 30.0);
1572   g_value_init (&src2, GST_TYPE_DOUBLE_RANGE);
1573   gst_value_set_double_range (&src2, 15.0, 20.0);
1574   ret = gst_value_subtract (&dest, &src1, &src2);
1575   fail_unless (ret == TRUE);
1576   fail_unless (GST_VALUE_HOLDS_LIST (&dest) == TRUE);
1577   tmp = gst_value_list_get_value (&dest, 0);
1578   fail_unless (GST_VALUE_HOLDS_DOUBLE_RANGE (tmp) == TRUE);
1579   fail_unless (gst_value_get_double_range_min (tmp) == 10.0);
1580   fail_unless (gst_value_get_double_range_max (tmp) == 15.0);
1581   tmp = gst_value_list_get_value (&dest, 1);
1582   fail_unless (GST_VALUE_HOLDS_DOUBLE_RANGE (tmp) == TRUE);
1583   fail_unless (gst_value_get_double_range_min (tmp) == 20.0);
1584   fail_unless (gst_value_get_double_range_max (tmp) == 30.0);
1585   g_value_unset (&dest);
1586   /* the other way */
1587   ret = gst_value_subtract (&dest, &src2, &src1);
1588   fail_unless (ret == FALSE);
1589   g_value_unset (&src1);
1590   g_value_unset (&src2);
1591 }
1592
1593 GST_END_TEST;
1594
1595 /* Test arithmetic subtraction of fractions */
1596 GST_START_TEST (test_value_subtract_fraction)
1597 {
1598   GValue result = { 0 };
1599   GValue src1 = { 0 };
1600   GValue src2 = { 0 };
1601
1602   /* Subtract 1/4 from 1/2 */
1603   g_value_init (&src1, GST_TYPE_FRACTION);
1604   g_value_init (&src2, GST_TYPE_FRACTION);
1605   g_value_init (&result, GST_TYPE_FRACTION);
1606   gst_value_set_fraction (&src1, 1, 2);
1607   gst_value_set_fraction (&src2, 1, 4);
1608   fail_unless (gst_value_fraction_subtract (&result, &src1, &src2) == TRUE);
1609   fail_unless (gst_value_get_fraction_numerator (&result) == 1);
1610   fail_unless (gst_value_get_fraction_denominator (&result) == 4);
1611
1612   g_value_unset (&src1);
1613   g_value_unset (&src2);
1614   g_value_unset (&result);
1615
1616   /* Subtract 1/12 from 7/8 */
1617   g_value_init (&src1, GST_TYPE_FRACTION);
1618   g_value_init (&src2, GST_TYPE_FRACTION);
1619   g_value_init (&result, GST_TYPE_FRACTION);
1620   gst_value_set_fraction (&src1, 7, 8);
1621   gst_value_set_fraction (&src2, 1, 12);
1622   fail_unless (gst_value_fraction_subtract (&result, &src1, &src2) == TRUE);
1623   fail_unless (gst_value_get_fraction_numerator (&result) == 19);
1624   fail_unless (gst_value_get_fraction_denominator (&result) == 24);
1625
1626   g_value_unset (&src1);
1627   g_value_unset (&src2);
1628   g_value_unset (&result);
1629
1630   /* Subtract 12/13 from 4/3 */
1631   g_value_init (&src1, GST_TYPE_FRACTION);
1632   g_value_init (&src2, GST_TYPE_FRACTION);
1633   g_value_init (&result, GST_TYPE_FRACTION);
1634   gst_value_set_fraction (&src1, 4, 3);
1635   gst_value_set_fraction (&src2, 12, 13);
1636   fail_unless (gst_value_fraction_subtract (&result, &src1, &src2) == TRUE);
1637   fail_unless (gst_value_get_fraction_numerator (&result) == 16);
1638   fail_unless (gst_value_get_fraction_denominator (&result) == 39);
1639
1640   g_value_unset (&src1);
1641   g_value_unset (&src2);
1642   g_value_unset (&result);
1643
1644   /* Subtract 1/12 from 7/8 */
1645 }
1646
1647 GST_END_TEST;
1648
1649 /* Test set subtraction operations on fraction ranges */
1650 GST_START_TEST (test_value_subtract_fraction_range)
1651 {
1652   GValue dest = { 0 };
1653   GValue src1 = { 0 };
1654   GValue src2 = { 0 };
1655   GValue cmp = { 0 };
1656   const GValue *tmp;
1657   gboolean ret;
1658
1659   /* Value for tests */
1660   g_value_init (&cmp, GST_TYPE_FRACTION);
1661
1662   /*  fraction <-> fraction
1663    */
1664   g_value_init (&src1, GST_TYPE_FRACTION);
1665   gst_value_set_fraction (&src1, 10, 1);
1666   g_value_init (&src2, GST_TYPE_FRACTION);
1667   gst_value_set_fraction (&src2, 20, 1);
1668   gst_value_set_fraction (&src1, 10, 1);
1669
1670   /* subtract as in sets, result is 10 */
1671   ret = gst_value_subtract (&dest, &src1, &src2);
1672   fail_unless (ret == TRUE);
1673   fail_unless (gst_value_compare (&dest, &src1) == GST_VALUE_EQUAL);
1674   g_value_unset (&dest);
1675
1676   /* same values, yields empty set */
1677   ret = gst_value_subtract (&dest, &src1, &src1);
1678   fail_unless (ret == FALSE);
1679   g_value_unset (&src1);
1680   g_value_unset (&src2);
1681
1682   /*  fraction <-> fraction_range
1683    */
1684
1685   /* would yield an empty set */
1686   g_value_init (&src1, GST_TYPE_FRACTION);
1687   gst_value_set_fraction (&src1, 10, 1);
1688   g_value_init (&src2, GST_TYPE_FRACTION_RANGE);
1689   gst_value_set_fraction_range_full (&src2, 0, 1, 20, 1);
1690   ret = gst_value_subtract (&dest, &src1, &src2);
1691   fail_unless (ret == FALSE);
1692
1693   /* and the other way around, we cannot create open ranges
1694    * so the result is the range again */
1695   ret = gst_value_subtract (&dest, &src2, &src1);
1696   fail_unless (ret == TRUE);
1697   fail_unless (GST_VALUE_HOLDS_FRACTION_RANGE (&dest) == TRUE);
1698   gst_value_set_fraction (&cmp, 0, 1);
1699   fail_unless (gst_value_compare (gst_value_get_fraction_range_min (&dest),
1700           &cmp) == GST_VALUE_EQUAL);
1701   gst_value_set_fraction (&cmp, 20, 1);
1702   fail_unless (gst_value_compare (gst_value_get_fraction_range_max (&dest),
1703           &cmp) == GST_VALUE_EQUAL);
1704   g_value_unset (&dest);
1705   g_value_unset (&src1);
1706   g_value_unset (&src2);
1707
1708   /* border case 1, empty set */
1709   g_value_init (&src1, GST_TYPE_FRACTION);
1710   gst_value_set_fraction (&src1, 10, 1);
1711   g_value_init (&src2, GST_TYPE_FRACTION_RANGE);
1712   gst_value_set_fraction_range_full (&src2, 10, 1, 20, 1);
1713   ret = gst_value_subtract (&dest, &src1, &src2);
1714   fail_unless (ret == FALSE);
1715
1716   /* and the other way around, should keep same range as
1717    * we don't have open ranges. */
1718   ret = gst_value_subtract (&dest, &src2, &src1);
1719   fail_unless (ret == TRUE);
1720   fail_unless (GST_VALUE_HOLDS_FRACTION_RANGE (&dest) == TRUE);
1721   gst_value_set_fraction (&cmp, 10, 1);
1722   fail_unless (gst_value_compare (gst_value_get_fraction_range_min (&dest),
1723           &cmp) == GST_VALUE_EQUAL);
1724   gst_value_set_fraction (&cmp, 20, 1);
1725   fail_unless (gst_value_compare (gst_value_get_fraction_range_max (&dest),
1726           &cmp) == GST_VALUE_EQUAL);
1727   g_value_unset (&dest);
1728   g_value_unset (&src1);
1729   g_value_unset (&src2);
1730
1731   /* case 2, valid set */
1732   g_value_init (&src1, GST_TYPE_FRACTION);
1733   gst_value_set_fraction (&src1, 0, 1);
1734   g_value_init (&src2, GST_TYPE_FRACTION_RANGE);
1735   gst_value_set_fraction_range_full (&src2, 10, 1, 20, 1);
1736   ret = gst_value_subtract (&dest, &src1, &src2);
1737   fail_unless (ret == TRUE);
1738   fail_unless (GST_VALUE_HOLDS_FRACTION (&dest) == TRUE);
1739   fail_unless (gst_value_compare (&dest, &src1) == GST_VALUE_EQUAL);
1740   g_value_unset (&dest);
1741
1742   /* and the other way around, should keep the range. */
1743   ret = gst_value_subtract (&dest, &src2, &src1);
1744   fail_unless (ret == TRUE);
1745   fail_unless (GST_VALUE_HOLDS_FRACTION_RANGE (&dest) == TRUE);
1746   fail_unless (gst_value_compare (&dest, &src2) == GST_VALUE_EQUAL);
1747   g_value_unset (&dest);
1748   g_value_unset (&src1);
1749   g_value_unset (&src2);
1750
1751   /*  fraction_range <-> fraction_range
1752    */
1753
1754   /* same range, empty set */
1755   g_value_init (&src1, GST_TYPE_FRACTION_RANGE);
1756   gst_value_set_fraction_range_full (&src1, 10, 2, 20, 2);
1757   g_value_init (&src2, GST_TYPE_FRACTION_RANGE);
1758   gst_value_set_fraction_range_full (&src2, 10, 2, 20, 2);
1759   ret = gst_value_subtract (&dest, &src1, &src2);
1760   fail_unless (ret == FALSE);
1761   ret = gst_value_subtract (&dest, &src2, &src1);
1762   fail_unless (ret == FALSE);
1763   g_value_unset (&src1);
1764   g_value_unset (&src2);
1765
1766   /* non overlapping ranges */
1767   g_value_init (&src1, GST_TYPE_FRACTION_RANGE);
1768   gst_value_set_fraction_range_full (&src1, 10, 2, 10, 1);
1769   g_value_init (&src2, GST_TYPE_FRACTION_RANGE);
1770   gst_value_set_fraction_range_full (&src2, 30, 2, 40, 2);
1771   ret = gst_value_subtract (&dest, &src1, &src2);
1772   fail_unless (ret == TRUE);
1773   fail_unless (GST_VALUE_HOLDS_FRACTION_RANGE (&dest) == TRUE);
1774   gst_value_set_fraction (&cmp, 5, 1);
1775   fail_unless (gst_value_compare (gst_value_get_fraction_range_min (&dest),
1776           &cmp) == GST_VALUE_EQUAL);
1777   gst_value_set_fraction (&cmp, 10, 1);
1778   fail_unless (gst_value_compare (gst_value_get_fraction_range_max (&dest),
1779           &cmp) == GST_VALUE_EQUAL);
1780
1781   g_value_unset (&dest);
1782   /* the other way */
1783   ret = gst_value_subtract (&dest, &src2, &src1);
1784   fail_unless (ret == TRUE);
1785   fail_unless (GST_VALUE_HOLDS_FRACTION_RANGE (&dest) == TRUE);
1786   gst_value_set_fraction (&cmp, 15, 1);
1787   fail_unless (gst_value_compare (gst_value_get_fraction_range_min (&dest),
1788           &cmp) == GST_VALUE_EQUAL);
1789   gst_value_set_fraction (&cmp, 20, 1);
1790   fail_unless (gst_value_compare (gst_value_get_fraction_range_max (&dest),
1791           &cmp) == GST_VALUE_EQUAL);
1792   g_value_unset (&dest);
1793   g_value_unset (&src1);
1794   g_value_unset (&src2);
1795
1796   /* completely overlapping ranges */
1797   g_value_init (&src1, GST_TYPE_FRACTION_RANGE);
1798   gst_value_set_fraction_range_full (&src1, 10, 1, 20, 1);
1799   g_value_init (&src2, GST_TYPE_FRACTION_RANGE);
1800   gst_value_set_fraction_range_full (&src2, 10, 1, 30, 1);
1801   ret = gst_value_subtract (&dest, &src1, &src2);
1802   fail_unless (ret == FALSE);
1803   /* the other way */
1804   ret = gst_value_subtract (&dest, &src2, &src1);
1805   fail_unless (ret == TRUE);
1806   fail_unless (GST_VALUE_HOLDS_FRACTION_RANGE (&dest) == TRUE);
1807   gst_value_set_fraction (&cmp, 20, 1);
1808   fail_unless (gst_value_compare (gst_value_get_fraction_range_min (&dest),
1809           &cmp) == GST_VALUE_EQUAL);
1810   gst_value_set_fraction (&cmp, 30, 1);
1811   fail_unless (gst_value_compare (gst_value_get_fraction_range_max (&dest),
1812           &cmp) == GST_VALUE_EQUAL);
1813   g_value_unset (&dest);
1814   g_value_unset (&src1);
1815   g_value_unset (&src2);
1816
1817   /* partially overlapping ranges */
1818   g_value_init (&src1, GST_TYPE_FRACTION_RANGE);
1819   gst_value_set_fraction_range_full (&src1, 10, 1, 20, 1);
1820   g_value_init (&src2, GST_TYPE_FRACTION_RANGE);
1821   gst_value_set_fraction_range_full (&src2, 15, 1, 30, 1);
1822   ret = gst_value_subtract (&dest, &src1, &src2);
1823   fail_unless (ret == TRUE);
1824   fail_unless (GST_VALUE_HOLDS_FRACTION_RANGE (&dest) == TRUE);
1825   gst_value_set_fraction (&cmp, 10, 1);
1826   fail_unless (gst_value_compare (gst_value_get_fraction_range_min (&dest),
1827           &cmp) == GST_VALUE_EQUAL);
1828   gst_value_set_fraction (&cmp, 15, 1);
1829   fail_unless (gst_value_compare (gst_value_get_fraction_range_max (&dest),
1830           &cmp) == GST_VALUE_EQUAL);
1831   g_value_unset (&dest);
1832
1833   /* the other way */
1834   ret = gst_value_subtract (&dest, &src2, &src1);
1835   fail_unless (ret == TRUE);
1836   fail_unless (GST_VALUE_HOLDS_FRACTION_RANGE (&dest) == TRUE);
1837   gst_value_set_fraction (&cmp, 20, 1);
1838   fail_unless (gst_value_compare (gst_value_get_fraction_range_min (&dest),
1839           &cmp) == GST_VALUE_EQUAL);
1840   gst_value_set_fraction (&cmp, 30, 1);
1841   fail_unless (gst_value_compare (gst_value_get_fraction_range_max (&dest),
1842           &cmp) == GST_VALUE_EQUAL);
1843   g_value_unset (&dest);
1844   g_value_unset (&src1);
1845   g_value_unset (&src2);
1846
1847   /* create a hole { double_range, double_range } */
1848   g_value_init (&src1, GST_TYPE_FRACTION_RANGE);
1849   gst_value_set_fraction_range_full (&src1, 10, 1, 30, 1);
1850   g_value_init (&src2, GST_TYPE_FRACTION_RANGE);
1851   gst_value_set_fraction_range_full (&src2, 15, 1, 20, 1);
1852   ret = gst_value_subtract (&dest, &src1, &src2);
1853   fail_unless (ret == TRUE);
1854   fail_unless (GST_VALUE_HOLDS_LIST (&dest) == TRUE);
1855   /* 1st list entry */
1856   tmp = gst_value_list_get_value (&dest, 0);
1857   fail_unless (GST_VALUE_HOLDS_FRACTION_RANGE (tmp) == TRUE);
1858   gst_value_set_fraction (&cmp, 10, 1);
1859   fail_unless (gst_value_compare (gst_value_get_fraction_range_min (tmp),
1860           &cmp) == GST_VALUE_EQUAL);
1861   gst_value_set_fraction (&cmp, 15, 1);
1862   fail_unless (gst_value_compare (gst_value_get_fraction_range_max (tmp),
1863           &cmp) == GST_VALUE_EQUAL);
1864   /* 2nd list entry */
1865   tmp = gst_value_list_get_value (&dest, 1);
1866   fail_unless (GST_VALUE_HOLDS_FRACTION_RANGE (tmp) == TRUE);
1867   gst_value_set_fraction (&cmp, 20, 1);
1868   fail_unless (gst_value_compare (gst_value_get_fraction_range_min (tmp),
1869           &cmp) == GST_VALUE_EQUAL);
1870   gst_value_set_fraction (&cmp, 30, 1);
1871   fail_unless (gst_value_compare (gst_value_get_fraction_range_max (tmp),
1872           &cmp) == GST_VALUE_EQUAL);
1873   g_value_unset (&dest);
1874   /* the other way */
1875   ret = gst_value_subtract (&dest, &src2, &src1);
1876   fail_unless (ret == FALSE);
1877   g_value_unset (&src1);
1878   g_value_unset (&src2);
1879
1880   g_value_unset (&cmp);
1881 }
1882
1883 GST_END_TEST;
1884
1885 /* Test set subtraction operations on fraction lists */
1886 GST_START_TEST (test_value_subtract_fraction_list)
1887 {
1888   GValue list1 = { 0 };
1889   GValue list2 = { 0 };
1890   GValue val1 = { 0 };
1891   GValue val2 = { 0 };
1892   GValue tmp = { 0 };
1893   gboolean ret;
1894
1895   g_value_init (&list1, GST_TYPE_LIST);
1896   g_value_init (&val1, GST_TYPE_FRACTION);
1897   gst_value_set_fraction (&val1, 15, 2);
1898   gst_value_list_append_value (&list1, &val1);
1899   g_value_init (&tmp, GST_TYPE_FRACTION);
1900   gst_value_set_fraction (&tmp, 5, 1);
1901   gst_value_list_append_value (&list1, &tmp);
1902   g_value_unset (&tmp);
1903
1904   g_value_init (&list2, GST_TYPE_LIST);
1905   g_value_init (&val2, GST_TYPE_FRACTION);
1906   gst_value_set_fraction (&val2, 15, 1);
1907   gst_value_list_append_value (&list2, &val2);
1908   g_value_init (&tmp, GST_TYPE_FRACTION);
1909   gst_value_set_fraction (&tmp, 5, 1);
1910   gst_value_list_append_value (&list2, &tmp);
1911   g_value_unset (&tmp);
1912
1913   /* should subtract all common elements */
1914   ret = gst_value_subtract (&tmp, &list1, &list2);
1915   fail_unless (ret == TRUE);
1916   fail_unless (gst_value_compare (&tmp, &val1) == GST_VALUE_EQUAL);
1917   g_value_unset (&val1);
1918   g_value_unset (&tmp);
1919
1920   ret = gst_value_subtract (&tmp, &list2, &list1);
1921   fail_unless (ret == TRUE);
1922   fail_unless (gst_value_compare (&tmp, &val2) == GST_VALUE_EQUAL);
1923   g_value_unset (&val2);
1924   g_value_unset (&tmp);
1925
1926   g_value_unset (&list1);
1927   g_value_unset (&list2);
1928 }
1929
1930 GST_END_TEST;
1931
1932 GST_START_TEST (test_date)
1933 {
1934   GstStructure *s;
1935   GDate *date, *date2;
1936   gchar *str;
1937
1938   date = g_date_new_dmy (22, 9, 2005);
1939
1940   s = gst_structure_new ("media/x-type", "SOME_DATE_TAG", G_TYPE_DATE,
1941       date, NULL);
1942
1943   fail_unless (gst_structure_has_field_typed (s, "SOME_DATE_TAG", G_TYPE_DATE));
1944   fail_unless (gst_structure_get_date (s, "SOME_DATE_TAG", &date2));
1945   fail_unless (date2 != NULL);
1946   fail_unless (g_date_valid (date2));
1947   fail_unless (g_date_compare (date, date2) == 0);
1948
1949   g_date_free (date);
1950   g_date_free (date2);
1951   date = NULL;
1952   date2 = NULL;
1953
1954   str = gst_structure_to_string (s);
1955   gst_structure_free (s);
1956   s = NULL;
1957
1958   fail_unless (g_str_equal (str,
1959           "media/x-type, SOME_DATE_TAG=(date)2005-09-22;"));
1960
1961   s = gst_structure_from_string (str, NULL);
1962   g_free (str);
1963   str = NULL;
1964
1965   fail_unless (s != NULL);
1966   fail_unless (gst_structure_has_name (s, "media/x-type"));
1967   fail_unless (gst_structure_has_field_typed (s, "SOME_DATE_TAG", G_TYPE_DATE));
1968   fail_unless (gst_structure_get_date (s, "SOME_DATE_TAG", &date));
1969   fail_unless (date != NULL);
1970   fail_unless (g_date_valid (date));
1971   fail_unless (g_date_get_day (date) == 22);
1972   fail_unless (g_date_get_month (date) == 9);
1973   fail_unless (g_date_get_year (date) == 2005);
1974   g_date_free (date);
1975   date = NULL;
1976
1977   str = gst_structure_to_string (s);
1978   gst_structure_free (s);
1979   s = NULL;
1980
1981   fail_unless (g_str_equal (str,
1982           "media/x-type, SOME_DATE_TAG=(date)2005-09-22;"));
1983   g_free (str);
1984   str = NULL;
1985 }
1986
1987 GST_END_TEST;
1988
1989 static gboolean
1990 date_time_equal (GstDateTime * a, GstDateTime * b)
1991 {
1992   if (gst_date_time_get_year (a) != gst_date_time_get_year (b) ||
1993       gst_date_time_get_month (a) != gst_date_time_get_month (b) ||
1994       gst_date_time_get_day (a) != gst_date_time_get_day (b))
1995     return FALSE;
1996
1997   if (gst_date_time_get_hour (a) != gst_date_time_get_hour (b) ||
1998       gst_date_time_get_minute (a) != gst_date_time_get_minute (b) ||
1999       gst_date_time_get_second (a) != gst_date_time_get_second (b) ||
2000       gst_date_time_get_microsecond (a) != gst_date_time_get_microsecond (b))
2001     return FALSE;
2002
2003   if (gst_date_time_get_time_zone_offset (a) !=
2004       gst_date_time_get_time_zone_offset (b))
2005     return FALSE;
2006
2007   return TRUE;
2008 }
2009
2010 GST_START_TEST (test_date_time)
2011 {
2012   GstStructure *s;
2013   GstDateTime *datetime, *datetime2;
2014   GValue val = { 0, };
2015   gchar *str;
2016
2017   /* utc timezone */
2018   datetime = gst_date_time_new (0, 2010, 6, 23, 7, 40, 10);
2019
2020   s = gst_structure_new ("media/x-type", "SOME_DATE_TIME_TAG",
2021       GST_TYPE_DATE_TIME, datetime, NULL);
2022
2023   fail_unless (gst_structure_has_field_typed (s, "SOME_DATE_TIME_TAG",
2024           GST_TYPE_DATE_TIME));
2025   fail_unless (gst_structure_get_date_time (s, "SOME_DATE_TIME_TAG",
2026           &datetime2));
2027   fail_unless (datetime2 != NULL);
2028   fail_unless (date_time_equal (datetime, datetime2));
2029
2030   gst_date_time_unref (datetime);
2031   gst_date_time_unref (datetime2);
2032   datetime = NULL;
2033   datetime2 = NULL;
2034
2035   str = gst_structure_to_string (s);
2036   gst_structure_free (s);
2037   s = NULL;
2038
2039   fail_unless_equals_string (str,
2040       "media/x-type, SOME_DATE_TIME_TAG=(datetime)2010-06-23T07:40:10Z;");
2041
2042   s = gst_structure_from_string (str, NULL);
2043   g_free (str);
2044   str = NULL;
2045
2046   fail_unless (s != NULL);
2047   fail_unless (gst_structure_has_name (s, "media/x-type"));
2048   fail_unless (gst_structure_has_field_typed (s, "SOME_DATE_TIME_TAG",
2049           GST_TYPE_DATE_TIME));
2050   fail_unless (gst_structure_get_date_time (s, "SOME_DATE_TIME_TAG",
2051           &datetime));
2052   fail_unless (datetime != NULL);
2053   fail_unless (gst_date_time_get_year (datetime) == 2010);
2054   fail_unless (gst_date_time_get_month (datetime) == 6);
2055   fail_unless (gst_date_time_get_day (datetime) == 23);
2056   fail_unless (gst_date_time_get_hour (datetime) == 7);
2057   fail_unless (gst_date_time_get_minute (datetime) == 40);
2058   fail_unless (gst_date_time_get_second (datetime) == 10);
2059   fail_unless (gst_date_time_get_microsecond (datetime) == 0);
2060   fail_unless (gst_date_time_get_time_zone_offset (datetime) == 0);
2061   gst_date_time_unref (datetime);
2062   datetime = NULL;
2063
2064   str = gst_structure_to_string (s);
2065   gst_structure_free (s);
2066   s = NULL;
2067
2068   fail_unless_equals_string (str,
2069       "media/x-type, SOME_DATE_TIME_TAG=(datetime)2010-06-23T07:40:10Z;");
2070   g_free (str);
2071   str = NULL;
2072
2073   /* with timezone */
2074   datetime = gst_date_time_new (-3.0, 2010, 6, 23, 7, 40, 10.000001);
2075
2076   s = gst_structure_new ("media/x-type", "SOME_DATE_TIME_TAG",
2077       GST_TYPE_DATE_TIME, datetime, NULL);
2078
2079   fail_unless (gst_structure_has_field_typed (s, "SOME_DATE_TIME_TAG",
2080           GST_TYPE_DATE_TIME));
2081   fail_unless (gst_structure_get_date_time (s, "SOME_DATE_TIME_TAG",
2082           &datetime2));
2083   fail_unless (datetime2 != NULL);
2084   fail_unless (date_time_equal (datetime, datetime2));
2085
2086   gst_date_time_unref (datetime);
2087   gst_date_time_unref (datetime2);
2088   datetime = NULL;
2089   datetime2 = NULL;
2090
2091   str = gst_structure_to_string (s);
2092   gst_structure_free (s);
2093   s = NULL;
2094
2095   fail_unless_equals_string (str,
2096       "media/x-type, SOME_DATE_TIME_TAG=(datetime)2010-06-23T07:40:10.000001-0300;");
2097
2098   s = gst_structure_from_string (str, NULL);
2099   g_free (str);
2100   str = NULL;
2101
2102   fail_unless (s != NULL);
2103   fail_unless (gst_structure_has_name (s, "media/x-type"));
2104   fail_unless (gst_structure_has_field_typed (s, "SOME_DATE_TIME_TAG",
2105           GST_TYPE_DATE_TIME));
2106   fail_unless (gst_structure_get_date_time (s, "SOME_DATE_TIME_TAG",
2107           &datetime));
2108   fail_unless (datetime != NULL);
2109   fail_unless (gst_date_time_get_year (datetime) == 2010);
2110   fail_unless (gst_date_time_get_month (datetime) == 6);
2111   fail_unless (gst_date_time_get_day (datetime) == 23);
2112   fail_unless (gst_date_time_get_hour (datetime) == 7);
2113   fail_unless (gst_date_time_get_minute (datetime) == 40);
2114   fail_unless (gst_date_time_get_second (datetime) == 10);
2115   fail_unless (gst_date_time_get_microsecond (datetime) == 1);
2116   fail_unless (gst_date_time_get_time_zone_offset (datetime) == -3);
2117   gst_date_time_unref (datetime);
2118   datetime = NULL;
2119
2120   str = gst_structure_to_string (s);
2121   gst_structure_free (s);
2122   s = NULL;
2123   fail_unless_equals_string (str,
2124       "media/x-type, SOME_DATE_TIME_TAG=(datetime)2010-06-23T07:40:10.000001-0300;");
2125
2126   g_free (str);
2127   str = NULL;
2128
2129   /* with positive timezone */
2130   datetime = gst_date_time_new (2.0, 2010, 6, 23, 7, 40, 10.000001);
2131
2132   s = gst_structure_new ("media/x-type", "SOME_DATE_TIME_TAG",
2133       GST_TYPE_DATE_TIME, datetime, NULL);
2134
2135   fail_unless (gst_structure_has_field_typed (s, "SOME_DATE_TIME_TAG",
2136           GST_TYPE_DATE_TIME));
2137   fail_unless (gst_structure_get_date_time (s, "SOME_DATE_TIME_TAG",
2138           &datetime2));
2139   fail_unless (datetime2 != NULL);
2140   fail_unless (date_time_equal (datetime, datetime2));
2141
2142   gst_date_time_unref (datetime);
2143   gst_date_time_unref (datetime2);
2144   datetime = NULL;
2145   datetime2 = NULL;
2146
2147   str = gst_structure_to_string (s);
2148   gst_structure_free (s);
2149   s = NULL;
2150
2151   fail_unless_equals_string (str,
2152       "media/x-type, SOME_DATE_TIME_TAG=(datetime)2010-06-23T07:40:10.000001+0200;");
2153
2154   s = gst_structure_from_string (str, NULL);
2155   g_free (str);
2156   str = NULL;
2157
2158   fail_unless (s != NULL);
2159   fail_unless (gst_structure_has_name (s, "media/x-type"));
2160   fail_unless (gst_structure_has_field_typed (s, "SOME_DATE_TIME_TAG",
2161           GST_TYPE_DATE_TIME));
2162   fail_unless (gst_structure_get_date_time (s, "SOME_DATE_TIME_TAG",
2163           &datetime));
2164   fail_unless (datetime != NULL);
2165   fail_unless (gst_date_time_get_year (datetime) == 2010);
2166   fail_unless (gst_date_time_get_month (datetime) == 6);
2167   fail_unless (gst_date_time_get_day (datetime) == 23);
2168   fail_unless (gst_date_time_get_hour (datetime) == 7);
2169   fail_unless (gst_date_time_get_minute (datetime) == 40);
2170   fail_unless (gst_date_time_get_second (datetime) == 10);
2171   fail_unless (gst_date_time_get_microsecond (datetime) == 1);
2172   fail_unless (gst_date_time_get_time_zone_offset (datetime) == 2);
2173   gst_date_time_unref (datetime);
2174   datetime = NULL;
2175
2176   str = gst_structure_to_string (s);
2177   gst_structure_free (s);
2178   s = NULL;
2179   fail_unless_equals_string (str,
2180       "media/x-type, SOME_DATE_TIME_TAG=(datetime)2010-06-23T07:40:10.000001+0200;");
2181
2182   g_free (str);
2183   str = NULL;
2184
2185   /* test partial dates */
2186   datetime = gst_date_time_new (0.0, 2010, -1, -1, -1, -1, -1.0);
2187   g_value_init (&val, GST_TYPE_DATE_TIME);
2188   g_value_take_boxed (&val, datetime);
2189   str = gst_value_serialize (&val);
2190   g_value_reset (&val);
2191   fail_unless_equals_string (str, "2010");
2192   fail_unless (gst_value_deserialize (&val, str));
2193   datetime = g_value_get_boxed (&val);
2194   fail_if (!gst_date_time_has_year (datetime));
2195   fail_if (gst_date_time_has_month (datetime));
2196   fail_if (gst_date_time_has_day (datetime));
2197   fail_if (gst_date_time_has_time (datetime));
2198   g_value_unset (&val);
2199   g_free (str);
2200
2201   datetime = gst_date_time_new (0.0, 2010, 9, -1, -1, -1, -1.0);
2202   g_value_init (&val, GST_TYPE_DATE_TIME);
2203   g_value_take_boxed (&val, datetime);
2204   str = gst_value_serialize (&val);
2205   g_value_reset (&val);
2206   fail_unless_equals_string (str, "2010-09");
2207   fail_unless (gst_value_deserialize (&val, str));
2208   datetime = g_value_get_boxed (&val);
2209   fail_if (!gst_date_time_has_year (datetime));
2210   fail_if (!gst_date_time_has_month (datetime));
2211   fail_if (gst_date_time_has_day (datetime));
2212   fail_if (gst_date_time_has_time (datetime));
2213   g_value_unset (&val);
2214   g_free (str);
2215
2216   datetime = gst_date_time_new (0.0, 1983, 11, 30, -1, -1, -1.0);
2217   g_value_init (&val, GST_TYPE_DATE_TIME);
2218   g_value_take_boxed (&val, datetime);
2219   str = gst_value_serialize (&val);
2220   g_value_reset (&val);
2221   fail_unless_equals_string (str, "1983-11-30");
2222   fail_unless (gst_value_deserialize (&val, str));
2223   datetime = g_value_get_boxed (&val);
2224   fail_if (!gst_date_time_has_year (datetime));
2225   fail_if (!gst_date_time_has_month (datetime));
2226   fail_if (!gst_date_time_has_day (datetime));
2227   fail_if (gst_date_time_has_time (datetime));
2228   g_value_unset (&val);
2229   g_free (str);
2230
2231   datetime = gst_date_time_new (0.0, 1983, 11, 30, 3, 52, -1.0);
2232   g_value_init (&val, GST_TYPE_DATE_TIME);
2233   g_value_take_boxed (&val, datetime);
2234   str = gst_value_serialize (&val);
2235   g_value_reset (&val);
2236   fail_unless_equals_string (str, "1983-11-30T03:52Z");
2237   fail_unless (gst_value_deserialize (&val, str));
2238   datetime = g_value_get_boxed (&val);
2239   fail_if (!gst_date_time_has_year (datetime));
2240   fail_if (!gst_date_time_has_month (datetime));
2241   fail_if (!gst_date_time_has_day (datetime));
2242   fail_if (!gst_date_time_has_time (datetime));
2243   fail_if (gst_date_time_has_second (datetime));
2244   fail_unless_equals_float (gst_date_time_get_time_zone_offset (datetime), 0.0);
2245   g_value_unset (&val);
2246   g_free (str);
2247
2248   datetime = gst_date_time_new (-4.5, 1983, 11, 30, 3, 52, -1.0);
2249   g_value_init (&val, GST_TYPE_DATE_TIME);
2250   g_value_take_boxed (&val, datetime);
2251   str = gst_value_serialize (&val);
2252   g_value_reset (&val);
2253   fail_unless_equals_string (str, "1983-11-30T03:52-0430");
2254   fail_unless (gst_value_deserialize (&val, str));
2255   datetime = g_value_get_boxed (&val);
2256   fail_if (!gst_date_time_has_year (datetime));
2257   fail_if (!gst_date_time_has_month (datetime));
2258   fail_if (!gst_date_time_has_day (datetime));
2259   fail_if (!gst_date_time_has_time (datetime));
2260   fail_if (gst_date_time_has_second (datetime));
2261   fail_unless_equals_float (gst_date_time_get_time_zone_offset (datetime),
2262       -4.5);
2263   g_value_unset (&val);
2264   g_free (str);
2265
2266   datetime = gst_date_time_new (4.5, 1983, 11, 30, 14, 52, 9);
2267   g_value_init (&val, GST_TYPE_DATE_TIME);
2268   g_value_take_boxed (&val, datetime);
2269   str = gst_value_serialize (&val);
2270   g_value_reset (&val);
2271   fail_unless_equals_string (str, "1983-11-30T14:52:09+0430");
2272   fail_unless (gst_value_deserialize (&val, str));
2273   datetime = g_value_get_boxed (&val);
2274   fail_if (!gst_date_time_has_year (datetime));
2275   fail_if (!gst_date_time_has_month (datetime));
2276   fail_if (!gst_date_time_has_day (datetime));
2277   fail_if (!gst_date_time_has_time (datetime));
2278   fail_if (!gst_date_time_has_second (datetime));
2279   fail_unless_equals_float (gst_date_time_get_time_zone_offset (datetime), 4.5);
2280   g_value_unset (&val);
2281   g_free (str);
2282
2283   datetime = gst_date_time_new (-4.5, 1983, 11, 30, 14, 52, 9.702);
2284   g_value_init (&val, GST_TYPE_DATE_TIME);
2285   g_value_take_boxed (&val, datetime);
2286   str = gst_value_serialize (&val);
2287   g_value_reset (&val);
2288   fail_unless_equals_string (str, "1983-11-30T14:52:09.702-0430");
2289   fail_unless (gst_value_deserialize (&val, str));
2290   datetime = g_value_get_boxed (&val);
2291   fail_if (!gst_date_time_has_year (datetime));
2292   fail_if (!gst_date_time_has_month (datetime));
2293   fail_if (!gst_date_time_has_day (datetime));
2294   fail_if (!gst_date_time_has_time (datetime));
2295   fail_if (!gst_date_time_has_second (datetime));
2296   fail_unless_equals_float (gst_date_time_get_time_zone_offset (datetime),
2297       -4.5);
2298   g_value_unset (&val);
2299   g_free (str);
2300 }
2301
2302 GST_END_TEST;
2303
2304 GST_START_TEST (test_fraction_range)
2305 {
2306   GValue range = { 0, };
2307   GValue start = { 0, };
2308   GValue end = { 0, };
2309   GValue src = { 0, };
2310   GValue dest = { 0, };
2311   GValue range2 = { 0, };
2312
2313   g_value_init (&range, GST_TYPE_FRACTION_RANGE);
2314   g_value_init (&range2, GST_TYPE_FRACTION_RANGE);
2315   g_value_init (&start, GST_TYPE_FRACTION);
2316   g_value_init (&end, GST_TYPE_FRACTION);
2317   g_value_init (&src, GST_TYPE_FRACTION);
2318
2319   gst_value_set_fraction (&src, 1, 2);
2320
2321   /* Check that a intersection of fraction & range = fraction */
2322   gst_value_set_fraction (&start, 1, 4);
2323   gst_value_set_fraction (&end, 2, 3);
2324   gst_value_set_fraction_range (&range, &start, &end);
2325
2326   fail_unless (gst_value_intersect (&dest, &src, &range) == TRUE);
2327   fail_unless (G_VALUE_TYPE (&dest) == GST_TYPE_FRACTION);
2328   fail_unless (gst_value_compare (&dest, &src) == GST_VALUE_EQUAL);
2329
2330   /* Check that a intersection selects the overlapping range */
2331   gst_value_set_fraction (&start, 1, 3);
2332   gst_value_set_fraction (&end, 2, 3);
2333   gst_value_set_fraction_range (&range2, &start, &end);
2334   g_value_unset (&dest);
2335   fail_unless (gst_value_intersect (&dest, &range, &range2) == TRUE);
2336   fail_unless (G_VALUE_TYPE (&dest) == GST_TYPE_FRACTION_RANGE);
2337
2338   gst_value_set_fraction_range (&range2, &start, &end);
2339   fail_unless (gst_value_compare (&dest, &range2) == GST_VALUE_EQUAL);
2340
2341   /* Check that non intersection ranges don't intersect */
2342   gst_value_set_fraction (&start, 4, 2);
2343   gst_value_set_fraction (&end, 5, 2);
2344   gst_value_set_fraction_range (&range2, &start, &end);
2345   g_value_unset (&dest);
2346   fail_unless (gst_value_intersect (&dest, &range, &range2) == FALSE);
2347
2348   g_value_unset (&start);
2349   g_value_unset (&end);
2350   g_value_unset (&range);
2351   g_value_unset (&range2);
2352   g_value_unset (&src);
2353 }
2354
2355 GST_END_TEST;
2356
2357 GST_START_TEST (test_serialize_deserialize_format_enum)
2358 {
2359   GstStructure *s, *s2;
2360   GstFormat foobar_fmt;
2361   gchar *str, *str2, *end = NULL;
2362
2363   /* make sure custom formats are serialised properly as well */
2364   foobar_fmt = gst_format_register ("foobar", "GST_FORMAT_FOOBAR");
2365   fail_unless (foobar_fmt != GST_FORMAT_UNDEFINED);
2366
2367   s = gst_structure_new ("foo/bar", "format1", GST_TYPE_FORMAT,
2368       GST_FORMAT_BYTES, "format2", GST_TYPE_FORMAT, GST_FORMAT_TIME,
2369       "format3", GST_TYPE_FORMAT, GST_FORMAT_DEFAULT, "format4",
2370       GST_TYPE_FORMAT, foobar_fmt, NULL);
2371
2372   str = gst_structure_to_string (s);
2373   GST_LOG ("Got structure string '%s'", GST_STR_NULL (str));
2374   fail_unless (str != NULL);
2375   fail_unless (strstr (str, "TIME") != NULL);
2376   fail_unless (strstr (str, "BYTE") != NULL);
2377   fail_unless (strstr (str, "DEFAULT") != NULL);
2378   fail_unless (strstr (str, "FOOBAR") != NULL);
2379
2380   s2 = gst_structure_from_string (str, &end);
2381   fail_unless (s2 != NULL);
2382
2383   str2 = gst_structure_to_string (s2);
2384   fail_unless (str2 != NULL);
2385
2386   fail_unless (g_str_equal (str, str2));
2387
2388   g_free (str);
2389   g_free (str2);
2390   gst_structure_free (s);
2391   gst_structure_free (s2);
2392 }
2393
2394 GST_END_TEST;
2395
2396 GST_START_TEST (test_serialize_deserialize_caps)
2397 {
2398   GValue value = { 0 }
2399   , value2 = {
2400   0};
2401   GstCaps *caps, *caps2;
2402   GstCaps *incaps;
2403   gchar *serialized;
2404
2405   incaps = gst_caps_new_simple ("caps/internal",
2406       "in-field", G_TYPE_INT, 20, "in-field2",
2407       G_TYPE_STRING, "some in ternal field", NULL);
2408   caps = gst_caps_new_simple ("test/caps",
2409       "foo", G_TYPE_INT, 10, "bar", G_TYPE_STRING, "test",
2410       "int-caps", GST_TYPE_CAPS, incaps, NULL);
2411   fail_if (GST_CAPS_REFCOUNT_VALUE (caps) != 1);
2412   gst_caps_unref (incaps);
2413
2414   /* and assign caps to gvalue */
2415   g_value_init (&value, GST_TYPE_CAPS);
2416   g_value_take_boxed (&value, caps);
2417   fail_if (GST_CAPS_REFCOUNT_VALUE (caps) != 1);
2418
2419   /* now serialize it */
2420   serialized = gst_value_serialize (&value);
2421   GST_DEBUG ("serialized caps to %s", serialized);
2422   fail_unless (serialized != NULL);
2423
2424   /* refcount should not change */
2425   fail_if (GST_CAPS_REFCOUNT_VALUE (caps) != 1);
2426
2427   /* now deserialize again */
2428   g_value_init (&value2, GST_TYPE_CAPS);
2429   gst_value_deserialize (&value2, serialized);
2430
2431   caps2 = g_value_get_boxed (&value2);
2432   fail_if (GST_CAPS_REFCOUNT_VALUE (caps2) != 1);
2433
2434   /* they should be equal */
2435   fail_unless (gst_caps_is_equal (caps, caps2));
2436
2437   /* cleanup */
2438   g_value_unset (&value);
2439   g_value_unset (&value2);
2440   g_free (serialized);
2441 }
2442
2443 GST_END_TEST;
2444
2445 GST_START_TEST (test_int_range)
2446 {
2447   GValue range = { 0, };
2448   GValue start = { 0, };
2449   GValue end = { 0, };
2450   GValue src = { 0, };
2451   GValue dest = { 0, };
2452   GValue range2 = { 0, };
2453
2454   g_value_init (&range, GST_TYPE_INT_RANGE);
2455   g_value_init (&range2, GST_TYPE_INT_RANGE);
2456   g_value_init (&start, G_TYPE_INT);
2457   g_value_init (&end, G_TYPE_INT);
2458   g_value_init (&src, G_TYPE_INT);
2459
2460   g_value_set_int (&src, 2);
2461
2462   /* Check that a intersection of int & range = int */
2463   gst_value_set_int_range (&range, 1, 5);
2464
2465   fail_unless (gst_value_intersect (&dest, &src, &range) == TRUE);
2466   fail_unless (G_VALUE_TYPE (&dest) == G_TYPE_INT);
2467   fail_unless (gst_value_compare (&dest, &src) == GST_VALUE_EQUAL);
2468
2469   /* Check that a intersection selects the overlapping range */
2470   gst_value_set_int_range (&range2, 2, 3);
2471   g_value_unset (&dest);
2472   fail_unless (gst_value_intersect (&dest, &range, &range2) == TRUE);
2473   fail_unless (G_VALUE_TYPE (&dest) == GST_TYPE_INT_RANGE);
2474
2475   fail_unless (gst_value_compare (&dest, &range2) == GST_VALUE_EQUAL);
2476
2477   /* Check that non intersection ranges don't intersect */
2478   gst_value_set_int_range (&range2, 6, 7);
2479   g_value_unset (&dest);
2480   fail_unless (gst_value_intersect (&dest, &range, &range2) == FALSE);
2481
2482   g_value_unset (&start);
2483   g_value_unset (&end);
2484   g_value_unset (&range);
2485   g_value_unset (&range2);
2486   g_value_unset (&src);
2487 }
2488
2489 GST_END_TEST;
2490
2491 GST_START_TEST (test_int64_range)
2492 {
2493   GValue range = { 0, };
2494   GValue start = { 0, };
2495   GValue end = { 0, };
2496   GValue src = { 0, };
2497   GValue dest = { 0, };
2498   GValue range2 = { 0, };
2499
2500   g_value_init (&range, GST_TYPE_INT64_RANGE);
2501   g_value_init (&range2, GST_TYPE_INT64_RANGE);
2502   g_value_init (&start, G_TYPE_INT64);
2503   g_value_init (&end, G_TYPE_INT64);
2504   g_value_init (&src, G_TYPE_INT64);
2505
2506   g_value_set_int64 (&src, 2);
2507
2508   /* Check that a intersection of int64 & range = int64 */
2509   gst_value_set_int64_range (&range, 1, 5);
2510
2511   fail_unless (gst_value_intersect (&dest, &src, &range) == TRUE);
2512   fail_unless (G_VALUE_TYPE (&dest) == G_TYPE_INT64);
2513   fail_unless (gst_value_compare (&dest, &src) == GST_VALUE_EQUAL);
2514
2515   /* Check that a intersection selects the overlapping range */
2516   gst_value_set_int64_range (&range2, 2, 3);
2517   g_value_unset (&dest);
2518   fail_unless (gst_value_intersect (&dest, &range, &range2) == TRUE);
2519   fail_unless (G_VALUE_TYPE (&dest) == GST_TYPE_INT64_RANGE);
2520
2521   fail_unless (gst_value_compare (&dest, &range2) == GST_VALUE_EQUAL);
2522
2523   /* Check that non intersection ranges don't intersect */
2524   gst_value_set_int64_range (&range2, 6, 7);
2525   g_value_unset (&dest);
2526   fail_unless (gst_value_intersect (&dest, &range, &range2) == FALSE);
2527
2528   g_value_unset (&start);
2529   g_value_unset (&end);
2530   g_value_unset (&range);
2531   g_value_unset (&range2);
2532   g_value_unset (&src);
2533 }
2534
2535 GST_END_TEST;
2536
2537 GST_START_TEST (test_serialize_int64_range)
2538 {
2539   int i = 0;
2540
2541   gint64 int64_ranges[] = {
2542     0, 5,
2543     0, G_MAXINT,
2544     5, G_MAXINT32,
2545     5, G_MAXINT64,
2546   };
2547   gint int64_ranges_size = sizeof (int64_ranges) / sizeof (int64_ranges[0]) / 2;
2548
2549   gchar *int64_range_strings[] = {
2550     g_strdup ("[ 0, 5 ]"),
2551     g_strdup_printf ("[ 0, %" G_GINT64_FORMAT " ]", (gint64) G_MAXINT),
2552     g_strdup_printf ("[ 5, %" G_GINT64_FORMAT " ]", (gint64) G_MAXINT32),
2553     g_strdup_printf ("[ 5, %" G_GINT64_FORMAT " ]", G_MAXINT64),
2554   };
2555   gint int64_range_strings_size =
2556       sizeof (int64_range_strings) / sizeof (int64_range_strings[0]);
2557
2558   fail_unless (int64_ranges_size == int64_range_strings_size);
2559
2560   while (i + 1 < (int64_ranges_size * 2)) {
2561     if ((i + 1) % 2) {
2562       gchar *str;
2563       gchar *str2;
2564       GValue value = { 0 };
2565       const GValue *deserialized_value;
2566       int idx = i / 2;
2567       GstStructure *s;
2568
2569       g_value_init (&value, GST_TYPE_INT64_RANGE);
2570
2571       /* check serialization */
2572       gst_value_set_int64_range (&value, int64_ranges[i], int64_ranges[i + 1]);
2573       str = gst_value_serialize (&value);
2574       fail_unless (strcmp (str, int64_range_strings[idx]) == 0);
2575       g_free (int64_range_strings[idx]);
2576       g_value_unset (&value);
2577
2578       /* now deserialize again to an int64 range */
2579       s = gst_structure_new ("foo/bar", "range", GST_TYPE_INT64_RANGE,
2580           int64_ranges[i], int64_ranges[i + 1], NULL);
2581       deserialized_value = gst_structure_get_value (s, "range");
2582       fail_unless (GST_VALUE_HOLDS_INT64_RANGE (deserialized_value) == TRUE);
2583       str2 = gst_value_serialize (deserialized_value);
2584
2585       fail_unless (gst_value_get_int64_range_min (deserialized_value) ==
2586           int64_ranges[i]);
2587       fail_unless (gst_value_get_int64_range_max (deserialized_value) ==
2588           int64_ranges[i + 1]);
2589
2590       gst_structure_free (s);
2591       g_free (str);
2592       g_free (str2);
2593     }
2594     i++;
2595   }
2596 }
2597
2598 GST_END_TEST;
2599
2600 GST_START_TEST (test_deserialize_int_range)
2601 {
2602   GstStructure *s;
2603   gchar *str, *str2;
2604   gchar *end = NULL;
2605   const GValue *deserialized_value;
2606
2607   /* check a valid int_range deserialization */
2608   str = g_strdup_printf ("foo/bar, range=[ 1, %d ];", G_MAXINT);
2609   s = gst_structure_from_string (str, &end);
2610   fail_unless (*end == '\0');
2611   deserialized_value = gst_structure_get_value (s, "range");
2612   fail_unless (GST_VALUE_HOLDS_INT_RANGE (deserialized_value) == TRUE);
2613   fail_unless (gst_value_get_int_range_min (deserialized_value) == 1);
2614   fail_unless (gst_value_get_int_range_max (deserialized_value) == G_MAXINT);
2615   gst_structure_free (s);
2616   end = NULL;
2617   g_free (str);
2618
2619   /* check invalid int_range deserialization */
2620   str =
2621       g_strdup_printf ("foo/bar, range=[ 1, %" G_GINT64_FORMAT " ];",
2622       (gint64) G_MAXINT + 1);
2623   ASSERT_CRITICAL (s = gst_structure_from_string (str, &end));
2624   g_free (str);
2625   gst_structure_free (s);
2626   str =
2627       g_strdup_printf ("foo/bar, range=[ %" G_GINT64_FORMAT ", %"
2628       G_GINT64_FORMAT " ];", (gint64) G_MAXINT, (gint64) G_MAXINT + 1);
2629   ASSERT_CRITICAL (s = gst_structure_from_string (str, NULL));
2630   end = NULL;
2631   g_free (str);
2632   gst_structure_free (s);
2633
2634   /* check a valid int64_range deserialization. Those ranges need to
2635    * be explicit about their storage type. */
2636   str = g_strdup_printf ("foo/bar, range=(gint64)[ 1, %d ];", G_MAXINT);
2637   s = gst_structure_from_string (str, &end);
2638   fail_unless (*end == '\0');
2639   deserialized_value = gst_structure_get_value (s, "range");
2640   fail_unless (GST_VALUE_HOLDS_INT64_RANGE (deserialized_value) == TRUE);
2641   fail_unless (gst_value_get_int64_range_min (deserialized_value) == 1);
2642   fail_unless (gst_value_get_int64_range_max (deserialized_value) == G_MAXINT);
2643   str2 = gst_structure_to_string (s);
2644   fail_unless (strcmp (str, str2) == 0);
2645   gst_structure_free (s);
2646   end = NULL;
2647   g_free (str);
2648   g_free (str2);
2649
2650   /* check invalid int64_range (starting with a gint) deserialization */
2651   str =
2652       g_strdup_printf ("foo/bar, range=(gint64)[ 1, %" G_GUINT64_FORMAT " ];",
2653       (guint64) G_MAXINT64 + 1);
2654   ASSERT_CRITICAL (s = gst_structure_from_string (str, &end));
2655   fail_unless (*end == '\0');
2656   gst_structure_free (s);
2657   end = NULL;
2658   g_free (str);
2659
2660   /* check invalid int64_range deserialization into a int64_range */
2661   str =
2662       g_strdup_printf ("foo/bar, range=(gint64)[ %" G_GINT64_FORMAT ", %"
2663       G_GUINT64_FORMAT " ];", (gint64) G_MAXINT, (guint64) G_MAXINT64 + 1);
2664   ASSERT_CRITICAL (s = gst_structure_from_string (str, NULL));
2665   g_free (str);
2666   gst_structure_free (s);
2667
2668   /* check invalid int64_range deserialization into a int_range */
2669   str =
2670       g_strdup_printf ("foo/bar, range=[ %" G_GINT64_FORMAT ", %"
2671       G_GUINT64_FORMAT " ];", (gint64) G_MAXINT, (guint64) G_MAXINT64 + 1);
2672   s = gst_structure_from_string (str, &end);
2673   fail_unless (s == NULL);
2674   fail_unless (end == NULL);
2675   g_free (str);
2676 }
2677
2678 GST_END_TEST;
2679
2680 GST_START_TEST (test_stepped_range_collection)
2681 {
2682   GstStructure *s;
2683   const GValue *v;
2684
2685   s = gst_structure_new ("foo/bar", "range", GST_TYPE_INT_RANGE, 8, 12, NULL);
2686   fail_unless (s != NULL);
2687   v = gst_structure_get_value (s, "range");
2688   fail_unless (v != NULL);
2689   fail_unless (gst_value_get_int_range_min (v) == 8);
2690   fail_unless (gst_value_get_int_range_max (v) == 12);
2691   fail_unless (gst_value_get_int_range_step (v) == 1);
2692   gst_structure_free (s);
2693
2694   s = gst_structure_new ("foo/bar", "range", GST_TYPE_INT64_RANGE, (gint64) 8,
2695       (gint64) 12, NULL);
2696   fail_unless (s != NULL);
2697   v = gst_structure_get_value (s, "range");
2698   fail_unless (v != NULL);
2699   fail_unless (gst_value_get_int64_range_min (v) == 8);
2700   fail_unless (gst_value_get_int64_range_max (v) == 12);
2701   fail_unless (gst_value_get_int64_range_step (v) == 1);
2702   gst_structure_free (s);
2703 }
2704
2705 GST_END_TEST;
2706
2707 GST_START_TEST (test_stepped_int_range_parsing)
2708 {
2709   gchar *str;
2710   guint n;
2711   gchar *end = NULL;
2712   GstStructure *s;
2713
2714   static const gchar *good_ranges[] = {
2715     "[0, 1, 1]",
2716     "[-2, 2, 2]",
2717     "[16, 4096, 16]",
2718   };
2719
2720   static const gchar *bad_ranges[] = {
2721     "[0, 1, -1]",
2722     "[1, 2, 2]",
2723     "[2, 3, 2]",
2724     "[0, 0, 0]",
2725   };
2726
2727   /* check we can parse good ranges */
2728   for (n = 0; n < G_N_ELEMENTS (good_ranges); ++n) {
2729     str = g_strdup_printf ("foo/bar, range=%s", good_ranges[n]);
2730     s = gst_structure_from_string (str, &end);
2731     fail_unless (s != NULL);
2732     fail_unless (*end == '\0');
2733     gst_structure_free (s);
2734     g_free (str);
2735   }
2736
2737   /* check we cannot parse bad ranges */
2738   for (n = 0; n < G_N_ELEMENTS (bad_ranges); ++n) {
2739     str = g_strdup_printf ("foo/bar, range=%s", bad_ranges[n]);
2740     ASSERT_CRITICAL (s = gst_structure_from_string (str, &end));
2741     gst_structure_free (s);
2742     g_free (str);
2743   }
2744 }
2745
2746 GST_END_TEST;
2747
2748 GST_START_TEST (test_stepped_int_range_ops)
2749 {
2750   gchar *str1, *str2, *str3;
2751   guint n;
2752   GstStructure *s1, *s2, *s3;
2753   const GValue *v1, *v2, *v3;
2754
2755   static const struct
2756   {
2757     const gchar *set1;
2758     const gchar *op;
2759     const gchar *set2;
2760     const gchar *result;
2761   } ranges[] = {
2762     {
2763     "[16, 4096, 16]", "inter", "[100, 200, 10]", "160"}, {
2764     "[16, 4096, 16]", "inter", "[100, 200, 100]", NULL}, {
2765     "[16, 4096, 16]", "inter", "[0, 512, 256]", "[256, 512, 256]"}, {
2766     "[16, 32, 16]", "union", "[32, 96, 16]", "[16, 96, 16]"}, {
2767     "[16, 32, 16]", "union", "[48, 96, 16]", "[16, 96, 16]"}, {
2768     "[112, 192, 16]", "union", "[48, 96, 16]", "[48, 192, 16]"}, {
2769     "[16, 32, 16]", "union", "[64, 96, 16]", NULL}, {
2770   "[112, 192, 16]", "union", "[48, 96, 8]", NULL},};
2771
2772   for (n = 0; n < G_N_ELEMENTS (ranges); ++n) {
2773     gchar *end = NULL;
2774     GValue dest = { 0 };
2775     gboolean ret;
2776
2777     str1 = g_strdup_printf ("foo/bar, range=%s", ranges[n].set1);
2778     s1 = gst_structure_from_string (str1, &end);
2779     fail_unless (s1 != NULL);
2780     fail_unless (*end == '\0');
2781     v1 = gst_structure_get_value (s1, "range");
2782     fail_unless (v1 != NULL);
2783
2784     str2 = g_strdup_printf ("foo/bar, range=%s", ranges[n].set2);
2785     s2 = gst_structure_from_string (str2, &end);
2786     fail_unless (s2 != NULL);
2787     fail_unless (*end == '\0');
2788     v2 = gst_structure_get_value (s2, "range");
2789     fail_unless (v2 != NULL);
2790
2791     if (!strcmp (ranges[n].op, "inter")) {
2792       ret = gst_value_intersect (&dest, v1, v2);
2793     } else if (!strcmp (ranges[n].op, "union")) {
2794       ret = gst_value_union (&dest, v1, v2);
2795     } else {
2796       fail_unless (FALSE);
2797       ret = FALSE;
2798     }
2799
2800     if (ranges[n].result) {
2801       fail_unless (ret);
2802     } else {
2803       fail_unless (!ret);
2804     }
2805
2806     if (ret) {
2807       str3 = g_strdup_printf ("foo/bar, range=%s", ranges[n].result);
2808       s3 = gst_structure_from_string (str3, &end);
2809       fail_unless (s3 != NULL);
2810       fail_unless (*end == '\0');
2811       v3 = gst_structure_get_value (s3, "range");
2812       fail_unless (v3 != NULL);
2813
2814       if (gst_value_compare (&dest, v3) != GST_VALUE_EQUAL) {
2815         GST_ERROR ("%s %s %s yielded %s, expected %s", str1, ranges[n].op, str2,
2816             gst_value_serialize (&dest), gst_value_serialize (v3));
2817         fail_unless (FALSE);
2818       }
2819
2820       gst_structure_free (s3);
2821       g_free (str3);
2822
2823       g_value_unset (&dest);
2824     }
2825
2826     gst_structure_free (s2);
2827     g_free (str2);
2828     gst_structure_free (s1);
2829     g_free (str1);
2830   }
2831 }
2832
2833 GST_END_TEST;
2834
2835 static Suite *
2836 gst_value_suite (void)
2837 {
2838   Suite *s = suite_create ("GstValue");
2839   TCase *tc_chain = tcase_create ("general");
2840
2841   suite_add_tcase (s, tc_chain);
2842   tcase_add_test (tc_chain, test_deserialize_buffer);
2843   tcase_add_test (tc_chain, test_serialize_buffer);
2844   tcase_add_test (tc_chain, test_deserialize_gint);
2845   tcase_add_test (tc_chain, test_deserialize_gint_failures);
2846   tcase_add_test (tc_chain, test_deserialize_guint);
2847   tcase_add_test (tc_chain, test_deserialize_guint_failures);
2848   tcase_add_test (tc_chain, test_deserialize_gint64);
2849   tcase_add_test (tc_chain, test_deserialize_guint64);
2850   tcase_add_test (tc_chain, test_deserialize_guchar);
2851   tcase_add_test (tc_chain, test_deserialize_gstfraction);
2852   tcase_add_test (tc_chain, test_deserialize_bitmask);
2853   tcase_add_test (tc_chain, test_serialize_flags);
2854   tcase_add_test (tc_chain, test_deserialize_flags);
2855   tcase_add_test (tc_chain, test_serialize_deserialize_format_enum);
2856   tcase_add_test (tc_chain, test_string);
2857   tcase_add_test (tc_chain, test_deserialize_string);
2858   tcase_add_test (tc_chain, test_value_compare);
2859   tcase_add_test (tc_chain, test_value_intersect);
2860   tcase_add_test (tc_chain, test_value_subtract_int);
2861   tcase_add_test (tc_chain, test_value_subtract_int64);
2862   tcase_add_test (tc_chain, test_value_subtract_double);
2863   tcase_add_test (tc_chain, test_value_subtract_fraction);
2864   tcase_add_test (tc_chain, test_value_subtract_fraction_range);
2865   tcase_add_test (tc_chain, test_value_subtract_fraction_list);
2866   tcase_add_test (tc_chain, test_date);
2867   tcase_add_test (tc_chain, test_date_time);
2868   tcase_add_test (tc_chain, test_fraction_range);
2869   tcase_add_test (tc_chain, test_serialize_deserialize_caps);
2870   tcase_add_test (tc_chain, test_int_range);
2871   tcase_add_test (tc_chain, test_int64_range);
2872   tcase_add_test (tc_chain, test_serialize_int64_range);
2873   tcase_add_test (tc_chain, test_deserialize_int_range);
2874   tcase_add_test (tc_chain, test_stepped_range_collection);
2875   tcase_add_test (tc_chain, test_stepped_int_range_parsing);
2876   tcase_add_test (tc_chain, test_stepped_int_range_ops);
2877
2878   return s;
2879 }
2880
2881 GST_CHECK_MAIN (gst_value);