An assign statement and a combinational always block describe pure logic. A synthesis tool builds gates and multiplexers from them, with no storage.
A combinational block names its inputs implicitly with always @*. Simulation and synthesis agree when every path through the block assigns every output.
Complete assignment means each output gets a value on every path. An if with an else, and a case covering every value with a default, both qualify.
Code shape | Every path assigns | Hardware |
|---|---|---|
| Yes | 2:1 multiplexer |
| Yes | Multiplexer |
| Yes | Multiplexer or gates |
| No | Latch (next lesson) |
The script below reads one 2:1 multiplexer and runs the generic front end. It pins exactly one $mux with no $dlatch and no $dff.
read_verilog <<EOV
module mux_top (
input wire a,
input wire b,
input wire sel,
output reg y
);
always @* begin
if (sel)
y = b;
else
y = a;
end
endmodule
EOV
hierarchy -check -top mux_top
proc
select -assert-count 1 t:$mux
select -assert-none t:$dlatch
select -assert-none t:$dff
log PASS: complete branch infers one mux with no latch and no flopif has an else and assigns the output in both branches. Which cell does the tool infer?A $mux. Every path assigns the output, so no storage is needed.
else. What changes in the netlist?A $dlatch appears. The missing path must hold the old value, which is exactly what a latch does.