我正在尝试学习汇编,并且发现在尝试从堆栈中推送/弹出数据时我一直在获得段错误。我已经阅读了一些指南,知道堆栈如何工作以及如何使用堆栈;但不知道为什么我一直收到错误。
有人可以帮忙吗?
segment .data
myvar: db "hello world", 0xA0, 0
myvarL: equ $-myvar
segment .text
global _start
_start:
push ebp
mov ebp, esp
push myvarL
push myvar
call _hworld
mov eax, 1
mov ebx, 0
int 0x80
_hworld:
mov eax, 4
mov ebx, 1
mov ecx, [ebp+4]
mov edx, [ebp+8]
pop ebp
int 0x80
ret
我假设+4是32位,然后+8是64位。我不清楚为什么在我读过的一些指南上做这种方式。我会假设myvar
是13个字节?
这是错误:
$ ./pushpop
Segmentation fault
答案 0 :(得分:0)
只是一个想法
segment .data
myvar: db "hello world", 0xA0, 0
myvarL: equ $-myvar
segment .text
global _start
_start:
push ebp
mov ebp, esp
push myvarL
push myvar
call _hworld
pop ebp //
//
mov eax,1
mov ebx,0
int 80h ; // exit
_hworld:
mov eax, 4
mov ebx, 1
mov ecx, [ebp+4]
mov edx, [ebp+8]
// pop ebp <-- this will pop the return address
int 0x80
ret
答案 1 :(得分:0)
_start:
push ebp
mov ebp, esp ; ebp points to its old value on the stack
; ebp + 4 points to the return address from _start
; ebp + 8 points to 1st on-stack parameter to _start
push myvarL ; ebp - 4 points to myvarL on stack
push myvar ; ebp - 8 points to myvar on stack
call _hworld
; are we going to now execute _hworld without a call???
; vvvv
_hworld:
mov eax, 4
mov ebx, 1
mov ecx, [ebp+4] ; ebp + 4 points to return address from _start
mov edx, [ebp+8] ; ebp + 8 points to 1st on-stack parameter to _start
; ^^^^ why???
顺便说一句,我不确定结肠是否正确:myvarL: equ $-myvar
,当然,除非push myvarL
原来是push 13
。
哦,这一行:
pop ebp
将从_hworld
窃取返回地址,因此以下ret
将从堆栈中获取myvar
作为返回地址并尝试执行myvar
作为代码
答案 2 :(得分:0)
我的代码是segfaulting的原因是因为我没有在进入_hworld
段时保存esp并且在离开时没有恢复它。
这是新的工作代码:
segment .data
myvar: db "hello world", 0x0A, 0
myvarL: equ $-myvar
myvar2: db "super bad test", 0x0A, 0
myvar2L: equ $-myvar2
segment .text
global _start
_start:
push myvarL ; store myvarL on the stack
push myvar ; store myvar on the stack
call _hworld
push myvar2L ; store myvar2L on the stack
push myvar2 ; store myvar2 on the stack
call _hworld2
mov eax, 1
mov ebx, 0
int 0x80
_hworld:
push ebp ; store the current value of ebp on the stack (hence +8)
mov ebp, esp ; store current esp in ebp
mov eax, 4
mov ebx, 1
mov ecx, [ebp+8] ; +4 is old ebp
mov edx, [ebp+12]
int 0x80
mov esp, ebp ; restore ebp to esp
pop ebp ; restore ebp
ret
_hworld2:
push ebp ; store old ebp on the stack
mov ebp, esp ; store esp in ebp
mov eax, 4
mov ebx, 1
mov ecx, [ebp +8] ; +4 is old ebp
mov edx, [ebp +12]
int 0x80
mov esp, ebp ; restore ebp to esp
pop ebp ; restore ebp
ret