Advanced Feature: Memory Generation
Relevant source files
The following files were used as context for generating this wiki page:
The regif tool provides functionality for generating register interfaces that behave like memory elements, specifically focusing on FIFO (First-In, First-Out) interfaces. While the project documentation lists a generic "mem" scenario, the concrete implementation available in the codebase is centered around the FIFO_IF feature. This feature allows users to define a register as a write-only FIFO interface, which generates a corresponding write-push signal in the RTL.
This page details the FIFO_IF feature, explaining how to use it, the Verilog code it generates, and the underlying Python implementation.
FIFO Interface (FIFO_IF) Generation
The primary memory-related feature implemented in regif is the generation of a FIFO interface. This is activated by a specific keyword in the input Excel file and results in specialized Verilog code for handling write operations as FIFO pushes.
Sources: regif.py:10-12, 408
Activation and Generation Flow
To use this feature, the user must include the string "FIFO_IF" in the register's description column within the input Excel spreadsheet. The regif script detects this keyword during parsing and flags the register as a FIFO interface. This triggers a different code generation path for the register's write logic.
Sources: regif.py:408
The following diagram illustrates the process from parsing the Excel file to generating the final Verilog code for a FIFO interface.
This diagram shows the conditional logic within regif for generating FIFO interface RTL.
Sources: regif.py:408, 415-417, 654-658
Generated Verilog Logic
When a register is marked with FIFO_IF, the tool generates a specific Verilog block instead of the standard register write logic. This block includes:
- A
wirenamed{reg_name}_push. - An
assignstatement that asserts this_pushsignal when a write operation (bmi_wr) occurs at the register's address. - Commented-out
assignstatements that serve as a template for connecting FIFO read data to the register fields.
The generated code is based on the FIFO_PUSH_L4 and FIFOMAP templates.
FIFO_PUSH_L4 Template:
//-------------------------------------------------------------------
//{addr} : {reg_name:{reg_align}} {if_Comment}
wire {reg_name}_push ;
assign {reg_name}_push = bmi_wr && (bmi_addr==`{reg_name});
{fifo_filed_assign}\n
Sources: regif.py:117-122
FIFOMAP Template:
This template is used to generate the commented-out field mappings.
//assign {pn:20} = fifo_rdata{section:8} ;
Sources: regif.py:101
For a register with FIFO_IF, the _push signal becomes an output of the _regif module, intended to be used by an external FIFO controller as a write enable/push signal.
Sources: regif.py:882-886
Implementation Details
The FIFO generation logic is primarily handled within the Reg, RegFields, and Field classes.
The following diagram shows the class relationships for this feature.
This class diagram highlights the key classes and methods involved in the FIFO_IF feature.
The table below summarizes the key components of the implementation.
| Class/Method | Responsibility | Source File |
|---|---|---|
Reg.__init__() | Initializes self.fifo_if = True by checking for "FIFO_IF" in the register description. | regif.py:408 |
Reg.write | A property that returns the Verilog write block. If fifo_if is true, it calls fifo_push_declar(). | regif.py:415-417 |
RegFields.fifo_push_declar() | Formats the FIFO_PUSH_L4 Verilog template to generate the push logic and field mappings. | regif.py:654-658 |
RegFields.fifo_filed_assign_L2() | Iterates through fields to generate commented-out FIFO read data mapping assignments using Field.fifomap(). | regif.py:650-653 |
Field.fifomap() | Generates a single commented-out assign statement for a field from FIFO read data if the field type is WO. | regif.py:863-865 |
Generic Memory (mem) Scenario
The readme.md file lists "mem" as a supported scenario for the regif tool. However, based on the provided source code, there is no explicit implementation for generating a generic memory block (e.g., a RAM). The functionality is currently limited to the FIFO_IF feature described above. This suggests that generic memory generation may be a planned or future feature.
Sources: readme.md