我发现可能会使用f.seek()
和LDREX
。但它们是两个指令(因此不提供STREX
的原子性)。我想原子交换的值是32位值。
xchgl
和LDREX
可以以提供32位值原子交换的方式使用,还是以其他方式实现它(假设它在armv7l或更高版本上运行)?
通常情况下,我是gcc的atomic builtins或更近期的(C ++ 11等效版)builtin functions 对于这种原子操作。但在这种情况下,我必须在C中使用内联汇编(将基于x86的futex实现移植到ARM体系结构)。谢谢!
答案 0 :(得分:7)
在ARM指令集中,没有原子交换指令。相反,您使用ldrex
和strex
并使用以下代码:
@ exchange r0 and [r1]
ldrex r2,[r1]
strex r3, r0,[r1]
mov r0,r2
在[r1]
和ldrex
之间修改strex
或由于某些其他原因无法保证交换是原子的,r3
中会返回1并且商店不是&执行了。如果序列是原子序列,则返回0。因此,通过在循环中执行此代码段直到获得零r3
,您最终可以达到原子交换操作。这实际上是gcc和clang如何实现相应的内在因素;将-S
传递给编译器以观察它的作用。
答案 1 :(得分:2)
SWP仍然支持某些核心,尽管文档说的是(他们经常说请不要使用而不是我们已经删除它)但它已经消失或可能已经消失了。
原子药价格昂贵,CISC价格昂贵,所以也许它很好,但是RISC对它们所做的事情很有意义。您基本上是在合成原子,但您可能必须重复它直到它工作(而不是在原子发生时停止总线上的所有数据移动)。不仅限于RISC / CISC,还仅仅是表演。