2 from copy
import deepcopy
4 from nmutil
.formaltest
import FHDLTestCase
5 from openpower
.consts
import SVP64CROffs
6 from openpower
.decoder
.isa
.caller
import SVP64State
7 from openpower
.decoder
.isa
.test_caller
import run_tst
8 from openpower
.decoder
.selectable_int
import SelectableInt
9 from openpower
.simulator
.program
import Program
10 from openpower
.sv
.trans
.svp64
import SVP64Asm
13 class DecoderTestCase(FHDLTestCase
):
15 def _check_regs(self
, sim
, expected
):
17 self
.assertEqual(sim
.gpr(i
), SelectableInt(expected
[i
], 64))
19 def test_sv_load_store(self
):
20 """>>> lst = ["addi 2, 0, 0x0010",
27 lst
= SVP64Asm(["addi 2, 0, 0x0010",
35 # SVSTATE (in this case, VL=2)
36 svstate
= SVP64State()
38 svstate
.maxvl
= 2 # MAXVL
39 print("SVSTATE", bin(svstate
.asint()))
41 with
Program(lst
, bigendian
=False) as program
:
42 sim
= self
.run_tst_program(program
, svstate
=svstate
)
44 self
.assertEqual(sim
.gpr(8), SelectableInt(0x1234, 64))
45 self
.assertEqual(sim
.gpr(9), SelectableInt(0x1235, 64))
47 def test_sv_branch_cond(self
):
48 for i
in [0, 10]: # , 10]: #[0, 10]:
50 [f
"addi 1, 0, {i}", # set r1 to i
51 f
"addi 2, 0, {i}", # set r2 to i
52 "cmpi cr0, 1, 1, 10", # compare r1 with 10 and store to cr0
53 "cmpi cr1, 1, 2, 10", # compare r2 with 10 and store to cr1
54 "sv.bc 12, *2, 0xc", # beq 0xc -
55 # branch if r1 equals 10 to the nop below
56 "addi 3, 0, 0x1234", # if r1 == 10 this shouldn't execute
57 "or 0, 0, 0"] # branch target
61 # SVSTATE (in this case, VL=2)
62 svstate
= SVP64State()
64 svstate
.maxvl
= 2 # MAXVL
65 print("SVSTATE", bin(svstate
.asint()))
67 with
Program(lst
, bigendian
=False) as program
:
68 sim
= self
.run_tst_program(program
, svstate
=svstate
)
70 self
.assertEqual(sim
.gpr(3), SelectableInt(0, 64))
72 self
.assertEqual(sim
.gpr(3), SelectableInt(0x1234, 64))
74 def test_sv_branch_cond_all(self
):
77 [f
"addi 1, 0, {i+1}", # set r1 to i
78 f
"addi 2, 0, {i}", # set r2 to i
79 "cmpi cr0, 1, 1, 8", # compare r1 with 10 and store to cr0
80 "cmpi cr1, 1, 2, 8", # compare r2 with 10 and store to cr1
81 "sv.bc/all 12, *1, 0xc", # bgt 0xc - branch if BOTH
82 # r1 AND r2 greater 8 to the nop below
83 "addi 3, 0, 0x1234", # if tests fail this shouldn't execute
84 "or 0, 0, 0"] # branch target
88 # SVSTATE (in this case, VL=2)
89 svstate
= SVP64State()
91 svstate
.maxvl
= 2 # MAXVL
92 print("SVSTATE", bin(svstate
.asint()))
94 with
Program(lst
, bigendian
=False) as program
:
95 sim
= self
.run_tst_program(program
, svstate
=svstate
)
97 self
.assertEqual(sim
.gpr(3), SelectableInt(0, 64))
99 self
.assertEqual(sim
.gpr(3), SelectableInt(0x1234, 64))
101 def test_sv_branch_cond_all_vlset(self
):
104 [f
"addi 1, 0, {i+1}", # set r1 to i
105 f
"addi 2, 0, {i}", # set r2 to i
106 "cmpi cr0, 1, 1, 8", # compare r1 with 10 and store to cr0
107 "cmpi cr1, 1, 2, 8", # compare r2 with 10 and store to cr1
108 "sv.bc/all/vs 12, *1, 0xc", # bgt 0xc - branch if BOTH
109 # r1 AND r2 greater 8 to the nop below
110 # also truncate VL at the fail-point
111 "addi 3, 0, 0x1234", # if tests fail this shouldn't execute
112 "or 0, 0, 0"] # branch target
116 # SVSTATE (in this case, VL=2)
117 svstate
= SVP64State()
119 svstate
.maxvl
= 2 # MAXVL
120 print("SVSTATE", bin(svstate
.asint()))
122 with
Program(lst
, bigendian
=False) as program
:
123 sim
= self
.run_tst_program(program
, svstate
=svstate
)
125 self
.assertEqual(sim
.gpr(3), SelectableInt(0, 64))
127 self
.assertEqual(sim
.gpr(3), SelectableInt(0x1234, 64))
128 print("SVSTATE.vl", bin(svstate
.vl
))
129 self
.assertEqual(svstate
.vl
, i
-7)
131 def test_sv_branch_cond_vlset_inv(self
):
134 [f
"addi 1, 0, {i+1}", # set r1 to i
135 f
"addi 2, 0, {i}", # set r2 to i
136 "cmpi cr0, 1, 1, 8", # compare r1 with 8 and store to cr0
137 "cmpi cr1, 1, 2, 8", # compare r2 with 8 and store to cr1
138 "sv.bc/vsb 4, *1, 0xc", # bgt 0xc - branch if BOTH
139 # r1 AND r2 greater 8 to the nop below
140 # also truncate VL at the fail-point
141 "addi 3, 0, 0x1234", # if tests fail this shouldn't execute
142 "or 0, 0, 0"] # branch target
146 # SVSTATE (in this case, VL=2)
147 svstate
= SVP64State()
149 svstate
.maxvl
= 2 # MAXVL
150 print("SVSTATE", bin(svstate
.asint()))
152 with self
.subTest("vlset_inv %d" % i
):
153 with
Program(lst
, bigendian
=False) as program
:
154 sim
= self
.run_tst_program(program
, svstate
=svstate
)
155 print("SVSTATE.vl", bin(svstate
.vl
))
157 self
.assertEqual(sim
.gpr(3), SelectableInt(0x1234, 64))
159 self
.assertEqual(sim
.gpr(3), SelectableInt(0, 64))
160 self
.assertEqual(svstate
.vl
, i
-7)
162 def test_sv_branch_cond_ctr_vlset_inv(self
):
165 [f
"addi 1, 0, {i+1}", # set r1 to i
166 f
"addi 2, 0, {i}", # set r2 to i
167 "cmpi cr0, 1, 1, 8", # compare r1 with 8 and store to cr0
168 "cmpi cr1, 1, 2, 8", # compare r2 with 8 and store to cr1
169 "sv.bc/vsb 0, *1, 0xc", # bgt 0xc - branch if BOTH
170 # r1 AND r2 greater 8 to the nop below
171 # also truncate VL at the fail-point
172 "addi 3, 0, 0x1234", # if tests fail this shouldn't execute
173 "or 0, 0, 0"] # branch target
177 # SVSTATE (in this case, VL=2)
178 svstate
= SVP64State()
180 svstate
.maxvl
= 2 # MAXVL
181 print("SVSTATE", bin(svstate
.asint()))
184 with self
.subTest("vlset_ctr_inv %d" % i
):
185 with
Program(lst
, bigendian
=False) as program
:
186 sim
= self
.run_tst_program(program
, svstate
=svstate
,
188 print("SVSTATE.vl", bin(svstate
.vl
))
189 print("CTR", sim
.spr('CTR').value
)
191 self
.assertEqual(sim
.gpr(3), SelectableInt(0x1234, 64))
193 self
.assertEqual(sim
.gpr(3), SelectableInt(0, 64))
194 self
.assertEqual(svstate
.vl
, i
-7)
196 def test_sv_branch_ctr(self
):
197 """XXX under development, seems to be good.
198 basically this will reduce CTR under a *vector* loop, where BO[0]
199 is 1 so there is no CR-bit-test, and BO[2] is 0 so there is a CTR-zero
200 test. when the CTR-zero test fails the loop is exited, with CTR
201 having been reduced by up to at least VL times. without VLSET
202 mode at the same time (which truncates VL at this same fail-point)
203 however this is not necessarily so useful, but at least the branch
204 occurs with CTR being reduced *at least* by VL.
209 "sv.bc/ctr/all 16, *0, 0xc", # branch, test CTR, reducing by VL
210 "addi 3, 0, 0x1234", # if tests fail this shouldn't execute
211 "or 0, 0, 0"] # branch target
215 # SVSTATE (in this case, VL=2)
216 svstate
= SVP64State()
218 svstate
.maxvl
= 2 # MAXVL
219 print("SVSTATE", bin(svstate
.asint()))
222 with
Program(lst
, bigendian
=False) as program
:
223 sim
= self
.run_tst_program(program
, svstate
=svstate
,
228 self
.assertEqual(sim
.gpr(3), SelectableInt(0x1234, 64))
229 self
.assertEqual(sim
.spr('CTR'), SelectableInt(0, 64))
231 self
.assertEqual(sim
.gpr(3), SelectableInt(0, 64))
232 self
.assertEqual(sim
.spr('CTR'), SelectableInt(1, 64))
234 def test_sv_branch_ctr_loop(self
):
235 """this is a branch-ctr-loop demo which shows an (unconditional)
236 decrementing of CTR by VL. BI still has to be set to Vector even
237 though it is unused (BO[0]=1).
242 # VL (and r1) = MIN(CTR,MAXVL=4)
243 "setvl 1, 0, %d, 0, 1, 1" % maxvl
,
244 "add 2, 2, 1", # for fun accumulate r1 (VL) into r2
245 "sv.bc/all 16, *0, -0x8", # branch, test CTR, reducing by VL
250 # SVSTATE - set vl and maxvl to 2, they get overridden with setvl
251 svstate
= SVP64State()
253 svstate
.maxvl
= 2 # MAXVL
254 print("SVSTATE", bin(svstate
.asint()))
256 sprs
= {'CTR': target
}
258 with
Program(lst
, bigendian
=False) as program
:
259 sim
= self
.run_tst_program(program
, svstate
=svstate
,
263 self
.assertEqual(sim
.spr('CTR'), SelectableInt(0, 64))
264 self
.assertEqual(sim
.gpr(2), SelectableInt(target
, 64))
265 # MAXVL repeatedly subtracted from VL (r1), last loop has remainder
266 self
.assertEqual(sim
.gpr(1), SelectableInt(target
% maxvl
, 64))
268 def norun_sv_add_cr(self
):
269 """>>> lst = ['sv.add. *1, *5, *9'
272 adds when Rc=1: TODO CRs higher up
273 * 1 = 5 + 9 => 0 = -1+1 CR0=0b100
274 * 2 = 6 + 10 => 0x3334 = 0x2223+0x1111 CR1=0b010
276 isa
= SVP64Asm(['sv.add. *1, *5, *9'
279 print("listing", lst
)
281 # initial values in GPR regfile
282 initial_regs
= [0] * 32
283 initial_regs
[9] = 0xffffffffffffffff
284 initial_regs
[10] = 0x1111
285 initial_regs
[5] = 0x1
286 initial_regs
[6] = 0x2223
287 # SVSTATE (in this case, VL=2)
288 svstate
= SVP64State()
290 svstate
.maxvl
= 2 # MAXVL
291 print("SVSTATE", bin(svstate
.asint()))
292 # copy before running
293 expected_regs
= deepcopy(initial_regs
)
294 expected_regs
[1] = initial_regs
[5] + initial_regs
[9] # 0x0
295 expected_regs
[2] = initial_regs
[6] + initial_regs
[10] # 0x3334
297 with
Program(lst
, bigendian
=False) as program
:
298 sim
= self
.run_tst_program(program
, initial_regs
, svstate
)
299 # XXX TODO, these need to move to higher range (offset)
300 cr0_idx
= SVP64CROffs
.CR0
301 cr1_idx
= SVP64CROffs
.CR1
302 CR0
= sim
.crl
[cr0_idx
].get_range().value
303 CR1
= sim
.crl
[cr1_idx
].get_range().value
306 self
._check
_regs
(sim
, expected_regs
)
307 self
.assertEqual(CR0
, SelectableInt(2, 4))
308 self
.assertEqual(CR1
, SelectableInt(4, 4))
310 def run_tst_program(self
, prog
, initial_regs
=None,
313 if initial_regs
is None:
314 initial_regs
= [0] * 32
315 simulator
= run_tst(prog
, initial_regs
, svstate
=svstate
,
316 initial_sprs
=initial_sprs
)
321 if __name__
== "__main__":