GDB调试显示< optimized_out >
最近使用GDB调试的时候,经常遇到GDB查看变量值的时候输出< optimized_out >
,Google了一下,找到几个解决方法,来应对不通情况下需要查看具体变量输出的场景。
解决方案
将GCC优化选项调整为O1
或是O0
GCC在O2
、O3
优化选项下会将代码优化的比较多,调试器有可能会找不到变量的信息。通常可以将优化级别降低到O0
,完全关闭优化,可以保留所有的变量和代码信息。使用O1
优化有可能也可以看得到变量的值。
当然,这种直接降低优化级别的方法还是比较暴力的。如果你的程序比较大,运行到你需要调试的地方需要很久的情况下,通常都是行不通的,毕竟所有优化选项都关掉了,程序跑的会非常慢……
输出打印信息
直接将变量的信息打印到屏幕上是最直接的方法。当然了,这种方法太糙,太繁琐了。一旦你需要看的变量比较多,输出的内容也会非常多,看起来就比较痛苦了。
用volatile
修饰需要显示的变量
在需要显示值的变量前面加上volatile
修饰符也是一种比较管用的方法。这种方法不需要修改编译器的优化级别,对于比较庞大的程序来说是比较合适的。如果这种方法也不管用或是也不适用的话,请往下看。
volatile
修饰符请看这里:https://stackoverflow.com/questions/4437527/why-do-we-use-volatile-keyword-in-c
GCC下关闭某函数的优化选项
在GCC中,我们可以指定将某个函数的优化选项关闭,比如说你可以将some_function
的优化级别设定为O0
。
void some_function() __attribute__ ((optimize(0))) {
...
}
这个方法在GCC 4.4版本以上有效
GCC下关闭一段函数的优化
在GCC中我们也可以将某一段代码(不一定是某个函数)的优化等级关掉。比如说。
void foo() {
func1();
#pragma GCC push_options
#pragma GCC optimize (0)
func2();
// do something
...
#pragma GCC pop_options
func3();
}
#pragma GCC push_options
可以将当前的GCC选项暂存。#pragma GCC optimize (0)
可以调整当前GCC的优化选项。0
就代表O0
优化。也支持字符串:#pragma GCC optimize ("O1")
#pragma GCC pop_options
将之前暂存的GCC编译选项还原出来。
GCC 4.4及以上版本有效
Ref
- https://stackoverflow.com/questions/9123676/how-do-i-view-the-value-of-an-optimized-out-variable-in-c/9133439
- https://stackoverflow.com/questions/5580140/is-there-a-way-to-tell-gcc-not-to-optimise-a-particular-piece-of-code
- https://stackoverflow.com/questions/31373885/how-to-change-optimization-level-of-one-function