GCC中-O0和-O1之间的差异。

时间:2021-06-06 02:12:14

While compiling some code I noticed big differences in the assembler created between -O0 and -O1. I wanted to run through enabling/disabling optimisations until I found out what was causing a certain change in the assembler.

在编译一些代码时,我注意到在-O0和-O1之间创建的汇编程序有很大的不同。我想通过启用/禁用优化来运行,直到我发现了在汇编程序中引起某种变化的原因。

If I use -fverbose-asm to find out exactly which flags O1 is enabling compared to O0, and then disable them manually, why is the assembler produced still so massively different? Even if I run gcc with O0 and manually add all the flags that fverbose-asm said were enabled with O1, I don't get the same assembler that I would have got just by using O1.

如果我使用-fverbose-asm来找出O1与O0相比较的哪个标志,然后手动禁用它们,为什么汇编程序产生的差异仍然如此巨大?即使我用O0运行gcc,并且手动添加fverbose说的所有标志,但是我没有使用O1来得到相同的汇编器。

Is there anything apart from '-f...' and '-m...' that can be changed?

有什么区别吗?”和“- m…“这可以改变吗?”

Or is is just that 'O1' has some magic compared with 'O0' that cannot be turned off.

或者只是“O1”和“O0”有一定的魔力,不能关闭。


Sorry for the crypticness - this was related to Reducing stack usage during recursion with GCC + ARM however the mention of it was making the question a bit hard to understand.

不好意思,这与在使用GCC + ARM递归时减少栈的使用有关,但是提到它使这个问题有点难以理解。

2 个解决方案

#1


5  

If all you want is to see which passes are enabled at O1 which are not enabled at O0 you could run something like:

如果你想要看到的是在O1中启用了哪些通道在O0中没有启用,你可以运行如下:

gcc -O0 test.c -fdump-tree-all -da
ls > O0
rm -f test.c.*
gcc -O1 test.c -fdump-tree-all -da
ls > O1
diff O0 O1

A similar process, using the set of flags which you discovered, will let you see what extra magic passes not controlled by flags are undertaken by GCC at O1.

一个类似的过程,使用您发现的一组标志,将会让您看到在O1中GCC所执行的额外的魔法传递不受标志控制。

EDIT:

编辑:

A less messy way might be to compare the output of -fdump-passes, which will list which passes are ON or OFF to stderr.

一种不那么混乱的方法可能是比较-fdump-pass的输出,它将会列出哪些通道是在或关闭到stderr。

So something like:

所以类似:

gcc -O0 test.c -fdump-passes |& grep ON > O0
gcc -O1 test.c -fdump-passes |& grep ON > O1
diff O0 O1

#2


3  

Not that this helps, other than providing some evidence for your suspicions about -O1 magic that can't be turned off:

这并不是说这有帮助,只是提供了一些证据来证明你对-O1魔法的怀疑是不能被关掉的:

  • From http://gcc.gnu.org/ml/gcc-help/2007-11/msg00214.html:

    从http://gcc.gnu.org/ml/gcc-help/2007-11/msg00214.html:

    CAVEAT, not all optimizations enabled by -O1 have a command-line toggle flag to disable them.

    注意,并不是-O1启用的所有优化都有一个命令行标记来禁用它们。

  • From Hagen's "Definitive Guide to GCC, 2nd Ed":

    从哈根的《海湾合作委员会的权威指南》,第2版:

    Note: Not all of GCC’s optimizations can be controlled using a flag. GCC performs some optimizations automatically and, short of modifying the source code, you cannot disable these optimizations when you request optimization using -O

    注意:不是所有GCC的优化都可以使用标记来控制。GCC会自动执行一些优化,并且,如果不修改源代码,当您使用-O请求优化时,您不能禁用这些优化。

Unfortunately, I haven't found any clear statement about what these hard-coded optimizations might be. Hopefully someone who is knowlegable about GCC's internals might post an answer with some information about that.

不幸的是,我还没有找到关于这些硬编码的优化可能是什么的清晰的声明。希望能够了解GCC内部信息的人可能会给出一些相关信息的答案。

#1


5  

If all you want is to see which passes are enabled at O1 which are not enabled at O0 you could run something like:

如果你想要看到的是在O1中启用了哪些通道在O0中没有启用,你可以运行如下:

gcc -O0 test.c -fdump-tree-all -da
ls > O0
rm -f test.c.*
gcc -O1 test.c -fdump-tree-all -da
ls > O1
diff O0 O1

A similar process, using the set of flags which you discovered, will let you see what extra magic passes not controlled by flags are undertaken by GCC at O1.

一个类似的过程,使用您发现的一组标志,将会让您看到在O1中GCC所执行的额外的魔法传递不受标志控制。

EDIT:

编辑:

A less messy way might be to compare the output of -fdump-passes, which will list which passes are ON or OFF to stderr.

一种不那么混乱的方法可能是比较-fdump-pass的输出,它将会列出哪些通道是在或关闭到stderr。

So something like:

所以类似:

gcc -O0 test.c -fdump-passes |& grep ON > O0
gcc -O1 test.c -fdump-passes |& grep ON > O1
diff O0 O1

#2


3  

Not that this helps, other than providing some evidence for your suspicions about -O1 magic that can't be turned off:

这并不是说这有帮助,只是提供了一些证据来证明你对-O1魔法的怀疑是不能被关掉的:

  • From http://gcc.gnu.org/ml/gcc-help/2007-11/msg00214.html:

    从http://gcc.gnu.org/ml/gcc-help/2007-11/msg00214.html:

    CAVEAT, not all optimizations enabled by -O1 have a command-line toggle flag to disable them.

    注意,并不是-O1启用的所有优化都有一个命令行标记来禁用它们。

  • From Hagen's "Definitive Guide to GCC, 2nd Ed":

    从哈根的《海湾合作委员会的权威指南》,第2版:

    Note: Not all of GCC’s optimizations can be controlled using a flag. GCC performs some optimizations automatically and, short of modifying the source code, you cannot disable these optimizations when you request optimization using -O

    注意:不是所有GCC的优化都可以使用标记来控制。GCC会自动执行一些优化,并且,如果不修改源代码,当您使用-O请求优化时,您不能禁用这些优化。

Unfortunately, I haven't found any clear statement about what these hard-coded optimizations might be. Hopefully someone who is knowlegable about GCC's internals might post an answer with some information about that.

不幸的是,我还没有找到关于这些硬编码的优化可能是什么的清晰的声明。希望能够了解GCC内部信息的人可能会给出一些相关信息的答案。