Agar


Note: The Agar manual pages follow certain conventions, notably concerning function return values. Please read AG_Intro(3) first.


SYNOPSIS

#include <agar/timeout.h>

DESCRIPTION

The agar AG_Timeout subsystem manages the scheduling and execution of specific callback functions at specific points in real-time or simulated real-time. A callback function has the prototype:


Uint32 fn (void *obj, Uint32 ival, void *arg)


Where obj is a pointer to the object managing the timeout (or NULL), ival is the delay in ticks before the next invocation, and arg is the user-supplied pointer passed to AG_ScheduleTimeout(). If the callback function returns a non-zero value, the timeout is automatically rescheduled to occur in t+n ticks.

Note that the object remains locked throughout the execution of fn() (see AG_ObjectLock(3)).

Note that AG_Timeout is used internally to implement AG_SchedEvent(3), which is an alternative interface to the one described here.

INTERFACE


void AG_SetTimeout (AG_Timeout *to, Uint32 (*fn)(void *obj, Uint32 ival, void *arg), void *arg, int flags)

void AG_ScheduleTimeout (void *obj, AG_Timeout *to, Uint32 ival)

void AG_DelTimeout (void *obj, AG_Timeout *to)

int AG_TimeoutIsScheduled (void *obj, AG_Timeout *to)

void AG_LockTimeouts (void *obj)

void AG_UnlockTimeouts (void *obj)


The AG_SetTimeout() function initializes a pre-allocated AG_Timeout structure using the specified callback function and argument.

The flags may contain:
AG_CANCEL_ONDETACHIn AG_ObjectDetach(), cancel any scheduled execution of the callback function.
AG_CANCEL_ONLOADIn AG_ObjectLoad(), cancel any scheduled execution of the callback function.

The AG_ScheduleTimeout() function schedules (or reschedules) the previously configured callback function for execution in t+ival ticks. The obj argument specifies the AG_Object(3) which is responsible for the scheduling and execution of the given callback function.

Different types of objects may implement different timing schemes involving either real-time or simulated real-time. If the obj argument is NULL, the callback is associated with a global "timer manager" object which uses the default timing algorithm.

With the default (real-time) timing algorithm, a tick is considered equivalent to roughly 1 millisecond. Different timing schemes can assign different meanings to a "tick". The AG_Timeout interface remains consistent across different timing schemes.

The AG_DelTimeout() function removes the given timeout from the queue if it is currently scheduled for execution. It is not necessary to invoke AG_DelTimeout() before AG_ScheduleTimeout() when re-scheduling an event.

AG_TimeoutIsScheduled() returns 1 if the given timeout is currently scheduled for execution. The timeouts must have been locked by the caller of the function (see below).

Both AG_ScheduleTimeout() and AG_DelTimeout() may be invoked safely from callback functions, but it is more efficient to use the callback's return value for rescheduling or cancelling timeouts.

The AG_TimeoutIsScheduled() function returns 1 if the given timeout is scheduled for execution, otherwise it returns 0.

The AG_Timeout interface is thread-safe, but it is important to use AG_LockTimeouts() and AG_UnlockTimeouts() in constructions such as:

AG_LockTimeouts(obj);
if (AG_TimeoutIsScheduled(obj, &timeout)) {
	AG_DelTimeout(obj, &timeout);
}
AG_UnlockTimeouts(obj);

CANCELLATION

Whenever an AG_Object(3) controlling timeouts is about to be detached, AG_ObjectDetach() cancels any scheduled timeout that has the AG_CANCEL_ONDETACH flag set.

Similarly, AG_ObjectLoad() cancels scheduled timeouts with the AG_CANCEL_ONLOAD flag.

AG_ObjectDestroy() always cancels all scheduled timeouts.

With a multithreaded timing scheme, cancelling a timeout might imply waiting for the termination of a thread (possibly sending it a signal as well).

ADVANCING TIME


int AG_TIMEOUTS_QUEUED (void)

void AG_ProcessTimeouts (Uint32 ticks)


The AG_TIMEOUTS_QUEUED() macro evaluates to 1 if there are possibly timeouts that need to be processed.

The AG_ProcessTimeouts() function advances the timing wheel and executes the callback functions of expired timeouts. The ticks argument is the current time in milliseconds (usually obtained from AG_GetTicks(3)). This function intended to be invoked from an event loop function such as AG_EventLoop(3), in the following way:
	if (AG_TIMEOUTS_QUEUED())
		AG_ProcessTimeouts(AG_GetTicks());

SEE ALSO

AG_Intro(3), AG_Event(3), AG_Object(3), AG_GetTicks(3)
  • "Hashed and Hierarchical Timing Wheels: Efficient Data Structures for Implementing a Timer Facility"
    George Varghese, Tony Lauck, February 14, 1996

HISTORY

The AG_Timeout facility first appeared in Agar 1.0. The interface was modeled after the OpenBSD timeout(9) API designed by Artur Grabowski and Thomas Nordin. Implementation uses the algorithms presented by George Varghese and Tony Lauck.