Jump to content

IES 10.2 -- Using config_db to set array of interfaces


Recommended Posts

AARGH!!!

It shouldn't be this difficult, but it apparently is for me.

In my top module, I am trying to support a parametric design where the number of interfaces is determined by a parameter (let's call it num_ifs). So, I declared an array of interfaces:

my_if_type`params_map my_if[0:num_ifs-1](.*);

Later, I would like to set the UVM config DB with these interfaces, so that each agent instance gets the right virtual interface to play with. So, I tried the following:

string inst_name;
initial begin : SET_CFG_DB
  foreach(my_if[i]) begin
    $sformat(inst_name, "MY_IF[%0d]", i);
    uvm_config_db#(virtual my_if_type`params_map)::set(uvm_root::get(), "*", inst_name, my_if[i]);
end : SET_CFG_DB

IES (10.20-s105) fails at compile-time with the following:

ncvlog: *E,NOTPAR (my_top.sv,line_no|col): Illegal operand for constant expression [4(IEEE)].

The error points to the i index in the config set method call.

WTF???!!! I am at a loss here. I don't see anything wrong with what I'm trying to do. Since I have no access to other simulators (Questa, VCS), I cannot say if this problem is Cadence-specific, or a broader UVM issue.

The funny part is that I actually have several arrays of interfaces, so the initial block would have several foreach loops. I initially got an INTERNAL EXCEPTION (MESSAGE: cetpfunc unknown wad struct id 'ifs_vst') and an ncvlog.err dump. As I commented each loop out, I could bypass the INTERNAL EXCEPTION and get to the NOTPAR error described earlier.

The only work-around I can think of is to do something stupid like this:

initial begin : SET_CFG_DB
  uvm_config_db#(virtual my_if_type`params_map)::set(uvm_root::get(), "*", "MY_IF[0]", my_if[0]);
  // and so on...
end : SET_CFG_DB

Clearly, that is not an acceptable work-around for a parametric design.

Ideas? Any help? Please?

Link to comment
Share on other sites

Hello,

How about something like this:

module top #(parameter int numif=1) ();
...
generate
genvar i;
 for (i=0; i<numif; i++) begin : blk
 apb_if apbif (clock, reset);
 memctldut dut (.clock, .reset, .apbif(apbif));
 initial
   uvm_config_db#(virtual apb_if)::set(uvm_root::get(), "*",
               $sformatf("MY_IF[%0d]",i), blk[i].apbif);
 end
endgenerate
...
endmodule

It uses a generate block but could do the trick...

Kathleen

-------------------------------------------

Kathleen Meade

Verification Solutions Architect

Cadence Design Systems

--------------------------------------------

Link to comment
Share on other sites

I also had to use the genvar for assignment of the dynamic array of interfaces in the top_tb. This was VMM 1.1.1a code though and I didn't have the config database and I was using an older version of the Questa (the 6.6 series -- so it could be different now with 10). So this may be across compilers. We had to go through push-ups to get this to work. (Not the top_tb, but the assignment of physical interfaces to the vif -- because we didn't have a config_db).

The other thing you can do to be more generic -- is don't paramterize your top.

You can actually use the command line parameter set_config_int and then you can have a configuration knob to change the number of interfaces on the fly. This is really useful if you have your on internal library of IP and need to test across different configurations. IE a channel based environment that can support 3 to 10 channels depending on what product the IP is going into.

It really depends on how flexible you need your knobs and configurations to be.

Edited by lisakb1963
Link to comment
Share on other sites

  • 6 months later...

Hello,

module top #(parameter int numif=1) ();
...
generate
genvar i;
for (i=0; i<numif; i++) begin : blk
apb_if apbif (clock, reset);
memctldut dut (.clock, .reset, .apbif(apbif));
initial
uvm_config_db#(virtual apb_if)::set(uvm_root::get(), "*",
$sformatf("MY_IF[%0d]",i), blk[i].apbif);
end
endgenerate
...
endmodule

Is it safe ? I mean, I use the same trick. However, I am wondering, whether it is fine, that somewhere else in top I have:

initial

Link to comment
Share on other sites

Hello,

module top #(parameter int numif=1) ();
...
generate
genvar i;
for (i=0; i<numif; i++) begin : blk
apb_if apbif (clock, reset);
memctldut dut (.clock, .reset, .apbif(apbif));
initial
uvm_config_db#(virtual apb_if)::set(uvm_root::get(), "*",
$sformatf("MY_IF[%0d]",i), blk[i].apbif);
end
endgenerate
...
endmodule

Is it safe ? I mean, I use the same trick. However, I am wondering, whether it is fine, that somewhere else in the top module I have:

initial
  run_test("My_Test")
Does it not introduce a race hazard of initial processes ? Of course, one could put start of the test as a condition in the last iteration of the generate loop, but in my opinion is not a clean solution... Edited by drianf0
Link to comment
Share on other sites

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.
Note: Your post will require moderator approval before it will be visible.

Guest
Reply to this topic...

×   Pasted as rich text.   Paste as plain text instead

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.

×
×
  • Create New...