数字IC验证23831--config机制

博客介绍了UVM config机制,它可在仿真时灵活控制验证环境。包括interface传递,解决软硬件连接问题;变量设置,可在build_phase配置底层组件变量;object传递,整合组件变量便于维护。还给出使用set()/get()方法的建议,如参数类型一致、确保先get后使用等。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

config机制

  • 在验证环境的创建过程build phase中,除了组件的实例化,配置也是必不可少的。
  • 为了验证环境的复用性,通过外部的参数配置,使得环境在创建时可以根据不同参数来选择创建的组件类型、组件实例数目、组件之间的连接以及组件的运行模式等。
  • 在更细致的环境调节(environment tuning)中有更多的变量需要配置,例如for-loop的阈值、字符串名称、随机变量的生成比重等。
  • 比起重新编译来调节变量,如果在仿真中可以通过变量设置来修改环境,那么就更灵活了,而UVM config机制正提供了这样的便捷。
  • 在UVM提供了avm_config_db配类以及几种方便的变量设置方法来实现仿真时的环境控制,常见的uvm_contig_db的使用方式包括:
    ·传递virtual interface到环境中。
    ·设置单一变量值,例如int、string、enum等。
    ·传递配置对象(config object)到环境。
  • uvm_config_db#(T)::set(uvm_uvm_component cntxt,string insstring_field name, value) ;
  • uvm_config_db# (T)::get(uvm_component cntxt, string inst_name,string field_ name , inout value) ;

interface传递

  • interface传递可以很好地解决了连接硬件世界和软件世界。
  • 而在之前SV验证模块中,虽然SV可以通过层次化的set_interface的索引来完成了传递,但是这种方式不利于软件环境的封装和复用。
  • UVM的uvm_config_db使得接口的传递和获取彻底分离开来。
  • 在实现接口传递的过程中需要注意:
    ·接口传递应该发生在run_test()之前,这保证了进入build phase之前virtual interface已经被传递到uvm_config_db中。
    ·用户应当把interface与virtual interface的声明区分开来,在传递过程中的类型应当为virtual interface,即实际接口的句柄。
interface intf1;
	logic enable = 0 ;
endinterface
class comp1 extends uvm_component;`
	uvm component_utils (comp1)
	virtual intf1 vif;
	function void build phase (uvm phase phase) ;
		if ( !uvm_config_db# (virtual intf1) ::get(this, "", "vif", vif)) begin //实现路径:root->test->c1->vif
			'uvm_error ( "GETVIF", "no virtual interface is assigned")
		end
		'uvm_info ("SETVAL",$sformatf("vif.enable is $b before set", vif.enable),UVM_LOW)
		vif.enable = 1;
		'uvm_info("SETVAL",$sformatf ("vif.enable is 8b after set",vif.enable),UVM_LOW)
	endfunction
endclass
  • 底层的get要和顶层的set配对,这地方顶层set相当于建立一个查找表,左边是path,右边是value。
    在这里插入图片描述
    下面是顶层的set
class test1 extends uvm_test;
	`uvm component _utils ( test1)
	comp c1;
endclass
intf1 intf();
initial begin
	uvm _config_db# (virtual intf1) : :set(uvm _root::get(),"uvm_test_top.c1","vif",intf);
	run_test( "test1"); //实现层次结构root->test->c1->vif
end

  • UVM世界中,顶层类uvm_root属于uvm_component的子类,作为顶层结构类。
  • uvm_config_db# (virtual intf1) ::get(this, “”, “vif”, vif)) 这行代码在comp1类的定义中,在test类中定义句柄,当run_test(“test”)执行时,会进入各个层次的build阶段,这行代码会在root ->uvm_test_top->c1->vif
  • uvm _config_db# (virtual intf1) : :set(uvm _root::get(),“uvm_test_top.c1”,“vif”,intf);在执行这行代码时,会将接口路径保存在root->uvm_test_top->c1->vif与上述的get相对应,实现接口传递。

变量设置

  • 在各个test中,可以在build_phase对底层组件的变量加以配置,进而在环境例化之前完成配置,使得环境可以按照预期运行。
class comp1 extends uvm component;
	`uvm_component_utils (comp1)
	int val1 = 1;
	string str1 = "null";
	function void build phase (uvm phase phase) ;
		`uvm_info("SETVAL",$sformatf ( "val1 is %d before get", val1),UVM_LOW)
		`uvm_info("SETVAL",$sformatf("str1 is %s before get", str1),UVM_LOW)
		`uvm config _db# (int) : : get(this, "","val1", val1);
		`uvm_config _db# (string) : : get(this, "" , "str1 " , str1);
		'uvm_info( "SETVA",$sformatf("val1 is %d after get", val1),UVM_LOW)
		'uvm _info( "SETVAL",$sformatf( "str1 is is after get",str1),UVM_LOW)
	endfunction
endclass
class test1 extends uvm test;
	'uvm_component _utils (test1)
	comp1 c1;
·	function void build phase(uvm phase phase) ;
		uvm_config_db# (int) : :set (this, "c1", "val1",100);
		uvm_config_db#(string) : :set(this, "c1", "str1", "comp1" ) ;
		c1 = comp1 : : type_id: : create ( "c1" , this) ;
	endfunction
endclass

首先要分析set路径:root->uvm_test_top->c1->val1/str1 ; get 路径:root->uvm_test_top->c1->val1/str1

object传递

  • 在test配置中,需要配置的参数不只是数量多,而且可能还分属于不同的组件。.
  • 那么如果对这么多层次中的变重做出类似与上面的变脸设置,需要更多的代码,容易出错还不易于复用,甚至底层组件的变量被删除后,也无法通过uvm_config_db::set()得知配置是否成功。
  • 然而如果将每个组件中的变量加以整合,首先放置到一个uvm_object中,再对中心化的配置对象进行传递,那么将会更有利于整体环境的修改维护。
class config1 extends uvm_object;  //定义一个配置类继承于object
	int val1 = 1;
	int str1 = "null" ;
	`uvm_object_utils (config1)
	...
endclass
class comp1 extends uvm_component; 
	'uvm_component_utils (comp1)
	config1 cfg ;
	...
	function void build_phase (uvm_phase phase) ;
		uvm_object tmp;  //声明了一个uvm_object 句柄
		uvm_config_db# (uvm_object) : :get(this, "", "cfg" , tmp) //这地方get于set传递类型都是一个父类uvm_object 
		void' ($cast(cfg , tmp)) ;
		uvm info ( "SETVAL",$sformatf( "cfg.val1 is %d after get" , cfg. val1), UVM_LOW)
		uvm info ( "SETVAL",$sformatf( "cfg.str1 is %s after get", cfg.str1), UVM_LOW)
	endfunction
endclass
class_test1 extends uvm_test;
	`uvm_component_utils ( test1)
	comp1 c1, c2;    //声明comp1句柄
	config1 cfg1, cfg2;
	...
	function void build phase (uvm_phase phase) ;
		cfg1 = config1 : : type_id: : create ( "cfg1") ;  //创建了两个配置类
		cfg2 = config1 : : type_id: :create ( "cfg2 " );
		cfg1. val1 = 30 ;
		cfg1.str1= "c1" ;
		cfg2 . val1 = 50;
		cfg2 .str1= "c2";
		uvm_config_db# (uvm_object)l :set(this, "c1", "cfg" , cfg1) ; //将root->uvm_test_top->c1->cfg配置成cfg1
		uvm_config_db# (uvm object) :set(this, "c2", "cfg" , cfg2) ;//将root->uvm_test_top->c2->cfg配置成cfg2
		c1 =comp1 : :type_id: :create ( "c1" , this) ;  //创建root->uvm_test_top->c1
		c2 = comp1 : : type_id: : create ( "c2", this) ;//创建root->uvm_test_top->c2
	endfunction
endclass

这地方不是很好理解:

  • 将变量放在一个object的子类(变量配置类)里面
  • 底层:在组件子类中声明这个变量配置类,并且在build_phase中声明一个object类,获取当前类的配置类变量(底层获取配置),因为此处传递的是父类句柄(object),但配置的实例时子类,所有做一个父类到子类的转换,这样才可以调用子类的资源
  • 顶层:声明组件类和配置类句柄,在build_phase进行配置类的创建和配置,然后将该配置设置到底层路径中的配置类中(注意传递类型于底层一致)。
  • 从而在顶层创建组件时,调用底层的build_phase时会获取配置再创建。

在使用uvm config db:set()/ge()t时,实际发生了这些后台操作:

  • uvm_config_d::set()通过层次和变量名,这些信息放置到uvm_pkg唯一的全局变量uvm_pkg::uvm_resources。
  • 全局变量uvm resources用来存储和释放配置资源信息(resourceinformation) 。
  • uvm_resources是uvm_resource_pool类的全局唯一实例,该实例中有两个resource数组用来存放配置信息,这两个数组中一个由层次名字索引,一个由类型索引,通过这两个关联数组可以存放通过层次配置的信息。
  • 同时,底层的组件也可以通过层次或者类型来取得来自高层的配置信息。这种方式使信息的配置和获取得到剥离,便于调试复用。
  • 在使用uvm_config_db:get()方法时,通过传递的参数构成索引层次,然后在uvm_resource已有的配置信息池中索引该配置,如果索引到,方法返回1,否则返回0。

建议

  • 在使用set()/get()方法时,传递的参数类型应当上下保持一致。对于uvm_obiect等实例的传递,如果get类型与set类型不一致,应当首先通过Scast()完成类型转换,再对类型转换后的对象进行操作。
  • Set()/get()方法传递的参数可以使用通配符“”来表示任意的层次,类似于正则表达式的用法。向时用户需要懂得“.comp1”与“*comp1”的区别,前者表示在目前层次以下所有名称为“compi”的组件,而后者表示包括当前层次及当前层次以下所有名为“comp1”的组件。’
  • 在module环境中如果要使用uvm_config db:set(),则传递的第一个参数uvm_component cntxt参数一般用来表示当前的层次。如果当前层次为最高层,用户可以设置为null,也可以设置为uvm_root:get()来表示uvm_root的全局顶层实例。
  • 在使用配置变量时,应当确保先进行uvm_config_db:get()操作,在获得了正确的配置值以后再便用。
  • 应当尽量确保uvm_config_db:set()方法在相关配置组件创建前调用。这是因为只有先完成配置,相关组件在例化前才可以得到配置值继而正确地例化。
  • 在set()方法第一个参数使用当前层次的前提下,对于同一组件的同一个变量,如果有多个高层组件对该变量进行设置,那么较高层组件的配置会覆盖较低层的配置;但是如果是同一层次组件对该变量进行多次配置时,应该遵循后面的配置会覆盖前面的配置。
  • 用户应该在使用uvm config db:.get()方法时,添加便于调试的语句,例如通过UVM报告信息得知get()方法中的配置变量是否从uvm_config _db获取到,如果没有获取,是否需要采取其它措施。
<think>我们正在讨论IC验证的学习资源和路径。根据引用[1],有一份《IC设计与验证:工作学习资料整理v1》的资料包,覆盖了IC设计与验证的多个方面,包括验证方法学等,总计1200页,适合初学者和专业人士。此外,引用[2]和[3]涉及形式验证验证完备性、UVM(Universal Verification Methodology)等相关知识,这些都是IC验证的核心内容。 因此,我们可以推荐以下学习路径和资源: 1. **基础知识**:学习数字电路设计、硬件描述语言(如Verilog或VHDL)以及计算机体系结构。这些是理解IC验证的基础。 2. **验证方法学**:学习SystemVerilog语言和UVM方法学。UVM是当前工业界主流的验证方法学,引用[2]中提到了UVM中的Sequence启动方式(Q27)和面向对象编程的优势(Q28),这些都是UVM的重要组成部分。 3. **形式验证**:引用[2]中详细介绍了形式验证(Q25)和如何保证验证完备性(Q26),这些是验证领域的重要部分。 4. **实践项目**:通过实际项目来巩固知识,例如使用UVM搭建验证环境,进行模块级和系统级验证。 5. **参考书籍和资料**: -IC设计与验证:工作学习资料整理v1》[^1]:作为综合资料,涵盖广泛。 - 《SystemVerilog for Verification》和《UVM实战》等书籍。 - 在线资源:EDA Playground(在线仿真平台),ChipVerify网站(提供UVM教程)等。 6. **进阶内容**:包括覆盖率驱动验证(CDV)、断言(SVA)、门级仿真、功耗验证(UPF)等。 此外,引用[3]提到了UVM的组件构建(component分支),这有助于理解UVM的层次结构。 学习路径建议: - 第一阶段:数字电路和Verilog基础。 - 第二阶段:SystemVerilog语言和验证技术(包括定向测试、随机测试等)。 - 第三阶段:UVM方法学,搭建验证环境- 第四阶段:学习形式验证、断言、覆盖率等高级主题。 - 第五阶段:参与实际项目,包括FPGA原型验证(引用[2]提到)和流片后的测试。 最后,持续关注行业动态,因为IC技术发展迅速。 相关问题: 1. UVM中的phase机制是如何工作的? 2. 如何搭建一个基本的UVM测试平台? 3. 形式验证中的等价性验证和模型检验有什么区别?</think>### IC验证学习资源与路径推荐 #### 基础理论准备 1. **数字电路基础** - 必学:布尔代数、组合逻辑/时序逻辑设计、状态机、计算机体系结构 - 推荐资源:《数字设计:原理与实践》(John F. Wakerly) - 实践工具:Verilog/VHDL仿真器(如ModelSim) 2. **硬件描述语言(HDL)** - 重点掌握: - SystemVerilog语法(面向验证的扩展:类、随机约束、覆盖率) - UVM方法学框架(如`uvm_component`层次结构[^3]) - 推荐资源: - 《SystemVerilog for Verification》 - UVM官方文档(Accellera标准) #### 核心验证技能 1. **验证方法学** - 学习UVM的四大核心机制- 工厂模式(Factory) - 配置机制Config DB) - 消息报告(Report Object[^3]) - 相位控制(Phase机制[^3]) - 关键实践: - Sequence启动方式(显式`start()`与隐式`default_sequence`[^2]) - 事务级建模(TLM通信) 2. **形式验证与完备性** - 掌握:等价性验证(RTL vs 网表)、模型检验[^2] - 完备性策略:IP级→子系统级→SoC级验证流程[^2] - 工具:Synopsys VC Formal/Cadence JasperGold 3. **高级验证技术** - 覆盖率驱动验证(CDV) - 断言验证(SVA) - 功耗验证(UPF流程[^2]) - FPGA原型验证[^2] #### 推荐学习路径 ```mermaid graph LR A[数字电路基础] --> B[Verilog/SystemVerilog] B --> C[UVM方法学] C --> D[形式验证FPGA原型] D --> E[SoC级验证项目] ``` #### 权威资源包 推荐《IC设计与验证:工作学习资料整理v1》[^1]: - **内容覆盖**: - 1200页系统教程,含数字IC验证全流程 - 形式验证/等价性验证原理[^2]详解 - UVM组件构建与面向对象设计[^3]实例 - 实际项目问题解决案例 - **独特价值**: - 提供验证完备性方法论(IP级→SoC级协同)[^2] - 包含DFT/STA等后端协同验证要点[^2] #### 实践建议 1. **工具链实践**: - 仿真工具:VCS/Xcelium - 波形查看:Verdi/Debussy 2. **开源项目**: - RISCV核验证(GitHub搜索”RISCV UVM Testbench“) 3. **进阶方向**: - 混合信号验证 - 安全性验证(ISO 26262) --- ###
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值