Search code examples
system-veriloguvm

How do I run only a child UVM test class inherited from uvm_test?


I want to run the inherited child uvm_test class. The problem is that when you run the test2 class using +UVMTESTNAME=test2, it also runs the test1 class.

This is because I expect test2 to be the only one executed except test1.

This means that if I implement 1000 inherited test classes and run the 1000th test class, I might run 1000 classes.

Is this the nature of uvm test execution? or do I miss it?

This class test1

class test1 extends test_base;
  `uvm_component_utils(test1)
   main_ahb_sequence seq;

  function new(string name, uvm_component parent);
    super.new(name, parent);
  endfunction
    
  function void build_phase(uvm_phase phase);
    super.build_phase(phase);
    seq = main_ahb_sequence::type_id::create("seq", this);  
    if(!seq.randomize())
    `uvm_error("rand failed", UVM_LOW)
  endfunction
    
  task run_phase(uvm_phase phase);
    phase.raise_objection(this);  
    seq.start(ahb0.sequencer);
    phase.drop_objection(this);
  endtask

this is test2 class inherited from test1.

class test2 extends test1;
  `uvm_component_utils(test2)
   
  function new(string name, uvm_component parent);
    super.new(name, parent);
  endfunction
 
  virtual function void build_phase(uvm_phase phase);
  super.build_phase(phase);
    factory.print();
  endfunction
 
  task run_phase(uvm_phase phase);
    super.run_phase(phase);
    phase.raise_objection(this);
    `uvm_info("TEST2", "THIS is run_phase from test2", UVM_LOW);
    phase.drop_objection(this);
  endtask
 
endclass

Solution

  • This means that if I implement 1000 inherited test classes and run the 1000th test class, I might run 1000 classes.

    Of course not. Once a test name has been selected, the run_test() task calls the factory to create an instance of the test with an instance name of uvm_test_top. Finally, run_test() starts the test by cycling through the simulation phases. Note that all the phases are virtual.

    I want to run the inherited child uvm_test class. The problem is that when you run the test2 class using +UVMTESTNAME=test2, it also runs the test1 class.

    As mentioned above, we actually only created one test2 instance. The reason you see the result is because of the inheritance of the class, and calling super.run_phase(phase); in the subclass test2.


    Supplement: About User-Defined Test and Inheritance refer to the UVM 1.2 User's Guide

    In common case, the build_phase() function of the base_test creates the env. This fully creates the top-level environment as each sub-component will create their own children components in their respective build_phase() functions. All of the definitions in the base_test are inherited by any test that derives from the base_test. This means any derivative test will not have to build the top-level environment if the test calls super.build_phase(). Likewise, the run_phase() task behavior can be inherited, as well as all other phases. As you have done, probably the general case will only have the base_test, which creates env, and the test1, which creates sequence and really runs the test. But if the current implementation of test1 does not meet the needs of the extended test, we can write a class test2 that inherits from test1, the build_phase() and/or run_phase(), as well as any other run-time phase methods may be refined as needed because they are all virtual. Since the top-level environment is created by the parent test's build_phase() function, and the run_phase() task defines the run phase, so the derivative tests can just make minor adjustments. For example, changing the default sequence executed by the agents in the environment.