8
votes

Comment les appels de procédure fonctionnent-ils dans l'assembleur?

Je viens de commencer à bricoler avec ASM et je ne sais pas si ma compréhension des appels de procédure est correcte.

Dites à un moment donné dans le code Il existe un appel de procédure P>

mov AX, 0004


0 commentaires

4 Réponses :


-1
votes

Je ne pense pas que la valeur de retour est stockée dans la hache de registre


1 commentaires

@ Int3: Cela dépend de la convention appelante. Il n'y a rien de automatique ici. La fonction d'appel et la fonction appelée doivent être d'accord sur l'endroit où la valeur de retour est.



1
votes
// possibly there are arguments pushed here
...
call dword ptr[123] // push next OP code offset in the stack and jump to procedure

// procedure
...
ret 0004 // pop offset, set EIP to that offset and decrease ESP by 4
we additionally decrease the ESP if we had pushed arguments in the stack prior calling the procedure.
If there are pushed arguments, your program crashes because you don't pop them. The return offset for the current procedure will be wrong since it will get a value from one of the pushed arguments as the offset.

0 commentaires

12
votes

dans l'assembleur X86 Le paramètre sur l'instruction RET CODE> signifie:

RET Immédiate i> code> P>

Retour à la procédure d'appel et pop immédiat em> octets de la pile. P> blockQuote>

(citant de logiciel Intel® 64 et IA-32 Architectures Manuels du développeur Vol 2b ) P>

Donc, lorsque vous tapez: p> xxx pré>

Vous dites à la CPU de revenir à l'instruction immédiatement après l'appel code> code>, et sur POP 4 octets la pile. C'est génial si vous poussés em> 4 octets sur la pile avant l'appel. P> xxx pré>

Notez que cela n'a rien à voir avec la valeur de retour. En fait, une procédure d'assemblage n'a aucun moyen de préciser qu'une valeur est une valeur retour em>. Tout cela est fait par convention. La plupart des compilateurs dont je suis conscient utiliseront EAX code> pour contenir la valeur de retour, mais cela est vrai uniquement parce que la fonction appeler em> s'attendrale là-bas. P> Donc, votre code d'appel serait: p> xxx pré>

et votre fonction qui renvoie la valeur 4 serait le suivant: p>

mov eax, 4
ret


3 commentaires

Merci! La plupart des tutoriels que j'ai googliés se font simplement utiliser RET et n'expliquent pas le fonctionnement immédiat immédiat . Je suis d'autres confuses lorsque l'assembleur LLVM avait apparemment une commande "RET ".


Y a-t-il une raison pour laquelle RET peut retourner à un endroit autre que l'appel? Je viens de créer une question et j'ai trouvé cela dans des questions connexes


Oui, si vous avez manipulé l'adresse de retour que appelez poussé sur la pile.



2
votes

Tout dépend du Convention d'appel utilisé. Je ne répète pas l'article Wikipedia ici, je viens de lire la définition.

Dans le C appelant convention , par exemple, la valeur de retour serait dans EALE / AX / AL. Votre instruction unique n'entre pas: il s'agit d'une fonction vide qui prend environ 4 octets de paramètres (éventuellement un seul int) qui ne fait rien. Comme il s'agit de l'obligation de Callee de nettoyer la pile dans cette convention appelante, ignorant de le faire et de remplacer l'appel avec une «hache MOV» ne fonctionne pas.

Je soupçonne également que vous soyez peut-être bricoler avec un assemblage 32 bits tout en lisant un document 16 bits. Ce n'est pas un gros problème, mais vous devriez être au courant des différences.


0 commentaires