7.2 uvm_resource_db in UVM

uvm_resource_db是一个类型参数化 type-parameterized的类,它是资源数据库顶部的一个方便层(convenience layer)。这个便利层简化了对低级数据库的访问,并且没有添加新功能。因此,uvm_resource_db不是从uvm_resource类派生的。
以下uvm_resource_db类的代码段取自uvm源代码。

cs 复制代码
class uvm_resource_db #(type T=uvm_object);

  typedef uvm_resource #(T) rsrc_t;

  protected function new();
  endfunction

  static function rsrc_t get_by_name(string scope, string name,
                                     bit rpterr=1);
    return rsrc_t::get_by_name(scope, name, rpterr);
  endfunction
  static function void set(input string scope, input string name,
                           T val, input uvm_object accessor = null);
    rsrc_t rsrc = new(name, scope);
    rsrc.write(val, accessor);
    rsrc.set();
    ...    
    ...
  endfunction

  ...
  ...
endclass

注:

  1. 这个uvm_resource_db类未实例化
  2. 它使用一组静态函数来操作资源和资源池。因此,必须使用范围解析操作符( ::)来调用它们。

例如:uvm_resource_db #(整数)::设置(...);

  1. 如果**+UVM_RESOURCE_DB_TRACE**作为命令行参数提供,它会打印所有资源数据库的访问(写入和读取)。

1. uvm_resource_db methods

所有函数都是下表中提到的静态函数

2. uvm_resource_db example

在下面的示例中,control位存储在数据库中,作为在component_B中为my_component创建对象的启用条件(enable condition)。

名为"control"、类型为bit的新资源将从测试用例添加到资源池中。

cs 复制代码
uvm_resource_db #(bit)::set("*", "control", 1, this);

//where,
//string scope = "*";
//string name = "control";
//T val = 1;
//uvm_object accessor =  this;

//In component_B, 
if(!uvm_resource_db #(bit)::read_by_name(get_full_name(), "control", ctrl))
  `uvm_fatal(get_type_name(), "read_by_name failed for resource in this scope");

使用read_by_name静态函数检索资源,该函数在名称为"control"的数据库中查找。如果read_by_name在数据库中找不到"control"字符串名,将报告致命错误。尽管致命检查不是强制性的,但建议将其用于调试目的。一旦表中的查找成功,存储在资源数据库中的值就会在局部变量ctrl中更新。此控制位用于控制my_component对象的创建。

cs 复制代码
`include "uvm_macros.svh"
import uvm_pkg::*;

class component_A #(parameter ID_WIDTH = 8) extends uvm_component;
  bit [ID_WIDTH-1:0] id;
  `uvm_component_param_utils(component_A #(ID_WIDTH))
  
  function new(string name = "component_A", uvm_component parent = null);
    super.new(name, parent);
    id = 1;
  endfunction
  
  function display();
    `uvm_info(get_type_name(), $sformatf("inside component_A: id = %0d", id), UVM_LOW);
  endfunction
endclass

class mycomponent #(parameter ID_WIDTH = 8) extends uvm_component;
  bit [ID_WIDTH-1:0] id;
  `uvm_component_param_utils(mycomponent #(ID_WIDTH))
  
  function new(string name = "mycomponent", uvm_component parent = null);
    super.new(name, parent);
    id = 2;
  endfunction
  
  function display();
    `uvm_info(get_type_name(), $sformatf("inside mycomponent: id = %0d", id), UVM_LOW);
  endfunction
endclass

class component_B #(int ID_WIDTH = 8) extends component_A #(ID_WIDTH);
  bit ctrl;
  bit [ID_WIDTH-1:0] id;
  mycomponent #(8) my_comp;
  `uvm_component_param_utils(component_B #(ID_WIDTH))
  
  function new(string name = "component_B", uvm_component parent = null);
    super.new(name, parent);
    id = 3;
  endfunction
  
  function void build_phase(uvm_phase phase);
    super.build_phase(phase);
    if(!uvm_resource_db #(bit)::read_by_name(get_full_name(), "control", ctrl))
      `uvm_fatal(get_type_name(), "read_by_name failed for resource in this scope");
    if(ctrl)  my_comp = mycomponent #(8)::type_id::create("my_comp", this);
    
  endfunction
  
  function display();
    `uvm_info(get_type_name(), $sformatf("inside component_B: id = %0d, ctrl = %0d", id, ctrl), UVM_LOW);
    if(ctrl) void'(my_comp.display());
  endfunction
endclass

class my_test extends uvm_test;
  bit control;
  `uvm_component_utils(my_test)
  component_A #(32) comp_A;
  component_B #(16) comp_B;
  
  function new(string name = "my_test", uvm_component parent = null);
    super.new(name, parent);
  endfunction
  
  function void build_phase(uvm_phase phase);
    super.build_phase(phase);
    comp_A = component_A #(32)::type_id::create("comp_A", this);
    comp_B = component_B #(16)::type_id::create("comp_B", this);
    
    uvm_resource_db #(bit)::set("*", "control", 1, this);
  endfunction
   
  function void end_of_elaboration_phase(uvm_phase phase);
    super.end_of_elaboration_phase(phase);
    uvm_top.print_topology();
  endfunction
  
  task run_phase(uvm_phase phase);
    super.run_phase(phase);
    void'(comp_A.display());
    void'(comp_B.display());
  endtask
endclass

module tb_top;
  initial begin
    run_test("my_test");
  end
endmodule

Output:

cs 复制代码
UVM_INFO /xcelium20.09/tools//methodology/UVM/CDNS-1.2/sv/src/base/uvm_root.svh(605) @ 0: reporter [UVMTOP] UVM testbench topology:
----------------------------------------
Name          Type           Size  Value
----------------------------------------
uvm_test_top  my_test        -     @1809
  comp_A      uvm_component  -     @1876
  comp_B      uvm_component  -     @1907
    my_comp   uvm_component  -     @1954
----------------------------------------

UVM_INFO testbench.sv(14) @ 0: uvm_test_top.comp_A [uvm_component] inside component_A: id = 1
UVM_INFO testbench.sv(52) @ 0: uvm_test_top.comp_B [uvm_component] inside component_B: id = 3, ctrl = 1
UVM_INFO testbench.sv(28) @ 0: uvm_test_top.comp_B.my_comp [uvm_component] inside mycomponent: id = 2
相关推荐
啄缘之间11 天前
8.【学习】工业级详细接口约束&覆盖率
开发语言·笔记·学习·uvm·sv
Ether IC Verifier11 天前
SystemVerilog 数据类型详解
php·systemverilog·uvm·ic验证
liuluyang5301 个月前
UVM 工厂机制 完整可编译运行 Demo
uvm·uvm工厂机制
liuluyang5301 个月前
UVM工厂机制
uvm·工厂机制
liuluyang5301 个月前
UVM工厂机制(二)
uvm·工厂机制
liuluyang5301 个月前
SystemVerilog常用关键词与函数
uvm·systermverilog
liuluyang5301 个月前
SV主要关键词详解
fpga开发·uvm·sv
liuluyang5302 个月前
clk_mux_seq sv改进
fpga开发·uvm
谷公子的藏经阁2 个月前
DVCon 2025 论文精华导读及下载链接
ai·论文·systemverilog·uvm·dvcon
蓝天下的守望者4 个月前
SystemVerilog中 `timescale的使用问题
systemverilog·uvm·vcs