【发布时间】:2021-05-28 09:00:00
【问题描述】:
我正在尝试在 MIPS 中创建递归乘法函数。逻辑是:
我们想将 x 乘以 y。
基本情况:x = 0,返回 y
一般情况:x != 0,返回 y + (x-1)*y
所以我编写了代码,一切正常,除了一点点。在代码的开头,我这样做:
# save the first address from $ra on the stack so that we can come back and exit
sw $ra 0($sp)
addi $sp $sp -4
jal recursive_multiplication
# get the last address on the stack for the last jr $ra to exit
lw $ra 0($sp)
addi $sp $sp 4
这应该将 $ra 的第一个地址存储在堆栈上,第一个地址是 00400018,即代码初始化中“隐藏”jal main 之后的行。将其放入堆栈并完成我的业务后,我可以回来阅读它,并以 jr $ra 结束我的代码并终止该过程。问题是:当我读取堆栈上的地址时,我得到的是 0,而不是 00400018。此外,我注意到每次将地址放在堆栈上时,堆栈都会添加如下所示的内容:
| . @ .
整个堆栈都是从这里开始的:
[7ffff6b0] 00000001 7ffff777 00000000 7fffffe1 . . . . w . . . . . . . . . . .
到这里:
[7ffff698] 0040007c 0040007c | . @ . | . @ .
[7ffff6a0] 0040007c 0040007c 0040003c 00000000 | . @ . | . @ . < . @ . . . . .
[7ffff6b0] 00400018 7ffff777 00000000 7fffffe1 . . @ . w . . . . . . . . . . .
当然,我只包括用户堆栈中有趣的部分。我的代码不会访问或修改其余部分。
我有一种感觉,错误来自最后两个@之间的事实,有 7 个点而不是常规的 2 和一个“|” ,这会导致读数返回 0 到 $ra(因为它读取“一个点”),但我无法真正理解它。
知道为什么会这样吗?感谢阅读!
【问题讨论】:
-
您应该能够使用调试器和单步执行查看问题。观察每条指令,并观察每条指令后寄存器和/或内存发生什么/何时发生变化。您将能够看到负载将转到与存储不同的地址。