【发布时间】:2018-06-12 19:04:15
【问题描述】:
我正在为课堂编写程序。它从控制台获取 x 和 epsilon,并且应该检索 sin(x) 近似值。当我在 QtSpim 中运行它时,我得到了错误:
未知指令类型:0
错误发生在这里:
floatsin: addi $sp, $sp, -64 # Frame
sw $ra, 64($ra)
sw $fp, 60($sp)
s.d $f0, 56($sp)
s.d $f4, 48($sp)
s.d $f20, 40($sp)
s.d $f8, 32($sp)
s.d $f10, 24($sp)
s.d $f14, 16($sp)
s.d $f18, 8($sp) # ERROR HERE
addi $fp, $sp, 64
可能是什么原因?我很困惑,因为直到s.d $f18 一切正常。感谢您的任何提示!
低于完整程序:
.data
xinput: .asciiz "\nPlease enter x\n"
epsinput: .asciiz "\nPlease enter epsilon\n"
sinxoutput: .asciiz "\nsin(x) is: "
.text
main: la $a0, xinput
li $v0, 4
syscall
li $v0, 7
syscall
mov.d $f2, $f12
la $a0, epsinput
li $v0, 4
syscall
li $v0, 7
syscall
mov.d $f0, $f12
jal floatsin
la $a0, sinxoutput
li $v0, 4
syscall
li $v0, 3
syscall
li $v0, 10
syscall
floatsin: addi $sp, $sp, -64 # Frame
sw $ra, 64($ra)
sw $fp, 60($sp)
s.d $f0, 56($sp)
s.d $f4, 48($sp)
s.d $f20, 40($sp)
s.d $f8, 32($sp)
s.d $f10, 24($sp)
s.d $f14, 16($sp)
s.d $f18, 8($sp)
addi $fp, $sp, 64
li.d $f8, 0.0 # Initialize
li.d $f14, 1.0
mov.d $f16, $f0
li.d $f18, 0.0
jal loop_p1
main_loop: add.d $f18, $f18, $f4
c.lt.d $f2, $f4
bc1f exit_fsin
jal loop_p1
sub.d $f18, $f18, $f4
c.lt.d $f2, $f4
bc1f exit_fsin
jal loop_p1
j main_loop
loop_p1: add.d $f8, $f8, $f14
li.d $f10, 1.0 #for (j < 2i-1)
mov.d $f4, $f16
li.d $f20, 0.0
add.d $f20, $f8, $f8
sub.d $f20, $f20, $f14
for: c.lt.d $f10, $f20
bc1f loop_p2
mul.d $f4, $f4, $f16 # (x*x)
add.d $f10, $f10, $f14
j for
loop_p2: mov.d $f0, $f20
move $t0, $ra
jal floatfac
div.d $f4, $f4, $f12
jr $t0
exit_fsin: mov.d $f12, $f18 # Write in target register
l.d $f18, 8($sp) # rewrite values
l.d $f14, 16($sp)
l.d $f10, 24($sp)
l.d $f8, 32($sp)
l.d $f20, 40($sp)
l.d $f4, 48($sp)
l.d $f0, 56($sp)
lw $fp, 60($sp)
lw $ra, 64($sp)
addi $sp, $sp, 64
jr $ra # back to caller
floatfac: addi $sp, $sp, -28 # Frame
sw $fp, 28($sp)
s.d $f4, 24($sp)
s.d $f2, 16($sp)
s.d $f0, 8($sp)
addi $fp, $sp, 28
li.d $f4, 0.0
c.le.d $f0, $f4
bc1t negative
li.d $f12, 1.0
li.d $f2, 1.0
while: c.le.d $f0, $f2 # Break condition
bc1t exit_floatfact
mul.d $f12, $f12, $f0
sub.d $f0, $f0, $f2
j while
negative: li.d $f12, 0.0
exit_floatfact: l.d $f0, 8($sp) # rewrite values
l.d $f2, 16($sp)
l.d $f4, 24($sp)
lw $fp, 28($sp)
addi $sp, $sp, 28
jr $ra
【问题讨论】:
-
clang 可以很好地组装您的代码。
clang -target mips mips-float.S -c生成了一个.o,llvm-objdump -d可以反汇编。我没有安装 SPIM,也没有在 MARS 上尝试过。你是说它组装但在运行时出错?您是否有可能在运行时使用错误的指针用数据覆盖您的代码?还是堆栈增长到与代码重叠?使用调试器检查$sp,并在错误发生后反汇编内存中的代码。 -
是的,这是一个运行时错误,下面的 Michael 指出了这个问题。但是您的评论有助于一般理解。
标签: assembly double mips spim qtspim