Verdi查看task内部变量

描述

任务(task)可以用来描述共同的代码段,并在模块内任意位置被调用,让代码更加的直观易读。task 更像一个过程,过程内一般按顺序执行,完成各种逻辑控制。

调试 testbench 中的 task 时,新手可能会遇到一些问题。典型的问题有两个,一个是 task 内部声明使用的变量为什么不能在 Verdi 波形中查看,另一个是 task 输出端连接的信号为什么不随 task 内部赋值变量的变化而变化。本节将对这两个问题进行讲解说明。

Verdi 查看 task 内部变量

创建一个简单的 task,包含内部变量 reg 和 output,如下所示。

//varialbes in task
       task reg_in_task  ;
              output [7:0]       data_test1 ;
              reg [7:0]              data_test2 ;
              begin
                     #100 ;
                     data_test1 = 8'h13 ;
                     data_test2 = 8'h24 ;
                     #100 ;
                     data_test1 = 8'h1a ;
                     data_test2 = 8'h2b ;
              end
       endtask

在 testbench 的 initial 语句中调用该task,并定义变量 data_test1_t,连接到该 task 输出端,如下所示。

`timescale 1ns/1ps
module test ;
   ......
       reg [7:0]       data_test1_t ;
       initial begin
              reg_in_task(data_test1_t) ;
       end
endmodule

使用 simv 进行仿真,不用添加特殊选项,如下所示。

./simv -ucli -i wave_gen.tcl -l sim.log

打开 Verdi 和 fsdb 波形文件,添加 task 内部的变量 data_test1 和输出端 data_test2 时,会提示相关信号无法找到。

代码

为解决上述问题,使用 simv 进行仿真时需要添加特殊选项 +fsdb+functions,如下所示。

./simv +fsdb+functions -ucli -i wave_gen.tcl -l sim.log

此时再在 Verdi 中添加 task 内部的变量 data_test2 和输出端 data_test1,其变化过程会在波形上显示,如下所示。

代码

◆ 小结:VCS 仿真时,需要在 simv 仿真时添加 fsdb+functions 参数,才可在 Verdi 中打开 fsdb 波形并查看 task 内部变量的变化情况。

TASK 操作全局变量

上述仿真波形中,细心的读者可能会看到,虽然连线信号 data_test1_t 连接的是 task 输出端,但是 data_test1_t 并不随 task 输出端的变化而变化。

代码

这是因为 testbench 中的代码一般是顺序执行,并没有对应的实际硬件结构。所以 task 输出端连接的对应信号不可以理解为连续赋值,而是理解为一个返回值。即 task 执行完毕时,只返回输出端连接的信号一个最终结果。所以,data_test1_t 只会在 task 结束时 (对应200ns) 被赋值为 8'h1a,并不会体现中间的变化过程。

如果一个信号在 task 中的变化能够体现在 task 外部,则该信号需要定义为全局变量。即信号需要定义在 task 外部,但是在 task 内部中驱动。

上述示例中,删除输出端 data_test1,并在 task 中直接对全局变量 data_test1_t 进行赋值驱动。

`timescale 1ns/1ps
module test ;


    reg [7:0]       data_test1_t
    //varialbes in task
    task reg_in_task  ;
        reg [7:0]              data_test2 ;
        begin
           #100 ;
           data_test1_t = 8'h13 ;
           data_test2   = 8'h24 ;
           #100 ;
           data_test1_t = 8'h1a ;
           data_test2   = 8'h2b ;
       end
    endtask


    initial begin
       reg_in_task ;
    end
endmodule

仿真结果如下。此时全局变量 data_test1_t 的变化过程并不局限于 task 内部。

代码

testbench 不用“Think In Hardware”,写法比较自由。在多个 task 中对同一个全局变量信号进行多驱动也是没有问题的,只要时间轴上分开驱动事件的先后顺序即可。

上述示例中再增加一个 task ,用以驱动全局信号 data_test1_t,则代码和仿真结果如下。这里不再分析。

task task_mult_drive  ;
        begin
            #150 ;
            data_test1_t = 8'hc8 ;
        end
    endtask


    initial begin
        task_mult_drive ;
    end

代码

小结:task 执行完毕时,只返回输出端连接的信号一个最终结果。如果 task 中信号的变化过程能够在 task 外部实时体现,则该信号也需要定义在 task 外部。

打开APP阅读更多精彩内容
声明:本文内容及配图由入驻作者撰写或者入驻合作网站授权转载。文章观点仅代表作者本人,不代表电子发烧友网立场。文章及其配图仅供工程师学习之用,如有内容侵权或者其他违规问题,请联系本站处理。 举报投诉

全部0条评论

快来发表一下你的评论吧 !

×
20
完善资料,
赚取积分