2010-11-24 14 views
9

He estado siguiendo el excelente libro Programming Ground Up, queriendo aprender ensamblaje. Aunque no estaba en el libro en este momento, quería llamar a mi función de ensamblaje desde C. en una máquina de 32 bits, esto funciona igual que cuando se trabaja desde el libro.C to assembly call convention 32bit vs 64bit

Lo que hago aquí es almacenar el primer argumento en %ebx y el segundo en %ecx.

.type power, @function 
.globl power 
power: 
    pushq %ebp 
    movl %esp, %ebp 
    subl $4, %esp 

    movl 8(%ebp), %ebx 
    movl 12(%ebp), %ecx 

Compilo esto (y el resto de la función) en un fichero objeto, se crea una main.c, donde prototipo de la función y la llamo, algo como esto:

int power(int b, int x); 
int a = power(2, 1); 

Sin embargo Cuando compilo esto en una máquina de 64 bits, obtengo algunos resultados muy inesperados. Modifiqué lo obvio, como el hecho de que %esp y %epb deben ser reemplazados por %rsp y %rpb, ¡pero al excavar con GDB se revela que los argumentos no se encuentran en la pila!

Revisando lo que sucede al usar la opción -S en GCC, puedo ver que en lugar de presionar las variables en la pila, GCC almacena los argumentos en los registros.

movl $1, %esi 
movl $2, %edi 
call power 

En la máquina de 32 bits, que hace lo que espero y empujar los argumentos en la pila:

movl $1, 4(%esp) 
movl $2, (%esp) 
call power 

Ahora lo que está pasando aquí? ¿Por qué GCC pasa los argumentos en registros en 64 bits y en la pila en 32 bits? ¡Esto es muy confuso! Y no puedo encontrar ninguna mención sobre esto en ningún lado. ¿Hay alguien que pueda iluminarme en esta situación?

+1

convenciones de llamada x64 son diferentes a las x86. En la mayoría de los casos, debido a los registros adicionales, los primeros cuatro argumentos se pasan en los registros. – wj32

Respuesta

27

64 bits convención de llamada C es:% RDI,% RSI,% RDX,% RCX,% R8 y% r9

Ver la descripción completa aquí: "System V Application Binary Interface: AMD64 Architecture Processor Supplement" http://www.x86-64.org/documentation/abi.pdf

3,2 Función secuencia de llamada

Cuando aprendí el mismo tema, realicé pequeños programas C con las funciones requeridas, los compilé en un compilador de 64 bits y leí el código ensamblado producido por el compilador C. El compilador C/C++ se puede usar como un tipo de referencia de ensamblado.

+0

hojeé ese documento exacto, pero lo estudié más de cerca ahora, y está todo allí, y tiene mucho sentido ahora. ¡Gracias! – Cbsch

+0

En cuanto a su edición: Sí, así es como trato de hacerlo también. Modificar la función de ensamblaje para que funcione no fue problema, y ​​observar lo que hace el compilador tampoco es problema, el problema fue que no entendía las reglas para este comportamiento. Pero el documento al que se vinculó fue la respuesta perfecta para eso. – Cbsch

+10

Como nota, Windows usa un ABI diferente - http://msdn.microsoft.com/en-us/library/ms235286.aspx con solo RCX, RDX, R8, R9 para los argumentos. – Brian