gcov的实现原理简介

应用开发 同时被 2 个专栏收录
172 篇文章 0 订阅
68 篇文章 1 订阅

Gcc中指定-ftest-coverage 等覆盖率测试选项后,gcc 会:

  • 在输出目标文件中留出一段存储区保存统计数据
  • 在源代码中每行可执行语句生成的代码之后附加一段更新覆盖率统计结果的代码
  • 在最终可执行文件中进入用户代码 main 函数之前调用 gcov_init 内部函数初始化统计数据区,并将gcov_exit 内部函数注册为 exit handlers
  • 用户代码调用 exit 正常结束时,gcov_exit 函数得到调用,其继续调用 __gcov_flush 函数输出统计数据到 *.gcda 文件中

2 对后台服务程序进行覆盖率测

从 gcc coverage test 实现原理可知,若用户进程并非调用 exit 正常退出,覆盖率统计数据就无法输出,也就无从生成报告了。后台服务程序若非专门设计,一旦启动就很少主动退出,用 kill 杀死进程强制退出时就不会调用 exit,因此没有覆盖率统计结果产生。

为了解决这个问题,我们可以给待测程序增加一个 signal handler,拦截 SIGHUP、SIGINT、SIGQUIT、SIGTERM 等常见强制退出信号,并在 signal handler 中主动调用 exit 或 __gcov_flush 函数输出统计结果即可。如何使用gcov完成对后台驻守程序的测试

该方案仍然需要修改待测程序代码,不过借用动态库预加载技术和 gcc 扩展的 constructor 属性,我们可以将 signalhandler 和其注册过程都封装到一个独立的动态库中,并在预加载动态库时实现信号拦截注册。这样,就可以简单地通过如下命令行来实现异常退出时的统计结果输出了:

1
LD_PRELOAD=./gcov_out.so ./daemon

测试完毕后可直接 kill 掉 daemon 进程,并获得正常的统计结果文件 *.gcda。gcov_out.so是你自己写的一个程序,接受SIG,然后exit,以触发gcov进行输出。

  • 0
    点赞
  • 2
    评论
  • 1
    收藏
  • 一键三连
    一键三连
  • 扫一扫,分享海报

相关推荐
©️2020 CSDN 皮肤主题: 数字20 设计师:CSDN官方博客 返回首页
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、C币套餐、付费专栏及课程。

余额充值