Question

I have written a simulation process that sets or changes signals sequentially as required, I use wait statements normally to wait certain time intervals or wait on signal assignments, but that is true only when I know when a signal should be coming, an example:

    reset      <= '1';
    write      <= '0';
    read       <= '0';
    wait for 25 ns;
    reset      <= '0';
    chipselect <= '1';
    wait until clk = '1';

but now I need to do something different, I have a signal that is normally 0, and I need to pause simulation stimulus whenever it is turned to 1. the signal however is not timed. meaning I cannot do it with a simple wait statement because the simulation will wait for it only at a certain time. I want that effect to happen at all times. how to do something like this?

Was it helpful?

Solution

Based on the description, I understand that you want to pause stimuli generation based on a signal, so stimuli time is extended corresponding to the time of the pause.

For this a signal with the active time (named active_time below) can be created, and stimuli can then be generated based on this time. The active time is only running when the active_stimuli is TRUE.

A support procedure (named active_wait_for below) corresponding to wait for can then be created to wait for the requested amount of active time, for use in the stimuli generation process.

Suggestion for code:

architecture syn of tb is

  -- Active declarations
  signal   active_stimuli    : boolean := TRUE;
  constant ACTIVE_RESOLUTION : time := 1 ps;
  signal   active_time       : time := 0 ps;

  -- Wait procedure for active delay
  procedure active_wait_for(delay : time) is
    variable active_time_start_v : time;
  begin
    active_time_start_v := active_time;
    if delay > 0 ps then
      wait until active_time >= active_time_start_v + delay;
    end if;
  end procedure;

  -- Stimuli signal
  signal stimuli_a : std_logic;
  signal stimuli_b : std_logic;

begin

  -- Active time generation
  process is
  begin
    wait for ACTIVE_RESOLUTION;
    if active_stimuli then
      active_time <= active_time + ACTIVE_RESOLUTION;
    else  -- Save execution time in loop by wait until
      wait until active_stimuli;
    end if;
  end process;

  -- Stimuli generation
  process is
  begin
    stimuli_a <= '0';
    stimuli_b <= '0';
    wait until active_time >= 2 ns;
    stimuli_a <= '1';
    active_wait_for(3 ns);
    stimuli_b <= '1';
    wait;
  end process;
...

Waveform showing operation is below:

enter image description here

Note that polarity is different than the signal in the question, but naming was clearer with this polarity.

OTHER TIPS

Some ideas for "pausing" a stimulus process on an interrupt-type signal:

  1. Rewrite the stimulus as a clocked process (a state machine, for example) and use the interrupt as a clock enable. This may be a pain, though.

  2. Maybe easier, whenever you wait, wait something like this:

    wait until clk = '1';
    if interrupt = '1' then
      wait until interrupt = '0';
      wait until clk = '1';
    end if;
    

    or if it's not a synchronous wait:

    wait for 100 ns;
    if interrupt = '1' then
      wait until interrupt = '0';
    end if;
    

    You could, of course, write a procedure to make these easier. There may be simpler/more elegant ways to code those, but what I wrote should work.

Is this what you want:

process (start) begin
    if rising_edge(start) then
        -- Respond to start signal rising
    end if;
end process;

There is nothing stopping your from writing another process in your testbench/simulation to wait for that other condition to happen. An example of when you might want to do this is when you are simply counting the number of events of a certain condition.

For example:

Signal_Waiter : process(interrupt)
begin
   if rising_edge(interrupt) then
      -- do stuff here such as increment a counter
   end if;
end process;

Since this process is completely independent from your "stimulus" section of code, it is always ready to wakeup and process. In this case, it will wake up whenever the signal interrupt changes.

Be careful if you are driving stimulus signals from the separate process, because you can't have two processes driving the same signal. If you need feedback to your main control process, you could do that with a signal or a shared variable.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top