de-modulify PartitionedSignal, call "set_module" to use it
[ieee754fpu.git] / src / ieee754 / part / partsig.py
1 # SPDX-License-Identifier: LGPL-2.1-or-later
2 # See Notices.txt for copyright information
3
4 """
5 Copyright (C) 2020 Luke Kenneth Casson Leighton <lkcl@lkcl.net>
6
7 dynamic-partitionable class similar to Signal, which, when the partition
8 is fully open will be identical to Signal. when partitions are closed,
9 the class turns into a SIMD variant of Signal. *this is dynamic*.
10
11 http://bugs.libre-riscv.org/show_bug.cgi?id=132
12 """
13
14 from ieee754.part_mul_add.adder import PartitionedAdder
15 from nmigen import (Signal,
16 )
17
18 class PartitionedSignal:
19 def __init__(self, partition_points, *args, **kwargs):
20 self.partpoints = partition_points
21 self.sig = Signal(*args, **kwargs)
22 self.modnames = {}
23 for name in ['add']:
24 self.modnames[name] = 0
25
26 def set_module(self, m):
27 self.m = m
28
29 def get_modname(self, category):
30 self.modnames[category] += 1
31 return "%s%d" % (category, self.modnames[category])
32
33 def eq(self, val):
34 return self.sig.eq(val)
35
36 def __xor__(self, other):
37 if isinstance(other, PartitionedSignal):
38 return self.sig ^ other.sig
39 return self.sig ^ other
40
41 def __add__(self, other):
42 shape = self.sig.shape()
43 pa = PartitionedAdder(shape[0], self.partpoints)
44 setattr(self.m.submodules, self.get_modname('add'), pa)
45 comb = self.m.d.comb
46 comb += pa.a.eq(self.sig)
47 if isinstance(other, PartitionedSignal):
48 comb += pa.b.eq(other.sig)
49 else:
50 comb += pa.b.eq(other)
51 return pa.output