Ahmed Naser
Ahmed Naser

Reputation: 11

Runtime exception at 0x00400014: address out of range 0x7fbffffc

I am trying to write a recursive function that prints numbers from 1 up to X, but I get this error, specifically at sw $a0, 0($sp).

.data

.text

# Getting user input
li $v0, 5
syscall
move $a0, $v0

PrintUp: 
     addi $sp, $sp, -8   #make a stack for two element 
     sw   $ra, 4($sp)    #save the address
     sw   $a0, 0($sp)    #save the argument 
     beq  $t0, 0, EqZero  #if X=0, go to EqZero
     addi $sp, $sp, 8  #pop the elements
     jr   $ra    #return
EqZero:
     addi $a0, $a0, -1    #decrement i
     jal  PrintUp  #call the recursive function
     lw   $a0, 0($sp)
     lw   $a0, 4($sp)
     addi $sp, $sp, 8  #pop the elements
     li $v0, 1       
     syscall 
     jr   $ra    #return

Upvotes: 1

Views: 1188

Answers (1)

Craig Estey
Craig Estey

Reputation: 33601

I've created two versions of your program. One with annotations for the bugs. And a cleaned up and working version. Please pardon the gratuitous style cleanup.

Here's the annotated version:

    .data

    .text

    # Getting user input
    li      $v0,5
    syscall
    move    $a0,$v0

# NOTE/BUG: doing fallthrough to PrintUp -- needs "jal PrintUp"

PrintUp:
    addi    $sp,$sp,-8              # make a stack for two element
    sw      $ra,4($sp)              # save the address
    sw      $a0,0($sp)              # save the argument

# NOTE/BUG: $t0 never set to anything -- should this be $a0?
    beq     $t0,0,EqZero            # if X=0, go to EqZero

# NOTE/BUG: does not restore $ra/$a0
    addi    $sp,$sp,8               # pop the elements
    jr      $ra                     # return

EqZero:
    addi    $a0,$a0,-1              # decrement i

    jal     PrintUp                 # call the recursive function

    lw      $a0,0($sp)

# NOTE/BUG: this should be $ra and not $a0
    lw      $a0,4($sp)
    addi    $sp,$sp,8               # pop the elements

# NOTE/BUG: this will only print the zero value
    li      $v0,1
    syscall

    jr      $ra                     # return

Here's the corrected version:

    .data
nl:         .asciiz     "\n"

    .text
    .globl  main
main:

    # Getting user input
    li      $v0,5
    syscall
    move    $a0,$v0

    jal     PrintUp

    # exit program
    li      $v0,10
    syscall

PrintUp:
    addi    $sp,$sp,-8              # make a stack for two element
    sw      $ra,4($sp)              # save the address
    sw      $a0,0($sp)              # save the argument

    bne     $a0,0,NeZero            # if X!=0, go to NeZero

    addi    $sp,$sp,8               # pop the elements
    jr      $ra                     # return

NeZero:
    addi    $a0,$a0,-1              # decrement i

    jal     PrintUp                 # call the recursive function

    lw      $a0,0($sp)
    lw      $ra,4($sp)
    addi    $sp,$sp,8               # pop the elements

    li      $v0,1
    syscall
    move    $t0,$a0

    li      $v0,4
    la      $a0,nl
    syscall

    move    $a0,$t0
    jr      $ra                     # return

Upvotes: 1

Related Questions