triggering event from default sequence to activate another sequence in test env - uvm

I have a default sequence set in the test (uvm_test) as:
uvm_config_db#(uvm_object_wrapper)::set(this, "sve.vs.main_phase", "default_sequence",main_vseq_c::type_id::get());
Unfortunately There is another sequence in the test_env which is being activated also on main_phase. called 'seq_seq_c'
How can I synchronize between the sequences? Can I use events in 'main_vseq_c' to trigger 'seq_seq_c'? and I can, how do I execute this?

You can create an uvm_event. The name of an uvm_event is unique, you can use uvm_event_pool to get the instance of the uvm_event with the same name. If an uvm_event of the name does not exist, uvm_event_pool will create one when get() is called the first time.
Both the main sequence and the other sequence get an uvm_event with the same name. The main sequence calls .wait_trigger() and the other sequence calls .trigger() of the uvm_event.

Related

What is the Spinnaker pipeline expression for the current stage?

I'm trying to write a Spinnaker pipeline expression that determines some criteria based on the current stage and its ancestors. Per the documentation, you can use the #root helper to get the current stage context; however, it doesn't appear there is any way to get the current stage.
For example, if you wanted to find out if the current stage has any ancestors that have a failure status, right now you have to know the stage name, which seems counter-intuitive given the existence of #root.
${ #stage("My Stage").ancestors().?[status.isFailure() && name != "My Stage"] }
I'd like to replace the #stage("My Stage") with something similar to #root however, again #root is the context object inside the stage, not the stage itself.
Note it also appears the Stage.ancestorsOnly() method is private at the moment so if you want to find only ancestors that have failed (or have some other criteria) you need to manually exclude the current stage. That's why I have the extra name comparison in there.
root and #this in SPEL are just aliases for when you need to reference the current object used in places like filters, I wouldn't get too caught up with it.
Maybe the right thing here is to add a few more values to the augmented context we evaluate SPEL against https://github.com/spinnaker/orca/blob/7de225679cf19cbcbfcfdbdcd08dc1962247f0fe/orca-core/src/main/java/com/netflix/spinnaker/orca/pipeline/util/ContextParameterProcessor.java#L90 to include values such as stage id so it would be easier to add helper functions like #currentStage() or #ancestorStaget() here https://github.com/spinnaker/orca/blob/fc87a8e99ec59a4e129646026987aa5adbde2d31/orca-core/src/main/java/com/netflix/spinnaker/orca/pipeline/expressions/ExpressionsSupport.java#L60
There are subtle issues here because stage expressions get evaluated before a stage runs so for static values like ancestors it should be ok, but for values like status the value you get will not be updated

Is Angular's foreach loop over an object asynchronous?

I read somewhere in the past that angular.foreach is asynchronous unlike looping over arrays which is synchronous. For a long time I was taking into account this and doing the necessary to avoid executing the code which comes after the loop before it's finishes all its iterations (by wrapping the angular.foreach inside an anonymous JavaScript function which calls a callback which will be executed once the loop finishes all iterations).
(function(callback){
angular.foreach(..)
callback();
})(callback)
But I had a conversation with a collegue who didn't agree that angular.foreach is asynchronous and I also couldn't find that information again which makes me confused now.
no. Take a look at the docs
Furthermore your code wouldn't work if foreach would be asynchronous.
If foreach would be async, the callback would be called immediately after calling foreach and foreach would be put onto the eventqueue which would execute it some time in the future.
Javascripts concurrency model does not have threads but instead uses an eventloop. This means every async operation is pushed onto the eventqueue and executed later.
Have a look into the MDN
There may be a scenario where you want to make code behave asynchronously.
I had a scenario where I used local storage to store an ad-hoc user selected collection of jobs that I wanted to perform the same operation on.
I had a web service call to convert a list of job names into a returned a collection of job objects. I initially tried using a
foreach loop inside the subscribe pf the service layer, that operated on the results.
Then I tried calling another method within the foreach loop that as it performed the operations removed the job name from local storage when the operation posted to the web service correctly.
The problem was on the second iteration I read the collection of names from local storage again - before the set to remove had completed.
There was a lot of manipulation of the job and object properties to create the parameters passed on the function call, so I ended up refactoring the code, creating a value object interface and stored the information in a value object array for the whole job collection I had returned. I included the index of the job too in the value object.
I introduced a BehaviourSubject property to the class.
During the restructuring, I just added an entry to the value object array collection within the forEach loop instead. At the end of the loop. I sent next(0) to the BehaviourSubject to start the ball rolling.
Each time a job name was removed from local storage, I converted service to return a Promise.
Then in the code after the service was called I put this code in the then part, behaviour subject.next(index from value object +1)
In the initialisation I set the behaviour subject up with a -1 value..
Then in the subscription to the BehaviourSubject class I ignored -1,
And when the index +1 was > length of value object collection called completion routine - which bounce app back to prior page.
When the index was between 0 and 1 less than collection size, I just called the method that had originally been in the forEach loop with the value object entry with the value object match the index of the behaviour subject.
By doing this I had converted the behaviour of the forEach into something asynchronous.

uvm_object_utils_begin fails set field after test set filed

For some reason my object at the creation time does not pick configuration passed by test. I don't see GET when I enable tracing, only SET.
I have object as following:
class top_env_cfg extends uvm_object;
int set_default_env = 1;
`uvm_object_utils_begin(top_env_cfg)
`uvm_field_int(set_default_env,UVM_DEFAULT);
`uvm_object_utils_end
function new(string name = "top_env_cfg");
super.new(name);
endfunction
endclass
In my test, inside the build_phase I am doing the following:
uvm_config_db#(int)::set(this, "*", "set_default_env" ,0);
In my environment in build_phase I am creating this object as:
env_cfg = top_env_cfg::type_id::create("env_cfg", this);
After creating this object the set_default_env still 1.
What may be wrong, and how I can debug this.
Thanks in advance.
The important thing to understand about the "automated retrieval of config_db resources" is that it does not actually happen automatically. This Verilab paper explains what happens under the hood, and I am quoting the relevant section here:
[...] one question that is often asked with respect to retrieving data is:
do you always have to explicitly call the get() function? The short
answer is that it depends. In the UVM, there are mechanisms to
automate the retrieval of data from the configuration database. In
order to have the resource automatically retrieved two things must
happen:
First, that resource has to be registered with the factory using the field automation macros.
Second, super.build_phase(phase) must be called in the build_phase() function.
The "automated" retrieval will happen when you call super.build_phase() from a uvm_component. In the case that you are referring to in your question, you have a uvm_object (you don't have a UVM build_phase), so you would need to explicitly perform a uvm_config get() call in order to retrieve the resource from the database.

Get response from sequence to control virtual sequence

I need to verify a function which will take an unknown number of cycles to complete. I can determine that it is done by reading some registers and comparing their values to a model.
I have a sequence extended from uvm_reg_sequence which does this checking. I need this sequence to run at the end of my virtual sequence, and if the check fails, loop back to the beginning of the virtual sequence to run some more cycles. I will repeat this until the check passes (or I hit some timeout).
What I think I need is a way for the virtual sequence to get a response from the checker sequence to control this loop. What is the recommended way for accomplishing this?
The simplest thing I can think of is a simple check_passed field inside your register sequence":
class some_reg_sequence extends uvm_reg_sequence;
bit check_passed;
task body();
some_reg.read();
if (<pass_condition>)
check_passed = 1;
endtask
endclass
The virtual sequence would just check this field after executing the register sequence:
class virtual_sequence extends uvm_sequence;
task body();
some_reg_sequence reg_sequence;
`uvm_create_on(reg_sequence, ...)
// do stuff
// ...
do
reg_sequence.start();
while (!reg_sequence.check_passed);
endtask
endclass
You can also implement a timeout by wrapping the do..while inside a fork...join_any, together with a wait statement.

Compare thread IDs using windows api

I'm working with windows api threads and I would like to compare thread IDs.
First I create a thread with CreateThread() and store the handle( HANDLE ) and ID ( LPDWORD ) that I get from the function.
Then I get the handle and id from the created thread using GetCurrentThread() and GetThreadId().
I always get different values for both handles and both IDs.
Is there a way to compare threads in a similar fashion as pthread?
I'm doing this to as a debug option to confirm correct execution. I have always gotten correct results from other libraries( pthread.h, threads.h) but not from windows api. It is not a critical problem but I would like to learn the procedure in winapi
Instead of using GetCurrentThread() and GetThreadId(), you can use GetCurrentThreadId() [http://msdn.microsoft.com/en-us/library/windows/desktop/ms683183%28v=vs.85%29.aspx].
As said before, don't use pseudo-HANDLE (returned by GetCurrentThread()) on another thread.
From what I know, there could several different HANDLE to one thread but ID should be an unique identifier.
GetCurrentThread() does not return a real handle. From MSDN:
Retrieves a pseudo handle for the calling thread.
...
A pseudo handle is a special constant that is interpreted as the current thread handle.
You cannot compare this value to the result of CreateThread(). If you are using this value in GetThreadId() from a different thread, you will also not get the ID you want.
You can use DuplicateHandle() on the pseudo handle to retrieve the real handle.

Resources