2011-09-11 33 views
0

如何查看函數execve(在x86_64 Linux下)的實現,它在庫unistd中? 我想要這個,因爲我想知道如何在不調用execve的情況下使用匯編程序調用外部程序。 我知道有一個名爲execve的系統調用,但我不知道如何使用它。執行函數execve(unistd.h)

如何將char *類型的變量和char * []類型的變量放入寄存器中?

回答

1

在用戶空間的execve()功能的實現看起來是這樣的:

int execve(const char *filename, char * const argv[], char * const envp[]) { 
    return syscall(SYS_execve, filename, argv, envp); 
} 

所有實際的「工作」是在內核中完成的。在libc中沒有什麼特別有趣的事情發生,除了可能的一些線程清理。

+0

謝謝大家,但我怎樣才能把類型char *和類型char * []的變量放入寄存器?,我只知道如何使寫和退出系統調用,例如,當我寫一個系統調用時,我必須將指針放入一個寄存器並將緩衝區大小放入另一個寄存器,但我現在怎麼做? – dv1729

+0

與之前沒有什麼不同 - 將指針指向文件名,參數數組和環境數組在三個寄存器中。後兩者應該簡單地指向'char *'數組的開頭,以NULL結尾。 – duskwuff

0

在glibc的源代碼中沒有真正直接的系統調用實現 - 這是在構建時從定義系統調用號的各種文件中生成的。

相關信息可以在sysdep.h發現,如果你瞭解它,除了實際的系統呼叫號碼(您想__NR_execve使用,IIRC,#include <asm/unistd.h> - 我不能隨便記得它是什麼在x86_64)。

系統調用編號進入%rax,參數進入%rdi%rsi%rdx。所有這些信息(包括堆棧對齊和內核註冊使用情況)都在sysdep.h中進行了註釋。

1

只需看看架構上的系統調用約定(更具體地說:arch/YOUR-ARCH/kernel/head * .S)(系統調用編號和參數的寄存器和/或堆棧)。

例如,在ARM上,您可以將__NR_execve加載到r7中,將參數加載到r0,r1,r2中,然後使用swi 0。您可能對this explantion of ARM EABI syscalls感興趣,以瞭解更多詳情。