2 * Unit test for a deterministic clock for Gstreamer unit tests
4 * Copyright (C) 2008 Ole André Vadla Ravnås <ole.andre.ravnas@tandberg.com>
5 * Copyright (C) 2012 Sebastian Rasmussen <sebastian.rasmussen@axis.com>
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.
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.
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., 59 Temple Place - Suite 330,
20 * Boston, MA 02111-1307, USA.
23 #include <gst/check/gstcheck.h>
24 #include <gst/check/gsttestclock.h>
28 GstTestClock *test_clock;
30 GstClockTime reference;
31 } GtuClockWaitContext;
36 GstClockTimeDiff jitter;
37 } SyncClockWaitContext;
39 #define assert_pending_id(pending_id, id, type, time) \
41 GstClockEntry *entry = GST_CLOCK_ENTRY (pending_id); \
42 g_assert (entry == (id)); \
43 g_assert (GST_CLOCK_ENTRY_TYPE (entry) == (type)); \
44 g_assert_cmpuint (GST_CLOCK_ENTRY_TIME (entry), ==, (time)); \
47 #define assert_processed_id(processed_id, id, type, time) \
49 GstClockEntry *entry = GST_CLOCK_ENTRY (processed_id); \
50 g_assert (entry == (id)); \
51 g_assert (GST_CLOCK_ENTRY_TYPE (entry) == (type)); \
52 g_assert_cmpuint (GST_CLOCK_ENTRY_STATUS (entry), ==, (time)); \
55 static gpointer test_wait_pending_single_shot_id_sync_worker (gpointer data);
56 static gpointer test_wait_pending_single_shot_id_async_worker (gpointer data);
57 static gpointer test_wait_pending_periodic_id_waiter_thread (gpointer data);
58 static gboolean test_async_wait_cb (GstClock * clock, GstClockTime time,
59 GstClockID id, gpointer user_data);
61 static GtuClockWaitContext *gst_test_util_wait_for_clock_id_begin (GstTestClock
62 * clock, GstClockID id, GstClockTimeDiff * jitter);
63 static GstClockReturn gst_test_util_wait_for_clock_id_end (GtuClockWaitContext *
66 gst_test_util_clock_wait_context_has_completed (GtuClockWaitContext * wait_ctx);
69 test_wait_pending_single_shot_id_sync_worker (gpointer data)
71 SyncClockWaitContext *ctx = data;
73 gst_clock_id_wait (ctx->clock_id, &ctx->jitter);
79 test_wait_pending_single_shot_id_async_worker (gpointer data)
81 GstClockID clock_id = data;
83 g_usleep (G_USEC_PER_SEC / 10);
84 gst_clock_id_wait_async (clock_id, test_async_wait_cb, NULL, NULL);
90 test_wait_pending_periodic_id_waiter_thread (gpointer data)
92 GstClockID clock_id = data;
93 gst_clock_id_wait (clock_id, NULL);
98 test_async_wait_cb (GstClock * clock,
99 GstClockTime time, GstClockID id, gpointer user_data)
102 gboolean *wait_complete = user_data;
104 if (wait_complete != NULL)
105 *wait_complete = TRUE;
110 static GtuClockWaitContext *
111 gst_test_util_wait_for_clock_id_begin (GstTestClock * test_clock, GstClockID id,
112 GstClockTimeDiff * jitter)
114 GtuClockWaitContext *wait_ctx;
116 wait_ctx = g_slice_new (GtuClockWaitContext);
117 wait_ctx->test_clock = gst_object_ref (test_clock);
118 wait_ctx->reference = gst_clock_get_time (GST_CLOCK (wait_ctx->test_clock));
119 wait_ctx->id = gst_clock_id_ref (id);
122 GstClockEntry *entry = GST_CLOCK_ENTRY (wait_ctx->id);
123 GstClockTime requested = GST_CLOCK_ENTRY_TIME (entry);
124 GstClockTime reference = wait_ctx->reference;
126 *jitter = GST_CLOCK_DIFF (requested, reference);
129 if (!gst_test_clock_has_id (wait_ctx->test_clock, wait_ctx->id)) {
130 GstClockClass *klass = GST_CLOCK_GET_CLASS (wait_ctx->test_clock);
131 GstClock *clock = GST_CLOCK (wait_ctx->test_clock);
132 g_assert (klass->wait_async (clock, wait_ctx->id) == GST_CLOCK_OK);
135 g_assert (gst_test_clock_has_id (wait_ctx->test_clock, wait_ctx->id));
136 g_assert_cmpint (gst_test_clock_peek_id_count (wait_ctx->test_clock), >, 0);
141 static GstClockReturn
142 gst_test_util_wait_for_clock_id_end (GtuClockWaitContext * wait_ctx)
144 GstClockReturn status = GST_CLOCK_ERROR;
145 GstClockEntry *entry = GST_CLOCK_ENTRY (wait_ctx->id);
147 if (G_UNLIKELY (GST_CLOCK_ENTRY_STATUS (entry) == GST_CLOCK_UNSCHEDULED)) {
148 status = GST_CLOCK_UNSCHEDULED;
150 GstClockTime requested = GST_CLOCK_ENTRY_TIME (entry);
151 GstClockTimeDiff diff;
153 g_assert (gst_test_clock_has_id (wait_ctx->test_clock, wait_ctx->id));
155 diff = GST_CLOCK_DIFF (requested, wait_ctx->reference);
158 status = GST_CLOCK_EARLY;
160 status = GST_CLOCK_OK;
163 g_atomic_int_set (&GST_CLOCK_ENTRY_STATUS (entry), status);
166 if (GST_CLOCK_ENTRY_TYPE (entry) == GST_CLOCK_ENTRY_SINGLE) {
167 GstClockClass *klass = GST_CLOCK_GET_CLASS (wait_ctx->test_clock);
168 GstClock *clock = GST_CLOCK (wait_ctx->test_clock);
170 klass->unschedule (clock, wait_ctx->id);
171 g_assert (!gst_test_clock_has_id (wait_ctx->test_clock, wait_ctx->id));
173 GST_CLOCK_ENTRY_TIME (entry) += GST_CLOCK_ENTRY_INTERVAL (entry);
174 g_assert (gst_test_clock_has_id (wait_ctx->test_clock, wait_ctx->id));
177 gst_clock_id_unref (wait_ctx->id);
178 gst_object_unref (wait_ctx->test_clock);
179 g_slice_free (GtuClockWaitContext, wait_ctx);
185 gst_test_util_clock_wait_context_has_completed (GtuClockWaitContext * wait_ctx)
187 GstClock *clock = GST_CLOCK (wait_ctx->test_clock);
188 GstClockEntry *entry = GST_CLOCK_ENTRY (wait_ctx->id);
189 GstClockTime requested = GST_CLOCK_ENTRY_TIME (entry);
190 GstClockTime now = gst_clock_get_time (clock);
192 return requested < now;
195 GST_START_TEST (test_object_flags)
197 GstClock *clock = gst_test_clock_new ();
198 g_assert (GST_OBJECT_FLAG_IS_SET (clock, GST_CLOCK_FLAG_CAN_DO_SINGLE_SYNC));
199 g_assert (GST_OBJECT_FLAG_IS_SET (clock, GST_CLOCK_FLAG_CAN_DO_SINGLE_ASYNC));
200 g_assert (GST_OBJECT_FLAG_IS_SET (clock,
201 GST_CLOCK_FLAG_CAN_DO_PERIODIC_SYNC));
202 g_assert (GST_OBJECT_FLAG_IS_SET (clock,
203 GST_CLOCK_FLAG_CAN_DO_PERIODIC_ASYNC));
204 gst_object_unref (clock);
209 GST_START_TEST (test_resolution_query)
211 GstClock *clock = gst_test_clock_new ();
212 g_assert_cmpuint (gst_clock_get_resolution (clock), ==, 1);
213 gst_object_unref (clock);
218 GST_START_TEST (test_start_time)
223 clock = gst_test_clock_new ();
224 g_assert_cmpuint (gst_clock_get_time (clock), ==, 0);
225 g_object_get (clock, "start-time", &start_time, NULL);
226 g_assert_cmpuint (start_time, ==, 0);
227 gst_object_unref (clock);
229 clock = gst_test_clock_new_with_start_time (GST_SECOND);
230 g_assert_cmpuint (gst_clock_get_time (clock), ==, GST_SECOND);
231 g_object_get (clock, "start-time", &start_time, NULL);
232 g_assert_cmpuint (start_time, ==, GST_SECOND);
233 gst_object_unref (clock);
238 GST_START_TEST (test_set_time)
240 GstClock *clock = gst_test_clock_new_with_start_time (GST_SECOND);
241 gst_test_clock_set_time (GST_TEST_CLOCK (clock), GST_SECOND);
242 g_assert_cmpuint (gst_clock_get_time (clock), ==, GST_SECOND);
243 gst_test_clock_set_time (GST_TEST_CLOCK (clock), GST_SECOND + 1);
244 g_assert_cmpuint (gst_clock_get_time (clock), ==, GST_SECOND + 1);
245 gst_object_unref (clock);
250 GST_START_TEST (test_advance_time)
252 GstClock *clock = gst_test_clock_new_with_start_time (GST_SECOND);
253 gst_test_clock_advance_time (GST_TEST_CLOCK (clock), 0);
254 g_assert_cmpuint (gst_clock_get_time (clock), ==, GST_SECOND);
255 gst_test_clock_advance_time (GST_TEST_CLOCK (clock), 42 * GST_MSECOND);
256 g_assert_cmpuint (gst_clock_get_time (clock), ==,
257 GST_SECOND + (42 * GST_MSECOND));
258 gst_object_unref (clock);
263 GST_START_TEST (test_wait_synchronous_no_timeout)
266 GstTestClock *test_clock;
268 GThread *worker_thread;
269 GstClockID pending_id;
270 GstClockID processed_id;
271 SyncClockWaitContext context;
273 clock = gst_test_clock_new_with_start_time (GST_SECOND);
274 test_clock = GST_TEST_CLOCK (clock);
276 clock_id = gst_clock_new_single_shot_id (clock, GST_SECOND - 1);
277 context.clock_id = gst_clock_id_ref (clock_id);
279 worker_thread = g_thread_create (test_wait_pending_single_shot_id_sync_worker,
280 &context, TRUE, NULL);
281 gst_test_clock_wait_for_next_pending_id (test_clock, &pending_id);
282 assert_pending_id (pending_id, clock_id, GST_CLOCK_ENTRY_SINGLE, GST_SECOND - 1);
283 gst_clock_id_unref (pending_id);
284 processed_id = gst_test_clock_process_next_clock_id (test_clock);
285 assert_processed_id (processed_id, clock_id, GST_CLOCK_ENTRY_SINGLE, GST_CLOCK_EARLY);
286 gst_clock_id_unref (processed_id);
287 g_thread_join (worker_thread);
288 g_assert_cmpuint (context.jitter, ==, 1);
289 gst_clock_id_unref (context.clock_id);
290 gst_clock_id_unref (clock_id);
292 clock_id = gst_clock_new_single_shot_id (clock, GST_SECOND);
293 context.clock_id = gst_clock_id_ref (clock_id);
295 worker_thread = g_thread_create (test_wait_pending_single_shot_id_sync_worker,
296 &context, TRUE, NULL);
297 gst_test_clock_wait_for_next_pending_id (test_clock, &pending_id);
298 assert_pending_id (pending_id, clock_id, GST_CLOCK_ENTRY_SINGLE, GST_SECOND);
299 gst_clock_id_unref (pending_id);
300 processed_id = gst_test_clock_process_next_clock_id (test_clock);
301 assert_processed_id (processed_id, clock_id, GST_CLOCK_ENTRY_SINGLE, GST_CLOCK_OK);
302 gst_clock_id_unref (processed_id);
303 g_thread_join (worker_thread);
304 g_assert_cmpuint (context.jitter, ==, 0);
305 gst_clock_id_unref (context.clock_id);
306 gst_clock_id_unref (clock_id);
308 clock_id = gst_clock_new_single_shot_id (clock, GST_SECOND + 1);
309 context.clock_id = gst_clock_id_ref (clock_id);
311 worker_thread = g_thread_create (test_wait_pending_single_shot_id_sync_worker,
312 &context, TRUE, NULL);
313 gst_test_clock_wait_for_next_pending_id (test_clock, &pending_id);
314 assert_pending_id (pending_id, clock_id, GST_CLOCK_ENTRY_SINGLE, GST_SECOND + 1);
315 gst_clock_id_unref (pending_id);
316 processed_id = gst_test_clock_process_next_clock_id (test_clock);
317 g_assert (processed_id == NULL);
318 gst_test_clock_advance_time (test_clock, 1);
319 processed_id = gst_test_clock_process_next_clock_id (test_clock);
320 assert_processed_id (processed_id, clock_id, GST_CLOCK_ENTRY_SINGLE, GST_CLOCK_OK);
321 gst_clock_id_unref (processed_id);
322 g_thread_join (worker_thread);
323 g_assert_cmpuint (context.jitter, ==, -1);
324 gst_clock_id_unref (context.clock_id);
325 gst_clock_id_unref (clock_id);
327 gst_object_unref (clock);
332 GST_START_TEST (test_wait_pending_single_shot_id)
335 GstTestClock *test_clock;
337 GstClockID processed_id;
338 GThread *worker_thread;
339 GstClockID pending_id;
341 clock = gst_test_clock_new_with_start_time (GST_SECOND);
342 test_clock = GST_TEST_CLOCK (clock);
344 clock_id = gst_clock_new_single_shot_id (clock, GST_SECOND);
345 gst_clock_id_wait_async (clock_id, test_async_wait_cb, NULL, NULL);
346 gst_test_clock_wait_for_next_pending_id (test_clock, &pending_id);
347 assert_pending_id (pending_id, clock_id, GST_CLOCK_ENTRY_SINGLE, GST_SECOND);
348 gst_clock_id_unref (pending_id);
349 processed_id = gst_test_clock_process_next_clock_id (test_clock);
350 assert_processed_id (processed_id, clock_id, GST_CLOCK_ENTRY_SINGLE, GST_CLOCK_OK);
351 gst_clock_id_unref (processed_id);
352 gst_clock_id_unref (clock_id);
354 clock_id = gst_clock_new_single_shot_id (clock, 2 * GST_SECOND);
355 worker_thread = g_thread_create (test_wait_pending_single_shot_id_async_worker,
356 clock_id, TRUE, NULL);
357 gst_test_clock_wait_for_next_pending_id (test_clock, &pending_id);
358 assert_pending_id (pending_id, clock_id, GST_CLOCK_ENTRY_SINGLE, 2 * GST_SECOND);
359 gst_clock_id_unref (pending_id);
360 g_thread_join (worker_thread);
361 gst_clock_id_unref (clock_id);
363 clock_id = gst_clock_new_single_shot_id (clock, 3 * GST_SECOND);
364 worker_thread = g_thread_create (test_wait_pending_single_shot_id_async_worker,
365 clock_id, TRUE, NULL);
366 gst_test_clock_wait_for_next_pending_id (test_clock, NULL);
367 g_thread_join (worker_thread);
368 gst_clock_id_unref (clock_id);
370 gst_object_unref (clock);
375 GST_START_TEST (test_wait_pending_periodic_id)
378 GstTestClock *test_clock;
380 GstClockID processed_id;
382 clock = gst_test_clock_new_with_start_time (GST_SECOND);
383 test_clock = GST_TEST_CLOCK (clock);
384 clock_id = gst_clock_new_periodic_id (clock, GST_SECOND, GST_MSECOND);
387 GThread *waiter_thread;
390 g_thread_create (test_wait_pending_periodic_id_waiter_thread, clock_id,
393 gst_test_clock_wait_for_next_pending_id (test_clock, NULL);
394 gst_test_clock_set_time (test_clock, GST_SECOND);
395 processed_id = gst_test_clock_process_next_clock_id (test_clock);
396 assert_processed_id (processed_id, clock_id, GST_CLOCK_ENTRY_PERIODIC, GST_CLOCK_OK);
397 gst_clock_id_unref (processed_id);
399 g_thread_join (waiter_thread);
404 GThread *waiter_thread;
406 for (i = 0; i < 3; i++) {
407 g_assert (!gst_test_clock_peek_next_pending_id (test_clock, NULL));
408 g_usleep (G_USEC_PER_SEC / 10 / 10);
412 g_thread_create (test_wait_pending_periodic_id_waiter_thread, clock_id,
415 gst_test_clock_wait_for_next_pending_id (test_clock, NULL);
416 gst_clock_id_unschedule (clock_id);
418 g_thread_join (waiter_thread);
421 gst_clock_id_unref (clock_id);
422 gst_object_unref (clock);
427 GST_START_TEST (test_single_shot_sync_past)
430 GstTestClock *test_clock;
432 GstClockTimeDiff jitter;
433 GtuClockWaitContext *wait_ctx;
435 clock = gst_test_clock_new_with_start_time (GST_SECOND);
436 test_clock = GST_TEST_CLOCK (clock);
438 clock_id = gst_clock_new_single_shot_id (clock, GST_SECOND - 1);
440 gst_test_util_wait_for_clock_id_begin (test_clock, clock_id, &jitter);
441 g_assert (gst_test_util_wait_for_clock_id_end (wait_ctx) == GST_CLOCK_EARLY);
442 g_assert_cmpint (jitter, ==, 1);
443 gst_clock_id_unref (clock_id);
445 gst_object_unref (clock);
450 GST_START_TEST (test_single_shot_sync_present)
453 GstTestClock *test_clock;
455 GstClockTimeDiff jitter;
456 GtuClockWaitContext *wait_ctx;
458 clock = gst_test_clock_new_with_start_time (GST_SECOND);
459 test_clock = GST_TEST_CLOCK (clock);
461 clock_id = gst_clock_new_single_shot_id (clock, GST_SECOND);
463 gst_test_util_wait_for_clock_id_begin (test_clock, clock_id, &jitter);
464 g_assert (gst_test_util_wait_for_clock_id_end (wait_ctx) == GST_CLOCK_OK);
465 g_assert_cmpint (jitter, ==, 0);
466 gst_clock_id_unref (clock_id);
468 gst_object_unref (clock);
473 GST_START_TEST (test_single_shot_sync_future)
476 GstTestClock *test_clock;
478 GstClockTimeDiff jitter;
479 GtuClockWaitContext *wait_ctx;
481 clock = gst_test_clock_new_with_start_time (GST_SECOND);
482 test_clock = GST_TEST_CLOCK (clock);
484 clock_id = gst_clock_new_single_shot_id (clock, 2 * GST_SECOND);
486 gst_test_util_wait_for_clock_id_begin (test_clock, clock_id, &jitter);
487 gst_test_clock_advance_time (test_clock, GST_SECOND);
488 g_assert (gst_test_util_wait_for_clock_id_end (wait_ctx) == GST_CLOCK_OK);
489 g_assert_cmpint (jitter, ==, -GST_SECOND);
490 gst_clock_id_unref (clock_id);
492 gst_object_unref (clock);
497 GST_START_TEST (test_single_shot_sync_unschedule)
500 GstTestClock *test_clock;
502 GtuClockWaitContext *wait_ctx;
504 clock = gst_test_clock_new_with_start_time (GST_SECOND);
505 test_clock = GST_TEST_CLOCK (clock);
507 clock_id = gst_clock_new_single_shot_id (clock, GST_SECOND);
508 gst_clock_id_unschedule (clock_id);
509 gst_clock_id_unref (clock_id);
511 clock_id = gst_clock_new_single_shot_id (clock, 2 * GST_SECOND);
512 wait_ctx = gst_test_util_wait_for_clock_id_begin (test_clock, clock_id, NULL);
513 gst_clock_id_unschedule (clock_id);
514 g_assert (gst_test_util_wait_for_clock_id_end (wait_ctx)
515 == GST_CLOCK_UNSCHEDULED);
516 gst_clock_id_unref (clock_id);
518 gst_object_unref (clock);
523 GST_START_TEST (test_single_shot_sync_ordering)
526 GstTestClock *test_clock;
527 GstClockID clock_id_a, clock_id_b;
528 GtuClockWaitContext *wait_ctx_a, *wait_ctx_b;
530 clock = gst_test_clock_new_with_start_time (GST_SECOND);
531 test_clock = GST_TEST_CLOCK (clock);
533 clock_id_a = gst_clock_new_single_shot_id (clock, 3 * GST_SECOND);
535 gst_test_util_wait_for_clock_id_begin (test_clock, clock_id_a, NULL);
537 gst_test_clock_advance_time (test_clock, GST_SECOND);
539 clock_id_b = gst_clock_new_single_shot_id (clock, 2 * GST_SECOND);
541 gst_test_util_wait_for_clock_id_begin (test_clock, clock_id_b, NULL);
543 gst_test_clock_advance_time (test_clock, GST_SECOND);
545 g_assert (gst_test_util_wait_for_clock_id_end (wait_ctx_b) == GST_CLOCK_OK);
546 g_assert (gst_test_util_wait_for_clock_id_end (wait_ctx_a) == GST_CLOCK_OK);
548 gst_clock_id_unref (clock_id_b);
549 gst_clock_id_unref (clock_id_a);
551 gst_object_unref (clock);
556 GST_START_TEST (test_single_shot_sync_ordering_parallel)
559 GstTestClock *test_clock;
560 GstClockID clock_id_a, clock_id_b;
561 GtuClockWaitContext *wait_ctx_a, *wait_ctx_b;
563 clock = gst_test_clock_new_with_start_time (GST_SECOND);
564 test_clock = GST_TEST_CLOCK (clock);
566 clock_id_a = gst_clock_new_single_shot_id (clock, 3 * GST_SECOND);
567 clock_id_b = gst_clock_new_single_shot_id (clock, 2 * GST_SECOND);
568 wait_ctx_a = gst_test_util_wait_for_clock_id_begin (test_clock, clock_id_a,
570 wait_ctx_b = gst_test_util_wait_for_clock_id_begin (test_clock, clock_id_b,
573 g_assert_cmpuint (gst_test_clock_get_next_entry_time (test_clock), ==,
575 gst_test_clock_advance_time (test_clock, GST_SECOND);
576 g_assert (gst_test_util_wait_for_clock_id_end (wait_ctx_b) == GST_CLOCK_OK);
578 g_assert_cmpuint (gst_test_clock_get_next_entry_time (test_clock), ==,
580 gst_test_clock_advance_time (test_clock, GST_SECOND);
581 g_assert (gst_test_util_wait_for_clock_id_end (wait_ctx_a) == GST_CLOCK_OK);
583 gst_clock_id_unref (clock_id_b);
584 gst_clock_id_unref (clock_id_a);
586 gst_object_unref (clock);
591 GST_START_TEST (test_single_shot_sync_simultaneous_no_timeout)
594 GstTestClock *test_clock;
595 GstClockID clock_id_a;
596 GstClockID clock_id_b;
597 SyncClockWaitContext context_a;
598 SyncClockWaitContext context_b;
599 GThread *worker_thread_a;
600 GThread *worker_thread_b;
601 GstClockID processed_id;
602 GstClockID pending_id;
604 clock = gst_test_clock_new_with_start_time (GST_SECOND);
605 test_clock = GST_TEST_CLOCK (clock);
607 clock_id_a = gst_clock_new_single_shot_id (clock, 5 * GST_SECOND);
608 clock_id_b = gst_clock_new_single_shot_id (clock, 6 * GST_SECOND);
610 context_a.clock_id = gst_clock_id_ref (clock_id_a);
611 context_a.jitter = 0;
612 context_b.clock_id = gst_clock_id_ref (clock_id_b);
613 context_b.jitter = 0;
615 gst_test_clock_wait_for_pending_id_count (test_clock, 0);
617 worker_thread_b = g_thread_create (test_wait_pending_single_shot_id_sync_worker,
618 &context_b, TRUE, NULL);
620 gst_test_clock_wait_for_pending_id_count (test_clock, 1);
621 gst_test_clock_wait_for_next_pending_id (test_clock, &pending_id);
622 assert_pending_id (pending_id, clock_id_b, GST_CLOCK_ENTRY_SINGLE, 6 * GST_SECOND);
623 gst_clock_id_unref (pending_id);
625 worker_thread_a = g_thread_create (test_wait_pending_single_shot_id_sync_worker,
626 &context_a, TRUE, NULL);
628 gst_test_clock_wait_for_pending_id_count (test_clock, 2);
629 gst_test_clock_wait_for_next_pending_id (test_clock, &pending_id);
630 assert_pending_id (pending_id, clock_id_a, GST_CLOCK_ENTRY_SINGLE, 5 * GST_SECOND);
631 gst_clock_id_unref (pending_id);
633 g_assert_cmpuint (gst_test_clock_get_next_entry_time (test_clock), ==,
635 gst_test_clock_advance_time (test_clock, 5 * GST_SECOND);
636 processed_id = gst_test_clock_process_next_clock_id (test_clock);
637 assert_processed_id (processed_id, clock_id_a, GST_CLOCK_ENTRY_SINGLE, GST_CLOCK_OK);
638 gst_clock_id_unref (processed_id);
640 gst_test_clock_wait_for_pending_id_count (test_clock, 1);
641 gst_test_clock_wait_for_next_pending_id (test_clock, &pending_id);
642 assert_pending_id (pending_id, clock_id_b, GST_CLOCK_ENTRY_SINGLE, 6 * GST_SECOND);
643 gst_clock_id_unref (pending_id);
645 g_assert_cmpuint (gst_test_clock_get_next_entry_time (test_clock), ==,
647 gst_test_clock_advance_time (test_clock, 6 * GST_SECOND);
648 processed_id = gst_test_clock_process_next_clock_id (test_clock);
649 assert_processed_id (processed_id, clock_id_b, GST_CLOCK_ENTRY_SINGLE, GST_CLOCK_OK);
650 gst_clock_id_unref (processed_id);
652 gst_test_clock_wait_for_pending_id_count (test_clock, 0);
654 g_thread_join (worker_thread_a);
655 g_thread_join (worker_thread_b);
657 g_assert_cmpuint (context_a.jitter, ==, -4 * GST_SECOND);
658 g_assert_cmpuint (context_b.jitter, ==, -5 * GST_SECOND);
660 gst_clock_id_unref (context_a.clock_id);
661 gst_clock_id_unref (context_b.clock_id);
663 gst_clock_id_unref (clock_id_a);
664 gst_clock_id_unref (clock_id_b);
666 gst_object_unref (clock);
671 GST_START_TEST (test_single_shot_async_past)
675 GstClockID processed_id;
676 gboolean wait_complete = FALSE;
678 clock = gst_test_clock_new_with_start_time (GST_SECOND);
679 clock_id = gst_clock_new_single_shot_id (clock, GST_SECOND - 1);
680 g_assert (gst_clock_id_wait_async (clock_id, test_async_wait_cb,
681 &wait_complete, NULL) == GST_CLOCK_OK);
682 g_assert (!wait_complete);
683 processed_id = gst_test_clock_process_next_clock_id (GST_TEST_CLOCK (clock));
684 g_assert (wait_complete);
685 assert_processed_id (processed_id, clock_id, GST_CLOCK_ENTRY_SINGLE, GST_CLOCK_EARLY);
686 gst_clock_id_unref (processed_id);
687 gst_clock_id_unref (clock_id);
688 gst_object_unref (clock);
693 GST_START_TEST (test_single_shot_async_present)
697 GstClockID processed_id;
698 gboolean wait_complete = FALSE;
700 clock = gst_test_clock_new_with_start_time (GST_SECOND);
701 clock_id = gst_clock_new_single_shot_id (clock, GST_SECOND);
702 g_assert (gst_clock_id_wait_async (clock_id, test_async_wait_cb,
703 &wait_complete, NULL) == GST_CLOCK_OK);
704 g_assert (!wait_complete);
705 processed_id = gst_test_clock_process_next_clock_id (GST_TEST_CLOCK (clock));
706 g_assert (wait_complete);
707 assert_processed_id (processed_id, clock_id, GST_CLOCK_ENTRY_SINGLE, GST_CLOCK_OK);
708 gst_clock_id_unref (processed_id);
709 gst_clock_id_unref (clock_id);
710 gst_object_unref (clock);
715 GST_START_TEST (test_single_shot_async_future)
719 GstClockID processed_id;
720 gboolean wait_complete = FALSE;
722 clock = gst_test_clock_new_with_start_time (GST_SECOND);
723 clock_id = gst_clock_new_single_shot_id (clock, 2 * GST_SECOND);
724 g_assert (gst_clock_id_wait_async (clock_id, test_async_wait_cb,
725 &wait_complete, NULL) == GST_CLOCK_OK);
726 processed_id = gst_test_clock_process_next_clock_id (GST_TEST_CLOCK (clock));
727 g_assert (processed_id == NULL);
728 g_assert (!wait_complete);
729 g_assert (GST_CLOCK_ENTRY_STATUS (GST_CLOCK_ENTRY (clock_id))
732 gst_test_clock_advance_time (GST_TEST_CLOCK (clock), GST_SECOND - 1);
733 processed_id = gst_test_clock_process_next_clock_id (GST_TEST_CLOCK (clock));
734 g_assert (processed_id == NULL);
735 g_assert (!wait_complete);
736 g_assert (GST_CLOCK_ENTRY_STATUS (GST_CLOCK_ENTRY (clock_id))
739 gst_test_clock_advance_time (GST_TEST_CLOCK (clock), 1);
740 processed_id = gst_test_clock_process_next_clock_id (GST_TEST_CLOCK (clock));
741 g_assert (wait_complete);
742 assert_processed_id (processed_id, clock_id, GST_CLOCK_ENTRY_SINGLE, GST_CLOCK_OK);
743 gst_clock_id_unref (processed_id);
744 g_assert (GST_CLOCK_ENTRY_STATUS (GST_CLOCK_ENTRY (clock_id))
747 gst_clock_id_unref (clock_id);
748 gst_object_unref (clock);
753 GST_START_TEST (test_single_shot_async_unschedule)
757 gboolean wait_complete = FALSE;
759 clock = gst_test_clock_new_with_start_time (GST_SECOND);
761 clock_id = gst_clock_new_single_shot_id (clock, 3 * GST_SECOND);
762 g_assert (gst_clock_id_wait_async (clock_id, test_async_wait_cb,
763 &wait_complete, NULL) == GST_CLOCK_OK);
765 gst_clock_id_unschedule (clock_id);
767 gst_test_clock_advance_time (GST_TEST_CLOCK (clock), 2 * GST_SECOND);
768 g_assert (gst_test_clock_process_next_clock_id (GST_TEST_CLOCK (clock))
770 g_assert (!wait_complete);
772 gst_clock_id_unref (clock_id);
773 gst_object_unref (clock);
778 GST_START_TEST (test_periodic_sync)
781 GstTestClock *test_clock;
784 const GstClockTime interval = 4 * GST_MSECOND;
786 clock = gst_test_clock_new ();
787 test_clock = GST_TEST_CLOCK (clock);
789 clock_id = gst_clock_new_periodic_id (clock, GST_SECOND, interval);
791 for (i = 0; i < 3; i++) {
792 GtuClockWaitContext *wait_ctx;
793 GstClockID pending_id;
797 gst_test_util_wait_for_clock_id_begin (test_clock, clock_id, NULL);
799 gst_test_clock_wait_for_next_pending_id (test_clock, &pending_id);
800 assert_pending_id (pending_id, clock_id, GST_CLOCK_ENTRY_PERIODIC, GST_SECOND + (i * interval));
801 gst_clock_id_unref (pending_id);
803 for (j = 0; j < 10; j++) {
804 g_usleep (G_USEC_PER_SEC / 10 / 10);
805 g_assert (!gst_test_util_clock_wait_context_has_completed (wait_ctx));
809 gst_test_clock_advance_time (test_clock, GST_SECOND);
811 gst_test_clock_advance_time (test_clock, interval);
813 gst_test_util_wait_for_clock_id_end (wait_ctx);
816 gst_clock_id_unref (clock_id);
817 gst_object_unref (clock);
822 GST_START_TEST (test_periodic_async)
826 GstClockID processed_id;
827 gboolean wait_complete = FALSE;
828 const GstClockTime interval = 4 * GST_MSECOND;
830 clock = gst_test_clock_new ();
831 clock_id = gst_clock_new_periodic_id (clock, gst_clock_get_time (clock),
833 g_assert (gst_clock_id_wait_async (clock_id, test_async_wait_cb,
834 &wait_complete, NULL) == GST_CLOCK_OK);
836 processed_id = gst_test_clock_process_next_clock_id (GST_TEST_CLOCK (clock));
837 assert_processed_id (processed_id, clock_id, GST_CLOCK_ENTRY_PERIODIC, GST_CLOCK_OK);
838 gst_clock_id_unref (processed_id);
840 g_assert (wait_complete);
841 wait_complete = FALSE;
843 gst_test_clock_advance_time (GST_TEST_CLOCK (clock), interval - 1);
844 processed_id = gst_test_clock_process_next_clock_id (GST_TEST_CLOCK (clock));
845 g_assert (processed_id == NULL);
846 g_assert (!wait_complete);
848 gst_test_clock_advance_time (GST_TEST_CLOCK (clock), 1);
849 processed_id = gst_test_clock_process_next_clock_id (GST_TEST_CLOCK (clock));
850 assert_processed_id (processed_id, clock_id, GST_CLOCK_ENTRY_PERIODIC, GST_CLOCK_OK);
851 gst_clock_id_unref (processed_id);
852 g_assert (wait_complete);
853 wait_complete = FALSE;
855 gst_test_clock_advance_time (GST_TEST_CLOCK (clock), interval - 1);
856 processed_id = gst_test_clock_process_next_clock_id (GST_TEST_CLOCK (clock));
857 g_assert (processed_id == NULL);
858 g_assert (!wait_complete);
860 gst_test_clock_advance_time (GST_TEST_CLOCK (clock), 1);
861 processed_id = gst_test_clock_process_next_clock_id (GST_TEST_CLOCK (clock));
862 assert_processed_id (processed_id, clock_id, GST_CLOCK_ENTRY_PERIODIC, GST_CLOCK_OK);
863 gst_clock_id_unref (processed_id);
864 g_assert (wait_complete);
865 wait_complete = FALSE;
867 gst_clock_id_unref (clock_id);
868 gst_object_unref (clock);
873 GST_START_TEST (test_periodic_uniqueness)
876 GstTestClock *test_clock;
879 const GstClockTime interval = 4 * GST_MSECOND;
881 clock = gst_test_clock_new ();
882 test_clock = GST_TEST_CLOCK (clock);
884 clock_id = gst_clock_new_periodic_id (clock, 0, interval);
886 for (i = 0; i < 3; i++) {
887 GtuClockWaitContext *wait_ctx;
891 gst_test_util_wait_for_clock_id_begin (test_clock, clock_id, NULL);
893 for (j = 0; j < 10; j++) {
894 g_usleep (G_USEC_PER_SEC / 10 / 10);
895 g_assert_cmpuint (gst_test_clock_peek_id_count (test_clock), ==, 1);
898 gst_test_clock_advance_time (test_clock, interval);
899 gst_test_util_wait_for_clock_id_end (wait_ctx);
902 gst_clock_id_unref (clock_id);
903 gst_object_unref (clock);
909 gst_test_clock_suite (void)
911 Suite *s = suite_create ("GstTestClock");
912 TCase *tc_chain = tcase_create ("testclock");
914 suite_add_tcase (s, tc_chain);
916 tcase_add_test (tc_chain, test_object_flags);
917 tcase_add_test (tc_chain, test_resolution_query);
918 tcase_add_test (tc_chain, test_start_time);
919 tcase_add_test (tc_chain, test_set_time);
920 tcase_add_test (tc_chain, test_advance_time);
921 tcase_add_test (tc_chain, test_wait_synchronous_no_timeout);
922 tcase_add_test (tc_chain, test_wait_pending_single_shot_id);
923 tcase_add_test (tc_chain, test_wait_pending_periodic_id);
924 tcase_add_test (tc_chain, test_single_shot_sync_simultaneous_no_timeout);
925 tcase_add_test (tc_chain, test_single_shot_sync_past);
926 tcase_add_test (tc_chain, test_single_shot_sync_present);
927 tcase_add_test (tc_chain, test_single_shot_sync_future);
928 tcase_add_test (tc_chain, test_single_shot_sync_unschedule);
929 tcase_add_test (tc_chain, test_single_shot_sync_ordering);
930 tcase_add_test (tc_chain, test_single_shot_sync_ordering_parallel);
931 tcase_add_test (tc_chain, test_single_shot_async_past);
932 tcase_add_test (tc_chain, test_single_shot_async_present);
933 tcase_add_test (tc_chain, test_single_shot_async_future);
934 tcase_add_test (tc_chain, test_single_shot_async_unschedule);
935 tcase_add_test (tc_chain, test_periodic_sync);
936 tcase_add_test (tc_chain, test_periodic_async);
937 tcase_add_test (tc_chain, test_periodic_uniqueness);
942 GST_CHECK_MAIN (gst_test_clock);