2

I have a SystemVerilog task I am trying to port to SystemC. The body of the task simply waits on a boolean expression and then pushes onto a queue. The SystemC wait mechanism doesn't work quite the same way though, it will only wait on time or events.

So I'm wondering what is the minimum length of cycles/time that SystemVerilog wait() will wait before re-testing the boolean expression. In other words, how often or what drives re-testing of boolean expressions in SV wait()?

If the answer is simply once every cycle, which I hope and expect but can not confirm, then the solution is easy.

Here is the code, with some things renamed and simplified to make more sense out of context:

    virtual task put(input cls_item item);
        wait (queuecount < queuemax);
        push_back(item);
    endtask
Rich
  • 1,165
  • 1
  • 15
  • 29
  • Can you post the code in question? SystemVerilog has a concept of cycles but they are not related to wait() –  Nov 08 '12 at 16:30

2 Answers2

3

From the LRM:

9.4.3 Level-sensitive event control

The execution of a procedural statement can also be delayed until a condition becomes true. This is accomplished using the wait statement, which is a special form of event control. The nature of the wait statement is level-sensitive, as opposed to basic event control (specified by the @ character), which is edge-sensitive.

The wait statement shall evaluate a condition; and, if it is false, the procedural statements following the wait statement shall remain blocked until that condition becomes true before continuing.

Basically, you can think of wait(<boolean expression>) as checking the expression continuously. Once the expression is true the wait will unblock and the execution of the sequential code will continue.

If the expression is true when the wait() is first encountered, it will not wait at all.

dwikle
  • 6,820
  • 1
  • 28
  • 38
1

I do agree you can think of wait(expression) as always checking the condition expression continuously. That's thought for the designer, but a computer program can not be designed at that way or it wastes CPU time in the condition checking loop.

In SystemVerilog, its compiler might model the boolean expression as an event. When the execution runs to wait() and condition is false, the simulation kernel suspend the current thread and execute others. In the simulation, every time queuecount or queuemax has been changed, the condition is re-computed using < operator. Once the condition is satisfied, the event is triggered and then the waiting thread is re-schedule and prepared to resume its execution.

In SystemC, because it's C/C++ world plus an event driven hardware modeling library, that's the natural of C/C++ you write a function like function(<condition expression>). However, after C/C++ compilation like GCC, actually the program will first evaluate the <condition expression> then pass as the argument to the function. It is the software way. Such that, in wait() function, it can only see true or false or 0/1, it does know about what you are waiting for. It does not make any sense for the real intent of wait() in hardware modeling. Therefore, the wait() can only accepts event argument in SystemC. For example,

wait (event);       // waiting for the event
wait (a_signal);    // signal interface has value_changed_event, posedge_event, negedge_event
wait (10, SC_NS);   // simulation time is also an event in SC kernel

If you would like to model the same condition for wait() like SystemVerilog, you have to manually write the detail of events. Following is a proof of concept pseudo code, you can find examples from SystemC or sc_fifo class.

    sc_event           waiting_event;

    void put( ... ) {
        while (!(queuecount < queuemax))
            wait( waiting_event);
        push_back(...);
    }

    void get( ... ) {
        ...
        notify_queue_available();
    }

    void notify_queue_available() {
        if (queuecount < queuemax)
            waiting_event.notify();
    }
jclin
  • 2,449
  • 1
  • 21
  • 27
  • Thanks for the detailed response. One thing I overlooked previously is that in SV this kind of wait() is blocking. In other words, the task (or thread in more SystemC/C terms) that calls this task won't regain control until the wait is finished. This means I could implement an equivalent in SystemC with a kind of blocking spinlock. Something like: while (!(queuecount < queuemax) sleep(1000); Do you agree, or do I misunderstand the nature of SV wait()? – Rich Nov 09 '12 at 12:28
  • No, sleep doesn't give control to other threads or processes in SYstemC. It will cause infinite loop because those two variables wont be changed. – jclin Nov 10 '12 at 11:19