blob: 60b16846695a48732fdc1cf7c5db26cad4a945bb [file] [log] [blame]
.. _register-file:
Register File
=============
Ibex has either 31 or 15 32-bit registers if the RV32E extension is disabled or enabled, respectively.
Register ``x0`` is statically bound to 0 and can only be read, it does not contain any sequential logic.
There are two flavors of register file available, both having their own benefits and trade-offs.
Flip-Flop-Based Register File
-----------------------------
The flip-flop-based register file uses regular, positive-edge-triggered flip-flops to implement the registers.
This makes it the **first choice for FPGA synthesis** or when simulating the design using Verilator.
To select the flip-flop-based register file, make sure to use the source file ``ibex_register_file_ff.sv`` in your project.
Latch-Based Register File
-------------------------
The latch-based register file uses level-sensitive latches to implement the registers.
This allows for significant area savings compared to an implementation using regular flip-flops and thus makes the latch-based register file the **first choice for ASIC implementations**.
Simulation of the latch-based register file is possible using commercial tools.
.. note:: The latch-based register file cannot be simulated using Verilator.
The latch-based register file can also be used for FPGA synthesis, but this is not recommended as FPGAs usually do not well support latches.
To select the latch-based register file, make sure to use the source file ``ibex_register_file_latch.sv`` in your project.
In addition, a technology-specific clock gating cell must be provided to keep the clock inactive when the latches are not written.
This cell must be wrapped in a module called ``prim_clock_gating``.
For more information regarding the clock gating cell, checkout :ref:`getting-started`.
.. note:: The latch-based register file requires the gated clock to be enabled in the cycle after the write enable ``we_a_i`` signal was set high.
This can be achieved by latching ``we_a_i`` in the clock gating cell during the low phase of ``clk_i``.
The resulting behavior of the latch-based register file is visualized in :numref:`timing`.
The input data ``wdata_a_i`` is sampled into a flip-flop-based register ``wdata_a_q`` using ``clk_int``.
The actual latch-based registers ``mem[1]`` and ``mem[2]`` are transparent during high phases of ``mem_clk[1]`` and ``mem_clk[2]``, respectively.
Their content is sampled from ``wdata_a_q`` on falling edges of these clocks.
.. wavedrom::
:name: timing
:caption: Latch-based register file operation
{"signal":
[
{"name": "clk_i", "wave": "hlhlhlhl"},
{"name": "we_a_i", "wave": "0.1...0."},
{"name": "waddr_a_i", "wave": "xx=.=.xx", "data": ["1","2"]},
{"name": "wdata_a_i", "wave": "xx=.=.xx", "data": ["Data1","Data2"]},
{"name": "clk_int", "wave": "0...HlHl"},
{"name": "wdata_a_q", "wave": "xxxx=.=.", "data": ["Data1", "Data2"]},
{"name": "mem_clk[1]", "wave": "0...hL.."},
{"name": "mem[1]", "wave": "xxxx=...", "data": ["Data1"]},
{"name": "mem_clk[2]", "wave": "0.....hL"},
{"name": "mem[2]", "wave": "xxxxxx=.", "data": ["Data2"]}
],
"config": { "hscale": 2 }
}