究竟如何做的gcc的优化? [英] How exactly does gcc do optimizations?
问题描述
为了了解GCC究竟做了优化,我已经写了两个程序与-O2编译,但组装code,还有一些分歧。在我的计划,我想在环路输出你好,并添加每个输出之间有一些延迟。这两个方案仅用于说明我的问题,我知道我可以用易挥发或汇编程序1达到我的目的。
In order to know how exactly the gcc do the optimization, I have written two program compiling with -O2, but there is some difference of the assembly code. In my programs, I want to output "hello" in the loop, and add some delay between each output. These two programs are only for illustrating my question, and I know I can using volatile or asm in program 1 to achieve my purpose.
程序1
#include <stdio.h>
int main(int argc, char **argv)
{
unsigned long i = 0;
while (1) {
if (++i > 0x1fffffffUL) {
printf("hello\n");
i = 0;
}
}
}
与-O2编译,装配code是:
Compile with -O2, the assembly code is:
Disassembly of section .text.startup:
00000000 <_main>:
#include <stdio.h>
int main(int argc, char **argv)
{
0: 55 push %ebp
1: 89 e5 mov %esp,%ebp
3: 83 e4 f0 and $0xfffffff0,%esp
6: 83 ec 10 sub $0x10,%esp
9: e8 00 00 00 00 call e <_main+0xe>
e: 66 90 xchg %ax,%ax
10: c7 04 24 00 00 00 00 movl $0x0,(%esp)
17: e8 00 00 00 00 call 1c <_main+0x1c>
1c: eb f2 jmp 10 <_main+0x10>
1e: 90 nop
1f: 90 nop
程序2
int main(int argc, char **argv)
{
unsigned long i = 0;
while (1) {
if (i > 0x1fffffffUL) {
printf("hello\n");
i = 0;
}
i++;
}
}
与-O2编译,装配code是:
Compile with -O2, the assembly code is:
Disassembly of section .text.startup:
00000000 <_main>:
#include <stdio.h>
int main(int argc, char **argv)
{
0: 55 push %ebp
1: 89 e5 mov %esp,%ebp
3: 83 e4 f0 and $0xfffffff0,%esp
6: 83 ec 10 sub $0x10,%esp
9: e8 00 00 00 00 call e <_main+0xe>
e: 31 c0 xor %eax,%eax
10: 83 c0 01 add $0x1,%eax
13: 3d ff ff ff 1f cmp $0x1fffffff,%eax
18: 76 f6 jbe 10 <_main+0x10>
1a: c7 04 24 00 00 00 00 movl $0x0,(%esp)
while (1) {
if (i > 0x1fffffffUL) {
printf("hello\n");
i = 0;
}
i++;
21: e8 00 00 00 00 call 26 <_main+0x26>
int main(int argc, char **argv)
{
unsigned long i = 0;
while (1) {
if (i > 0x1fffffffUL) {
26: 31 c0 xor %eax,%eax
28: eb e6 jmp 10 <_main+0x10>
printf("hello\n");
2a: 90 nop
2b: 90 nop
2c: 90 nop
2d: 90 nop
2e: 90 nop
2f: 90 nop
在方案1,的提高I
进行了优化,但是它不是在节目2.为什么出现这种情况?什么样的规则与-O2优化这两种方案在使用是gcc?
In program 1, the increase of i
is optimized out, but it's not in program 2. Why this happens? What rules is gcc using when optimizing with -O2 for these two programs?
推荐答案
问为什么关于优化通常是浪费时间,因为那里的是的没有规则,其中优化经营 - 除好像:优化器可能不会改变符合code的观察行为
Asking "why" about optimizers is usually a waste of time, because there are no "rules" by which optimizers operate -- other than "as if": The optimizer may not change the observable behaviour of conforming code.
你的两种方案的看得见的行为是打印你好反反复复。
The "observable behaviour" of both your programs is to print "hello" repeatedly.
在你的第一个程序,计数被优化掉,使得观察到的行为发生得更快。的这是一个优化的工作。的竭诚为您code现在更有效率!
In your first program, the counting is optimized away, making the observable behaviour happen faster. That is the job of an optimizer. Be happy your code is more efficient now!
在你的第二个方案,点票的不的优化掉,因为不知何故优化 - 在这个版本这个编译< STRONG>这个设置 - 没有看到,它可能离不开它。为什么?谁知道(比编译器的优化器模块的维护等)?
In your second program, the counting is not optimized away, because somehow the optimizer -- in this version of this compiler with this setting -- did not see that it could do without it. Why? Who knows (other than the maintainer of the compiler's optimizer module)?
如果您的所需的的行为是有输出之间的延迟,使用类似的 thrd_sleep()。空循环计数分别推迟对C64 BASIC 2.0程序的方式,但他们不应该在C中使用,确切的原因,你只需观察:你永远不知道优化做什么
If your desired behaviour is to have a delay between outputs, use something like thrd_sleep(). Empty count loops were a way to delay BASIC 2.0 programs on the C64, but they should not be used in C, for the exact reason you just observed: You never know what the optimizer does.
这篇关于究竟如何做的gcc的优化?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!