Groups | Search | Server Info | Keyboard shortcuts | Login | Register [http] [https] [nntp] [nntps]
Groups > comp.lang.c > #96367 > unrolled thread
| Started by | spacewar@gmail.com |
|---|---|
| First post | 2016-11-10 19:34 -0800 |
| Last post | 2016-11-15 10:42 -0800 |
| Articles | 14 — 6 participants |
Back to article view | Back to comp.lang.c
compound assignment to atomic type spacewar@gmail.com - 2016-11-10 19:34 -0800
Re: compound assignment to atomic type Ben Bacarisse <ben.usenet@bsb.me.uk> - 2016-11-11 16:04 +0000
Re: compound assignment to atomic type supercat@casperkitty.com - 2016-11-11 09:01 -0800
Re: compound assignment to atomic type Tim Rentsch <txr@alumni.caltech.edu> - 2016-11-15 10:54 -0800
Re: compound assignment to atomic type spacewar@gmail.com - 2016-11-12 00:48 -0800
Re: compound assignment to atomic type Ben Bacarisse <ben.usenet@bsb.me.uk> - 2016-11-12 11:06 +0000
Re: compound assignment to atomic type supercat <flatfinger@casperkitty.com> - 2016-11-12 11:03 -0800
Re: compound assignment to atomic type Tim Rentsch <txr@alumni.caltech.edu> - 2016-11-13 10:57 -0800
Re: compound assignment to atomic type Tim Rentsch <txr@alumni.caltech.edu> - 2016-11-13 10:31 -0800
Re: compound assignment to atomic type "Chris M. Thomasson" <invalid@invalid.invalid> - 2016-11-12 11:24 -0800
Re: compound assignment to atomic type Tim Rentsch <txr@alumni.caltech.edu> - 2016-11-13 10:59 -0800
Re: compound assignment to atomic type "Chris M. Thomasson" <invalid@invalid.invalid> - 2016-11-13 17:34 -0800
Re: compound assignment to atomic type "Chris M. Thomasson" <invalid@invalid.invalid> - 2016-11-13 17:48 -0800
Re: compound assignment to atomic type Tim Rentsch <txr@alumni.caltech.edu> - 2016-11-15 10:42 -0800
| From | spacewar@gmail.com |
|---|---|
| Date | 2016-11-10 19:34 -0800 |
| Subject | compound assignment to atomic type |
| Message-ID | <c023fb24-93f5-463d-8618-e19499f78f0a@googlegroups.com> |
I'm confused about C11 compound assignments with E1 (left hand side) being an atomic type.
§6.5.16.2 ¶3 states:
If E1 has an atomic type, compound assignment is a
read-modify-write operation with memory_order_seq_cst memory order
semantics.
Footnote 113 says
Where a pointer to an atomic object can be formed and E1 and E2 have
integer type, this is equivalent to the following code sequence [...]"
with the code sequence using atomic_compare_exchange_strong().
On the other hand, §7.17.7.5 ¶5 states:
NOTE The operation of the atomic_fetch and modify generic functions are
nearly equivalent to the operation of the corresponding op= compound
assignment operators. The only differences are that the compound
assignment operators are not guaranteed to operate atomically, [...]
Doesn't that directly contradict §6.5.16.2 ¶3 and footnote 113?
GCC 6.2.1 generates atomic RMW code for compound assignments with atomic LHS, but the NOTE in §7.17.7.5 makes me worry about that being non-portable.
[toc] | [next] | [standalone]
| From | Ben Bacarisse <ben.usenet@bsb.me.uk> |
|---|---|
| Date | 2016-11-11 16:04 +0000 |
| Message-ID | <8737iyovea.fsf@bsb.me.uk> |
| In reply to | #96367 |
spacewar@gmail.com writes: > I'm confused about C11 compound assignments with E1 (left hand side) > being an atomic type. > > §6.5.16.2 ¶3 states: > If E1 has an atomic type, compound assignment is a > read-modify-write operation with memory_order_seq_cst memory order > semantics. > > Footnote 113 says > Where a pointer to an atomic object can be formed and E1 and E2 have > integer type, this is equivalent to the following code sequence [...]" > with the code sequence using atomic_compare_exchange_strong(). > > On the other hand, §7.17.7.5 ¶5 states: > NOTE The operation of the atomic_fetch and modify generic functions are > nearly equivalent to the operation of the corresponding op= compound > assignment operators. The only differences are that the compound > assignment operators are not guaranteed to operate atomically, [...] > > Doesn't that directly contradict §6.5.16.2 ¶3 and footnote 113? This came up in a DR about the use of various terms relating to atomic types and atomic operations: http://www.open-std.org/jtc1/sc22/wg14/www/docs/summary.htm#dr_486 > GCC 6.2.1 generates atomic RMW code for compound assignments with > atomic LHS, but the NOTE in §7.17.7.5 makes me worry about that being > non-portable. The DR is under review, but I get the feeling the committee agrees that the wording is confusing. I think you can rely on x <op>= y having the RMW sematics described in 6.5.16.2 (along with the extensive footnote 113). -- Ben.
[toc] | [prev] | [next] | [standalone]
| From | supercat@casperkitty.com |
|---|---|
| Date | 2016-11-11 09:01 -0800 |
| Message-ID | <d41c2041-75f0-44ea-b64f-576e8a0f64d1@googlegroups.com> |
| In reply to | #96383 |
On Friday, November 11, 2016 at 10:04:38 AM UTC-6, Ben Bacarisse wrote: > This came up in a DR about the use of various terms relating to atomic > types and atomic operations: > > http://www.open-std.org/jtc1/sc22/wg14/www/docs/summary.htm#dr_486 I'm not sure why the authors seem to have trouble with the idea that implementations which don't meet certain common-but-possibly-not-universal requirements (e.g. use of two's-complement arithmetic) would be unable to support the optional threading features. I'm also not clear what the author of the Standard finds unclear about the notion that atomic pointer operations may yield invalid pointers but would otherwise have defined behavior; the obvious sensible meaning would be that an atomic operation on any type will never do anything other than change some, all, or none of the bits in the storage associated therewith. The resulting pattern of bits may or may not be meaningful, but the requested atomic operation will never have any other effect. It may also be helpful to have a Standard make clear that atomically adding or subtracting any combination of displacements to a pointer, in any order, will be equivalent to adding or subtracting the mathematical sum of those displacements, without regard for whether intermediate values would be valid pointers.
[toc] | [prev] | [next] | [standalone]
| From | Tim Rentsch <txr@alumni.caltech.edu> |
|---|---|
| Date | 2016-11-15 10:54 -0800 |
| Message-ID | <kfninrosheo.fsf@x-alumni2.alumni.caltech.edu> |
| In reply to | #96390 |
supercat@casperkitty.com writes: > On Friday, November 11, 2016 at 10:04:38 AM UTC-6, Ben Bacarisse wrote: >> This came up in a DR about the use of various terms relating to atomic >> types and atomic operations: >> >> http://www.open-std.org/jtc1/sc22/wg14/www/docs/summary.htm#dr_486 > > I'm not sure why the authors seem to have trouble with the idea that > implementations which don't meet certain common-but-possibly-not- > universal requirements (e.g. use of two's-complement arithmetic) > would be unable to support the optional threading features. Assumes facts not in evidence. > I'm also not clear what the author of the Standard finds unclear > about the notion that atomic pointer operations may yield invalid > pointers but would otherwise have defined behavior; [...] Also assumes facts not in evidence.
[toc] | [prev] | [next] | [standalone]
| From | spacewar@gmail.com |
|---|---|
| Date | 2016-11-12 00:48 -0800 |
| Message-ID | <a78d7205-33d3-48d1-bf53-a928e042bdcc@googlegroups.com> |
| In reply to | #96383 |
On Friday, November 11, 2016 at 9:04:38 AM UTC-7, Ben Bacarisse wrote: > This came up in a DR about the use of various terms relating to atomic > types and atomic operations: > > http://www.open-std.org/jtc1/sc22/wg14/www/docs/summary.htm#dr_486 > The DR is under review, but I get the feeling the committee agrees that > the wording is confusing. I think you can rely on x <op>= y having the > RMW sematics described in 6.5.16.2 (along with the extensive footnote > 113). Thanks! I'm rather unimpressed with the committee's statement that it "does not feel that this DR is 'actionable'", and that they apparently don't want to address the issues in a Technical Corrigendum. I don't see the outright contradiction between §6.5.16.2 ¶3 and §7.17.7.5 ¶5 as a "small inconsistency". Oh well.
[toc] | [prev] | [next] | [standalone]
| From | Ben Bacarisse <ben.usenet@bsb.me.uk> |
|---|---|
| Date | 2016-11-12 11:06 +0000 |
| Message-ID | <87wpg9lzxr.fsf@bsb.me.uk> |
| In reply to | #96408 |
spacewar@gmail.com writes: > On Friday, November 11, 2016 at 9:04:38 AM UTC-7, Ben Bacarisse wrote: >> This came up in a DR about the use of various terms relating to atomic >> types and atomic operations: >> >> http://www.open-std.org/jtc1/sc22/wg14/www/docs/summary.htm#dr_486 > >> The DR is under review, but I get the feeling the committee agrees that >> the wording is confusing. I think you can rely on x <op>= y having the >> RMW sematics described in 6.5.16.2 (along with the extensive footnote >> 113). > > Thanks! I'm rather unimpressed with the committee's statement that it > "does not feel that this DR is 'actionable'", and that they apparently > don't want to address the issues in a Technical Corrigendum. I don't > see the outright contradiction between §6.5.16.2 ¶3 and §7.17.7.5 ¶5 > as a "small inconsistency". I don't see the wording as an outright contradiction. The problem comes down to what atomic means, and the depends on the observer. x += y is atomic to an observer in C, but not (I think[1]) to an observer of volatile accesses. The functions of 7.17.7.5 are (again, I think) atomic to all but a hardware observer. [1] I'm not an expert in this. I'd welcome a technical discussion of C's atomic primitives because I either don't understand them properly or there are other rough edges to the description of them. -- Ben.
[toc] | [prev] | [next] | [standalone]
| From | supercat <flatfinger@casperkitty.com> |
|---|---|
| Date | 2016-11-12 11:03 -0800 |
| Message-ID | <3468d7af-8959-415f-9da8-e702b0dfe5fd@googlegroups.com> |
| In reply to | #96409 |
On Saturday, November 12, 2016 at 5:07:03 AM UTC-6, Ben Bacarisse wrote: > I don't see the wording as an outright contradiction. The problem comes > down to what atomic means, and the depends on the observer. x += y is > atomic to an observer in C, but not (I think[1]) to an observer of > volatile accesses. The functions of 7.17.7.5 are (again, I think) > atomic to all but a hardware observer. > > [1] I'm not an expert in this. I'd welcome a technical discussion of > C's atomic primitives because I either don't understand them properly or > there are other rough edges to the description of them. There are a number of places where the Standard defines certain syntactic forms as equivalent to others, where it would be more helpful to define the standard-mandated behavioral aspects as being equivalent but explicitly allow for the operations to differ in other regards not covered by the Standard. For example, some hardware platforms include operations to read a value, write a value, and perform various atomic operations on a value. On some platforms, the constructs "atomic += 1;" and "atomic = atomic + 1;" may have usefully-different meanings, and it would be helpful to have the Standard specify that when an atomic read-modify-write will have different effect from an atomic read, computation, and atomic write, compilers may use syntax to distinguish the two forms. It might also be helpful to suggest that compilers include an option to reject the use of compound operators on atomic values in cases where the operation as a whole cannot be made atomic, or provide a construct to request an atomic read-modify- write sequence of a form not supported by any existing operators (e.g. the Freescale KL27 has hardware so that a single CPU instruction can trigger atomic operation of the form ioreg &= ~mask; ioreg |= (value & mask); in cases where mask is a constant with a single run of 1's in its binary representation), with the semantics that compilers would not be required to accept any particular form, but would be required to treat as atomic any forms they accept.
[toc] | [prev] | [next] | [standalone]
| From | Tim Rentsch <txr@alumni.caltech.edu> |
|---|---|
| Date | 2016-11-13 10:57 -0800 |
| Message-ID | <kfny40ntdgq.fsf@x-alumni2.alumni.caltech.edu> |
| In reply to | #96409 |
Ben Bacarisse <ben.usenet@bsb.me.uk> writes: > spacewar@gmail.com writes: > >> On Friday, November 11, 2016 at 9:04:38 AM UTC-7, Ben Bacarisse wrote: >>> This came up in a DR about the use of various terms relating to atomic >>> types and atomic operations: >>> >>> http://www.open-std.org/jtc1/sc22/wg14/www/docs/summary.htm#dr_486 >>> >>> The DR is under review, but I get the feeling the committee agrees that >>> the wording is confusing. I think you can rely on x <op>= y having the >>> RMW sematics described in 6.5.16.2 (along with the extensive footnote >>> 113). >> >> Thanks! I'm rather unimpressed with the committee's statement that it >> "does not feel that this DR is 'actionable'", and that they apparently >> don't want to address the issues in a Technical Corrigendum. I don't >> see the outright contradiction between 6.5.16.2 p3 and 7.17.7.5 p5 >> as a "small inconsistency". > > I don't see the wording as an outright contradiction. The problem comes > down to what atomic means, and the depends on the observer. x += y is > atomic to an observer in C, but not (I think[1]) to an observer of > volatile accesses. The functions of 7.17.7.5 are (again, I think) > atomic to all but a hardware observer. > > [1] I'm not an expert in this. I'd welcome a technical discussion of > C's atomic primitives because I either don't understand them properly or > there are other rough edges to the description of them. Note that "atomic operation" is a defined term in the Standard (in 5.1.2.4 p5). AFAICT the Standard does not define the term "atomically". What I think they mean is that the whole operation is indivisible as far as other threads are concerned. The functions in 7.17 are atomic operations (or at least some of them are - I haven't verified that all are), and they operate atomically (ditto the last parenthesized comment). Looking at the extensive footnote, compound assignment operators do not operate atomically because the combining operation and the update do not take place indivisibly. That is, it is possible in principle for another thread to run "between" the computation of the new value and the function call that does the update. The conditional update and the loop protect against that eventuality interfering with inter-thread semantics, but even so the operator is not "indivisible". And that makes a certain amount of sense, because most processors probably do not have, eg, an opcode to do a "read-divide-write" as an indivisible operation. In the Standard the term "atomically" looks like it is restricted to operations that take place "indivisably" from the point of view of other threads, but a compound assignment operation might not act that way. P.S. I don't claim to be an expert either. I mean just to offer a contribution to the best of my current understanding.
[toc] | [prev] | [next] | [standalone]
| From | Tim Rentsch <txr@alumni.caltech.edu> |
|---|---|
| Date | 2016-11-13 10:31 -0800 |
| Message-ID | <kfn37ivut94.fsf@x-alumni2.alumni.caltech.edu> |
| In reply to | #96408 |
spacewar@gmail.com writes: > On Friday, November 11, 2016 at 9:04:38 AM UTC-7, Ben Bacarisse wrote: >> This came up in a DR about the use of various terms relating to atomic >> types and atomic operations: >> >> http://www.open-std.org/jtc1/sc22/wg14/www/docs/summary.htm#dr_486 >> >> The DR is under review, but I get the feeling the committee agrees that >> the wording is confusing. I think you can rely on x <op>= y having the >> RMW sematics described in 6.5.16.2 (along with the extensive footnote >> 113). > > Thanks! I'm rather unimpressed with the committee's statement that > it "does not feel that this DR is 'actionable'", and that they > apparently don't want to address the issues in a Technical > Corrigendum. I don't see the outright contradiction between 6.5.16.2 > p3 and 7.17.7.5 p5 as a "small inconsistency". I have had a chance now to look into this, mainly reading carefully new sections of the Standard that have to do with multi-threading and data races. First I agree with Ben's assessment that x <op>= y will behave as you desire. Second I believe that what you see as a contradiction is not really a contradiction, it just looks like one in isolation. The Standard is using the term "atomically" in a specialized sense, which is stronger than just "thread-safe update". A compound assignment operator on an atomic type will behave in a way that is thread safe, as the extensive footnote makes apparent. However, those operations are not guaranteed to occur "all in one fell swoop", which is what "atomically" means in the Standard. The key piece of the loop(s) in the footnote /does/ operate atomically; it is only the operation as a whole that is not atomic. The presence of the loop demonstrates that the behavior is not taking place "atomically". However, what you are concerned with it not whether the operation occurs "atomically" but whether it is guaranteed to observe appropriate inter-thread semantics. The code given in the footnote shows that this property is indeed respected.
[toc] | [prev] | [next] | [standalone]
| From | "Chris M. Thomasson" <invalid@invalid.invalid> |
|---|---|
| Date | 2016-11-12 11:24 -0800 |
| Message-ID | <o07q85$kbl$1@dont-email.me> |
| In reply to | #96367 |
On 11/10/2016 7:34 PM, spacewar@gmail.com wrote: > I'm confused about C11 compound assignments with E1 (left hand side) being an atomic type. > > §6.5.16.2 ¶3 states: > If E1 has an atomic type, compound assignment is a > read-modify-write operation with memory_order_seq_cst memory order > semantics. > > Footnote 113 says > Where a pointer to an atomic object can be formed and E1 and E2 have > integer type, this is equivalent to the following code sequence [...]" > with the code sequence using atomic_compare_exchange_strong(). > > On the other hand, §7.17.7.5 ¶5 states: > NOTE The operation of the atomic_fetch and modify generic functions are > nearly equivalent to the operation of the corresponding op= compound > assignment operators. The only differences are that the compound > assignment operators are not guaranteed to operate atomically, [...] > > Doesn't that directly contradict §6.5.16.2 ¶3 and footnote 113? > > GCC 6.2.1 generates atomic RMW code for compound assignments with atomic LHS, but the NOTE in §7.17.7.5 makes me worry about that being non-portable. FWIW, just to be safe, its much better to use the actual atomic functions to perform operations on atomic types. They let you specifically define exactly what you want, and what type of memory order semantics that particular operation requires for your specific program's needs. If you use normal C to, say, increment something like foo = foo + 1 where foo is an atomic type, the compiler will use strong CAS, and memory_order_seq_cst for a mem order. This is just, usually, way to strong for most work dealing with atomics. Just stick to the atomic functions, and remove any possible ambiguities.
[toc] | [prev] | [next] | [standalone]
| From | Tim Rentsch <txr@alumni.caltech.edu> |
|---|---|
| Date | 2016-11-13 10:59 -0800 |
| Message-ID | <kfntwbbtdde.fsf@x-alumni2.alumni.caltech.edu> |
| In reply to | #96420 |
"Chris M. Thomasson" <invalid@invalid.invalid> writes:
> On 11/10/2016 7:34 PM, spacewar@gmail.com wrote:
>> I'm confused about C11 compound assignments with E1 (left hand side)
>> {} being an atomic type.
>>
>> 6.5.16.2 p3 states:
>> If E1 has an atomic type, compound assignment is a
>> read-modify-write operation with memory_order_seq_cst memory order
>> semantics.
>>
>> Footnote 113 says
>> Where a pointer to an atomic object can be formed and E1 and E2 have
>> integer type, this is equivalent to the following code sequence [...]"
>> with the code sequence using atomic_compare_exchange_strong().
>>
>> On the other hand, 7.17.7.5 p5 states:
>> NOTE The operation of the atomic_fetch and modify generic functions are
>> nearly equivalent to the operation of the corresponding op= compound
>> assignment operators. The only differences are that the compound
>> assignment operators are not guaranteed to operate atomically, [...]
>>
>> Doesn't that directly contradict 6.5.16.2 p3 and footnote 113?
>>
>> GCC 6.2.1 generates atomic RMW code for compound assignments with
>> atomic LHS, but the NOTE in 7.17.7.5 makes me worry about that being
>> non-portable.
>
> FWIW, just to be safe, its much better to use the actual atomic
> functions to perform operations on atomic types. They let you
> specifically define exactly what you want, and what type of memory
> order semantics that particular operation requires for your specific
> program's needs.
>
> If you use normal C to, say, increment something like foo = foo + 1
> where foo is an atomic type, the compiler will use strong CAS, and
> memory_order_seq_cst for a mem order. This is just, usually, way to
> strong for most work dealing with atomics.
That is an interesting statement. What do you recommend in place
of memory_order_seq_cst, perhaps under various scenarios?
[toc] | [prev] | [next] | [standalone]
| From | "Chris M. Thomasson" <invalid@invalid.invalid> |
|---|---|
| Date | 2016-11-13 17:34 -0800 |
| Message-ID | <o0b49f$2p5$1@dont-email.me> |
| In reply to | #96502 |
On 11/13/2016 10:59 AM, Tim Rentsch wrote:
> "Chris M. Thomasson" <invalid@invalid.invalid> writes:
>
>> On 11/10/2016 7:34 PM, spacewar@gmail.com wrote:
>>> I'm confused about C11 compound assignments with E1 (left hand side)
>>> {} being an atomic type.
>>>
>>> 6.5.16.2 p3 states:
>>> If E1 has an atomic type, compound assignment is a
>>> read-modify-write operation with memory_order_seq_cst memory order
>>> semantics.
>>>
>>> Footnote 113 says
>>> Where a pointer to an atomic object can be formed and E1 and E2 have
>>> integer type, this is equivalent to the following code sequence [...]"
>>> with the code sequence using atomic_compare_exchange_strong().
>>>
>>> On the other hand, 7.17.7.5 p5 states:
>>> NOTE The operation of the atomic_fetch and modify generic functions are
>>> nearly equivalent to the operation of the corresponding op= compound
>>> assignment operators. The only differences are that the compound
>>> assignment operators are not guaranteed to operate atomically, [...]
>>>
>>> Doesn't that directly contradict 6.5.16.2 p3 and footnote 113?
>>>
>>> GCC 6.2.1 generates atomic RMW code for compound assignments with
>>> atomic LHS, but the NOTE in 7.17.7.5 makes me worry about that being
>>> non-portable.
>>
>> FWIW, just to be safe, its much better to use the actual atomic
>> functions to perform operations on atomic types. They let you
>> specifically define exactly what you want, and what type of memory
>> order semantics that particular operation requires for your specific
>> program's needs.
>>
>> If you use normal C to, say, increment something like foo = foo + 1
>> where foo is an atomic type, the compiler will use strong CAS, and
>> memory_order_seq_cst for a mem order. This is just, usually, way to
>> strong for most work dealing with atomics.
>
> That is an interesting statement. What do you recommend in place
> of memory_order_seq_cst, perhaps under various scenarios?
>
Well, if your building a custom lock-free container, perhaps
memory_order_acquire/release is enough. Or if your building a proxy
collector, RCU like, a memory_order_consume can be used instead of an
acquire. It really depends on the algorithms specific needs.
memory_order_seq_cst is just too strong for a lot of synchronization
algorithms, and can really destroy performance.
[toc] | [prev] | [next] | [standalone]
| From | "Chris M. Thomasson" <invalid@invalid.invalid> |
|---|---|
| Date | 2016-11-13 17:48 -0800 |
| Message-ID | <o0b549$4o0$1@dont-email.me> |
| In reply to | #96521 |
On 11/13/2016 5:34 PM, Chris M. Thomasson wrote:
> On 11/13/2016 10:59 AM, Tim Rentsch wrote:
>> "Chris M. Thomasson" <invalid@invalid.invalid> writes:
>>
>>> On 11/10/2016 7:34 PM, spacewar@gmail.com wrote:
>>>> I'm confused about C11 compound assignments with E1 (left hand side)
>>>> {} being an atomic type.
>>>>
>>>> 6.5.16.2 p3 states:
>>>> If E1 has an atomic type, compound assignment is a
>>>> read-modify-write operation with memory_order_seq_cst memory order
>>>> semantics.
>>>>
>>>> Footnote 113 says
>>>> Where a pointer to an atomic object can be formed and E1 and E2
>>>> have
>>>> integer type, this is equivalent to the following code sequence
>>>> [...]"
>>>> with the code sequence using atomic_compare_exchange_strong().
>>>>
>>>> On the other hand, 7.17.7.5 p5 states:
>>>> NOTE The operation of the atomic_fetch and modify generic
>>>> functions are
>>>> nearly equivalent to the operation of the corresponding op=
>>>> compound
>>>> assignment operators. The only differences are that the compound
>>>> assignment operators are not guaranteed to operate atomically,
>>>> [...]
>>>>
>>>> Doesn't that directly contradict 6.5.16.2 p3 and footnote 113?
>>>>
>>>> GCC 6.2.1 generates atomic RMW code for compound assignments with
>>>> atomic LHS, but the NOTE in 7.17.7.5 makes me worry about that being
>>>> non-portable.
>>>
>>> FWIW, just to be safe, its much better to use the actual atomic
>>> functions to perform operations on atomic types. They let you
>>> specifically define exactly what you want, and what type of memory
>>> order semantics that particular operation requires for your specific
>>> program's needs.
>>>
>>> If you use normal C to, say, increment something like foo = foo + 1
>>> where foo is an atomic type, the compiler will use strong CAS, and
>>> memory_order_seq_cst for a mem order. This is just, usually, way to
>>> strong for most work dealing with atomics.
>>
>> That is an interesting statement. What do you recommend in place
>> of memory_order_seq_cst, perhaps under various scenarios?
>>
>
> Well, if your building a custom lock-free container, perhaps
> memory_order_acquire/release is enough. Or if your building a proxy
> collector, RCU like, a memory_order_consume can be used instead of an
> acquire.
When one can get away with using memory_order_consume, well, it boils
down to a nop on a lot of archs out there, except a DEC Alpha!
;^)
> It really depends on the algorithms specific needs.
> memory_order_seq_cst is just too strong for a lot of synchronization
> algorithms, and can really destroy performance.
[toc] | [prev] | [next] | [standalone]
| From | Tim Rentsch <txr@alumni.caltech.edu> |
|---|---|
| Date | 2016-11-15 10:42 -0800 |
| Message-ID | <kfnvavoshyr.fsf@x-alumni2.alumni.caltech.edu> |
| In reply to | #96521 |
"Chris M. Thomasson" <invalid@invalid.invalid> writes:
> On 11/13/2016 10:59 AM, Tim Rentsch wrote:
>> "Chris M. Thomasson" <invalid@invalid.invalid> writes:
>>
>>> On 11/10/2016 7:34 PM, spacewar@gmail.com wrote:
>>>> I'm confused about C11 compound assignments with E1 (left hand side)
>>>> {} being an atomic type.
>>>>
>>>> 6.5.16.2 p3 states:
>>>> If E1 has an atomic type, compound assignment is a
>>>> read-modify-write operation with memory_order_seq_cst memory order
>>>> semantics.
>>>>
>>>> Footnote 113 says
>>>> Where a pointer to an atomic object can be formed and E1 and E2 have
>>>> integer type, this is equivalent to the following code sequence [...]"
>>>> with the code sequence using atomic_compare_exchange_strong().
>>>>
>>>> On the other hand, 7.17.7.5 p5 states:
>>>> NOTE The operation of the atomic_fetch and modify generic functions are
>>>> nearly equivalent to the operation of the corresponding op= compound
>>>> assignment operators. The only differences are that the compound
>>>> assignment operators are not guaranteed to operate atomically, [...]
>>>>
>>>> Doesn't that directly contradict 6.5.16.2 p3 and footnote 113?
>>>>
>>>> GCC 6.2.1 generates atomic RMW code for compound assignments with
>>>> atomic LHS, but the NOTE in 7.17.7.5 makes me worry about that being
>>>> non-portable.
>>>
>>> FWIW, just to be safe, its much better to use the actual atomic
>>> functions to perform operations on atomic types. They let you
>>> specifically define exactly what you want, and what type of memory
>>> order semantics that particular operation requires for your specific
>>> program's needs.
>>>
>>> If you use normal C to, say, increment something like foo = foo + 1
>>> where foo is an atomic type, the compiler will use strong CAS, and
>>> memory_order_seq_cst for a mem order. This is just, usually, way to
>>> strong for most work dealing with atomics.
>>
>> That is an interesting statement. What do you recommend in place
>> of memory_order_seq_cst, perhaps under various scenarios?
>
> Well, if your building a custom lock-free container, perhaps
> memory_order_acquire/release is enough. Or if your building a proxy
> collector, RCU like, a memory_order_consume can be used instead of an
> acquire. It really depends on the algorithms specific
> needs. memory_order_seq_cst is just too strong for a lot of
> synchronization algorithms, and can really destroy performance.
I see. IIUC, what you're saying is that using memory_order_seq_cst
all the time is too expensive, so in most cases more specialized
patterns are used that can employ less expensive sequencing
guarantees. Did I understand that right or is there something
more?
[toc] | [prev] | [standalone]
Back to top | Article view | comp.lang.c
csiph-web