minor code-munge on SPR-to-FAST mapping
[soc.git] / src / soc / decoder / power_decoder2.py
1 """Power ISA Decoder second stage
2
3 based on Anton Blanchard microwatt decode2.vhdl
4
5 Note: OP_TRAP is used for exceptions and interrupts (micro-code style) by
6 over-riding the internal opcode when an exception is needed.
7 """
8
9 from nmigen import Module, Elaboratable, Signal, Mux, Const, Cat, Repl, Record
10 from nmigen.cli import rtlil
11 from soc.regfile.regfiles import XERRegs
12
13 from nmutil.picker import PriorityPicker
14 from nmutil.iocontrol import RecordObject
15 from nmutil.extend import exts
16
17 from soc.decoder.power_regspec_map import regspec_decode_read
18 from soc.decoder.power_regspec_map import regspec_decode_write
19 from soc.decoder.power_decoder import create_pdecode
20 from soc.decoder.power_enums import (MicrOp, CryIn, Function,
21 CRInSel, CROutSel,
22 LdstLen, In1Sel, In2Sel, In3Sel,
23 OutSel, SPR, RC, LDSTMode)
24 from soc.decoder.decode2execute1 import Decode2ToExecute1Type, Data
25 from soc.consts import MSR
26
27 from soc.regfile.regfiles import FastRegs
28 from soc.consts import TT
29 from soc.config.state import CoreState
30 from soc.regfile.util import spr_to_fast
31
32
33 def decode_spr_num(spr):
34 return Cat(spr[5:10], spr[0:5])
35
36
37 def instr_is_priv(m, op, insn):
38 """determines if the instruction is privileged or not
39 """
40 comb = m.d.comb
41 is_priv_insn = Signal(reset_less=True)
42 with m.Switch(op):
43 with m.Case(MicrOp.OP_ATTN, MicrOp.OP_MFMSR, MicrOp.OP_MTMSRD,
44 MicrOp.OP_MTMSR, MicrOp.OP_RFID):
45 comb += is_priv_insn.eq(1)
46 # XXX TODO
47 #with m.Case(MicrOp.OP_TLBIE) : comb += is_priv_insn.eq(1)
48 with m.Case(MicrOp.OP_MFSPR, MicrOp.OP_MTSPR):
49 with m.If(insn[20]): # field XFX.spr[-1] i think
50 comb += is_priv_insn.eq(1)
51 return is_priv_insn
52
53
54 class SPRMap(Elaboratable):
55 """SPRMap: maps POWER9 SPR numbers to internal enum values, fast and slow
56 """
57
58 def __init__(self):
59 self.spr_i = Signal(10, reset_less=True)
60 self.spr_o = Data(SPR, name="spr_o")
61 self.fast_o = Data(3, name="fast_o")
62
63 def elaborate(self, platform):
64 m = Module()
65 with m.Switch(self.spr_i):
66 for i, x in enumerate(SPR):
67 with m.Case(x.value):
68 m.d.comb += self.spr_o.data.eq(i)
69 m.d.comb += self.spr_o.ok.eq(1)
70 for x, v in spr_to_fast.items():
71 with m.Case(x.value):
72 m.d.comb += self.fast_o.data.eq(v)
73 m.d.comb += self.fast_o.ok.eq(1)
74 return m
75
76
77 class DecodeA(Elaboratable):
78 """DecodeA from instruction
79
80 decodes register RA, whether immediate-zero, implicit and
81 explicit CSRs
82 """
83
84 def __init__(self, dec):
85 self.dec = dec
86 self.sel_in = Signal(In1Sel, reset_less=True)
87 self.insn_in = Signal(32, reset_less=True)
88 self.reg_out = Data(5, name="reg_a")
89 self.immz_out = Signal(reset_less=True)
90 self.spr_out = Data(SPR, "spr_a")
91 self.fast_out = Data(3, "fast_a")
92
93 def elaborate(self, platform):
94 m = Module()
95 comb = m.d.comb
96 m.submodules.sprmap = sprmap = SPRMap()
97
98 # select Register A field
99 ra = Signal(5, reset_less=True)
100 comb += ra.eq(self.dec.RA)
101 with m.If((self.sel_in == In1Sel.RA) |
102 ((self.sel_in == In1Sel.RA_OR_ZERO) &
103 (ra != Const(0, 5)))):
104 comb += self.reg_out.data.eq(ra)
105 comb += self.reg_out.ok.eq(1)
106
107 # zero immediate requested
108 with m.If((self.sel_in == In1Sel.RA_OR_ZERO) &
109 (self.reg_out.data == Const(0, 5))):
110 comb += self.immz_out.eq(1)
111
112 # some Logic/ALU ops have RS as the 3rd arg, but no "RA".
113 with m.If(self.sel_in == In1Sel.RS):
114 comb += self.reg_out.data.eq(self.dec.RS)
115 comb += self.reg_out.ok.eq(1)
116
117 # decode Fast-SPR based on instruction type
118 op = self.dec.op
119 with m.Switch(op.internal_op):
120
121 # BC or BCREG: implicit register (CTR) NOTE: same in DecodeOut
122 with m.Case(MicrOp.OP_BC):
123 with m.If(~self.dec.BO[2]): # 3.0B p38 BO2=0, use CTR reg
124 # constant: CTR
125 comb += self.fast_out.data.eq(FastRegs.CTR)
126 comb += self.fast_out.ok.eq(1)
127 with m.Case(MicrOp.OP_BCREG):
128 xo9 = self.dec.FormXL.XO[9] # 3.0B p38 top bit of XO
129 xo5 = self.dec.FormXL.XO[5] # 3.0B p38
130 with m.If(xo9 & ~xo5):
131 # constant: CTR
132 comb += self.fast_out.data.eq(FastRegs.CTR)
133 comb += self.fast_out.ok.eq(1)
134
135 # MFSPR move from SPRs
136 with m.Case(MicrOp.OP_MFSPR):
137 spr = Signal(10, reset_less=True)
138 comb += spr.eq(decode_spr_num(self.dec.SPR)) # from XFX
139 comb += sprmap.spr_i.eq(spr)
140 comb += self.spr_out.eq(sprmap.spr_o)
141 comb += self.fast_out.eq(sprmap.fast_o)
142
143 return m
144
145
146 class DecodeB(Elaboratable):
147 """DecodeB from instruction
148
149 decodes register RB, different forms of immediate (signed, unsigned),
150 and implicit SPRs. register B is basically "lane 2" into the CompUnits.
151 by industry-standard convention, "lane 2" is where fully-decoded
152 immediates are muxed in.
153 """
154
155 def __init__(self, dec):
156 self.dec = dec
157 self.sel_in = Signal(In2Sel, reset_less=True)
158 self.insn_in = Signal(32, reset_less=True)
159 self.reg_out = Data(5, "reg_b")
160 self.imm_out = Data(64, "imm_b")
161 self.fast_out = Data(3, "fast_b")
162
163 def elaborate(self, platform):
164 m = Module()
165 comb = m.d.comb
166
167 # select Register B field
168 with m.Switch(self.sel_in):
169 with m.Case(In2Sel.RB):
170 comb += self.reg_out.data.eq(self.dec.RB)
171 comb += self.reg_out.ok.eq(1)
172 with m.Case(In2Sel.RS):
173 # for M-Form shiftrot
174 comb += self.reg_out.data.eq(self.dec.RS)
175 comb += self.reg_out.ok.eq(1)
176 with m.Case(In2Sel.CONST_UI): # unsigned
177 comb += self.imm_out.data.eq(self.dec.UI)
178 comb += self.imm_out.ok.eq(1)
179 with m.Case(In2Sel.CONST_SI): # sign-extended 16-bit
180 si = Signal(16, reset_less=True)
181 comb += si.eq(self.dec.SI)
182 comb += self.imm_out.data.eq(exts(si, 16, 64))
183 comb += self.imm_out.ok.eq(1)
184 with m.Case(In2Sel.CONST_SI_HI): # sign-extended 16+16=32 bit
185 si_hi = Signal(32, reset_less=True)
186 comb += si_hi.eq(self.dec.SI << 16)
187 comb += self.imm_out.data.eq(exts(si_hi, 32, 64))
188 comb += self.imm_out.ok.eq(1)
189 with m.Case(In2Sel.CONST_UI_HI): # unsigned
190 ui = Signal(16, reset_less=True)
191 comb += ui.eq(self.dec.UI)
192 comb += self.imm_out.data.eq(ui << 16)
193 comb += self.imm_out.ok.eq(1)
194 with m.Case(In2Sel.CONST_LI): # sign-extend 24+2=26 bit
195 li = Signal(26, reset_less=True)
196 comb += li.eq(self.dec.LI << 2)
197 comb += self.imm_out.data.eq(exts(li, 26, 64))
198 comb += self.imm_out.ok.eq(1)
199 with m.Case(In2Sel.CONST_BD): # sign-extend (14+2)=16 bit
200 bd = Signal(16, reset_less=True)
201 comb += bd.eq(self.dec.BD << 2)
202 comb += self.imm_out.data.eq(exts(bd, 16, 64))
203 comb += self.imm_out.ok.eq(1)
204 with m.Case(In2Sel.CONST_DS): # sign-extended (14+2=16) bit
205 ds = Signal(16, reset_less=True)
206 comb += ds.eq(self.dec.DS << 2)
207 comb += self.imm_out.data.eq(exts(ds, 16, 64))
208 comb += self.imm_out.ok.eq(1)
209 with m.Case(In2Sel.CONST_M1): # signed (-1)
210 comb += self.imm_out.data.eq(~Const(0, 64)) # all 1s
211 comb += self.imm_out.ok.eq(1)
212 with m.Case(In2Sel.CONST_SH): # unsigned - for shift
213 comb += self.imm_out.data.eq(self.dec.sh)
214 comb += self.imm_out.ok.eq(1)
215 with m.Case(In2Sel.CONST_SH32): # unsigned - for shift
216 comb += self.imm_out.data.eq(self.dec.SH32)
217 comb += self.imm_out.ok.eq(1)
218
219 # decode SPR2 based on instruction type
220 op = self.dec.op
221 # BCREG implicitly uses LR or TAR for 2nd reg
222 # CTR however is already in fast_spr1 *not* 2.
223 with m.If(op.internal_op == MicrOp.OP_BCREG):
224 xo9 = self.dec.FormXL.XO[9] # 3.0B p38 top bit of XO
225 xo5 = self.dec.FormXL.XO[5] # 3.0B p38
226 with m.If(~xo9):
227 comb += self.fast_out.data.eq(FastRegs.LR)
228 comb += self.fast_out.ok.eq(1)
229 with m.Elif(xo5):
230 comb += self.fast_out.data.eq(FastRegs.TAR)
231 comb += self.fast_out.ok.eq(1)
232
233 return m
234
235
236 class DecodeC(Elaboratable):
237 """DecodeC from instruction
238
239 decodes register RC. this is "lane 3" into some CompUnits (not many)
240 """
241
242 def __init__(self, dec):
243 self.dec = dec
244 self.sel_in = Signal(In3Sel, reset_less=True)
245 self.insn_in = Signal(32, reset_less=True)
246 self.reg_out = Data(5, "reg_c")
247
248 def elaborate(self, platform):
249 m = Module()
250 comb = m.d.comb
251
252 # select Register C field
253 with m.Switch(self.sel_in):
254 with m.Case(In3Sel.RB):
255 # for M-Form shiftrot
256 comb += self.reg_out.data.eq(self.dec.RB)
257 comb += self.reg_out.ok.eq(1)
258 with m.Case(In3Sel.RS):
259 comb += self.reg_out.data.eq(self.dec.RS)
260 comb += self.reg_out.ok.eq(1)
261
262 return m
263
264
265 class DecodeOut(Elaboratable):
266 """DecodeOut from instruction
267
268 decodes output register RA, RT or SPR
269 """
270
271 def __init__(self, dec):
272 self.dec = dec
273 self.sel_in = Signal(OutSel, reset_less=True)
274 self.insn_in = Signal(32, reset_less=True)
275 self.reg_out = Data(5, "reg_o")
276 self.spr_out = Data(SPR, "spr_o")
277 self.fast_out = Data(3, "fast_o")
278
279 def elaborate(self, platform):
280 m = Module()
281 comb = m.d.comb
282 m.submodules.sprmap = sprmap = SPRMap()
283 op = self.dec.op
284
285 # select Register out field
286 with m.Switch(self.sel_in):
287 with m.Case(OutSel.RT):
288 comb += self.reg_out.data.eq(self.dec.RT)
289 comb += self.reg_out.ok.eq(1)
290 with m.Case(OutSel.RA):
291 comb += self.reg_out.data.eq(self.dec.RA)
292 comb += self.reg_out.ok.eq(1)
293 with m.Case(OutSel.SPR):
294 spr = Signal(10, reset_less=True)
295 comb += spr.eq(decode_spr_num(self.dec.SPR)) # from XFX
296 # MFSPR move to SPRs - needs mapping
297 with m.If(op.internal_op == MicrOp.OP_MTSPR):
298 comb += sprmap.spr_i.eq(spr)
299 comb += self.spr_out.eq(sprmap.spr_o)
300 comb += self.fast_out.eq(sprmap.fast_o)
301
302 with m.Switch(op.internal_op):
303
304 # BC or BCREG: implicit register (CTR) NOTE: same in DecodeA
305 with m.Case(MicrOp.OP_BC, MicrOp.OP_BCREG):
306 with m.If(~self.dec.BO[2]): # 3.0B p38 BO2=0, use CTR reg
307 # constant: CTR
308 comb += self.fast_out.data.eq(FastRegs.CTR)
309 comb += self.fast_out.ok.eq(1)
310
311 # RFID 1st spr (fast)
312 with m.Case(MicrOp.OP_RFID):
313 comb += self.fast_out.data.eq(FastRegs.SRR0) # constant: SRR0
314 comb += self.fast_out.ok.eq(1)
315
316 return m
317
318
319 class DecodeOut2(Elaboratable):
320 """DecodeOut2 from instruction
321
322 decodes output registers
323 """
324
325 def __init__(self, dec):
326 self.dec = dec
327 self.sel_in = Signal(OutSel, reset_less=True)
328 self.lk = Signal(reset_less=True)
329 self.insn_in = Signal(32, reset_less=True)
330 self.reg_out = Data(5, "reg_o")
331 self.fast_out = Data(3, "fast_o")
332
333 def elaborate(self, platform):
334 m = Module()
335 comb = m.d.comb
336
337 # update mode LD/ST uses read-reg A also as an output
338 with m.If(self.dec.op.upd == LDSTMode.update):
339 comb += self.reg_out.eq(self.dec.RA)
340 comb += self.reg_out.ok.eq(1)
341
342 # B, BC or BCREG: potential implicit register (LR) output
343 # these give bl, bcl, bclrl, etc.
344 op = self.dec.op
345 with m.Switch(op.internal_op):
346
347 # BC* implicit register (LR)
348 with m.Case(MicrOp.OP_BC, MicrOp.OP_B, MicrOp.OP_BCREG):
349 with m.If(self.lk): # "link" mode
350 comb += self.fast_out.data.eq(FastRegs.LR) # constant: LR
351 comb += self.fast_out.ok.eq(1)
352
353 # RFID 2nd spr (fast)
354 with m.Case(MicrOp.OP_RFID):
355 comb += self.fast_out.data.eq(FastRegs.SRR1) # constant: SRR1
356 comb += self.fast_out.ok.eq(1)
357
358 return m
359
360
361 class DecodeRC(Elaboratable):
362 """DecodeRc from instruction
363
364 decodes Record bit Rc
365 """
366
367 def __init__(self, dec):
368 self.dec = dec
369 self.sel_in = Signal(RC, reset_less=True)
370 self.insn_in = Signal(32, reset_less=True)
371 self.rc_out = Data(1, "rc")
372
373 def elaborate(self, platform):
374 m = Module()
375 comb = m.d.comb
376
377 # select Record bit out field
378 with m.Switch(self.sel_in):
379 with m.Case(RC.RC):
380 comb += self.rc_out.data.eq(self.dec.Rc)
381 comb += self.rc_out.ok.eq(1)
382 with m.Case(RC.ONE):
383 comb += self.rc_out.data.eq(1)
384 comb += self.rc_out.ok.eq(1)
385 with m.Case(RC.NONE):
386 comb += self.rc_out.data.eq(0)
387 comb += self.rc_out.ok.eq(1)
388
389 return m
390
391
392 class DecodeOE(Elaboratable):
393 """DecodeOE from instruction
394
395 decodes OE field: uses RC decode detection which might not be good
396
397 -- For now, use "rc" in the decode table to decide whether oe exists.
398 -- This is not entirely correct architecturally: For mulhd and
399 -- mulhdu, the OE field is reserved. It remains to be seen what an
400 -- actual POWER9 does if we set it on those instructions, for now we
401 -- test that further down when assigning to the multiplier oe input.
402 """
403
404 def __init__(self, dec):
405 self.dec = dec
406 self.sel_in = Signal(RC, reset_less=True)
407 self.insn_in = Signal(32, reset_less=True)
408 self.oe_out = Data(1, "oe")
409
410 def elaborate(self, platform):
411 m = Module()
412 comb = m.d.comb
413 op = self.dec.op
414
415 with m.Switch(op.internal_op):
416
417 # mulhw, mulhwu, mulhd, mulhdu - these *ignore* OE
418 # also rotate
419 # XXX ARGH! ignoring OE causes incompatibility with microwatt
420 # http://lists.libre-soc.org/pipermail/libre-soc-dev/2020-August/000302.html
421 with m.Case(MicrOp.OP_MUL_H64, MicrOp.OP_MUL_H32,
422 MicrOp.OP_EXTS, MicrOp.OP_CNTZ,
423 MicrOp.OP_SHL, MicrOp.OP_SHR, MicrOp.OP_RLC,
424 MicrOp.OP_LOAD, MicrOp.OP_STORE,
425 MicrOp.OP_RLCL, MicrOp.OP_RLCR,
426 MicrOp.OP_EXTSWSLI):
427 pass
428
429 # all other ops decode OE field
430 with m.Default():
431 # select OE bit out field
432 with m.Switch(self.sel_in):
433 with m.Case(RC.RC):
434 comb += self.oe_out.data.eq(self.dec.OE)
435 comb += self.oe_out.ok.eq(1)
436
437 return m
438
439
440 class DecodeCRIn(Elaboratable):
441 """Decodes input CR from instruction
442
443 CR indices - insn fields - (not the data *in* the CR) require only 3
444 bits because they refer to CR0-CR7
445 """
446
447 def __init__(self, dec):
448 self.dec = dec
449 self.sel_in = Signal(CRInSel, reset_less=True)
450 self.insn_in = Signal(32, reset_less=True)
451 self.cr_bitfield = Data(3, "cr_bitfield")
452 self.cr_bitfield_b = Data(3, "cr_bitfield_b")
453 self.cr_bitfield_o = Data(3, "cr_bitfield_o")
454 self.whole_reg = Data(8, "cr_fxm")
455
456 def elaborate(self, platform):
457 m = Module()
458 m.submodules.ppick = ppick = PriorityPicker(8, reverse_i=True,
459 reverse_o=True)
460
461 comb = m.d.comb
462 op = self.dec.op
463
464 comb += self.cr_bitfield.ok.eq(0)
465 comb += self.cr_bitfield_b.ok.eq(0)
466 comb += self.whole_reg.ok.eq(0)
467 with m.Switch(self.sel_in):
468 with m.Case(CRInSel.NONE):
469 pass # No bitfield activated
470 with m.Case(CRInSel.CR0):
471 comb += self.cr_bitfield.data.eq(0) # CR0 (MSB0 numbering)
472 comb += self.cr_bitfield.ok.eq(1)
473 with m.Case(CRInSel.BI):
474 comb += self.cr_bitfield.data.eq(self.dec.BI[2:5])
475 comb += self.cr_bitfield.ok.eq(1)
476 with m.Case(CRInSel.BFA):
477 comb += self.cr_bitfield.data.eq(self.dec.FormX.BFA)
478 comb += self.cr_bitfield.ok.eq(1)
479 with m.Case(CRInSel.BA_BB):
480 comb += self.cr_bitfield.data.eq(self.dec.BA[2:5])
481 comb += self.cr_bitfield.ok.eq(1)
482 comb += self.cr_bitfield_b.data.eq(self.dec.BB[2:5])
483 comb += self.cr_bitfield_b.ok.eq(1)
484 comb += self.cr_bitfield_o.data.eq(self.dec.BT[2:5])
485 comb += self.cr_bitfield_o.ok.eq(1)
486 with m.Case(CRInSel.BC):
487 comb += self.cr_bitfield.data.eq(self.dec.BC[2:5])
488 comb += self.cr_bitfield.ok.eq(1)
489 with m.Case(CRInSel.WHOLE_REG):
490 comb += self.whole_reg.ok.eq(1)
491 move_one = Signal(reset_less=True)
492 comb += move_one.eq(self.insn_in[20]) # MSB0 bit 11
493 with m.If((op.internal_op == MicrOp.OP_MFCR) & move_one):
494 # must one-hot the FXM field
495 comb += ppick.i.eq(self.dec.FXM)
496 comb += self.whole_reg.data.eq(ppick.o)
497 with m.Else():
498 # otherwise use all of it
499 comb += self.whole_reg.data.eq(0xff)
500
501 return m
502
503
504 class DecodeCROut(Elaboratable):
505 """Decodes input CR from instruction
506
507 CR indices - insn fields - (not the data *in* the CR) require only 3
508 bits because they refer to CR0-CR7
509 """
510
511 def __init__(self, dec):
512 self.dec = dec
513 self.rc_in = Signal(reset_less=True)
514 self.sel_in = Signal(CROutSel, reset_less=True)
515 self.insn_in = Signal(32, reset_less=True)
516 self.cr_bitfield = Data(3, "cr_bitfield")
517 self.whole_reg = Data(8, "cr_fxm")
518
519 def elaborate(self, platform):
520 m = Module()
521 comb = m.d.comb
522 op = self.dec.op
523 m.submodules.ppick = ppick = PriorityPicker(8, reverse_i=True,
524 reverse_o=True)
525
526 comb += self.cr_bitfield.ok.eq(0)
527 comb += self.whole_reg.ok.eq(0)
528 with m.Switch(self.sel_in):
529 with m.Case(CROutSel.NONE):
530 pass # No bitfield activated
531 with m.Case(CROutSel.CR0):
532 comb += self.cr_bitfield.data.eq(0) # CR0 (MSB0 numbering)
533 comb += self.cr_bitfield.ok.eq(self.rc_in) # only when RC=1
534 with m.Case(CROutSel.BF):
535 comb += self.cr_bitfield.data.eq(self.dec.FormX.BF)
536 comb += self.cr_bitfield.ok.eq(1)
537 with m.Case(CROutSel.BT):
538 comb += self.cr_bitfield.data.eq(self.dec.FormXL.BT[2:5])
539 comb += self.cr_bitfield.ok.eq(1)
540 with m.Case(CROutSel.WHOLE_REG):
541 comb += self.whole_reg.ok.eq(1)
542 move_one = Signal(reset_less=True)
543 comb += move_one.eq(self.insn_in[20])
544 with m.If((op.internal_op == MicrOp.OP_MTCRF)):
545 with m.If(move_one):
546 # must one-hot the FXM field
547 comb += ppick.i.eq(self.dec.FXM)
548 with m.If(ppick.en_o):
549 comb += self.whole_reg.data.eq(ppick.o)
550 with m.Else():
551 comb += self.whole_reg.data.eq(0b00000001) # CR7
552 with m.Else():
553 comb += self.whole_reg.data.eq(self.dec.FXM)
554 with m.Else():
555 # otherwise use all of it
556 comb += self.whole_reg.data.eq(0xff)
557
558 return m
559
560
561 class PowerDecode2(Elaboratable):
562 """PowerDecode2: the main instruction decoder.
563
564 whilst PowerDecode is responsible for decoding the actual opcode, this
565 module encapsulates further specialist, sparse information and
566 expansion of fields that is inconvenient to have in the CSV files.
567 for example: the encoding of the immediates, which are detected
568 and expanded out to their full value from an annotated (enum)
569 representation.
570
571 implicit register usage is also set up, here. for example: OP_BC
572 requires implicitly reading CTR, OP_RFID requires implicitly writing
573 to SRR1 and so on.
574
575 in addition, PowerDecoder2 is responsible for detecting whether
576 instructions are illegal (or privileged) or not, and instead of
577 just leaving at that, *replacing* the instruction to execute with
578 a suitable alternative (trap).
579 """
580
581 def __init__(self, dec):
582
583 self.dec = dec
584 self.e = Decode2ToExecute1Type()
585
586 # state information needed by the Decoder (TODO: this as a Record)
587 self.state = CoreState("dec2")
588
589 def ports(self):
590 return self.dec.ports() + self.e.ports()
591
592 def elaborate(self, platform):
593 m = Module()
594 comb = m.d.comb
595 state = self.state
596 e_out, op, do_out = self.e, self.dec.op, self.e.do
597 dec_spr, msr, cia, ext_irq = state.dec, state.msr, state.pc, state.eint
598
599 # fill in for a normal instruction (not an exception)
600 # copy over if non-exception, non-privileged etc. is detected
601 e = Decode2ToExecute1Type()
602 do = e.do
603
604 # set up submodule decoders
605 m.submodules.dec = self.dec
606 m.submodules.dec_a = dec_a = DecodeA(self.dec)
607 m.submodules.dec_b = dec_b = DecodeB(self.dec)
608 m.submodules.dec_c = dec_c = DecodeC(self.dec)
609 m.submodules.dec_o = dec_o = DecodeOut(self.dec)
610 m.submodules.dec_o2 = dec_o2 = DecodeOut2(self.dec)
611 m.submodules.dec_rc = dec_rc = DecodeRC(self.dec)
612 m.submodules.dec_oe = dec_oe = DecodeOE(self.dec)
613 m.submodules.dec_cr_in = dec_cr_in = DecodeCRIn(self.dec)
614 m.submodules.dec_cr_out = dec_cr_out = DecodeCROut(self.dec)
615
616 # copy instruction through...
617 for i in [do.insn, dec_a.insn_in, dec_b.insn_in,
618 dec_c.insn_in, dec_o.insn_in, dec_o2.insn_in, dec_rc.insn_in,
619 dec_oe.insn_in, dec_cr_in.insn_in, dec_cr_out.insn_in]:
620 comb += i.eq(self.dec.opcode_in)
621
622 # ...and subdecoders' input fields
623 comb += dec_a.sel_in.eq(op.in1_sel)
624 comb += dec_b.sel_in.eq(op.in2_sel)
625 comb += dec_c.sel_in.eq(op.in3_sel)
626 comb += dec_o.sel_in.eq(op.out_sel)
627 comb += dec_o2.sel_in.eq(op.out_sel)
628 comb += dec_o2.lk.eq(do.lk)
629 comb += dec_rc.sel_in.eq(op.rc_sel)
630 comb += dec_oe.sel_in.eq(op.rc_sel) # XXX should be OE sel
631 comb += dec_cr_in.sel_in.eq(op.cr_in)
632 comb += dec_cr_out.sel_in.eq(op.cr_out)
633 comb += dec_cr_out.rc_in.eq(dec_rc.rc_out.data)
634
635 # copy "state" over
636 comb += do.msr.eq(msr)
637 comb += do.cia.eq(cia)
638
639 # set up instruction, pick fn unit
640 # no op: defaults to OP_ILLEGAL
641 comb += do.insn_type.eq(op.internal_op)
642 comb += do.fn_unit.eq(op.function_unit)
643
644 # registers a, b, c and out and out2 (LD/ST EA)
645 comb += e.read_reg1.eq(dec_a.reg_out)
646 comb += e.read_reg2.eq(dec_b.reg_out)
647 comb += e.read_reg3.eq(dec_c.reg_out)
648 comb += e.write_reg.eq(dec_o.reg_out)
649 comb += e.write_ea.eq(dec_o2.reg_out)
650 comb += do.imm_data.eq(dec_b.imm_out) # immediate in RB (usually)
651 comb += do.zero_a.eq(dec_a.immz_out) # RA==0 detected
652
653 # rc and oe out
654 comb += do.rc.eq(dec_rc.rc_out)
655 comb += do.oe.eq(dec_oe.oe_out)
656
657 # SPRs out
658 comb += e.read_spr1.eq(dec_a.spr_out)
659 comb += e.write_spr.eq(dec_o.spr_out)
660
661 # Fast regs out
662 comb += e.read_fast1.eq(dec_a.fast_out)
663 comb += e.read_fast2.eq(dec_b.fast_out)
664 comb += e.write_fast1.eq(dec_o.fast_out)
665 comb += e.write_fast2.eq(dec_o2.fast_out)
666
667 # condition registers (CR)
668 comb += e.read_cr1.eq(dec_cr_in.cr_bitfield)
669 comb += e.read_cr2.eq(dec_cr_in.cr_bitfield_b)
670 comb += e.read_cr3.eq(dec_cr_in.cr_bitfield_o)
671 comb += e.write_cr.eq(dec_cr_out.cr_bitfield)
672
673 comb += do.read_cr_whole.eq(dec_cr_in.whole_reg)
674 comb += do.write_cr_whole.eq(dec_cr_out.whole_reg)
675 comb += do.write_cr0.eq(dec_cr_out.cr_bitfield.ok)
676
677 # decoded/selected instruction flags
678 comb += do.data_len.eq(op.ldst_len)
679 comb += do.invert_in.eq(op.inv_a)
680 comb += do.invert_out.eq(op.inv_out)
681 comb += do.input_carry.eq(op.cry_in) # carry comes in
682 comb += do.output_carry.eq(op.cry_out) # carry goes out
683 comb += do.is_32bit.eq(op.is_32b)
684 comb += do.is_signed.eq(op.sgn)
685 with m.If(op.lk):
686 comb += do.lk.eq(self.dec.LK) # XXX TODO: accessor
687
688 comb += do.byte_reverse.eq(op.br)
689 comb += do.sign_extend.eq(op.sgn_ext)
690 comb += do.ldst_mode.eq(op.upd) # LD/ST mode (update, cache-inhibit)
691
692 # These should be removed eventually
693 comb += do.input_cr.eq(op.cr_in) # condition reg comes in
694 comb += do.output_cr.eq(op.cr_out) # condition reg goes in
695
696 # sigh this is exactly the sort of thing for which the
697 # decoder is designed to not need. MTSPR, MFSPR and others need
698 # access to the XER bits. however setting e.oe is not appropriate
699 with m.If(op.internal_op == MicrOp.OP_MFSPR):
700 comb += e.xer_in.eq(0b111) # SO, CA, OV
701 with m.If(op.internal_op == MicrOp.OP_CMP):
702 comb += e.xer_in.eq(1<<XERRegs.SO) # SO
703 with m.If(op.internal_op == MicrOp.OP_MTSPR):
704 comb += e.xer_out.eq(1)
705
706 # set the trapaddr to 0x700 for a td/tw/tdi/twi operation
707 with m.If(op.internal_op == MicrOp.OP_TRAP):
708 # *DO NOT* call self.trap here. that would reset absolutely
709 # rverything including destroying read of RA and RB.
710 comb += do.trapaddr.eq(0x70) # addr=0x700 (strip first nibble)
711
712 # check if instruction is privileged
713 is_priv_insn = instr_is_priv(m, op.internal_op, e.do.insn)
714
715 # external interrupt? only if MSR.EE set
716 with m.If(ext_irq & msr[MSR.EE]): # v3.0B p944 (MSR.EE)
717 self.trap(m, TT.EINT, 0x500)
718
719 # decrement counter (v3.0B p1099): TODO 32-bit version (MSR.LPCR)
720 with m.If(dec_spr[63] & msr[MSR.EE]): # v3.0B 6.5.11 p1076
721 self.trap(m, TT.DEC, 0x900) # v3.0B 6.5 p1065
722
723 # privileged instruction trap
724 with m.Elif(is_priv_insn & msr[MSR.PR]):
725 self.trap(m, TT.PRIV, 0x700)
726
727 # illegal instruction must redirect to trap. this is done by
728 # *overwriting* the decoded instruction and starting again.
729 # (note: the same goes for interrupts and for privileged operations,
730 # just with different trapaddr and traptype)
731 with m.Elif(op.internal_op == MicrOp.OP_ILLEGAL):
732 # illegal instruction trap
733 self.trap(m, TT.ILLEG, 0x700)
734
735 # no exception, just copy things to the output
736 with m.Else():
737 comb += e_out.eq(e)
738
739 # trap: (note e.insn_type so this includes OP_ILLEGAL) set up fast regs
740 # Note: OP_SC could actually be modified to just be a trap
741 with m.If((do_out.insn_type == MicrOp.OP_TRAP) |
742 (do_out.insn_type == MicrOp.OP_SC)):
743 # TRAP write fast1 = SRR0
744 comb += e_out.write_fast1.data.eq(FastRegs.SRR0) # constant: SRR0
745 comb += e_out.write_fast1.ok.eq(1)
746 # TRAP write fast2 = SRR1
747 comb += e_out.write_fast2.data.eq(FastRegs.SRR1) # constant: SRR1
748 comb += e_out.write_fast2.ok.eq(1)
749
750 # RFID: needs to read SRR0/1
751 with m.If(do_out.insn_type == MicrOp.OP_RFID):
752 # TRAP read fast1 = SRR0
753 comb += e_out.read_fast1.data.eq(FastRegs.SRR0) # constant: SRR0
754 comb += e_out.read_fast1.ok.eq(1)
755 # TRAP read fast2 = SRR1
756 comb += e_out.read_fast2.data.eq(FastRegs.SRR1) # constant: SRR1
757 comb += e_out.read_fast2.ok.eq(1)
758
759 return m
760
761 def trap(self, m, traptype, trapaddr):
762 """trap: this basically "rewrites" the decoded instruction as a trap
763 """
764 comb = m.d.comb
765 op, do, e = self.dec.op, self.e.do, self.e
766 comb += e.eq(0) # reset eeeeeverything
767
768 # start again
769 comb += do.insn.eq(self.dec.opcode_in)
770 comb += do.insn_type.eq(MicrOp.OP_TRAP)
771 comb += do.fn_unit.eq(Function.TRAP)
772 comb += do.trapaddr.eq(trapaddr >> 4) # cut bottom 4 bits
773 comb += do.traptype.eq(traptype) # request type
774 comb += do.msr.eq(self.state.msr) # copy of MSR "state"
775 comb += do.cia.eq(self.state.pc) # copy of PC "state"
776
777
778 def get_rdflags(e, cu):
779 rdl = []
780 for idx in range(cu.n_src):
781 regfile, regname, _ = cu.get_in_spec(idx)
782 rdflag, read = regspec_decode_read(e, regfile, regname)
783 rdl.append(rdflag)
784 print("rdflags", rdl)
785 return Cat(*rdl)
786
787
788 if __name__ == '__main__':
789 pdecode = create_pdecode()
790 dec2 = PowerDecode2(pdecode)
791 vl = rtlil.convert(dec2, ports=dec2.ports() + pdecode.ports())
792 with open("dec2.il", "w") as f:
793 f.write(vl)