编译优化,会使编译器尝试以牺牲编译时间和调试程序的能力为代价,来提高性能或代码大小;
合理的优化级别,能够在代码体积、执行性能、RAM占有率上获得均衡!
https://gcc.gnu.org/onlinedocs/gcc/Optimize-Options.html
1、优化级别说明
GCC优化级别有-O0、-O1、-O2、-O3、-Og、-Os、-Ofast
总结如下:
优化级别 | 说明 | 备注 |
---|---|---|
-O0 | 关闭所有优化 | 代码空间大,执行效率低 |
-O1 | 基本优化等级 | 编译器在不花费太多编译时间基础上,试图生成更快、更小的代码 |
-O2 | O1的升级版,推荐的优化级别 | 编译器试图提高代码性能,而不会增大体积和占用太多编译时间 |
-O3 | 最危险的优化等级 | 会延长代码编译时间,生成更大体积、更耗内存的二进制文件,大大增加编译失败的几率和不可预知的程序行为,得不偿失 |
-Og | O1基础上,去掉了那些影响调试的优化 | 如果最终是为了调试程序,可以使用这个参数。不过光有这个参数也是不行的,这个参数只是告诉编译器,编译后的代码不要影响调试,但调试信息的生成还是靠 -g 参数的 |
-Os | O2基础上,进一步优化代码尺寸 | 去掉了那些会导致最终可执行程序增大的优化,如果想要更小的可执行程序,可选择这个参数。 |
-Ofast | 优化到破坏标准合规性的点(等效于-O3 -ffast-math ) | 是在 -O3 的基础上,添加了一些非常规优化,这些优化是通过打破一些国际标准(比如一些数学函数的实现标准)来实现的,所以一般不推荐使用该参数。 |
举例:
2、MDK优化等级修改
-
全局设置优化等级
-
局部设置优化级别
通常情况下,随着代码结构复杂,第三方组件的加入,全局的优化等级已经不能满足实际的使用场景;
MDK可以单独对单个文件,或者单组文件进行单独设定优化级别。
- 代码中设置优化级别
在代码中,针对某个函数进行优化级别单独设置
https://www.keil.com/support/man/docs/armcc/armcc_chr1359124988971.htm
AC5中设置方法:
#pragma push
#pragma O1
void function(void){
... // Optimized at O0
}
#pragma pop
AC6中设置方法:
void function(void) _attribute__((optnone))
{
... // Optimized none
}