MIPS无法识别我的ascii到十进制转换?

时间:2014-10-09 03:03:48

标签: type-conversion mips

我正在尝试用MIPS为我的Comp-Sci类手动构建一个计算器。我不是很远,因为我会通过我的代码看到,但我的主要问题是我的转换不起作用。当我输入一个数字时似乎很好,但是当我尝试输入像+或*这样的运算符时,它会存储疯狂的值,如" b" for +是11,而不是42.此外,它不能将我的输入键识别为十进制值为10的新行命令。

请让我直截了当?现在只有添加才能完全发挥作用,但在我能解决其他问题之前,我甚至无法证明这些问题能够起作用并转移到其他所有问题上。

.globl main 
.globl done
.globl rdlp #read loop
.globl rdop #read operator
.globl stro #store operator
.globl strd #store digit
.globl chkd #check digit
.globl dig2 #10's digit 
.globl dig3 #100's digit
.globl dig4 #1000's digit
.globl lp2d #10's digit loop
.globl lp3d #100's digit loop
.globl lp4d #1000's digit loop
.globl comp #computation loop
.globl chex
.globl chem
.globl chea
.globl adtn
.globl sbtr
.globl mulp
.globl mllp
.globl mul0
.globl mul1
.globl divi
.globl dvlp
.globl dv2a
.globl dv2b
.globl div3
.globl expo
.globl exlp
.globl excn
.globl exp0
.globl exp1
.globl modu
.globl molp
.globl mo2a
.globl mo2b
.globl mod3
.globl msrt
.globl srt1



.data
line:   .asciiz     "\n"                        #new line




#----------------------------------------------------
# Main body of the calculator
# reads string and converts
# from ascii
# 
# s0 is main equation storage
# t0 is character storage
# t1 is boolean
# t2 is tens, 100's digit counter
# t3 is temp numerical storage
# t4 is temp storage
# t5 is counter for subtraction/mult/div
# t9 is loop counter for digits
#----------------------------------------------------

.text
main:   lui $s0, 0x1000     #creates base address for storage
    addi    $s0, $s0, 4
rdlp:   addi    $v0, $0, 12     #empty prompt for calculator string entry
    syscall 
    add $t0, $0, $0     #initialize t0 for loop sake
    add $t0, $0, $v0        #dumps string into address of t0
    add $t0, $t0, -48       #adjusts ascii value to decimal
    beq $t0, 10, comp       #moves out of read loop                                 
    j rdop
    or  $0, $0, $0      #no op

rdop:   beq $t0, 94, stro
    or  $0, $0, $0
    beq $t0, 37, stro
    or  $0, $0, $0
    beq $t0, 42, stro
    or  $0, $0, $0      #no op
    beq $t0, 43, stro
    or  $0, $0, $0
    beq $t0, 45, stro
    or  $0, $0, $0      #no op
    beq $t0, 47, stro
    or  $0, $0, $0      #no op
    beq $0, $0, chkd
    or  $0, $0, $0      #no op

stro:   bgtz    $t2, strd       #checks is a numerical digit is present
    or  $0, $0, $0
    sw  $t0, ($s0)      #stores oprator into address in s0
    addi    $s0, $s0, 4     #increments address for next entry  
    j rdlp              #jumps back to rdlp to 
    add $0, $0, $0      #increment operation counter

strd:   sw  $t3, ($s0)      #adds value in t3 to store address
    addi    $s0, $s0, 4     #increments address for next value
    add $t2, $0, $0     #initializes t2 to show no number 
    j stro              #jump back to store operator
    add $0, $0, $0      #increment operation counter

chkd:   beq $t2, 1, dig2        #branches to 2dig to multiply by ten
    or  $0, $0, $0      #no op
    beq $t2, 2, dig3        #addresses 100's position issue
    or  $0, $0, $0      #no op
    beq $t2, 3, dig4        #addresses 1000's 
    or  $0, $0, $0      #no op
    add $t3, $0, $t0        #places digit value in t3 for temp
    j rdlp              #back to read loop
    add $t2, $0, 1      #add 1 to digits count for 10's, 100's

dig2:   add $t9, $0, 9      #add 9 to counter
    lw  $t1, ($s0)
    add $t8, $0, $t1        
lp2d:   add $t1, $t1, $t8       #add t0 to itself and place in t0
    add $t9, $t9, -1        #decrement counter
    bne $0, $t9, lp2d       #loop
    add $t2, $t2, 1     #increment digit counter
    add $t3, $t1, $t0       #adds 10's digit to value in t3 if any
    add $t8, $0, $0
    add $t1, $0, $0
    j rdlp
    add $t9, $0, $0     #reinitialize t9 counter 

dig3:   add $t9, $0, 99     #add 9 to counter
    lw  $t1, -4($s0)
    add $t8, $0, $t1        
lp3d:   add $t1, $t1, $t8       #add t0 to itself and place in t0
    add $t9, $t9, -1        #decrement counter
    bne $0, $t9, lp3d       #loop
    add $t2, $t2, 1     #increment digit counter
    add $t3, $t1, $t0       #adds 10's digit to value in t3 if any
    add $t8, $0, $0
    add $t1, $0, $0
    j rdlp
    add $t9, $0, $0     #reinitialize t9 counter 

dig4:   add $t9, $0, 999        #add 9 to counter
    lw  $t1, -9($s0)
    add $t8, $0, $t1        
lp4d:   add $t1, $t1, $t8       #add t0 to itself and place in t0
    add $t9, $t9, -1        #decrement counter
    bne $0, $t9, lp4d       #loop
    add $t2, $t2, 1     #increment digit counter
    add $t3, $t1, $t0       #adds 10's digit to value in t3 if any
    add $t8, $0,$0
    add $t1, $0, $0
    j rdlp
    add $t9, $0, $0     #reinitialize t9 counter 

#----------------------------------------------------
# Section dealing with the calculator
# calculations and operators.
#----------------------------------------------------

comp:   add $s2, $0, $s0        #saves address of final digit
    lui $s0, 0x1000     #return to first address
    addi    $s0, $s0, 4     #increment mem address, 0 will store answers
chex:   lw  $a2, ($s0)      #load possible operator into a2
    beq $a2, 94, expo       #branch to expo if ^ found
    or  $0, $0, $0
    bne $s0, $s2, chex  
    addi    $s0, $s0, 4     #increment address
    lui $s0, 0x1000
    addi    $s0, $s0, 4
chem:   lw  $a2, ($s0)      #load possible operator into a2
    beq $a2, 42, mulp       #branch to mulp if * found
    or  $0, $0, $0
    beq $a2, 47, divi       #branch to divi if / found
    or  $0, $0, $0
    beq $a2, 47, modu       #branch to modu if % found
    or  $0, $0, $0
    bne $s0, $s2, chem  
    addi    $s0, $s0, 4     #increment address
    lui $s0, 0x1000
    addi    $s0, $s0, 4         
chea:   lw  $a2, ($s0)      #load possible operator into a2
    beq $a2, 43, adtn       #branch to adtn if + found
    or  $0, $0, $0
    beq $a2, 45, sbtr       #branch to sbtr if - found
    or  $0, $0, $0
    bne $s0, $s2, chea  
    addi    $s0, $s0, 4     #increment address

done:   lui $s0, 0x1000
    lw  $a1, ($s0)
    or  $0, $0, $0
    addi    $v0, $0, 4
    add $a0, $0, $a1
    syscall

    beq $0, $0,rdlp 





#----------------------------------------------------
# the addition subroutine
#----------------------------------------------------

adtn:   lw  $a1, -4($s0)        #add value left of operator in a1
    lw  $a3, 4($s0)     #add value right of operator in a3
    add $a1, $a1, $a3       #adds the values in a1 and a3
    sw  $a1, -4($s0)        #store value into memory address
    add $t8, $0, $s0        #add memory address to t8
    lui $s0, 0x1000     #move focus back to first address
    sw  $a1, 0($s0)     #store answer into first address
    add $s0, $0, $t8        #restore original address focus
    add $t8, $0, $0     #intialize t8
    j msrt              #jump to memory sorter
    addi    $s0, $s0, 4     #incremments memory

#----------------------------------------------------
# the substitution subroutine
#----------------------------------------------------

sbtr:   sub $a1, $a1, $a3       #subtraction

#----------------------------------------------------
# the multiplication subroutine
# mllp is the actual loop for multiplying
# mul0 and mul1 deal with the cases of
# multiplying by 0 and 1.
#----------------------------------------------------

mulp:   add $t5, $0, $a3        #begin multiplication set counter
    beq $a1, 0, mul0        #event of mult by 0
    or  $0, $0, $0      #no op      
    beq $a3, 0, mul0        #event of mult by 0     
    or  $0, $0, $0      #no op
    beq $a1, 1, mul1        #event of mult by 1
    or  $0, $0, $0      #no op
    beq $a3, 1, mul1        #event of mult by 1
    or  $0, $0, $0      #no op
mllp:   add $a1, $a1, $a1       #begin multiplcation loop
    add $t5, $t5, -1        #decrement loop counter
    bne $t5, 1, mllp        #branch when loop reaches 1
    or  $0, $0, $0      #no op
mul0:   add $a1, $0, $0     #set value of zero due to mult by 0
mul1:   add $a1, $0, $a1        #set value for mult by one

#----------------------------------------------------
# the division subroutine
# unchanged from my project 0 submission
#----------------------------------------------------

divi:   add $t5, $0, 17     #set division loop counter
    add $t3, $0, $a1        #set t3 to dividend from a1
    add $t4, $0, $a3        #set t4 to divisor from a3 
    add $t6, $0, $a1        #set t6 to remainder which equals the dividend
    sll $t4, $t4, 16        #shift the divisor left logical 16 places
dvlp:   sub     $t6, $t6, $t4       #subtracts divisor from remainder
    bgez    $t6 dv2a        #if sub is greater than equal to zero  branch 
    add     $0, $0, $0      #NOP
    bltz    $t6 dv2b        #branch if less than zero
    add     $0, $0, $0          #NOP
dv2a:   sll     $t7, $t7, 1     #logic shift left one zero to quotient
    j div3              #moves calculation to third step 
    add     $t7, $t7, 1     #add one to quotient 
dv2b:   add     $t6, $t6, $t4       #restores value of remainder
    j div3              #moves calculation to third step
    sll     $t7, $t7, 1     #shifts quotient left one bit and inserts zero
div3:   srl     $t4, $t4, 1     #shifts the divisor register one bit right 
    add     $t5, $t5, -1        #decrements counter by one
    bne     $0,  $t5, dvlp      #loops back to division for next loop
    or      $0, $0, $0      #NOP

#----------------------------------------------------
# the exponent subroutine
#----------------------------------------------------

expo:   add $t5, $0, $a1        #begin multiplication set counter
    add $t6, $0, $a3        #exponent loop counter
    add $t6, $t6, -1        #decrement power counter by 1 for first run
    beq $a1, 0, exp0        #event of mult by 0
    or  $0, $0, $0      #no op      
    beq $a3, 0, exp0        #event of mult by 0     
    or  $0, $0, $0      #no op
    beq $a1, 1, exp1        #event of mult by 1
    or  $0, $0, $0      #no op
    beq $a3, 1, exp1        #event of mult by 1
    or  $0, $0, $0      #no op
exlp:   add $a1, $a1, $a1       #begin multiplcation loop
    add $t5, $t5, -1        #decrement loop counter
    bne $t5, 1, exlp        #branch when loop reaches 1
    or  $0, $0, $0      #no op
excn:   add $t6, $t6, -1        #decrement power loop
    bgtz    $t6, exlp
    add $t5, $0, $a1        #branch delay reset mult counter
    #placer for branch remember to zero out t5

exp0:   add $a1, $0, $0     #set value of zero due to mult by 0
exp1:   add $a1, $0, $a1        #set value for mult by one

#----------------------------------------------------
# the division subroutine
# unchanged from my project 0 submission
#----------------------------------------------------

modu:   add $t5, $0, 17     #set division loop counter
    add $t3, $0, $a1        #set t3 to dividend from a1
    add $t4, $0, $a3        #set t4 to divisor from a3 
    add $t6, $0, $a1        #set t6 to remainder which equals the dividend
    sll $t4, $t4, 16        #shift the divisor left logical 16 places
molp:   sub     $t6, $t6, $t4       #subtracts divisor from remainder
    bgez    $t6 dv2a        #if sub is greater than equal to zero  branch 
    add     $0, $0, $0      #NOP
    bltz    $t6 dv2b        #branch if less than zero
    add     $0, $0, $0          #NOP
mo2a:   sll     $t7, $t7, 1     #logic shift left one zero to quotient
    j div3              #moves calculation to third step 
    add     $t7, $t7, 1     #add one to quotient 
mo2b:   add     $t6, $t6, $t4       #restores value of remainder
    j div3              #moves calculation to third step
    sll     $t7, $t7, 1     #shifts quotient left one bit and inserts zero
mod3:   srl     $t4, $t4, 1     #shifts the divisor register one bit right 
    add     $t5, $t5, -1        #decrements counter by one
    bne     $0,  $t5, dvlp      #loops back to division for next loop
    or      $0, $0, $0      #NOP
    # placer remember the answer is the remainder t6

#----------------------------------------------------
# sort memory locations subroutine
#----------------------------------------------------

msrt:   beq $s2, $s0, srt1      #branch to comp if memory is at last address    
    or  $0, $0, $0
    lw  $a2, 4($s0)     #load value into a2 
    sw  $a2, -4($s0)        #store a2 into earlier address
    lw  $a2, 8($s0)     #load value into a2
    sw  $a2, ($s0)      #store a2 into current address
    or  $0, $0, $0
    j comp              #jump back to comp
    or  $0, $0, $0

srt1:   addi    $s0, $s0, -8        #move memory address

0 个答案:

没有答案