I want to create a clock in my top level testbench whose period can be controlled from the test. What I did was set the period into the uvm_config_db and get it back in the testbench. I had to put in a #1 to make sure that the build phase was finished, otherwise the get returned the wrong value:
module testbench_top;
int clk_period;
bit clk = 0;
initial begin
#1;
void'(uvm_config_db #(int) ::get(null, "uvm_test_top.env", "clk_period", clk_period));
// Create clk
forever begin
#(clk_period/2) clk = !clk;
end
end
I am annoyed by the #1. Is there a better way to check that the config has been set? Can I somehow block until start_of_simulation_phase?
In practice get() can be used to fetch an object destined to any component in the hierarchy. Typically for set() and get(), this is used in the “cntxt” field to specify the current instance/scope. set() uses “inst _ name” to address the object to the appropriate sub-block in the hierarchy.
In particular, uvm_resource_db uses a "last write wins" approach. The uvm_config_db, on the other hand, looks at where things are in the hierarchy up through end_of_elaboration, so "parent wins." Once you start start_of_simulation, the config_db becomes "last write wins."
set_config_* can be used only for the components not for the sequences. By using configuration you can change the variables inside components only not in sequences.
This is the global version of set_config_object in uvm_component. This function places the configuration setting for an object field in a global override table, which has highest precedence over any component-level setting. See uvm_component::set_config_object for details on setting configuration.
I found it buried in the class reference: You can access the global singleton versions of each phase with <phase name>_ph
. Then I can use the wait_for_state
function to block until the start of the start of simulation phase. Simulated and it seems to work:
module testbench_top;
int clk_period;
bit clk = 0;
initial begin
start_of_simulation_ph.wait_for_state(UVM_PHASE_STARTED);
if(!uvm_config_db #(int) ::get(null, "uvm_test_top.env", "clk_period", clk_period))
`uvm_fatal("CONFIG", "clk_period not set");
// Create clk
forever begin
#(clk_period/2) clk = !clk;
end
end
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With