避免编译器优化掉代码
发布于 2016-08-11
c++代码编译成Release版本,编译器会做一些优化,生成的二进制可执行文件执行更快,体积更小。这种优化会复用栈上不同变量的空间,导致调试的时候,有些局部变量看不到了。比如如下代码:
int main()
{
int ia = 1;
ia++;
int ib = ia++;
ib++;
int ic = ia - ib;
ic++;
printf("%d", ic);
system("pause");
return 0;
}
在调试的的时候,调试器直接运行到printf(“%d”, ic);这一行,而ia,ib,ic这些局部变量统统被优化了看不到,如下图所示:
如果程序在某个地方崩溃了,而崩溃地方的局部变量恰好被编译器优化掉了,调试的时候看堆栈的变量值几乎没有什么价值。chromium的base库里里面有个解决办法,就是把局部变量传给Alias,Alias函数的实现如下:
#pragma optimize("", off)
void Alias(const void* var) {
}
#pragma optimize("", on)
Alias函数其实不对传进来的局部变量做什么,只是函数内的代码实现禁用了编译器优化,这样调试的时候就可以看到局部变量来,效果如下:
这样就在#pragma optimize("", off)
和#pragma optimize("", off)
之间的c++代码不被编译器优化了。
#pragma optimize
是微软vc++编译器的开关,如果要对clang编译器实现同样的效果,可以使用下面的代码:
#if defined(COMPILER_MSVC)
#pragma optimize("", off)
#elif defined(__clang__)
#pragma clang optimize off
#endif
void Alias(const void* var) {
}
#if defined(COMPILER_MSVC)
#pragma optimize("", on)
#elif defined(__clang__)
#pragma clang optimize on
#endif
参考: