This page is a snapshot from the LWG issues list, see theLibrary Active Issues List for more information and the meaning ofC++11 status.
Section: 32.6.7.2[thread.once.callonce]Status:C++11Submitter: INCITSOpened: 2010-08-25Last modified: 2016-01-28
Priority:Not Prioritized
View all otherissues in [thread.once.callonce].
View all issues withC++11 status.
Discussion:
Addresses US-190
The term "are serialized" is never defined (32.6.7.2[thread.once.callonce] p. 2).
[Resolution proposed by ballot comment:]
Remove the sentence with "are serialized" fromparagraph 2. Add "Calls tocall_once on the sameonce_flag object shall not introduce data races(17.6.4.8)." to paragraph 3.
[2010-11-01 Daniel translates NB comment into wording]
[2011-02-17: Hans proposes an alternative resolution]
[2011-02-25: Hans, Clark, and Lawrence update the suggested wording]
[2011-02-26 Reflector discussion]
Moved to Tentatively Ready after 5 votes.
Proposed resolution:
Change 32.6.7.2[thread.once.callonce] p.2+3 as indicated:
template<class Callable, class ...Args>void call_once(once_flag& flag, Callable&& func, Args&&... args);[..]
2Effects:Calls toAn execution ofcall_onceon the sameonce_flagobject are serialized.If there has been a prior effective call tocall_onceon the sameonce_flag object, the call tocall_oncereturns without invokingfunc. If there has been no prior effective call tocall_onceon the sameonce_flagobject,INVOKE(decay_copy( std::forward<Callable>(func)), decay_copy(std::forward<Args>(args))...)is executed. The call tocall_onceis effective if and only ifINVOKE(decay_copy( std::forward<Callable>(func)), decay_copy(std::forward<Args>(args))...)returns without throwing an exception. If an exception is thrown it is propagated to the caller.call_oncethat does not call itsfuncis a passive execution.An execution ofcall_oncethat calls itsfuncis an active execution.An active execution shall callINVOKE(decay_copy(std::forward<Callable>(func)),decay_copy(std::forward<Args>(args))...). If such a call tofuncthrows an exception,the execution is exceptional, otherwise it is returning.An exceptional execution shall propagate the exception to the caller ofcall_once.Among all executions ofcall_oncefor any givenonce_flag: at most one shall be a returning execution; if there is a returning execution, it shall be the last active execution; andthere are passive executions only if there is a returning execution.[Note: Passive executions allow other threads to reliably observe the results produced by the earlier returning execution. —end note]3Synchronization:The completion of an effective call toFor any givencall_onceon aonce_flagobjectsynchronizes with (6.10.2[intro.multithread]) all subsequent calls tocall_onceon the sameonce_flagobject.once_flag: all active executions occur in a total order; completion of an active execution synchronizes with (6.10.2[intro.multithread]) the start of the next one in this total order; and the returning execution synchronizes with the return from all passive executions.