printf是否需要x86-64上额外的堆栈空间?

时间:2012-04-25 21:49:47

标签: assembly x86 printf x86-64

虽然我知道最好使用编译器内在函数,就此而言printf_chk,以及将数据放入.rodata部分,我正在寻求深入理解汇编语言我对紧凑的代码感兴趣。有一些关于printf我不明白的事情。我知道在哪里放置参数,我知道如何使用%al进行varargs,但它似乎需要额外的堆栈空间,我无法解释。

这个简短的程序

        .text
        .globl  main
main:
        movsd   value(%rip), %xmm0    # value to print
        movl    $format, %edi         # format string
        movl    $1, %eax              # one floating-point arg
        call    printf
        movl    $0, %eax              # return 0 from main
        ret
        .align 8
value:  .double 74.321 
format: .asciz "%g\n"

给出了段错误。

但是,当我向框架添加额外的堆栈空间时,它可以正常工作:

        .text
        .globl  main
main:
        subq    $8, %rsp              # ADD SOME STACK SPACE TO FRAME (WHY?)
        movsd   value(%rip), %xmm0    # value to print
        movl    $format, %edi         # format string
        movl    $1, %eax              # one floating-point arg
        call    printf
        movl    $0, %eax              # return 0 from main
        addq    $8, %rsp              # REMOVE ADDED STACK SPACE
        ret
        .align 8
value:  .double 74.321 
format: .asciz "%g\n"

这可能是对齐问题吗? (当valueformat部分位于.rodata部分时,我遇到同样的问题。)

1 个答案:

答案 0 :(得分:4)

根据www.x86-64.org/documentation/abi.pdf以及Microsoft的http://msdn.microsoft.com/en-us/library/ms235286(v=vs.80).aspx

,堆栈必须是16字节对齐的。