Skip to content

Commit d24c6bc

Browse files
committed
Merge 2017-03 CWG Motion 10
2 parents dbf8971 + 795ecfe commit d24c6bc

File tree

3 files changed

+117
-54
lines changed

3 files changed

+117
-54
lines changed

source/basic.tex

Lines changed: 87 additions & 40 deletions
Original file line numberDiff line numberDiff line change
@@ -2433,8 +2433,12 @@
24332433

24342434
\pnum
24352435
\indextext{program!start|(}%
2436-
A program shall contain a global function called \tcode{main}, which is the designated
2437-
start of the program. It is \impldef{defining \tcode{main} in freestanding environment}
2436+
A program shall contain a global function called \tcode{main}.
2437+
Executing a program starts a main thread of execution~(\ref{intro.multithread}, \ref{thread.threads})
2438+
in which the \tcode{main} function is invoked,
2439+
and in which variables of static storage duration
2440+
might be initialized~(\ref{basic.start.static}) and destroyed~(\ref{basic.start.term}).
2441+
It is \impldef{defining \tcode{main} in freestanding environment}
24382442
whether a program in a freestanding environment is required to define a \tcode{main}
24392443
function. \begin{note} In a freestanding environment, start-up and termination is
24402444
\impldef{start-up and termination in freestanding environment}; start-up contains the
@@ -2546,7 +2550,8 @@
25462550
\indextext{initialization!dynamic}%
25472551
\defn{static initialization};
25482552
all other initialization is \defn{dynamic initialization}.
2549-
Static initialization shall be performed before any dynamic initialization takes place.
2553+
All static initialization strongly happens before~(\ref{intro.races})
2554+
any dynamic initialization.
25502555
\begin{note} The dynamic initialization of non-local variables is described
25512556
in~\ref{basic.start.dynamic}; that of local static variables is described
25522557
in~\ref{stmt.dcl}. \end{note}
@@ -2612,14 +2617,28 @@
26122617
\item
26132618
If \tcode{V} has partially-ordered initialization, \tcode{W} does not have
26142619
unordered initialization, and \tcode{V} is defined before \tcode{W} in
2615-
every translation unit in which \tcode{W} is defined, the initialization of
2616-
\tcode{V} is sequenced before the initialization of \tcode{W} if the
2617-
program does not start a thread (\ref{intro.multithread}) and otherwise
2618-
happens before the initialization of \tcode{W}.
2620+
every translation unit in which \tcode{W} is defined, then
2621+
\begin{itemize}
2622+
\item
2623+
if the program starts a thread~(\ref{intro.multithread})
2624+
other than the main thread~(\ref{basic.start.main}),
2625+
the initialization of \tcode{V}
2626+
strongly happens before
2627+
the initialization of \tcode{W};
2628+
\item
2629+
otherwise,
2630+
the initialization of \tcode{V}
2631+
is sequenced before
2632+
the initialization of \tcode{W}.
2633+
\end{itemize}
26192634

26202635
\item
2621-
Otherwise, if a program starts a thread before either \tcode{V} or \tcode{W} is
2622-
initialized, the initializations of \tcode{V} and \tcode{W} are unsequenced.
2636+
Otherwise, if the program starts a thread
2637+
other than the main thread
2638+
before either \tcode{V} or \tcode{W} is initialized,
2639+
it is unspecified in which threads
2640+
the initializations of \tcode{V} and \tcode{W} occur;
2641+
the initializations are unsequenced if they occur in the same thread.
26232642

26242643
\item
26252644
Otherwise, the initializations of \tcode{V} and \tcode{W} are indeterminately sequenced.
@@ -2629,18 +2648,31 @@
26292648
ordered variables concurrently with another sequence.
26302649
\end{note}
26312650

2651+
\pnum
2652+
\indextext{non-initialization odr-use|see{odr-use, non-initialization}}%
2653+
A \defnx{non-initialization odr-use}{odr-use!non-initialization}
2654+
is an odr-use~(\ref{basic.def.odr}) not caused directly or indirectly by
2655+
the initialization of a non-local static or thread storage duration variable.
2656+
26322657
\pnum
26332658
\indextext{evaluation!unspecified order of}%
2634-
It is \impldef{dynamic initialization of static variables before \tcode{main}} whether the
2635-
dynamic initialization of a non-local non-inline variable with static storage duration
2636-
happens before the first statement of \tcode{main}. If the initialization is deferred to
2637-
happen after the first statement of \tcode{main}, it happens before the
2638-
first odr-use~(\ref{basic.def.odr}) of any non-inline function or non-inline variable
2639-
defined in the same translation unit as the variable
2640-
to be initialized.\footnote{A non-local variable with static storage duration
2659+
It is \impldef{dynamic initialization of static variables before \tcode{main}}
2660+
whether the dynamic initialization of a
2661+
non-local non-inline variable with static storage duration
2662+
is sequenced before the first statement of \tcode{main} or is deferred.
2663+
If it is deferred, it strongly happens before
2664+
any non-initialization odr-use
2665+
of any non-inline function or non-inline variable
2666+
defined in the same translation unit as the variable to be initialized.%
2667+
\footnote{A non-local variable with static storage duration
26412668
having initialization
2642-
with side effects must be initialized even if it is not
2643-
odr-used (\ref{basic.def.odr},~\ref{basic.stc.static}).}
2669+
with side effects is initialized in this case,
2670+
even if it is not itself odr-used (\ref{basic.def.odr},~\ref{basic.stc.static}).}
2671+
It is \impldef{threads and program points at which deferred dynamic initialization is performed}
2672+
in which threads and at which points in the program such deferred dynamic initialization occurs.
2673+
\begin{note}
2674+
Such points should be chosen in a way that allows the programmer to avoid deadlocks.
2675+
\end{note}
26442676
\begin{example}
26452677
\begin{codeblock}
26462678
// - File 1 -
@@ -2681,21 +2713,26 @@
26812713
\pnum
26822714
It is \impldef{dynamic initialization of static inline variables before \tcode{main}}
26832715
whether the dynamic initialization of a
2684-
non-local inline variable with static storage duration happens before the
2685-
first statement of \tcode{main}. If the initialization is deferred
2686-
to happen after the first statement of \tcode{main}, it happens before
2687-
the first odr-use~(\ref{basic.def.odr}) of that variable.
2716+
non-local inline variable with static storage duration
2717+
is sequenced before the first statement of \tcode{main} or is deferred.
2718+
If it is deferred, it strongly happens before
2719+
any non-initialization odr-use
2720+
of that variable.
2721+
It is \impldef{threads and program points at which deferred dynamic initialization is performed}
2722+
in which threads and at which points in the program such deferred dynamic initialization occurs.
26882723

26892724
\pnum
26902725
It is \impldef{dynamic initialization of thread-local variables before entry}
2691-
whether the dynamic initialization of a non-local non-inline variable with static
2692-
or thread storage duration is sequenced before
2693-
the first statement of the initial function of the thread.
2694-
If the initialization is deferred to some point in time sequenced after
2695-
the first statement of the initial function of the thread,
2696-
it is sequenced before the first odr-use~(\ref{basic.def.odr})
2697-
of any non-inline variable with thread storage duration defined
2698-
in the same translation unit as the variable to be initialized.
2726+
whether the dynamic initialization of a
2727+
non-local non-inline variable with thread storage duration
2728+
is sequenced before the first statement of the initial function of a thread or is deferred.
2729+
If it is deferred,
2730+
the initialization associated with the entity for thread \placeholder{t}
2731+
is sequenced before the first non-initialization odr-use by \placeholder{t}
2732+
of any non-inline variable with thread storage duration
2733+
defined in the same translation unit as the variable to be initialized.
2734+
It is \impldef{threads and program points at which deferred dynamic initialization is performed}
2735+
in which threads and at which points in the program such deferred dynamic initialization occurs.
26992736

27002737
\pnum
27012738
If the initialization of a non-local variable with static or thread storage duration
@@ -2711,24 +2748,34 @@
27112748
\indextext{\idxcode{main} function!return from}%
27122749
Destructors~(\ref{class.dtor}) for initialized objects
27132750
(that is, objects whose lifetime~(\ref{basic.life}) has begun)
2714-
with static storage duration
2715-
are called as a result of returning from \tcode{main} and as a result of calling
2751+
with static storage duration,
2752+
and functions registered with \tcode{std::atexit},
2753+
are called as part of a call to
27162754
\indextext{\idxcode{exit}}%
27172755
\indexlibrary{\idxcode{exit}}%
27182756
\tcode{std::exit}~(\ref{support.start.term}).
2757+
The call to \tcode{std::exit} is sequenced before
2758+
the invocations of the destructors and the registered functions.
2759+
\begin{note}
2760+
Returning from \tcode{main} invokes \tcode{std::exit}~(\ref{basic.start.main}).
2761+
\end{note}
2762+
2763+
\pnum
27192764
Destructors for initialized objects with thread storage duration within a given thread
27202765
are called as a result of returning from the initial function of that thread and as a
27212766
result of that thread calling \tcode{std::exit}.
27222767
The completions of the destructors for all initialized objects with thread storage
2723-
duration within that thread are sequenced before the initiation of the destructors of
2768+
duration within that thread strongly happen before the initiation of the destructors of
27242769
any object with static storage duration.
2725-
If the completion of the constructor or dynamic initialization of an object with thread
2726-
storage duration is sequenced before that of another, the completion of the destructor
2727-
of the second is sequenced before the initiation of the destructor of the first.
2770+
2771+
\pnum
27282772
If the completion of the constructor or dynamic initialization of an object with static
2773+
storage duration strongly happens before that of another, the completion of the destructor
2774+
of the second is sequenced before the initiation of the destructor of the first.
2775+
If the completion of the constructor or dynamic initialization of an object with thread
27292776
storage duration is sequenced before that of another, the completion of the destructor
27302777
of the second is sequenced before the initiation of the destructor of the first.
2731-
\begin{note} This definition permits concurrent destruction. \end{note} If an object is
2778+
If an object is
27322779
initialized statically, the object is destroyed in the same order as if
27332780
the object was dynamically initialized. For an object of array or class
27342781
type, all subobjects of that object are destroyed before any block-scope
@@ -2750,13 +2797,13 @@
27502797
\indextext{\idxcode{atexit}}%
27512798
\indexlibrary{\idxcode{atexit}}%
27522799
If the completion of the initialization of an object with static storage
2753-
duration is sequenced before a call to \tcode{std::atexit}~(see
2800+
duration strongly happens before a call to \tcode{std::atexit}~(see
27542801
\tcode{<cstdlib>},~\ref{support.start.term}), the call to the function passed to
27552802
\tcode{std::atexit} is sequenced before the call to the destructor for the object. If a
2756-
call to \tcode{std::atexit} is sequenced before the completion of the initialization of
2803+
call to \tcode{std::atexit} strongly happens before the completion of the initialization of
27572804
an object with static storage duration, the call to the destructor for the
27582805
object is sequenced before the call to the function passed to \tcode{std::atexit}. If a
2759-
call to \tcode{std::atexit} is sequenced before another call to \tcode{std::atexit}, the
2806+
call to \tcode{std::atexit} strongly happens before another call to \tcode{std::atexit}, the
27602807
call to the function passed to the second \tcode{std::atexit} call is sequenced before
27612808
the call to the function passed to the first \tcode{std::atexit} call.
27622809

source/intro.tex

Lines changed: 27 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -795,23 +795,13 @@
795795
A conforming implementation executing a well-formed program shall
796796
produce the same observable behavior as one of the possible executions
797797
of the corresponding instance of the abstract machine with the
798-
same program and the same input. However, if any such execution contains an undefined operation, this International Standard places no
798+
same program and the same input.
799+
\indextext{behavior!undefined}%
800+
However, if any such execution contains an undefined operation, this International Standard places no
799801
requirement on the implementation executing that program with that input
800802
(not even with regard to operations preceding the first undefined
801803
operation).
802804

803-
\indextext{behavior!unspecified}%
804-
\indextext{behavior!undefined}%
805-
\indextext{behavior!on receipt of signal}%
806-
\indextext{signal}%
807-
\pnum
808-
If a signal handler is executed as a result of a call to the \tcode{std::raise}
809-
function, then the execution of the handler is sequenced after the invocation
810-
of the \tcode{std::raise} function and before its return.
811-
\begin{note} When a signal is received for another reason, the execution of the
812-
signal handler is usually unsequenced with respect to the rest of the program.
813-
\end{note}
814-
815805
\pnum
816806
An instance of each object with automatic storage
817807
duration~(\ref{basic.stc.auto}) is associated with each entry into its
@@ -1124,6 +1114,16 @@
11241114
described above) are features of the function calls as evaluated,
11251115
whatever the syntax of the expression that calls the function might be.%
11261116
\indextext{value computation|)}%
1117+
1118+
\indextext{behavior!on receipt of signal}%
1119+
\indextext{signal}%
1120+
\pnum
1121+
If a signal handler is executed as a result of a call to the \tcode{std::raise}
1122+
function, then the execution of the handler is sequenced after the invocation
1123+
of the \tcode{std::raise} function and before its return.
1124+
\begin{note} When a signal is received for another reason, the execution of the
1125+
signal handler is usually unsequenced with respect to the rest of the program.
1126+
\end{note}
11271127
\indextext{program execution|)}
11281128

11291129
\rSec1[intro.multithread]{Multi-threaded executions and data races}
@@ -1328,6 +1328,20 @@
13281328
in the ``happens before'' relation. \begin{note} This cycle would otherwise be
13291329
possible only through the use of consume operations. \end{note}
13301330

1331+
\pnum
1332+
An evaluation \placeholder{A} \defn{strongly happens before} an evaluation \placeholder{B}
1333+
if either
1334+
\begin{itemize}
1335+
\item \placeholder{A} is sequenced before \placeholder{B}, or
1336+
\item \placeholder{A} synchronizes with \placeholder{B}, or
1337+
\item \placeholder{A} strongly happens before \placeholder{X} and \placeholder{X} strongly happens before \placeholder{B}.
1338+
\end{itemize}
1339+
\begin{note}
1340+
In the absence of consume operations,
1341+
the happens before and strongly happens before relations are identical.
1342+
Strongly happens before essentially excludes consume operations.
1343+
\end{note}
1344+
13311345
\pnum
13321346
A \defnx{visible side effect}{side effects!visible} \placeholder{A} on a scalar object or bit-field \placeholder{M}
13331347
with respect to a value computation \placeholder{B} of \placeholder{M} satisfies the

source/support.tex

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1785,7 +1785,9 @@
17851785
function does not provide a handler for a thrown exception, \tcode{std::terminate()} shall
17861786
be called.\indexlibrary{\idxcode{terminate}}
17871787
\begin{note}
1788-
\tcode{at_quick_exit} may call a registered function from a different thread
1788+
A function registered via \tcode{at_quick_exit}
1789+
is invoked by the thread that calls \tcode{quick_exit},
1790+
which can be a different thread
17891791
than the one that registered it, so registered functions should not rely on the identity
17901792
of objects with thread storage duration.
17911793
\end{note}

0 commit comments

Comments
 (0)