Bootstrap

VCS 代码覆盖率和功能覆盖率使用分析

目录

1.序言

2.覆盖率相关命令

  2.1 Compile options for coverage

  2.2 Simulation options for coverage

  2.3 Analysis options for coverage

3.功能覆盖率介绍

  3.1 Covergroup

  3.2 Coverpoint

  3.3 Coverpoint 关键字

  3.4 交叉覆盖率

  3.5 覆盖率选项

option使用

type_option使用

  3.6 功能覆盖率相关系统函数


1.序言

        代码覆盖率和功能覆盖率是保证验证完备性的重要指标之一,下文将对这两种覆盖率的收集方法以及常规操作进行介绍。

2.覆盖率相关命令

  2.1 Compile options for coverage

        -cm line+cond+fsm+tgl+branch+assert:行/条件/状态机/翻转/分支/断言覆盖率收集

        -cm_dir directory_path_name:指定生成覆盖率相关编译信息的存储位置

        -cm_hier cov_scope.txt:指定覆盖率收集的范围, cov_scope.txt文件示例如下:

//cov_scopes.txt
//+tree instance_name [level_number]
//level_number:0表示统计所有,1表示只统计当前层,2表示统计当前层和下一层,之后依次类推;默认为0

+tree dut_top.inst_top 0 //收集inst_top以及其层级以下模块的覆盖率
-tree dut_top.inst_top.inst_ctrl    //exclude掉inst_ctrl以及其层级以下模块的覆盖率
+module module_name    //只收集该模块的覆盖率,该模块层级以下的不收集
-module module_name    //exclude掉该模块的覆盖率,该模块层级以下的继续收集
+filelist file_name    //收集该filename以及该模块以下的覆盖率,采用绝对路径
-filelist file_name    //exclude掉该filename以及该模块以下的覆盖率,采用绝对路径
+node top.cnt_inst*.out[7:5]  //对该信号的[7:5]比特,统计toggle覆盖率
-node top.cnt_inst*.out[4:0]  //对该信号[4:0]比特,不统计toggle覆盖率

  2.2 Simulation options for coverage

        -cm line+cond+fsm+tgl+branch+assert:行/条件/状态机/翻转/分支/断言覆盖率收集

        -cm_dir directory_path_name:指定生成覆盖率信息的存储位置

                Note:如果该命令指定的位置与编译命令中的不同,在查看覆盖率报告中需要将所

                           有的覆盖率位置加上,示例:

vcs -cm_dir ./cov_dbs/covdb -cm line
simv -cm_dir ./coverage/test1db -cm line
simv -cm_dir ./coverage/test2db -cm line

urg -dir ./cov_dbs/covdb -dir ./coverage/testdb \
-dir ./coverage/test2db

        -cm_name tc_name_seed:指定生成覆盖率文件的名字

  2.3 Analysis options for coverage

    合并覆盖率:

两种合并方式:1)通过-dbname命令,将所有vdb文件夹合并为一个merge.vdb        

                         2)通过-report命令,将所有vdb文件下的覆盖率信息生成html/txt的报告

//-cm_dir编译和仿真指定的位置不同,每个case都会对应一个tc_name_seed.vdb
vcs ** -cm line+cond+fsm+tgl+branch+assert -cm_dir cov_path/comp -cm_hier cov_scope.txt
simv ** -cm line+cond+fsm+tgl+branch+assert -cm_dir cov_path/$(tc_name)_$(seed)
urg -full64
    -dir cov_path/comp.vdb \
    -dir cov_path/tc_name1_seed1.vdb \
    -dir cov_path/tc_name2_seed1.vdb \
    ...
    -dir cov_path/tc_nameN_seed1.vdb \
    //-f cov_path/xxx_vdb.f      如果vdb文件过多,可以通过filelist的形式合并
    -dbname simv_merge.vdb      //在当前路径下会生成一个simv_merge.vdb文件夹
    -report ./cov_report        //在当前路径下生成一个合并后的html/txt格式的覆盖率报告    

   
//-cm_dir编译和仿真指定的位置相同,编译和仿真的vdb都会在一个文件夹下
//所有case覆盖率信息都会都会放在simv.vdb文件夹下
vcs **  -cm_dir cov_path/simv 
simv ** -cm_dir cov_path/simv
urg -full64 -dir cov_path/simv.vdb \
    -dbname simv_merge.vdb            //在当前路径下会生成一个simv_merge.vdb文件夹
    -report ./cov_report        //在当前路径下生成一个合并后的html/txt格式的覆盖率报告 

      查看覆盖率:

//DVE:
dve -full64 -covdir xx_path/simv.vdb

//verdi:
verdi -cov -covdir xx_path/simv.vdb

//使用urg将vdb文件转成html文件,使用浏览器打开html文件
firefox cov_report/dashboard.html

3.功能覆盖率介绍

  3.1 Covergroup

        covergoup可以在program、module以及class里定义,它包含有coverpoint、option、输入参数以及触发条件等。一个覆盖组里的coverpoint在同一时间进行采样。主要有定义、实例化和采样三个步骤。covergroup的使用示例如下:

class test_cov;
    covergroup covport;  //定义
        option.per_instance=1;
        A: coverpoint tr.port;
    endgroup
 ...
    function new();
        covport = new();  //实例化
    endfuntion;
    task main;
        forever begin
            tr = mbx.get;
            covport.sample(); //采样
        end
    endtask
endclass

  3.2 Coverpoint

        coverpoint需要指定采样的信号或者表达式,其包含的仓(bins)可由用户显示定义,也可自动创建。同时coverpoint还可设置采样的条件。coverpoint示例如下:

logic  [3:0]    kind;
logic  [1:0]    options;
logic  [2:0]    head;
logic  [3:0]    payload;
int             para;

typedef enum {INIT, SEND, RECEIVE, FINISHED} fsm_state_e;
fsm_state_e pfsm_state;

covergroup covkind_options;
    A:coverpoint kind {
            bins  zero={0};     //一个仓代表kind=0
            bins  lo={[1:3],5}; //一个仓代表kind=1、2、3、5
            bins  hi[]={[8:$]}; //八个仓代表kind=8~15,$代表边界值
            bins  trans=(0=>1),(0=>3);  //翻转覆盖率,翻转几次,就要对应采样几次
            bins  misc=default; //一个仓代表kind剩下的值,即4
    }
    B:coverpoint options;        //自动生成4个仓
endgroup

covergroup covlen; //coverpoint为表达式
  len16:coverpoint (head+payload); //采用式中变量的最大位宽,4bit,即产生16个仓,为[0:15]
  len32:coverpoint (head+payload+5’d0);//采用式中变量的最大位宽,5bit,即产生32个仓,为[0:31]
  len:coverpoint (head+payload+5’d0) {
        bins range[]={[0:23]}    //24个仓,实现表达式结果范围全覆盖
endgroup

covergroup covoptions @(posdge dta_vld);//使用时间触发采样,dta_vld上升沿的时候采样options的值
    A:coverpoint options;
endgroup

covergroup covfsb ;//对枚举类型创建仓
    A:coverpoint pfsm_state;
endgroup

covergroup cov_para (ref int value, input int low, int high );//带参数的covergroup
    A:coverpoint value{
        bins good = { [low : high] };
        bins bad[] = default;
    }
endgroup
...
function new();
    cov_para para1 = new(para, 0, 50 ); // cover variable para in the range 0 to 50
endfunction

  3.3 Coverpoint 关键字

//条件覆盖,iff
covergroup covport;
    coverpoint cov iff(rst_n);  //只有在rst_n为1的时候进行采样
endgroup

//with关键字
A:coverpoint value{
    bins mod3[] = {[0:255]} with (item % 3 == 0);  //选择0~255中能被3整除的数建仓
  }

//wildcard关键字
A:coverpoint value{
    wildcard bins gg = { 4'b110? }; //?为通配符,该仓有1100、1101两个值
  }

//ignore_bins、illegal_bins关键字
covergroup covvalue;
    coverpoint value{
        ignore_bins ignore_vals = {7,8};      //不统计value=7、8
        ignore_bins ignore_trans = (1=>3=>5); //不统计value=1>3>5的翻转
        illegal_bins bad_vals = {0};         //非法值value=0
    }
endgroup

  3.4 交叉覆盖率

bit [3:0] a, b, c;
covergroup cov;
    A:coverpoint a;  //自动产生16个仓
    B:coverpoint b;
    C:coverpoint c{
        bins low={[0:3]};
        bins mid={[4:10]};
        bins high={[11:15]};
    }
        
    aXb: cross a, b;  //产生16*16个仓
    aXc: cross a, c{
        bins ac1 = binsof(a) intersect {[0:9]};  // 10*3个值
        bins ac2 = !binsof(c.low);               // 2*16个值
        bins ac3 = binsof(a.2) || binsof(c.mid); // 3*16个值
        bins ac4 = binsof(a.3) && binsof(c.high); // 一个值
        }
    bxc: coverpoint {b,c} {   //使用串联值代替交叉
            ignore_bins b2clow = binsof(b.1) && binsof(c.low);
        }
endgroup

  3.5 覆盖率选项

        覆盖率选项有两种类型,1)option,只影响covergoup内的覆盖率;

                                                2)type_option,影响整体的覆盖率;

  option使用

        option的选项以及作用如下表所示:

 除了per_instance只能在covergroup定义中设置,其他实例特定的选项可以在covergroup实例化之后设置。另外一些选项还可以在coverpoint中定义,见下表:

 option的使用示例如下:

bit [3:0] a, b, c;
covergroup covabc;
    option.per_instance = 1;
    A:coverpoint a;  //自动产生16个仓
    B:coverpoint b{
        option.auto_bin_max = 8;
      }
    C:coverpoint c{
        bins low={[0:3]};
        bins mid={[4:10]};
        bins high={[11:15]};
    }
endgroup

function new();
    covabc = new();
    covabc.option.comment = "coverage for abc";

endfunction
type_option使用

type_option的选项以及作用如下表所示:

和coverpoint共享的一些type_option选项如下表:

type_option可以在仿真任何时候进行定义,使用示例如下:

bit [3:0] a, b, c;
covergroup covabc;
    option.per_instance = 1;
    type_option.strobe = 1;
    A:coverpoint a;  //自动产生16个仓
    B:coverpoint b{
        type_option.weight = 3;
      }
    C:coverpoint c{
        bins low={[0:3]};
        bins mid={[4:10]};
        bins high={[11:15]};
        type_option.weight = 4;
    }
endgroup

function new();
    covabc::type_option.comment = "coverage for covabc";
    covabc = new();

endfunction

  3.6 功能覆盖率相关系统函数

;