用于预取,返回地址为: R14_abt =中止指令的地址+4
并且对于数据中止,返回地址是: R14_abt =中止指令的地址+ 8
答案 0 :(得分:14)
这些偏移是由处理器的流水线操作和提取/解码/执行阶段引起的。
处理器的程序计数器(PC)在执行期间的特定点更新。在获取/解码/执行的不同阶段可能会发生异常。
在预取中止的情况下,指令不能(尚未执行);仅当处理器实际尝试执行指令时才会发生异常(某些预取指令可能无法执行)。
在数据中止的情况下,正在执行指令,并且指令的执行会导致异常。
来自ARM文档:
关于预取中止:
[预取中止异常]发生时 处理器尝试执行 从中预取的指令 一个非法的地址,即一个 地址即内存管理 子系统已经确定了 其处理器无法访问 目前的模式。
...管道中已有的指令继续执行,直到到达无效指令,此时会生成预取中止。
...因为在发出预取中止时程序计数器没有更新,lr_ABT指向导致异常的指令之后的指令。处理程序必须返回到lr_ABT - 4
关于数据中止:
[数据中止例外]发生时 尝试数据传输指令 加载或存储非法数据 地址。
当加载或存储指令尝试访问内存时,程序计数器已更新。 lr_ABT中的(pc - 4)存储值指向超出异常地址的第二条指令生成了。当MMU已将适当的地址加载到物理内存中时,处理程序应返回到原始的中止指令,以便可以再次尝试执行它。 返回地址因此比lr_ABT中的两个字(八个字节)
换句话说,对于数据中止,处理程序必须返回 lr_ABT - 8 (前两个单词/指令)
答案 1 :(得分:2)
我不记得看到官方解释,但如果你考虑一下,这是非常合乎逻辑的。
让我们考虑这个例子:
00000 INSN1 [PC = 08]
00004 INSN2 [PC = 0C]
00008 INSN3 [PC = 10]
如果处理器无法获取INSN3,则在执行之前发生中止,因此PC值仍然是INSN2的值,即0C。
如果在执行INSN3期间发生数据中止,则PC值已更新为10。
答案 2 :(得分:0)
对于预取中止
new_lr_value = if CPSR.T == ‘1’ then PC else PC-4
数据中止
new_lr_value = if CPSR.T == ‘1’ then PC+4 else PC;
参考TRM TakePrefetchAbortException()和TakeDataAbortException()