本简要介绍Icarus Verilog和GTKwave的使用,使用iverilog(Icarus Verilog)编译仿真verilog而使用GTKWave查看仿真数据波形
最近看一本书中有提到GTKwave这个软件,所以就去了解下,发现都是讲iverilog+GTKWave的使用,索性就再解了一下iverilog。这两个软件都是开源软件,而且两个软件安装包总共不足10MB,而且基本的verilog仿真都支持,普通FPGA设计的仿真完全够用。
由于其他文章都只是很简单的介绍了hello world的一个简单的例子,没有对使用各FPGA公司库的使用做介绍,所以才有本文的产生。本文从安装开始介绍;然后基本使用,最终给出包含Xilinx或Lattice IP的verilog设计的仿真方法;最后给出一些注意事项和使用技巧
本文测试文件在windows10和windows7上测试通过,其它平台请参考官方文档
由于Icarus Verilog中已经包含了GTKWave所以直接从http://bleyer.org/icarus/下载安装,这里提供的为Windows版,我下载的为当前时间最新版:iverilog-10.1.1-x64_setup.exe,整个安装包才9.77MB,安装后也只有不到50MB。经测试,其实安装后只要把安装所在目录打包复制到其它电脑也可以用,即下载的这个安装类似一个自解压文件,但会增加两个路径到PATH。所以将安装目录打包复制到其它电脑后只要将以下两个目录(iverilog和gtkwave可执行文件所在目录)加入系统PATH环境变量中即可(这里假设放入其它电脑的目录为E:\iverilog):
E:\iverilog\bin
E:\iverilog\gtkwave\bin
或者在运行批处理文件前加入如下代码即可(即使用前将这两个路径临时加入PATH):
set iverilog_path=d:\iverilog\bin;
set gtkwave_path=d:\iverilog\gtkwave\bin;
set path=%iverilog_path%%gtkwave_path%%path%
下面给出可能会用到的网址:
这里给出一个简单的hello world例程,先对使用方法有一个大概的了解
仿真当然首先要提供verilog源代码,这里简单的实现了一个打印”hello world!”的例子,由于涉及到GTKWave的使用所以加入了clk和rst_n两个信号,以便介绍GTKWave的使用
/*****
** 文件名称:hello_world_tb.v
** 创 建 人:hsp
** 创建日期:2017-03-05
** 功能描述:一个iverilog和GTKWave使用方式介绍的hello world例子
*****/
// synopsys translate_off
`timescale 1 ns / 1 ps
// synopsys translate_on
module hello_world_tb;
parameter PERI = 10;
reg clk;
reg rst_n;
always #(PERI/2) clk = ~clk;
initial
begin
$dumpfile("hello_world_tb.vcd");
$dumpvars(0,hello_world_tb);
$display("hello world!");
clk = 0;
rst_n = 0;
repeat(10) @(posedge clk);
rst_n = 1;
repeat(100) @(posedge clk);
$finish;
end
endmodule
以上verilog:
PERI
,用于指定clk
输出周期reg
:clk
和rst_n
always
给出了时钟信号clk
的输出initial
$dumpfile
指定要保存仿真波形数据需要存储到的文件,指定保存在当前目录中hello_world_tb.vcd
文件中(GTKWave还支持LXT,LXT2,VZT,FST和GHW等类型文件)$dumpvars
指定要保存仿真波形数据的信号,这里指定为hello_world_tb
模块(即本模块)之下及其子模块中的所有信号,当然这个例子中没有子模块,所以仿真数据被存储的为本模块中仅有的两个信号:clk
和rst_n
$display
打印hello world!
clk
和rst_n
的赋值操作$finish
而不是$stop
,因为若使用$stop
在iverilog仿真完后需要手动停止,而用$finish
则会自动停止注意:以上代码最好保存为名称为hello_world_tb.v
的文件,即模块名和文件名(不包括后缀)相同
之后就是仿真命令的问题,可使用以下批处理使用iverilog执行仿真并最后使用GTKWave打开仿真波形(将以下代码保存为xxx.bat或.cmd后缀的文件并放入以上verilog相同目录即可)
@echo off
rem 若没有设置路径到PATH则关闭以下注释
rem set iverilog_path=d:\iverilog\bin;
rem set gtkwave_path=d:\iverilog\gtkwave\bin;
rem set path=%iverilog_path%%gtkwave_path%%path%
set testbentch_module=hello_world_tb
set testbentch_file="./%testbentch_module%.v"
iverilog -o "%testbentch_module%.vvp" %testbentch_file%
vvp "%testbentch_module%.vvp"
set gtkw_file="%testbentch_module%.gtkw"
if exist %gtkw_file% (gtkwave %gtkw_file%) else (gtkwave "%testbentch_module%.vcd")
以上批处理:
testbentch_module
设置为前面verilog模块名相同testbentch_file
设置为verilog文件名,即模块名+.viverilog
编译verilog -o
指定输出文件名,这里使用模块名+.vvpvvp
开始仿真,参数为上面iverilog
的输出文件通过上面批处理最后一条中gtkwave
命令即可打开GTKWave软件,同时打开了对应的.gtkw或.vcd文件;首次运行打开的为.vcd文件,此时可以看到GTKWave软件界面的Signals和Waves窗口并没有信号显示,需要:
G
可以将信号分组,推荐将不同模块的信号分为不同的组,这样方便查看注:查看.gtkw文件可以发现其保存的内容不包括波形数据而只包括.vcd文件路径和GTKWave的一些设置(如添加的信号和分组等)
直接运行iverilog -help
或iverilog
则会显示以下帮助信息,显示了iverilog支持的参数
Usage: iverilog [-ESvV] [-B base] [-c cmdfile|-f cmdfile]
[-g1995|-g2001|-g2005|-g2005-sv|-g2009|-g2012] [-g<feature>]
[-D macro[=defn]] [-I includedir]
[-M [mode=]depfile] [-m module]
[-N file] [-o filename] [-p flag=value]
[-s topmodule] [-t target] [-T min|typ|max]
[-W class] [-y dir] [-Y suf] source_file(s)
下面简单列举几个常用的参数的简单说明,详细参数列表请查看http://iverilog.wikia.com/wiki/Iverilog_Flags
指定使用verilog的版本,推荐使用最新的-g2012
基本的SystemVerilog语法都支持(不完全支持),方便使用SV仿真。如上帮助信息显示支持:
还支持:
指定编译后输出文件,若不指定默认为a.out
指定库的目录,编译时发现了一个没有定义的模块时会到这个参数指定的目录中查找,此选项在使用Xilinx和Lattice库时会用到
指定verilog中`include
包含文件的搜索目录,会按-I
出现顺序查找
传递一个宏定义,如-DIS_DEF
同-DIS_DEF=1
,则在verilog中就可以用IS_DEF这个宏定义
使用-tvhdl
可将verilog转换为VHDL,如将上面的例子转换为VHDL:iverilog -tvhdl -o hello_world_tb.vhd hello_world_tb.v
若要仿真使用了各FPGA公司IP的设计则需要支持对应公司的库,这里简单介绍使用Xilinx和Lattice公司库的方法
本人安装的为vivado 2015.3,安装在E盘:E:\Xilinx\Vivado\2015.3
;则在使用iverilog编译时使用以下命令即可(替换上面例子中iverilog命令那行):
set vivado_dir=E:\Xilinx\Vivado\2015.3\data\verilog\src
set vivado_lib="-y%vivado_dir%" "-y%vivado_dir%\retarget" "-y%vivado_dir%\unifast" "-y%vivado_dir%\unimacro" "-y%vivado_dir%\unisims" "-y%vivado_dir%\xeclib"
iverilog -g2012 -o "%testbentch_module%.vvp" %vivado_lib% %rtl_file% %testbentch_file% %vivado_dir%/glbl.v
以上命令:
-y
选项列出仿真库各子目录: %vivado_dir%/glbl.v
,否则IP编译出错注意:以上iverilog中还增加了一个%rtl_file%
,为要仿真RTL文件,类似%testbentch_file%
的变量需要在之前设置
Lattice的库仿真,编译较简单只要指定使用到的芯片的库即可(不同于Xilinx,Lattice各芯片的仿真库不同),只是在仿真测试文件中(如上面例子中的hello_world_tb.v文件)模块中需要例化两个模块:
// lattice库使用testbentch模块中要加
GSR GSR_INST(.GSR(1'b1));
PUR PUR_INST(.PUR(1'b1));
本机安装Diamond3.5,安装目录在E盘
则在使用iverilog编译时使用以下命令即可(替换上面例子中iverilog命令那行)
set lattice_dir=E:\lscc\diamond\3.5_x64\cae_library\simulation\verilog
set ecp3_lib="-y%lattice_dir%\ecp3" "-y%lattice_dir%\pmi"
iverilog -g2012 -o "%testbentch_module%.vvp" %ecp3_lib% %rtl_file% %testbentch_file%
以上命令:
-y
选项列出ECP3芯片仿真库子目录: 则在使用iverilog编译时使用以下命令即可(替换上面例子中iverilog命令那行)
set lattice_dir=E:\lscc\diamond\3.5_x64\cae_library\simulation\verilog
set machxo2_lib="-y%lattice_dir%\machxo2" "-y%lattice_dir%\pmi"
iverilog -g2012 -o "%testbentch_module%.vvp" %machxo2_lib% %rtl_file% %testbentch_file%
以上命令:
-y
选项列出MachOX2芯片仿真库子目录: 这里列出我在使用中遇到的一些问题或建议
-y
方式指定目录时查找模块时iverilog要求模块名和文件名要相同,否则可能导致无法找到对应模块(这个要求也是平时写verilog应该有的好习惯)$finish
而不用$stop
;因为$finish
可以直接结束仿真并退出,而不需要手动退出,这样运行类似以上例子批处理后可以直接打开GTKWave窗口iverilog
命令中通过-y
指定目录时,需要放在源文件参数之前,否则提示有错iverilog
命令中通过-D
传递宏包含引号的方法:-DIN_FILE="\"xxx.v\""
,这在verilog有`include IN_FILE
时需要使用;而iverilog命令中使用-DIN_FILE="xxx.v"
方式有错误*
,如本人用的批处理中通常使用这种方式指定RTL文件:set rtl_file="../rtl/*.v"
$display
的打印,有时iverilog编译打印的信息较多时会导致部分信息无法查看,所以需要加大DOS窗口的高度:在DOS窗口标题栏右键->默认值->布局中设置屏幕缓冲区中高度为较大的值(如1000)即可-g2012
也不支持break、static等(测试得到)