Mips过程:无限循环和PC发生异常

时间:2013-12-31 13:09:48

标签: exception for-loop mips procedure

查看网站上的主题,但我无法解决我的问题。我注意到程序中的代码是无限的,在QTSpim中,我看到所涉及的寄存器是$s0$s1$t2$t4

几个周期后,消息Exception occurred at PC然后expection 7 Bad data address。 这是代码,我无法弄清楚错误在哪里,我试着在没有程序的情况下编写它并且它完美地工作。

.data
string: .asciiz "Hello Simon"
string2: .asciiz ""
    .text
    .globl main

Delete_space:
addi $sp, $sp, -16
sw $s0, 0($sp)
sw $s1, 4($sp)

add $t8, $a0, $zero
lenght_string:
lb $t0, 0($t8)
beqz $t0, for #t8 contain the lenght of string
add $t8, 1
j lenght_string
for:
add $s0, $zero, $zero #i=0
add $s1, $zero, $zero #j=0

condition:
slt $t1, $s0, $t8 #i< lenght_string
beq $t1, $zero, endfor


consequence:
add $t2, $t8, $s0
lb $t3, 0($t2)
bne $t3, ' ', op1
beq $t3, ' ', else
addi $s0, $s0, 1
addi $s1, $s1, 1
j condition
op1:
add $t4, $a1, $s1
sb $t3, 0($t4)
addi $s0, $s0, 1
addi $s1, $s1, 1
j condition
else:
sub $s1, $s1, 1
addi $s0, $s0, 1
addi $s1, $s1, 1
j condition
endfor:

#end 
lw $s1, 4($sp)
lw $s0, 0($sp)
addi $sp, $sp, 16
jr $ra

main:
la $a0, string
la $a1, string2
jal Delete_space

la $a0, string2
li $v0, 4
syscall

li $v0, 10
syscall

1 个答案:

答案 0 :(得分:1)

我认为你试图将字符从一个字符串复制到另一个字符串,跳过空格。 (也许这不是你想要做的 - 不幸的是,我没有时间详细跟踪代码。)我认为问题是你从源字符串复制到没有的数据区域属于你。

在汇编语言中,字符串的处理方式与高级语言中的字符串不同。它们只是一个字节序列 - 没有一个String的概念可以自动扩展以包含你放入它的内容。并且没有边界检查的概念。

查看这些字符串声明:

.data
string: .asciiz "Hello Simon"
string2: .asciiz ""

您所做的是将string分配给包含字节值'H'的内存地址。后续内存位置包含'e', 'l', 'l', 'o', ' ', 'S', 'i', 'm', 'o', 'n', '\0'

然后,您已将string2分配给包含字节值'\0'(空终止符)的内存地址。

如果将一个字节写入string2指向的内存地址,它将替换空终止符。 (此时你已经遇到了麻烦,因为syscall不知道你的字符串结束的位置。)如果你再写一个字节到string2 + 1所指向的内存地址,你现在就是写入您未分配给string2的内存。它可能属于存储的其他变量 - 在这种情况下,您只需覆盖之前的变量。这是一个“缓冲区溢出”,这就是像Internet Explorer这样写得不好的程序如何被黑客利用。

如果我正确地解释了你的程序的目的,你需要为你的输出创建一个足以容纳它的缓冲区。假设您的输出永远不会超过您的输入,那么这样的东西就会起作用:

.data
string: .asciiz "Hello Simon"
string2: .asciiz "xxxxxxxxxxx"