Linux平台代码覆盖率测试-从GCC源码中抽取gcov/gcov-dump程序
Linux平台代码覆盖率测试-从GCC源码中抽取gcov/gcov-dump程序
Content
0. 序
1. gcov
1.1 gcov 必须的文件
(1) 实现文件
(2) 版本文件
(3) 配置文件
(4) 系统文件
1.2 如何编译生成 gcov
2. gcov-dump
3. gcov-tools
4. 小结
Reference
附:本文代码下载地址
0. 序
若想研究 gcov/gcov-dump 原理或者代码,深入函数内部跟踪调试是最好的理解方式,但 gcc 的源代码毕竟比较庞大,欲从中抽丝剥茧,往往会被 gcc 的庞大源代码吓住。那么,有没有一种方式,允许我们从 gcc 的源代码中抽取想要研究的程序或代码?
有!
本文以 gcov 程序为例,说明如何从 GCC 源代码中抽取 gcov/gcov-dump 程序并编译生成可执行的程序。有了这个独立的 gcov/gcov-dump ,研究、调试很方便。想搞清楚 gcc 的内部机理,并非一朝一夕之功,本文只是一种探索,希望对一些想研究 gcc coverage test 的朋友有些帮助。余愿足矣。
本文 gcc 源代码版本为 gcc-4.1.2 ,其位置在 /usr/src/gcc-4.1.2 目录, . 表示 /usr/src/gcc-4.1.2 。
1. gcov
gcov 程序的输入是一个 .c 文件,前提是已经编译生成了 .gcno 文件并运行可执行程序生成 .gcda 文件; gcov 根据 .c 文件相应的 .gcda 文件和 .gcno 文件生成相应的 .c.gcov 并报告覆盖率测试结果。
1.1 gcov 必须的文件
(1) 实现文件
根据 " Linux 平台代码覆盖率测试 -GCC 如何编译生成 gcov/gcov-dump 程序及其 bug 分析 " 一文的讨论, gcov 所需的 .c 文件有 gcov.c, gcov-io.c, intl.c, error.c, version.c 。
注: gcov-io.c 在编译 gcov 时并没有显示被编译 ( 成 .o 文件 ) ,实际上, gcov-io.c 被包含进了 gcov.c 文件中,请参考 gcov.c 代码。
因此,我们需要将这些 .c 文件及其 .h 文件抽取出来。
(2) 版本文件
gcov-iov.h : 该文件的内容由 ./gcc/gcov-iov 程序生成。请参考 " Linux 平台代码覆盖率测试工具 GCOV 相关文件分析 " 一文。内容如下。
- /* Generated automatically by the program `./gcov-iov'
- from `4.1.2 (4 1) and p (p)'. */
- #define GCOV_VERSION ((gcov_unsigned_t)0x34303170) /* 401p */
(3) 配置文件
auto-host.h
config.h
其中,
auto-host.h 文件可以使用 ./gcc/configure 程序自动生成,当然,这里的 auto-host.h 文件只需要包含在 gcov 程序中需要的常量,且有些常量需要修改,内容如下。
- /* auto-host.h. Generated from auto-host.h.in by configure. */
- /* auto-host.h.in. Generated from configure.ac by autoheader. */
- /* Define to 1 if you have the <boost/filesystem/path.hpp> header file. */
- #define HAVE_BOOST_FILESYSTEM_PATH_HPP 1
- /* Define to 1 if you have the <boost/graph/graph_utility.hpp> header file. */
- #define HAVE_BOOST_GRAPH_GRAPH_UTILITY_HPP 1
- /* Define to 1 if you have the <dlfcn.h> header file. */
- #define HAVE_DLFCN_H 1
- /* Define to 1 if you have the <inttypes.h> header file. */
- #define HAVE_INTTYPES_H 1
- /* Define to 1 if you have the <memory.h> header file. */
- #define HAVE_MEMORY_H 1
- /* Define to 1 if you have the <stdint.h> header file. */
- #define HAVE_STDINT_H 1
- /* Define to 1 if you have the <stdlib.h> header file. */
- #define HAVE_STDLIB_H 1
- /* Define to 1 if you have the <strings.h> header file. */
- #define HAVE_STRINGS_H 1
- /* Define to 1 if you have the <string.h> header file. */
- #define HAVE_STRING_H 1
- /* Define to 1 if you have the <sys/stat.h> header file. */
- #define HAVE_SYS_STAT_H 1
- /* Define to 1 if you have the <sys/types.h> header file. */
- #define HAVE_SYS_TYPES_H 1
- /* Define to 1 if you have the <unistd.h> header file. */
- #define HAVE_UNISTD_H 1
- /* Name of package */
- #define PACKAGE "gcov"
- /* Define to the address where bug reports for this package should be sent. */
- #define PACKAGE_BUGREPORT "livelylittlefish@gmail.com"
- /* Define to the full name of this package. */
- #define PACKAGE_NAME "gcov"
- /* Define to the full name and version of this package. */
- #define PACKAGE_STRING "gcov 1.0"
- /* Define to the one symbol short name of this package. */
- #define PACKAGE_TARNAME "gcov"
- /* Define to the version of this package. */
- #define PACKAGE_VERSION "1.0"
- /* Define to 1 if you have the ANSI C header files. */
- #define STDC_HEADERS 1
- /* Version number of package */
- #define VERSION "1.0"
config.h 文件也可以参考 ./gcc/build/config.h( 该文件是在编译 gcc 时自动生成的 ) ,也可自己手写,内容如下。
- #ifndef _GCOV_DUMP_CONFIG_H_
- #define _GCOV_DUMP_CONFIG_H_
- #define ATTRIBUTE_NORETURN
- #define ATTRIBUTE_UNUSED
- #define ATTRIBUTE_PRINTF_1
- #define ATTRIBUTE_PRINTF_2
- /**
- * this macro definition is for the following warning.
- * In file included from gcov.c:62:
- * gcov-io.c: In function ‘gcov_allocate’:
- * gcov-io.c:204: warning: implicit declaration of function ‘xrealloc’
- * gcov-io.c:204: warning: assignment makes pointer from integer without a cast
- */
- #define xrealloc realloc
- #include "auto-host.h"
- #ifdef IN_GCC
- /* # include "ansidecl.h" */
- #endif
- #endif /* _GCOV_DUMP_CONFIG_H_ */
|
评论暂时关闭