gcov和全局析构函数

9

MWE

#include <iostream>

struct Foo {
  Foo() {
    std::cout << "Constructing Foo " << this << std::endl;
  }

  ~Foo() {
    std::cout << "Destructing Foo " << this << std::endl;
  }
};

Foo global_foo;

int main () {
  std::cout << "Entering and exiting main()" << std::endl;
  return 0;

问题

使用选项-fprofile-arcs -ftest-coverage编译上述代码,运行程序,然后运行gcov。程序输出清楚地显示Foo :: Foo(),main()和Foo ::〜Foo()按顺序调用。 gcov输出显示调用了Foo :: Foo()和main(),但没有调用Foo ::〜Foo()。

根本原因

全局对象由GNU内部退出处理程序(使用at_exit()注册的函数)销毁。另一个退出处理程序生成最终的gcov统计信息。显然,在全局销毁退出处理程序之前,gcov退出处理程序被调用,因此gcov看不到析构函数被调用。

错误状态

这是gcov中一个古老的、非常老的bug。以下是Bugzilla链接:http://gcc.gnu.org/bugzilla/show_bug.cgi?id=7970。该错误至少在i686-apple-darwin10-g++-4.2.1中仍然存在九年之后。

问题

这是gcov中一个无法解决的bug,我必须接受它,还是只是一个被忽略了的问题(九年之久,完全被遗忘)?如果是后者,如何解决?


一些赞同,一个反对(没有评论?),但目前还没有答案或评论。是否有任何Stack Overflow成员与gcc开发团队沟通的方式? - David Hammen
1个回答

2
首先,请注意,自2005年以来,该错误报告尚未重新确认;您应该添加一条注释,说明您仍然在g++-4.2.1中看到了错误行为。即使没有人采取行动,将该信息公开也很有用。
短期内,如果您想继续使用gcov,您必须接受它。您可以考虑使用lcov,它可以让您排除指定行的覆盖分析。公平警告:我听说它很好用,但我自己从未使用过。
中期内,将该响应添加到错误跟踪器!虽然不能保证,但也许这会引起足够的兴趣,以便某个善良的人为您编写一个补丁。
长期来看,如果没有人愿意为您修补它,您可能能够自己修补它。gcc不是世界上最友好的代码库,使您的更改被接受可能是一次冒险,但如果您真的需要它,您可以实现它。
祝你好运。

2
感谢回复。我已经在Bugzilla报告中添加了此问题。短期答案显然是“忍受它”。我们的产品是一个C++库,主要用于自动编码模拟环境。由于这是我们的目标,因此我们的许多测试都在该环境中进行。该环境的最新版本创建了全局静态数据。我们还有一个单元测试功能,可以绕过该环境。因此,一个明显的解决方案是要求开发人员开发ctor_dtor单元测试。(我已经这样做了,并且已经听到了抱怨声。) - David Hammen

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接