NAME
RUN_ONCE
,
INIT_ONCE
, FINI_ONCE
— run a function exactly
once
SYNOPSIS
#include
<sys/once.h>
ONCE_DECL(control);
int
RUN_ONCE
(once_t
*control, int
(*init_func)(void));
int
INIT_ONCE
(once_t
*control, int
(*init_func)(void));
void
FINI_ONCE
(once_t
*control, void
(*fini_func)(void));
DESCRIPTION
RUN_ONCE
()
provides a functionality similar to
pthread_once(3). It ensures that, for a given
control,
init_func
()
is executed (successfully) exactly once. It is considered as a successful
execution if and only if init_func
() returned 0. As
long as there was no successful execution, RUN_ONCE
()
will try again each time it is called.
RUN_ONCE
()
can sleep if it's called concurrently.
INIT_ONCE
()
is used in pair with
FINI_ONCE
().
INIT_ONCE
() will only be run once similar to
RUN_ONCE
(). FINI_ONCE
() will
only be run at last time if it is called as many times as calling
INIT_ONCE
(). When
FINI_ONCE
() is executed, the next call to
INIT_ONCE
() will be executed again. That is,
INIT_ONCE
() and FINI_ONCE
()
can be nested.
RETURN VALUES
On failure, RUN_ONCE
() returns what
init_func
() returned. Otherwise, it returns 0.
EXAMPLES
The following example shows how RUN_ONCE
()
is used. Regardless of how many times some_func
() is
executed, init_func
() will be executed exactly
once.
static int init_func(void) { /* * do some initialization. */ return 0; /* success */ } int some_func(void) { static ONCE_DECL(control); RUN_ONCE(&control, init_func); /* * we are sure that init_func has already been completed here. */ }