[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[avr-libc-dev] Re: bug #22163 (atomic not working as expected in C++)
From: |
David Brown |
Subject: |
[avr-libc-dev] Re: bug #22163 (atomic not working as expected in C++) |
Date: |
Wed, 09 Jun 2010 13:05:38 +0200 |
User-agent: |
Mozilla/5.0 (Windows; U; Windows NT 5.1; en-US; rv:1.9.1.9) Gecko/20100317 Lightning/1.0b1 Thunderbird/3.0.4 |
On 09/06/2010 10:23, Joerg Wunsch wrote:
https://savannah.nongnu.org/bugs/?22163
The bug looks serious enough to me so I'd like to include David's
alternative C++ implementation. Did anyone else test this? Any
objections?
It's been a while since I wrote that code!
Looking back at it, there are a couple of points regarding memory blocks
and interrupt flags in the description I wrote.
One is that I wrote that the memory barrier must occur /before/ a "sei"
instruction or SREG restore. I'm not sure how specific memory barriers
are, especially if they are part of a single instruction such as
asm("sei" ::: "memory"). I think it's important that there is a barrier
both before and after these instructions - you don't want any reordering
to occur. And in contrast to what I wrote earlier, this applies to both
"sei" and "cli" instructions. As far as I understand it, you will get
the correct effect by including the memory clobber in the asm statement
itself.
To see what can go wrong with a single memory barrier that is not tied
to the instruction, consider the sequence:
nonAtomicInt1 = 1234;
cli();
asm volatile ("" ::: "memory");
atomicGlobalInt = 12345;
sei();
asm volatile ("" ::: "memory");
nonAtomicInt2 = 5678;
The compiler can re-order the stores across the cli() and sei()
instructions, but not across the memory barrier:
cli();
nonAtomicInt1 = 1234;
asm volatile ("" ::: "memory");
sei();
atomicGlobalInt = 12345;
asm volatile ("" ::: "memory");
nonAtomicInt2 = 5678;
The first move of nonAtomicInt1 will not affect the correctness of the
code, but will lead to interrupts being disabled for longer than
desired. The second one will make the storage of atomicGlobalInt
non-atomic.
If the memory barriers are placed before cli() and sei(), you get a
similar effect.
If the memory clobbers are added to the definitions of cli() and sei(),
as well as an "sreg set" macro (or inline function), then these should
be used in the code here instead of writing the inline assembly explicitly.
mvh.,
David
- [avr-libc-dev] bug #22163 (atomic not working as expected in C++), Joerg Wunsch, 2010/06/09
- [avr-libc-dev] Re: bug #22163 (atomic not working as expected in C++), Dean Camera, 2010/06/09
- [avr-libc-dev] Re: bug #22163 (atomic not working as expected in C++),
David Brown <=
- [avr-libc-dev] Re: bug #22163 (atomic not working as expected in C++), Dean Camera, 2010/06/09
- [avr-libc-dev] Re: bug #22163 (atomic not working as expected in C++), Joerg Wunsch, 2010/06/09
- RE: [avr-libc-dev] Re: bug #22163 (atomic not working as expected inC++), Stu Bell, 2010/06/09
- Re: [avr-libc-dev] Re: bug #22163 (atomic not working as expected inC++), Joerg Wunsch, 2010/06/09
- RE: [avr-libc-dev] Re: bug #22163 (atomic not working as expectedinC++), Weddington, Eric, 2010/06/09
- Re: [avr-libc-dev] Re: bug #22163 (atomic not working as expectedinC++), Joerg Wunsch, 2010/06/09
- RE: [avr-libc-dev] Re: bug #22163 (atomic not working asexpectedinC++), Weddington, Eric, 2010/06/09
- RE: [avr-libc-dev] Re: bug #22163 (atomic not working as expectedinC++), Stu Bell, 2010/06/09
- Re: [avr-libc-dev] Re: bug #22163 (atomic not working as expected inC++), David Brown, 2010/06/09
- Re: [avr-libc-dev] Re: bug #22163 (atomic not working as expected inC++), Joerg Wunsch, 2010/06/09