Converting C to mips assembly, Unaligned address error

齐天大圣

i'm doing an assignment now, it's almost done but i keep getting error saying

Unaligned address in inst/data fetch: 0x10010016

at line:

lw   $t3,0($a1)     # get the value of b[k] and save it into t3

I search online and i find an answer saying i have to use .align 2 to fix this, but that doesn't work for my problem.

can someone please give me a hint on this, I literally spend 6 hours on this..

thank you very much

Here is my code:

# a -> $a0
# b -> $a1
# n -> $a2
# j -> $a3
# k -> $s0
# i -> $t0


.data

.align 2

arra:   .word 1,2,7,4,5
arrb:   .word 3,4,7,2,9



.text


    la $a0, arra        # we have array a[] = { 1,2,7,4,5}
    la $a1, arrb        # we have array b[] = {3,4,7,2,9}






    addi $a2,$zero,0        # n = 0
    addi $a2,$zero,3        # n = 3

    addi $a3,$zero,0        # j = 0
    addi $a3,$zero,3        # j = 3

    addi $s0,$zero,0        # k = 0
    addi $s0,$zero,2        # k = 2



g:

    addi $sp, $sp, -24

    sw   $ra, 20($sp)       # save $ra on stack
    sw   $s0, 16($sp)        # save $s0 (k) on stack
    sw   $a0, 12($sp)        # save a0(a) on stack
    sw   $a1, 8($sp)        # save a1(b) on stack
    sw   $a2, 4($sp)        # save a2(n) on stack
    sw   $a3, 0($sp)        # save a3(j) on stack


    move $a3,$s0            # set j = k
    jal    f            # f(a,b,n,k,k)

    add  $a1,$a1,$s0    # return the address of b[k]
    lw   $t3,0($a1)     # get the value of b[k] and save it into t3
    add  $v0, $t3,$zero # return the value


    lw  $a3,0($sp)
    lw  $a2,4($sp)
    lw  $a1,8($sp)
    lw  $a0,12($sp)
    lw  $s0,16($sp)
    lw  $ra,20($sp)

    addi $sp,$sp,24

    jr   $ra





f:
    bne  $a2, $zero, ELSE   # if (n != 0) go to ELSE


    addi $t0, $zero, 1  # set $t0 = 1
    sw   $t0, 0($a1)    # then set b[0] = 1

    addi $t0, $zero, 1  # set $t0 = 1
    sw   $t0, 0($a1)    # then set b[0] = 1

    addi $t0, $zero, 1  # set i = 1 for the loop

forLoop:
    slt $t1,$s0, $t0    # if k < i, end the loop, use $t1 to store the boolean value
    bne $t1, 1, forLoopDone
    add $a1, $a1, $t0       # b[i] address
    add $t2,$zero,$zero
    sw  $t2, 0($a1)         # b[i] = 0
    addi $t0, $t0, 1        # i = i + 1
    j    forLoop


ELSE:
    bne $a3, $zero, updateJ     # test if (j == 0), if not, j = j -1
    j    iteratef

updateJ:
    addi $a3, $a3, -1       # j = j -1
    j    iteratef

iteratef:
    addi $a2, $a2, -1       # iterate, n = n - 1
    j    f              # f(b, a, n-1, j_update, k)

    bne  $a3, $zero, forLoop1Ini    # if (j != 0), go to for_loop1_ini
    lw   $a0, 0($a0)        # there might be sth wrong here
    sw   $a1, 0($a1)        # set b[0] = a[0]
    addi $a3, $a3, 1        # j++


forLoop1Ini:
    addi $t0, $a3, 0        # set i = j

forLoop1Start:
    slt  $t1,$s0, $t0   
    bne  $t1, 1, forLoop1Done
    add  $a0, $a0, $t0      # get a[i] address
    lw   $t1, 0($a0)        # t1 = a[i]
    lw   $t2, -4($a0)       # get b[i]
    add  $a1, $a1, $t0      # get b[i] address
    add  $t1, $t1, $t2      # t1 = a[i-1] + a[i]
    sw   $t1, 0($t1)        # b[i] = a[i-1] + a[i]
    addi $t0, $t0, 1        # i++
    j    forLoop1Start

forLoop1Done:
    nop

forLoopDone:
    nop



    jr  $ra
gusbro

Your problem is that you are not taking into account the size of each element of the array. Each element occupies 4 bytes. Therefore, instead of issuing

  add  $a1,$a1,$s0    # return the address of b[k] 

you should multiply the index by 4 (which is the size of element) to get the effective offset:

  sll $s1, $s0, 2     # Compute effective offset (i.e. multiply index by 4)
  add  $a1,$a1,$s1    # return the address of b[k]
  lw   $t3,0($a1)     # get the value of b[k] and save it into t3

Collected from the Internet

Please contact [email protected] to delete if infringement.

edited at
0

Comments

0 comments
Login to comment

Related