RHDL’s gate-level synthesis backend lowers HDL components to primitive gate netlists — AND, OR, XOR, NOT, MUX, BUF, CONST, and DFF. This provides gate count metrics, structural verification, and a path to hardware implementation.

Quick Start

CLI

# Synthesize all components to gate-level JSON
rhdl gates --export
 
# Show gate count statistics
rhdl gates --stats
 
# Synthesize CPU datapath components
rhdl gates --simcpu
 
# Clean output
rhdl gates --clean

Programmatic

# Lower a component to gate-level IR
component = RHDL::HDL::ALU.new('alu', width: 8)
ir = RHDL::Codegen::Structure::Lower.from_components([component], name: 'alu')
 
puts "Gates: #{ir.gates.length}"
puts "DFFs:  #{ir.dffs.length}"
puts "Nets:  #{ir.net_count}"
 
# Export to JSON
File.write('alu.json', ir.to_json)

Statistics Output

RHDL Gate-Level Synthesis Statistics
==================================================

Components by Gate Count:
--------------------------------------------------
  cpu/synth_datapath: 505 gates, 24 DFFs, 892 nets
  arithmetic/alu: 312 gates, 0 DFFs, 456 nets
  arithmetic/multiplier: 256 gates, 0 DFFs, 384 nets
  ...

==================================================
Total Components: 53
Total Gates: 2847
Total DFFs: 156

Primitive Gate Types

GateFunctionNotes
ANDa & bN-ary reduced to binary tree
ORa | bN-ary reduced to binary tree
XORa ^ bBinary only
NOT~aInverter
MUXsel ? t : f2-to-1 multiplexer
BUFaBuffer (fan-out)
CONST0 or 1Constant value
DFFD flip-flopWith optional reset and enable

Supported Components (53 total)

CategoryCountExamples
Gates13AND, OR, XOR, NOT, NAND, NOR, Bitwise ops
Sequential12DFF, Register, ShiftRegister, Counter, PC, SP
Arithmetic10Adders, Subtractor, ALU, Multiplier, Divider
Combinational16Mux2–MuxN, Decoders, Encoders, BarrelShifter
CPU2InstructionDecoder, SynthDatapath

Gate Count Reference

ComponentWidthGatesDFFsNets
AndGate1103
FullAdder1509
RippleCarryAdder848067
Register80824
Counter8~608~80
ALU8~4000~500
Multiplier8~8000~1000
SynthDatapath (CPU)~50524~600

Output Format

Each component generates two files:

export/gates/
├── arithmetic/
│   ├── alu.json          # Machine-readable netlist
│   ├── alu.txt           # Human-readable statistics
│   └── ...
├── sequential/
│   ├── counter.json
│   ├── counter.txt
│   └── ...
└── cpu/
    ├── synth_datapath.json
    └── synth_datapath.txt

JSON Netlist Format

{
  "name": "alu",
  "net_count": 1234,
  "inputs": {
    "a": [0, 1, 2, 3, 4, 5, 6, 7],
    "b": [8, 9, 10, 11, 12, 13, 14, 15]
  },
  "outputs": {
    "result": [100, 101, 102, 103, 104, 105, 106, 107]
  },
  "gates": [
    {"type": "AND", "inputs": [0, 8], "output": 50},
    {"type": "XOR", "inputs": [0, 8], "output": 51}
  ],
  "dffs": []
}

Limitations

  • Memories: RAM/ROM not supported at gate level
  • Clock domains: Single clock domain only
  • Tristate: Lowers to simple gates (not true high-Z)
  • Large designs: Gate counts grow quadratically for multipliers/dividers
  • Timing: Functional only, no propagation delay modeling

Next Steps