【发布时间】:2021-05-14 20:24:22
【问题描述】:
edit: I added an image of the error shown in gdb 我的汇编代码有问题。这段代码曾经对我有用,它给出了我需要的正确输出(主要是 string1,因为我需要将它的元音字符更改为其他字符)。然而,几个小时后,它停止工作,现在正在转储分段错误。
section .data
NULL equ 0
SYS_EXIT equ 60
string1 db 'hello everyone', NULL
strlen dq 0
section .bss
string2 resb 20
section .text
_start:
mov rdi, string1
mov rsi, strlen
call get_strlen
mov rdi, qword[strlen]
mov rsi, string1
mov rdx, string2
call get_vowel
exit_here:
mov rax, SYS_EXIT
xor rdi, rdi
syscall
get_strlen:
len_loop:
mov al, byte[rdi]
cmp al, NULL
je return
inc rdi
inc byte[rsi]
jmp len_loop
return:
ret
get_vowel:
mov rcx, rdi
mov rsi, rsi
mov rdi, rdx
cld
str_loop:
lodsb
stosb
cmp al, 'a'
je vowel_a
cmp al, 'e'
je vowel_e
cmp al, 'i'
je vowel_i
cmp al, 'o'
je vowel_o
cmp al, 'u'
je vowel_u
loop str_loop
mov byte[rdi], NULL
jmp str_copy
vowel_a:
dec rdi
mov byte[rdi], '@'
inc rdi
jmp str_loop
vowel_e:
dec rdi
mov byte[rdi], '3'
inc rdi
jmp str_loop
vowel_i:
dec rdi
mov byte[rdi], '1'
inc rdi
jmp str_loop
vowel_o:
dec rdi
mov byte[rdi], '0'
inc rdi
jmp str_loop
vowel_u:
dec rdi
mov byte[rdi], 'U'
inc rdi
jmp str_loop
str_copy:
mov rcx, rdi
mov rsi, rdx
mov rdi, rsi
cld
jmp loop1
loop1:
lodsb
stosb
loop loop1
mov byte[rdi], NULL
jmp return1
return1:
ret
根据 gdb,函数 get_vowel 的 on loop1 存在问题。但是,根据我目前对组装的了解,我相当确定它是有效的。
在这种情况下 string1 的假定值为
h3ll0 3v3ry0n3
但是它只输出它的默认值
【问题讨论】:
-
补充一点,在这一切发生之前,我的电脑突然变得不稳定而且非常慢,所以我重新启动它,它也带有一个错误代码,据说与我的内存有关。不确定这与它有什么关系,但我不妨把它放在那里。
-
可能与问题无关,但您忘记在定义
_start之前输入global _start,因此链接器找不到它,可能会默认使用其他地址进行输入。 -
是的,我在帖子中省略了使函数全局化的部分
-
在
loop str_looprcx之后为零。然后你做一个jmp str_copy最终以loop loop1结束,然后尝试重复 2^64 次。这是一种可能的故障模式,可能还有其他的。在 gdb 中使用单步。 -
是的。您有
jmp str_copy,但str_copy以mov rcx, rdi开头,但rdi已设置为mov rdi, rdx的地址。