无法在NASM中执行循环

问题描述:

我试图在NASM中编写一个简单的汇编程序,它将打印5次Hello World。但是,在无限循环印刷hello world中执行失败。我试图调试代码,发现ecx没有正确执行,并且eax显示了一些其他值。我的代码如下:无法在NASM中执行循环

section .data 
    msg: db "Hello World",10,0 
    section .text 
     global main 
     extern printf 
    main: push ebp 
     mov ebp,esp 

     mov ecx,0 
     mov DWORD[esp-4],0x5 
     mov eax,DWORD[esp-4] 
     jmp .loop 
    .loop: 
     push eax 
     push ecx 
     add esp,8 

     pop ecx 
     pop eax 

     cmp ecx,eax 
     jne .task 

     jmp .done 
    .task: 
     push DWORD msg 
     call printf 
     add esp,4 

     add ecx,1 

     jmp .loop 
     .done: 
     mov esp,ebp 
     pop ebp 
     ret 

你能帮我通过显示我的缺点。

+0

我不知道太清楚的ASM,但我认为你可以从http://www.csee.umbc.edu/portal/help/nasm/sample启动.shtml和http://blog.markloiseau.com/2012/04/hello-world-nasm-linux/ – user1929959

根据X86 calling conventions,寄存器EAX,ECX和EDX被保存。您在致电printf之前保存它们,然后再恢复。

你的代码中还有一段我不明白的东西(add esp, 8环绕在push/pop中)。我在这里可以不提供任何解释,但如果您不明白或者,则可能是错误的。

安东(上图)是正确的 - 不明原因的add esp,8将垃圾堆栈和混乱的一切(你应该假设printf将垃圾在你依赖的ECX和EAX值)。

这里有一个参考版本:

section .data 
msg: db "Hello World",10,0 
section .text 
    global main 
    extern printf 


main: 
    push dword 0x5  ;count = 5; 

.next: 
    push dword msg 
    call printf 
    add esp,4 

    sub dword [esp],1 ;count--; 
    jne .next   ;if(count != 0) goto next; 

    add esp,4   ;Remove "count" from stack 
    mov eax,0   ;Value to return from "main" 
    ret