Blocking vs nonblocking assignment in Verilog: = and <=
Verilog has two procedural assignments. A blocking assignment, written =, takes effect immediately, so the next statement in the same block already sees the new value. A nonblocking assignment, written <=, reads its right-hand side now but updates the variable only at the end of the current time step, so every statement in the block sees the old values. That one difference decides whether a clocked block describes a chain of flip-flops or collapses into one. The rule most designers follow: use nonblocking (<=) in clocked blocks that describe flip-flops, and blocking (=) in combinational blocks.
What each one is right for
Nonblocking assignments model real flip-flops. On a clock edge every flip-flop samples its input at the same instant, before any of them changes, and <= gives exactly that: all right-hand sides are read with the old values, then all the registers update together, so the order of the statements does not matter and two always blocks on the same clock cannot race. Blocking assignments model a calculation done step by step, which is what combinational logic is: in an always @(*) block an intermediate result can be computed and then used on the next line. Mixing them up is a classic bug: blocking assignments in a clocked block make the result depend on statement order, and can make simulation disagree with the synthesized hardware.
See the difference in a live circuit
The live 4-bit shift register is the hardware that nonblocking code describes: four D flip-flops share one clock, and on each rising edge every bit moves one place, because each flip-flop takes its neighbour's value from before the edge. digiwleea's simulator works the same way, updating every flip-flop from the values just before the clock edge, so what you build matches what <= means. You build these circuits from transistors up, in the browser, and the lab can export a circuit to Verilog or VHDL. For the languages themselves, see Verilog vs VHDL and Verilog vs SystemVerilog.
Blocking and nonblocking side by side
| Blocking (=) | Nonblocking (<=) | |
|---|---|---|
| When the variable changes | Immediately | At the end of the time step |
| What the next statement sees | The new value | The old value |
| Statement order matters | Yes | No |
| Use for | Combinational always @(*) blocks | Clocked always @(posedge clk) blocks |
| Hardware it describes | Gates, evaluated in order | Flip-flops that all update on the edge |
The same two lines, two different circuits
// Nonblocking: a two-stage shift register
always @(posedge clk) begin
q1 <= d;
q2 <= q1; // reads the old q1
end
// Blocking: q1 and q2 both get d
always @(posedge clk) begin
q1 = d;
q2 = q1; // reads the new q1
end
The first block builds two flip-flops in a chain, so q2 follows d two clocks later. The second builds one, because q2 copies the q1 that was just written. Combinational blocks are the opposite case:
// Combinational logic: blocking, in order
always @(*) begin
t = a & b;
y = t | c;
end
No sign-up is needed to start: open the lab and place your first transistor, or read the free theory course. The account (and the AI tutor) are optional.
More comparisons: HDL, FPGA and chip design tools
See for yourself: build a logic gate from transistors in the simulator, then follow the path from sand to an 8-bit CPU.
Open the digiwleea lab →Frequently asked
What is the difference between blocking and nonblocking assignments in Verilog?
A blocking assignment (=) updates the variable immediately, so later statements in the block see the new value. A nonblocking assignment (<=) evaluates its right-hand side immediately but updates the variable at the end of the time step, so later statements still see the old value.
Why use nonblocking assignments for flip-flops?
Because all flip-flops on a clock sample their inputs at the same moment. With <=, every right-hand side is read before any register changes, so a chain such as q1 <= d; q2 <= q1; becomes two flip-flops in a row, whatever the statement order, and separate always blocks on the same clock cannot race.
What happens if I use blocking assignments in a clocked always block?
The statements run in order, so q1 = d; q2 = q1; gives q2 the new q1, which is d: the two flip-flops collapse into one. Reversing the two lines changes the result, and blocks that share a clock can race in simulation.
Should I use blocking assignments for combinational logic?
Yes. In an always @(*) block, blocking assignments let one line compute an intermediate value that the next line uses, just like the gates of a combinational circuit. Assign every output on every path, or synthesis infers a latch.
Can I mix blocking and nonblocking assignments in one always block?
The language allows it, but widely used coding guidelines say not to, because it makes the code hard to read and easy to get wrong. Keep clocked blocks nonblocking and combinational blocks blocking.
What are the VHDL equivalents?
A VHDL signal assignment (<=) updates when the process suspends, like a Verilog nonblocking assignment, and a variable assignment (:=) updates immediately, like a blocking one.