【发布时间】:2015-05-30 12:05:40
【问题描述】:
我试图更好地了解编译器如何为 undefined 表达式生成代码,例如对于以下代码:
int main()
{
int i = 5;
i = i++;
return 0;
}
这是 gcc 4.8.2 生成的汇编代码(优化关闭 -O0,我插入了自己的行号以供参考):
(gdb) disassemble main
Dump of assembler code for function main:
(1) 0x0000000000000000 <+0>: push %rbp
(2) 0x0000000000000001 <+1>: mov %rsp,%rbp
(3) 0x0000000000000004 <+4>: movl $0x5,-0x4(%rbp)
(4) 0x000000000000000b <+11>: mov -0x4(%rbp),%eax
(5) 0x000000000000000e <+14>: lea 0x1(%rax),%edx
(6) 0x0000000000000011 <+17>: mov %edx,-0x4(%rbp)
(7) 0x0000000000000014 <+20>: mov %eax,-0x4(%rbp)
(8) 0x0000000000000017 <+23>: mov $0x0,%eax
(9) 0x000000000000001c <+28>: pop %rbp
(10) 0x000000000000001d <+29>: retq
End of assembler dump.
执行此代码会导致 i 的值保持在 5 的值(使用 printf() 语句验证),即 i 似乎永远不会增加。我知道不同的编译器会以不同的方式评估/编译未定义的表达式,这可能只是 gcc 的方式,即我可以使用不同的编译器得到不同的结果。
关于汇编代码,据我了解:
忽略行 - 1-2 设置堆栈/基指针等。
第 3/4 行 - 5 的值如何分配给 i。
谁能解释第 5-6 行发生了什么?看起来i 最终将被重新分配 5 的值(第 7 行),但增量操作(后增量操作i++ 所需)只是被编译器放弃/跳过在这种情况下?
【问题讨论】:
标签: c assembly undefined x86-64