Specman -How to wait for an event to happen several times - wait

I have to events:
event clk_e is rise (smp.port_uart_clk$) #sim;
event async_16_clk_e is rise (smp.port_br_clk_16$) #sim;
*uart clk is faster than br_clk_16
update_int()#clk_e is {
while TRUE
{
if ((uart_env.uart_regs.uartis.rxmi | uart_env.uart_regs.uartis.txmi | uart_env.uart_regs.uartis.rtmi | uart_env.uart_regs.uartis.femi | uart_env.uart_regs.uartis.blmi | uart_env.uart_regs.uartis.rxoemi | uart_env.uart_regs.uartis.txoemi) == 1)
{
first of
{
{
wait true(smp.port_uart_int$ == 0);
message(LOW, "INTRP MON : Intrpt has occured");
};
{
message(LOW, "EXPECT INTERRUPT");
if (uart_env.uart_regs.uartis.rxmi == 1)
{
wait[10] #async_16_clk_e; --I want to wait 10 clocks of br_clk_16
}
else if (uart_env.uart_regs.uartis.txmi == 1)
{
wait[2] #tx_clk_e;
};
dut_error ("Interrupt should be asserted, but it's not");
--message(LOW, "INTRP MON : Intrpt has occured");
};
}; -- all of
};
wait;
};
};
For some reason I wait more than 10 clocks.
How can I wait 10 clocks of br_clk_16?

You are waiting for async_16_clk_e at the default sampling event of the TCM.
Try instead wait [10] * cycle#async_16_clk_e;

I suggest running it with 'trace events'. There might be issues like multiple ticks at the same simulation time, etc., which lead to counter-intuitive behavior. Also, try to convert "true(smp.port_uart_int$ == 0)" to a separate event, as it too can have sampling glitches with clk_e, tcm's sampling event.

Related

How do I set iterations for stage runs?

I am trying to setup a run in K6 with staged setup and rundown. I am trying to find out how to setup K6 so that it will start a new iteration of the run once the stages are complete. Do I simply include iterations in the stage block, or is there something else I need to do?
What you basically want is a given set of stages to repeat over prolonged period of time.
There are two solutions:
Just run the script in a loop in a bash/cmd/shell script - will have some pauses in between runs as k6 will need to initialize again. Additionally you will have multiple outputs but this might not be bad, see below
Have stages that are as many as you need. You can do it by hand or just script it inside the test script:
import http from "k6/http";
import { check, sleep } from "k6";
let stages = [// total 30 seconds
// Ramp-up from 1 to 5 VUs in 10s
{ duration: "10s", target: 5 },
// Stay at rest on 5 VUs for 5s
{ duration: "5s" },
// Ramp-down from 5 to 0 in 15s
{ duration: "15s", target: 0}
];
let final_stages = [];
// 30 seconds by 120 seconds is 3600 seconds or 1 hour
for (let i =0 ;i < 120; i++) {
final_stages = final_stages.concat(stages)
}
export let options = {
stages: final_stages,
discardResponseBodies: true
};
export function setup() {
console.log(JSON.stringify(options.stages));
}
export default function(testStart) {
// normal execution
let res = http.get("http://httpbin.org/");
check(res, { "status is 200": (r) => r.status === 200 });
}
I highly advise running k6 with --no-summary and maybe even --no-thresholds or just not using thresholds if the time it will be ran for will be great as you are probably going to run out memory just collecting data inside k6. This means that you probably should use some storage for the metrics like influxdb or even Load Impact's Insights. This of course might not be true in your case - you will have to check :).
Answer as I understood the question previously: "I want to have stages and then I want to do some concrete amount of iterations of the script instead of for a given duration as will happen with another stage"
The simple answer is no.
If you have stages, iterations and duration for a test are mutually
exclusive - only one of them will be taken into account. Look at the
end for possible work around.
Long answer:
If I understand correctly what you want is to have a bunch of stages
and then after all the stages have ran to have a few VUS which do a
given number of iterations. This is currently not supported and is
interesting to us (the k6 team) why you would need this.
Workaround(s): Currently I can think of two workarounds - both hacky:
If you don't need anything from the test in the later iterations make two tests and make a bash/shell/cmd script to run them one after
the other. This will have some pause in between the test runs and you
will have two outputs but will definitely be easier.
Make another stage after all the stages have finished with long enough duration to run all the iterations. Have a variable that you
record the beginning of the whole test - preferably in the setup and
then calculate when you reach the last stage. Run as many iterations
as you want and then sleep for the remaining of the test.
It's important to note that at this point there is no way to
communicate between VUs, so you will have to decide that when you have
10 VUs each will do 5 to get 50 iterations and maybe one VU will
finish much faster or later or something like that.
import http from "k6/http";
import { check, sleep } from "k6";
export let options = {
stages: [
// Ramp-up from 1 to 5 VUs in 10s
{ duration: "10s", target: 5 },
// Stay at rest on 5 VUs for 5s
{ duration: "5s" },
// run for some amount of time after that
{ duration: "15s"}
],
discardResponseBodies: true
};
export function setup() {
return Date.now();
}
let iter = 5; // how many iteration per VU should be done in the iterations part
export default function(testStart) {
// 15ms is the amount of time for the pre iterations phase
if (Date.now() - testStart > 15 * 1000) {
// "iterations part"
if (iter == 0) { // we have ran out of iterations to do
sleep(15000) // sleep for the duration of the phase
}
iter = iter - 1;
// debug log
console.log(__VU, __ITER, iter);
// the actual part you want to do
let res = http.get("http://httpbin.org/");
check(res, { "status is 200": (r) => r.status === 200 });
} else {
// normal execution
let res = http.get("http://httpbin.org/");
check(res, { "status is 200": (r) => r.status === 200 });
}
}
This obviously needs to be tailored to your case
and won't be exact, but once again it's much more interesting what you
want to do with it and why.
Sidenote:
During the discussion of the arrival rate based execution this
has been discussed and the current plan is this to be supported but
this work is probably at least a month a way from alpha/beta
capability as there is a lot of internal refactoring needed for
supporting everything we want to add along with it. You should
probably write an issue with your use case as to be taken into
consideration in the future.

Access last value from a SignalProducer when terminated

I have a signal producer, when it's terminated I would like to know if a value was sent, I only need the last one, seems so simple ...
let myProducer: SignalProducer<MyObject, MyError> = getMyProducer()
myProducer.on(terminated: {
// I need the last value here
// Or I need to know if value was never called
}).start()
I've tried to store the value in a local var :
let myProducer: SignalProducer<MyObject, MyError> = getMyProducer()
var myValue: MyObject?
myProducer.on(value: { value in
myValue = value
}, terminated: {
guard let value = myValue else {
// value was never called
return
}
// value was called
}).start()
But sometimes terminated is called while value has been called but myValue is still nil...
First, are you really sure that you want the terminated event?
Under normal conditions, an event stream ends with a completed event. Exceptions are failed when a failure has occurred and interrupted, when the observation was ended before the stream could complete normally (E.g. cancellation).
Second: Can your SignalProducer fail, and in the failure case, do you still want the last value sent before the failure?
If not, its as easy as using the take(last:) operator:
enum MyError: Error {
case testError
}
let (signal, input) = Signal<Int, MyError>.pipe()
let observer = Signal<Int, MyError>.Observer(
value: { print("value: \($0)") },
failed: { print("error: \($0)") },
completed: { print("completed") },
interrupted: { print("interrupted") }
)
signal
.take(last: 1)
.observe(observer)
input.send(value: 1) // Nothing printed
input.send(value: 2) // Nothing printed
input.send(value: 3) // Nothing printed
input.sendCompleted() // value 3 printed
I'm using a Signal here so I can manually send events to it just for demonstration, the same works for SignalProducer as well.
Note: If we send interrupted or a failed event, the last value 3 will not be sent because those to terminating events short circuit the normal flow.
If your SignalProducer can fail, and you still want to get the last value before the failure, you can use flatMapError to ignore the Error before the last operator:
signal
.flatMapError { _ in
return .empty
}
.take(last: 1)
.observe(observer)
my answer :
producer
.flatMapError { _ in SignalProducer<Value, NoError>.empty }
.collect()
startWithResult( { result in
case let .success(results):
done(with: results.last)
case let .failure(error):
() // should not happen as errors are flatmapped
})

Geb: Warn when a page takes longer than expected - Test Context in Page Object

We want to add some type of functionality that when a page takes longer than x seconds to load a warning is presented. We don't want that to throw a WaitTimeoutException, because the test can still execute cleanly, just longer than desired. We would still use the default timeout to throw our WaitTimeoutException after 20 seconds. This implies that x is less than 20. It's essentially a performance check on the page itself.
I've tried using the onLoad function:
void onLoad(Page previousPage) {
double warnSeconds = 0.001
LocalDateTime warnTime = LocalDateTime.now().plusMillis((int)(warnSeconds * 1000))
boolean warned = false
boolean pageReady = false
while(!warned && !pageReady) {
if(LocalDateTime.now() > warnTime) {
log.warn("${this.class.simpleName} took longer than ${warnSeconds} seconds to load")
warned = true
}
pageReady = js.exec('return document.readyState') == 'complete'
}
}
However:
"Sets this browser's page to be the given page, which has already been
initialised with this browser instance."
Any help would be great. Thanks.
______________________________________EDIT_______________________________________
Instead of using my own timer, used javascript window.performance. Now I'm looking to be able to access a variable in my test from my pages.
______________________________________EDIT_______________________________________
void onLoad(Page previousPage) {
def performance
//TODO system property page time
def pageTime = 8000
if (browser.driver instanceof InternetExplorerDriver) {
performance = js.exec('return JSON.stringify(window.performance.toJSON());')
} else {
performance = js.exec('return window.performance || window.webkitPerformance || window.mozPerformance ' +
'|| window.msPerformance;')
}
int time = performance['timing']['loadEventEnd'] - performance['timing']['fetchStart']
if (time > pageTime) {
String errorMessage = "${this.class.simpleName} took longer than ${pageTime} milliseconds " +
"to load. Took ${time} milliseconds."
log.error(errorMessage)
//TODO Soft Assert
}
}
New chunk of code to actually get the correct performance data instead of using my own timer. Now where I have //TODO Soft Assert, I have an object in my test that I want to access from my Page Object, but have no context. How can I get context?

Simple Timer in Meteor JS

I am creating a simple countdown timer for a game. I am using CoffeeScript and Meteor. I have a Handlebars "Timer" template with a {{time}} expression.
Here is the code:
clock = 10
timeLeft = () ->
if clock > 0
clock--
else
"That's All Folks"
Meteor.clearInterval(interval)
interval = Meteor.setInterval(timeLeft, 1000)
if Meteor.isClient
Template.timer.time = interval
The above code just gives me a static display of 8 or 6 instead of the countdown timer.
If I add a few console.log statements I can see it work as designed in the terminal.
clock = 10
timeLeft = () ->
if clock > 0
clock--
console.log clock
else
console.log "That's All Folks"
Meteor.clearInterval(interval)
interval = Meteor.setInterval(timeLeft, 1000)
if Meteor.isClient
Template.timer.time = interval
If you want to update a value in handlebars you need to use Session so that its reactive, otherwise the Templating system won't be aware of when to update it in the ui. Also you passed the template a handler thats the handle instead of the timer value.
Using the below, I've used Session to pass this data through to handlebars.
clock = 10
timeLeft = ->
if clock > 0
clock--
Session.set "time", clock
console.log clock
else
console.log "That's All Folks"
Meteor.clearInterval interval
interval = Meteor.setInterval(timeLeft, 1000)
if Meteor.isClient
Template.timer.time = ->
Session.get "time"
Also in javascript in case anyone else wants this:
var clock = 10;
var timeLeft = function() {
if (clock > 0) {
clock--;
Session.set("time", clock);
return console.log(clock);
} else {
console.log("That's All Folks");
return Meteor.clearInterval(interval);
}
};
var interval = Meteor.setInterval(timeLeft, 1000);
if (Meteor.isClient) {
Template.registerHelper("time", function() {
return Session.get("time");
});
}
In essence you tell Session the time value, and when its updated it tells the templating system to redraw with the updated time value.

Capturing Cmd-C (or Ctrl-C) keyboard event from modular Flex application in browser or AIR

It seems that it is impossible to capture the keyboard event normally used for copy when running a Flex application in the browser or as an AIR app, presumably because the browser or OS is intercepting it first.
Is there a way to tell the browser or OS to let the event through?
For example, on an AdvancedDataGrid I have set the keyUp event to handleCaseListKeyUp(event), which calls the following function:
private function handleCaseListKeyUp(event:KeyboardEvent):void
{
var char:String = String.fromCharCode(event.charCode).toUpperCase();
if (event.ctrlKey && char == "C")
{
trace("Ctrl-C");
copyCasesToClipboard();
return;
}
if (!event.ctrlKey && char == "C")
{
trace("C");
copyCasesToClipboard();
return;
}
// Didn't match event to capture, just drop out.
trace("charCode: " + event.charCode);
trace("char: " + char);
trace("keyCode: " + event.keyCode);
trace("ctrlKey: " + event.ctrlKey);
trace("altKey: " + event.altKey);
trace("shiftKey: " + event.shiftKey);
}
When run, I can never get the release of the "C" key while also pressing the command key (which shows up as KeyboardEvent.ctrlKey). I get the following trace results:
charCode: 0
char:
keyCode: 17
ctrlKey: false
altKey: false
shiftKey: false
As you can see, the only event I can capture is the release of the command key, the release of the "C" key while holding the command key isn't even sent.
Has anyone successfully implemented standard copy and paste keyboard handling?
Am I destined to just use the "C" key on it's own (as shown in the code example) or make a copy button available?
Or do I need to create the listener manually at a higher level and pass the event down into my modular application's guts?
I did a test where I listened for key up events on the stage and noticed that (on my Mac) I could capture control-c, control-v, etc. just fine, but anything involving command (the  key) wasn't captured until I released the command key, and then ctrlKey was false (even though the docs says that ctrlKey should be true for the command key on the Mac), and the charCode was 0. Pretty useless, in short.
Another incredibly annoying thing that I just realized is that ctrl-c can't be captured by event.ctrlKey && event.keyCode = Keyboard.C (or ...event.charCode == 67), instead you have to test for charCode or keyCode being 3. It kind of makes sense for charCode since ctrl-c is 3 in the ASCII table, but it doesn't make sense for keyCode, which is supposed to represent the key on the keyboard, not the typed character. The same goes for all other key combos (because every ctrl combo has an ASCII equivalent).
Edit Found a bug in the Flex bug system about this: https://bugs.adobe.com/jira/browse/FP-375
I've found one workaround to this one based on the capture sequence. When you press Cmd+A, for example, the sequence is:
type: KEY_DOWN, keyCode 15
type: KEY_UP, keyCode 15
type: KEY_DOWN, keyCode 65
So everytime you get keyCode 15 down and then up and the next capture is down you can assume that the user pressed the key combination. My implementation end up like this:
protected var lastKeys:Array;
this.stage.addEventListener(KeyboardEvent.KEY_DOWN, keyHandler, false, 0, true);
this.stage.addEventListener(KeyboardEvent.KEY_UP, keyHandler, false, 0, true);
private function getCmdKey(ev:KeyboardEvent):Boolean {
this.lastKeys.push(ev);
this.lastKeys = this.lastKeys.splice(Math.max(0, this.lastKeys.length-3), 3);
if (this.lastKeys.length < 3) return false;
if (ev.keyCode != 15 && ev.type == KeyboardEvent.KEY_UP) {
var firstKey:KeyboardEvent = this.lastKeys[0] as KeyboardEvent;
var secondKey:KeyboardEvent = this.lastKeys[1] as KeyboardEvent;
if (firstKey.keyCode == 15 && firstKey.type == KeyboardEvent.KEY_DOWN &&
secondKey.keyCode == 15 && secondKey.type == KeyboardEvent.KEY_UP) {
return true;
}
}
return false;
}
private function keyHandler(ev:KeyboardEvent):void {
var cmdKey:Boolean = this.getCmdKey(ev.clone() as KeyboardEvent);
var ctrlKey:Boolean = ev.ctrlKey || cmdKey;
if (ctrlKey) {
if (ev.keyCode == 65) {
// ctrl + "a"-- select all!
}
}
}
For me, the following works:
private var _ctrlHoldFlag:Boolean = false;
// Do something if CTRL was held down and C was pressed
// Otherwise release the ctrl flag if it was pressed
public function onKey_Up(event:KeyboardEvent):void {
var keycode_c:uint = 67;
if (_ctrlHoldFlag && event.keyCode == keycode_c)
{
//do whatever you need on CTRL-C
}
if (event.ctrlKey)
{
_ctrlHoldFlag = false;
}
}
// Track ctrl key down press
public function onKey_Down(event:KeyboardEvent):void
{
if (event.ctrlKey)
{
_ctrlHoldFlag = true;
}
}

Resources