Exporting functions object hierarchy

Hello,

I have just began playing with SV DPI interface with Questasim. I have successfully gotten a very simple example to work. Now I would like to try and co-simulate a large test-bench along with software code which until now I am only able to run attached to real HW.

Now, I understand how to import/export functions, however all examples I have come across use functions located within the testbench top module. In my case this is more complex.
My simulation is class-based. So I have a bunch of classes which act as drivers of the underlying HDL modules. Moreover, the system I am simulating is a modular system, so I often try to keep the number of instances of the HDl module that I am simulating flexible. That means I can simulate N entities using HDL parameters.
To run the tests on those entities I often keep their drivers/virtual interfaces in arrays. This means my TB code usually looks like:

integer unsigned data [10];
data = '{default: 32'hcacacaca};

//do a bulk write (translated to an axi burst)
drivers[0].regs_bfm.write_burst(32'habcd0000, data);

//Do a single write
drivers[0].regs_bfm.write(32'h01234567, 32'ha5a5a5a5);

The functions I am calling here in this snippet are either inside a class (of which the drivers elements are instances), or inside an interface driver, such as regs_bfm, which is the BFM of an interface which has the read/write/read_burst/write_burst functions.

I see no easy way to call those functions in a “flexible” fashion from the C portion of the code. I could use a function called “drivers0_regs_bfm_write” and “drivers0_regs_bfm_write_burst” and export those I guess… but that seems very bad in my opinion…

Another options I guess would be doing some sort of decoding with parameters, for example I could have a single function called “driver_c_interface” which could take an integer and perhaps some sort of string (enum might be better?) to call the appropriate function…
I also see many problems with this approach, for instance different functions take different arguments, and also return different data types…

Anyway, can anybody give me some ideas on how to deal with this? I really don’t want to make my own way and make it more complex than it needs to be.

Thanks

Hi,

anyboday can make any suggestions?

Thanks.

In reply to arquer:

This as a complicated topic and may want to ask for additional help from your tool vendor.

There are a number of ways of dealing with multiple exported instances and class-based exports. You can wrap a non-class method around a class method call with an extra argument indicating which class instance needs to be called

module bfms;

driver_class table[];

export "DPI-C" task write;

task write(bit[31:0] addr, data, int index);
table[index].write(addr,data);
end task

Someone has to populate that table with the correct class handles at initialization.

You may want to see this example.