Multiplexers¶
Multiplexers are generated by the Verilog HDL frontend for ?:
-expressions.
Multiplexers are also generated by the proc pass to map the decision trees from
RTLIL::Process objects to logic.
The simplest multiplexer cell type is $mux
. Cells of this type have a
WITDH
parameter and data inputs A
and B
and a data output Y
, all
of the specified width. This cell also has a single bit control input S
. If
S
is 0 the value from the input A
is sent to the output, if it is 1 the
value from the B
input is sent to the output. So the $mux
cell implements
the function Y = S ? B : A
.
The $pmux
cell is used to multiplex between many inputs using a one-hot select
signal. Cells of this type have a WIDTH
and a S_WIDTH
parameter and
inputs A
, B
, and S
and an output Y
. The S
input is
S_WIDTH
bits wide. The A
input and the output are both WIDTH
bits
wide and the B
input is WIDTH*S_WIDTH
bits wide. When all bits of S
are zero, the value from A
input is sent to the output. If the \(n\)‘th bit from S
is set, the value \(n\)‘th WIDTH
bits wide slice of
the B
input is sent to the output. When more than one bit from S
is set
the output is undefined. Cells of this type are used to model “parallel cases”
(defined by using the parallel_case
attribute or detected by an
optimization).
The $tribuf
cell is used to implement tristate logic. Cells of this type have
a WIDTH
parameter and inputs A
and EN
and an output Y
. The A
input and Y
output are WIDTH
bits wide, and the EN
input is one bit
wide. When EN
is 0, the output is not driven. When EN
is 1, the value
from A
input is sent to the Y
output. Therefore, the $tribuf
cell
implements the function Y = EN ? A : 'bz
.
Behavioural code with cascaded if-then-else- and case-statements usually results
in trees of multiplexer cells. Many passes (from various optimizations to FSM
extraction) heavily depend on these multiplexer trees to understand dependencies
between signals. Therefore optimizations should not break these multiplexer
trees (e.g. by replacing a multiplexer between a calculated signal and a
constant zero with an $and
gate).
- yosys> help $bmux¶
Binary-encoded multiplexer
Selects between ‘slices’ of A where each value of S corresponds to a unique slice.
- Properties:
- Simulation model (verilog)¶
1658module \$bmux (A, S, Y); 1659 1660 parameter WIDTH = 0; 1661 parameter S_WIDTH = 0; 1662 1663 input [(WIDTH << S_WIDTH)-1:0] A; 1664 input [S_WIDTH-1:0] S; 1665 output [WIDTH-1:0] Y; 1666 1667 wire [WIDTH-1:0] bm0_out, bm1_out; 1668 1669 generate 1670 if (S_WIDTH > 1) begin:muxlogic 1671 \$bmux #(.WIDTH(WIDTH), .S_WIDTH(S_WIDTH-1)) bm0 (.A(A[(WIDTH << (S_WIDTH - 1))-1:0]), .S(S[S_WIDTH-2:0]), .Y(bm0_out)); 1672 \$bmux #(.WIDTH(WIDTH), .S_WIDTH(S_WIDTH-1)) bm1 (.A(A[(WIDTH << S_WIDTH)-1:WIDTH << (S_WIDTH - 1)]), .S(S[S_WIDTH-2:0]), .Y(bm1_out)); 1673 assign Y = S[S_WIDTH-1] ? bm1_out : bm0_out; 1674 end else if (S_WIDTH == 1) begin:simple 1675 assign Y = S ? A[2*WIDTH-1:WIDTH] : A[WIDTH-1:0]; 1676 end else begin:passthru 1677 assign Y = A; 1678 end 1679 endgenerate 1680 1681endmodule
- yosys> help $bwmux¶
Bit-wise multiplexer
Equivalent to a series of 1-bit wide
$mux
cells.- Properties:
- Simulation model (verilog)¶
2027module \$bwmux (A, B, S, Y); 2028 2029 parameter WIDTH = 0; 2030 2031 input [WIDTH-1:0] A, B; 2032 input [WIDTH-1:0] S; 2033 output [WIDTH-1:0] Y; 2034 2035 genvar i; 2036 generate 2037 for (i = 0; i < WIDTH; i = i + 1) begin:slices 2038 assign Y[i] = S[i] ? B[i] : A[i]; 2039 end 2040 endgenerate 2041 2042endmodule
- yosys> help $demux¶
Demultiplexer i.e routing single input to several outputs based on select signal. Unselected outputs are driven to zero.
- Properties:
- Simulation model (verilog)¶
1733module \$demux (A, S, Y); 1734 1735 parameter WIDTH = 1; 1736 parameter S_WIDTH = 1; 1737 1738 input [WIDTH-1:0] A; 1739 input [S_WIDTH-1:0] S; 1740 output [(WIDTH << S_WIDTH)-1:0] Y; 1741 1742 genvar i; 1743 generate 1744 for (i = 0; i < (1 << S_WIDTH); i = i + 1) begin:slices 1745 assign Y[i*WIDTH+:WIDTH] = (S == i) ? A : 0; 1746 end 1747 endgenerate 1748 1749endmodule
- yosys> help $mux¶
Multiplexer i.e selecting between two inputs based on select signal.
- Properties:
- Simulation model (verilog)¶
1639module \$mux (A, B, S, Y); 1640 1641 parameter WIDTH = 0; 1642 1643 input [WIDTH-1:0] A, B; 1644 input S; 1645 output [WIDTH-1:0] Y; 1646 1647 assign Y = S ? B : A; 1648 1649endmodule
- yosys> help $pmux¶
Priority-encoded multiplexer
Selects between ‘slices’ of B where each slice corresponds to a single bit of S. Outputs A when all bits of S are low.
- Properties:
- Simulation model (verilog)¶
1691module \$pmux (A, B, S, Y); 1692 1693 parameter WIDTH = 0; 1694 parameter S_WIDTH = 0; 1695 1696 input [WIDTH-1:0] A; 1697 input [WIDTH*S_WIDTH-1:0] B; 1698 input [S_WIDTH-1:0] S; 1699 output reg [WIDTH-1:0] Y; 1700 1701 integer i; 1702 reg found_active_sel_bit; 1703 1704 always @* begin 1705 Y = A; 1706 found_active_sel_bit = 0; 1707 for (i = 0; i < S_WIDTH; i = i+1) 1708 case (S[i]) 1709 1'b1: begin 1710 Y = found_active_sel_bit ? 'bx : B >> (WIDTH*i); 1711 found_active_sel_bit = 1; 1712 end 1713 1'b0: ; 1714 1'bx: begin 1715 Y = 'bx; 1716 found_active_sel_bit = 'bx; 1717 end 1718 endcase 1719 end 1720 1721endmodule
- yosys> help $tribuf¶
A tri-state buffer. This buffer conditionally drives the output with the value of the input based on the enable signal.
- Properties:
- Simulation model (verilog)¶
1808module \$tribuf (A, EN, Y); 1809 1810 parameter WIDTH = 0; 1811 1812 input [WIDTH-1:0] A; 1813 input EN; 1814 output [WIDTH-1:0] Y; 1815 1816 assign Y = EN ? A : 'bz; 1817 1818endmodule