identify test 9 code with comment
[ieee754fpu.git] / src / add / nmigen_add_experiment.py
index 15f39d80f481908fba8d0d903771274e965f4e3f..b7c771f7da989e8d4c4d9f66807c003622ee3905 100644 (file)
@@ -9,7 +9,7 @@ from math import log
 
 from fpbase import FPNumIn, FPNumOut, FPOp, Overflow, FPBase, FPNumBase
 from fpbase import MultiShiftRMerge, Trigger
-from example_buf_pipe import StageChain
+from example_buf_pipe import StageChain, UnbufferedPipeline
 #from fpbase import FPNumShiftMultiRight
 
 
@@ -266,11 +266,12 @@ class FPSCData:
         self.a = FPNumBase(width, True)
         self.b = FPNumBase(width, True)
         self.z = FPNumOut(width, False)
+        self.oz = Signal(width, reset_less=True)
         self.out_do_z = Signal(reset_less=True)
         self.mid = Signal(id_wid, reset_less=True)
 
     def eq(self, i):
-        return [self.z.eq(i.z), self.out_do_z.eq(i.out_do_z),
+        return [self.z.eq(i.z), self.out_do_z.eq(i.out_do_z), self.oz.eq(i.oz),
                 self.a.eq(i.a), self.b.eq(i.b), self.mid.eq(i.mid)]
 
 
@@ -382,6 +383,7 @@ class FPAddSpecialCasesMod:
             m.d.comb += self.o.a.eq(self.i.a)
             m.d.comb += self.o.b.eq(self.i.b)
 
+        m.d.comb += self.o.oz.eq(self.o.z.v)
         m.d.comb += self.o.mid.eq(self.i.mid)
 
         return m
@@ -458,9 +460,9 @@ class FPAddSpecialCasesDeNorm(FPState):
         m.d.sync += self.o.eq(self.dmod.o)
 
     def action(self, m):
-        with m.If(self.out_do_z):
-            m.next = "put_z"
-        with m.Else():
+        #with m.If(self.out_do_z):
+        #    m.next = "put_z"
+        #with m.Else():
             m.next = "align"
 
 
@@ -508,6 +510,7 @@ class FPAddDeNormMod(FPState):
         m.d.comb += self.o.mid.eq(self.i.mid)
         m.d.comb += self.o.z.eq(self.i.z)
         m.d.comb += self.o.out_do_z.eq(self.i.out_do_z)
+        m.d.comb += self.o.oz.eq(self.i.oz)
 
         return m
 
@@ -608,10 +611,11 @@ class FPNumIn2Ops:
         self.b = FPNumIn(None, width)
         self.z = FPNumOut(width, False)
         self.out_do_z = Signal(reset_less=True)
+        self.oz = Signal(width, reset_less=True)
         self.mid = Signal(id_wid, reset_less=True)
 
     def eq(self, i):
-        return [self.z.eq(i.z), self.out_do_z.eq(i.out_do_z),
+        return [self.z.eq(i.z), self.out_do_z.eq(i.out_do_z), self.oz.eq(i.oz),
                 self.a.eq(i.a), self.b.eq(i.b), self.mid.eq(i.mid)]
 
 
@@ -705,6 +709,7 @@ class FPAddAlignSingleMod:
         m.d.comb += self.o.mid.eq(self.i.mid)
         m.d.comb += self.o.z.eq(self.i.z)
         m.d.comb += self.o.out_do_z.eq(self.i.out_do_z)
+        m.d.comb += self.o.oz.eq(self.i.oz)
 
         return m
 
@@ -767,11 +772,12 @@ class FPAddStage0Data:
     def __init__(self, width, id_wid):
         self.z = FPNumBase(width, False)
         self.out_do_z = Signal(reset_less=True)
+        self.oz = Signal(width, reset_less=True)
         self.tot = Signal(self.z.m_width + 4, reset_less=True)
         self.mid = Signal(id_wid, reset_less=True)
 
     def eq(self, i):
-        return [self.z.eq(i.z), self.out_do_z.eq(i.out_do_z),
+        return [self.z.eq(i.z), self.out_do_z.eq(i.out_do_z), self.oz.eq(i.oz),
                 self.tot.eq(i.tot), self.mid.eq(i.mid)]
 
 
@@ -834,9 +840,8 @@ class FPAddStage0Mod:
                     self.o.tot.eq(bm0 - am0),
                     self.o.z.s.eq(self.i.b.s)
             ]
-        with m.Else():
-            m.d.comb += self.o.z.eq(self.i.z)
 
+        m.d.comb += self.o.oz.eq(self.i.oz)
         m.d.comb += self.o.out_do_z.eq(self.i.out_do_z)
         m.d.comb += self.o.mid.eq(self.i.mid)
         return m
@@ -870,11 +875,12 @@ class FPAddStage1Data:
     def __init__(self, width, id_wid):
         self.z = FPNumBase(width, False)
         self.out_do_z = Signal(reset_less=True)
+        self.oz = Signal(width, reset_less=True)
         self.of = Overflow()
         self.mid = Signal(id_wid, reset_less=True)
 
     def eq(self, i):
-        return [self.z.eq(i.z), self.out_do_z.eq(i.out_do_z),
+        return [self.z.eq(i.z), self.out_do_z.eq(i.out_do_z), self.oz.eq(i.oz),
                 self.of.eq(i.of), self.mid.eq(i.mid)]
 
 
@@ -936,6 +942,7 @@ class FPAddStage1Mod(FPState):
             ]
 
         m.d.comb += self.o.out_do_z.eq(self.i.out_do_z)
+        m.d.comb += self.o.oz.eq(self.i.oz)
         m.d.comb += self.o.mid.eq(self.i.mid)
 
         return m
@@ -1038,10 +1045,11 @@ class FPNorm1Data:
         self.roundz = Signal(reset_less=True)
         self.z = FPNumBase(width, False)
         self.out_do_z = Signal(reset_less=True)
+        self.oz = Signal(width, reset_less=True)
         self.mid = Signal(id_wid, reset_less=True)
 
     def eq(self, i):
-        return [self.z.eq(i.z), self.out_do_z.eq(i.out_do_z),
+        return [self.z.eq(i.z), self.out_do_z.eq(i.out_do_z), self.oz.eq(i.oz),
                 self.roundz.eq(i.roundz), self.mid.eq(i.mid)]
 
 
@@ -1148,6 +1156,7 @@ class FPNorm1ModSingle:
 
         m.d.comb += self.o.mid.eq(self.i.mid)
         m.d.comb += self.o.out_do_z.eq(self.i.out_do_z)
+        m.d.comb += self.o.oz.eq(self.i.oz)
 
         return m
 
@@ -1323,10 +1332,11 @@ class FPRoundData:
     def __init__(self, width, id_wid):
         self.z = FPNumBase(width, False)
         self.out_do_z = Signal(reset_less=True)
+        self.oz = Signal(width, reset_less=True)
         self.mid = Signal(id_wid, reset_less=True)
 
     def eq(self, i):
-        return [self.z.eq(i.z), self.out_do_z.eq(i.out_do_z),
+        return [self.z.eq(i.z), self.out_do_z.eq(i.out_do_z), self.oz.eq(i.oz),
                 self.mid.eq(i.mid)]
 
 
@@ -1485,22 +1495,16 @@ class FPPackMod:
         m = Module()
         m.submodules.pack_in_z = self.i.z
         m.d.comb += self.o.mid.eq(self.i.mid)
-        with m.If(self.i.z.is_overflowed):
-            m.d.comb += self.o.z.inf(self.i.z.s)
+        with m.If(~self.i.out_do_z):
+            with m.If(self.i.z.is_overflowed):
+                m.d.comb += self.o.z.inf(self.i.z.s)
+            with m.Else():
+                m.d.comb += self.o.z.create(self.i.z.s, self.i.z.e, self.i.z.m)
         with m.Else():
-            m.d.comb += self.o.z.create(self.i.z.s, self.i.z.e, self.i.z.m)
+            m.d.comb += self.o.z.v.eq(self.i.oz)
         return m
 
 
-class FPPackData:
-    def __init__(self, width, id_wid):
-        self.z = FPNumOut(width, False)
-        self.mid = Signal(id_wid, reset_less=True)
-
-    def eq(self, i):
-        return [self.z.eq(i.z), self.mid.eq(i.mid)]
-
-
 class FPPack(FPState):
 
     def __init__(self, width, id_wid):
@@ -1716,8 +1720,8 @@ class FPADDBaseMod:
         ppz = self.add_state(FPPutZ("pack_put_z", n1.out_z.z, self.o,
                                     n1.out_z.mid, self.o.mid))
 
-        pz = self.add_state(FPPutZ("put_z", sc.out_z.z, self.o,
-                                    sc.o.mid, self.o.mid))
+        #pz = self.add_state(FPPutZ("put_z", sc.out_z.z, self.o,
+        #                            sc.o.mid, self.o.mid))
 
 
 class FPADDBase(FPState):
@@ -1810,6 +1814,57 @@ class FPADDBase(FPState):
             with m.Else():
                 m.d.sync += self.out_z.stb.eq(1)
 
+class FPADDStageIn:
+    def __init__(self, width, id_wid):
+        self.a = Signal(width)
+        self.b = Signal(width)
+        self.mid = Signal(id_wid, reset_less=True)
+
+    def eq(self, i):
+        return [self.a.eq(i.a), self.b.eq(i.b), self.mid.eq(i.mid)]
+
+
+class FPADDStageOut:
+    def __init__(self, width, id_wid):
+        self.z = Signal(width)
+        self.mid = Signal(id_wid, reset_less=True)
+
+    def eq(self, i):
+        return [self.z.eq(i.z), self.mid.eq(i.mid)]
+
+
+# matches the format of FPADDStageOut, allows eq function to do assignments
+class PlaceHolder: pass
+
+
+class FPAddBaseStage:
+    def __init__(self, width, id_wid):
+        self.width = width
+        self.id_wid = id_wid
+
+    def ispec(self):
+        return FPADDStageIn(self.width, self.id_wid)
+
+    def ospec(self):
+        return FPADDStageOut(self.width, self.id_wid)
+
+    def process(self, i):
+        o = PlaceHolder()
+        o.z = i.a + i.b
+        o.mid = i.mid
+        return o
+
+
+class FPADDBasePipe:
+    def __init__(self, width, id_wid):
+        stage1 = FPAddBaseStage(width, id_wid)
+        self.pipe = UnbufferedPipeline(stage1)
+
+    def elaborate(self, platform):
+        return self.pipe.elaborate(platform)
+
+    def ports(self):
+        return self.pipe.ports()
 
 class ResArray:
     def __init__(self, width, id_wid):