3 * https://bugs.libre-soc.org/show_bug.cgi?id=361
11 from openpower
.decoder
.power_enums
import XER_bits
, CryIn
, spr_dict
12 from openpower
.util
import fast_reg_to_spr
, slow_reg_to_spr
# HACK!
13 from openpower
.consts
import XERRegsEnum
16 # TODO: make this a util routine (somewhere)
17 def mask_extend(x
, nbits
, repeat
):
19 extended
= (1<<repeat
)-1
20 for i
in range(nbits
):
22 res |
= extended
<< (i
*repeat
)
26 class SkipCase(Exception):
27 """Raise this exception to skip a test case.
29 Usually you'd use one of the skip_case* decorators.
31 For use with TestAccumulatorBase
36 """identity function"""
40 def skip_case(reason
):
42 Unconditionally skip a test case.
45 @skip_case("my reason for skipping")
53 For use with TestAccumulatorBase
56 assert not isinstance(item
, type), \
57 "can't use skip_case to decorate types"
59 @functools.wraps(item
)
60 def wrapper(*args
, **kwargs
):
61 raise SkipCase(reason
)
63 if isinstance(reason
, types
.FunctionType
):
66 return decorator(item
)
70 def skip_case_if(condition
, reason
):
72 Conditionally skip a test case.
75 @skip_case_if(should_i_skip(), "my reason for skipping")
79 For use with TestAccumulatorBase
82 return skip_case(reason
)
86 class TestAccumulatorBase
:
90 # automatically identifies anything starting with "case_" and
91 # runs it. very similar to unittest auto-identification except
92 # we need a different system
93 for n
, v
in self
.__class
__.__dict
__.items():
94 if n
.startswith("case_") and callable(v
):
98 # TODO(programmerjake): translate to final test sending
99 # skip signal to unittest. for now, just print the skipped
101 print(f
"SKIPPED({n}):", str(e
))
103 def add_case(self
, prog
, initial_regs
=None, initial_sprs
=None,
104 initial_cr
=0, initial_msr
=0,
110 test_name
= inspect
.stack()[1][3] # name of caller of this function
111 # name of file containing test case
112 test_file
= os
.path
.splitext(os
.path
.basename(
113 inspect
.stack()[1][1]))[0]
114 tc
= TestCase(prog
, test_name
,
115 regs
=initial_regs
, sprs
=initial_sprs
, cr
=initial_cr
,
118 svstate
=initial_svstate
,
120 stop_at_pc
=stop_at_pc
,
123 self
.test_data
.append(tc
)
127 def __init__(self
, program
, name
, regs
=None, sprs
=None, cr
=0, mem
=None,
130 extra_break_addr
=None,
136 self
.program
= program
151 self
.extra_break_addr
= extra_break_addr
152 self
.svstate
= svstate
153 self
.expected
= expected
# expected results from the test
154 self
.stop_at_pc
= stop_at_pc
# hard-stop address (do not attempt to run)
155 self
.test_file
= test_file
160 def get_sim_fast_reg(res
, sim
, dec2
, reg
, name
):
161 spr_sel
= fast_reg_to_spr(reg
)
162 spr_data
= sim
.spr
[spr_sel
].value
165 def get_sim_cia(res
, sim
, dec2
):
166 res
['cia'] = sim
.pc
.CIA
.value
168 # use this *after* the simulation has run a step (it returns CIA)
169 def get_sim_nia(res
, sim
, dec2
):
170 res
['nia'] = sim
.pc
.CIA
.value
172 def get_sim_msr(res
, sim
, dec2
):
173 res
['msr'] = sim
.msr
.value
175 def get_sim_slow_spr1(res
, sim
, dec2
):
176 spr1_en
= yield dec2
.e
.read_spr1
.ok
178 spr1_sel
= yield dec2
.e
.read_spr1
.data
179 spr1_sel
= slow_reg_to_spr(spr1_sel
)
180 spr1_data
= sim
.spr
[spr1_sel
].value
181 res
['spr1'] = spr1_data
183 def get_sim_fast_spr1(res
, sim
, dec2
):
184 fast1_en
= yield dec2
.e
.read_fast1
.ok
186 fast1_sel
= yield dec2
.e
.read_fast1
.data
187 spr1_sel
= fast_reg_to_spr(fast1_sel
)
188 spr1_data
= sim
.spr
[spr1_sel
].value
189 res
['fast1'] = spr1_data
191 def get_sim_fast_spr2(res
, sim
, dec2
):
192 fast2_en
= yield dec2
.e
.read_fast2
.ok
194 fast2_sel
= yield dec2
.e
.read_fast2
.data
195 spr2_sel
= fast_reg_to_spr(fast2_sel
)
196 spr2_data
= sim
.spr
[spr2_sel
].value
197 res
['fast2'] = spr2_data
199 def get_sim_fast_spr3(res
, sim
, dec2
):
200 fast3_en
= yield dec2
.e
.read_fast3
.ok
202 fast3_sel
= yield dec2
.e
.read_fast3
.data
203 spr3_sel
= fast_reg_to_spr(fast3_sel
)
204 spr3_data
= sim
.spr
[spr3_sel
].value
205 res
['fast3'] = spr3_data
207 def get_sim_cr_a(res
, sim
, dec2
):
208 cridx_ok
= yield dec2
.e
.read_cr1
.ok
210 cridx
= yield dec2
.e
.read_cr1
.data
211 res
['cr_a'] = sim
.crl
[cridx
].get_range().value
213 def get_sim_cr_b(res
, sim
, dec2
):
214 cridx_ok
= yield dec2
.e
.read_cr2
.ok
216 cridx
= yield dec2
.e
.read_cr2
.data
217 res
['cr_b'] = sim
.crl
[cridx
].get_range().value
219 def get_sim_cr_c(res
, sim
, dec2
):
220 cridx_ok
= yield dec2
.e
.read_cr3
.ok
222 cridx
= yield dec2
.e
.read_cr3
.data
223 res
['cr_c'] = sim
.crl
[cridx
].get_range().value
225 def get_sim_int_ra(res
, sim
, dec2
):
226 # TODO: immediate RA zero
227 reg1_ok
= yield dec2
.e
.read_reg1
.ok
229 data1
= yield dec2
.e
.read_reg1
.data
230 res
['ra'] = sim
.gpr(data1
).value
232 def get_sim_int_rb(res
, sim
, dec2
):
233 reg2_ok
= yield dec2
.e
.read_reg2
.ok
235 data
= yield dec2
.e
.read_reg2
.data
236 res
['rb'] = sim
.gpr(data
).value
238 def get_sim_int_rc(res
, sim
, dec2
):
239 reg3_ok
= yield dec2
.e
.read_reg3
.ok
241 data
= yield dec2
.e
.read_reg3
.data
242 res
['rc'] = sim
.gpr(data
).value
244 def get_rd_sim_xer_ca(res
, sim
, dec2
):
245 cry_in
= yield dec2
.e
.do
.input_carry
246 xer_in
= yield dec2
.e
.xer_in
247 if (xer_in
& (1<<XERRegsEnum
.CA
)) or cry_in
== CryIn
.CA
.value
:
248 expected_carry
= 1 if sim
.spr
['XER'][XER_bits
['CA']] else 0
249 expected_carry32
= 1 if sim
.spr
['XER'][XER_bits
['CA32']] else 0
250 res
['xer_ca'] = expected_carry |
(expected_carry32
<< 1)
252 def set_int_ra(alu
, dec2
, inp
):
253 # TODO: immediate RA zero.
255 yield alu
.p
.i_data
.ra
.eq(inp
['ra'])
257 yield alu
.p
.i_data
.ra
.eq(0)
259 def set_int_rb(alu
, dec2
, inp
):
260 yield alu
.p
.i_data
.rb
.eq(0)
262 yield alu
.p
.i_data
.rb
.eq(inp
['rb'])
263 if not hasattr(dec2
.e
.do
, "imm_data"):
265 # If there's an immediate, set the B operand to that
266 imm_ok
= yield dec2
.e
.do
.imm_data
.ok
268 data2
= yield dec2
.e
.do
.imm_data
.data
269 yield alu
.p
.i_data
.rb
.eq(data2
)
271 def set_int_rc(alu
, dec2
, inp
):
273 yield alu
.p
.i_data
.rc
.eq(inp
['rc'])
275 yield alu
.p
.i_data
.rc
.eq(0)
277 def set_xer_ca(alu
, dec2
, inp
):
279 yield alu
.p
.i_data
.xer_ca
.eq(inp
['xer_ca'])
280 print("extra inputs: CA/32", bin(inp
['xer_ca']))
282 def set_xer_ov(alu
, dec2
, inp
):
284 yield alu
.p
.i_data
.xer_ov
.eq(inp
['xer_ov'])
285 print("extra inputs: OV/32", bin(inp
['xer_ov']))
287 def set_xer_so(alu
, dec2
, inp
):
290 print("extra inputs: so", so
)
291 yield alu
.p
.i_data
.xer_so
.eq(so
)
293 def set_msr(alu
, dec2
, inp
):
294 print("TODO: deprecate set_msr")
296 yield alu
.p
.i_data
.msr
.eq(inp
['msr'])
298 def set_cia(alu
, dec2
, inp
):
299 print("TODO: deprecate set_cia")
301 yield alu
.p
.i_data
.cia
.eq(inp
['cia'])
303 def set_slow_spr1(alu
, dec2
, inp
):
305 yield alu
.p
.i_data
.spr1
.eq(inp
['spr1'])
307 def set_slow_spr2(alu
, dec2
, inp
):
309 yield alu
.p
.i_data
.spr2
.eq(inp
['spr2'])
311 def set_fast_spr1(alu
, dec2
, inp
):
313 yield alu
.p
.i_data
.fast1
.eq(inp
['fast1'])
315 def set_fast_spr2(alu
, dec2
, inp
):
317 yield alu
.p
.i_data
.fast2
.eq(inp
['fast2'])
319 def set_fast_spr3(alu
, dec2
, inp
):
321 yield alu
.p
.i_data
.fast3
.eq(inp
['fast3'])
323 def set_cr_a(alu
, dec2
, inp
):
325 yield alu
.p
.i_data
.cr_a
.eq(inp
['cr_a'])
327 def set_cr_b(alu
, dec2
, inp
):
329 yield alu
.p
.i_data
.cr_b
.eq(inp
['cr_b'])
331 def set_cr_c(alu
, dec2
, inp
):
333 yield alu
.p
.i_data
.cr_c
.eq(inp
['cr_c'])
335 def set_full_cr(alu
, dec2
, inp
):
337 full_reg
= yield dec2
.dec_cr_in
.whole_reg
.data
338 full_reg_ok
= yield dec2
.dec_cr_in
.whole_reg
.ok
339 full_cr_mask
= mask_extend(full_reg
, 8, 4)
340 yield alu
.p
.i_data
.full_cr
.eq(inp
['full_cr'] & full_cr_mask
)
342 yield alu
.p
.i_data
.full_cr
.eq(0)
344 def get_slow_spr1(res
, alu
, dec2
):
345 spr1_valid
= yield alu
.n
.o_data
.spr1
.ok
347 res
['spr1'] = yield alu
.n
.o_data
.spr1
.data
349 def get_slow_spr2(res
, alu
, dec2
):
350 spr2_valid
= yield alu
.n
.o_data
.spr2
.ok
352 res
['spr2'] = yield alu
.n
.o_data
.spr2
.data
354 def get_fast_spr1(res
, alu
, dec2
):
355 spr1_valid
= yield alu
.n
.o_data
.fast1
.ok
357 res
['fast1'] = yield alu
.n
.o_data
.fast1
.data
359 def get_fast_spr2(res
, alu
, dec2
):
360 spr2_valid
= yield alu
.n
.o_data
.fast2
.ok
362 res
['fast2'] = yield alu
.n
.o_data
.fast2
.data
364 def get_fast_spr3(res
, alu
, dec2
):
365 spr3_valid
= yield alu
.n
.o_data
.fast3
.ok
367 res
['fast3'] = yield alu
.n
.o_data
.fast3
.data
369 def get_cia(res
, alu
, dec2
):
370 res
['cia'] = yield alu
.p
.i_data
.cia
372 def get_nia(res
, alu
, dec2
):
373 nia_valid
= yield alu
.n
.o_data
.nia
.ok
375 res
['nia'] = yield alu
.n
.o_data
.nia
.data
377 def get_msr(res
, alu
, dec2
):
378 msr_valid
= yield alu
.n
.o_data
.msr
.ok
380 res
['msr'] = yield alu
.n
.o_data
.msr
.data
382 def get_int_o1(res
, alu
, dec2
):
383 out_reg_valid
= yield dec2
.e
.write_ea
.ok
385 res
['o1'] = yield alu
.n
.o_data
.o1
.data
387 def get_int_o(res
, alu
, dec2
):
388 out_reg_valid
= yield dec2
.e
.write_reg
.ok
390 res
['o'] = yield alu
.n
.o_data
.o
.data
392 def get_cr_a(res
, alu
, dec2
):
393 cridx_ok
= yield dec2
.e
.write_cr
.ok
395 res
['cr_a'] = yield alu
.n
.o_data
.cr0
.data
397 def get_xer_so(res
, alu
, dec2
):
398 oe
= yield dec2
.e
.do
.oe
.oe
399 oe_ok
= yield dec2
.e
.do
.oe
.ok
400 xer_out
= yield dec2
.e
.xer_out
401 if not (yield alu
.n
.o_data
.xer_so
.ok
):
403 if xer_out
or (oe
and oe_ok
):
404 res
['xer_so'] = yield alu
.n
.o_data
.xer_so
.data
[0]
406 def get_xer_ov(res
, alu
, dec2
):
407 oe
= yield dec2
.e
.do
.oe
.oe
408 oe_ok
= yield dec2
.e
.do
.oe
.ok
409 xer_out
= yield dec2
.e
.xer_out
410 if not (yield alu
.n
.o_data
.xer_ov
.ok
):
412 if xer_out
or (oe
and oe_ok
):
413 res
['xer_ov'] = yield alu
.n
.o_data
.xer_ov
.data
415 def get_xer_ca(res
, alu
, dec2
):
416 cry_out
= yield dec2
.e
.do
.output_carry
417 xer_out
= yield dec2
.e
.xer_out
418 if not (yield alu
.n
.o_data
.xer_ca
.ok
):
420 if xer_out
or (cry_out
):
421 res
['xer_ca'] = yield alu
.n
.o_data
.xer_ca
.data
423 def get_sim_int_o(res
, sim
, dec2
):
424 out_reg_valid
= yield dec2
.e
.write_reg
.ok
426 write_reg_idx
= yield dec2
.e
.write_reg
.data
427 res
['o'] = sim
.gpr(write_reg_idx
).value
429 def get_sim_int_o1(res
, sim
, dec2
):
430 out_reg_valid
= yield dec2
.e
.write_ea
.ok
432 write_reg_idx
= yield dec2
.e
.write_ea
.data
433 res
['o1'] = sim
.gpr(write_reg_idx
).value
435 def get_wr_sim_cr_a(res
, sim
, dec2
):
436 cridx_ok
= yield dec2
.e
.write_cr
.ok
438 cridx
= yield dec2
.e
.write_cr
.data
439 res
['cr_a'] = sim
.crl
[cridx
].get_range().value
441 def get_wr_fast_spr3(res
, sim
, dec2
):
442 ok
= yield dec2
.e
.write_fast3
.ok
444 spr_num
= yield dec2
.e
.write_fast3
.data
445 spr_num
= fast_reg_to_spr(spr_num
)
446 spr_name
= spr_dict
[spr_num
].SPR
447 res
['fast3'] = sim
.spr
[spr_name
].value
449 def get_wr_fast_spr2(res
, sim
, dec2
):
450 ok
= yield dec2
.e
.write_fast2
.ok
452 spr_num
= yield dec2
.e
.write_fast2
.data
453 spr_num
= fast_reg_to_spr(spr_num
)
454 spr_name
= spr_dict
[spr_num
].SPR
455 res
['fast2'] = sim
.spr
[spr_name
].value
457 def get_wr_fast_spr1(res
, sim
, dec2
):
458 ok
= yield dec2
.e
.write_fast1
.ok
460 spr_num
= yield dec2
.e
.write_fast1
.data
461 spr_num
= fast_reg_to_spr(spr_num
)
462 spr_name
= spr_dict
[spr_num
].SPR
463 res
['fast1'] = sim
.spr
[spr_name
].value
465 def get_wr_slow_spr1(res
, sim
, dec2
):
466 ok
= yield dec2
.e
.write_spr
.ok
468 spr_num
= yield dec2
.e
.write_spr
.data
469 spr_num
= slow_reg_to_spr(spr_num
)
470 spr_name
= spr_dict
[spr_num
].SPR
471 res
['spr1'] = sim
.spr
[spr_name
].value
473 def get_wr_sim_xer_ca(res
, sim
, dec2
):
474 # if not (yield alu.n.o_data.xer_ca.ok):
476 cry_out
= yield dec2
.e
.do
.output_carry
477 xer_out
= yield dec2
.e
.xer_out
478 if cry_out
or xer_out
:
479 expected_carry
= 1 if sim
.spr
['XER'][XER_bits
['CA']] else 0
480 expected_carry32
= 1 if sim
.spr
['XER'][XER_bits
['CA32']] else 0
481 res
['xer_ca'] = expected_carry |
(expected_carry32
<< 1)
483 def get_wr_sim_xer_ov(res
, sim
, alu
, dec2
):
484 oe
= yield dec2
.e
.do
.oe
.oe
485 oe_ok
= yield dec2
.e
.do
.oe
.ok
486 xer_out
= yield dec2
.e
.xer_out
487 print("get_wr_sim_xer_ov", xer_out
)
488 if not (yield alu
.n
.o_data
.xer_ov
.ok
):
490 if xer_out
or (oe
and oe_ok
):
491 expected_ov
= 1 if sim
.spr
['XER'][XER_bits
['OV']] else 0
492 expected_ov32
= 1 if sim
.spr
['XER'][XER_bits
['OV32']] else 0
493 res
['xer_ov'] = expected_ov |
(expected_ov32
<< 1)
495 def get_wr_sim_xer_so(res
, sim
, alu
, dec2
):
496 oe
= yield dec2
.e
.do
.oe
.oe
497 oe_ok
= yield dec2
.e
.do
.oe
.ok
498 xer_out
= yield dec2
.e
.xer_out
499 if not (yield alu
.n
.o_data
.xer_so
.ok
):
501 if xer_out
or (oe
and oe_ok
):
502 res
['xer_so'] = 1 if sim
.spr
['XER'][XER_bits
['SO']] else 0
504 def get_sim_xer_ov(res
, sim
, dec2
):
505 oe
= yield dec2
.e
.do
.oe
.oe
506 oe_ok
= yield dec2
.e
.do
.oe
.ok
507 xer_in
= yield dec2
.e
.xer_in
508 print("get_sim_xer_ov", xer_in
)
509 if (xer_in
& (1<<XERRegsEnum
.OV
)) or (oe
and oe_ok
):
510 expected_ov
= 1 if sim
.spr
['XER'][XER_bits
['OV']] else 0
511 expected_ov32
= 1 if sim
.spr
['XER'][XER_bits
['OV32']] else 0
512 res
['xer_ov'] = expected_ov |
(expected_ov32
<< 1)
514 def get_sim_xer_so(res
, sim
, dec2
):
515 print ("XER", sim
.spr
.__class
__, sim
.spr
, sim
.spr
['XER'])
516 oe
= yield dec2
.e
.do
.oe
.oe
517 oe_ok
= yield dec2
.e
.do
.oe
.ok
518 xer_in
= yield dec2
.e
.xer_in
519 rc
= yield dec2
.e
.do
.rc
.rc
520 rc_ok
= yield dec2
.e
.do
.rc
.ok
521 if (xer_in
& (1<<XERRegsEnum
.SO
)) or (oe
and oe_ok
) or (rc
and rc_ok
):
522 res
['xer_so'] = 1 if sim
.spr
['XER'][XER_bits
['SO']] else 0
524 def check_slow_spr1(dut
, res
, sim_o
, msg
):
526 expected
= sim_o
['spr1']
527 alu_out
= res
['spr1']
528 print(f
"expected {expected:x}, actual: {alu_out:x}")
529 dut
.assertEqual(expected
, alu_out
, msg
)
531 def check_fast_spr1(dut
, res
, sim_o
, msg
):
533 expected
= sim_o
['fast1']
534 alu_out
= res
['fast1']
535 print(f
"expected {expected:x}, actual: {alu_out:x}")
536 dut
.assertEqual(expected
, alu_out
, msg
)
538 def check_fast_spr2(dut
, res
, sim_o
, msg
):
540 expected
= sim_o
['fast2']
541 alu_out
= res
['fast2']
542 print(f
"expected {expected:x}, actual: {alu_out:x}")
543 dut
.assertEqual(expected
, alu_out
, msg
)
545 def check_fast_spr3(dut
, res
, sim_o
, msg
):
547 expected
= sim_o
['fast3']
548 alu_out
= res
['fast3']
549 print(f
"expected {expected:x}, actual: {alu_out:x}")
550 dut
.assertEqual(expected
, alu_out
, msg
)
552 def check_int_o1(dut
, res
, sim_o
, msg
):
554 expected
= sim_o
['o1']
556 print(f
"expected {expected:x}, actual: {alu_out:x}")
557 dut
.assertEqual(expected
, alu_out
, msg
)
559 def check_int_o(dut
, res
, sim_o
, msg
):
561 expected
= sim_o
['o']
563 print(f
"expected int sim {expected:x}, actual: {alu_out:x}")
564 dut
.assertEqual(expected
, alu_out
, msg
)
566 def check_msr(dut
, res
, sim_o
, msg
):
568 expected
= sim_o
['msr']
570 print(f
"expected {expected:x}, actual: {alu_out:x}")
571 dut
.assertEqual(expected
, alu_out
, msg
)
573 def check_nia(dut
, res
, sim_o
, msg
):
575 expected
= sim_o
['nia']
577 print(f
"expected {expected:x}, actual: {alu_out:x}")
578 dut
.assertEqual(expected
, alu_out
, msg
)
580 def check_cr_a(dut
, res
, sim_o
, msg
):
582 cr_expected
= sim_o
['cr_a']
583 cr_actual
= res
['cr_a']
584 print("CR", cr_expected
, cr_actual
)
585 dut
.assertEqual(cr_expected
, cr_actual
, msg
)
587 def check_xer_ca(dut
, res
, sim_o
, msg
):
589 ca_expected
= sim_o
['xer_ca']
590 ca_actual
= res
['xer_ca']
591 print("CA", ca_expected
, ca_actual
)
592 dut
.assertEqual(ca_expected
, ca_actual
, msg
)
594 def check_xer_ov(dut
, res
, sim_o
, msg
):
596 ov_expected
= sim_o
['xer_ov']
597 ov_actual
= res
['xer_ov']
598 print("OV", ov_expected
, ov_actual
)
599 dut
.assertEqual(ov_expected
, ov_actual
, msg
)
601 def check_xer_so(dut
, res
, sim_o
, msg
):
603 so_expected
= sim_o
['xer_so']
604 so_actual
= res
['xer_so']
605 print("SO", so_expected
, so_actual
)
606 dut
.assertEqual(so_expected
, so_actual
, msg
)