remap SPR PowerISA numbers to internal SPR enum
[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
12 from nmutil.iocontrol import RecordObject
13 from nmutil.extend import exts
14
15 from soc.decoder.power_regspec_map import regspec_decode_read
16 from soc.decoder.power_regspec_map import regspec_decode_write
17 from soc.decoder.power_decoder import create_pdecode
18 from soc.decoder.power_enums import (InternalOp, CryIn, Function,
19 CRInSel, CROutSel,
20 LdstLen, In1Sel, In2Sel, In3Sel,
21 OutSel, SPR, RC)
22 from soc.decoder.decode2execute1 import Decode2ToExecute1Type, Data
23
24 from soc.regfile.regfiles import FastRegs
25
26 # see traptype (and trap main_stage.py)
27
28 TT_FP = 1<<0
29 TT_PRIV = 1<<1
30 TT_TRAP = 1<<2
31 TT_ADDR = 1<<3
32 TT_ILLEG = 1<<4
33
34 def decode_spr_num(spr):
35 return Cat(spr[5:10], spr[0:5])
36
37
38 def instr_is_priv(m, op, insn):
39 """determines if the instruction is privileged or not
40 """
41 comb = m.d.comb
42 Signal = is_priv_insn(reset_less=True)
43 with m.Switch(op):
44 with m.Case(InternalOp.OP_ATTN) : comb += is_priv_insn.eq(1)
45 with m.Case(InternalOp.OP_MFMSR) : comb += is_priv_insn.eq(1)
46 with m.Case(InternalOp.OP_MTMSRD): comb += is_priv_insn.eq(1)
47 with m.Case(InternalOp.OP_RFID) : comb += is_priv_insn.eq(1)
48 with m.Case(InternalOp.OP_TLBIE) : comb += is_priv_insn.eq(1)
49 with m.If(op == OP_MFSPR | op == OP_MTSPR):
50 with m.If(insn[20]): # field XFX.spr[-1] i think
51 comb += is_priv_insn.eq(1)
52 return is_priv_insn
53
54
55 class SPRMap(Elaboratable):
56 """SPRMap: maps POWER9 SPR numbers to internal enum values
57 """
58 def __init__(self):
59 self.spr_i = Signal(10, reset_less=True)
60 self.spr_o = Signal(SPR, reset_less=True)
61
62 def elaborate(self, platform):
63 m = Module()
64 with m.Switch(self.spr_i):
65 for i, x in enumerate(SPR):
66 with m.Case(x.value):
67 m.d.comb += self.spr_o.eq(i)
68 return m
69
70
71 class DecodeA(Elaboratable):
72 """DecodeA from instruction
73
74 decodes register RA, whether immediate-zero, implicit and
75 explicit CSRs
76 """
77
78 def __init__(self, dec):
79 self.dec = dec
80 self.sel_in = Signal(In1Sel, reset_less=True)
81 self.insn_in = Signal(32, reset_less=True)
82 self.reg_out = Data(5, name="reg_a")
83 self.immz_out = Signal(reset_less=True)
84 self.spr_out = Data(SPR, "spr_a")
85 self.fast_out = Data(3, "fast_a")
86
87 def elaborate(self, platform):
88 m = Module()
89 comb = m.d.comb
90 m.submodules.sprmap = sprmap = SPRMap()
91
92 # select Register A field
93 ra = Signal(5, reset_less=True)
94 comb += ra.eq(self.dec.RA)
95 with m.If((self.sel_in == In1Sel.RA) |
96 ((self.sel_in == In1Sel.RA_OR_ZERO) &
97 (ra != Const(0, 5)))):
98 comb += self.reg_out.data.eq(ra)
99 comb += self.reg_out.ok.eq(1)
100
101 # zero immediate requested
102 with m.If((self.sel_in == In1Sel.RA_OR_ZERO) &
103 (self.reg_out.data == Const(0, 5))):
104 comb += self.immz_out.eq(1)
105
106 # some Logic/ALU ops have RS as the 3rd arg, but no "RA".
107 with m.If(self.sel_in == In1Sel.RS):
108 comb += self.reg_out.data.eq(self.dec.RS)
109 comb += self.reg_out.ok.eq(1)
110
111 # decode Fast-SPR based on instruction type
112 op = self.dec.op
113 # BC or BCREG: potential implicit register (CTR) NOTE: same in DecodeOut
114 with m.If(op.internal_op == InternalOp.OP_BC):
115 with m.If(~self.dec.BO[2]): # 3.0B p38 BO2=0, use CTR reg
116 comb += self.fast_out.data.eq(FastRegs.CTR) # constant: CTR
117 comb += self.fast_out.ok.eq(1)
118 with m.Elif(op.internal_op == InternalOp.OP_BCREG):
119 xo9 = self.dec.FormXL.XO[9] # 3.0B p38 top bit of XO
120 xo5 = self.dec.FormXL.XO[5] # 3.0B p38
121 with m.If(xo9 & ~xo5):
122 comb += self.fast_out.data.eq(FastRegs.CTR) # constant: CTR
123 comb += self.fast_out.ok.eq(1)
124
125 # MFSPR move from SPRs
126 with m.If(op.internal_op == InternalOp.OP_MFSPR):
127 spr = Signal(10, reset_less=True)
128 comb += spr.eq(decode_spr_num(self.dec.SPR)) # from XFX
129 with m.Switch(spr):
130 # fast SPRs
131 with m.Case(SPR.CTR.value):
132 comb += self.fast_out.data.eq(FastRegs.CTR)
133 comb += self.fast_out.ok.eq(1)
134 with m.Case(SPR.LR.value):
135 comb += self.fast_out.data.eq(FastRegs.LR)
136 comb += self.fast_out.ok.eq(1)
137 with m.Case(SPR.TAR.value):
138 comb += self.fast_out.data.eq(FastRegs.TAR)
139 comb += self.fast_out.ok.eq(1)
140 with m.Case(SPR.SRR0.value):
141 comb += self.fast_out.data.eq(FastRegs.SRR0)
142 comb += self.fast_out.ok.eq(1)
143 with m.Case(SPR.SRR1.value):
144 comb += self.fast_out.data.eq(FastRegs.SRR1)
145 comb += self.fast_out.ok.eq(1)
146 with m.Case(SPR.XER.value):
147 pass # do nothing
148 # XXX TODO: map to internal SPR numbers
149 # XXX TODO: dec and tb not to go through mapping.
150 with m.Default():
151 comb += sprmap.spr_i.eq(spr)
152 comb += self.spr_out.data.eq(sprmap.spr_o)
153 comb += self.spr_out.ok.eq(1)
154
155
156 return m
157
158
159 class DecodeB(Elaboratable):
160 """DecodeB from instruction
161
162 decodes register RB, different forms of immediate (signed, unsigned),
163 and implicit SPRs. register B is basically "lane 2" into the CompUnits.
164 by industry-standard convention, "lane 2" is where fully-decoded
165 immediates are muxed in.
166 """
167
168 def __init__(self, dec):
169 self.dec = dec
170 self.sel_in = Signal(In2Sel, reset_less=True)
171 self.insn_in = Signal(32, reset_less=True)
172 self.reg_out = Data(5, "reg_b")
173 self.imm_out = Data(64, "imm_b")
174 self.fast_out = Data(3, "fast_b")
175
176 def elaborate(self, platform):
177 m = Module()
178 comb = m.d.comb
179
180 # select Register B field
181 with m.Switch(self.sel_in):
182 with m.Case(In2Sel.RB):
183 comb += self.reg_out.data.eq(self.dec.RB)
184 comb += self.reg_out.ok.eq(1)
185 with m.Case(In2Sel.RS):
186 comb += self.reg_out.data.eq(self.dec.RS) # for M-Form shiftrot
187 comb += self.reg_out.ok.eq(1)
188 with m.Case(In2Sel.CONST_UI):
189 comb += self.imm_out.data.eq(self.dec.UI)
190 comb += self.imm_out.ok.eq(1)
191 with m.Case(In2Sel.CONST_SI): # TODO: sign-extend here?
192 comb += self.imm_out.data.eq(
193 exts(self.dec.SI, 16, 64))
194 comb += self.imm_out.ok.eq(1)
195 with m.Case(In2Sel.CONST_UI_HI):
196 comb += self.imm_out.data.eq(self.dec.UI<<16)
197 comb += self.imm_out.ok.eq(1)
198 with m.Case(In2Sel.CONST_SI_HI): # TODO: sign-extend here?
199 comb += self.imm_out.data.eq(self.dec.SI<<16)
200 comb += self.imm_out.data.eq(
201 exts(self.dec.SI << 16, 32, 64))
202 comb += self.imm_out.ok.eq(1)
203 with m.Case(In2Sel.CONST_LI):
204 comb += self.imm_out.data.eq(self.dec.LI<<2)
205 comb += self.imm_out.ok.eq(1)
206 with m.Case(In2Sel.CONST_BD):
207 comb += self.imm_out.data.eq(self.dec.BD<<2)
208 comb += self.imm_out.ok.eq(1)
209 with m.Case(In2Sel.CONST_DS):
210 comb += self.imm_out.data.eq(self.dec.DS<<2)
211 comb += self.imm_out.ok.eq(1)
212 with m.Case(In2Sel.CONST_M1):
213 comb += self.imm_out.data.eq(~Const(0, 64)) # all 1s
214 comb += self.imm_out.ok.eq(1)
215 with m.Case(In2Sel.CONST_SH):
216 comb += self.imm_out.data.eq(self.dec.sh)
217 comb += self.imm_out.ok.eq(1)
218 with m.Case(In2Sel.CONST_SH32):
219 comb += self.imm_out.data.eq(self.dec.SH32)
220 comb += self.imm_out.ok.eq(1)
221
222 # decode SPR2 based on instruction type
223 op = self.dec.op
224 # BCREG implicitly uses LR or TAR for 2nd reg
225 # CTR however is already in fast_spr1 *not* 2.
226 with m.If(op.internal_op == InternalOp.OP_BCREG):
227 xo9 = self.dec.FormXL.XO[9] # 3.0B p38 top bit of XO
228 xo5 = self.dec.FormXL.XO[5] # 3.0B p38
229 with m.If(~xo9):
230 comb += self.fast_out.data.eq(FastRegs.LR)
231 comb += self.fast_out.ok.eq(1)
232 with m.Elif(xo5):
233 comb += self.fast_out.data.eq(FastRegs.TAR)
234 comb += self.fast_out.ok.eq(1)
235
236 return m
237
238
239 class DecodeC(Elaboratable):
240 """DecodeC from instruction
241
242 decodes register RC. this is "lane 3" into some CompUnits (not many)
243 """
244
245 def __init__(self, dec):
246 self.dec = dec
247 self.sel_in = Signal(In3Sel, reset_less=True)
248 self.insn_in = Signal(32, reset_less=True)
249 self.reg_out = Data(5, "reg_c")
250
251 def elaborate(self, platform):
252 m = Module()
253 comb = m.d.comb
254
255 # select Register C field
256 with m.Switch(self.sel_in):
257 with m.Case(In3Sel.RB):
258 comb += self.reg_out.data.eq(self.dec.RB) # for M-Form shiftrot
259 comb += self.reg_out.ok.eq(1)
260 with m.Case(In3Sel.RS):
261 comb += self.reg_out.data.eq(self.dec.RS)
262 comb += self.reg_out.ok.eq(1)
263
264 return m
265
266
267 class DecodeOut(Elaboratable):
268 """DecodeOut from instruction
269
270 decodes output register RA, RT or SPR
271 """
272
273 def __init__(self, dec):
274 self.dec = dec
275 self.sel_in = Signal(OutSel, reset_less=True)
276 self.insn_in = Signal(32, reset_less=True)
277 self.reg_out = Data(5, "reg_o")
278 self.spr_out = Data(SPR, "spr_o")
279 self.fast_out = Data(3, "fast_o")
280
281 def elaborate(self, platform):
282 m = Module()
283 comb = m.d.comb
284 m.submodules.sprmap = sprmap = SPRMap()
285 op = self.dec.op
286
287 # select Register out field
288 with m.Switch(self.sel_in):
289 with m.Case(OutSel.RT):
290 comb += self.reg_out.data.eq(self.dec.RT)
291 comb += self.reg_out.ok.eq(1)
292 with m.Case(OutSel.RA):
293 comb += self.reg_out.data.eq(self.dec.RA)
294 comb += self.reg_out.ok.eq(1)
295 with m.Case(OutSel.SPR):
296 spr = Signal(10, reset_less=True)
297 comb += spr.eq(decode_spr_num(self.dec.SPR)) # from XFX
298 # TODO MTSPR 1st spr (fast)
299 with m.If(op.internal_op == InternalOp.OP_MTSPR):
300 with m.Switch(spr):
301 # fast SPRs
302 with m.Case(SPR.CTR.value):
303 comb += self.fast_out.data.eq(FastRegs.CTR)
304 comb += self.fast_out.ok.eq(1)
305 with m.Case(SPR.LR.value):
306 comb += self.fast_out.data.eq(FastRegs.LR)
307 comb += self.fast_out.ok.eq(1)
308 with m.Case(SPR.TAR.value):
309 comb += self.fast_out.data.eq(FastRegs.TAR)
310 comb += self.fast_out.ok.eq(1)
311 with m.Case(SPR.SRR0.value):
312 comb += self.fast_out.data.eq(FastRegs.SRR0)
313 comb += self.fast_out.ok.eq(1)
314 with m.Case(SPR.SRR1.value):
315 comb += self.fast_out.data.eq(FastRegs.SRR1)
316 comb += self.fast_out.ok.eq(1)
317 with m.Case(SPR.XER.value):
318 pass # do nothing
319 # XXX TODO: map to internal SPR numbers
320 # XXX TODO: dec and tb not to go through mapping.
321 with m.Default():
322 comb += sprmap.spr_i.eq(spr)
323 comb += self.spr_out.data.eq(sprmap.spr_o)
324 comb += self.spr_out.ok.eq(1)
325
326 # BC or BCREG: potential implicit register (CTR) NOTE: same in DecodeA
327 op = self.dec.op
328 with m.If((op.internal_op == InternalOp.OP_BC) |
329 (op.internal_op == InternalOp.OP_BCREG)):
330 with m.If(~self.dec.BO[2]): # 3.0B p38 BO2=0, use CTR reg
331 comb += self.fast_out.data.eq(FastRegs.CTR) # constant: CTR
332 comb += self.fast_out.ok.eq(1)
333
334 # RFID 1st spr (fast)
335 with m.If(op.internal_op == InternalOp.OP_RFID):
336 comb += self.fast_out.data.eq(FastRegs.SRR0) # constant: SRR0
337 comb += self.fast_out.ok.eq(1)
338
339 return m
340
341
342 class DecodeOut2(Elaboratable):
343 """DecodeOut2 from instruction
344
345 decodes output registers
346 """
347
348 def __init__(self, dec):
349 self.dec = dec
350 self.sel_in = Signal(OutSel, reset_less=True)
351 self.lk = Signal(reset_less=True)
352 self.insn_in = Signal(32, reset_less=True)
353 self.reg_out = Data(5, "reg_o")
354 self.fast_out = Data(3, "fast_o")
355
356 def elaborate(self, platform):
357 m = Module()
358 comb = m.d.comb
359
360 # update mode LD/ST uses read-reg A also as an output
361 with m.If(self.dec.op.upd):
362 comb += self.reg_out.eq(self.dec.RA)
363 comb += self.reg_out.ok.eq(1)
364
365 # BC or BCREG: potential implicit register (LR) output
366 op = self.dec.op
367 with m.If((op.internal_op == InternalOp.OP_BC) |
368 (op.internal_op == InternalOp.OP_BCREG)):
369 with m.If(self.lk): # "link" mode
370 comb += self.fast_out.data.eq(FastRegs.LR) # constant: LR
371 comb += self.fast_out.ok.eq(1)
372
373 # RFID 2nd spr (fast)
374 with m.If(op.internal_op == InternalOp.OP_RFID):
375 comb += self.fast_out.data.eq(FastRegs.SRR1) # constant: SRR1
376 comb += self.fast_out.ok.eq(1)
377
378 return m
379
380
381 class DecodeRC(Elaboratable):
382 """DecodeRc from instruction
383
384 decodes Record bit Rc
385 """
386 def __init__(self, dec):
387 self.dec = dec
388 self.sel_in = Signal(RC, reset_less=True)
389 self.insn_in = Signal(32, reset_less=True)
390 self.rc_out = Data(1, "rc")
391
392 def elaborate(self, platform):
393 m = Module()
394 comb = m.d.comb
395
396 # select Record bit out field
397 with m.Switch(self.sel_in):
398 with m.Case(RC.RC):
399 comb += self.rc_out.data.eq(self.dec.Rc)
400 comb += self.rc_out.ok.eq(1)
401 with m.Case(RC.ONE):
402 comb += self.rc_out.data.eq(1)
403 comb += self.rc_out.ok.eq(1)
404 with m.Case(RC.NONE):
405 comb += self.rc_out.data.eq(0)
406 comb += self.rc_out.ok.eq(1)
407
408 return m
409
410
411 class DecodeOE(Elaboratable):
412 """DecodeOE from instruction
413
414 decodes OE field: uses RC decode detection which might not be good
415
416 -- For now, use "rc" in the decode table to decide whether oe exists.
417 -- This is not entirely correct architecturally: For mulhd and
418 -- mulhdu, the OE field is reserved. It remains to be seen what an
419 -- actual POWER9 does if we set it on those instructions, for now we
420 -- test that further down when assigning to the multiplier oe input.
421 """
422 def __init__(self, dec):
423 self.dec = dec
424 self.sel_in = Signal(RC, reset_less=True)
425 self.insn_in = Signal(32, reset_less=True)
426 self.oe_out = Data(1, "oe")
427
428 def elaborate(self, platform):
429 m = Module()
430 comb = m.d.comb
431
432 # select OE bit out field
433 with m.Switch(self.sel_in):
434 with m.Case(RC.RC):
435 comb += self.oe_out.data.eq(self.dec.OE)
436 comb += self.oe_out.ok.eq(1)
437
438 return m
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 = Signal(reset_less=True)
455
456 def elaborate(self, platform):
457 m = Module()
458 comb = m.d.comb
459
460 comb += self.cr_bitfield.ok.eq(0)
461 comb += self.cr_bitfield_b.ok.eq(0)
462 comb += self.whole_reg.eq(0)
463 with m.Switch(self.sel_in):
464 with m.Case(CRInSel.NONE):
465 pass # No bitfield activated
466 with m.Case(CRInSel.CR0):
467 comb += self.cr_bitfield.data.eq(0)
468 comb += self.cr_bitfield.ok.eq(1)
469 with m.Case(CRInSel.BI):
470 comb += self.cr_bitfield.data.eq(self.dec.BI[2:5])
471 comb += self.cr_bitfield.ok.eq(1)
472 with m.Case(CRInSel.BFA):
473 comb += self.cr_bitfield.data.eq(self.dec.FormX.BFA)
474 comb += self.cr_bitfield.ok.eq(1)
475 with m.Case(CRInSel.BA_BB):
476 comb += self.cr_bitfield.data.eq(self.dec.BA[2:5])
477 comb += self.cr_bitfield.ok.eq(1)
478 comb += self.cr_bitfield_b.data.eq(self.dec.BB[2:5])
479 comb += self.cr_bitfield_b.ok.eq(1)
480 comb += self.cr_bitfield_o.data.eq(self.dec.BT[2:5])
481 comb += self.cr_bitfield_o.ok.eq(1)
482 with m.Case(CRInSel.BC):
483 comb += self.cr_bitfield.data.eq(self.dec.BC[2:5])
484 comb += self.cr_bitfield.ok.eq(1)
485 with m.Case(CRInSel.WHOLE_REG):
486 comb += self.whole_reg.eq(1)
487
488 return m
489
490
491 class DecodeCROut(Elaboratable):
492 """Decodes input CR from instruction
493
494 CR indices - insn fields - (not the data *in* the CR) require only 3
495 bits because they refer to CR0-CR7
496 """
497
498 def __init__(self, dec):
499 self.dec = dec
500 self.rc_in = Signal(reset_less=True)
501 self.sel_in = Signal(CROutSel, reset_less=True)
502 self.insn_in = Signal(32, reset_less=True)
503 self.cr_bitfield = Data(3, "cr_bitfield")
504 self.whole_reg = Signal(reset_less=True)
505
506 def elaborate(self, platform):
507 m = Module()
508 comb = m.d.comb
509
510 comb += self.cr_bitfield.ok.eq(0)
511 comb += self.whole_reg.eq(0)
512 with m.Switch(self.sel_in):
513 with m.Case(CROutSel.NONE):
514 pass # No bitfield activated
515 with m.Case(CROutSel.CR0):
516 comb += self.cr_bitfield.data.eq(0)
517 comb += self.cr_bitfield.ok.eq(self.rc_in) # only when RC=1
518 with m.Case(CROutSel.BF):
519 comb += self.cr_bitfield.data.eq(self.dec.FormX.BF)
520 comb += self.cr_bitfield.ok.eq(1)
521 with m.Case(CROutSel.BT):
522 comb += self.cr_bitfield.data.eq(self.dec.FormXL.BT[2:5])
523 comb += self.cr_bitfield.ok.eq(1)
524 with m.Case(CROutSel.WHOLE_REG):
525 comb += self.whole_reg.eq(1)
526
527 return m
528
529
530 class XerBits:
531 def __init__(self):
532 self.ca = Signal(2, reset_less=True)
533 self.ov = Signal(2, reset_less=True)
534 self.so = Signal(reset_less=True)
535
536 def ports(self):
537 return [self.ca, self.ov, self.so]
538
539
540 class PowerDecode2(Elaboratable):
541
542 def __init__(self, dec):
543
544 self.dec = dec
545 self.e = Decode2ToExecute1Type()
546
547 def ports(self):
548 return self.dec.ports() + self.e.ports()
549
550 def elaborate(self, platform):
551 m = Module()
552 comb = m.d.comb
553 e, op = self.e, self.dec.op
554
555 # set up submodule decoders
556 m.submodules.dec = self.dec
557 m.submodules.dec_a = dec_a = DecodeA(self.dec)
558 m.submodules.dec_b = dec_b = DecodeB(self.dec)
559 m.submodules.dec_c = dec_c = DecodeC(self.dec)
560 m.submodules.dec_o = dec_o = DecodeOut(self.dec)
561 m.submodules.dec_o2 = dec_o2 = DecodeOut2(self.dec)
562 m.submodules.dec_rc = dec_rc = DecodeRC(self.dec)
563 m.submodules.dec_oe = dec_oe = DecodeOE(self.dec)
564 m.submodules.dec_cr_in = dec_cr_in = DecodeCRIn(self.dec)
565 m.submodules.dec_cr_out = dec_cr_out = DecodeCROut(self.dec)
566
567 # copy instruction through...
568 for i in [e.insn, dec_a.insn_in, dec_b.insn_in,
569 dec_c.insn_in, dec_o.insn_in, dec_o2.insn_in, dec_rc.insn_in,
570 dec_oe.insn_in, dec_cr_in.insn_in, dec_cr_out.insn_in]:
571 comb += i.eq(self.dec.opcode_in)
572
573 # ...and subdecoders' input fields
574 comb += dec_a.sel_in.eq(op.in1_sel)
575 comb += dec_b.sel_in.eq(op.in2_sel)
576 comb += dec_c.sel_in.eq(op.in3_sel)
577 comb += dec_o.sel_in.eq(op.out_sel)
578 comb += dec_o2.sel_in.eq(op.out_sel)
579 comb += dec_o2.lk.eq(e.lk)
580 comb += dec_rc.sel_in.eq(op.rc_sel)
581 comb += dec_oe.sel_in.eq(op.rc_sel) # XXX should be OE sel
582 comb += dec_cr_in.sel_in.eq(op.cr_in)
583 comb += dec_cr_out.sel_in.eq(op.cr_out)
584 comb += dec_cr_out.rc_in.eq(dec_rc.rc_out.data)
585
586 # set up instruction, pick fn unit
587 comb += e.nia.eq(0) # XXX TODO (or remove? not sure yet)
588 fu = op.function_unit
589 itype = Mux(fu == Function.NONE, InternalOp.OP_ILLEGAL, op.internal_op)
590 comb += e.insn_type.eq(itype)
591 comb += e.fn_unit.eq(fu)
592
593 # registers a, b, c and out and out2 (LD/ST EA)
594 comb += e.read_reg1.eq(dec_a.reg_out)
595 comb += e.read_reg2.eq(dec_b.reg_out)
596 comb += e.read_reg3.eq(dec_c.reg_out)
597 comb += e.write_reg.eq(dec_o.reg_out)
598 comb += e.write_ea.eq(dec_o2.reg_out)
599 comb += e.imm_data.eq(dec_b.imm_out) # immediate in RB (usually)
600 comb += e.zero_a.eq(dec_a.immz_out) # RA==0 detected
601
602 # rc and oe out
603 comb += e.rc.eq(dec_rc.rc_out)
604 comb += e.oe.eq(dec_oe.oe_out)
605
606 # SPRs out
607 comb += e.read_spr1.eq(dec_a.spr_out)
608 comb += e.write_spr.eq(dec_o.spr_out)
609
610 # Fast regs out
611 comb += e.read_fast1.eq(dec_a.fast_out)
612 comb += e.read_fast2.eq(dec_b.fast_out)
613 comb += e.write_fast1.eq(dec_o.fast_out)
614 comb += e.write_fast2.eq(dec_o2.fast_out)
615
616 # condition registers (CR)
617 comb += e.read_cr1.eq(dec_cr_in.cr_bitfield)
618 comb += e.read_cr2.eq(dec_cr_in.cr_bitfield_b)
619 comb += e.read_cr3.eq(dec_cr_in.cr_bitfield_o)
620 comb += e.read_cr_whole.eq(dec_cr_in.whole_reg)
621
622 comb += e.write_cr.eq(dec_cr_out.cr_bitfield)
623 comb += e.write_cr_whole.eq(dec_cr_out.whole_reg)
624
625 # decoded/selected instruction flags
626 comb += e.data_len.eq(op.ldst_len)
627 comb += e.invert_a.eq(op.inv_a)
628 comb += e.invert_out.eq(op.inv_out)
629 comb += e.input_carry.eq(op.cry_in) # carry comes in
630 comb += e.output_carry.eq(op.cry_out) # carry goes out
631 comb += e.is_32bit.eq(op.is_32b)
632 comb += e.is_signed.eq(op.sgn)
633 with m.If(op.lk):
634 comb += e.lk.eq(self.dec.LK) # XXX TODO: accessor
635
636 comb += e.byte_reverse.eq(op.br)
637 comb += e.sign_extend.eq(op.sgn_ext)
638 comb += e.update.eq(op.upd) # LD/ST "update" mode.
639
640 # These should be removed eventually
641 comb += e.input_cr.eq(op.cr_in) # condition reg comes in
642 comb += e.output_cr.eq(op.cr_out) # condition reg goes in
643
644 # set the trapaddr to 0x700 for a td/tw/tdi/twi operation
645 with m.If(op.internal_op == InternalOp.OP_TRAP):
646 comb += e.trapaddr.eq(0x70) # addr=0x700 (strip first nibble)
647
648 # illegal instruction must redirect to trap. this is done by
649 # *overwriting* the decoded instruction and starting again.
650 # (note: the same goes for interrupts and for privileged operations,
651 # just with different trapaddr and traptype)
652 with m.If(op.internal_op == InternalOp.OP_ILLEGAL):
653 comb += e.eq(0) # reset eeeeeverything
654 # start again
655 comb += e.insn.eq(self.dec.opcode_in)
656 comb += e.insn_type.eq(InternalOp.OP_TRAP)
657 comb += e.fn_unit.eq(Function.TRAP)
658 comb += e.trapaddr.eq(0x70) # addr=0x700 (strip first nibble)
659 comb += e.traptype.eq(TT_ILLEG) # request illegal instruction
660
661 # trap: (note e.insn_type so this includes OP_ILLEGAL) set up fast regs
662 # Note: OP_SC could actually be modified to just be a trap
663 with m.If((e.insn_type == InternalOp.OP_TRAP) |
664 (e.insn_type == InternalOp.OP_SC)):
665 # TRAP write fast1 = SRR0
666 comb += e.write_fast1.data.eq(FastRegs.SRR0) # constant: SRR0
667 comb += e.write_fast1.ok.eq(1)
668 # TRAP write fast2 = SRR1
669 comb += e.write_fast2.data.eq(FastRegs.SRR1) # constant: SRR1
670 comb += e.write_fast2.ok.eq(1)
671
672 # RFID: needs to read SRR0/1
673 with m.If(e.insn_type == InternalOp.OP_RFID):
674 # TRAP read fast1 = SRR0
675 comb += e.read_fast1.data.eq(FastRegs.SRR0) # constant: SRR0
676 comb += e.read_fast1.ok.eq(1)
677 # TRAP read fast2 = SRR1
678 comb += e.read_fast2.data.eq(FastRegs.SRR1) # constant: SRR1
679 comb += e.read_fast2.ok.eq(1)
680
681 return m
682
683 # TODO: get msr, then can do privileged instruction
684 with m.If(instr_is_priv(m, op.internal_op, e.insn) & msr[MSR_PR]):
685 comb += e.eq(0) # reset eeeeeverything
686 # start again
687 comb += e.insn.eq(self.dec.opcode_in)
688 comb += e.insn_type.eq(InternalOp.OP_TRAP)
689 comb += e.fn_unit.eq(Function.TRAP)
690 # privileged instruction trap
691 comb += e.traptype.eq(TT_PRIV) # request privileged instruction
692 comb += e.trapaddr.eq(0x70) # addr=0x700 (strip first nibble)
693 return m
694
695 def regspecmap_read(self, regfile, regname):
696 """regspecmap_read: provides PowerDecode2 with an encoding relationship
697 to Function Unit port regfiles (read-enable, read regnum, write regnum)
698 regfile and regname arguments are fields 1 and 2 from a given regspec.
699 """
700 return regspec_decode_read(self.e, regfile, regname)
701
702 def regspecmap_write(self, regfile, regname):
703 """regspecmap_write: provides PowerDecode2 with an encoding relationship
704 to Function Unit port regfiles (write port, write regnum)
705 regfile and regname arguments are fields 1 and 2 from a given regspec.
706 """
707 return regspec_decode_write(self.e, regfile, regname)
708
709 def rdflags(self, cu):
710 rdl = []
711 for idx in range(cu.n_src):
712 regfile, regname, _ = cu.get_in_spec(idx)
713 rdflag, read = self.regspecmap_read(regfile, regname)
714 rdl.append(rdflag)
715 print ("rdflags", rdl)
716 return Cat(*rdl)
717
718
719 if __name__ == '__main__':
720 pdecode = create_pdecode()
721 dec2 = PowerDecode2(pdecode)
722 vl = rtlil.convert(dec2, ports=dec2.ports() + pdecode.ports())
723 with open("dec2.il", "w") as f:
724 f.write(vl)
725