de responsabilidad: No sé MIPS, pero conozco algunos x86, y creo que el principio debe ser el mismo ..
En la convención de llamada de función habitual, el compilador empujará el valor de n
en la pila para pasarlo a la función foo
. Sin embargo, existe la convención fastcall
que puede usar para decirle a gcc que pase el valor a través de los registros en su lugar. (MSVC también tiene esta opción, pero no estoy seguro de cuál es su sintaxis.)
test.cpp:
int foo1 (int n) { return ++n; }
int foo2 (int n) __attribute__((fastcall));
int foo2 (int n) {
return ++n;
}
Compilación de lo anterior con g++ -O3 -fomit-frame-pointer -c test.cpp
, me pasa por foo1
:
mov eax,DWORD PTR [esp+0x4]
add eax,0x1
ret
Como se puede ver, se lee en el valor de la pila.
Y aquí es foo2
:
lea eax,[ecx+0x1]
ret
Ahora toma el valor directamente del registro.
Por supuesto, si incorpora la función, el compilador hará una simple adición en el cuerpo de su función más grande, independientemente de la convención de llamadas que especifique. Pero cuando no se puede incluir en línea, esto va a suceder.
Descargo de responsabilidad 2: No estoy diciendo que deba adivinar continuamente el compilador. Probablemente no sea práctico y necesario en la mayoría de los casos. Pero no suponga que produce un código perfecto.
Edit 1: Si habla de variables locales simples (no argumentos de funciones), entonces sí, el compilador las asignará en los registros o en la pila como lo considere oportuno.
Editar 2: Parece que la convención de llamadas es específica de la arquitectura, y MIPS pasará los primeros cuatro argumentos en la pila, como Richard Pennington ha declarado en su respuesta. Por lo tanto, en su caso, no tiene que especificar el atributo adicional (que es, de hecho, un atributo específico de x86).
El compilador optimizaría. Pruebe 'gcc -fverbose-asm -O2 -S yoursource.c' luego mire dentro de' yoursource.s' –