x86-64 ELF начальная компоновка стека при вызове glibc - PullRequest
1 голос
/ 30 апреля 2011

По сути, я прочитал части http://www.nasm.us/links/unix64abi и на странице 29 он показывает начальный стек процессов программы на Си.

Мой вопрос: я пытаюсь взаимодействовать с glibc из x86-64 nasm и исходя из того, что показано выше, argc должен быть на rsp. Поэтому следующий код должен напечатать argc:

[SECTION .data]
PrintStr: db "You just entered %d arguments.", 10, 0

[SECTION .bss]

[SECTION .text]
extern printf
global main

main:
     mov rax, 0        ; Required for functions taking in variable no. of args
     mov rdi, PrintStr
     mov rsi, [rsp]
     call printf
     ret

Но это не так. Может ли кто-нибудь просветить меня, если я допустил какие-либо ошибки в своем коде, или скажите, какова структура стека?

Спасибо!

ОБНОВЛЕНИЕ : Я просто случайно попробовал некоторые смещения и изменил «mov rsi, [rsp]» на «mov rsi, [rsp + 28]», добился цели.

Но это означает, что показанная структура стека неверна. Кто-нибудь знает, что такое начальная компоновка стека для эльфа x86-64? Эквивалент http://asm.sourceforge.net/articles/startup.html был бы действительно хорош.

ОБНОВЛЕНИЕ 2: Я пропустил, как я строю этот код. Я делаю это по:

nasm -f elf64 -g <filename>
gcc <filename>.o -o <outputfile>

1 Ответ

1 голос
/ 30 апреля 2011

Исходный макет стека содержит argc в указателе стека, за которым следует массив char *argv[], а не указатель на него, как main. Поэтому для вызова main нужно сделать что-то вроде:

pop %rdi
mov %rsp,%rsi
call main

В действительности обычно существует функция-обертка, которая вызывает main, а не код запуска, делающий это напрямую.

Если вы хотите просто напечатать argv[0], вы можете сделать что-то вроде:

pop %rdi
pop %rdi
call puts
xor %edi,%edi
jmp exit
...