1 from soc
.decoder
.power_enums
import (Function
, Form
, InternalOp
,
2 In1Sel
, In2Sel
, In3Sel
, OutSel
, RC
, LdstLen
,
3 CryIn
, get_csv
, single_bit_flags
,
4 get_signal_name
, default_values
)
9 def __init__(self
, bytes_per_word
=8):
11 self
.bytes_per_word
= bytes_per_word
12 self
.word_log2
= math
.ceil(math
.log2(bytes_per_word
))
14 # TODO: Implement ld/st of lesser width
15 def ld(self
, address
):
16 address
= address
>> self
.word_log2
17 if address
in self
.mem
:
18 val
= self
.mem
[address
]
21 print("Read {:x} from addr {:x}".format(val
, address
))
24 def st(self
, address
, value
):
25 address
= address
>> self
.word_log2
26 print("Writing {:x} to addr {:x}".format(value
, address
))
27 self
.mem
[address
] = value
32 self
.regfile
= [0] * 32
35 def write_reg(self
, regnum
, value
):
36 print("Writing {:x} to reg r{}".format(value
, regnum
))
37 self
.regfile
[regnum
] = value
39 def read_reg(self
, regnum
):
40 val
= self
.regfile
[regnum
]
41 print("Read {:x} from reg r{}".format(val
, regnum
))
44 def assert_gprs(self
, gprs
):
45 for k
,v
in list(gprs
.items()):
46 reg_val
= self
.read_reg(k
)
47 msg
= "reg r{} got {:x}, expecting {:x}".format(
49 assert reg_val
== v
, msg
52 class InternalOpSimulator
:
54 self
.mem_sim
= MemorySim()
55 self
.regfile
= RegFile()
57 def execute_alu_op(self
, op1
, op2
, internal_op
):
59 if internal_op
== InternalOp
.OP_ADD
.value
:
61 elif internal_op
== InternalOp
.OP_AND
.value
:
64 assert(False, "Not implemented")
66 def alu_op(self
, pdecode2
):
67 internal_op
= yield pdecode2
.dec
.op
.internal_op
71 r1_ok
= yield pdecode2
.e
.read_reg1
.ok
72 r2_ok
= yield pdecode2
.e
.read_reg2
.ok
73 r3_ok
= yield pdecode2
.e
.read_reg3
.ok
74 imm_ok
= yield pdecode2
.e
.imm_data
.ok
76 r1_sel
= yield pdecode2
.e
.read_reg1
.data
77 operand1
= self
.regfile
.read_reg(r1_sel
)
79 r3_sel
= yield pdecode2
.e
.read_reg3
.data
80 operand1
= self
.regfile
.read_reg(r3_sel
)
82 r2_sel
= yield pdecode2
.e
.read_reg2
.data
83 operand2
= self
.regfile
.read_reg(r2_sel
)
85 operand2
= yield pdecode2
.e
.imm_data
.data
87 result
= self
.execute_alu_op(operand1
, operand2
, internal_op
)
88 ro_ok
= yield pdecode2
.e
.write_reg
.ok
90 ro_sel
= yield pdecode2
.e
.write_reg
.data
91 self
.regfile
.write_reg(ro_sel
, result
)
93 def mem_op(self
, pdecode2
):
94 internal_op
= yield pdecode2
.dec
.op
.internal_op
95 addr_reg
= yield pdecode2
.e
.read_reg1
.data
96 addr
= self
.regfile
.read_reg(addr_reg
)
98 imm_ok
= yield pdecode2
.e
.imm_data
.ok
100 imm
= yield pdecode2
.e
.imm_data
.data
102 if internal_op
== InternalOp
.OP_STORE
.value
:
103 val_reg
= yield pdecode2
.e
.read_reg3
.data
104 val
= self
.regfile
.read_reg(val_reg
)
105 self
.mem_sim
.st(addr
, val
)
106 elif internal_op
== InternalOp
.OP_LOAD
.value
:
107 dest_reg
= yield pdecode2
.e
.write_reg
.data
108 val
= self
.mem_sim
.ld(addr
)
109 self
.regfile
.write_reg(dest_reg
, val
)
112 def execute_op(self
, pdecode2
):
113 function
= yield pdecode2
.dec
.op
.function_unit
114 if function
== Function
.ALU
.value
:
115 yield from self
.alu_op(pdecode2
)
116 elif function
== Function
.LDST
.value
:
117 yield from self
.mem_op(pdecode2
)