#import "../src/lib.typ": get_image_by_id = The Tiny Tapeout Multiplexer == Overview The Tiny Tapeout Multiplexer distributes a single set of user IOs to multiple user designs. It is the backbone of the Tiny Tapeout chip. It has the following features: - 10 dedicated inputs - 8 dedicated outputs - 8 bidirectional outputs - Supports up to 512 user designs (32 mux units, each with up to 16 designs) - Designs can have different sizes. The basic unit is called a tile, and each design can occupy up to 16 tiles. == Operation The multiplexer consists of three main units: 1. The controller $dash.em$ used to set the address of the active design 2. The spine $dash.em$ a bus that connects the controller with all the mux units 3. Mux units $dash.em$ connects the spine to individual user designs === The Controller The mux controller has 3 input lines: #align(center)[ #table( columns: 2, rows: 4, table.header( [Input], [Description] ), `ena`, [Sent as-is (buffered) to the downstream mux units], `sel_rst_n`, [Resets the internal address counter to 0 (active low)], `sel_inc`, [Increments the internal address counter by 1] ) ] It outputs the address of the currently selected design on the `si_sel` port of the spine (see below). For instance, to select the design at address 12, you need to pulse `sel_rst_n` low, and then pulse `sel_inc` 12 times: #figure( caption: [Mux signals for activating the design at address 12], align(center, get_image_by_id("images", "mux_address_select_waveform")) ) #figure( caption: [Mux Diagram], align(center, get_image_by_id("images", "mux_diagram", height: 55%)) ) #figure( caption: [Mux Controller Diagram], align(center, get_image_by_id("images", "mux_controller")) ) Internally, the controller is just a chain of 10 D-flip-flops. The `sel_inc` signal is connected to the clock of the first flip-flop, and the output of each flip-flop is connected to the clock of the next flip-flop. The `sel_rst_n` signal is connected to the reset of all flip-flops. The following Wokwi project demonstrates this setup: #link("https://wokwi.com/projects/36434780766")[wokwi.com/projects/36434780766]. It contains an Arduino Nano that decodes the currently selected mux address and displays it on a 7-segment display. Click on the button labeled `RST_N` to reset the counter, and click on the button labeled `INC` to increment the counter. === The Spine The controller and all muxes are connected together through the spine. The spine has the following signals going to it: *From controller to mux*: - `si_ena` $dash.em$ the `ena` input - `si_sel` $dash.em$ selected design address (10 bits) - `ui_in` $dash.em$ user clock, user `rst_n`, user_inputs (10 bits) - `uio_in` $dash.em$ bidirectional I/O inputs (8 bits) *From mux to controller*: - `uo_out` $dash.em$ user outputs (8 bits) - `uio_oe` $dash.em$ bidirectional I/O output enable (8 bits) - `uio_out` $dash.em$ bidirectional I/O outputs (8 bits) The only signal which is actually generated by the controller is `si_sel` (using `sel_rst_n` and `sel_inc`, as explained above). The other signals are just going through from/to chip I/O pads. === The Multiplexer Each mux branch is connected to up to 16 designs. It also has 5 bits of a hard-coded address (each unit gets assigned a different address, based on its position on the die). The mux implements the following logic: If `si_ena` is 1, and `si_sel` matches the mux address, we know the mux is active. Then, it activates the specific user design port that matches the remaining bits of `si_sel`. *For the active design*: - `clk`, `rst_n`, `ui_in`, `uio_in` are connected to the respective pins coming from the spine (through a buffer) - `uo_out`, `uio_oe`, `uio_out` are connected to the respective pins going out to the spine (through a tristate buffer) *For all others, inactive designs* (including all designs in inactive muxes): - `clk`, `rst_n`, `ui_in`, `uio_in` are all tied to zero - `uo_out`, `uio_oe`, `uio_out` are disconnected from the spine (the tristate buffer output enable is disabled) == Pinout // this pinout table must be populated from within the datasheet template itself