使用验证程序作为RTL项目的快速建模方法。 UVM简介

本文将介绍在Verilog中用于对数字逻辑电路建模的免费软件的安装和使用,以替代Cadense的Incisve和MentorGraphics的ModelSim的商业产品。 比较ModelSim和Verilator中的仿真。 还将考虑使用通用验证方法UVM。

SystemC UVM软件安装


1.验证者


硬件描述语言之一是verilog。 您可以使用这种语言编写模块。

例如,有一个对抗方案:

图片

其代码如下所示:

reg [3:0]counter; always @(posedge clk or posedge reset)   if(reset)    counter <= 4'd0;   else    counter <= counter + 1'd1; 

仿真后,我们得到波形:

图片

可以看出,下一个值,比前一个值大一个,将沿着时钟频率前沿写入计数器寄存器。

书面模块可以具有更复杂的结构,这将很难手动验证其所有状态。 我们将需要自动化测试。 为此,有必要使用一种编程语言来开发测试环境。 测试环境将使我们有机会对设备进行全面的功能检查。

为了测试项目代码,除了使用Verilog,SystemVerilog,Python等语言(用于编写模型)之外,还可以使用SystemC语言。 SystemC是用于系统级模型的系统级设计和验证语言,已实现为开源C ++库。

使用SystemC验证Verilog模块的一种方法是将Verilog文件转换为C ++。 使用此Verilator帮助我们。

Verilator是最快的免费Verilog HDL模拟器,超过了大多数商业模拟器。 Verilator将综合的SystemVerilog(通常不是测试平台代码)以及一些SystemVerilog和Synthesis的语句编译为单线程或多线程C ++或SystemC代码。 Verilator专为仿真性能至关重要的大型项目而设计,特别适合为嵌入式软件开发团队生成可执行处理器模型。 Verilator用于模拟具有数以千计的模块的数百万美元的超大型网关设计,并得到许多IP技术提供商的支持,包括Arm的IP和所有著名的RISC-V IP提供商。

如果您希望功能全面的替代NC-Verilog,VCS或其他商用Verilog模拟器,或者对于很小的项目使用Verilog行为模拟器,则Verilator可能不是最佳选择。 但是,如果您正在寻找将合成Verilog移植到C ++或SystemC的方法,并且您的团队可以自由地仅编写C ++代码,那么这是为您提供的免费Verilog编译器。

要在Ubuntu上安装最新版本,请执行以下操作: 从官方网站的链接下载存档。

安装:

 #sudo apt-get install make autoconf g++ flex bison # Prerequisites unsetenv VERILATOR_ROOT # For csh; ignore error if on bash unset VERILATOR_ROOT # For bash tar xvzf verilator*.t*gz cd verilator* ./configure make sudo make install 

2. GTK浪潮


图片
GTKWave是功能齐全的波形查看器,还允许您将文件从vcd转换为fst格式,更加方便,快捷。

安装:

 sudo apt-get install gtkwave 

3.系统


一种用于设计和验证以开源C ++库形式实现的系统级模型的语言。

如前所述,verilator支持systemc,因此您需要创建一个项目,在该项目中将在systemc上描述测试基准,并在综合verilog上描述源文件。 为此,我们需要Accelera提供的g ++编译器库。 Accellera Systems Initiative是一个独立的非营利组织,致力于创建,支持,促进和推广用于全球电子行业的系统级设计,仿真和验证标准。

下载档案:
http://accellera.org/images/downloads/standards/systemc/systemc-2.3.1a.tar.gz

安装:

 tar -xvf systemc-2.3.1a.tar.gz cd systemc-2.3.1a mkdir objdir sudo ./configure --prefix=/usr/local/systemc-2.3.1a/ sudo make sudo make install cd ../ 

4.适用于SYSTEMC的UVM


本文将回顾一个实现UVM验证工具的项目。 验证是对最终产品是否符合预定义参考要求的确认。 测试是他们的验证工具之一。 为了在RTL描述级别在真实设备的模型上运行测试序列,有必要开发一个测试环境。

UVM- (通用验证方法)是一种通用验证方法,该标准可实现IP块验证环境的有效开发和重用。 UVM是一种验证方法,其任务包括在被测设备周围组织有效的环境。 优点:

  • 明确的结构,以专用块的形式决定具体
  • 任务
  • 在后续项目中重用块的能力;
  • 最大程度地实现自动化验证;
  • 最完整的报告信息,可在发生错误时尽快,准确地确定其原因并提出解决方案。

UVM方法由两部分组成:用于构建测试环境的一组规则和用于验证的块空白库,例如,文本生成器,统计信息收集器等。 UVM的主要优点是它的多功能性和与第三方环境的兼容性。

由于systemc支持UVM方法,因此让我们继续安装必要的库。

下载档案:

https://www.accellera.org/images/downloads/drafts-review/uvm-systemc-1.0-beta2.tar.gz

安装:

 tar -xvf uvm-systemc-1.0-beta2.tar.gz cd uvm-systemc-1.0-beta2/ mkdir objdir sudo ./configure --prefix=/usr/local/systemc_uvm/ --with-systemc=/usr/local/systemc-2.3.1a sudo make sudo make install 

我们建立联盟:

 sudo mkdir /usr/local/uvm_systemc_aliance 

将/ usr / local / uvm_systemc_aliance /和/usr/local/systemc-2.3.1/文件夹的内容复制到此文件夹

通过以下链接下载完成的项目:
https://github.com/paprikun/SYSTEMC/

打开“ verilator examples”文件夹。
rtl文件夹包含设备说明。 在此示例中,它是一个PWM控制器。
在sim文件夹中,用于生成项目的makefile文件。
在tb文件夹中是验证程序的代码。 tb / uvm文件夹包含uvm环境的示例。 主文件是测试的入口点;它将被测设备与uvm环境连接起来。
我们尝试使用make all命令从sim文件夹构建项目。 我们看到一个错误:

 /usr/local/uvm_systemc_aliance//include/systemc.h:120:16: error: 'std::gets' has not been declared using std::gets; 

我们通过替换第120行来解决此问题:

 #if defined(__cplusplus) && (__cplusplus < 201103L) using std::gets; #endif 

再一次,我们尝试运行测试平台并偶然发现警告:

 /usr/local/uvm_systemc_aliance//include/sysc/packages/boost/get_pointer.hpp:21:40: warning: 'template<class> class std::auto_ptr' is deprecated [-Wdeprecated-declarations] template<class T> T * get_pointer(std::auto_ptr<T> const& p) 

将auto_ptr更改为unique_ptr。

项目组装与模拟


现在库已安装并可以使用,我们正在构建项目:全部完成。 simu可执行文件应出现在sim文件夹中。 这是由编译器创建的对象。 我们从./simu团队开始。 应显示以下内容:

 SystemC 2.3.1-Accellera --- Jun 28 2019 11:39:29 Copyright (c) 1996-2014 by all Contributors, ALL RIGHTS RESERVED Universal Verification Methodology for SystemC (UVM-SystemC) Version: 1.0-beta2 Date: 2018-10-24 Copyright (c) 2006 - 2018 by all Contributors See NOTICE file for all Contributors ALL RIGHTS RESERVED Licensed under the Apache License, Version 2.0 UVM_INFO @ 0 s: reporter [RNTST] Running test ... simulation real time = 9 sec UVM_INFO uvm_default_report_server.cpp(666) @ 179490249010 ps: reporter [UVM/REPORT/SERVER] --- UVM Report Summary --- ** Report counts by severity UVM_INFO : 1 UVM_WARNING : 0 UVM_ERROR : 0 UVM_FATAL : 0 ** Report counts by id [RNTST] 1 UVM_INFO @ 179490249010 ps: reporter [FINISH] UVM-SystemC phasing completed; simulation finished 

模拟完成后,波形记录结束。 可以使用gtkwave打开simu.vcd文件:



要在左侧显示信号,请选择SystemC,然后按住Shift选择任何信号,然后单击“追加”。 悬停时,工具栏上会出现工具提示。 鼠标滚动有效,您需要按住shift或cntrl。

还有一些方法可以将该文件转换为另一个较小的文件。

如果有modelsim将进行转换。 在终端中,输入vsim命令。 在终端模型中:

 vcd2wlf simu.vcd simu.wlf 

或在Linux终端中使用gtkwave:
 vcd2lxt simu.vcd simu.lxt vcd2lxt2 simu.vcd simu.lxt2 

为了比较仿真时间,创建了一个类似的项目,但是已经为Modelsim创建了一个项目。 文件夹模型im_example。 类似创建的UVM环境。 尽管存在不同的语言,但语法相似。 如果安装了具有uvm支持的Modelsim,则可以运行make all命令。

除了两个项目中的环境外,还进行了测量的实时仿真。

随着时间的流逝,事实证明:
星期三波形运行命令模拟时间(秒)
模型是的使sim TRACE = 118岁
验证者是的使sim TRACE = 19
模型没有啦使sim TRACE = 010
验证者没有啦使sim TRACE = 04

从表中可以看出,verilator具有优势。 数据是针对具有8GB RAM,8核处理器,800 MHz,加载一个核的PC给出的。

比较文件大小:
simu.vcd807.7兆字节
simu.wlf(在Verilator中创建的转换)41兆字节
simu.wlf(在modelsim中创建)9.3兆字节
仿真器128兆字节
simu.lxt2162兆字节

在这里,验证器会丢失,但是您可以尝试创建波形和走线深度,记录周期(可以更改波形记录的开始和结束)。 使用哪个文件由您决定。

在测试期间,除了模拟本身的时间外,还发现从in总线读取输入数据时存在差异。 如果在clk前端期间来自in总线的数据发生变化,则Modelsim在前端,验证器之前读取数据:

 input clk; input [7:0] in; reg [7:0] in_last_ ; ... always @(posedge clk) begin ... in_last_ <= in; ... end 

图片

在测试过程中,由于针对不同模拟器的部分测试环境将以不同的方式工作,因此需要考虑这一点。

同样,验证器不考虑信号的“ x”状态,而是将所有内容转换为“ 0”;

UVM TESTBENCH


考虑一下测试环境的tb / uvm文件夹。

UVM测试台是设备上方的环境。 在此示例中,该设备是PWM控制器。 UVM环境图:

图片

从图中可以看出,UVM由块(类)组成。 每个块执行其功能。 该示例显示了测试环境的可能布局之一。 每个类的名称和功能都与其继承的类相对应。 让我们更详细地考虑每个类。

环境文件env.h或env.svh。 这是一个可以包含一个或多个代理程序类的类,其中连接了三个类:音序器,驱动程序,监视器。 示例中没有代理,但是其功能在env类中实现。 对于测试,我们需要编写一些动作序列-排序。

让我们继续进行排序的开始代码:

 sequence_[n]->start(sqr, NULL); 

定序器(sequencer)-文件sequncer.h。 在系统Verilog中,原来是使用默认的音序器。 包含一个或多个序列(序列)的类(文件sequence_a.h,sequence_a.svh)。 每个序列都是一连串的动作。 这些动作之一可能是发送交易。 事务处理-将数据从一类传输到另一类。 描述事务的类是bus_trans。 下面是对两个类的描述,每个类在意识形态上都有其自己的特定功能:驱动程序和监视器。

驱动程序-文件drv.h,drv.svh。 一个从定序器接收事务并将其转换为信号的类。 该驱动程序在较低级别充当音序器助手。 考虑发送一个包裹。

Sequence打开一个事务窗口,驱动程序检测到此事件并开始接收数据。 该序列正在等待驱动程序的响应。 驱动程序模拟设备的信号,然后向音序器发送信号,告知该窗口可以关闭。 这个想法是定序器在较高级别上工作,而驱动程序在较低级别上工作。

信号通过接口总线连接到设备。 该接口在文件vip_if.h,vip_if.svh中进行了描述。

接下来,您需要检查输出信号是否与期望的信号匹配。 有两种解决方案:

  • 编写设备模型
  • 通过UVM代理进行信号验证

在该示例中,考虑了第二个选项。 要在功能级别上测试设备,必须将输出与预期进行比较。 该设备的要求是给定信号占空比和信号周期的正确性。 为了监视输出信号,编写了一个新类-Monitor(监视器(文件monitor.h,monitor.svh))。 通常,在测试环境中,监视器将事务中的信号传输到更高级别,然后发送到比较类-记分板。

在此示例中,将立即检查信号。 如果期望值和测量值之间存在差异,则测试将停止。

Source: https://habr.com/ru/post/zh-CN459338/


All Articles