gen/fhdl/verilog: Switch Assign/Operator types to IntEnum.

This commit is contained in:
Florent Kermarrec 2023-11-06 17:24:03 +01:00
parent 33fd7742c9
commit 5b989bcb0e
1 changed files with 21 additions and 13 deletions

View File

@ -17,6 +17,7 @@ import time
import datetime import datetime
import collections import collections
from enum import IntEnum
from operator import itemgetter from operator import itemgetter
from migen.fhdl.structure import * from migen.fhdl.structure import *
@ -181,19 +182,22 @@ def _generate_signal(ns, s):
# Print Operator ----------------------------------------------------------------------------------- # Print Operator -----------------------------------------------------------------------------------
(UNARY, BINARY, TERNARY) = (1, 2, 3) class OperatorType(IntEnum):
UNARY = 1
BINARY = 2
TERNARY = 3
def _generate_operator(ns, node): def _generate_operator(ns, node):
operator = node.op operator = node.op
operands = node.operands operands = node.operands
arity = len(operands) arity = len(operands)
assert arity in [UNARY, BINARY, TERNARY] assert arity in [item.value for item in OperatorType]
def to_signed(r): def to_signed(r):
return f"$signed({{1'd0, {r}}})" return f"$signed({{1'd0, {r}}})"
# Unary Operator. # Unary Operator.
if arity == UNARY: if arity == OperatorType.UNARY:
r1, s1 = _generate_expression(ns, operands[0]) r1, s1 = _generate_expression(ns, operands[0])
# Negation Operator. # Negation Operator.
if operator == "-": if operator == "-":
@ -206,7 +210,7 @@ def _generate_operator(ns, node):
s = s1 s = s1
# Binary Operator. # Binary Operator.
if arity == BINARY: if arity == OperatorType.BINARY:
r1, s1 = _generate_expression(ns, operands[0]) r1, s1 = _generate_expression(ns, operands[0])
r2, s2 = _generate_expression(ns, operands[1]) r2, s2 = _generate_expression(ns, operands[1])
# Convert all expressions to signed when at least one is signed. # Convert all expressions to signed when at least one is signed.
@ -219,7 +223,7 @@ def _generate_operator(ns, node):
s = s1 or s2 s = s1 or s2
# Ternary Operator. # Ternary Operator.
if arity == TERNARY: if arity == OperatorType.TERNARY:
assert operator == "m" assert operator == "m"
r1, s1 = _generate_expression(ns, operands[0]) r1, s1 = _generate_expression(ns, operands[0])
r2, s2 = _generate_expression(ns, operands[1]) r2, s2 = _generate_expression(ns, operands[1])
@ -292,17 +296,21 @@ def _generate_expression(ns, node):
# NODES # # NODES #
# ------------------------------------------------------------------------------------------------ # # ------------------------------------------------------------------------------------------------ #
(_AT_BLOCKING, _AT_NONBLOCKING, _AT_SIGNAL) = range(3) class AssignType(IntEnum):
BLOCKING = 0
NON_BLOCKING = 1
SIGNAL = 2
def _generate_node(ns, at, level, node, target_filter=None): def _generate_node(ns, at, level, node, target_filter=None):
assert at in [item.value for item in AssignType]
if target_filter is not None and target_filter not in list_targets(node): if target_filter is not None and target_filter not in list_targets(node):
return "" return ""
# Assignment. # Assignment.
elif isinstance(node, _Assign): elif isinstance(node, _Assign):
if at == _AT_BLOCKING: if at == AssignType.BLOCKING:
assignment = " = " assignment = " = "
elif at == _AT_NONBLOCKING: elif at == AssignType.NON_BLOCKING:
assignment = " <= " assignment = " <= "
elif is_variable(node.l): elif is_variable(node.l):
assignment = " = " assignment = " = "
@ -478,11 +486,11 @@ def _generate_combinatorial_logic_sim(f, ns):
for n, (t, stmts) in enumerate(target_stmt_map.items()): for n, (t, stmts) in enumerate(target_stmt_map.items()):
assert isinstance(t, Signal) assert isinstance(t, Signal)
if _use_wire(stmts): if _use_wire(stmts):
r += "assign " + _generate_node(ns, _AT_BLOCKING, 0, stmts[0]) r += "assign " + _generate_node(ns, AssignType.BLOCKING, 0, stmts[0])
else: else:
r += "always @(*) begin\n" r += "always @(*) begin\n"
r += _tab + ns.get_name(t) + " <= " + _generate_expression(ns, t.reset)[0] + ";\n" r += _tab + ns.get_name(t) + " <= " + _generate_expression(ns, t.reset)[0] + ";\n"
r += _generate_node(ns, _AT_NONBLOCKING, 1, stmts, t) r += _generate_node(ns, AssignType.NON_BLOCKING, 1, stmts, t)
r += "end\n" r += "end\n"
r += "\n" r += "\n"
return r return r
@ -494,12 +502,12 @@ def _generate_combinatorial_logic_synth(f, ns):
for n, g in enumerate(groups): for n, g in enumerate(groups):
if _use_wire(g[1]): if _use_wire(g[1]):
r += "assign " + _generate_node(ns, _AT_BLOCKING, 0, g[1][0]) r += "assign " + _generate_node(ns, AssignType.BLOCKING, 0, g[1][0])
else: else:
r += "always @(*) begin\n" r += "always @(*) begin\n"
for t in sorted(g[0], key=lambda x: ns.get_name(x)): for t in sorted(g[0], key=lambda x: ns.get_name(x)):
r += _tab + ns.get_name(t) + " <= " + _generate_expression(ns, t.reset)[0] + ";\n" r += _tab + ns.get_name(t) + " <= " + _generate_expression(ns, t.reset)[0] + ";\n"
r += _generate_node(ns, _AT_NONBLOCKING, 1, g[1]) r += _generate_node(ns, AssignType.NON_BLOCKING, 1, g[1])
r += "end\n" r += "end\n"
r += "\n" r += "\n"
return r return r
@ -512,7 +520,7 @@ def _generate_synchronous_logic(f, ns):
r = "" r = ""
for k, v in sorted(f.sync.items(), key=itemgetter(0)): for k, v in sorted(f.sync.items(), key=itemgetter(0)):
r += "always @(posedge " + ns.get_name(f.clock_domains[k].clk) + ") begin\n" r += "always @(posedge " + ns.get_name(f.clock_domains[k].clk) + ") begin\n"
r += _generate_node(ns, _AT_SIGNAL, 1, v) r += _generate_node(ns, AssignType.SIGNAL, 1, v)
r += "end\n\n" r += "end\n\n"
return r return r