通过x86程序集从argv读取文件名

时间:2011-10-21 20:07:06

标签: x86 nasm argv

我正在尝试读取传递给我的可执行文件的文件名并使用程序集写入该文件。它编译时没有错误但在执行时失败。我的代码究竟出了什么问题?

BITS 32
segment .data
text db "text"

segment .text

global main

main:
pop ebx 
pop ebx
pop ebx    ; pop pointer to filename into ebx
mov eax,0x5  ;syscall open
mov ecx,0x2   ;flag read/write
int 0x80   ;call kernel
mov ebx,eax   ;save returned file descriptor
mov eax,0x4 ; write syscall
mov ecx,text ;mov pointer to text into ecx
mov edx,0x4 ;string length
int 0x80  ;exit syscall
mov eax,0x1
int 0x80

2 个答案:

答案 0 :(得分:5)

由于你是从libc调用的,你还必须记得你有回复地址,所以你可以回到那里。这与你得到的东西不同,如果你只有一个简单的汇编程序(就像很多教程!)。考虑到这一点:

pop ebx    ;; pops return address to libc caller (_start usually)
pop ebx    ;; pops argc
pop ebx    ;; pops argv !!WAS!!: ; pop pointer to filename into ebx

以下是打印第一个参数的方法。你应该能够从那里开始(注意:我可能犯了错误):

    BITS 32

    section .text
    global main
    extern strlen

main:
    pop ecx ; Return address
    pop ecx ; argc
    pop ecx ; argv 
    mov ecx, [ecx+4] ; argv[1]

    push ecx
    call strlen
    mov edx, eax ; count
    pop ecx ; buf

    mov eax, 4 ; sys_write
    mov ebx, 1 ; stdout
    int 0x80

    mov eax, 1 ; sys_exit
    mov ebx, 0 ; status
    int 0x80

答案 1 :(得分:2)

在进入main时:堆栈具有以下内容:

...
*envp[]
*argv[]
argc
return address

当您pop ebx三次时,您最终会访问argv而不是 argv[1]

argv是一个指向以NULL结尾的char *数组的指针,所以你必须遵循间接,就像@ user786653所示。