Я изучаю превосходную книгу «Программирование с нуля», желая изучить ассемблер.Хотя в данный момент этого не было в книге, я хотел вызвать свою функцию ассемблера из C. на 32-битном компьютере, но это работает так же, как и при работе с книгой.
Здесь я сохраняю первый аргументв %ebx
и второй в %ecx
.
.type power, @function
.globl power
power:
pushq %ebp
movl %esp, %ebp
subl $4, %esp
movl 8(%ebp), %ebx
movl 12(%ebp), %ecx
Я скомпилирую это (и остальную часть функции) в объектный файл, создаю main.c, где я прототипирую функцию и вызываюэто, что-то вроде этого:
int power(int b, int x);
int a = power(2, 1);
Однако, когда я компилирую это на 64-битной машине, я получаю некоторые очень неожиданные результаты.Я изменил очевидное, например, тот факт, что %esp
и %epb
необходимо заменить на %rsp
и %rpb
, но копание с помощью GDB показывает, что аргументов нигде нет в стеке!
Проверка того, что происходит с помощью опции -S
для GCC. Я вижу, что вместо помещения переменных в стек, GCC сохраняет аргументы в регистрах.
movl $1, %esi
movl $2, %edi
call power
На 32-битной машине,он выполняет то, что я ожидаю, и помещает аргументы в стек:
movl $1, 4(%esp)
movl $2, (%esp)
call power
Что здесь происходит?Почему GCC передает аргументы в регистрах на 64-битных и в стеке на 32-битных?Это очень запутанно!И я нигде не могу найти упоминания об этом.Есть ли кто-нибудь, кто может просветить меня в этой ситуации?