有多少GCC优化级别?
有多少优化级别 我试过gcc-O1、gcc-O2、gcc-O3和gcc-O4 如果我使用一个非常大的数字,它将不起作用 然而,我已经试过了有多少GCC优化级别?,c,optimization,gcc,compiler-construction,C,Optimization,Gcc,Compiler Construction,有多少优化级别 我试过gcc-O1、gcc-O2、gcc-O3和gcc-O4 如果我使用一个非常大的数字,它将不起作用 然而,我已经试过了 gcc -O100 它被编译了 有多少优化级别?四(0-3):参见GCC 4.4.2。任何更高的值都只是-O3,但在某一点上,您将超出可变大小限制。为了学究式的理解,您可以为gcc提供8种不同的有效-O选项,尽管有些选项的含义相同 该答案的原始版本说明有7个选项。此后,GCC增加了-Og,使总数达到8 从 -O(与-O1相同) -O0(不进行优化,如果未
gcc -O100
它被编译了
有多少优化级别?四(0-3):参见GCC 4.4.2。任何更高的值都只是-O3,但在某一点上,您将超出可变大小限制。为了学究式的理解,您可以为gcc提供8种不同的有效-O选项,尽管有些选项的含义相同 该答案的原始版本说明有7个选项。此后,GCC增加了
-Og
,使总数达到8
从
(与-O
相同)-O1
(不进行优化,如果未指定优化级别,则为默认值)-O0
(最低限度地优化)-O1
(优化更多)-O2
(进一步优化)-O3
(非常积极地进行优化,达到违反标准的程度)-Ofast
(优化调试体验。-Og启用不会干扰调试的优化。它应该是 标准编辑编译调试周期的优化级别选择,提供合理的优化级别 同时保持快速编译和良好的调试体验。)-Og
(针对大小进行优化。-Os
启用通常不会增加代码大小的所有-Os
优化。它还执行进一步的优化 旨在减少代码大小。-O2
禁用以下优化标志:-Os
)-falign函数-falign跳跃-falign循环-falign标签-freorder块-freorder块和分区-fprefetch循环数组-ftree向量循环版本
(默认):无优化-O0
或-O
(同样的事情):优化,但不要花费太多时间-O1
:更积极地优化-O2
:最积极地优化-O3
:相当于-Ofast
<代码>-ffast math触发不符合标准的浮点优化。这允许编译器假装浮点数是无限精确的,并且浮点数上的代数遵循实数代数的标准规则。它还告诉编译器告诉硬件将非规范化刷新为零,并将非规范化视为零,至少在某些处理器上是这样,包括x86和x86-64。非规范化会在许多FPU上触发一条慢路径,因此将其视为零(这不会触发慢路径)可能是一个巨大的性能胜利-O3-ffast数学
:优化代码大小。由于更好的I-cache行为,在某些情况下,这实际上可以提高速度-Os
:优化,但不要干扰调试。这使调试版本的性能不会令人尴尬,并用于替换调试版本的-Og
-O0
有关更多信息,请参阅GCC网站。让我们来解释GCC 5.1的源代码。 我们将尝试了解
-O100
上发生了什么,因为手册页上不清楚
我们将得出结论:
- 任何高于
到-O3
的内容都与INT_MAX
相同,但这在将来很容易改变,因此不要依赖它-O3
- 如果输入的整数大于
,GCC 5.1将运行未定义的行为INT\u MAX
- 参数只能有数字,否则将正常失败。特别是,这排除了像
-O-1
cpp
、as
、cc1
、collect2
的前端。一个快速的/XXX--help
说明只有收集2
和cc1
才能获取-O
,所以让我们重点关注它们
以及:
给出:
COLLECT_GCC_OPTIONS='-O100' '-v' '-mtune=generic' '-march=x86-64'
/usr/local/libexec/gcc/x86_64-unknown-linux-gnu/5.1.0/cc1 [[noise]] hello_world.c -O100 -o /tmp/ccetECB5.
因此-O
被转发到cc1
和collect2
O共同点。选择
是中描述的特定于GCC的CLI选项描述格式,并由和转换为C
它包含以下有趣的行:
O
Common JoinedOrMissing Optimization
-O<number> Set optimization level to <number>
Os
Common Optimization
Optimize for space rather than speed
Ofast
Common Optimization
Optimize for speed disregarding exact standards compliance
Og
Common Optimization
Optimize for debugging experience rather than speed or size
作为奖励,当我们在\bO\n
中搜索common.opt
时,我们注意到以下几行:
-optimize
Common Alias(O)
Variable
int optimize
这告诉我们,--optimize
(双破折号,因为它在.opt
文件上以破折号-optimize
开头)是-O
的未记录别名,可以用作--optimize=3
使用OPT_O的位置
现在我们grep:
git grep -E '\bOPT_O\b'
这就指向了两个文件:
opts.c
选项c:默认选项\u优化
所有opts.c
用法都发生在内部:默认选项\u优化
我们grep backtrack查看是谁调用此函数,我们看到唯一的代码路径是:
main.c:main
toplev.c:toplev::main
opts global.c:decode\u opts
opts.c:默认选项优化
main.c
是cc1
的入口点。好!
此功能的第一部分:
- 调用
integral\u参数
git grep -E '\bOPT_O\b'
struct gcc_options { int x_optimize; [...] }
Variable int optimize
struct gcc_options global_options;
if ((unsigned int) opts->x_optimize > 255) opts->x_optimize = 255;
# All of the optimization switches gathered together so they can be saved and restored. # This will allow attribute((cold)) to turn on space optimization.
struct GTY(()) cl_optimization { unsigned char x_optimize;
switch (default_opt->levels) { [...] case OPT_LEVELS_1_PLUS: enabled = (level >= 1); break; [...] case OPT_LEVELS_3_PLUS: enabled = (level >= 3); break;
enum opt_levels { OPT_LEVELS_NONE, /* No levels (mark end of array). */ OPT_LEVELS_ALL, /* All levels (used by targets to disable options enabled in target-independent code). */ OPT_LEVELS_0_ONLY, /* -O0 only. */ OPT_LEVELS_1_PLUS, /* -O1 and above, including -Os and -Og. */ OPT_LEVELS_1_PLUS_SPEED_ONLY, /* -O1 and above, but not -Os or -Og. */ OPT_LEVELS_1_PLUS_NOT_DEBUG, /* -O1 and above, but not -Og. */ OPT_LEVELS_2_PLUS, /* -O2 and above, including -Os. */ OPT_LEVELS_2_PLUS_SPEED_ONLY, /* -O2 and above, but not -Os or -Og. */ OPT_LEVELS_3_PLUS, /* -O3 and above. */ OPT_LEVELS_3_PLUS_AND_SIZE, /* -O3 and above and -Os. */ OPT_LEVELS_SIZE, /* -Os only. */ OPT_LEVELS_FAST /* -Ofast only. */ };
static const struct default_options default_options_table[] = { /* -O1 optimizations. */ { OPT_LEVELS_1_PLUS, OPT_fdefer_pop, NULL, 1 }, [...] /* -O3 optimizations. */ { OPT_LEVELS_3_PLUS, OPT_ftree_loop_distribute_patterns, NULL, 1 }, [...] }
/* Wrapper to call lto. Used by collect2 and the linker plugin.