1 """Power ISA Decoder second stage
3 based on Anton Blanchard microwatt decode2.vhdl
6 from nmigen
import Module
, Elaboratable
, Signal
7 from power_enums
import (InternalOp
, CryIn
,
8 In1Sel
, In2Sel
, In3Sel
, OutSel
, SPR
, RC
)
10 class DecodeA(Elaboratable
):
11 def __init__(self
, dec
):
13 self
.sel_in
= Signal(In1Sel
, reset_less
=True)
14 self
.insn_in
= Signal(32, reset_less
=True)
15 self
.reg_out
= Signal(5, reset_less
=True)
16 self
.regok_out
= Signal(reset_less
=True)
17 self
.immz_out
= Signal(reset_less
=True)
18 self
.spr_out
= Signal(10, reset_less
=True)
19 self
.sprok_out
= Signal(reset_less
=True)
21 def elaborate(self
, platform
):
25 # select Register A field
26 with m
.If((self
.sel_in
== In1Sel
.RA
) |
27 ((self
.sel_in
== In1Sel
.RA_OR_ZERO
) &
28 (self
.reg_out
!= Const(0, 5)))):
29 comb
+= self
.reg_out
.eq(self
.dec
.RA
)
30 comb
+= self
.regok_out
.eq(1)
32 # zero immediate requested
33 with m
.If((self
.sel_in
== In1Sel
.RA_OR_ZERO
) &
34 (self
.reg_out
== Const(0, 5))):
35 comb
+= self
.immz_out
.eq(1)
37 # decode SPR1 based on instruction type
39 # BC or BCREG: potential implicit register (CTR)
40 with m
.If(op
.internal_op
== InternalOP
.OP_BC |
41 op
.internal_op
== InternalOP
.OP_BCREG
):
42 with m
.If(~self
.dec
.BO
[2]): # 3.0B p38 BO2=0, use CTR reg
43 self
.spr_out
.eq(SPR
.CTR
) # constant: CTR
45 # MFSPR or MTSPR: move-from / move-to SPRs
46 with m
.If(op
.internal_op
== InternalOP
.OP_MFSPR |
47 op
.internal_op
== InternalOP
.OP_MTSPR
):
48 self
.spr_out
.eq(self
.dec
.SPR
) # decode SPR field from XFX insn
54 class DecodeB(Elaboratable
):
55 def __init__(self
, dec
):
57 self
.sel_in
= Signal(In2Sel
, reset_less
=True)
58 self
.insn_in
= Signal(32, reset_less
=True)
59 self
.reg_out
= Signal(5, reset_less
=True)
60 self
.regok_out
= Signal(reset_less
=True)
61 self
.imm_out
= Signal(64, reset_less
=True)
62 self
.immok_out
= Signal(reset_less
=True)
63 self
.spr_out
= Signal(10, reset_less
=True)
64 self
.sprok_out
= Signal(reset_less
=True)
66 def elaborate(self
, platform
):
70 # select Register B field
71 with m
.Switch(self
.sel_in
):
72 with m
.Case(In2Sel
.RB
):
73 comb
+= self
.reg_out
.eq(self
.dec
.RB
)
74 comb
+= self
.regok_out
.eq(1)
75 with m
.Case(In2Sel
.CONST_UI
):
76 comb
+= self
.imm_out
.eq(self
.dec
.SI
)
77 comb
+= self
.immok_out
.eq(1)
78 with m
.Case(In2Sel
.CONST_SI
): # TODO: sign-extend here?
79 comb
+= self
.imm_out
.eq(self
.dec
.SI
)
80 comb
+= self
.immok_out
.eq(1)
81 with m
.Case(In2Sel
.CONST_UI_HI
):
82 comb
+= self
.imm_out
.eq(self
.dec
.UI
<<4)
83 comb
+= self
.immok_out
.eq(1)
84 with m
.Case(In2Sel
.CONST_UI_SI
): # TODO: sign-extend here?
85 comb
+= self
.imm_out
.eq(self
.dec
.UI
<<4)
86 comb
+= self
.immok_out
.eq(1)
87 with m
.Case(In2Sel
.CONST_LI
):
88 comb
+= self
.imm_out
.eq(self
.dec
.LI
<<2)
89 comb
+= self
.immok_out
.eq(1)
90 with m
.Case(In2Sel
.CONST_BD
):
91 comb
+= self
.imm_out
.eq(self
.dec
.BD
<<2)
92 comb
+= self
.immok_out
.eq(1)
93 with m
.Case(In2Sel
.CONST_DS
):
94 comb
+= self
.imm_out
.eq(self
.dec
.DS
<<2)
95 comb
+= self
.immok_out
.eq(1)
96 with m
.Case(In2Sel
.CONST_M1
):
97 comb
+= self
.imm_out
.eq(~
Const(0, 64)) # all 1s
98 comb
+= self
.immok_out
.eq(1)
99 with m
.Case(In2Sel
.CONST_SH
):
100 comb
+= self
.imm_out
.eq(self
.dec
.sh
)
101 comb
+= self
.immok_out
.eq(1)
102 with m
.Case(In2Sel
.CONST_SH32
):
103 comb
+= self
.imm_out
.eq(self
.dec
.SH32
)
104 comb
+= self
.immok_out
.eq(1)
106 # decode SPR2 based on instruction type
108 # BCREG implicitly uses CTR or LR for 2nd reg
109 with m
.If(op
.internal_op
== InternalOP
.OP_BCREG
):
110 with m
.If(self
.dec
.FormXL
.XO
[10]): # 3.0B p38 top bit of XO
111 self
.spr_out
.eq(SPR
.CTR
)
113 self
.spr_out
.eq(SPR
.LR
)
119 class DecodeC(Elaboratable
):
120 def __init__(self
, dec
):
122 self
.sel_in
= Signal(In3Sel
, reset_less
=True)
123 self
.insn_in
= Signal(32, reset_less
=True)
124 self
.reg_out
= Signal(5, reset_less
=True)
125 self
.regok_out
= Signal(reset_less
=True)
127 def elaborate(self
, platform
):
131 # select Register C field
132 with m
.If(self
.sel_in
== In3Sel
.RC
):
133 comb
+= self
.reg_out
.eq(self
.dec
.RC
)
134 comb
+= self
.regok_out
.eq(1)
139 class DecodeOut(Elaboratable
):
140 def __init__(self
, dec
):
142 self
.sel_in
= Signal(In1Sel
, reset_less
=True)
143 self
.insn_in
= Signal(32, reset_less
=True)
144 self
.reg_out
= Signal(5, reset_less
=True)
145 self
.regok_out
= Signal(reset_less
=True)
146 self
.spr_out
= Signal(10, reset_less
=True)
147 self
.sprok_out
= Signal(reset_less
=True)
149 def elaborate(self
, platform
):
153 # select Register out field
154 with m
.Switch(self
.sel_in
):
155 with m
.Case(In1Sel
.RT
):
156 comb
+= self
.reg_out
.eq(self
.dec
.RT
)
157 comb
+= self
.regok_out
.eq(1)
158 with m
.Case(In1Sel
.RA
):
159 comb
+= self
.reg_out
.eq(self
.dec
.RA
)
160 comb
+= self
.regok_out
.eq(1)
161 with m
.Case(In1Sel
.SPR
):
162 self
.spr_out
.eq(self
.dec
.SPR
) # decode SPR field from XFX insn
168 class DecodeRC(Elaboratable
):
169 def __init__(self
, dec
):
171 self
.sel_in
= Signal(RC
, reset_less
=True)
172 self
.insn_in
= Signal(32, reset_less
=True)
173 self
.rc_out
= Signal(1, reset_less
=True)
174 self
.rcok_out
= Signal(reset_less
=True)
176 def elaborate(self
, platform
):
180 # select Record bit out field
181 with m
.Switch(self
.sel_in
):
183 comb
+= self
.rc_out
.eq(self
.dec
.Rc
)
184 comb
+= self
.rcok_out
.eq(1)
186 comb
+= self
.rc_out
.eq(1)
187 comb
+= self
.rcok_out
.eq(1)
188 with m
.Case(RC
.NONE
):
189 comb
+= self
.rc_out
.eq(0)
190 comb
+= self
.rcok_out
.eq(1)
195 class DecodeOE(Elaboratable
):
197 -- For now, use "rc" in the decode table to decide whether oe exists.
198 -- This is not entirely correct architecturally: For mulhd and
199 -- mulhdu, the OE field is reserved. It remains to be seen what an
200 -- actual POWER9 does if we set it on those instructions, for now we
201 -- test that further down when assigning to the multiplier oe input.
203 def __init__(self
, dec
):
205 self
.sel_in
= Signal(RC
, reset_less
=True)
206 self
.insn_in
= Signal(32, reset_less
=True)
207 self
.oe_out
= Signal(1, reset_less
=True)
208 self
.oeok_out
= Signal(reset_less
=True)
210 def elaborate(self
, platform
):
214 # select OE bit out field
215 with m
.Switch(self
.sel_in
):
217 comb
+= self
.oe_out
.eq(self
.dec
.OE
)
218 comb
+= self
.oeok_out
.eq(1)
225 self
.ca
= Signal(reset_less
=True)
226 self
.ca32
= Signal(reset_less
=True)
227 self
.ov
= Signal(reset_less
=True)
228 self
.ov32
= Signal(reset_less
=True)
229 self
.so
= Signal(reset_less
=True)
232 class PowerDecodeToExecute(Elaboratable
):
234 def __init__(self
, width
):
236 self
.valid
= Signal(reset_less
=True)
237 self
.insn_type
= Signal(InternalOp
, reset_less
=True)
238 self
.nia
= Signal(64, reset_less
=True)
239 self
.write_reg
= Signal(5, reset_less
=True)
240 self
.read_reg1
= Signal(5, reset_less
=True)
241 self
.read_reg2
= Signal(5, reset_less
=True)
242 self
.read_data1
= Signal(64, reset_less
=True)
243 self
.read_data2
= Signal(64, reset_less
=True)
244 self
.read_data3
= Signal(64, reset_less
=True)
245 self
.cr
= Signal(32, reset_less
=True)
246 self
.xerc
= XerBits()
247 self
.lr
= Signal(reset_less
=True)
248 self
.rc
= Signal(reset_less
=True)
249 self
.oe
= Signal(reset_less
=True)
250 self
.invert_a
= Signal(reset_less
=True)
251 self
.invert_out
= Signal(reset_less
=True)
252 self
.input_carry
: Signal(CryIn
, reset_less
=True)
253 self
.output_carry
= Signal(reset_less
=True)
254 self
.input_cr
= Signal(reset_less
=True)
255 self
.output_cr
= Signal(reset_less
=True)
256 self
.is_32bit
= Signal(reset_less
=True)
257 self
.is_signed
= Signal(reset_less
=True)
258 self
.insn
= Signal(32, reset_less
=True)
259 self
.data_len
= Signal(4, reset_less
=True) # bytes
260 self
.byte_reverse
= Signal(reset_less
=True)
261 self
.sign_extend
= Signal(reset_less
=True)# do we need this?
262 self
.update
= Signal(reset_less
=True) # is this an update instruction?
264 def elaborate(self
, platform
):