【问题标题】:disassembling simple code in C on LLVM GCC 4.2在 LLVM GCC 4.2 上反汇编 C 中的简单代码
【发布时间】:2012-01-05 05:22:54
【问题描述】:

当我在 C 中反汇编以下简单程序时:

int main ()
{
 int a = 'a';
return 0;
}

我知道了:

Dump of assembler code for function main:
0x0000000100000f20 <main+0>:    push   rbp
0x0000000100000f21 <main+1>:    mov    rbp,rsp
0x0000000100000f24 <main+4>:    mov    BYTE PTR [rbp-0x9],0x61
0x0000000100000f28 <main+8>:    mov    DWORD PTR [rbp-0x8],0x0
0x0000000100000f2f <main+15>:   mov    eax,DWORD PTR [rbp-0x8]
0x0000000100000f32 <main+18>:   mov    DWORD PTR [rbp-0x4],eax
0x0000000100000f35 <main+21>:   mov    eax,DWORD PTR [rbp-0x4]
0x0000000100000f38 <main+24>:   pop    rbp
0x0000000100000f39 <main+25>:   ret    
End of assembler dump.
  1. 为什么没有设置 rsp (sub rep 0xa)
  2. 为什么会有赋值 0 -> [rbp-0x8] -> eax -> [rbp-0x4] -> eax

【问题讨论】:

    标签: assembly


    【解决方案1】:

    为什么没有设置 rsp (sub rep 0xa)

    由于该函数没有任何调用(这是一个叶函数),因此无需调整堆栈。

    为什么会有赋值 0 -> [rbp-0x8] -> eax -> [rbp-0x4] -> eax

    我怀疑这些来自某种 SSA(静态单一分配)形式的中间表示。在 SSA 形式中,您只能为每个变量分配一次,并且使用大量变量。 SSA 是一个很好的表示,这就是编译器倾向于使用它的原因。提高优化级别后,临时分配将消失。

    【讨论】:

    • +1,但如果提高优化级别,分配可能会完全消失,因为a 的值实际上从未在任何地方使用!
    • @MatthewSlattery:返回值有临时赋值。
    • 编译器为什么要保留 8 个字节,以及为什么他用 0 填充它
    • @badeleux:正如我所说,我认为这些是 SSA 表单使用的临时变量。
    • @ninjalj:好的,是的,我误读了。 (整个事情可能会变成xor eax, eax ; ret。)
    猜你喜欢
    • 1970-01-01
    • 2011-05-20
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2011-12-29
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多