uvm_primer ch15 和多个对象对话

uvm_primer ch15 和多个对象对话

oop的思想

在一个类或者一个函数中只干一件事情;

使用变量来沟通不同的object,是一个糟糕的方法;

class dice_test extends uvm_test;
   `uvm_component_utils(dice_test);

   dice_roller dice_roller_h;
   coverage coverage_h;
   histogram histogram_h;
   average average_h;

   function void build_phase(uvm_phase phase);
      coverage_h = new("coverage_h", this);
      histogram_h = new("histogram_h",this);
      average_h     = new("average_h",this);
      dice_roller_h = new("dice_roller_h",this);
   endfunction : build_phase

   task run_phase(uvm_phase phase);
      int the_roll;  //定义一个变量
      phase.raise_objection(this);
      repeat (20) begin
         the_roll = dice_roller_h.two_dice();
         coverage_h.write(the_roll);  //使用变量来沟通不同的object  连接不同的object
         histogram_h.write(the_roll);
         average_h.write(the_roll);
      end
      phase.drop_objection(this);
   endtask : run_phase
   
   function new(string name, uvm_component parent);
      super.new(name,parent);
   endfunction : new
endclass : dice_test

观察者模式

之前我们学习过factory模式
现在引入一个新的设计模式,observer模式或者 twitter模式;

发twitter时:

  • 不需要知道谁是你的粉丝;
  • 不需要知道粉丝在得到twitter后会做什么;
  • 甚至不需要有粉丝, 一样可以发twitter;

observer模式中一个对象只需要创建数据并分享出去,其他不用care;
每一个follower会得到一份同样的数据, 每一个follower怎么处理这个数据由各个follower决定;

也就是广播模式;

  • uvm_anlysis_port 提供一个广播的途径;uvm_anlysis_port 不是uvm_component 的子类,但是它也是在仿真中始终存在的;使用write()函数来广播数据;使用connect()和subscriber相连接;
  • uvm_subscriber extends uvm_component ;包含一个analysis_export;需要自己创建一个write()函数,用来处理收到的数据;

实现subscriber

class average extends uvm_subscriber #(int);
   `uvm_component_utils(average);

   real dice_total;
   real count;

   function new(string name, uvm_component parent = null);
      super.new(name,parent);
      dice_total = 0.0;
      count = 0.0;
   endfunction : new

   function void write(int t);
      dice_total = dice_total + t;
      count++;
   endfunction : write

   function void report_phase(uvm_phase phase);
      
      $display ("DICE AVERAGE: %2.1f",dice_total/count);
   endfunction : report_phase
   
endclass : average

连接对象

定义analysis_port

class dice_roller extends uvm_component;
   `uvm_component_utils(dice_roller);
   uvm_analysis_port #(int) roll_ap;  //定义analysis_port
   function void build_phase (uvm_phase phase);
      roll_ap = new("roll_ap",this);
   endfunction : build_phase
   
   rand byte die1;
   rand byte die2;
   
   constraint d6 {
    
     die1 >= 1; die1 <= 6; 
                   die2 >= 1; die2 <= 6; }
   task run_phase(uvm_phase phase);
      int the_roll;
      phase.raise_objection(this);
      void'(randomize());
      repeat (20) begin
         void'(randomize());
         the_roll = die1 + die2;
         roll_ap.write(the_roll);  //调用write方法
      end
      phase.drop_objection(this);
   endtask : run_phase
 
   function new(string name, uvm_component parent);
      super.new(name,parent);
   endfunction : new
   
endclass : dice_roller

连接analysis_port

  • build_phase是top-bottom的模式从顶往下
  • connect_phase 是bottom-top模式
class dice_test extends uvm_test;
   `uvm_component_utils(dice_test);
   dice_roller dice_roller_h;
   coverage coverage_h;
   histogram histogram_h;
   average average_h;
   function void connect_phase(uvm_phase phase);
      dice_roller_h.roll_ap.connect(coverage_h.analysis_export);  //连接analysis_port
      dice_roller_h.roll_ap.connect(histogram_h.analysis_export);      
      dice_roller_h.roll_ap.connect(average_h.analysis_export);
   endfunction : connect_phase
   
   function new(string name, uvm_component parent);
      super.new(name,parent);
   endfunction : new

   function void build_phase(uvm_phase phase);
      dice_roller_h = new("dice_roller_h", this);
      coverage_h = new("coverage_h", this);
      histogram_h = new("histogram_h",this);
      average_h     = new("average_h",this);
   endfunction : build_phase
endclass : dice_test

连接关系示意图
在这里插入图片描述

猜你喜欢

转载自blog.csdn.net/weixin_39060517/article/details/113091196