【发布时间】:2011-06-03 00:02:02
【问题描述】:
假设在条件分支的分支延迟槽中遇到异常
例如
BEQ a0, zero, _true
BREAK (0000)
sw a0, 0000(t0)
_true:
sw a1, 0000(t0)
我的异常处理程序将从 BREAK 指令中提取异常 type 9 并设置 CAUSEBD 位/em> 在分支延迟中注册为 1,EPC 将是分支的地址。
文档说这将需要未描述的复杂处理。即获取分支/跳转的目标,进行任何所需的比较,然后将 PC 设置为真或假地址。
我绕过复杂处理的解决方案(有点破解)如下:
- 将指令存储在分支延迟槽中
- NOP 分支延迟槽中的指令
- 从恢复所有寄存器的异常处理程序中返回
- 重新执行 *BEQ a0, zero, _true* 并且分支延迟将是 nop 所以它没有效果
- 在分支的目标处放置一个 sw 断点并设置一个标志
- 一旦遇到 sw 断点,就恢复分支延迟槽并移除 sw 断点的痕迹。
解析分支和跳转很好(这就是为什么我可以得到目标)但是在条件分支中,一旦我解析了,我就必须进行比较以确定是否跳转到 go to false 的 true 部分(下一行)我觉得这比我想要的要多。 不是吗?
我的 hacky 方法的问题是:
CPU 是否已经存储了它已经到达条件分支并确定在执行了分支延迟槽之后它是否要进行分支,因此一旦我指向 程序计数器 回到分支,它被执行而不是正确执行,它认为它必须跳转到在异常发生之前预先确定的分支的真或假部分? (尝试“双跳”)
【问题讨论】: