From 490c41e78c79a18ab683f83299b041564cb4a69b Mon Sep 17 00:00:00 2001 From: lurchi Date: Mon, 4 Sep 2017 15:05:26 +0200 Subject: [PATCH] Fix select loop running conditions The select loop has to keep running as long as the driver has tasks available (indicating that there are file descriptors left to wait for) or the timeout is not FOREVER (indicating that the scheduler has tasks with timeout left). --- src/include/gnunet_scheduler_lib.h | 12 ++++++++---- src/util/scheduler.c | 6 +++++- 2 files changed, 13 insertions(+), 5 deletions(-) diff --git a/src/include/gnunet_scheduler_lib.h b/src/include/gnunet_scheduler_lib.h index b6f127f0c..aded41de8 100644 --- a/src/include/gnunet_scheduler_lib.h +++ b/src/include/gnunet_scheduler_lib.h @@ -242,15 +242,16 @@ struct GNUNET_SCHEDULER_Handle; * there are tasks left to run just to give other tasks a chance as * well. If we return #GNUNET_YES, the driver should call this * function again as soon as possible, while if we return #GNUNET_NO - * it must block until the operating system has more work as the - * scheduler has no more work to do right now. + * it must block until either the operating system has more work (the + * scheduler has no more work to do right now) or the timeout set by + * the scheduler (using the set_wakeup callback) is reached. * * @param sh scheduler handle that was given to the `loop` * @return #GNUNET_OK if there are more tasks that are ready, * and thus we would like to run more (yield to avoid * blocking other activities for too long) * #GNUNET_NO if we are done running tasks (yield to block) - * #GNUNET_SYSERR on error + * #GNUNET_SYSERR on error, e.g. no tasks were ready */ int GNUNET_SCHEDULER_run_from_driver (struct GNUNET_SCHEDULER_Handle *sh); @@ -313,7 +314,10 @@ struct GNUNET_SCHEDULER_Driver /** * Event loop's "main" function, to be called from * #GNUNET_SCHEDULER_run_with_driver() to actually - * launch the loop. + * launch the loop. The loop should run as long as + * tasks (added by the add callback) are available + * OR the wakeup time (added by the set_wakeup + * callback) is not FOREVER. * * @param cls closure * @param sh scheduler handle to pass to diff --git a/src/util/scheduler.c b/src/util/scheduler.c index 72f2b7230..4b963209d 100644 --- a/src/util/scheduler.c +++ b/src/util/scheduler.c @@ -2209,7 +2209,8 @@ select_loop (void *cls, rs = GNUNET_NETWORK_fdset_create (); ws = GNUNET_NETWORK_fdset_create (); tasks_ready = GNUNET_NO; - while (NULL != context->scheduled_head || GNUNET_YES == tasks_ready) + while (NULL != context->scheduled_head || + GNUNET_TIME_UNIT_FOREVER_REL.rel_value_us != context->timeout.rel_value_us) { LOG (GNUNET_ERROR_TYPE_DEBUG, "select timeout = %s\n", @@ -2300,6 +2301,9 @@ select_loop (void *cls, } tasks_ready = GNUNET_SCHEDULER_run_from_driver (sh); GNUNET_assert (GNUNET_SYSERR != tasks_ready); + LOG (GNUNET_ERROR_TYPE_WARNING, + "select timeout = %s\n", + GNUNET_STRINGS_relative_time_to_string (context->timeout, GNUNET_NO)); } return GNUNET_OK; } -- 2.25.1