Skip to content
Permalink

Comparing changes

Choose two branches to see what’s changed or to start a new pull request. If you need to, you can also or learn more about diff comparisons.

Open a pull request

Create a new pull request by comparing changes across two branches. If you need to, you can also . Learn more about diff comparisons here.
base repository: m-labs/nmigen
Failed to load repositories. Confirm that selected base ref is valid, then try again.
Loading
base: 1880686e2e40
Choose a base ref
...
head repository: m-labs/nmigen
Failed to load repositories. Confirm that selected head ref is valid, then try again.
Loading
compare: 655d02d5b839
Choose a head ref
  • 3 commits
  • 5 files changed
  • 1 contributor

Commits on Jan 15, 2019

  1. hdl.ast: Add AnyConst and AnySeq value types.

    cr1901 authored and whitequark committed Jan 15, 2019
    Copy the full SHA
    6fdbc3d View commit details
  2. hdl.xfrm: Add on_AnyConst and on_AnySeq abstract methods for ValueVis…

    …itor and children.
    cr1901 authored and whitequark committed Jan 15, 2019
    Copy the full SHA
    77728c2 View commit details
  3. back.rtlil: Generate $anyconst and $anyseq cells.

    cr1901 authored and whitequark committed Jan 15, 2019
    Copy the full SHA
    655d02d View commit details
Showing with 84 additions and 2 deletions.
  1. +1 −1 nmigen/__init__.py
  2. +12 −0 nmigen/back/pysim.py
  3. +26 −0 nmigen/back/rtlil.py
  4. +27 −1 nmigen/hdl/ast.py
  5. +18 −0 nmigen/hdl/xfrm.py
2 changes: 1 addition & 1 deletion nmigen/__init__.py
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
from .hdl.ast import Value, Const, C, Mux, Cat, Repl, Array, Signal, ClockSignal, ResetSignal, Assert, Assume
from .hdl.ast import Value, Const, C, AnyConst, AnySeq, Mux, Cat, Repl, Array, Signal, ClockSignal, ResetSignal, Assert, Assume
from .hdl.dsl import Module
from .hdl.cd import ClockDomain
from .hdl.ir import Fragment, Instance
12 changes: 12 additions & 0 deletions nmigen/back/pysim.py
Original file line number Diff line number Diff line change
@@ -87,6 +87,12 @@ def __init__(self, signal_slots, sensitivity=None, mode="rhs"):
def on_Const(self, value):
return lambda state: value.value

def on_AnyConst(self, value):
raise NotImplementedError # :nocov:

def on_AnySeq(self, value):
raise NotImplementedError # :nocov:

def on_Signal(self, value):
if self.sensitivity is not None:
self.sensitivity.add(value)
@@ -219,6 +225,12 @@ def __init__(self, signal_slots, rhs_compiler):
def on_Const(self, value):
raise TypeError # :nocov:

def on_AnyConst(self, value):
raise TypeError # :nocov:

def on_AnySeq(self, value):
raise TypeError # :nocov:

def on_Signal(self, value):
shape = value.shape()
value_slot = self.signal_slots[value]
26 changes: 26 additions & 0 deletions nmigen/back/rtlil.py
Original file line number Diff line number Diff line change
@@ -370,6 +370,26 @@ def on_Const(self, value):
value_twos_compl = value.value & ((1 << value.nbits) - 1)
return "{}'{:0{}b}".format(value.nbits, value_twos_compl, value.nbits)

def on_AnyConst(self, value):
res_bits, res_sign = value.shape()
res = self.s.rtlil.wire(width=res_bits)
self.s.rtlil.cell("$anyconst", ports={
"\\Y": res,
}, params={
"Y_WIDTH": res_bits,
}, src=src(value.src_loc))
return res

def on_AnySeq(self, value):
res_bits, res_sign = value.shape()
res = self.s.rtlil.wire(width=res_bits)
self.s.rtlil.cell("$anyseq", ports={
"\\Y": res,
}, params={
"Y_WIDTH": res_bits,
}, src=src(value.src_loc))
return res

def on_Signal(self, value):
wire_curr, wire_next = self.s.resolve(value)
return wire_curr
@@ -503,6 +523,12 @@ class _LHSValueCompiler(_ValueCompiler):
def on_Const(self, value):
raise TypeError # :nocov:

def on_AnyConst(self, value):
raise TypeError # :nocov:

def on_AnySeq(self, value):
raise TypeError # :nocov:

def on_Operator(self, value):
raise TypeError # :nocov:

28 changes: 27 additions & 1 deletion nmigen/hdl/ast.py
Original file line number Diff line number Diff line change
@@ -9,7 +9,7 @@


__all__ = [
"Value", "Const", "C", "Operator", "Mux", "Part", "Slice", "Cat", "Repl",
"Value", "Const", "C", "AnyConst", "AnySeq", "Operator", "Mux", "Part", "Slice", "Cat", "Repl",
"Array", "ArrayProxy",
"Signal", "ClockSignal", "ResetSignal",
"Statement", "Assign", "Assert", "Assume", "Switch", "Delay", "Tick",
@@ -254,6 +254,32 @@ def __repr__(self):
C = Const # shorthand


class AnyValue(Value):
def __init__(self, shape):
super().__init__(src_loc_at=0)
if isinstance(shape, int):
shape = shape, False
self.nbits, self.signed = shape
if not isinstance(self.nbits, int) or self.nbits < 0:
raise TypeError("Width must be a non-negative integer, not '{!r}'", self.nbits)

def shape(self):
return self.nbits, self.signed

def _rhs_signals(self):
return ValueSet()


class AnyConst(AnyValue):
def __repr__(self):
return "(anyconst {}'{})".format(self.nbits, "s" if self.signed else "")


class AnySeq(AnyValue):
def __repr__(self):
return "(anyseq {}'{})".format(self.nbits, "s" if self.signed else "")


class Operator(Value):
def __init__(self, op, operands, src_loc_at=0):
super().__init__(src_loc_at=1 + src_loc_at)
18 changes: 18 additions & 0 deletions nmigen/hdl/xfrm.py
Original file line number Diff line number Diff line change
@@ -23,6 +23,14 @@ class ValueVisitor(metaclass=ABCMeta):
def on_Const(self, value):
pass # :nocov:

@abstractmethod
def on_AnyConst(self, value):
pass # :nocov:

@abstractmethod
def on_AnySeq(self, value):
pass # :nocov:

@abstractmethod
def on_Signal(self, value):
pass # :nocov:
@@ -69,6 +77,10 @@ def on_unknown_value(self, value):
def on_value(self, value):
if type(value) is Const:
new_value = self.on_Const(value)
elif type(value) is AnyConst:
new_value = self.on_AnyConst(value)
elif type(value) is AnySeq:
new_value = self.on_AnySeq(value)
elif type(value) is Signal:
new_value = self.on_Signal(value)
elif type(value) is Record:
@@ -104,6 +116,12 @@ class ValueTransformer(ValueVisitor):
def on_Const(self, value):
return value

def on_AnyConst(self, value):
return value

def on_AnySeq(self, value):
return value

def on_Signal(self, value):
return value