禁用优化后,gdb stl函数仍显示为内联

时间:2016-10-21 09:31:07

标签: c++ stl gdb

我已经使用python支持构建了gdb-7.12并启用了漂亮的打印并按照https://sourceware.org/gdb/wiki/STLSupport配置了我的gdbinit文件。

但每当我打印任何容器的大小时:

p ivec.size()
Cannot evaluate function -- may be inlined

这是我正在使用的MCVE

#include <vector>

using namespace std;

int main(){
  vector<int> ivec;
  return 0;
}

我尝试了不同的编译选项

g++-6 -g -O0 -fno-inline-functions -gdwarf-2 Source.cpp --std=c++14

事实上,我已尝试过上述各种选项的组合,并始终存在同样的问题。

我尝试切换到gdb-7.11(也是从源代码构建)来查看它是否修复了问题并且还切换到g ++ - 4.8,它们似乎都无法解决问题。

我做错了什么?是否有一些特定的顺序,您必须提供选项?

修改 很多人建议使用一些宏来解决这个问题,但我的问题是不能以某种方式打印这些函数,我可以为此编写自己的漂亮打印方法。

我的问题是,即使在使用 -O0 选项禁用优化后,为什么功能会显示为内联?

2 个答案:

答案 0 :(得分:3)

  

我的问题是,即使在使用-O0选项禁用优化后,为什么函数会显示为内联?

g ++只会实例化程序实际使用的模板,而您的程序实际上并没有使用size方法。

您可以使用nm

进行检查
$ nm -C q|grep size
$

如果我将程序更改为使用return ivec.size(),那么我可以:

(gdb) p ivec.size()
$1 = 0

内联和非实例化的整个情况是编写gdb xmethod支持的原因。并且,libstdc ++有一些xmethods(虽然我没有检查它是否特别有这个)。我推荐使用它。

答案 1 :(得分:0)

GDB错误消息Cannot evaluate function -- may be inlined有点误导,因为内联不是功能不可用的唯一原因。

在您的示例中,std::vector<T>::size()简单没有在编译时实例化(插入std::vector<int>::size()),因为它没有被使用。

当您键入size()p ivec.size()时,是否可以解决缺少的call ivec.size()实例化(例如Fedora 27上的GDB 8.0.1),这取决于您的GDB漂亮打印支持的版本。能够)。但是,即使使用旧版本的STL漂亮打印支持,您也可以通过仅打印矢量本身来解决此问题,即:

(gdb) p ivec
$1 = std::vector of length 0, capacity 0

但是,您可以通过在程序中的某个位置使用size()或通过在一个翻译单元中显式实例化int的完整模板类来明确确保实例化template class std::vector<int>;

most_common