gasyncqueue: fix a 32bit overflow in g_async_queue_timed_pop

also, add a test for g_async_queue_timed_pop() and
g_async_queue_timeout_pop() to tests/asyncqueue.c

https://bugzilla.gnome.org/show_bug.cgi?id=669670
This commit is contained in:
Dan Winship 2012-02-22 08:12:52 -05:00
parent 9ff09f34cf
commit 88182d375e
2 changed files with 36 additions and 1 deletions

View File

@ -602,7 +602,7 @@ g_async_queue_timed_pop (GAsyncQueue *queue,
if (end_time != NULL) if (end_time != NULL)
{ {
m_end_time = g_get_monotonic_time () + m_end_time = g_get_monotonic_time () +
(end_time->tv_sec * G_USEC_PER_SEC + end_time->tv_usec - ((gint64)end_time->tv_sec * G_USEC_PER_SEC + end_time->tv_usec -
g_get_real_time ()); g_get_real_time ());
} }
else else

View File

@ -169,6 +169,40 @@ test_async_queue_threads (void)
g_assert_cmpint (c, ==, 1000); g_assert_cmpint (c, ==, 1000);
} }
static void
test_async_queue_timed (void)
{
GAsyncQueue *q;
GTimeVal tv;
gint64 start, end, diff;
gpointer val;
q = g_async_queue_new ();
start = g_get_monotonic_time ();
val = g_async_queue_timeout_pop (q, G_USEC_PER_SEC / 10);
g_assert (val == NULL);
end = g_get_monotonic_time ();
diff = end - start;
g_assert_cmpint (diff, >=, G_USEC_PER_SEC / 10);
/* diff should be only a little bit more than G_USEC_PER_SEC/10, but
* we have to leave some wiggle room for heavily-loaded machines...
*/
g_assert_cmpint (diff, <, G_USEC_PER_SEC);
start = end;
g_get_current_time (&tv);
g_time_val_add (&tv, G_USEC_PER_SEC / 10);
val = g_async_queue_timed_pop (q, &tv);
g_assert (val == NULL);
end = g_get_monotonic_time ();
diff = end - start;
g_assert_cmpint (diff, >=, G_USEC_PER_SEC / 10);
g_assert_cmpint (diff, <, G_USEC_PER_SEC);
}
int int
main (int argc, char *argv[]) main (int argc, char *argv[])
{ {
@ -177,6 +211,7 @@ main (int argc, char *argv[])
g_test_add_func ("/asyncqueue/sort", test_async_queue_sort); g_test_add_func ("/asyncqueue/sort", test_async_queue_sort);
g_test_add_func ("/asyncqueue/destroy", test_async_queue_destroy); g_test_add_func ("/asyncqueue/destroy", test_async_queue_destroy);
g_test_add_func ("/asyncqueue/threads", test_async_queue_threads); g_test_add_func ("/asyncqueue/threads", test_async_queue_threads);
g_test_add_func ("/asyncqueue/timed", test_async_queue_timed);
return g_test_run (); return g_test_run ();
} }