Stos i instrukcja "ret" - dlaczego instrukcja "ret 8" nie działa poprawnie?

0

Hej, mam problem z bardzo prostym programem w asm. Pierwszy program wykonuje się poprawnie a drugi nie

extern _printf

section .text
global _main:
_main:
	push dword [number]
	push dword format
	call _printf
	add esp, 8
	ret
section .data
	format db "some number: %d", 0
	number dd 15

Program poniżej wywala się po wypisaniu linijki z tekstem.

extern _printf

section .text
global _main:
_main:
	push dword [number]
	push dword format
	call _printf
	;add esp, 8
	ret 8
section .data
	format db "some number: %d", 0
	number dd 15

Moje pytanie jest następujące: dlaczego instrukcja ret 8 nie działa poprawnie? Z tego co czytałem powinna ona wrócić pod adres który jest na stosie o 8 bajtów wyżej (czyli tak jakbyśmy przesunęli się z esp o 8 w górę) i oba programy powinny kończyć się bez błędu. Ta sprawa nie daje mi spokoju :(

0

The optional numeric (16- or 32-bit) parameter to ret specifies the number of stack bytes or words to be released after the return address is popped from the stack. Typically, these bytes or words are used as input parameters to the called procedure.
http://docs.oracle.com/cd/E19957-01/816-1323/instructionset-67/index.html

0

OK, dzięki.
Więc to działa tak że ret z parametrem jest używane przez funkcję do czyszczenia stosu z argumentami, a nie przez wywołującego. W takim razie będę się trzymać dodawania do esp po wywołaniu.
Wychodzi na to że jestem lewy z angielskiego :(

0

Najprościej:

ret 8

oznacza tak jakby

ret
add esp, 8

a ty potrzebujesz odwrotnie.

0

Jeszcze raz dziękuję :)
@Azarien - dobry przykład podałeś, wcześniej byłem przekonany że to pierwsze ściąga ze stosu a dopiero później robi ret, i to był spory błąd.

1 użytkowników online, w tym zalogowanych: 0, gości: 1