In the previous tutorial we learned the main differences between signals and variables. We learned that signals have a broader scope than variables, which are only accessible within one process. So how can we use signals for communication between several processes?
We have already learned to use
wait; to wait infinitely, and
wait for to wait for a specific amount of time. There exist two more types of wait statements in VHDL.
This blog post is part of the Basic VHDL Tutorials series.
The Wait On statement will pause the process until one of the specified signals change:
wait on <signal_name1>, <signal_name2> ...;
The Wait Until statement will pause until an event causes the condition to become true:
wait until <condition>;
In fact, Wait On, Wait Until and Wait For can be combined:
wait on <signal_name1> until <condition> for <time_value>;
This example will pause for 10 nanoseconds, or until
signal1 changes and
signal2 is equal to
wait on signal1 until signal2 = signal3 for 10 ns;
In this video tutorial we will learn how to use the Wait On and Wait Until statements for inter-process communication in VHDL:
The final code we created in this tutorial:
entity T07_WaitOnUntilTb is end entity; architecture sim of T07_WaitOnUntilTb is signal CountUp : integer := 0; signal CountDown : integer := 10; begin process is begin CountUp <= CountUp + 1; CountDown <= CountDown - 1; wait for 10 ns; end process; process is begin wait on CountUp, CountDown; report "CountUp=" & integer'image(CountUp) & " CountDown=" & integer'image(CountDown); end process; process is begin wait until CountUp = CountDown; report "Jackpot!"; end process; end architecture;
The output to the simulator console when we pressed the run button in ModelSim:
VSIM 2> run # ** Note: CountUp=1 CountDown=9 # Time: 0 ns Iteration: 1 Instance: /t07_waitonuntiltb # ** Note: CountUp=2 CountDown=8 # Time: 10 ns Iteration: 1 Instance: /t07_waitonuntiltb # ** Note: CountUp=3 CountDown=7 # Time: 20 ns Iteration: 1 Instance: /t07_waitonuntiltb # ** Note: CountUp=4 CountDown=6 # Time: 30 ns Iteration: 1 Instance: /t07_waitonuntiltb # ** Note: CountUp=5 CountDown=5 # Time: 40 ns Iteration: 1 Instance: /t07_waitonuntiltb # ** Note: Jackpot! # Time: 40 ns Iteration: 1 Instance: /t07_waitonuntiltb # ** Note: CountUp=6 CountDown=4 # Time: 50 ns Iteration: 1 Instance: /t07_waitonuntiltb # ** Note: CountUp=7 CountDown=3 # Time: 60 ns Iteration: 1 Instance: /t07_waitonuntiltb # ** Note: CountUp=8 CountDown=2 # Time: 70 ns Iteration: 1 Instance: /t07_waitonuntiltb # ** Note: CountUp=9 CountDown=1 # Time: 80 ns Iteration: 1 Instance: /t07_waitonuntiltb # ** Note: CountUp=10 CountDown=0 # Time: 90 ns Iteration: 1 Instance: /t07_waitonuntiltb # ** Note: CountUp=11 CountDown=-1 # Time: 100 ns Iteration: 1 Instance: /t07_waitonuntiltb
The first process increments the
CountUp counter and decrements the
CountDown counter. They are updated simultaneously. Although the signal assignments of the two signals are on different lines in the process, assigned signal values only become effective when the program hits a Wait statement. The process performs this operation at the start of the simulation, and then every 10 nanoseconds.
The second process’ first line is
wait on CountUp, CountDown;. The program will wait at this line until one or both of the signals change. As we can see from the printout, this happens at 0 ns simulation time when the counters are changed for the first time, and every time they change after that.
The third process’ first line is
wait until CountUp = CountDown;. The program will wake up every time one of the two signals change, just like the first process did. But it will only continue if the expression evaluates to
true, otherwise it will go back to sleep. As we can see from the printout, “Jackpot!” is only printed once, at 40 ns when both counters have the same value.
- Wait On will wait until one of the signals change
- Wait Until will wake up if one of the signals change, but will only continue if the expression is
- Wait On, Wait Until and Wait For can be combined
9 thoughts on “How to use Wait On and Wait Until in VHDL”
Hello Jonas. I’m loving your tutorials for vhdl so far.
I have a question about though. could your explain why did you create multiple processes?
Nice to hear from you!
The first process is solely for changing the counter signals. It provides input to the other processes.
The other two “wait” statements each have their own processes because that’s the only way they could both be waiting at the same time. I wanted to show how “wait on” and “wait until” works, and also introduce you to some of the parallel features of VHDL.
It’s just a demo, the code doesn’t do anything useful. Although, it is common to have multiple processes waiting on the same signal. For example on the clock signal.
Good Job Jonas… effective and practical way to learn VHDL coding at no cost.
Thank you for the nice words. Perhaps you would be interested in the premium VHDL and FPGA course that I am creating. You can read more about it here:
HI Jonas, this is just part of my project
the Quartus II gives me an error when I try to use …Wait for…
Error (10533): VHDL Wait Statement error at DE0_TOP.vhd(105): Wait Statement must contain condition clause with UNTIL keyword
this is part of a test equipment system I inherited for my shop and only have the file (quartus diagram) and the FPGA, I’m new using these devices, electronic engineer but never use it before, really desperate to get it running, can you help me?
I think your DE0_TOP module is not really the top module of your design. The code looks more like part of a testbench. The
wait for (500 ms);line is not synthesizable.
And the second process won’t compile because it lacks a sensitivity list or a Wait statement. Every process must have either a sensitivity list or a Wait statement.
Maybe you should check out my article and video about it:
Finally, it may be that you are trying to synthesize the testbench in Quartus. Setting the testbench as the top module is a typical newbie error that will produce such errors.
Great tutorial, thanks for putting all this together.
Quick question; after running simulation, in the output to the sim console, I only get this:
# ** Note: CountUp=1CountDown=9
# Time: 0 ps Iteration: 1 Instance: /t07_waitonuntiltb
Only one iteration.
It looks like the simulation is still starting because we can see the first printout at 0 ps. Are you running the simulation for long enough? More than 0 ps?
Try to start the simulation from the command prompt and run it for 100 ns like this:
run 100 ns