linux-sysprog · beginner · ~10 min
The once-only semantics of pthread_once.
Model the "run exactly once" rule of pthread_once: out of many threads that try to run the initializer, only the first one actually does. Here that reduces to finding the first attempt in an array.
Implement int once_init_run_index(const int *calls, int n) that returns which call performs the one-time initialization.
calls, n: an array where calls[i] == 1 means "a thread invoked pthread_once at index i" (0 means no invocation there).Returns the index of the first 1 in the array — that call runs init_fn; every later call is a no-op. Returns -1 if no call was made (all zeros, or empty).
once_init_run_index({0,0,1,1,0,1}, 6) -> 2 (first invocation)
once_init_run_index({1,1,1}, 3) -> 0
once_init_run_index({0,0,0}, 3) -> -1 (never invoked)
once_init_run_index(NULL, 0) -> -1
-1.1, the answer is 0.pthread_once is the canonical 'initialise this lazily, exactly once, across all threads' primitive. Tracing through its semantics builds intuition.
An array calls of n flags, where calls[i]==1 means a thread invoked pthread_once at index i.
The index of the first 1 (the call that runs init_fn), or -1 if there is none.
Return the lowest index whose value is 1; -1 if all are 0 or n is 0.
int once_init_run_index(const int *calls, int n) { /* TODO */ (void)calls; (void)n; return -1; }
Returning the LAST call.
All zeros. Empty array. First index is 1.
O(n).
Solve this exercise in the browser editor — compile and run against the test harness, no setup required.