汇编程序中的函数

时间:2010-03-10 18:42:25

标签: assembly function callstack

我对堆栈的目的进行了哲学思考,经过一些编码后,我发现它的强度是多少。我的胃口唯一的东西是它如何与功能一起使用?我尝试使用通用寄存器来添加两个数字,但是我想它不是如何在C中工作的例子..所有参数,局部变量以及存储结果的位置在哪里?

你会如何将它重写为汇编程序?(C编译器如何重写它?)

int function(int a, int &b, int *c){
 return a*(b++)+(*c);
}

我知道这个例子有点糟透..但这样我就能理解所有的可能性

3 个答案:

答案 0 :(得分:5)

您正在寻找的是有关calling conventions的信息。调用和返回函数的方式取决于许多因素,包括处理器体系结构,编译器和操作系统。调用者和被调用者必须就约定达成一致,以便正确传递参数和返回值。

答案 1 :(得分:5)

首先,引用(int&)不在C中,只是C ++。

如果你想通过gcc了解幕后发生的事情,请使用-S标志。你不需要有实际的程序。

g++ -S func.c

创建一个文件func.s,其中包含(减去x86框上的标题等):

    .text
.globl __Z8functioniRiPi
__Z8functioniRiPi:
LFB2:
    pushq   %rbp
LCFI0:
    movq    %rsp, %rbp
LCFI1:
    movl    %edi, -4(%rbp)
    movq    %rsi, -16(%rbp)
    movq    %rdx, -24(%rbp)
    movq    -16(%rbp), %rax
    movl    (%rax), %edx
    movl    %edx, %ecx
    imull   -4(%rbp), %ecx
    movq    -24(%rbp), %rax
    movl    (%rax), %eax
    addl    %eax, %ecx
    incl    %edx
    movq    -16(%rbp), %rax
    movl    %edx, (%rax)
    movl    %ecx, %eax
    leave
    ret

请注意C ++名称修改(__Z8functioniRiPi)。现在我们给g ++ -O2标志:

    .text
    .align 4,0x90
.globl __Z8functioniRiPi
__Z8functioniRiPi:
LFB2:
    pushq   %rbp
LCFI0:
    movq    %rsp, %rbp
LCFI1:
    movl    (%rsi), %ecx
    movl    %ecx, %eax
    imull   %edi, %eax
    addl    (%rdx), %eax
    incl    %ecx
    movl    %ecx, (%rsi)
    leave
    ret

-O3提供相同的代码;没有什么可以优化的。

玩装配玩得开心。 ^ _ ^

答案 2 :(得分:3)

Aaron关于召集会议的说法是正确的答案。对于我自己对该主题的个人探索,我发现Smashing the Stack For Fun and Profit是一个很好的练习堆栈框架的角色,以及当它被破坏时会发生什么。 Finlay我推荐使用assembly primer for hackers来解决重要的汇编程序概念以及使用调试器可以做的有趣事情。