from nmigen import Module, Signal
-from nmigen.back.pysim import Simulator, Delay, Settle
+from nmigen.sim import Simulator, Delay, Settle
from nmutil.formaltest import FHDLTestCase
import unittest
from openpower.decoder.isa.caller import ISACaller
from openpower.consts import SVP64CROffs
from copy import deepcopy
from openpower.decoder.helpers import fp64toselectable
-from openpower.decoder.isafunctions.double2single import DOUBLE2SINGLE
from functools import reduce
import operator
for i in range(32):
self.assertEqual(sim.gpr(i), SelectableInt(expected[i], 64))
- def test_sv_remap(self):
- """>>> lst = ["svremap 2, 2, 3, 0",
- "sv.fmadds 0.v, 8.v, 16.v, 0.v"
+ def tst_sv_remap1(self):
+ """>>> lst = ["svshape 2, 2, 3, 0, 0",
+ "svremap 31, 1, 2, 3, 0, 0, 0",
+ "sv.fmadds *0, *8, *16, *0"
]
REMAP fmadds FRT, FRA, FRC, FRB
"""
- lst = SVP64Asm(["svremap 2, 2, 3, 0",
- "sv.fmadds 0.v, 8.v, 16.v, 0.v"
+ lst = SVP64Asm(["svshape 2, 2, 3, 0, 0",
+ "svremap 31, 1, 2, 3, 0, 0, 0",
+ "sv.fmadds *0, *16, *32, *0"
])
lst = list(lst)
print ("\t", yf)
# and create a linear result2, same scheme
- #result2 = [0] * (ydim1*xdim2)
+ #result1 = [0] * (ydim1*xdim2)
res = []
# store FPs
- for i, (x, y) in enumerate(zip(xf, yf)):
- fprs[i+8] = fp64toselectable(float(x)) # X matrix
- fprs[i+16] = fp64toselectable(float(y)) # Y matrix
+ for i, x in enumerate(xf):
+ fprs[i+16] = fp64toselectable(float(x)) # X matrix
+ for i, y in enumerate(yf):
+ fprs[i+32] = fp64toselectable(float(y)) # Y matrix
continue
#t = DOUBLE2SINGLE(fp64toselectable(t)) # convert to Power single
#u = DOUBLE2SINGLE(fp64toselectable(u)) # from double
#print ("FFT", i, "in", a, b, "coeff", c, "mul",
# mul, "res", t, u)
- # SVSTATE (in this case, VL=12, to cover all of matrix)
- svstate = SVP64State()
- svstate.vl[0:7] = 12 # VL
- svstate.maxvl[0:7] = 12 # MAXVL
- print ("SVSTATE", bin(svstate.spr.asint()))
-
with Program(lst, bigendian=False) as program:
- sim = self.run_tst_program(program, svstate=svstate,
- initial_fprs=fprs)
+ sim = self.run_tst_program(program, initial_fprs=fprs)
print ("spr svshape0", sim.spr['SVSHAPE0'])
+ print (" xdimsz", sim.spr['SVSHAPE0'].xdimsz)
+ print (" ydimsz", sim.spr['SVSHAPE0'].ydimsz)
+ print (" zdimsz", sim.spr['SVSHAPE0'].zdimsz)
print ("spr svshape1", sim.spr['SVSHAPE1'])
print ("spr svshape2", sim.spr['SVSHAPE2'])
print ("spr svshape3", sim.spr['SVSHAPE3'])
# self.assertEqual(sim.fpr(i+2), t)
# self.assertEqual(sim.fpr(i+6), u)
+ def tst_sv_remap2(self):
+ """>>> lst = ["svshape 5, 4, 3, 0, 0",
+ "svremap 31, 1, 2, 3, 0, 0, 0",
+ "sv.fmadds *0, *8, *16, *0"
+ ]
+ REMAP fmadds FRT, FRA, FRC, FRB
+ """
+ lst = SVP64Asm(["svshape 4, 3, 3, 0, 0",
+ "svremap 31, 1, 2, 3, 0, 0, 0",
+ "sv.fmadds *0, *16, *32, *0"
+ ])
+ lst = list(lst)
+
+ # 3x2 matrix
+ X1 = [[1, 2, 3],
+ [3, 4, 5],
+ ]
+ # 2x3 matrix
+ Y1 = [[6, 7],
+ [8, 9],
+ [10, 11],
+ ]
+
+ #### test matrices 2
+ # 3x3 matrix
+ X2 = [[12,7,3],
+ [4 ,5,6],
+ [7 ,8,9],
+ ]
+ # 3x4 matrix
+ Y2 = [[5,8,1,2],
+ [6,7,3,0],
+ [4,5,9,1]]
+
+ #### test matrices 3
+ # 3x4 matrix
+ X3 = [[12,7,3],
+ [4 ,5,6],
+ [7 ,8,9],
+ [2 ,0,1]]
+ # 3x5 matrix
+ Y3 = [[5,8,1,2,3],
+ [6,7,3,0,9],
+ [4,5,9,1,2]]
+
+ X = X2
+ Y = Y2
+
+ # get the dimensions of the 2 matrices
+ xdim1 = len(X[0])
+ ydim1 = len(X)
+ xdim2 = len(Y[0])
+ ydim2 = len(Y)
+
+ print ("xdim2 ydim1 ydim2", xdim2, ydim1, ydim2)
+
+ xf = reduce(operator.add, X)
+ yf = reduce(operator.add, Y)
+ print ("flattened X,Y")
+ print ("\t", xf)
+ print ("\t", yf)
+
+ # and create a linear result2, same scheme
+ #result1 = [0] * (ydim1*xdim2)
+
+
+ res = []
+ # store FPs
+ fprs = [0] * 64
+ for i, x in enumerate(xf):
+ fprs[i+16] = fp64toselectable(float(x)) # X matrix
+ for i, y in enumerate(yf):
+ fprs[i+32] = fp64toselectable(float(y)) # Y matrix
+ continue
+ #t = DOUBLE2SINGLE(fp64toselectable(t)) # convert to Power single
+ #u = DOUBLE2SINGLE(fp64toselectable(u)) # from double
+ #res.append((t, u))
+ #print ("FFT", i, "in", a, b, "coeff", c, "mul",
+ # mul, "res", t, u)
+
+ with Program(lst, bigendian=False) as program:
+ sim = self.run_tst_program(program, initial_fprs=fprs)
+ print ("spr svshape0", sim.spr['SVSHAPE0'])
+ print (" xdimsz", sim.spr['SVSHAPE0'].xdimsz)
+ print (" ydimsz", sim.spr['SVSHAPE0'].ydimsz)
+ print (" zdimsz", sim.spr['SVSHAPE0'].zdimsz)
+ print ("spr svshape1", sim.spr['SVSHAPE1'])
+ print ("spr svshape2", sim.spr['SVSHAPE2'])
+ print ("spr svshape3", sim.spr['SVSHAPE3'])
+ for i in range(16):
+ print ("i", i, float(sim.fpr(i)))
+ # confirm that the results are as expected
+ #for i, (t, u) in enumerate(res):
+ # self.assertEqual(sim.fpr(i+2), t)
+ # self.assertEqual(sim.fpr(i+6), u)
+
+ def test_sv_remap3_horizontal_or(self):
+ """>>> lst = ["svshape 3, 2, 1, 0, 0",
+ "svremap 31, 1, 3, 1, 1, 1, 0",
+ "sv.or *0, *0, *6"
+ ]
+ REMAP horizontal-or using "or RA,RS,RB"
+ same trick can be applied to do horizontal-add
+ or horizontal-multiply. just remember for multiply
+ to pre-load 1 (1.0) into the results first (or any other
+ scaling factor).
+
+ sv.or is horribly obscure because RA (the destination)
+ actually gets treated as RT by the REMAP subsystem.
+
+ The purpose here is to demonstrate a horizontal mapreduce
+ by using/abusing Matrix REMAP (ignoring the B-Matrix entirely)
+
+ if data is laid out in R G B R G B R G B format and
+ comprises tuples (R<<16 G<<8 B<<0) then a horizontal-or
+ may reduce down to (R<<16) | (G<<8> | (B<<0) on a per-row
+ basis.
+ """
+ # 3x4 matrix of data to be ORed together by row.
+ # Add any number of extra rows (up to 6) here (6 because sv.or *0,*0,*6)
+ X1 = [[0x1, 0x10, 0x100], # 0x111
+ [0x2, 0x40, 0x300], # 0x342
+ [0x9, 0x70, 0x800], # 0x879
+ [0x3, 0x71, 0x460], # overlaps (still ORed) - 0x473
+ ]
+
+ # get the dimensions of the array
+ xdim1 = len(X1[0])
+ ydim1 = len(X1)
+
+ lst = SVP64Asm(["svshape %d, %d, 1, 0, 0" % (xdim1, ydim1),
+ # also works:
+ # "svremap 31, 3, 0, 3, 1, 2, 0",
+ # "sv.ternlogi *12, *0, *6, 250" # 0b11111110
+ "svremap 31, 1, 3, 1, 1, 1, 0",
+ "sv.or *0, *0, *6"
+ ])
+ lst = list(lst)
+
+ print ("xdim1, ydim1", xdim1, ydim1)
+
+ expected = [0] * ydim1
+ for i, row in enumerate(X1):
+ expected[i] = reduce(operator.or_, row)
+ print ("\texpected ORed", hex(expected[i]))
+ xf = reduce(operator.add, X1)
+ print ("flattened X")
+ print ("\t", xf)
+
+ res = []
+ # store FPs
+ gprs = [0] * 64
+ for i, x in enumerate(xf):
+ gprs[i+6] = x
+
+ with Program(lst, bigendian=False) as program:
+ sim = self.run_tst_program(program, gprs)
+ print ("spr svshape0", sim.spr['SVSHAPE0'])
+ print (" xdimsz", sim.spr['SVSHAPE0'].xdimsz)
+ print (" ydimsz", sim.spr['SVSHAPE0'].ydimsz)
+ print (" zdimsz", sim.spr['SVSHAPE0'].zdimsz)
+ print ("spr svshape1", sim.spr['SVSHAPE1'])
+ print ("spr svshape2", sim.spr['SVSHAPE2'])
+ print ("spr svshape3", sim.spr['SVSHAPE3'])
+ for i in range(ydim1):
+ print ("i", i, sim.gpr(0+i), hex(expected[i]))
+ for i in range(ydim1):
+ self.assertEqual(sim.gpr(0+i), SelectableInt(expected[i], 64))
+
def run_tst_program(self, prog, initial_regs=None,
svstate=None,
initial_mem=None,