免费注册 查看新帖 |

Chinaunix

  平台 论坛 博客 文库
最近访问板块 发新帖
查看: 1399 | 回复: 0
打印 上一主题 下一主题

用gcov来测试代码覆盖率 [复制链接]

论坛徽章:
0
跳转到指定楼层
1 [收藏(0)] [报告]
发表于 2006-06-13 12:03 |只看该作者 |倒序浏览
关于gcov
gcov是gnu/gcc工具库中的一个组件,一般来说,都会被安装的
可以用whereis gcov来找一下

如果没有安装,可以用google来搜一下,关于gcov的安装的文章

为什么要测试代码覆盖率?
我是不喜欢在代码中有跑不到的地方,那只是在白白浪费空间,降低效率

当然了,有些时候,我们可以通过跑代码覆盖率来发现我们有什么异常情况没有进行测试,毕竟单元测试的用例,不可能一下就想的很全面的

举个例子
你的程序在某个函数的入口前处检测了指针不为空,你进入调用函数以后又检测了一回这个指针,并且对为NULL的情况进行处理,那么两处之中必有一处是在浪费空间,当然你的硬盘大,放的下,但是代码写的精致一些,不是更好么?

gcov怎么用?

很简单,你编译的时候加上-fprofile-arcs -ftest-coverage
链接的时候也加上
举个例子,你的代码由main.c和tmp.c两个组成

然后你可以去跑你的程序了
跑完了?很好,然后 gcov main.c,gcov tmp.c.
这个时候你就会发现,你有了新的文件main.c.gcov,和tmp.c.gcov了,稍等一下,我再说怎么看

噢,你的代码覆盖率会在终端上有显示,你想保存下来你的覆盖率?
很简单,修改一下,gcov main.c >>yourfile,gcov tmp.c >>yourfile
打开你的文件看一下,是不是有了?

那么我的程序是哪一行没跑到呢?
那我们就来看看main.c.gcov(我用的是vi啊,不会emacs,笨吧,我是一大笨人,呵呵)
看看我的例子啊,别骂我写的烂,呵呵
        -:   65:/***************************************************************************************
        -:   66: * name         : main
        -:   67: * return       : 0 OK
        -:   68: *                other ERROR
        -:   69: * history      : 2006-06-13
        -:   70:****************************************************************************************/
        -:   71:int main( int argc, char *argv[] )                                                      /* the entrance for program  */
function main called 4 returned 100% blocks executed 81%
        4:   72:{
        4:   73:        int loop = 0 ;
        4:   74:        int ret = OK ;
        4:   75:        int empty_line = 0 ;
        4:   76:        int code_line = 0 ;
        4:   77:        int annotation_line = 0 ;
        4:   78:        struct stat file_stat ;                                                         /* use for file state  */
        4:   79:        char recu_name[256] ;
        4:   80:        char *pwd = NULL ;
        4:   81:        char *tmp = NULL ;
        -:   82:
        4:   83:        if( argc <= 1 ){                                                                /* no input file  */
        1:   84:                printf( "lease Input file name like this :\n ./SourceCounter xxx\n" ) ;
        1:   85:                goto END_OF_FUNC ;
        -:   86:        }
        3:   87:        pwd = getcwd( tmp, 256 ) ;
第一列的数字,说的是,你这一行代码被使用了多少次,
第二列的,那就是行号了,vi里就是:set nu这个命令看到的结果
function main called 4 returned 100% blocks executed 81%
看到了么,gcov多好,把咱这个函数用了多少回,覆盖率是多少都说了,
main被用了四次,这说明我的程序跑了四回

那没跑到的是什么样子的?
       2:   97:                if( file_stat.st_size >= MAX_FILE ){                                    /* file size larger than max size  */
    #####:   98:                        printf( "file [%s] size is over 64K! \ncontinue....\n", argv[loop] ) ;
    #####:   99:                        continue ;
        -:  100:                }


看看,##### 这就是表示没跑到的


好了
有没跑到的是吧,你就得去再做几个测试用例,争取跑到
测试用例做好了,直接再执行程序就好,又执行完了?
gcov main.c >>yourfile,gcov tmp.c >>yourfile
你要想保存历史记录就这么直接用,我是先删除了再做的,呵呵


等等,你修改程序了?你的代码有重复的地方?
哦,那就很不幸运了,你要重新编译程序,然后重新去跑你的测试用例子了,呵呵,我比较烂,一般都写成一个脚本,然后来测试,每次执行一下脚本就好了

你发现什么?
在你的目录下多了几个文件,后缀是.gcda,gcno,呵呵,恭喜你,你的gcov的版本还是比较新的,在以前旧一点的版本中,有.bb,.bbg这种后缀,不过现在都没了,其实gcov跑的数据统计什么的都保存在这些文件中,这就是为什么,你可以多次跑程序,而gcov会自己统计的神奇本领所在
#gcov -v
gcov (GCC) 3.4.2 20041017 (Red Hat 3.4.2-6.fc3)
Copyright (C) 2004 Free Software Foundation, Inc.
This is free software; see the source for copying conditions.
There is NO warranty; not even for MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE.
这是我的

我们再来看看gcov都有什么参数
这个可不是我懒的翻译啊
我怕我翻译的不到位,耽误大家理解,其实很简单        

       

gcov [-b] [-c] [-v] [-n] [-l] [-f] [-o directory] sourcefile

-b
    Write branch frequencies to the output file, and write branch summary info to the standard output. This option allows you to see how often each branch in your program was taken.
        //b(ranch),分支测试
-c
    Write branch frequencies as the number of branches taken, rather than the percentage of branches taken.

-v
    Display the gcov version number (on the standard error stream).
        //太简单了吧,我上面用了

-n
    Do not create the gcov output file.

-l
    Create long file names for included source files. For example, if the header file `x.h' contains code, and was included in the file `a.c', then running gcov on the file `a.c' will produce an output file called `a.c.x.h.gcov' instead of `x.h.gcov'. This can be useful if `x.h' is included in multiple source files.

-f
    Output summaries for each function in addition to the file level summary.

-o
    The directory where the object files live. Gcov will search for `.bb', `.bbg', and `.da' files in this directory.
        //新版的是这么说的
         -o directory│file
       --object-directory directory
       --object-file file
           Specify either the directory containing the gcov data files, or the
           object path name. The .gcno, and .gcda data files are searched for
           using this option. If a directory is specified, the data files are
           in that directory and named after the source file name, without its
           extension. If a file is specified here, the data files are named
           after that file, without its extension. If this option is not sup-
           plied, it defaults to the current directory.


其他的还有新版的-u,
         -u
       --unconditional-branches
           When branch counts are given, include those of unconditional
           branches.  Unconditional branches are normally not interesting.
      -p
       --preserve-paths
           Preserve complete path information in the names of generated .gcov
           files. Without this option, just the filename component is used.
           With this option, all directories are used, with ’/’ characters
           translated to ’#’ characters, ’.’ directory components removed and
           ’..’  components renamed to ’^’. This is useful if sourcefiles are
           in several different directories. It also affects the -l option.

        man一下就能看到,我也不多说了


OK
等你的程序代码和函数都跑到100%了,你是不是很有一种成就感呢?
那你赶快回去尝试一下gcov吧

PS:
gcov还有valgrid是我在公司工作以后才接触到的,对我的代码编写的触动是很大的
今天偶然google了gcov一把,发现中文说这个的不多,并且中文讲怎么用的也不多,就写了一点使用方法
欢迎大家来给我拍砖

这是我的原创,大家想拿去给人看看,也成(我很虚荣的)
但是您得说,是我(alaiyeshi)写的,我的联系方式是alaiyeshi_peter#163.com
名字没起好,呵呵
您需要登录后才可以回帖 登录 | 注册

本版积分规则 发表回复

  

北京盛拓优讯信息技术有限公司. 版权所有 京ICP备16024965号-6 北京市公安局海淀分局网监中心备案编号:11010802020122 niuxiaotong@pcpop.com 17352615567
未成年举报专区
中国互联网协会会员  联系我们:huangweiwei@itpub.net
感谢所有关心和支持过ChinaUnix的朋友们 转载本站内容请注明原作者名及出处

清除 Cookies - ChinaUnix - Archiver - WAP - TOP