ARM:"STMDB SP!,{R0-R8}"(又名PUSH {R0-R8})是原子操作吗?

use*_*952 5 assembly stack arm atomic

我想知道STMDB SP!,{R0-R8}是否是ARM(v7)中的原子操作,因为它对我来说看起来很复杂.那么例如可能的是,CPU在"中间"某处被中断并且已经将R5-R8存储在堆栈上并且SP现在是SP_old-16并且在处理中断之后处理器继续R0-R4?谢谢.

Not*_*hat 5

为了澄清这里稍微令人困惑的答案组合,首先;v7-A 1

在标准配置中,唯一可以中断多路访问指令的异常是同步数据中止,因此它们在中断方面是有效的原子(尽管不是在内存访问方面)。

然而,如果低延迟中断配置受支持并已启用,则情况并非如此。这里 IRQ、FIQ 和异步中止也可以中断指令。在此引用 v7-A ARM ARM:

ARM 反对任何软件依赖的行为,即在访问普通内存的单个加载或存储指令生成的一系列内存事务中不会发生中断或异步中止。

笔记

显示这种依赖的一个特殊情况是从内存加载堆栈指针的加载倍数。在 LDM 期间发生中断的实现中,这可能会破坏堆栈指针。

以这种方式中断的指令将被放弃,如果返回,则从头开始重新执行(因此对于存储,较低的地址可能会看到两次写入)。

其次是 v7-M 2,其古怪的异常模型:

这里每天都是低延迟的。在多次访问指令期间总是可以采取例外,但架构允许(在某些条件下)根据问题中的建议从中断点继续执行。放弃和重启行为也被允许作为替代方案,并且是不可连续指令/异常组合的唯一选择。

[1] ARMv7-A ARM (DDI0406C.b) 的A3.5.3 和 B1.8.12 节

[2] ARMv7-M ARM (DDI0403D) 的 B1.5.10 节


Sim*_*ter 4

就中断处理而言,它是原子的。

如果我没记错的话,中断指令会导致指令被中止并在中断处理完成后重新执行,以保证中断延迟。