Testbench编写技巧
一、基本架构(常用模板)
`timescale 1ns/1ps //时间精度
`define Clock //时钟周期 module my_design_tb; //==================<端口>==================================================
reg clk ; //时钟,50Mhz
reg rst_n ; //复位,低电平有效
reg [XX:] in ; //
wire [XX:] out ; // //--------------------------------------------------------------------------
//-- 模块例化
//--------------------------------------------------------------------------
my_design u_my_design
(
.clk (clk ),
.rst_n (rst_n ),
.in (in ),
.out (out )
); //----------------------------------------------------------------------
//-- 时钟信号和复位信号
//----------------------------------------------------------------------
initial begin
clk = ;
forever
#(`Clock/) clk = ~clk;
end initial begin
rst_n = ; #(`Clock*+);
rst_n = ;
end //----------------------------------------------------------------------
//-- 设计输入信号
//----------------------------------------------------------------------
initial begin
in = ;
#(`Clock*+); //初始化完成 $stop;
end endmodule
二、时钟激励设计
`timescale 1ns/1ps //时间精度
`define Clock //时钟周期 //==========================================================================
//== 方法一,50%占空比
//==========================================================================
initial begin
clk = ;
forever
#(`Clock/) clk = ~clk;
end //==========================================================================
//== 方法二,50%占空比
//==========================================================================
initial begin
clk = ;
always
#(`Clock/) clk = ~clk;
end //==========================================================================
//== 方法三,产生固定输入的时钟脉冲
//==========================================================================
initial begin
clk = ;
repeat()
#(`Clock/) clk = ~clk;
end //==========================================================================
//== 方法四,非50%占空比
//==========================================================================
initial begin
clk = ;
forever begin
#((`Clock/)-) clk = ;
#((`Clock/)+) clk = ;
end
end
三、复位信号设计
`timescale 1ns/1ps //时间精度
`define Clock //时钟周期 //==========================================================================
//== 方法一,异步复位
//==========================================================================
initial begin
rst_n = ; #(`Clock*+);
rst_n = ;
end //==========================================================================
//== 方法二,同步复位
//==========================================================================
initial begin
rst_n = ; #(`Clock*);
rst_n = ;
end
四、task常用方法
//==========================================================================
//== 输入信号任务封装
//==========================================================================
task i_data;
input [:] dut_data;
begin
@(posedge data_en); send_data=;
@(posedge data_en); send_data=dut_data[];
@(posedge data_en); send_data=dut_data[];
@(posedge data_en); send_data=dut_data[];
@(posedge data_en); send_data=dut_data[];
@(posedge data_en); send_data=dut_data[];
@(posedge data_en); send_data=dut_data[];
@(posedge data_en); send_data=dut_data[];
@(posedge data_en); send_data=dut_data[];
@(posedge data_en); send_data=;
#;
end
endtask //调用方法:i_data(8'hXX); //==========================================================================
//== 多输入信号任务封装
//==========================================================================
task more_input;
input [ :] a;
input [ :] b;
input [:] times;
output [ :] c;
begin
repeat(times) @(posedge clk) //等待 times 个时钟上升沿
c=a+b;
end
endtask //调用方法:more_input(x,y,t,z); //按声明顺序
五、@和wait
//==========================================================================
//== @为边沿触发
//==========================================================================
initial begin
start = ;
repeat() @(posedge clk) //等待5个时钟上升沿
start = ;
end //==========================================================================
//== wait为电平触发
//==========================================================================
initial begin
start = ;
wait(en); //等待en==1
start = ;
end
六、常用仿真控制语句
$random //产生随机数
$random % n //产生范围 {-n,n} 的随机数
{$random} % n //产生范围 { 0,n} 的随机数 $stop //停止运行仿真,Modelsim 中可继续仿真
$finish //结束运行仿真,Modelsim 中不可继续仿真 $stop(n) //带参数系统任务,根据参数 0、1、2 不同,输出仿真信息
$finish(n) //带参数系统任务,根据参数 0、1、2 不同,输出仿真信息
/*------------------------------------------------------------------------*\
0:不输出任何信息
1:输出当前仿真时刻和位置
2:输出当前仿真时刻、位置和仿真过程中用到的 memory 以及 CPU 时间的统计
\*------------------------------------------------------------------------*/
七、仿真终端显示描述
$monitor //仿真打印输出,打印出仿真过程中的变量,使其终端显示
/*------------------------------------------------------------------------*\
$monitor($time,,,"clk=%d reset=%d out=%d",clk,reset,out);
\*------------------------------------------------------------------------*/ $display //终端打印字符串,显示仿真结果等
/*------------------------------------------------------------------------*\
$display(” Simulation start ! ");
$display(” At time %t,input is %b%b%b,output is %b",$time,a,b,en,z);
\*------------------------------------------------------------------------*/ $time //返回 64 位整型时间 $stime //返回 32 位整型时间 $realtime //实行实时模拟时间
八、文本输入
$readmemb/$readmemh("<数据文件名>",<存储器名>);
$readmemb/$readmemh("<数据文件名>",<存储器名>,<起始地址>);
$readmemb/$readmemh("<数据文件名>",<存储器名>,<起始地址>,<结束地址>);
$readmemb
/*------------------------------------------------------------------------*\
读取二进制数据,读取文件内容只能包含:空白位置,注释行,二进制数
数据中不能包含位宽说明和格式说明,每个数字必须是二进制数字。
\*------------------------------------------------------------------------*/
$readmemh
/*------------------------------------------------------------------------*\
读取十六进制数据,读取文件内容只能包含:空白位置,注释行,十六进制数
数据中不能包含位宽说明和格式说明,每个数字必须是十六进制数字.
\*------------------------------------------------------------------------*/
例如:
/*------------------------------------------------------------------------*\
//mem.dat 文件内容
@001
AB CD
@003
A1
\*------------------------------------------------------------------------*/
reg [:] memory[:0] ;//声明 8 个 8 位存储单元
integer i ; initial begin
$readmemh("mem.dat",memory);//读取系统文件到存储器中的给定地址
for(i=;i<;i=i+)
$display("Memory[%d]=%h",i,memory[i]);
end /*------------------------------------------------------------------------*\
//仿真输出为
Memory[0] = xx;
Memory[1] = AB;
Memory[2] = CD;
Memory[3] = A1;
\*------------------------------------------------------------------------*/
九、简单的仿真案例
1.设计文件
module add
//==================<端口>==================================================
(
input wire [ :] a ,
input wire [:] b , // 输入信号b
input wire [:] c , // 输入信号a
input wire [:] d , // 输入信号b
output wire [:] e // 求和输出信号
); //==================<设计>==================================================
assign e = a + b + c + d; endmodule
2.仿真文件
`timescale 1ns/1ps //时间精度 module add_tb; //==================<端口>==================================================
//输入输出---------------------------------------
reg [:] a ;
reg [:] b ;
reg [:] c ;
reg [:] d ;
wire [:] e ;
//中间变量---------------------------------------
reg [:] i ; //--------------------------------------------------------------------------
//-- 模块例化
//--------------------------------------------------------------------------
add u_add
(
.a (a ),
.b (b ),
.c (c ),
.d (d ),
.e (e )
); //----------------------------------------------------------------------
//-- 设计输入信号
//----------------------------------------------------------------------
initial begin
a = ;
b = ;
c = ;
d = ;
for(i=;i<;i=i+) begin
#;
a = i;
b = i;
c = i;
d = i;
end
end initial begin
$monitor($time,,"%d + %d + %d + %d ={%d}",a,b,c,d,e); // 信号打印输出
#;
$stop;
end endmodule
3.Modelsim仿真

参考资料:
[1]米联客FPGA教程
[2]吴厚航. 深入浅出玩转FPGA[M]. 北京航空航天大学出版社, 2013.
Testbench编写技巧的更多相关文章
- 14条最佳JS代码编写技巧
http://gaohaixian.blog.163.com/blog/static/123260105201142645458315/写任何编程代码,不同的开发者都会有不同的见解.但参考一下总是好的 ...
- Flutter实战视频-移动电商-17.首页_楼层组件的编写技巧
17.首页_楼层组件的编写技巧 博客地址: https://jspang.com/post/FlutterShop.html#toc-b50 楼层的效果: 标题 stlessW快速生成: 接收一个St ...
- bug的编写技巧与级别划分
一.bug编写技巧 确.清晰.简洁.完整.一致 二.bug包含的要素 缺陷ID.缺陷标题.测试环境.缺陷发现日期时间.缺陷提交人 缺陷优先级.缺陷严重等级.发现缺陷软件版本.测试类型 缺陷复现步骤.期 ...
- X86逆向15:OD脚本的编写技巧
本章节我们将学习OD脚本的使用与编写技巧,脚本有啥用呢?脚本的用处非常的大,比如我们要对按钮事件进行批量下断点,此时使用自动化脚本将大大减小我们的工作量,再比如有些比较简单的压缩壳需要脱壳,此时我们也 ...
- Hexo之旅(四):文章编写技巧
hexo 编写文章可以使用以下命令创建hexo new "文件名" #创建的文章会在_pots目录下文章的后缀名是以md命名的文件格式,遵循markdown语法,所以编写文章可以使 ...
- CSS编写技巧
1.尽量少的使用全局的重置代码 全局重置代码:*{margin:0; padding:0;}对于熟悉CSS的人来说并不陌生,并且有很多人的第一句CSS代码就是这句.它可以避免不同浏览器的默认间距不同而 ...
- Grunt配置文件编写技巧及示范
受益于grunt这么久,继续分享关于grunt的一些技巧.grunt确实是前端项目中不可或缺的提升效率的工具.第一次接触grunt是在去年7月份,开始有接触LESS.Coffee Script的等需要 ...
- 高效率JavaScript编写技巧
最近在编写一个JavaScript框架,发现有很多细节注意得不够,担心长时间积累会导致框架实际应用的时候出现严重的效率问题.于是开始关注JavaScript提高效率的一些技巧,在这里分享给大家. 1. ...
- 简历编写技巧-java开发工程师简历实战
看到一遍简历编写的文章 想到也快找工作了 早晚能够用上 现在摘录如下 640?wx_fmt=jpeg 工欲善其事,必先利其器,这是自古以来的道理.所以如果想找到一份好的工作,一定要先整理一份好的简历. ...
随机推荐
- Hdu 3037 Saving Beans(Lucus定理+乘法逆元)
Saving Beans Time Limit: 3000 MS Memory Limit: 32768 K Problem Description Although winter is far aw ...
- JavaScript对象及面向对象
1.创建对象(1)自定义对象 语法:var 对象名称=new Object();(2)内置对象 String(字符串)对象. Date(对象)对象 Array(数组)对象 Boll ...
- CSP-S乱搞记
还有一年的时间,没人能挡住我前进的脚步 以后不打算写游记了,补完这篇再写就等退役吧,不太想传播什么负能量,走这条路,希望能得到自己想要的东西 Day-n 上了一个月文化课,班主任突然催我搞竞赛??? ...
- 辨析Java方法参数中的值传递和引用传递
小方法大门道 小瓜瓜作为一个Java初学者,今天跟我说她想通过一个Java方法,将外部变量通过参数传递到方法中去,进行逻辑处理,方法执行完毕之后,再对修改过的变量进行判断处理,代码如下所示. publ ...
- vscode插件开发之如何玩转vscode命令
这里以插件开发为例,VsCode之所以那么强大是因为它背后有千千万万的开发者们为其开发大量功能插件,WordPress同理. 那么如何玩转VsCode命令呢(以插件开发为例)? 官方文档必不可少 ht ...
- golang 文件传输小demo(转载)
转载地址:https://www.cnblogs.com/qq702368956/p/10195497.html 获取文件信息需要用到os. Stat接口,发送文件前开启接收者(服务端),启动客户端先 ...
- JVM探究之 —— OOM异常
在Java虚拟机规范的描述中,除了程序计数器外,虚拟机内存的其他几个运行时区域都有发生OutOfMemoryError(下文称OOM)异常的可能.本节探究主要基于jdk1.8的内存结构. 1. Jav ...
- kubectl -n ingress-nginx exec nginx-ingress-controller-78bd49949c-t22bl -- cat /etc/nginx/nginx.conf
kubectl -n ingress-nginx exec nginx-ingress-controller-78bd49949c-t22bl -- cat /etc/nginx/nginx.conf
- Linux下打开超大文件的方法
Linux下打开超大文件方法 在Linux下用VIM打开大小几个G.甚至几十个G的文件时,是非常慢的. 这时,我们可以利用下面的方法分割文件,然后再打开. 1 查看文件的前多少行 head -1000 ...
- C++ Java throw goto
throw goto - 国内版 Binghttps://cn.bing.com/search?FORM=U227DF&PC=U227&q=throw+goto C++ throw 代 ...