On Tue, 2017-09-19 at 15:36 +0200, Florian Weimer wrote: > On 09/19/2017 03:32 PM, Torvald Riegel wrote: > > On Tue, 2017-09-19 at 07:19 +0200, Florian Weimer wrote: > >> On 09/18/2017 10:07 PM, Torvald Riegel wrote: > >>> On Mon, 2017-09-18 at 14:19 +0200, Florian Weimer wrote: > >>>> I would like to see the GCC project to document that if the address of a > >>>> member is taken, this does not constitute an access to the object as a > >>>> whole. > >>>> > >>>> That is, in the following code: > >>>> > >>>> #include <stdatomic.h> > >>>> > >>>> struct S { > >>>> _Atomic int a; > >>>> int b; > >>>> }; > >>>> > >>>> int > >>>> load_a (struct S *p) > >>>> { > >>>> return atomic_load_explicit (&p->a, memory_order_relaxed); > >>>> } > >>>> > >>>> int > >>>> store_b (struct S *p, int b) > >>>> { > >>>> p->b = b; > >>>> } > >>>> > >>>> If one thread calls load_a and another thread calls store_b on the same > >>>> struct S *, no data race happens. > >>> > >>> There is no data race in this example; a and b are separate objects as > >>> far as the memory model is concerned. That's my understanding and I > >>> believe also the understanding in the C++ committee. > >> > >> I'm not sure what the C++ standard says in this matter. > >> > >> C++ may indeed have addressed this and related issues (e.g., that a > >> memory location which is passed by reference to a function is not > >> actually read in the caller). > > > > The memory models of C and C++ are intended to be the same. In the > > example above, the values of p in both calls are supposed to be equal, > > so accesses go to the same object of type S; as far as the memory model > > is concerned, a and b are separate objects. > > The definition of “access” is quite different in C and C++, and this > affects the definition of a data race. The core model is hopefully very > similar, but the languages around that are quite different, so similar > syntax can have very different behavior.
The behavior is intended to be the same (including cases such as the example), although there may be corner cases where it's not (eg, signal handlers are still being worked on). The example above (where accesses by different threads go to different members of the same struct object) is not a data race; otherwise, you could never embed a lock and data into the same struct, for example. I don't know enough about the details of the C standardese to assess whether the wording is indeed imprecise.