Segmentation fault in assembler language
I'm learning assembler language. When I started reading about stack, I tried to write code that adds two numbers and debug it. But when try to call function "add" I get
Program received signal SIGSEGV, Segmentation fault.
The main problem is that the program gives this error without even entering the ADD function. That is, the program, even without executing the call add command, terminates urgently.
here is the code:
global _start
section .text
_start:
call main
add:
push ebp
mov ebp, esp
sub esp, 4
mov eax, [ebp + 8]
mov ebx, [ebp + 12]
add eax, ebx
mov [ebp - 4], eax
ret
main:
push ebp
mov ebp, esp
sub esp, 12
mov [ebp - 8], dword 2
mov [ebp - 12], dword 40
call add
ret
here is the debugging process
Firstly, you never exit the program, which would cause the program to go to an infinite loop, if it could return from the functions successfully. You see, ret is equivalent to pop eip
, which jumps into the address at the top of the stack and continues execution there. Your program however, pushed many additional values onto the stack without ever restoring it, thus, when the ret instruction was executed, the wrong address was popped. You really need to be careful when it comes to the stack in procedures.
I fixed the errors and mentioned, and maybe you could pick up some ideas from my version. But in any case, just remember to restore the stack and exit from the program.
global _start
section .text
_start:
call main
mov ebx, eax ;; using the sum as the return code
mov eax, 1 ;; SYS_exit
int 0x80 ;; syscall
add:
push ebp ;; stack frame
mov ebp, esp
mov eax, [esp+8] ;; first argument (getting esp+8 because we pushed ebp)
mov ebx, [esp+12] ;; second argument
add eax, ebx
mov esp, ebp
pop ebp ;; stack frame restore
ret ;; returning from function
main:
push ebp
mov ebp, esp ;; set up frame pointer.
push dword 2 ;; pushing the arguments
push dword 40
call add
mov esp, ebp ;; tear down stack frame
pop ebp ;; restore frame pointer
ret ;; returning to _start where we exit
nasm -g -f elf32 -o program.o program.asm ; ld -g -m elf_i386 -o program program.o ; ./program ; echo $?