QtSpim汇编程序:使用double进行堆栈操作时出错

时间:2018-06-12 19:04:15

标签: assembly double mips spim qtspim

我正在为课堂写一个程序。它需要来自控制台的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

1 个答案:

答案 0 :(得分:2)

这是不正确的:sw $ra, 64($ra)

这里发生的事情是您将$ra(0x40005c)的当前值存储在64($ra),即(0x40009c),从而覆盖指令{{ 1}}。

你应该做的是s.d $f14, 16($sp)