SystemRDL Compiler
The systemrdl-compiler project implements a generic compiler front-end for Accellera's SystemRDL 2.0 register description language. It provides an elaborated register model that is easy to traverse and query, facilitating the creation of custom register space view generators. The project is actively maintained with frequent minor releases addressing bugs and adding features.
Warnings
- deprecated The `Node.inst` API layer was deprecated from the public API in v1.30.1. Directly querying `Component` objects via `Node.inst` is no longer recommended and may break in future releases.
- gotcha Version `1.30.0` was yanked from PyPI due to a regression. Users should avoid installing this specific version.
- breaking Support for Python 3.5 and 3.6 was officially dropped in version `1.28.0`.
- gotcha The behavior of `RegNode.fields(include_gaps=True)` with overlapping fields was fixed in `v1.32.0`. Previously, it could return 'nonsensical reserved regions'. This change might alter results for designs with overlapping fields if `include_gaps` was used.
- breaking In `v1.29.3`, methods like `Node.children()`, `Node.signals()`, `RegNode.fields()`, etc., changed their return type from generators to lists. Code expecting generator behavior (e.g., lazy evaluation or single iteration without explicit conversion) may need adjustment.
- gotcha If RDL source files contain embedded Perl preprocessor tags, a Perl installation visible through the system's `PATH` environment variable is required for the compiler to function correctly.
- gotcha In `v1.32.2`, the `FieldNode.is_volatile` property was updated to correctly include 'singlepulse' fields as volatile. This change reflects a more accurate interpretation of the SystemRDL specification.
Install
-
pip install systemrdl-compiler
Imports
- RDLCompiler
from systemrdl import RDLCompiler
- RootNode
from systemrdl.node import RootNode
- Node
from systemrdl.node import Node
Quickstart
from systemrdl import RDLCompiler
from systemrdl.node import RootNode, Node
# Create a dummy RDL file content
rdl_content = """
addrmap my_block {
reg {
field { sw=rw; } my_field[31:0] = 0;
} my_register @0x0;
};
"""
# 1. Instantiate the compiler
compiler = RDLCompiler()
# 2. Compile the RDL source
try:
compiler.compile_string(rdl_content, "dummy.rdl")
except Exception as e:
print(f"Compilation failed: {e}")
exit(1)
# 3. Elaborate the design
try:
# 'my_block' is the top-level addrmap definition name
root = compiler.elaborate(top_def_name="my_block")
except Exception as e:
print(f"Elaboration failed: {e}")
exit(1)
# 4. Traverse the elaborated model
print("Elaborated RDL Model:")
for node in root.descendants(): # Use descendants for recursive traversal
indent = " " * node.depth
print(f"{indent}- {node.get_path()} (Type: {node.type_name})")
# Example: Access a specific register node
reg_node = root.find_by_path("my_block.my_register")
if reg_node:
print(f"Found register: {reg_node.inst_name} at address {hex(reg_node.addr_offset)}")
for field in reg_node.fields():
print(f" Field: {field.inst_name}, Bits: [{field.msb}:{field.lsb}]")