From Jason Turner

[intro.races]

Diff to HTML by rtfpessoa

Files changed (1) hide show
  1. tmp/tmpzsulnlyk/{from.md → to.md} +289 -0
tmp/tmpzsulnlyk/{from.md → to.md} RENAMED
@@ -0,0 +1,289 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ ### Data races <a id="intro.races">[[intro.races]]</a>
2
+
3
+ The value of an object visible to a thread *T* at a particular point is
4
+ the initial value of the object, a value assigned to the object by *T*,
5
+ or a value assigned to the object by another thread, according to the
6
+ rules below.
7
+
8
+ [*Note 1*: In some cases, there may instead be undefined behavior. Much
9
+ of this section is motivated by the desire to support atomic operations
10
+ with explicit and detailed visibility constraints. However, it also
11
+ implicitly supports a simpler view for more restricted
12
+ programs. — *end note*]
13
+
14
+ Two expression evaluations *conflict* if one of them modifies a memory
15
+ location ([[intro.memory]]) and the other one reads or modifies the
16
+ same memory location.
17
+
18
+ The library defines a number of atomic operations (Clause  [[atomics]])
19
+ and operations on mutexes (Clause  [[thread]]) that are specially
20
+ identified as synchronization operations. These operations play a
21
+ special role in making assignments in one thread visible to another. A
22
+ synchronization operation on one or more memory locations is either a
23
+ consume operation, an acquire operation, a release operation, or both an
24
+ acquire and release operation. A synchronization operation without an
25
+ associated memory location is a fence and can be either an acquire
26
+ fence, a release fence, or both an acquire and release fence. In
27
+ addition, there are relaxed atomic operations, which are not
28
+ synchronization operations, and atomic read-modify-write operations,
29
+ which have special characteristics.
30
+
31
+ [*Note 2*: For example, a call that acquires a mutex will perform an
32
+ acquire operation on the locations comprising the mutex.
33
+ Correspondingly, a call that releases the same mutex will perform a
34
+ release operation on those same locations. Informally, performing a
35
+ release operation on *A* forces prior side effects on other memory
36
+ locations to become visible to other threads that later perform a
37
+ consume or an acquire operation on *A*. “Relaxed” atomic operations are
38
+ not synchronization operations even though, like synchronization
39
+ operations, they cannot contribute to data races. — *end note*]
40
+
41
+ All modifications to a particular atomic object *M* occur in some
42
+ particular total order, called the *modification order* of *M*.
43
+
44
+ [*Note 3*: There is a separate order for each atomic object. There is
45
+ no requirement that these can be combined into a single total order for
46
+ all objects. In general this will be impossible since different threads
47
+ may observe modifications to different objects in inconsistent
48
+ orders. — *end note*]
49
+
50
+ A *release sequence* headed by a release operation *A* on an atomic
51
+ object *M* is a maximal contiguous sub-sequence of side effects in the
52
+ modification order of *M*, where the first operation is `A`, and every
53
+ subsequent operation
54
+
55
+ - is performed by the same thread that performed `A`, or
56
+ - is an atomic read-modify-write operation.
57
+
58
+ Certain library calls *synchronize with* other library calls performed
59
+ by another thread. For example, an atomic store-release synchronizes
60
+ with a load-acquire that takes its value from the store (
61
+ [[atomics.order]]).
62
+
63
+ [*Note 4*: Except in the specified cases, reading a later value does
64
+ not necessarily ensure visibility as described below. Such a requirement
65
+ would sometimes interfere with efficient implementation. — *end note*]
66
+
67
+ [*Note 5*: The specifications of the synchronization operations define
68
+ when one reads the value written by another. For atomic objects, the
69
+ definition is clear. All operations on a given mutex occur in a single
70
+ total order. Each mutex acquisition “reads the value written” by the
71
+ last mutex release. — *end note*]
72
+
73
+ An evaluation *A* *carries a dependency* to an evaluation *B* if
74
+
75
+ - the value of *A* is used as an operand of *B*, unless:
76
+ - *B* is an invocation of any specialization of
77
+ `std::kill_dependency` ([[atomics.order]]), or
78
+ - *A* is the left operand of a built-in logical AND (`&&`, see 
79
+ [[expr.log.and]]) or logical OR (`||`, see  [[expr.log.or]])
80
+ operator, or
81
+ - *A* is the left operand of a conditional (`?:`, see  [[expr.cond]])
82
+ operator, or
83
+ - *A* is the left operand of the built-in comma (`,`) operator (
84
+ [[expr.comma]]);
85
+
86
+ or
87
+ - *A* writes a scalar object or bit-field *M*, *B* reads the value
88
+ written by *A* from *M*, and *A* is sequenced before *B*, or
89
+ - for some evaluation *X*, *A* carries a dependency to *X*, and *X*
90
+ carries a dependency to *B*.
91
+
92
+ [*Note 6*: “Carries a dependency to” is a subset of “is sequenced
93
+ before”, and is similarly strictly intra-thread. — *end note*]
94
+
95
+ An evaluation *A* is *dependency-ordered before* an evaluation *B* if
96
+
97
+ - *A* performs a release operation on an atomic object *M*, and, in
98
+ another thread, *B* performs a consume operation on *M* and reads a
99
+ value written by any side effect in the release sequence headed by
100
+ *A*, or
101
+ - for some evaluation *X*, *A* is dependency-ordered before *X* and *X*
102
+ carries a dependency to *B*.
103
+
104
+ [*Note 7*: The relation “is dependency-ordered before” is analogous to
105
+ “synchronizes with”, but uses release/consume in place of
106
+ release/acquire. — *end note*]
107
+
108
+ An evaluation *A* *inter-thread happens before* an evaluation *B* if
109
+
110
+ - *A* synchronizes with *B*, or
111
+ - *A* is dependency-ordered before *B*, or
112
+ - for some evaluation *X*
113
+ - *A* synchronizes with *X* and *X* is sequenced before *B*, or
114
+ - *A* is sequenced before *X* and *X* inter-thread happens before *B*,
115
+ or
116
+ - *A* inter-thread happens before *X* and *X* inter-thread happens
117
+ before *B*.
118
+
119
+ [*Note 8*: The “inter-thread happens before” relation describes
120
+ arbitrary concatenations of “sequenced before”, “synchronizes with” and
121
+ “dependency-ordered before” relationships, with two exceptions. The
122
+ first exception is that a concatenation is not permitted to end with
123
+ “dependency-ordered before” followed by “sequenced before”. The reason
124
+ for this limitation is that a consume operation participating in a
125
+ “dependency-ordered before” relationship provides ordering only with
126
+ respect to operations to which this consume operation actually carries a
127
+ dependency. The reason that this limitation applies only to the end of
128
+ such a concatenation is that any subsequent release operation will
129
+ provide the required ordering for a prior consume operation. The second
130
+ exception is that a concatenation is not permitted to consist entirely
131
+ of “sequenced before”. The reasons for this limitation are (1) to permit
132
+ “inter-thread happens before” to be transitively closed and (2) the
133
+ “happens before” relation, defined below, provides for relationships
134
+ consisting entirely of “sequenced before”. — *end note*]
135
+
136
+ An evaluation *A* *happens before* an evaluation *B* (or, equivalently,
137
+ *B* *happens after* *A*) if:
138
+
139
+ - *A* is sequenced before *B*, or
140
+ - *A* inter-thread happens before *B*.
141
+
142
+ The implementation shall ensure that no program execution demonstrates a
143
+ cycle in the “happens before” relation.
144
+
145
+ [*Note 9*: This cycle would otherwise be possible only through the use
146
+ of consume operations. — *end note*]
147
+
148
+ An evaluation *A* *strongly happens before* an evaluation *B* if either
149
+
150
+ - *A* is sequenced before *B*, or
151
+ - *A* synchronizes with *B*, or
152
+ - *A* strongly happens before *X* and *X* strongly happens before *B*.
153
+
154
+ [*Note 10*: In the absence of consume operations, the happens before
155
+ and strongly happens before relations are identical. Strongly happens
156
+ before essentially excludes consume operations. — *end note*]
157
+
158
+ A *visible side effect* *A* on a scalar object or bit-field *M* with
159
+ respect to a value computation *B* of *M* satisfies the conditions:
160
+
161
+ - *A* happens before *B* and
162
+ - there is no other side effect *X* to *M* such that *A* happens before
163
+ *X* and *X* happens before *B*.
164
+
165
+ The value of a non-atomic scalar object or bit-field *M*, as determined
166
+ by evaluation *B*, shall be the value stored by the visible side effect
167
+ *A*.
168
+
169
+ [*Note 11*: If there is ambiguity about which side effect to a
170
+ non-atomic object or bit-field is visible, then the behavior is either
171
+ unspecified or undefined. — *end note*]
172
+
173
+ [*Note 12*: This states that operations on ordinary objects are not
174
+ visibly reordered. This is not actually detectable without data races,
175
+ but it is necessary to ensure that data races, as defined below, and
176
+ with suitable restrictions on the use of atomics, correspond to data
177
+ races in a simple interleaved (sequentially consistent)
178
+ execution. — *end note*]
179
+
180
+ The value of an atomic object *M*, as determined by evaluation *B*,
181
+ shall be the value stored by some side effect *A* that modifies *M*,
182
+ where *B* does not happen before *A*.
183
+
184
+ [*Note 13*: The set of such side effects is also restricted by the rest
185
+ of the rules described here, and in particular, by the coherence
186
+ requirements below. — *end note*]
187
+
188
+ If an operation *A* that modifies an atomic object *M* happens before an
189
+ operation *B* that modifies *M*, then *A* shall be earlier than *B* in
190
+ the modification order of *M*.
191
+
192
+ [*Note 14*: This requirement is known as write-write
193
+ coherence. — *end note*]
194
+
195
+ If a value computation *A* of an atomic object *M* happens before a
196
+ value computation *B* of *M*, and *A* takes its value from a side effect
197
+ *X* on *M*, then the value computed by *B* shall either be the value
198
+ stored by *X* or the value stored by a side effect *Y* on *M*, where *Y*
199
+ follows *X* in the modification order of *M*.
200
+
201
+ [*Note 15*: This requirement is known as read-read
202
+ coherence. — *end note*]
203
+
204
+ If a value computation *A* of an atomic object *M* happens before an
205
+ operation *B* that modifies *M*, then *A* shall take its value from a
206
+ side effect *X* on *M*, where *X* precedes *B* in the modification order
207
+ of *M*.
208
+
209
+ [*Note 16*: This requirement is known as read-write
210
+ coherence. — *end note*]
211
+
212
+ If a side effect *X* on an atomic object *M* happens before a value
213
+ computation *B* of *M*, then the evaluation *B* shall take its value
214
+ from *X* or from a side effect *Y* that follows *X* in the modification
215
+ order of *M*.
216
+
217
+ [*Note 17*: This requirement is known as write-read
218
+ coherence. — *end note*]
219
+
220
+ [*Note 18*: The four preceding coherence requirements effectively
221
+ disallow compiler reordering of atomic operations to a single object,
222
+ even if both operations are relaxed loads. This effectively makes the
223
+ cache coherence guarantee provided by most hardware available to
224
+ C++atomic operations. — *end note*]
225
+
226
+ [*Note 19*: The value observed by a load of an atomic depends on the
227
+ “happens before” relation, which depends on the values observed by loads
228
+ of atomics. The intended reading is that there must exist an association
229
+ of atomic loads with modifications they observe that, together with
230
+ suitably chosen modification orders and the “happens before” relation
231
+ derived as described above, satisfy the resulting constraints as imposed
232
+ here. — *end note*]
233
+
234
+ Two actions are *potentially concurrent* if
235
+
236
+ - they are performed by different threads, or
237
+ - they are unsequenced, at least one is performed by a signal handler,
238
+ and they are not both performed by the same signal handler invocation.
239
+
240
+ The execution of a program contains a *data race* if it contains two
241
+ potentially concurrent conflicting actions, at least one of which is not
242
+ atomic, and neither happens before the other, except for the special
243
+ case for signal handlers described below. Any such data race results in
244
+ undefined behavior.
245
+
246
+ [*Note 20*: It can be shown that programs that correctly use mutexes
247
+ and `memory_order_seq_cst` operations to prevent all data races and use
248
+ no other synchronization operations behave as if the operations executed
249
+ by their constituent threads were simply interleaved, with each value
250
+ computation of an object being taken from the last side effect on that
251
+ object in that interleaving. This is normally referred to as “sequential
252
+ consistency”. However, this applies only to data-race-free programs, and
253
+ data-race-free programs cannot observe most program transformations that
254
+ do not change single-threaded program semantics. In fact, most
255
+ single-threaded program transformations continue to be allowed, since
256
+ any program that behaves differently as a result must perform an
257
+ undefined operation. — *end note*]
258
+
259
+ Two accesses to the same object of type `volatile std::sig_atomic_t` do
260
+ not result in a data race if both occur in the same thread, even if one
261
+ or more occurs in a signal handler. For each signal handler invocation,
262
+ evaluations performed by the thread invoking a signal handler can be
263
+ divided into two groups *A* and *B*, such that no evaluations in *B*
264
+ happen before evaluations in *A*, and the evaluations of such
265
+ `volatile std::sig_atomic_t` objects take values as though all
266
+ evaluations in *A* happened before the execution of the signal handler
267
+ and the execution of the signal handler happened before all evaluations
268
+ in *B*.
269
+
270
+ [*Note 21*: Compiler transformations that introduce assignments to a
271
+ potentially shared memory location that would not be modified by the
272
+ abstract machine are generally precluded by this International Standard,
273
+ since such an assignment might overwrite another assignment by a
274
+ different thread in cases in which an abstract machine execution would
275
+ not have encountered a data race. This includes implementations of data
276
+ member assignment that overwrite adjacent members in separate memory
277
+ locations. Reordering of atomic loads in cases in which the atomics in
278
+ question may alias is also generally precluded, since this may violate
279
+ the coherence rules. — *end note*]
280
+
281
+ [*Note 22*: Transformations that introduce a speculative read of a
282
+ potentially shared memory location may not preserve the semantics of the
283
+ C++program as defined in this International Standard, since they
284
+ potentially introduce a data race. However, they are typically valid in
285
+ the context of an optimizing compiler that targets a specific machine
286
+ with well-defined semantics for data races. They would be invalid for a
287
+ hypothetical machine that is not tolerant of races or provides hardware
288
+ race detection. — *end note*]
289
+