[thread.once.callonce]

# 32 Concurrency support library [[thread]](./#thread)

## 32.6 Mutual exclusion [[thread.mutex]](thread.mutex#thread.once.callonce)

### 32.6.7 Call once [[thread.once]](thread.once#callonce)

#### 32.6.7.2 Function call_once [thread.once.callonce]

[ð](#lib:call_once)

`template<class Callable, class... Args>
  void call_once(once_flag& flag, Callable&& func, Args&&... args);
`

[1](#1)

[#](http://github.com/Eelis/draft/tree/9adde4bc1c62ec234483e63ea3b70a59724c745a/source/threads.tex#L9409)

*Mandates*: is_invocable_v<Callable, Args...> is true[.](#1.sentence-1)

[2](#2)

[#](http://github.com/Eelis/draft/tree/9adde4bc1c62ec234483e63ea3b70a59724c745a/source/threads.tex#L9413)

*Effects*: An execution of call_once that does not call its func is a[*passive*](#def:passive) execution[.](#2.sentence-1)

An execution of call_once that calls its func is an [*active*](#def:active) execution[.](#2.sentence-2)

An active execution evaluates*INVOKE*(​std​::​forward<Callable>(func),
std​::​forward<Args>(args)...) ([[func.require]](func.require "22.10.4 Requirements"))[.](#2.sentence-3)

If such a call to func throws an exception the execution is [*exceptional*](#def:exceptional), otherwise it is [*returning*](#def:returning)[.](#2.sentence-4)

An exceptional execution propagates the exception to the caller ofcall_once[.](#2.sentence-5)

Among all executions of call_once for any givenonce_flag: at most one is a returning execution; if there is a
returning execution, it is the last active execution; and there are
passive executions only if there is a returning execution[.](#2.sentence-6)

[*Note [1](#note-1)*:

Passive
executions allow other threads to reliably observe the results produced by the
earlier returning execution[.](#2.sentence-7)

â *end note*]

[3](#3)

[#](http://github.com/Eelis/draft/tree/9adde4bc1c62ec234483e63ea3b70a59724c745a/source/threads.tex#L9433)

*Synchronization*: For any given once_flag: all active executions occur in a total
order; completion of an active execution [synchronizes with](intro.multithread#def:synchronize_with "6.10.2 Multi-threaded executions and data races [intro.multithread]") the start of the next one in this total order; and the returning execution
synchronizes with the return from all passive executions[.](#3.sentence-1)

[4](#4)

[#](http://github.com/Eelis/draft/tree/9adde4bc1c62ec234483e63ea3b70a59724c745a/source/threads.tex#L9440)

*Throws*: system_error when
an exception is required ([[thread.req.exception]](thread.req.exception "32.2.2 Exceptions")), or any exception thrown by func[.](#4.sentence-1)

[5](#5)

[#](http://github.com/Eelis/draft/tree/9adde4bc1c62ec234483e63ea3b70a59724c745a/source/threads.tex#L9445)

[*Example [1](#example-1)*: // global flag, regular functionvoid init();
std::once_flag flag;

void f() { std::call_once(flag, init);}// function static flag, function objectstruct initializer {void operator()();};

void g() {static std::once_flag flag2;
 std::call_once(flag2, initializer());}// object flag, member functionclass information { std::once_flag verified; void verifier();public:void verify() { std::call_once(verified, &information::verifier, *this); }}; â *end example*]
