Author Topic: 32F417 / ARM32: which variables are atomic?  (Read 2693 times)

0 Members and 1 Guest are viewing this topic.

Offline peter-hTopic starter

  • Super Contributor
  • ***
  • Posts: 3728
  • Country: gb
  • Doing electronics since the 1960s...
32F417 / ARM32: which variables are atomic?
« on: March 27, 2023, 02:48:58 pm »
Fairly obviously it must be

boolean (which GCC implements as an int, I think)
8 bit ints
16 bit ints
32 bit ints

NOT 64 bit variables (these will be accessed as at least two goes).

What about single floats?

The more tricky case is that the 32F4 supports unaligned variables, transparently. AFAIK GCC does not assume this and aligns them. I don't use packed structs, but somebody working on this project one day might. I am 99% sure that an unaligned 32 bit variable access will not allow interrupts (therefore RTOS switching) in between the two hardware accesses, but is this right? I would expect DMA can jump in though!

Z80 Z180 Z280 Z8 S8 8031 8051 H8/300 H8/500 80x86 90S1200 32F417
 

Online abyrvalg

  • Frequent Contributor
  • **
  • Posts: 825
  • Country: es
Re: 32F417 / ARM32: which variables are atomic?
« Reply #1 on: March 27, 2023, 03:10:52 pm »
Technically, LDRD/STRD can access 64 bits uninterrupted, but there is no way (except asm of course) to force the compiler to use it.
 

Offline peter-hTopic starter

  • Super Contributor
  • ***
  • Posts: 3728
  • Country: gb
  • Doing electronics since the 1960s...
Re: 32F417 / ARM32: which variables are atomic?
« Reply #2 on: March 28, 2023, 07:31:14 pm »
I am surprised that all my guesses in post #1 were correct ;)

On a slightly different tack, could one achieve an atomic write of say 20 bytes with memory-memory DMA?
Z80 Z180 Z280 Z8 S8 8031 8051 H8/300 H8/500 80x86 90S1200 32F417
 

Offline gf

  • Super Contributor
  • ***
  • Posts: 1238
  • Country: de
Re: 32F417 / ARM32: which variables are atomic?
« Reply #3 on: March 28, 2023, 08:33:52 pm »
The more tricky case is that the 32F4 supports unaligned variables, transparently. AFAIK GCC does not assume this

Doesn't option -munaligned-access enable that?
 

Offline peter-hTopic starter

  • Super Contributor
  • ***
  • Posts: 3728
  • Country: gb
  • Doing electronics since the 1960s...
Re: 32F417 / ARM32: which variables are atomic?
« Reply #4 on: March 30, 2023, 03:48:27 pm »
How would that change whether a memory access is atomic or not, on a CPU which supports unaligned access.

On a slightly different tack, could one achieve an atomic write of say 20 bytes with memory-memory DMA?
Z80 Z180 Z280 Z8 S8 8031 8051 H8/300 H8/500 80x86 90S1200 32F417
 

Offline wek

  • Frequent Contributor
  • **
  • Posts: 495
  • Country: sk
Re: 32F417 / ARM32: which variables are atomic?
« Reply #5 on: March 30, 2023, 04:12:46 pm »
Quote
On a slightly different tack, could one achieve an atomic write of say 20 bytes with memory-memory DMA?

Define, very precisely, atomic.

JW
 

Offline peter-hTopic starter

  • Super Contributor
  • ***
  • Posts: 3728
  • Country: gb
  • Doing electronics since the 1960s...
Re: 32F417 / ARM32: which variables are atomic?
« Reply #6 on: March 30, 2023, 04:49:51 pm »
Atomic from interrupts (which implicitly includes RTOS task switching, which uses SysTick).

Does't have to be atomic from DMA (which I know historically, old days, could optionally use what they used to call cycle stealing).

My question re DMA was in the opposite direction: can a 32F4 perform a DMA write or read, n words, which is atomic from interrupts? I have used DMAs which could do this.

Z80 Z180 Z280 Z8 S8 8031 8051 H8/300 H8/500 80x86 90S1200 32F417
 

Offline wek

  • Frequent Contributor
  • **
  • Posts: 495
  • Country: sk
Re: 32F417 / ARM32: which variables are atomic?
« Reply #7 on: March 30, 2023, 05:16:49 pm »
No. And it wouldn't be atomic "from DMA" either, as individual streams are arbitrated round-robin, and even if you'd employ higher priority, the peripheral/memory sides alternate and have individual arbitration... this wold need to be drawn as timing diagram for detailed discussion.

What *would* be atomic - regarding both interrupts and DMA - would be a 4-beat burst, i.e. max. 16 bytes (appropriately aligned), see Single and burst transfers subchapter of DMA chapter in RM0090 - bursts are unsplittable at the bus transfer level.

JW

 
The following users thanked this post: peter-h, Georgy.Moshkin

Offline peter-hTopic starter

  • Super Contributor
  • ***
  • Posts: 3728
  • Country: gb
  • Doing electronics since the 1960s...
Re: 32F417 / ARM32: which variables are atomic?
« Reply #8 on: March 30, 2023, 06:36:50 pm »
Well, that's good as it provides a means of atomically writing two double float, by copying them from elsewhere in RAM, and same for reading. That's useful and easy to do.
Z80 Z180 Z280 Z8 S8 8031 8051 H8/300 H8/500 80x86 90S1200 32F417
 

Offline wek

  • Frequent Contributor
  • **
  • Posts: 495
  • Country: sk
Re: 32F417 / ARM32: which variables are atomic?
« Reply #9 on: March 30, 2023, 07:19:29 pm »
Well, that's good as it provides a means of atomically writing two double float, by copying them from elsewhere in RAM, and same for reading. That's useful and easy to do.
You may find that setting up the DMA and then waiting until it finished is not worth the hassle, and conventional disable-store-enable may be simpler, smaller and faster too.

JW
 

Offline peter-hTopic starter

  • Super Contributor
  • ***
  • Posts: 3728
  • Country: gb
  • Doing electronics since the 1960s...
Re: 32F417 / ARM32: which variables are atomic?
« Reply #10 on: March 31, 2023, 07:08:12 am »
Yes of course; this is for unusual situations where interrupts must not be disabled for some reason.
Z80 Z180 Z280 Z8 S8 8031 8051 H8/300 H8/500 80x86 90S1200 32F417
 

Offline bson

  • Supporter
  • ****
  • Posts: 2282
  • Country: us
Re: 32F417 / ARM32: which variables are atomic?
« Reply #11 on: April 05, 2023, 05:08:14 pm »
On a slightly different tack, could one achieve an atomic write of say 20 bytes with memory-memory DMA?
Depends on the DMA controller(s).  Remember that some peripherals, like ethernet and USB often have their own DMA controllers.  If the DMA controller you use for the m2m transfer can be set to the highest priority and you disable interrupts during the transfer, then the m2m transfer should be atomic.  If you can't verify that it excludes the peripheral DMA controllers, then you can always stop those during the transfer if they can possibly ever overlap with your source/dest data.

stm/ldm aren't atomic in that I'm fairly certain that DMA transfers can interleave with them.  If interrupted they're restarted on return so in that sense they're atomic (last to finish wins), but from a system perspective they're not. Unaligned transfer I'd assume can be interleaved with DMA as well.
« Last Edit: April 05, 2023, 05:09:53 pm by bson »
 

Offline peter-hTopic starter

  • Super Contributor
  • ***
  • Posts: 3728
  • Country: gb
  • Doing electronics since the 1960s...
Re: 32F417 / ARM32: which variables are atomic?
« Reply #12 on: April 05, 2023, 07:19:07 pm »
Quote
Unaligned transfer I'd assume can be interleaved with DMA as well.

That would surprise me.
Z80 Z180 Z280 Z8 S8 8031 8051 H8/300 H8/500 80x86 90S1200 32F417
 

Online abyrvalg

  • Frequent Contributor
  • **
  • Posts: 825
  • Country: es
Re: 32F417 / ARM32: which variables are atomic?
« Reply #13 on: April 06, 2023, 08:41:50 am »
Why rely on a trick in the first place? Your project is RTOS-based IIRC, use it’s synchronization primitives instead of working around it. Tricks were the only option in 8-bit era, but nowadays most of the common problems have common solutions and looking for a trick on every occasion is a sign of something done wrong on upper design levels.
 

Offline peter-hTopic starter

  • Super Contributor
  • ***
  • Posts: 3728
  • Country: gb
  • Doing electronics since the 1960s...
Re: 32F417 / ARM32: which variables are atomic?
« Reply #14 on: April 06, 2023, 09:04:24 am »
Don't worry - I am not using any tricks :) I am just interested to know how this works.

I use FreeRTOS mutexes etc extensively.

But there are times when a boolean flag is just fine - or should be. What if one isn't using an RTOS and needs to flag "main loop" versus an ISR?

Out of interest - is there a "test and set" instruction accessible from GCC C ? I used that extensively in the past. Far more efficient than a mutex (looking at FreeRTOS code).
« Last Edit: April 06, 2023, 09:17:27 am by peter-h »
Z80 Z180 Z280 Z8 S8 8031 8051 H8/300 H8/500 80x86 90S1200 32F417
 

Offline gf

  • Super Contributor
  • ***
  • Posts: 1238
  • Country: de
 

Offline peter-hTopic starter

  • Super Contributor
  • ***
  • Posts: 3728
  • Country: gb
  • Doing electronics since the 1960s...
Re: 32F417 / ARM32: which variables are atomic?
« Reply #16 on: April 06, 2023, 10:12:19 am »
Is that for C, not just C++?

Interesting that you specify a "memory order" there.
Z80 Z180 Z280 Z8 S8 8031 8051 H8/300 H8/500 80x86 90S1200 32F417
 

Offline Jeroen3

  • Super Contributor
  • ***
  • Posts: 4078
  • Country: nl
  • Embedded Engineer
    • jeroen3.nl
Re: 32F417 / ARM32: which variables are atomic?
« Reply #17 on: April 06, 2023, 12:15:05 pm »
Architecture reference manual says all <= 32 bit operands are atomic.

Plus:
Quote
On exception return, the instruction that generated the sequence of accesses is re-executed and so any accesses that had already been performed before the exception was taken might be repeated, see Exceptions in Load Multiple and Store Multiple operations.
 

Offline gf

  • Super Contributor
  • ***
  • Posts: 1238
  • Country: de
Re: 32F417 / ARM32: which variables are atomic?
« Reply #18 on: April 06, 2023, 12:48:50 pm »
Is that for C, not just C++?

Yes, the link is for C.
The corresponding functionality for C++ is std::atomic (https://en.cppreference.com/w/cpp/atomic/atomic)
 

Offline peter-hTopic starter

  • Super Contributor
  • ***
  • Posts: 3728
  • Country: gb
  • Doing electronics since the 1960s...
Re: 32F417 / ARM32: which variables are atomic?
« Reply #19 on: April 06, 2023, 01:12:28 pm »
Quote
so any accesses that had already been performed before the exception was taken might be repeated

Just as well then that accesses to the peripherals can't generate an exception ;)

That memory ordering stuff is pretty complicated. I might have expected to see something like __DSB in there.
Z80 Z180 Z280 Z8 S8 8031 8051 H8/300 H8/500 80x86 90S1200 32F417
 

Offline newbrain

  • Super Contributor
  • ***
  • Posts: 1721
  • Country: se
Re: 32F417 / ARM32: which variables are atomic?
« Reply #20 on: April 06, 2023, 02:59:45 pm »

Architecture reference manual says all <= 32 bit operands are atomic.
Single-copy atomic access is guaranteed only for:
Quote from: reference from Jeroen3 post
    all byte accesses
    all halfword accesses to halfword-aligned locations
    all word accesses to word-aligned locations
So I would qualify the ≤ 32 bit with "aligned", at least according to the reference.

I am not using any tricks :)
I beg to differ, but that's an old topic (busy loops in FreeRTOS tasks).
Nandemo wa shiranai wa yo, shitteru koto dake.
 

Offline peter-hTopic starter

  • Super Contributor
  • ***
  • Posts: 3728
  • Country: gb
  • Doing electronics since the 1960s...
Re: 32F417 / ARM32: which variables are atomic?
« Reply #21 on: April 06, 2023, 07:28:05 pm »
So unaligned 16 or 32 bit accesses are not atomic between say two RTOS tasks (i.e. not thread-safe).

I am not doing loops inside RTOS tasks. That would just totally waste 1ms+ of the CPU time. I yield to the RTOS with say osDelay(100) if there is nothing to do. This surely is 100% fine "co-operative multitasking". It works extremely well, when I wrote all the tasks, and less well when I didn't (MbedTLS grabs the CPU for 3 seconds solid, so the only chance of another task running at all is if its priority is higher - or same or higher in my RTOS config).
Z80 Z180 Z280 Z8 S8 8031 8051 H8/300 H8/500 80x86 90S1200 32F417
 

Offline thinkfat

  • Supporter
  • ****
  • Posts: 2152
  • Country: de
  • This is just a hobby I spend too much time on.
    • Matthias' Hackerstübchen
Re: 32F417 / ARM32: which variables are atomic?
« Reply #22 on: April 07, 2023, 12:29:13 pm »
That depends very much on the definition of "atomic". If it's just about loading or storing a memory location uninterruptible, then any aligned access to <= 32bit data types will be fine.

However:

ARM as a load-store architecture doesn't have any atomically modifiable data types. ARM deemed this problematic enough to later introduce an "exclusive monitor" and the "LDREX/STREX" instructions. Prior to that the only way to implement "atomic" r/m/w was using SWP{B}. But both require implementing a protocol and asserting that all involved parties stick to it.

LDREX/STREX only work on cached memory and the behavior if used on uncached memory is UNDEFINED, and some Cortex-A cores are known to just lock up hard, which is a real problem because LDREX/STREX are not privileged.
Everybody likes gadgets. Until they try to make them.
 

Offline gf

  • Super Contributor
  • ***
  • Posts: 1238
  • Country: de
Re: 32F417 / ARM32: which variables are atomic?
« Reply #23 on: April 07, 2023, 02:58:06 pm »
@peter-h, btw, in C it's unsafe anyway to assume that accessing any regular variable would be atomic. If may happen by chance, but the language specification does not guarantee that at all.

Atomicity is only guaranteed for objects of _Atomic datatypes. Even large objects can be _Atomic, but not all _Atomic datatypes are necesssarily lock-free, and large atomic objects usually aren't. Non-lock-free _Atomic data types are still thread-safe (i.e. atomic wrt. different threads), but it is not safe to access them from a signal/interrupt handler. Only lock-free _Atomic objects can be safely accessed from a signal handler as well. See also https://en.cppreference.com/w/c/language/atomic

ARM GCC obviously emits LDREXD, STREXD, DMB,... for particular operations on particular lock-free _Atomic data types.
Arbitrary example: https://godbolt.org/z/YeMKevd7x
 

Offline gf

  • Super Contributor
  • ***
  • Posts: 1238
  • Country: de
Re: 32F417 / ARM32: which variables are atomic?
« Reply #24 on: April 07, 2023, 05:13:49 pm »
ARM GCC obviously emits LDREXD, STREXD, DMB,... for particular operations on particular lock-free _Atomic data types.
Arbitrary example: https://godbolt.org/z/YeMKevd7x

I had missed that you are using a cortex-m4. For this processor, GCC does not generate inline code, but a call to e.g. __atomic_store_8() for "_Atomic long long" datatype. So it seems that 8 byte atomic operations are no longer lock-free in the code generated for this CPU. https://godbolt.org/z/TobaeYeoK
 
The following users thanked this post: peter-h


Share me

Digg  Facebook  SlashDot  Delicious  Technorati  Twitter  Google  Yahoo
Smf