我的程序假设要求用户输入,然后打印出字符串中的字符数。截至目前,它告诉我输入Hello时有104个字符然后有一个段错误
这是我的代码
userInput:
.asciz "\nEnter a string: "
TemptRet:
.word 10
inputBuffer:
.skip 11
countMessage:
.STRING "There are %d characters in: \"%s\".\n"
.text
.global main
main:
LDR R0, =courseStr
BL puts
countString:
LDR R0, =userInput
BL printf
LDR R0, =TemptRet
BL scanf
getLine:
MOV R2, R0
BL getchar
LDR R2, =inputBuffer
MOV R1, R0
LDR R0, =countMessage
BL printf
一些建议。
您使用scanf
读取字符串将停止在输入的第一个空格处。相反,您可以使用fgets
,它看起来稍微复杂一些,但了解ARM过程调用约定非常容易。
其次,将.data
部分移到最后并以push {ip, lr}
开头,这样您的例程可以以pop {ip, pc}
结尾。
请考虑在装配体中使用注释来逐步了解每一行的工作。用高级语言编写而没有注释已经够糟糕的了,在汇编中甚至更容易忘记自己在做什么。
下面的代码有几个关键部分:
fgets
(特别注意将FILE* stdin
的值加载到r2中的使用).global main
main:
push {ip, lr}
ldr r0,=prompt // r0 <- prompt*
bl printf
ldr r0,=buffer // r0 <- buffer*
ldr r1,=buflen
ldr r1,[r1] // r1 <- buflen
ldr r2,=stdin
ldr r2,[r2] // r2 <- STDIN
bl fgets // fgets(buffer, buflen, STDIN)
bl strlen // r0 <- strlen(buffer)
mov r1,r0 // r1 <- strlen(buffer)
sub r1,#1 // r1 <- r1 - 1
ldr r0,=output // r0 <- output*
ldr r2,=buffer // r2 <- buffer*
mov r4,#0
str r4,[r2,r1] // r4(NULL) -> buffer + strlen
bl printf
pop {ip, pc}
.data
prompt:.asciz "Enter a string: "
output:.asciz "There are %d characters in: \"%s\".\n"
buflen:.int 128
buffer:.space 128
pi@raspberrypi:~ $ ./input
Enter a string: this is a string of moderate length
There are 35 characters in: "this is a string of moderate length".
祝你好运。>>