Is there a method to execute a block of code after a user calls $finish? - system-verilog

We want to be able to provide a predefined list of things to be done at the end of every SystemVerilog test. Since multiple people are working on this project, it'd be nice if they did not have to think about the things we are doing in the background, but simply call $finish at the end of a test as usual. I know we could create our own custom $finish macro, but we would prefer to not have to change preexisting tests.
Is there any way in SystemVerilog to have a block of code run after a $finish call? Using something like UVM is not an option. I've looked around, but I can't seem to find something that does this behavior.

The final keyword can help you out here. Refer to IEEE Std 1800-2017, section 9.2.3 Final procedures:
A final procedure executes when simulation ends due to an explicit or
implicit call to $finish .
One limitation is that it executes in zero time, which means you can not have any delays, etc. Read the full description for all the details.
Example:
final begin
$display("something");
do_something();
end

If the list of things does not consume time, a final block is the antithesis of an initial block, except it cannot consume any time. Otherwise, it would not be the "final" thing.
If you need steps that consume time, there is no way of doing this without modifying the existing tests. The simplest approach is declaring a global event like test_done in a package p, and then replacing $finish; with ->p::test_done;. But sometimes you need to shut down other free-running process. Doing that requires much more coordination, which is exactly what UVM accomplishes with its phases and objections mechanism.

Related

AppleScript pass expression into function to be re-evaluated repeatedly? (or: AppleScript handler with callback?)

I think the correct description for what I'm trying to do is be able to pass an expression or function/handler into another handler as a parameter/argument. Some code to be evaluated inside the receiving handler. Similar to Javascript callbacks, I think.
For example, something like this:
on waitFor(theConditionExpression)
timeout_start(5) -- start a 5 second timer
repeat until (theConditionExpression or timeout_isExpired())
delay 0.1
end repeat
return theConditionExpression
end waitFor
theConditionExpression should be some expression or function that evaluates to a boolean result.
not really relevant to the question, but just FYI, timeout_start(…) and timeout_isExpired() are two simple handlers I've written that do exactly what they say. (…start() doesn't return anything, …isExpired() returns a boolean).
Of course, typically if I pass in some boolean expression, it will evaluate that expression once, at the time I pass it in. But I want it to evaluate it every time it's referenced in the code inside the handler.
Some languages (not sure about AS) have some kind of eval() function that you can pass it some code as a string and it will execute that string as code. Theoretically that could solve this, but: (a) I don't know if AS has anything like that, but even if it does, (b) it's not desired for various reasons (performance, injection risks, etc.)
So I'm thinking something more like eg. JavaScript's ability to pass in a function (named or anonymous) as function parameter/argument that can be re-evaluated every iteration in a loop, etc. (eg. like the compareFn argument in JS's Array.sort(compareFn)).
Can AS do anything like this, and if so how?
Thanks!
I'm going to suggest (pro forma) that an AppleScript application with an on idle handler is generally a better solution for wait conditions than a repeat/delay loop. It's more efficient for the system, and doesn't freeze up the script. But that would involve reconceptualizing your script, and I'm not certain it would work in this case, given the way you formed the problem.
There's an old but good site called AppleScript Power Handlers that shows a bunch of nifty-neato tricks for sophisticated use of AppleScript handlers: passing handlers as values or parameters; creating Script Objects within handlers; making closures and constructors. I'm pretty sure the answer to your request is in there. aLikely you'll want to set up a bunch of handlers that serve as condition expressions, then pass them as parameters to the evaluating handler. Or maybe you'll want to set up a script object containing the condition handlers and call it as needed?
At any rate, see what you can do with it, and ask more specific questions if you run into problems.

How to change verbosity of uvm components after certain condition

I am trying to change the UVM verbosity of the simulation after satisfying certain conditions. Verbosity options of different components are passing through the command line as +uvm_set_verbosity. Once the conditions are satisfied, then the simulations should run with the the command line +uvm_set_verbosity option. Till then simulation runs with low verbosity for all components.
Looking through the UVM library code, it appears that there is a function called m_set_cl_msg_args(). This function calls three other functions that appear to consume the command line arguments like: +uvm_set_verbosity, +uvm_set_action, +uvm_set_severity.
So what I did was get the uvm_root instance from the uvm_coreservice singleton, and then use the get_children() function from uvm_component class to recursively get a queue of all of the uvm_components in the simulation. Then call the m_set_cl_msg_args() function on all of the components.
My code looks like:
begin
uvm_root r;
uvm_coreservice_t cs_t;
uvm_component array_uvm[$];
cs_t = uvm_coreservice_t::get();
r = cs_t.get_root();
r.get_children(array_uvm);
foreach(array_uvm[i])
array_uvm[i].m_set_cl_msg_args();
end
Even though this code compiles properly, But this is not changing verbosity. Any idea ?
Moreover I am able to print all the components in array_uvm. So I am guessing
array_uvm[i].m_set_cl_msg_args();
this as a wrong call.
Anyone have any other suggestion to change verbosity during run time.
You should never use functions in the UVM that are not documented in the language reference manual. They can (and do) change in any revision. I'm guessing +uvm_set_verbosity only works at time 0 by default.
There is already a function to do what you want
umm_top.set_report_verbosity_level_hier()
I suggest using +UVM_VERBOSITY=UVM_LOW to start your test, and then define your own switch for activating the conditional setting.
If you want a specific component, use component_h.set_report_verbosity_level() (add the _hier to set all its children)
You can use the UVM's command line processor get_arg_values() method to specify the name of the component(s) you want to set, and then use umm_top.find() to get a handle to the component.

Managing multiple anylogic simulations within an experiment

We are developing an ABM under AnyLogic 7 and are at the point where we want to make multiple simulations from a single experiment. Different parameters are to be set for each simulation run so as to generate results for a small suite of standard scenarios.
We have an experiment that auto-starts without the need to press the "Run". Subsequent pressing of the Run does increment the experiment counter and reruns the model.
What we'd like is a way to have the auto-run, or single press of Run, launch a loop of simulations. Within that loop would be the programmatic adjustment of the variables linked to passed parameters.
EDIT- One wrinkle is that some parameters are strings. The Optimization or Parameter Variation experiments don't lend themselves to enumerating a set of strings to be be used across a set of simulation runs. You can set a string per parameter for all the simulation runs within one experiment.
We've used the help sample for "Running a Model from Outside Without Presentation Window", to add the auto-run capability to the initial experiment setup block of code. A method to wait for Run 0 to complete, then dispatch Run 1, 2, etc, is needed.
Pointers to tutorial models with such features, or to a snip of code for the experiment's java blocks are much appreciated.
maybe I don't understand your need but this certainly sounds like you'd want to use a "Parameter Variation" experiment. You can specify which parameters should be varied in which steps and running the experiment automatically starts as many simulation runs as needed, all without animation.
hope that helps
As you, I was confronted to this problem. My aim was to use parameter variation with a model and variation were on non numeric data, and I knew the number of runs to start.
Then i succeed in this task with the help of Custom Variation.
Firstly I build an experiment typed as 'multiple run', create my GUI (user was able to select the string values used in each run.
Then, I create a new java class which inherit from the previous 'multiple run' experiment,
In this class (called MyMultipleRunClass) was present:
- overload of the getMaximumIterations method from default experiment to provide to default anylogic callback the correct number of iteration, and idnex was also used to retrieve my parameter value from array,
- implementation of the static method start,
public static void start() {
prepareBeforeExperimentStart_xjal( MyMultipleRunClass.class);
MyMultipleRunClass ex = new MyMultipleRunClass();
ex.setCommandLuneArguments_xjal(null);
ex.setup(null);
}
Then the experiment to run is the 'empty' customExperiment, which automatically start the other Multiple run experiment thru the presented subclass.
Maybe it exists shortest path, but from my point of view anylogic is correctly used (no trick with non exposed interface) and it works as expected.

What is the architecture behind Scratch programming blocks?

I need to build a mini version of the programming blocks that are used in Scratch or later in snap! or openblocks.
The code in all of them is big and hard to follow, especially in Scratch which is written in some kind of subset of SmallTalk, which I don't know.
Where can I find the algorithm they all use to parse the blocks and transform it into a set of instructions that work on something, such as animations or games as in Scratch?
I am really interested in the algorithmic or architecture behind the concept of programming blocks.
This is going to be just a really general explanation, and it's up to you to work out specifics.
Defining a block
There is a Block class that all blocks inherit from. They get initialized with their label (name), shape, and a reference to the method. When they are run/called, the associated method is passed the current context (sprite) and the arguments.
Exact implementations differ among versions. For example, In Scratch 1.x, methods took arguments corresponding to the block's arguments, and the context (this or self) is the sprite. In 2.0, they are passed a single argument containing all of the block's arguments and context. Snap! seems to follow the 1.x method.
Stack (command) blocks do not return anything; reporter blocks do.
Interpreting
The interpreter works somewhat like this. Each block contains a reference to the next one, and any subroutines (reporter blocks in arguments; command blocks in a C-slot).
First, all arguments are resolved. Reporters are called, and their return value stored. This is done recursively for lots of Reporter blocks inside each other.
Then, the command itself is executed. Ideally this is a simple command (e.g. move). The method is called, the Stage is updated.
Continue with the next block.
C blocks
C blocks have a slightly different procedure. These are the if <> style, and the repeat <> ones. In addition to their ordinary arguments, they reference their "miniscript" subroutine.
For a simple if/else C block, just execute the subroutine normally if applicable.
When dealing with loops though, you have to make sure to thread properly, and wait for other scripts.
Events
Keypress/click events can be dealt with easily enough. Just execute them on keypress/click.
Something like broadcasts can be done by executing the hat when the broadcast stack is run.
Other events you'll have to work out on your own.
Wait blocks
This, along with threading, is the most confusing part of the interpretation to me. Basically, you need to figure out when to continue with the script. Perhaps set a timer to execute after the time, but you still need to thread properly.
I hope this helps!

VHDL Bus Functional Modelling - Can't put groups of procedures into a package to clean up the code

I want to organize a working bus functional model and push commonly used procedures (which look like CPU subroutines) out into a package and get them out of the main cpu model, but I'm stuck.
The procedures don't have access to the hardware bits when they're pushed out in a package.
In Verilog, I would put commonly used procedures out into an include file and link them into the CPU model as required for a given test suite.
More details:
I have a working bus functional model of a CPU, for simulation test benching.
At the "user interface" level I have a process called "main" running inside the CPU model which calls my predefined "instruction set" like this:
cpu_read(address, read_result);
cpu_write(address, write_data);
etc.
I bundle groups of those calls up into higher level procedures like
configure_communication_bus;
clear_all_packet_counters;
etc.
At the next layer these generic functions call a more hardware specific version which knows the interface timing for the design,
and those procedures then use an input record and output record to connect to the hardware module ports and waggle the cpu bus signals as required.
cpu_read calls hardware_cpu_read(cpu_input_record, cpu_output_record, address);
Something like this:
procedure cpu_read (address : in std_logic_vector(15 downto 0);
read_result : out std_logic_vector(31 downto 0));
begin
hardware_cpu_read(cpu_input_record, cpu_output_record, address, read_result);
end procedure;
The cpu_input_record and cpu_output_record are declared as signals of type nnn_record in the cpu model vhdl file.
So this is all working, but every single one of these procedures is all stored in the cpu VHDL module file, and all in the procedure declaration section so that they are all in the same scope.
If I share the model with team members they will need to add their own testing subroutines, and those also are all in the same location in the file, as well, their simulation test code has to go into the "main" process along with mine.
I'd rather link in various tests from outside the model, and only keep model specific procedures in the model file..
Ironically I can push the lowest level hardware procedure out to a package, and call those procedures from within the "main" process, but the higher level processes can't be put out into that package or any other packages because they don't have access to the cpu_read_record and cpu_write_record.
I feel like there must be a simple way to clean up this code and make it modular, and I'm just missing something obvious.
I don't really think making a command interpreter and loading my test code into a behavioral ROM is the right way to go by the way. Nor is fighting with the simulator interface to connect up a C program, but I may break down and try this..
Quick sketch of an answer (to the question I think you are asking! :-) though I may be off-beam...
To move the BFM subprograms into a reusable package, they need to be independent of the execution scope - that usually means a long parameter list for each of them. So using them in a testbench quickly gets tedious compared with the parameterless (or parameter-lite) versions you have now..
The usual workaround is to implement the BFM in a package, with long parameter lists.
Then write parameter-lite local equivalents (wrappers) in the execution scope, which simply call the package versions supplying all the parameters explicitly.
This is just boilerplate - not pretty but it does allow you to move the BFM into a package. These wrappers can be local to the testbench, to a process within it, or even to a subprogram within that process.
(The parameter types can be records for tidiness : these are probably declared in a third package, shared between BFM. TB, and synthesisable device under test...)
Thanks to overloading, there is no ambiguity between the local and BFM package versions, so the actual testbench remains as simple as possible.
Example wrapper function :
function cpu_read(address : unsigned) return slv_32 is
begin
return BFM_pack.cpu_read (
address => address,
rd_data_bus => tb_rd_data_bus,
wait => tb_wait_signal,
oe => tb_mem_oe,
-- ditto for all the signals constants variables it needs from the tb_ scope
);
end cpu_read;
Currently your test procedures require two extra signals on them, cpu_input_record and cpu_output_record. This is not so bad. It is not uncommon to just have these on all procedures that interact with the cpu and be done with it. So use hardware_cpu_read and not cpu_read. Add cpu_input_record, cpu_output_record to your configure_communication_bus and clear_all_packet_counters procedures and be done. Perhaps choose shorter names.
I do a similar approach, except I use only one record with resolved elements. To make this work, you need to initialize the record so that all elements are non-driving (ie: 'Z' for std_logic). To make this more flexible, I have created resolution functions for integer, time, and real. However, this only saves you one signal. Not a real huge win. Perhaps half way to where you think you want to be. But it is more work than what you are doing.
For VHDL-201X, we are working on syntax to allow parameters/ports automatically map to a identically named signal. This will get you to where you want to be with any of the approaches (yours, mine, or Brian's without the extra wrapper subprogram). It is posted here: http://www.eda.org/twiki/bin/view.cgi/P1076/ImplicitConnections. Given this, I would add the two records to your procedures and call it good enough for now.
Once you get by this problem, you seem to also be asking is how do I write separate tests using the same testbench. For this I use multiple architectures - I like to think of these as a Factory Class for concurrent code. To make this feasible, I separate the stimulus generation code from the rest of the testbench (typically: netlist connections and clock). My presentation, "VHDL Testbench Techniques that Leapfrog SystemVerilog", has an overview of this architecture along with a number of other goodies. It is available at: http://www.synthworks.com/papers/index.htm
You're definitely on the right track, in fact I have a variant like this (what you describe).
The catch is, now I build up a whole subroutine using the "parameter light" procedures, and those are what I want to put in a package to share and reuse. The problem is that any procedure pushed out to a package can't call to the parameter light procedures in the main vhdl file..
So what happens is we have one main vhdl file with all the common CPU hardware setup routines, and every designer's test code all in the same vhdl file..
Long story short, putting our test subroutines into separate files is really what I was hoping for..