UVM入门与进阶学习笔记4——UVM仿真的开始与结束
目录
- UVM的编译和运行顺序
- UVM仿真开始
- UVM世界的“诞生”
- UVM仿真结束
UVM的编译和运行顺序
下图是UVM的编译运行顺序,非常重要的知识点!
- 在加载硬件模型调用仿真器之前,要完成编译和建模阶段。
- 在开始仿真之前,分别执行硬件的always/initial语句,以及UVM的调用测试方法run_test和几个phase,分别是
build、connect、end_of_elaboration和start_of_simulation
。 - 在开始仿真后,执行run phase或对应的12个分支phase。
- 在仿真结束后,执行剩余的phase,分别是
extract、check、report和final
。
UVM仿真开始
要在仿真开始时建立验证环境,可考虑选择下面几种方式:
- 可通过全局函数
run_test()
(uvm_pkg
提供)选择性指定运行哪个uvm_test
,这里的test类均继承于uvm_test。指定的test类将被例化并指定为顶层的组件。run_test()
函数可在合适的module/program中的initial进程块中调用。 - 若无任何参数传递给
run_test()
,那么用户可在仿真时通过传递参数+UVM_TESTNAME=<test_name>
指定仿真时调用的uvm_test;即便run_test()
函数在调用时已经有test名称传递,在仿真时+UVM_TESTNAME=<test_name>
也可从顶层覆盖已指定的test。这种方式使仿真不用通过再次修改run_test()调用的test名称和重复编译,就可灵活选定test。 - 无论上面哪种方式都必须在顶层调用全局函数run_test()。
- 全局函数run_test()的重要性,正是从uvm_root创建一个UVM世界。
UVM世界的“诞生”
task run_test (string test_name="");uvm_root top;uvm_coreservice_t cs;cs = uvm_coreservice_t::get();top = cs.get_root();top.run_test(test_name);
endtask
uvm-1.2/base/uvm_globals.svh
- UVM顶层类
uvm_root
继承于uvm_component
,可以作为顶层结构类,也是UVM环境结构的一员,提供一些像run_test()的方法充当UVM世界中的核心角色。 - 在uvm_pkg中有且只有一个顶层类uvm_root所例化的对象,即
uvm_top
。
uvm_top
充当的主要核心任务包括:
- 作为隐形的UVM世界顶层,任何其它的组件都在它之下,通过创建组件时指定parent来构成层次。如果parent设定为null,那么它将作为uvm_top的子组件。
- phase控制:控制所有组件的phase顺序。
- 索引功能:通过层次名称来索引组件实例。
- 报告配置:通过uvm_top来全局配置报告的繁简度(verbosity)。
- 全局报告设备:由于uvm_top全局可以访问,因此UVM的报告配置在组件内部和组件外部(例如module和sequence)都可以访问。
通过uvm_top调用方法run_test(test_name)
,uvm_top做了如下的初始化:(重点)
- 得到正确的test_name;
- 初始化objection机制;
- 创建uvm_test_top实例;
- 调用phase控制方法,安排所有组件的phase方法执行顺序;
- 等待所有phase执行结束,关闭phase控制进程;
- 报告总结和结束仿真。
UVM仿真结束
UVM-1.1之后,结束仿真的机制只有利用objection挂起机制来控制仿真结束——uvm_objection
类提供一种供所有component和sequence共享的计数器,若有组件挂起objection,还应记得落下objection;参与到objection机制的组件,可各自独立挂起objection防止run phase退出,只有这些组件都落下objection后,uvm_objection共享的counter才变为0,即可以退出run phase。
uvm_objection类用来反停止的控制方法包括:
raise_objection(uvm_object obj = null, string description = " " , int count = 1)
挂起objection。drop_objection(uvm_object obj = null, string description = " " , int count = 1)
落下objection。set_drain_time(uvm_object obj = null , time drain)
设置退出时间。
对这些方法在实际应用中的建议:
- 对于component(),用户可在run_phase()中使用。
phase.raise_objection()/phase.drop_objection()
控制run phase退出。 - 用户最好为description字符串参数提供说明,这有利于后期的调试。
- 应使用默认count值。
- 对于
uvm_top或uvm_test_top
应尽可能少地使用set_drain_time()
。
class test1 extends uvm_test;
`uvm_component_utils(test1)
function new(string name, uvm_component parent);super.new(name, parent);
endfunction
task run_phase(uvm_phase phase);phase.raise_objection(this); //在run_phase中进行objection机制的使用`uvm_info("run_phase", "entered ..", UVM_LOW)#1us;`uvm_info("run_phase", "exited ..", UVM_LOW)phase.drop_objection(this);
endtask
endclass
initial beginrun_test("test1");
end
endmodule
输出结果
UVM_INFO @ 0: reporter [RNTST] Running test test1...
UVM_INFO @ 0: uvm_test_top [run_phase] entered ..
UVM_INFO @ 1000000: uvm_test_top [run_phase] exited ..
UVM_INFO @ 1000000: reporter [TEST_DONE] 'run' phase is ready to proceed to the 'extract' phase
UVM_INFO @ 1000000: reporter [UVM/REPORT/CATCHER]
uvm_pkg::uvm_test_done
实例会在test1的run_phase()执行完毕之后,才会退出run_phase,这得益于test1::run_phase()
中在仿真一开始就挂起objection。- 执行完毕才落下objection。这时
uvm_pkg::uvm_test_done
认为run_phase已经可以退出,进而转向extract_phase。 - 直到退出所有phase之后,UVM进入报告总结阶段。
如果没有第一时间挂起objection:
class test1 extends uvm_test;
`uvm_component_utils(test1)
function new(string name, uvm_component parent);super.new(name, parent);
endfunction
task run_phase(uvm_phase phase);#1ps; //NOTICEphase.raise_objection(this);`uvm_info("run_phase", "entered ..", UVM_LOW)#1us;`uvm_info("run_phase", "exited ..", UVM_LOW)phase.drop_objection(this);
endtask
endclass
initial beginrun_test("test1");
end
endmodule
输出结果
UVM_INFO @ 0: reporter [RNTST] Running test test1...
UVM_INFO @ 0: reporter [UVM/REPORT/CATCHER]
- 看起来挂起objection()已经晚了,因为run phase立即退出了。这是因为在挂起objection之前还需运行1ps,而处于fork_join_none后的run_phase任务在0时刻被调用后,run_phase退出机制在0时刻发现没有挂起objection,因此终止所有run_phase()任务,继而转入extract phase。
- 所以,如果要在component中挂起objection,建议在一进入run_phase()后就挂起,保证objection counter及时被增加。
- 另外需要用户习惯在sequence中挂起objection,由于sequence是
uvm_object
类,因此它只有body()方法而没有run_phase()方法。 - 所以在sequence中使用objection机制,可以在body()中的首尾部分挂起和落下objection。
UVM入门与进阶学习笔记4——UVM仿真的开始与结束相关推荐
- UVM入门与进阶学习笔记16——sequencer和sequence(2)
目录 sequence的层次化 Hierarchical Sequence Virtual Sequence Layering Sequence sequence的层次化 就水平复用而言,在MCDF各 ...
- UVM入门与进阶学习笔记17——寄存器模型(2)
目录 寄存器模型集成 总线UVC的实现 总线UVC解析 MCDF寄存器设计代码 Adapter的实现 Adapter的集成 访问方式 前门访问 后门访问 前门与后门的比较 前门与后门的混合应用 寄存器 ...
- UVM实战 卷I学习笔记10——UVM中的寄存器模型(3)
目录 后门访问与前门访问 *UVM中前门访问的实现 后门访问操作的定义 *使用interface进行后门访问操作 UVM中后门访问操作的实现:DPI+VPI *UVM中后门访问操作接口 后门访问与前门 ...
- UVM入门与进阶学习笔11——TLM通信(3)
目录 通信管道 TLM FIFO Analysis Port Analysis TLM FIFO Request & Response通信管道 通信管道 TLM通信的实现方式的共同点在于都是端 ...
- Python数据分析入门--NumPy进阶学习笔记
提示:文章写完后,目录可以自动生成,如何生成可参考右边的帮助文档 文章目录 前言 NumPy 进阶操作 1.NumPy dtype 层次结构 2.NumPy 高阶数组操作 2.1数组的重塑 2.2数组 ...
- UVM实战 卷I学习笔记8——UVM验证平台的运行(2)
目录 *build阶段出现UVM_ERROR停止仿真 *phase的跳转 phase机制的必要性 phase的调试 超时退出 *build阶段出现UVM_ERROR停止仿真 之前的代码中,如果使用co ...
- opencv进阶学习笔记3:像素运算和图像亮度对比度调节
基础版传送门: python3+opencv学习笔记汇总目录(适合基础入门学习) 进阶版目录: python+opencv进阶版学习笔记目录(适合有一定基础) 像素运算 要求两张图大小,以及格式(np ...
- 尚硅谷JavaScript高级教程(javascript实战进阶)学习笔记
前言 这个是我学习过程中的笔记,分享给大家,希望对大家有用. 学习内容是尚硅谷JavaScript高级教程(javascript实战进阶),这里是视频链接. 我在前面有两篇对于web前端HTML和CS ...
- 机器学习入门到进阶学习路线
机器学习入门到进阶学习路线 参考:https://mp.weixin.qq.com/s/f-v-NUW7pTbVF9Sa3A4qUA 1. 定义 机器学习研究的是计算机怎样模拟人类的学习行为,以获取新 ...
最新文章
- kitbash贫民区三维场景模型 Kitbash3d – Favelas
- mysql数据库教程外联_MySQL--外联语句练习
- 勘误《iOS网络高级编程:iPhone和iPad的企业应用开发》
- 【Python】Django生成API 文档
- elasticsearch 索引_Elasticsearch系列---索引管理
- why SAP OData default 100 entries are returned
- 廖雪峰JavaScript学习笔记(基础及数据类型、变量)
- 理解Linux系统中的load average
- Ocelot(三)- 服务发现
- mysqld已删除但仍占用空间的_Windows 10删除备份文件方法
- java 线程百科_Java并发——线程介绍
- 服务器支持http tcp,Nginx配置http和tcp(示例代码)
- GDAL C# “OSGeo.GDAL.GdalPINVOKE”的类型初始值设定项引发异常 解决方法
- oracle 主键自动地址实现
- vue、react隐式实例化
- 统计学三大相关系数之斯皮尔曼(spearman)相关系数
- 常见报错(2)没有为工厂1010订单类型PP01定义参数 消息号 RU010
- 机器学习在金融风控的经验总结!
- java计算机毕业设计微留学学生管理系统源码+数据库+系统+lw文档+mybatis+运行部署
- 帆软报表决策系统忘记密码了,使用重置密码插件