Assembly 在malloc(程序集NASM x86)之后调用get
在使用malloc(也是C库的)分配内存后,我试图调用C库的“get”函数,但我一直遇到分段错误,我不知道为什么!! 我知道堆栈有问题,但我不知道是什么! 代码如下:Assembly 在malloc(程序集NASM x86)之后调用get,assembly,x86,nasm,Assembly,X86,Nasm,在使用malloc(也是C库的)分配内存后,我试图调用C库的“get”函数,但我一直遇到分段错误,我不知道为什么!! 我知道堆栈有问题,但我不知道是什么! 代码如下: section .rodata LC0: DB "The number is: %i", 10, 0 ; string LC1: DB "Allocation failed!!!", 10, 0 ; string section .data section .bss stack_size:
section .rodata
LC0:
DB "The number is: %i", 10, 0 ; string
LC1:
DB "Allocation failed!!!", 10, 0 ; string
section .data
section .bss
stack_size:
RESB 20
section .text
align 16
global main
extern printf
extern malloc
extern gets
link_size EQU 5
_start:
jmp main
main:
mov dword edi, link_size
push edi
call malloc
mov dword [stack_size], eax
test eax,eax
jz fail_exit
add esp,4
push ecx
call gets
pop ecx
ret
fail_exit:
push LC1
call printf
add esp,4
暂且不提
get
是一个非常不安全的函数,即使您正确使用它(无法防止缓冲区溢出),您的直接问题在于:
push ecx
call gets
pop ecx
如果该ecx
应该是读取字符串的缓冲区,那么您没有将其设置为任何有用的值。这几乎可以肯定是为什么你会出现内存故障
从malloc
返回的缓冲区被放入eax
,而不是ecx
。我怀疑这就是您希望在获取
参数时推送的内容
如果您分配的内存不在希望将
gets
中的字符放入的位置,则需要先将ecx
初始化到其他缓冲区,然后再将其推入。我不是要推eax,我想推ecx作为缓冲区,我知道malloc的返回地址在eax中,我准备将结果移动到stack_size变量中。另外,初始化ecx也无助于解决问题-分段错误。@yair,按ecx作为确切的缓冲区。实际上,您没有将ecx
设置为任何值gets
需要一个缓冲区,您似乎给了它一些随机值,因此出现了故障。您希望将从gets
中获取的字符确切放置在何处(您刚才调用的缓冲区似乎是最符合逻辑的位置)?在按下之前,您需要初始化ecx
。我想将它们放入eax中,然后将它们复制到我指定的缓冲区中(调用C函数的返回值总是放在eax中)。即使我用“mov ECX,0”或诸如此类的东西初始化ECX,它仍然会给出错误。@yair:好的,malloc
中的内存地址在eax
中,而不是ECX
。因此,在调用get
之前,需要按下eax
。如前所述,您没有显式地将ecx
设置为任何值,因此它可能是一些不适合传递给get
的任意值。而将ecx设置为0也无济于事,这是空指针。您需要将其设置为指向某种类型的有效缓冲区。如果我在开始时删除所有部分,那么:push ecx call gets pop ecx工作正常,我甚至可以打印结果,如果ecx不作为缓冲区处理,您如何解释它?