UNIX pasa argumentos a través de la pila. Linux sigue la convención MSDOS pasando argumentos a través de registros. ¿Por qué?

No estoy seguro de por qué esta pregunta piensa que Unix tiene la convención de pasar por la pila. Todas las máquinas RISC (con las que Unix se asoció estrechamente) tienen un gran número de registros en gran parte para facilitar las convenciones de llamadas basadas en registros. Al menos un RISC incluso tiene argumentos de registro integrados en su arquitectura: SPARC y sus ventanas de registro. Por lo tanto, la suposición en esta pregunta parece incorrecta, ya que muchos Unix han usado durante mucho tiempo la transferencia de argumentos de registro, especialmente Solaris en SPARC.

De hecho, es en x86 donde las convenciones de llamadas a menudo se basan en la pila, no en el registro, ya que x86 tiene muy pocos GPR disponibles. No conozco MS-DOS, pero la convención de llamadas predeterminada en Linux en x86 de 32 bits con cadena de herramientas GNU normal ha estado basada en * stack * durante mucho tiempo para argumentos.

Resumen: para llamadas a sistemas, no sería por rendimiento.

Como señaló Paul, esta no es realmente la convención estándar para C. La convención de llamada C estándar (cdecl) en IA32 es usar la pila. Si está utilizando la convención de llamada de llamada rápida (no estándar pero proporcionada por algunos compiladores como atributos de función), puede ser más rápida en algunos casos donde la asignación de registros no es un problema y los valores pueden propagarse en los mismos registros a través de la llamada de función .

Si se refiere a las convenciones de llamada del sistema Linux IA32, entonces es cierto que los GPR se utilizan para al menos un número fijo de argumentos. Sin embargo, por encima de este límite, está utilizando la pila en 32 bits. En AMD64 es un poco más complicado, pero también hay un retroceso en la pila.

Un error común es que esto es para el rendimiento. No sé si el rendimiento fue la motivación inicial, pero no es válida. Incluso en el pasado, la instrucción “int” en IA32 significaría invariablemente accesos a la pila de cualquier manera. Esta fue la ruta inicial elegida para Linux y es posible que se haya adherido a algo parecido a la compatibilidad ABI. La realidad es que esta convención de aprobación de argumentos de llamadas al sistema generalmente hace que la interacción espacio-usuario sea más voluminosa, ya que las aplicaciones tienen que preocuparse por guardar y restaurar el estado del registro hacia y desde la memoria (que puede ser costoso dependiendo de los costos de caché y TLB de la llamada al sistema).