OpenCores
URL https://opencores.org/ocsvn/raptor64/raptor64/trunk

Subversion Repositories raptor64

[/] [raptor64/] [trunk/] [rtl/] [verilog/] [Raptor64sc.v] - Blame information for rev 19

Go to most recent revision | Details | Compare with Previous | View Log

Line No. Rev Author Line
1 13 robfinch
// ============================================================================
2
// (C) 2012 Robert Finch
3
// All Rights Reserved.
4
// robfinch<remove>@opencores.org
5
//
6
// Raptor64.v
7
//  - 64 bit CPU
8
//
9
// This source file is free software: you can redistribute it and/or modify 
10
// it under the terms of the GNU Lesser General Public License as published 
11
// by the Free Software Foundation, either version 3 of the License, or     
12
// (at your option) any later version.                                      
13
//                                                                          
14
// This source file is distributed in the hope that it will be useful,      
15
// but WITHOUT ANY WARRANTY; without even the implied warranty of           
16
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the            
17
// GNU General Public License for more details.                             
18
//                                                                          
19
// You should have received a copy of the GNU General Public License        
20
// along with this program.  If not, see <http://www.gnu.org/licenses/>.    
21
//                                                                          
22
// ============================================================================
23
//
24 19 robfinch
//`define RAS_PREDICTION                1
25
//`define BTB                                   1
26
//`define TLB           1
27
//`define BRANCH_PREDICTION_SIMPLE      1
28
 
29 13 robfinch
`define RESET_VECTOR    64'hFFFF_FFFF_FFFF_FFF0
30
`define NMI_VECTOR              64'hFFFF_FFFF_FFFF_FFE0
31
`define IRQ_VECTOR              64'hFFFF_FFFF_FFFF_FFD0
32
`define TRAP_VECTOR             64'h0000_0000_0000_0000
33
 
34
`define TLBMissPage             52'hFFFF_FFFF_FFFF_F
35
`define ITLB_MissHandler        64'hFFFF_FFFF_FFFF_FFC0
36
`define DTLB_MissHandler        64'hFFFF_FFFF_FFFF_FFB0
37
 
38
`define GEN_TRAP_OFFSET         13'h0200
39
`define DBZ_TRAP_OFFSET         13'h0050
40
`define OFL_TRAP_OFFSET         13'h0070
41 14 robfinch
`define PRIV_OFFSET                     13'h0080
42 13 robfinch
 
43
`define EX_NON          8'd0
44
`define EX_RST          8'd1
45
`define EX_NMI          8'd2
46
`define EX_IRQ          8'd3
47
`define EX_TRAP         8'd4
48 14 robfinch
`define EX_PRIV         8'd5    // priviledge violation
49 13 robfinch
`define EX_OFL          8'd16   // overflow
50
`define EX_DBZ          8'd17   // divide by zero
51
`define EX_TLBI         8'd19   // TLB exception - ifetch
52
`define EX_TLBD         8'd20   // TLB exception - data
53
 
54
`define EXCEPT_Int              5'd00
55
`define EXCEPT_Mod              5'd01   // TLB modification
56
`define EXCEPT_TLBL             5'd02   // TLB exception - load or ifetch
57
`define EXCEPT_TLBS             5'd03   // TLB exception - store
58
`define EXCEPT_AdEL             5'd04   // Address error - load or ifetch
59
`define EXCEPT_AdES             5'd05   // Address error - store
60
`define EXCEPT_IBE              5'd06   // Bus Error - instruction fetch
61
`define EXCEPT_DBE              5'd07   // Bus Error - load or store
62
`define EXCEPT_Sys              5'd08
63
`define EXCEPT_Bp               5'd09
64
`define EXCEPT_RI               5'd10   // reserved instruction
65
`define EXCEPT_CpU              5'd11   // Coprocessor unusable
66
`define EXCEPT_Ov               5'd12   // Integer Overflow
67
`define EXCEPT_Tr               5'd13   // Trap exception
68
// 14-22 Reserved
69
`define EXCEPT_WATCH    5'd23
70
`define EXCEPT_MCheck   5'd24   // Machine check
71
// 25-31 Reserved
72
 
73
 
74
`define MISC    7'd0
75
`define         BRK             7'd0
76
`define         IRQ             7'd1
77 19 robfinch
`define         ICACHE_ON       7'd10
78
`define         ICACHE_OFF      7'd11
79 13 robfinch
`define     FIP         7'd20
80
`define         IRET    7'd32
81
`define         ERET    7'd33
82
`define         WAIT    7'd40
83 14 robfinch
`define         TLBP    7'd49
84 13 robfinch
`define     TLBR        7'd50
85
`define     TLBWI       7'd51
86
`define     TLBWR       7'd52
87
`define         CLI             7'd64
88
`define         SEI             7'd65
89
`define R               7'd1
90
`define         COM             7'd4
91
`define         NOT             7'd5
92
`define         NEG             7'd6
93
`define         ABS             7'd7
94
`define         SWAP    7'd13
95
`define         CTLZ    7'd16
96
`define         CTLO    7'd17
97
`define         CTPOP   7'd18
98
`define         SEXT8   7'd19
99
`define         SEXT16  7'd20
100
`define         SEXT32  7'd21
101
`define         SQRT    7'd24
102
`define         REDOR   7'd30
103
`define         REDAND  7'd31
104
`define     MFSPR       7'd40
105
`define     MTSPR       7'd41
106
`define         TLBIndex        6'd01
107
`define         TLBRandom               6'd02
108
`define         PageTableAddr   6'd04
109
`define         BadVAddr        6'd08
110 14 robfinch
`define         TLBPhysPage0    6'd10
111
`define         TLBPhysPage1    6'd11
112
`define         TLBVirtPage             6'd12
113
`define                 TLBPageMask             6'd13
114
`define                 TLBASID                 6'd14
115
`define         ASID                    6'd15
116
`define                 Wired                   6'd16
117
`define         EP0             6'd17
118
`define         EP1             6'd18
119
`define         EP2             6'd19
120
`define         EP3             6'd20
121
`define         AXC             6'd21
122
`define                 Tick                    6'd22
123
`define                 EPC                             6'd23
124
`define                 CauseCode               6'd24
125
`define                 TBA                             6'd25
126 19 robfinch
`define                 NON_ICACHE_SEG  6'd26
127 13 robfinch
`define         OMG             7'd50
128
`define         CMG             7'd51
129
`define         OMGI    7'd52
130
`define         CMGI    7'd53
131 19 robfinch
`define         EXEC    7'd58
132 13 robfinch
`define RR      7'd2
133
`define         ADD             7'd2
134
`define         ADDU    7'd3
135
`define         SUB             7'd4
136
`define         SUBU    7'd5
137
`define         CMP             7'd6
138
`define         CMPU    7'd7
139
`define         AND             7'd8
140
`define         OR              7'd9
141
`define         XOR             7'd10
142
`define         ANDC    7'd11
143
`define         NAND    7'd12
144
`define         NOR             7'd13
145
`define         XNOR    7'd14
146
`define         ORC             7'd15
147
`define         MIN             7'd20
148
`define         MAX             7'd21
149
`define         MULU    7'd24
150
`define         MULS    7'd25
151
`define         DIVU    7'd26
152
`define         DIVS    7'd27
153
`define         MOD             7'd28
154
`define         MOVZ    7'd30
155
`define         MOVNZ   7'd31
156
 
157
`define         SHL             7'd40
158
`define         SHRU    7'd41
159
`define         ROL             7'd42
160
`define         ROR             7'd43
161
`define         SHR             7'd44
162
`define         ROLAM   7'd45
163
 
164
`define         NOP             7'd60
165
 
166
`define         SLT             7'd96
167
`define         SLE             7'd97
168
`define         SGT             7'd98
169
`define         SGE             7'd99
170
`define         SLTU    7'd100
171
`define         SLEU    7'd101
172
`define         SGTU    7'd102
173
`define         SGEU    7'd103
174
`define         SEQ             7'd104
175
`define         SNE             7'd105
176
 
177
`define     BCD_ADD     7'd110
178
`define     BCD_SUB 7'd111
179
 
180
`define SHFTI   7'd3
181
`define SHLI            7'd0
182
`define SHRUI           7'd1
183
`define ROLI            7'd2
184
`define SHRI            7'd3
185
`define RORI            7'd4
186
`define ROLAMI          7'd5
187
`define BFINS           7'd8
188
`define BFSET           7'd9
189
`define BFCLR           7'd10
190
`define BFCHG           7'd11
191
 
192
`define ADDI    7'd4
193
`define ADDUI   7'd5
194
`define SUBI    7'd6
195 14 robfinch
`define SUBUI   7'd7
196
`define CMPI    7'd8
197
`define CMPUI   7'd9
198
`define ANDI    7'd10
199
`define ORI             7'd11
200
`define XORI    7'd12
201 13 robfinch
 
202 14 robfinch
`define MULUI   7'd13
203
`define MULSI   7'd14
204
`define DIVUI   7'd15
205
`define DIVSI   7'd16
206 13 robfinch
 
207
`define TRAPcc  7'd17
208
`define         TEQ             7'd0
209
`define         TNE             7'd1
210
`define         TLT             7'd2
211 14 robfinch
`define         TGE             7'd3
212
`define         TLE             7'd4
213
`define         TGT             7'd5
214
`define         TLTU    7'd6
215
`define         TGEU    7'd7
216
`define         TLEU    7'd8
217
`define         TGTU    7'd9
218 13 robfinch
`define         TRAP    7'd10
219
`define         TRN             7'd11
220
`define TRAPcci 7'd18
221
`define         TEQI    5'd0
222
`define         TNEI    5'd1
223
`define         TLTI    5'd2
224 14 robfinch
`define         TGEI    5'd3
225
`define         TLEI    5'd4
226
`define         TGTI    5'd5
227
`define         TLTUI   5'd6
228
`define         TGEUI   5'd7
229
`define         TLEUI   5'd8
230
`define         TGTUI   5'd9
231 13 robfinch
`define         TRAI    5'd10
232
`define         TRNI    5'd11
233 14 robfinch
// SETLO=20 to 23
234
`define SETLO   7'b00101xx
235 13 robfinch
`define CALL    7'd24
236
`define JMP             7'd25
237
`define JAL             7'd26
238
`define RET             7'd27
239 14 robfinch
// SETLO=28 to 31
240
`define SETHI   7'b00111xx
241 13 robfinch
`define LB              7'd32
242
`define LC              7'd33
243
`define LH              7'd34
244
`define LW              7'd35
245
`define LP              7'd36
246
`define LBU             7'd37
247
`define LCU             7'd38
248
`define LHU             7'd39
249
`define LSH             7'd40
250
`define LSW             7'd41
251
`define LF              7'd42
252
`define LFD             7'd43
253
`define LFP             7'd44
254
`define LFDP    7'd45
255
`define LWR             7'd46
256
`define LDONE   7'd47
257
 
258
`define SB              7'd48
259
`define SC              7'd49
260
`define SH              7'd50
261
`define SW              7'd51
262
`define SP              7'd52
263
`define MEMNDX  7'd53
264
`define SSH             7'd56
265
`define SSW             7'd57
266
`define SF              7'd58
267
`define SFD             7'd59
268
`define SFP             7'd60
269
`define SFDP    7'd61
270
`define SWC             7'd62
271
 
272
`define INB             7'd64
273
`define INCH    7'd65
274
`define INH             7'd66
275
`define INW             7'd67
276 14 robfinch
`define INBU    7'd68
277
`define INCU    7'd69
278
`define INHU    7'd70
279 13 robfinch
`define OUTB    7'd72
280
`define OUTC    7'd73
281
`define OUTH    7'd74
282
`define OUTW    7'd75
283
 
284
`define BLTI    7'd80
285
`define BGEI    7'd81
286
`define BLEI    7'd82
287
`define BGTI    7'd83
288
`define BLTUI   7'd84
289
`define BGEUI   7'd85
290
`define BLEUI   7'd86
291
`define BGTUI   7'd87
292
`define BEQI    7'd88
293
`define BNEI    7'd89
294
`define BRAI    7'd90
295
`define BRNI    7'd91
296
 
297
`define BTRI    7'd94
298
`define         BLTRI   5'd0
299
`define         BGERI   5'd1
300
`define         BLERI   5'd2
301
`define         BGTRI   5'd3
302
`define         BLTURI  5'd4
303
`define         BGEURI  5'd5
304
`define         BLEURI  5'd6
305
`define         BGTURI  5'd7
306
`define         BEQRI   5'd8
307
`define         BNERI   5'd9
308
`define         BRARI   5'd10
309
`define         BRNRI   5'd11
310
`define         BANDRI  5'd12
311
`define         BORRI   5'd13
312
`define BTRR    7'd95
313
`define         BLT             5'd0
314
`define         BGE             5'd1
315
`define         BLE             5'd2
316
`define         BGT             5'd3
317
`define         BLTU    5'd4
318
`define         BGEU    5'd5
319
`define         BLEU    5'd6
320
`define         BGTU    5'd7
321
`define         BEQ             5'd8
322
`define         BNE             5'd9
323
`define         BRA             5'd10
324
`define         BRN             5'd11
325
`define         BAND    5'd12
326
`define         BOR             5'd13
327
`define         BNR             5'd14
328
`define         BLTR    5'd16
329
`define         BGER    5'd17
330
`define         BLER    5'd18
331
`define         BGTR    5'd19
332
`define         BLTUR   5'd20
333
`define         BGEUR   5'd21
334
`define         BLEUR   5'd22
335
`define         BGTUR   5'd23
336
`define         BEQR    5'd24
337
`define         BNER    5'd25
338
`define         BRAR    5'd26
339
`define         BRNR    5'd27
340
 
341
 
342
`define SLTI    7'd96
343
`define SLEI    7'd97
344
`define SGTI    7'd98
345
`define SGEI    7'd99
346
`define SLTUI   7'd100
347
`define SLEUI   7'd101
348
`define SGTUI   7'd102
349
`define SGEUI   7'd103
350
`define SEQI    7'd104
351
`define SNEI    7'd105
352
 
353
`define FPLOO   7'd109
354
`define FPZL    7'd110
355
`define NOPI    7'd111
356
 
357
`define IMM             3'd7
358
 
359
`define NOP_INSN        42'b1101111_000_00000000_00000000_00000000_00000000
360
 
361 14 robfinch
module Raptor64sc(rst_i, clk_i, nmi_i, irq_i, bte_o, cti_o, bl_o,
362
        cyc_o, stb_o, ack_i, we_o, sel_o, rsv_o, adr_o, dat_i, dat_o, sys_adv, sys_adr
363 13 robfinch
);
364
parameter IDLE = 5'd1;
365
parameter ICACT = 5'd2;
366
parameter ICACT0 = 5'd3;
367
parameter ICACT1 = 5'd4;
368
parameter ICACT2 = 5'd5;
369
parameter ICACT3 = 5'd6;
370
parameter ICACT4 = 5'd7;
371
parameter ICACT5 = 5'd8;
372
parameter ICACT6 = 5'd9;
373
parameter ICACT7 = 5'd10;
374
parameter ICDLY = 5'd11;
375
parameter DCIDLE = 5'd20;
376
parameter DCACT = 5'd21;
377
parameter DCACT0 = 5'd22;
378
parameter DCACT1 = 5'd23;
379
parameter DCACT2 = 5'd24;
380
parameter DCACT3 = 5'd25;
381
parameter DCACT4 = 5'd26;
382
parameter DCACT5 = 5'd27;
383
parameter DCACT6 = 5'd28;
384
parameter DCACT7 = 5'd29;
385
parameter DCDLY = 5'd30;
386
 
387
input rst_i;
388
input clk_i;
389
input nmi_i;
390
input irq_i;
391
 
392
output [1:0] bte_o;
393
reg [1:0] bte_o;
394
output [2:0] cti_o;
395
reg [2:0] cti_o;
396 14 robfinch
output [4:0] bl_o;
397
reg [4:0] bl_o;
398 13 robfinch
output cyc_o;
399
reg cyc_o;
400
output stb_o;
401
reg stb_o;
402
input ack_i;
403
output we_o;
404
reg we_o;
405 14 robfinch
output [7:0] sel_o;
406
reg [7:0] sel_o;
407 13 robfinch
output rsv_o;
408
reg rsv_o;
409 14 robfinch
output [63:0] adr_o;
410
reg [63:0] adr_o;
411
input [63:0] dat_i;
412
output [63:0] dat_o;
413
reg [63:0] dat_o;
414 13 robfinch
 
415
input sys_adv;
416
input [63:5] sys_adr;
417
 
418
reg resetA;
419 14 robfinch
reg im,bu_im;                   // interrupt mask
420 13 robfinch
reg [1:0] rm;            // fp rounding mode
421
reg [41:0] dIR;
422
reg [41:0] xIR;
423
reg [63:0] pc;
424 14 robfinch
reg [63:0] ErrorEPC,EPC,IPC;
425 19 robfinch
reg [63:0] dpc,m1pc,m2pc,wpc;
426
reg dpcv,xpcv,m1pcv,m2pcv,wpcv; // PC valid indicators
427 13 robfinch
reg [63:0] xpc;
428
reg [63:0] tlbra;                // return address for a TLB exception
429
reg [8:0] dRa,dRb,dRc;
430 19 robfinch
reg [8:0] wRt,mRt,m1Rt,m2Rt,tRt,dRt;
431 13 robfinch
reg [8:0] xRt;
432
reg [63:0] dImm;
433
reg [63:0] ea;
434
reg [63:0] iadr_o;
435
reg [31:0] idat;
436
reg [4:0] cstate;
437
reg dbranch_taken,xbranch_taken;
438
reg [63:0] mutex_gate;
439
reg [63:0] TBA;
440 19 robfinch
reg [1:0] dhwxtype,xhwxtype,m1hwxtype,m2hwxtype,whwxtype;
441 14 robfinch
reg [3:0] AXC,dAXC,xAXC;
442
reg dtinit;
443 19 robfinch
reg [63:32] nonICacheSeg;
444 13 robfinch
 
445
//reg wr_icache;
446
reg dccyc;
447
wire [63:0] cdat;
448
reg [63:0] wr_addr;
449 14 robfinch
reg [41:0] insn;
450 13 robfinch
wire [63:0] rfoa,rfob;
451
reg clk_en;
452
reg cpu_clk_en;
453
reg StatusERL;          // 1= in error processing
454
reg StatusEXL;          // 1= in exception processing
455 14 robfinch
reg StatusHWI;          // 1= in interrupt processing
456
reg StatusUM;           // 1= user mode
457 13 robfinch
reg [7:0] CauseCode;
458
reg [7:0] ASID;          // address space identifier (process ID)
459
integer n;
460
reg [63:13] BadVAddr;
461
reg [63:13] PageTableAddr;
462
 
463
function [63:0] fnIncPC;
464
input [63:0] fpc;
465
begin
466
case(fpc[3:2])
467
2'd0:   fnIncPC = {fpc[63:4],4'b0100};
468
2'd1:   fnIncPC = {fpc[63:4],4'b1000};
469
2'd2:   fnIncPC = {fpc[63:4]+60'd1,4'b0000};
470
2'd3:   fnIncPC = {fpc[63:4]+60'd1,4'b0000};
471
endcase
472
end
473
endfunction
474
 
475 14 robfinch
wire KernelMode = StatusEXL;
476
 
477 13 robfinch
//-----------------------------------------------------------------------------
478 14 robfinch
// TLB
479 19 robfinch
// The TLB contains 64 entries, that are 8 way set associative.
480
// The TLB is dual ported and shared between the instruction and data streams.
481 13 robfinch
//-----------------------------------------------------------------------------
482
 
483 19 robfinch
wire unmappedArea = pc[63:52]==12'hFFD || pc[63:52]==12'hFFE || pc[63:52]==12'hFFF;
484
wire unmappedDataArea = ea[63:52]==12'hFFD || ea[63:52]==12'hFFE || ea[63:52]==12'hFFF;
485
wire [63:0] ppc;
486
wire [63:0] pea;
487
 
488
`ifdef TLB
489 14 robfinch
reg [24:13] TLBPageMask;
490
reg [63:13] TLBVirtPage;
491
reg [63:13] TLBPhysPage0;
492
reg [63:13] TLBPhysPage1;
493
reg [7:0] TLBASID;
494
reg TLBG;
495
reg TLBD;
496
reg TLBValid;
497
reg [63:0] Index;
498 19 robfinch
reg [2:0] Random;
499
reg [2:0] Wired;
500 14 robfinch
reg [15:0] IMatch,DMatch;
501
 
502 19 robfinch
reg [3:0] m;
503
reg [5:0] i;
504
reg [24:13] ITLBPageMask [63:0];
505
reg [63:13] ITLBVirtPage [63:0];
506
reg [63:13] ITLBPhysPage0 [63:0];
507
reg [63:13] ITLBPhysPage1 [63:0];
508
reg [63:0] ITLBG;
509
reg [63:0] ITLBD;
510
reg [7:0] ITLBASID [63:0];
511 13 robfinch
reg [15:0] ITLBValid;
512
initial begin
513 19 robfinch
        for (n = 0; n < 64; n = n + 1)
514 13 robfinch
        begin
515
                ITLBPageMask[n] = 0;
516
                ITLBVirtPage[n] = 0;
517 14 robfinch
                ITLBPhysPage0[n] = 0;
518
                ITLBPhysPage1[n] = 0;
519 13 robfinch
                ITLBG[n] = 0;
520
                ITLBASID[n] = 0;
521
                ITLBValid[n] = 0;
522
        end
523
end
524
always @*
525 19 robfinch
for (n = 0; n < 8; n = n + 1)
526
        IMatch[n] = ((pc[63:13]|ITLBPageMask[{n[2:0],pc[15:13]}])==(ITLBVirtPage[{n[2:0],pc[15:13]}]|ITLBPageMask[{n[2:0],pc[15:13]}])) &&
527
                                ((ITLBASID[{n,pc[15:13]}]==ASID) || ITLBG[{n,pc[15:13]}]) &&
528
                                ITLBValid[{n,pc[15:13]}];
529 13 robfinch
always @(IMatch)
530 19 robfinch
if (IMatch[0]) m <= 4'd0;
531
else if (IMatch[1]) m <= 4'd1;
532
else if (IMatch[2]) m <= 4'd2;
533
else if (IMatch[3]) m <= 4'd3;
534
else if (IMatch[4]) m <= 4'd4;
535
else if (IMatch[5]) m <= 4'd5;
536
else if (IMatch[6]) m <= 4'd6;
537
else if (IMatch[7]) m <= 4'd7;
538
else m <= 4'd15;
539 13 robfinch
 
540 19 robfinch
wire ioddpage = |({ITLBPageMask[{m[2:0],pc[15:13]}]+19'd1,13'd0}&pc);
541
wire [63:13] IPFN = ioddpage ? ITLBPhysPage1[{m[2:0],pc[15:13]}] : ITLBPhysPage0[{m[2:0],pc[15:13]}];
542 14 robfinch
 
543 19 robfinch
wire ITLBMiss = !unmappedArea & m[3];
544 13 robfinch
 
545 19 robfinch
assign ppc[63:13] = unmappedArea ? pc[63:13] : m[3] ? `TLBMissPage: IPFN;
546 13 robfinch
assign ppc[12:0] = pc[12:0];
547
 
548 19 robfinch
reg [3:0] q;
549 13 robfinch
always @(ea)
550 19 robfinch
for (n = 0; n < 7; n = n + 1)
551
        DMatch[n] = ((ea[63:13]|ITLBPageMask[{n,ea[15:13]}])==(ITLBVirtPage[{n,ea[15:13]}]|ITLBPageMask[{n,ea[15:13]}])) &&
552
                                ((ITLBASID[{n,ea[15:13]}]==ASID) || ITLBG[{n,ea[15:13]}]) &&
553
                                ITLBValid[{n,ea[15:13]}];
554 13 robfinch
always @(DMatch)
555 19 robfinch
if (DMatch[0]) q <= 4'd0;
556
else if (DMatch[1]) q <= 4'd1;
557
else if (DMatch[2]) q <= 4'd2;
558
else if (DMatch[3]) q <= 4'd3;
559
else if (DMatch[4]) q <= 4'd4;
560
else if (DMatch[5]) q <= 4'd5;
561
else if (DMatch[6]) q <= 4'd6;
562
else if (DMatch[7]) q <= 4'd7;
563
else q <= 4'd15;
564 13 robfinch
 
565 19 robfinch
wire doddpage = |({ITLBPageMask[{q[2:0],ea[15:13]}]+19'd1,13'd0}&ea);
566
wire [63:13] DPFN = doddpage ? ITLBPhysPage1[{q[2:0],ea[15:13]}] : ITLBPhysPage0[{q[2:0],ea[15:13]}];
567 14 robfinch
 
568 19 robfinch
wire DTLBMiss = !unmappedDataArea & q[3];
569
 
570
assign pea[63:13] = unmappedDataArea ? ea[63:13] : q[3] ? `TLBMissPage: DPFN;
571
assign pea[12:0] = ea[12:0];
572
`else
573
assign ppc = pc;
574
assign pea = ea;
575
`endif
576 14 robfinch
wire m1UnmappedDataArea = pea[63:13]>=12'hFFD;
577 13 robfinch
 
578 14 robfinch
wire dram_bus = !pea[63];
579
wire m2_dram_bus = !m2Addr[63];
580 13 robfinch
 
581
//-----------------------------------------------------------------------------
582
// Clock control
583
// - reset or NMI reenables the clock
584
// - this circuit must be under the clk_i domain
585
//-----------------------------------------------------------------------------
586
//
587
BUFGCE u20 (.CE(cpu_clk_en), .I(clk_i), .O(clk) );
588
 
589
always @(posedge clk_i)
590
if (rst_i) begin
591
        cpu_clk_en <= 1'b1;
592
end
593
else begin
594
        if (nmi_i)
595
                cpu_clk_en <= 1'b1;
596
        else
597
                cpu_clk_en <= clk_en;
598
end
599
 
600
//-----------------------------------------------------------------------------
601
// Instruction Cache
602
// 8kB
603
// 
604
//-----------------------------------------------------------------------------
605 14 robfinch
reg icaccess;
606 19 robfinch
//wire nonICachedArea;
607 13 robfinch
 
608 14 robfinch
//Raptor64_icache_ram_x32 u1
609
//(
610
//      .clk(clk),
611
//      .wr(icaccess & ack_i),
612
//      .adr_i(adr_o[12:0]),
613
//      .dat_i(dat_i),
614
//      .pc(pc),
615
//      .insn(insn)
616
//);
617 19 robfinch
reg ICacheOn;
618
wire ibufrdy;
619
reg [63:0] tmpbuf;
620 14 robfinch
wire [127:0] insnbundle;
621 19 robfinch
reg [127:0] insnbuf;
622
reg [63:4] ibuftag;
623
wire isICached = ppc[63:32]!=nonICacheSeg;
624
wire ICacheAct = ICacheOn & isICached;
625 14 robfinch
 
626
Raptor64_icache_ram u1
627 13 robfinch
(
628 14 robfinch
        .clka(clk), // input clka
629
        .wea(icaccess & ack_i), // input [0 : 0] wea
630
        .addra(adr_o[12:3]), // input [9 : 0] addra
631
        .dina(dat_i), // input [63 : 0] dina
632
        .clkb(~clk), // input clkb
633
        .addrb(pc[12:4]), // input [9 : 0] addrb
634
        .doutb(insnbundle) // output [63 : 0] doutb
635 13 robfinch
);
636
 
637 19 robfinch
always @(pc or insnbundle or ICacheAct or insnbuf)
638 14 robfinch
begin
639 19 robfinch
        case({ICacheAct,pc[3:2]})
640
        3'd0:   insn <= insnbuf[ 41: 0];
641
        3'd1:   insn <= insnbuf[ 83:42];
642
        3'd2:   insn <= insnbuf[125:84];
643
        3'd3:   insn <= 42'h37800000000;
644
        3'd4:   insn <= insnbundle[ 41: 0];
645
        3'd5:   insn <= insnbundle[ 83:42];
646
        3'd6:   insn <= insnbundle[125:84];
647
        3'd7:   insn <= 42'h37800000000;        // NOP instruction
648 14 robfinch
        endcase
649
end
650
 
651
 
652 13 robfinch
reg [63:13] tmem [127:0];
653
reg [127:0] tvalid;
654
 
655
initial begin
656
        for (n=0; n < 128; n = n + 1)
657
                tmem[n] = 0;
658
        for (n=0; n < 128; n = n + 1)
659
                tvalid[n] = 0;
660
end
661
 
662
wire [64:13] tgout;
663
assign tgout = {tvalid[pc[12:6]],tmem[pc[12:6]]};
664
assign ihit = (tgout=={1'b1,ppc[63:13]});
665 19 robfinch
assign ibufrdy = ibuftag==ppc[63:4];
666 13 robfinch
 
667
//-----------------------------------------------------------------------------
668
// Data Cache
669
// No-allocate on write
670
//-----------------------------------------------------------------------------
671
reg dcaccess;
672
wire dhit;
673 14 robfinch
wire [64:15] dtgout;
674 13 robfinch
reg wrhit;
675
reg [7:0] dsel_o;
676
reg [63:0] dadr_o;
677
reg [31:0] ddat;
678
reg wr_dcache;
679
 
680
// cache RAM 16Kb
681 14 robfinch
/*Raptor64_dcache_ram u10
682 13 robfinch
(
683
        .clk(clk),
684 14 robfinch
        .wr(dcaccess ? wr_dcache : wrhit ? (dram_bus ? wr_en: we_o): 1'b0),
685 13 robfinch
        .sel(dcaccess ? 4'b1111 : wrhit ? ~wr_mask : 4'b0000),
686
        .wadr(dcaccess ? dadr_o[13:2] : wr_addr[13:2]),
687
        .i(dcaccess ? ddat : wr_data),
688
        .radr(pea[13:3]),
689
        .o(cdat)
690
);
691 14 robfinch
*/
692
Raptor64_dcache_ram u10
693
(
694
        .clka(clk), // input clka
695
        .ena(1'b1),
696
        .wea(dcaccess ? {8{ack_i}} : wrhit ? sel_o : 8'h00), // input [7 : 0] wea
697
        .addra(adr_o[14:3]), // input [11 : 0] addra
698
        .dina(dcaccess ? dat_i : dat_o), // input [63 : 0] dina
699 13 robfinch
 
700 14 robfinch
        .clkb(~clk), // input clkb
701
        .addrb(adr_o[14:3]), // input [11 : 0] addrb
702
        .doutb(cdat) // output [63 : 0] doutb
703
);
704
 
705
 
706
Raptor64_dcache_tagram u11
707 13 robfinch
(
708 14 robfinch
        .clka(clk), // input clka
709
        .ena(dtinit | (adr_o[5:3]==3'b111)), // input ena
710
        .wea(dtinit | (dcaccess & ack_i)), // input [0 : 0] wea
711
        .addra({1'b0,adr_o[14:6]}), // input [9 : 0] addra
712
        .dina(dtinit ? {1'b0,adr_o[63:15]} : {1'b1,adr_o[63:15]}), // input [48 : 0] dina
713 13 robfinch
 
714 14 robfinch
        .clkb(~clk), // input clkb
715
        .addrb({1'b0,pea[14:6]}), // input [9 : 0] addrb
716
        .doutb(dtgout) // output [48 : 0] doutb
717 13 robfinch
);
718 14 robfinch
// tag ram
719
//syncRam512x64_1rw1r u11
720
//(
721
//      .wrst(1'b0),
722
//      .wclk(clk),
723
//      .wce(adr_o[4:2]==3'b111),
724
//      .we(ack_i),
725
//      .wadr(adr_o[14:5]),
726
//      .i({14'h3FFF,dadr_o[63:14]}),
727
//      .wo(),
728
//
729
//      .rrst(1'b0),
730
//      .rclk(~clk),
731
//      .rce(1'b1),
732
//      .radr(pea[13:5]),
733
//      .ro({dtign,dtgout})
734
//);
735 13 robfinch
 
736 14 robfinch
assign dhit = (dtgout=={1'b1,pea[63:15]});
737 13 robfinch
 
738
//-----------------------------------------------------------------------------
739
//-----------------------------------------------------------------------------
740
 
741
reg [64:0] xData;
742 19 robfinch
wire xisCacheElement = xData[63:52] != 12'hFFD && xData[63:52]!=12'hFFF;
743 13 robfinch
reg m1IsCacheElement;
744
 
745
reg nopI;
746
wire [6:0] iFunc = insn[6:0];
747
wire [6:0] dFunc = dIR[6:0];
748
wire [6:0] xFunc = xIR[6:0];
749
wire [6:0] iOpcode = insn[41:35];
750
wire [6:0] xOpcode = xIR[41:35];
751
wire [6:0] dOpcode = dIR[41:35];
752 19 robfinch
reg [6:0] m1Opcode,m2Opcode;
753
reg [6:0] m1Func,m2Func;
754
reg [63:0] m1Data,m2Data,wData,tData;
755
reg [63:0] m2Addr;
756 13 robfinch
reg [63:0] tick;
757
reg [63:0] tba;
758
reg [63:0] exception_address,ipc;
759
reg [63:0] a,b,c,imm,m1b;
760
reg prev_ihit;
761
reg rsf;
762
reg [63:5] resv_address;
763 19 robfinch
reg dirqf,rirqf,m1irqf,m2irqf,wirqf,tirqf;
764 13 robfinch
reg xirqf;
765 19 robfinch
reg [7:0] dextype,m1extype,m2extype,wextype,textype,exception_type;
766 13 robfinch
reg [7:0] xextype;
767
wire advanceX_edge;
768
reg takb;
769
 
770
wire [127:0] mult_out;
771
wire [63:0] sqrt_out;
772
wire [63:0] div_q;
773
wire [63:0] div_r;
774
wire sqrt_done,mult_done,div_done;
775
wire isSqrt = xOpcode==`R && xFunc==`SQRT;
776
wire [7:0] bcdaddo,bcdsubo;
777
 
778
BCDAdd u40(.ci(1'b0),.a(a[7:0]),.b(b[7:0]),.o(bcdaddo),.c());
779
BCDSub u41(.ci(1'b0),.a(a[7:0]),.b(b[7:0]),.o(bcdsubo),.c());
780
 
781
isqrt #(64) u14
782
(
783
        .rst(rst_i),
784
        .clk(clk),
785
        .ce(1'b1),
786
        .ld(isSqrt),
787
        .a(a),
788
        .o(sqrt_out),
789
        .done(sqrt_done)
790
);
791
 
792
wire isMulu = xOpcode==`RR && xFunc==`MULU;
793
wire isMuls = (xOpcode==`RR && xFunc==`MULS) || xOpcode==`MULSI;
794
wire isMuli = xOpcode==`MULSI || xOpcode==`MULUI;
795
wire isMult = xOpcode==`MULSI || xOpcode==`MULUI || (xOpcode==`RR && (xFunc==`MULS || xFunc==`MULU));
796
wire isDivu = xOpcode==`RR && xFunc==`DIVU;
797
wire isDivs = (xOpcode==`RR && xFunc==`DIVS) || xOpcode==`DIVSI;
798
wire isDivi = xOpcode==`DIVSI || xOpcode==`DIVUI;
799
wire isDiv = xOpcode==`DIVSI || xOpcode==`DIVUI || (xOpcode==`RR && (xFunc==`DIVS || xFunc==`DIVU));
800
 
801
wire disRRShift = dOpcode==`RR && (
802
        dFunc==`SHL || dFunc==`ROL || dFunc==`SHR ||
803
        dFunc==`SHRU || dFunc==`ROR || dFunc==`ROLAM
804
        );
805
wire disRightShift = dOpcode==`RR && (
806
        dFunc==`SHR || dFunc==`SHRU || dFunc==`ROR
807
        );
808
 
809
Raptor64Mult u18
810
(
811
        .rst(rst_i),
812
        .clk(clk),
813
        .ld(isMult),
814
        .sgn(isMuls),
815
        .isMuli(isMuli),
816
        .a(a),
817
        .b(b),
818
        .imm(imm),
819
        .o(mult_out),
820
        .done(mult_done)
821
);
822
 
823
Raptor64Div u19
824
(
825
        .rst(rst_i),
826
        .clk(clk),
827
        .ld(isDiv),
828
        .sgn(isDivs),
829
        .isDivi(isDivi),
830
        .a(a),
831
        .b(b),
832
        .imm(imm),
833
        .qo(div_q),
834
        .ro(div_r),
835
        .dvByZr(),
836
        .done(div_done)
837
);
838
 
839
wire [63:0] fpZLOut;
840
wire [63:0] fpLooOut;
841
wire fpLooDone;
842
 
843
fpZLUnit #(64) u30
844
(
845
        .op(xFunc[5:0]),
846
        .a(a),
847
        .b(b),  // for fcmp
848
        .o(fpZLOut),
849
        .nanx()
850
);
851
 
852
fpLOOUnit #(64) u31
853
(
854
        .clk(clk),
855
        .ce(1'b1),
856
        .rm(rm),
857
        .op(xFunc[5:0]),
858
        .a(a),
859
        .o(fpLooOut),
860
        .done(fpLooDone)
861
);
862
 
863
function [2:0] popcnt6;
864
input [5:0] a;
865
begin
866
case(a)
867
6'b000000:      popcnt6 = 3'd0;
868
6'b000001:      popcnt6 = 3'd1;
869
6'b000010:      popcnt6 = 3'd1;
870
6'b000011:      popcnt6 = 3'd2;
871
6'b000100:      popcnt6 = 3'd1;
872
6'b000101:      popcnt6 = 3'd2;
873
6'b000110:      popcnt6 = 3'd2;
874
6'b000111:      popcnt6 = 3'd3;
875
6'b001000:      popcnt6 = 3'd1;
876
6'b001001:      popcnt6 = 3'd2;
877
6'b001010:      popcnt6 = 3'd2;
878
6'b001011:      popcnt6 = 3'd3;
879
6'b001100:      popcnt6 = 3'd2;
880
6'b001101:      popcnt6 = 3'd3;
881
6'b001110:      popcnt6 = 3'd3;
882
6'b001111:  popcnt6 = 3'd4;
883
6'b010000:      popcnt6 = 3'd1;
884
6'b010001:      popcnt6 = 3'd2;
885
6'b010010:  popcnt6 = 3'd2;
886
6'b010011:      popcnt6 = 3'd3;
887
6'b010100:  popcnt6 = 3'd2;
888
6'b010101:  popcnt6 = 3'd3;
889
6'b010110:  popcnt6 = 3'd3;
890
6'b010111:      popcnt6 = 3'd4;
891
6'b011000:      popcnt6 = 3'd2;
892
6'b011001:      popcnt6 = 3'd3;
893
6'b011010:      popcnt6 = 3'd3;
894
6'b011011:      popcnt6 = 3'd4;
895
6'b011100:      popcnt6 = 3'd3;
896
6'b011101:      popcnt6 = 3'd4;
897
6'b011110:      popcnt6 = 3'd4;
898
6'b011111:      popcnt6 = 3'd5;
899
6'b100000:      popcnt6 = 3'd1;
900
6'b100001:      popcnt6 = 3'd2;
901
6'b100010:      popcnt6 = 3'd2;
902
6'b100011:      popcnt6 = 3'd3;
903
6'b100100:      popcnt6 = 3'd2;
904
6'b100101:      popcnt6 = 3'd3;
905
6'b100110:      popcnt6 = 3'd3;
906
6'b100111:      popcnt6 = 3'd4;
907
6'b101000:      popcnt6 = 3'd2;
908
6'b101001:      popcnt6 = 3'd3;
909
6'b101010:      popcnt6 = 3'd3;
910
6'b101011:      popcnt6 = 3'd4;
911
6'b101100:      popcnt6 = 3'd3;
912
6'b101101:      popcnt6 = 3'd4;
913
6'b101110:      popcnt6 = 3'd4;
914
6'b101111:      popcnt6 = 3'd5;
915
6'b110000:      popcnt6 = 3'd2;
916
6'b110001:      popcnt6 = 3'd3;
917
6'b110010:      popcnt6 = 3'd3;
918
6'b110011:      popcnt6 = 3'd4;
919
6'b110100:      popcnt6 = 3'd3;
920
6'b110101:      popcnt6 = 3'd4;
921
6'b110110:      popcnt6 = 3'd4;
922
6'b110111:      popcnt6 = 3'd5;
923
6'b111000:      popcnt6 = 3'd3;
924
6'b111001:      popcnt6 = 3'd4;
925
6'b111010:      popcnt6 = 3'd4;
926
6'b111011:      popcnt6 = 3'd5;
927
6'b111100:      popcnt6 = 3'd4;
928
6'b111101:      popcnt6 = 3'd5;
929
6'b111110:      popcnt6 = 3'd5;
930
6'b111111:      popcnt6 = 3'd6;
931
endcase
932
end
933
endfunction
934
 
935
wire [63:0] jmp_tgt = dOpcode[6:4]==`IMM ? {dIR[26:0],insn[34:0],2'b00} : {pc[63:37],insn[34:0],2'b00};
936
 
937
//-----------------------------------------------------------------------------
938 19 robfinch
//-----------------------------------------------------------------------------
939
`ifdef RAS_PREDICTION
940
reg [63:0] ras [63:0];    // return address stack, return predictions
941
reg [5:0] ras_sp;
942
`endif
943
`ifdef BTB
944
reg [63:0] btb [63:0];    // branch target buffer
945
`endif
946
 
947
`ifdef BRANCH_PREDICTION_SIMPLE
948
//-----------------------------------------------------------------------------
949
// Simple predictor:
950
// - backwards branches are predicted taken, others predicted not taken.
951
//-----------------------------------------------------------------------------
952
reg predict_taken;
953
 
954
always @(iOpcode or insn)
955
case(iOpcode)
956
`BTRR:
957
        case(insn[4:0])
958
        `BEQ,`BNE,`BLT,`BLE,`BGT,`BGE,`BLTU,`BLEU,`BGTU,`BGEU,`BAND,`BOR,`BNR:
959
                predict_taken = insn[24];
960
        default:        predict_taken = 1'd0;
961
        endcase
962
`BEQI,`BNEI,`BLTI,`BLEI,`BGTI,`BGEI,`BLTUI,`BLEUI,`BGTUI,`BGEUI:
963
        predict_taken = insn[29];
964
default:
965
        predict_taken = 1'd0;
966
endcase
967
`else
968
//-----------------------------------------------------------------------------
969 13 robfinch
// Branch history table.
970
// The history table is updated by the EX stage and read in
971
// both the EX and IF stages.
972
//-----------------------------------------------------------------------------
973
reg [2:0] gbl_branch_hist;
974
reg [1:0] branch_history_table [255:0];
975
wire [7:0] bht_wa = {xpc[5:0],gbl_branch_hist[2:1]};              // write address
976
wire [7:0] bht_ra1 = {xpc[5:0],gbl_branch_hist[2:1]};             // read address (EX stage)
977
wire [7:0] bht_ra2 = {pc[5:0],gbl_branch_hist[2:1]};      // read address (IF stage)
978
wire [1:0] bht_xbits = branch_history_table[bht_ra1];
979
wire [1:0] bht_ibits = branch_history_table[bht_ra2];
980
wire predict_taken = bht_ibits==2'd0 || bht_ibits==2'd1;
981
 
982
wire isxBranchI = (xOpcode==`BRAI || xOpcode==`BRNI || xOpcode==`BEQI || xOpcode==`BNEI ||
983
                                        xOpcode==`BLTI || xOpcode==`BLEI || xOpcode==`BGTI || xOpcode==`BGEI ||
984
                                        xOpcode==`BLTUI || xOpcode==`BLEUI || xOpcode==`BGTUI || xOpcode==`BGEUI)
985
                                ;
986
wire isxBranch = isxBranchI || xOpcode==`TRAPcc || xOpcode==`TRAPcci || xOpcode==`BTRI || xOpcode==`BTRR;
987
 
988
reg [1:0] xbits_new;
989
 
990
always @(takb or bht_xbits)
991
if (takb) begin
992
        if (bht_xbits != 2'd1)
993
                xbits_new <= bht_xbits + 2'd1;
994
        else
995
                xbits_new <= bht_xbits;
996
end
997
else begin
998
        if (bht_xbits != 2'd2)
999
                xbits_new <= bht_xbits - 2'd1;
1000
        else
1001
                xbits_new <= bht_xbits;
1002
end
1003
 
1004
// For simulation only, initialize the history table to zeros.
1005
// In the real world we don't care.
1006
initial begin
1007
        for (n = 0; n < 256; n = n + 1)
1008
                branch_history_table[n] = 0;
1009
end
1010 19 robfinch
`endif
1011 13 robfinch
 
1012
//-----------------------------------------------------------------------------
1013
// Evaluate branch conditions.
1014
//-----------------------------------------------------------------------------
1015
wire signed [63:0] as = a;
1016
wire signed [63:0] bs = b;
1017
wire signed [63:0] imms = imm;
1018
wire aeqz = a==64'd0;
1019
wire beqz = b==64'd0;
1020
wire immeqz = imm==64'd0;
1021
wire eq = a==b;
1022
wire eqi = a==imm;
1023 19 robfinch
wire lt = $signed(a) < $signed(b);
1024 13 robfinch
wire lti = as < imms;
1025
wire ltu = a < b;
1026
wire ltui = a < imm;
1027
 
1028
always @(xOpcode or xFunc or a or eq or eqi or lt or lti or ltu or ltui or aeqz or beqz or rsf or xIR)
1029
case (xOpcode)
1030
`BTRR:
1031 14 robfinch
        case(xIR[4:0])
1032 13 robfinch
        `BRA:   takb = 1'b1;
1033
        `BRN:   takb = 1'b0;
1034
        `BEQ:   takb = eq;
1035
        `BNE:   takb = !eq;
1036
        `BLT:   takb = lt;
1037
        `BLE:   takb = lt|eq;
1038
        `BGT:   takb = !(lt|eq);
1039
        `BGE:   takb = !lt;
1040
        `BLTU:  takb = ltu;
1041
        `BLEU:  takb = ltu|eq;
1042
        `BGTU:  takb = !(ltu|eq);
1043
        `BGEU:  takb = !ltu;
1044
        `BOR:   takb = !aeqz || !beqz;
1045
        `BAND:  takb = !aeqz && !beqz;
1046
        `BNR:   takb = !rsf;
1047
        `BEQR:  takb = eq;
1048
        `BNER:  takb = !eq;
1049
        `BLTR:  takb = lt;
1050
        `BLER:  takb = lt|eq;
1051
        `BGTR:  takb = !(lt|eq);
1052
        `BGER:  takb = !lt;
1053
        `BLTUR: takb = ltu;
1054
        `BLEUR: takb = ltu|eq;
1055
        `BGTUR: takb = !(ltu|eq);
1056
        `BGEUR: takb = !ltu;
1057
        default:        takb = 1'b0;
1058
        endcase
1059
`BRAI:  takb = 1'b1;
1060
`BRNI:  takb = 1'b0;
1061
`BEQI:  takb = eqi;
1062
`BNEI:  takb = !eqi;
1063
`BLTI:  takb = lti;
1064
`BLEI:  takb = lti|eqi;
1065
`BGTI:  takb = !(lti|eqi);
1066
`BGEI:  takb = !lti;
1067
`BLTUI: takb = ltui;
1068
`BLEUI: takb = ltui|eqi;
1069
`BGTUI: takb = !(ltui|eqi);
1070
`BGEUI: takb = !ltui;
1071
`BTRI:
1072
        case(xIR[24:18])
1073
        `BRA:   takb = 1'b1;
1074
        `BRN:   takb = 1'b0;
1075
        `BEQ:   takb = eqi;
1076
        `BNE:   takb = !eqi;
1077
        `BLT:   takb = lti;
1078
        `BLE:   takb = lti|eqi;
1079
        `BGT:   takb = !(lti|eqi);
1080
        `BGE:   takb = !lti;
1081
        `BLTU:  takb = ltui;
1082
        `BLEU:  takb = ltui|eqi;
1083
        `BGTU:  takb = !(ltui|eqi);
1084
        `BGEU:  takb = !ltui;
1085
        default:        takb = 1'b0;
1086
        endcase
1087
`TRAPcc:
1088
        case(xFunc)
1089
        `TEQ:   takb = eq;
1090
        `TNE:   takb = !eq;
1091
        `TLT:   takb = lt;
1092
        `TLE:   takb = lt|eq;
1093
        `TGT:   takb = !(lt|eq);
1094
        `TGE:   takb = !lt;
1095 14 robfinch
        `TLTU:  takb = ltu;
1096
        `TLEU:  takb = ltu|eq;
1097
        `TGTU:  takb = !(ltu|eq);
1098
        `TGEU:  takb = !ltu;
1099 13 robfinch
        default:        takb = 1'b0;
1100
        endcase
1101
`TRAPcci:
1102
        case(xIR[29:25])
1103
        `TEQI:  takb = eqi;
1104
        `TNEI:  takb = !eqi;
1105
        `TLTI:  takb = lti;
1106
        `TLEI:  takb = lti|eqi;
1107
        `TGTI:  takb = !(lti|eqi);
1108
        `TGEI:  takb = !lti;
1109 14 robfinch
        `TLTUI: takb = ltui;
1110
        `TLEUI: takb = ltui|eqi;
1111
        `TGTUI: takb = !(ltui|eqi);
1112
        `TGEUI: takb = !ltui;
1113 13 robfinch
        default:        takb = 1'b0;
1114
        endcase
1115
default:
1116
        takb = 1'b0;
1117
endcase
1118
 
1119
 
1120
//-----------------------------------------------------------------------------
1121
// Datapath (ALU) operations.
1122
//-----------------------------------------------------------------------------
1123
wire [6:0] cntlzo,cntloo;
1124
cntlz64 u12 ( .i(a),  .o(cntlzo) );
1125
cntlo64 u13 ( .i(a),  .o(cntloo) );
1126
 
1127
reg [1:0] shftop;
1128
wire [63:0] shfto;
1129
always @(xFunc)
1130
        if (xFunc==`SHL)
1131
                shftop = 2'b00;
1132
        else if (xFunc==`ROL || xFunc==`ROR)
1133
                shftop = 2'b01;
1134
        else if (xFunc==`SHRU)
1135
                shftop = 2'b10;
1136
        else if (xFunc==`SHR)
1137
                shftop = 2'b11;
1138
        else
1139
                shftop = 2'b01;
1140
 
1141
wire [63:0] masko;
1142
shiftAndMask u15
1143
(
1144
        .op(shftop),
1145
        .oz(1'b0),              // zero the output
1146
        .a(a),
1147
        .b(b[5:0]),
1148
        .mb(xIR[12:7]),
1149
        .me(xIR[18:13]),
1150
        .o(shfto),
1151
        .mo(masko)
1152
);
1153
 
1154
always @(xOpcode or xFunc or a or b or imm or as or bs or imms or xpc or
1155 14 robfinch
        sqrt_out or cntlzo or cntloo or tick or ipc or tba or AXC or
1156 13 robfinch
        lt or eq or ltu or mult_out or lti or eqi or ltui or xIR or div_q or div_r or
1157 19 robfinch
        shfto or masko or bcdaddo or bcdsubo or fpLooOut or fpZLOut
1158
`ifdef TLB
1159
        or Wired or Index or Random or TLBPhysPage0 or TLBPhysPage1 or TLBVirtPage or TLBASID or
1160 13 robfinch
        PageTableAddr or BadVAddr or ASID or TLBPageMask
1161 19 robfinch
`endif
1162 13 robfinch
)
1163 16 robfinch
casex(xOpcode)
1164 13 robfinch
`R:
1165
        casex(xFunc)
1166
        `COM:   xData = ~a;
1167
        `NOT:   xData = ~|a;
1168
        `NEG:   xData = -a;
1169
        `ABS:   xData = a[63] ? -a : a;
1170
        `SQRT:  xData = sqrt_out;
1171
        `SWAP:  xData = {a[31:0],a[63:32]};
1172
 
1173
        `REDOR:         xData = |a;
1174
        `REDAND:        xData = &a;
1175
 
1176
        `CTLZ:  xData = cntlzo;
1177
        `CTLO:  xData = cntloo;
1178
        `CTPOP: xData = {4'd0,popcnt6(a[5:0])} +
1179
                                        {4'd0,popcnt6(a[11:6])} +
1180
                                        {4'd0,popcnt6(a[17:12])} +
1181
                                        {4'd0,popcnt6(a[23:18])} +
1182
                                        {4'd0,popcnt6(a[29:24])} +
1183
                                        {4'd0,popcnt6(a[35:30])} +
1184
                                        {4'd0,popcnt6(a[41:36])} +
1185
                                        {4'd0,popcnt6(a[47:42])} +
1186
                                        {4'd0,popcnt6(a[53:48])} +
1187
                                        {4'd0,popcnt6(a[59:54])} +
1188
                                        {4'd0,popcnt6(a[63:60])}
1189
                                        ;
1190
        `SEXT8:         xData = {{56{a[7]}},a[7:0]};
1191
        `SEXT16:        xData = {{48{a[15]}},a[15:0]};
1192
        `SEXT32:        xData = {{32{a[31]}},a[31:0]};
1193
 
1194
        `MFSPR:
1195
                case(xIR[12:7])
1196 19 robfinch
`ifdef TLB
1197 13 robfinch
                `Wired:                 xData = Wired;
1198
                `TLBIndex:              xData = Index;
1199
                `TLBRandom:             xData = Random;
1200 14 robfinch
                `TLBPhysPage0:  xData = {TLBPhysPage0,13'd0};
1201
                `TLBPhysPage1:  xData = {TLBPhysPage1,13'd0};
1202 13 robfinch
                `TLBVirtPage:   xData = {TLBVirtPage,13'd0};
1203
                `TLBPageMask:   xData = {TLBPageMask,13'd0};
1204 14 robfinch
                `TLBASID:       begin
1205
                                        xData = 65'd0;
1206
                                        xData[0] = TLBValid;
1207
                                        xData[1] = TLBD;
1208
                                        xData[2] = TLBG;
1209
                                        xData[15:8] = TLBASID;
1210
                                        end
1211 13 robfinch
                `PageTableAddr: xData = {PageTableAddr,13'd0};
1212
                `BadVAddr:              xData = {BadVAddr,13'd0};
1213 19 robfinch
`endif
1214 13 robfinch
                `ASID:                  xData = ASID;
1215
                `Tick:                  xData = tick;
1216
                `EPC:                   xData = EPC;
1217
                `CauseCode:             xData = CauseCode;
1218
                `TBA:                   xData = TBA;
1219 14 robfinch
                `AXC:                   xData = xAXC;
1220 19 robfinch
                `NON_ICACHE_SEG:        xData = nonICacheSeg;
1221 13 robfinch
                default:        xData = 65'd0;
1222
                endcase
1223
        `OMG:           xData = mutex_gate[a[5:0]];
1224
        `CMG:           xData = mutex_gate[a[5:0]];
1225 14 robfinch
        `OMGI:          begin
1226
                                xData = mutex_gate[xIR[12:7]];
1227
                                $display("mutex_gate[%d]=%d",xIR[12:7],mutex_gate[xIR[12:7]]);
1228
                                end
1229 13 robfinch
        `CMGI:          xData = mutex_gate[xIR[12:7]];
1230
        default:        xData = 65'd0;
1231
        endcase
1232
`RR:
1233
        case(xFunc)
1234
        `ADD:   xData = a + b;
1235
        `ADDU:  xData = a + b;
1236
        `SUB:   xData = a - b;
1237
        `SUBU:  xData = a - b;
1238
        `CMP:   xData = lt ? 64'hFFFFFFFFFFFFF : eq ? 64'd0 : 64'd1;
1239
        `CMPU:  xData = ltu ? 64'hFFFFFFFFFFFFF : eq ? 64'd0 : 64'd1;
1240
        `SEQ:   xData = eq;
1241
        `SNE:   xData = !eq;
1242
        `SLT:   xData = lt;
1243
        `SLE:   xData = lt|eq;
1244
        `SGT:   xData = !(lt|eq);
1245
        `SGE:   xData = !lt;
1246
        `SLTU:  xData = ltu;
1247
        `SLEU:  xData = ltu|eq;
1248
        `SGTU:  xData = !(ltu|eq);
1249
        `SGEU:  xData = !ltu;
1250
        `AND:   xData = a & b;
1251
        `OR:    xData = a | b;
1252
        `XOR:   xData = a ^ b;
1253
        `ANDC:  xData = a & ~b;
1254
        `NAND:  xData = ~(a & b);
1255
        `NOR:   xData = ~(a | b);
1256
        `XNOR:  xData = ~(a ^ b);
1257
        `ORC:   xData = a | ~b;
1258
        `MIN:   xData = lt ? a : b;
1259
        `MAX:   xData = lt ? b : a;
1260
        `MOVZ:  xData = b;
1261
        `MOVNZ: xData = b;
1262
        `MULS:  xData = mult_out[63:0];
1263
        `MULU:  xData = mult_out[63:0];
1264
        `DIVS:  xData = div_q;
1265
        `DIVU:  xData = div_q;
1266
        `MOD:   xData = div_r;
1267
 
1268
        `SHL:   xData = shfto;
1269
        `SHRU:  xData = shfto;
1270
        `ROL:   xData = shfto;
1271
        `ROR:   xData = {a[0],a[63:1]};
1272
        `SHR:   xData = shfto;
1273
        `ROLAM: xData = shfto & masko;
1274
 
1275
        `BCD_ADD:       xData = bcdaddo;
1276
        `BCD_SUB:       xData = bcdsubo;
1277
 
1278
        default:        xData = 65'd0;
1279
        endcase
1280
`SHFTI:
1281
        case(xFunc)
1282
        `SHLI:  xData = shfto;
1283
        `SHRUI: xData = shfto;
1284
        `ROLI:  xData = shfto;
1285
        `RORI:  xData = {a[0],a[63:1]};
1286
        `SHRI:  xData = shfto;
1287
        `ROLAMI:        xData = shfto & masko;
1288
        `BFINS:         begin for (n = 0; n < 64; n = n + 1) xData[n] = masko[n] ? shfto[n] : b[n]; xData[64] = 1'b0; end
1289
        `BFSET:         begin for (n = 0; n < 64; n = n + 1) xData[n] = masko[n] ? 1'b1 : b[n]; xData[64] = 1'b0; end
1290
        `BFCLR:         begin for (n = 0; n < 64; n = n + 1) xData[n] = masko[n] ? 1'b0 : b[n]; xData[64] = 1'b0; end
1291
        `BFCHG:         begin for (n = 0; n < 64; n = n + 1) xData[n] = masko[n] ? ~b[n] : b[n]; xData[64] = 1'b0; end
1292
        default:        xData = 65'd0;
1293
        endcase
1294 14 robfinch
`SETLO: xData = {{32{xIR[31]}},xIR[31:0]};
1295
`SETHI: xData = {xIR[31:0],a[31:0]};
1296 13 robfinch
`ADDI:  xData = a + imm;
1297
`ADDUI: xData = a + imm;
1298
`SUBI:  xData = a - imm;
1299 14 robfinch
`SUBUI: xData = a - imm;
1300 13 robfinch
`CMPI:  xData = lti ? 64'hFFFFFFFFFFFFF : eqi ? 64'd0 : 64'd1;
1301
`CMPUI: xData = ltui ? 64'hFFFFFFFFFFFFF : eqi ? 64'd0 : 64'd1;
1302
`MULSI: xData = mult_out[63:0];
1303
`MULUI: xData = mult_out[63:0];
1304
`DIVSI: xData = div_q;
1305
`DIVUI: xData = div_q;
1306
`ANDI:  xData = a & imm;
1307
`ORI:   xData = a | imm;
1308
`XORI:  xData = a ^ imm;
1309
`SEQI:  xData = eqi;
1310
`SNEI:  xData = !eqi;
1311
`SLTI:  xData = lti;
1312
`SLEI:  xData = lti|eqi;
1313
`SGTI:  xData = !(lti|eqi);
1314
`SGEI:  xData = !lti;
1315
`SLTUI: xData = ltui;
1316
`SLEUI: xData = ltui|eqi;
1317
`SGTUI: xData = !(ltui|eqi);
1318
`SGEUI: xData = !ltui;
1319
`INB,`INCH,`INH,`INW:
1320
                xData = a + imm;
1321
`OUTB,`OUTC,`OUTH,`OUTW:
1322
                xData = a + imm;
1323
`LW,`LH,`LC,`LB,`LHU,`LCU,`LBU,`LWR:
1324
                xData = a + imm;
1325
`SW,`SH,`SC,`SB,`SWC:
1326
                xData = a + imm;
1327
`MEMNDX:
1328
                xData = a + b + imm;
1329
`BEQ,`BNE,`BLT,`BLE,`BGT,`BGE,`BLTU,`BLEU,`BGTU,`BGEU,`BOR,`BAND:
1330
                xData = 64'd0;
1331
`TRAPcc:        xData = fnIncPC(xpc);
1332
`TRAPcci:       xData = fnIncPC(xpc);
1333
`CALL:          xData = fnIncPC(xpc);
1334
`JAL:           xData = xpc + {xIR[29:25],2'b00};
1335
`RET:   xData = a + {imm,2'b00};
1336
`FPLOO: xData = fpLooOut;
1337
`FPZL:  xData = fpZLOut;
1338
default:        xData = 65'd0;
1339
endcase
1340
 
1341 14 robfinch
wire v_ri,v_rr;
1342
overflow u2 (.op(xOpcode==`SUBI), .a(a[63]), .b(imm[63]), .s(xData[63]), .v(v_ri));
1343
overflow u3 (.op(xOpcode==`RR && xFunc==`SUB), .a(a[63]), .b(b[63]), .s(xData[63]), .v(v_rr));
1344
 
1345 13 robfinch
wire dbz_error = (xOpcode==`DIVSI||xOpcode==`DIVUI) && b==64'd0;
1346 19 robfinch
wire ovr_error = ((xOpcode==`ADDI || xOpcode==`SUBI) && v_ri) || ((xOpcode==`RR && (xFunc==`SUB || xFunc==`ADD)) && v_rr);
1347 14 robfinch
wire priv_violation = !KernelMode && (xOpcode==`MISC &&
1348
        (xFunc==`IRET || xFunc==`ERET || xFunc==`CLI || xFunc==`SEI ||
1349
         xFunc==`TLBP || xFunc==`TLBR || xFunc==`TLBWR || xFunc==`TLBWI
1350
        ));
1351 13 robfinch
wire xIsSqrt = xOpcode==`R && xFunc==`SQRT;
1352
wire xIsMult = (xOpcode==`RR && (xFunc==`MULU || xFunc==`MULS)) ||
1353
        xOpcode==`MULSI || xOpcode==`MULUI;
1354
wire xIsDiv = (xOpcode==`RR && (xFunc==`DIVU || xFunc==`DIVS)) ||
1355
        xOpcode==`DIVSI || xOpcode==`DIVUI;
1356
 
1357
wire xIsLoad =
1358
        xOpcode==`LW || xOpcode==`LH || xOpcode==`LB || xOpcode==`LWR ||
1359
        xOpcode==`LHU || xOpcode==`LBU ||
1360
        xOpcode==`LC || xOpcode==`LCU ||
1361
        xOpcode==`INW || xOpcode==`INB || xOpcode==`INH || xOpcode==`INCH
1362
        ;
1363
wire xIsStore =
1364
        xOpcode==`SW || xOpcode==`SH || xOpcode==`SB || xOpcode==`SC || xOpcode==`SWC ||
1365
        xOpcode==`OUTW || xOpcode==`OUTH || xOpcode==`OUTB || xOpcode==`OUTC
1366
        ;
1367
wire xIsSWC = xOpcode==`SWC;
1368
wire xIsIn =
1369
        xOpcode==`INW || xOpcode==`INH || xOpcode==`INCH || xOpcode==`INB
1370
        ;
1371
//wire mIsSWC = mOpcode==`SWC;
1372
 
1373
//wire mIsLoad =
1374
//      mOpcode==`LW || mOpcode==`LH || mOpcode==`LB || mOpcode==`LC || mOpcode==`LWR ||
1375
//      mOpcode==`LHU || mOpcode==`LBU || mOpcode==`LCU ||
1376
//      mOpcode==`INW || mOpcode==`INB || mOpcode==`INH
1377
//      ;
1378
wire m1IsLoad =
1379
        m1Opcode==`LW || m1Opcode==`LH || m1Opcode==`LB || m1Opcode==`LC || m1Opcode==`LWR ||
1380
        m1Opcode==`LHU || m1Opcode==`LBU || m1Opcode==`LCU
1381
        ;
1382
wire m1IsIn =
1383
        m1Opcode==`INW || m1Opcode==`INH || m1Opcode==`INCH || m1Opcode==`INB
1384
        ;
1385 14 robfinch
wire m2IsInW = m2Opcode==`INW;
1386 13 robfinch
wire m1IsStore =
1387
        m1Opcode==`SW || m1Opcode==`SH || m1Opcode==`SB || m1Opcode==`SC || m1Opcode==`SWC
1388
        ;
1389 14 robfinch
wire xIsIO =
1390
        xIsIn ||
1391
        xOpcode==`OUTW || xOpcode==`OUTH || xOpcode==`OUTC || xOpcode==`OUTB
1392
        ;
1393 13 robfinch
wire m1IsIO =
1394
        m1IsIn ||
1395
        m1Opcode==`OUTW || m1Opcode==`OUTH || m1Opcode==`OUTC || m1Opcode==`OUTB
1396
        ;
1397
wire m2IsLoad =
1398
        m2Opcode==`LW || m2Opcode==`LH || m2Opcode==`LB || m2Opcode==`LC || m2Opcode==`LWR ||
1399
        m2Opcode==`LHU || m2Opcode==`LBU || m2Opcode==`LCU
1400
        ;
1401 14 robfinch
wire m2IsStore =
1402
        m2Opcode==`SW || m2Opcode==`SWC || m2Opcode==`SH || m2Opcode==`SC || m2Opcode==`SB;
1403 13 robfinch
 
1404
wire xIsFPLoo = xOpcode==`FPLOO;
1405
 
1406 14 robfinch
wire xneedBus = xIsIO;
1407 19 robfinch
wire m1needBus = (m1IsLoad & !m1IsCacheElement) || m1IsStore || m1IsIO;
1408 14 robfinch
wire m2needBus = (m2IsLoad | m2IsStore);
1409
 
1410 13 robfinch
// Stall on SWC allows rsf flag to be loaded for the next instruction
1411
// Currently stalls on load of R0, but doesn't need to.
1412 14 robfinch
wire StallR =   (((xIsLoad||xIsIn) && ((xRt==dRa)||(xRt==dRb)||(xRt==dRt))) || xIsSWC) ||
1413
                                (((m1IsLoad||m1IsIn) && ((m1Rt==dRa)||(m1Rt==dRb)||(m1Rt==dRt)))) ||
1414 19 robfinch
                                (((m2IsLoad) && ((m2Rt==dRa)||(m2Rt==dRb)||(m2Rt==dRt))))
1415 14 robfinch
                                ;
1416
wire StallX = xneedBus & (m1needBus|m2needBus|icaccess|dcaccess);
1417
wire StallM1 = m1needBus & (m2needBus|icaccess|dcaccess);
1418
wire StallM2 =  icaccess|dcaccess;
1419 13 robfinch
 
1420
wire advanceT = !resetA;
1421
wire advanceW = advanceT;
1422 14 robfinch
wire advanceM2 = advanceW &&
1423
                                        ((m2IsLoad || m2IsStore) ? ack_i : 1'b1) &&
1424
                                        !StallM2
1425 13 robfinch
                                        ;
1426 14 robfinch
wire advanceM1 = advanceM2 &
1427 13 robfinch
                                        (m1IsIO ? ack_i : 1'b1) &
1428
                                        ((m1IsLoad & m1IsCacheElement) ? dhit : 1'b1) &
1429
                                        !StallM1
1430
                                        ;
1431 14 robfinch
wire advanceX = advanceM1 & (
1432 13 robfinch
                                        xIsSqrt ? sqrt_done :
1433
                                        xIsMult ? mult_done :
1434
                                        xIsDiv ? div_done :
1435
                                        xIsFPLoo ? fpLooDone :
1436 14 robfinch
                                        1'b1) &
1437
                                        !StallX;
1438
wire advanceR = advanceX & !StallR;
1439 19 robfinch
wire advanceI = advanceR & (ICacheOn ? ihit : ibufrdy);
1440 13 robfinch
 
1441
wire triggerDCacheLoad = (m1IsLoad & m1IsCacheElement & !dhit) &&       // there is a miss
1442 14 robfinch
                                                !(icaccess | dcaccess) &&       // caches are not active
1443
                                                m2Opcode==`NOPI                         // and the pipeline is free of memory-ops
1444 13 robfinch
                                                ;
1445
// Since IMM is "sticky" we have to check for it.
1446 19 robfinch
wire triggerICacheLoad = (ICacheAct ? !ihit : !ibufrdy) && !triggerDCacheLoad &&        // There is a miss
1447
                                                !(icaccess | dcaccess) &&       // caches are not active
1448 13 robfinch
                                                (dOpcode==`NOPI || dOpcode[6:4]==`IMM) &&                       // and the pipeline is flushed
1449
                                                (xOpcode==`NOPI || xOpcode[6:4]==`IMM) &&
1450
                                                m1Opcode==`NOPI &&
1451 14 robfinch
                                                m2Opcode==`NOPI
1452 13 robfinch
                                                ;
1453 14 robfinch
wire EXexception_pending = ovr_error || dbz_error || priv_violation || xOpcode==`TRAPcci || xOpcode==`TRAPcc;
1454 19 robfinch
`ifdef TLB
1455 14 robfinch
wire M1exception_pending = advanceM1 & (m1IsLoad|m1IsStore) & DTLBMiss;
1456 19 robfinch
`else
1457
wire M1exception_pending = 1'b0;
1458
`endif
1459 14 robfinch
wire exception_pending = EXexception_pending | M1exception_pending;
1460 13 robfinch
 
1461
wire xWillLoadStore = (xIsLoad||xIsStore) & advanceX;
1462
wire stallCacheLoad = xWillLoadStore;
1463
 
1464
reg prev_nmi,nmi_edge;
1465
 
1466
 
1467
//---------------------------------------------------------
1468
// Register file.
1469
//---------------------------------------------------------
1470
 
1471
syncRam512x64_1rw3r u5
1472
(
1473
        .wrst(1'b0),
1474
        .wclk(clk),
1475
        .wce(advanceW),
1476
        .we(1'b1),
1477
        .wadr(wRt),
1478
        .i(wData),
1479
        .wo(),
1480
 
1481
        .rrsta(1'b0),
1482
        .rclka(~clk),
1483
        .rcea(advanceR),
1484
        .radra(dRa),
1485
        .roa(rfoa),
1486
 
1487
        .rrstb(1'b0),
1488
        .rclkb(~clk),
1489
        .rceb(advanceR),
1490
        .radrb(dRb),
1491
        .rob(rfob),
1492
 
1493
        .rrstc(1'b0),
1494
        .rclkc(~clk),
1495
        .rcec(advanceR),
1496
        .radrc(dRc),
1497
        .roc(rfoc)
1498
);
1499
 
1500
 
1501
reg m1clkoff,m2clkoff,m3clkoff,m4clkoff,wclkoff;
1502
reg dFip,xFip,m1Fip,m2Fip,m3Fip,m4Fip,wFip;
1503
 
1504
always @(posedge clk)
1505
if (rst_i) begin
1506
        bte_o <= 2'b00;
1507
        cti_o <= 3'b000;
1508
        cyc_o <= 1'b0;
1509
        stb_o <= 1'b0;
1510
        we_o <= 1'b0;
1511
        sel_o <= 8'h00;
1512
        adr_o <= 64'd0;
1513
        dat_o <= 64'd0;
1514
        dccyc <= 1'b0;
1515
 
1516 19 robfinch
        nonICacheSeg <= 32'hFFFF_FFFD;
1517 14 robfinch
        TBA <= 64'd0;
1518
        pc <= `RESET_VECTOR;
1519 13 robfinch
        m1Opcode <= `NOPI;
1520
        m2Opcode <= `NOPI;
1521
        dIR <= `NOP_INSN;
1522
        dRt <= 9'd0;
1523
        tRt <= 9'd0;
1524
        wRt <= 9'd0;
1525
        m1Rt <= 9'd0;
1526
        m2Rt <= 9'd0;
1527
        tData <= 64'd0;
1528
        wData <= 64'd0;
1529
        m1Data <= 64'd0;
1530
        m2Data <= 64'd0;
1531
        icaccess <= 1'b0;
1532
        dcaccess <= 1'b0;
1533
        nopI <= 1'b0;
1534
        prev_ihit <= 1'b0;
1535 14 robfinch
        dhwxtype <= 2'b00;
1536
        xhwxtype <= 2'b00;
1537
        m1hwxtype <= 2'b00;
1538
        m2hwxtype <= 2'b00;
1539
        whwxtype <= 2'b00;
1540 13 robfinch
        wFip <= 1'b0;
1541
        m2Fip <= 1'b0;
1542
        m1Fip <= 1'b0;
1543
        xFip <= 1'b0;
1544
        dFip <= 1'b0;
1545
        dirqf <= 1'b0;
1546 16 robfinch
        dpcv <= 1'b0;
1547
        xpcv <= 1'b0;
1548
        m1pcv <= 1'b0;
1549
        m2pcv <= 1'b0;
1550
        wpcv <= 1'b0;
1551 13 robfinch
        tick <= 32'd0;
1552
        cstate <= IDLE;
1553
        dImm <= 64'd0;
1554 14 robfinch
        AXC <= 4'd0;
1555
        dAXC <= 4'd0;
1556 13 robfinch
        xirqf <= 1'b0;
1557
        xextype <= 8'h00;
1558
        xIR <= `NOP_INSN;
1559
        xpc <= 64'd0;
1560
        a <= 64'd0;
1561
        b <= 64'd0;
1562
        imm <= 64'd0;
1563
        xRt <= 9'd0;
1564
        clk_en <= 1'b1;
1565 19 robfinch
`ifdef TLB
1566 13 robfinch
        Random <= 4'hF;
1567
        Wired <= 4'd0;
1568 19 robfinch
`endif
1569 14 robfinch
        StatusEXL <= 1'b1;
1570
        StatusHWI <= 1'b0;
1571 13 robfinch
        resetA <= 1'b1;
1572 14 robfinch
        mutex_gate <= 64'h0;
1573 19 robfinch
`ifndef BRANCH_PREDICTION_SIMPLE
1574 13 robfinch
        gbl_branch_hist <= 3'b000;
1575 19 robfinch
`endif
1576
        ICacheOn <= 1'b0;
1577
        ibuftag <= 64'h0;
1578 14 robfinch
        m1IsCacheElement <= 1'b0;
1579
        dtinit <= 1'b1;
1580 19 robfinch
`ifdef RAS_PREDICTION
1581
        ras_sp <= 6'd63;
1582
`endif
1583 13 robfinch
end
1584
else begin
1585
 
1586
//---------------------------------------------------------
1587
// Initialize program counters
1588 14 robfinch
// Initialize data tags to zero.
1589 13 robfinch
//---------------------------------------------------------
1590
if (resetA) begin
1591
        pc <= `RESET_VECTOR;
1592 14 robfinch
        adr_o[14:6] <= adr_o[14:6]+9'd1;
1593
        if (adr_o[14:6]==9'h1FF) begin
1594
                dtinit <= 1'b0;
1595
                resetA <= 1'b0;
1596
        end
1597 13 robfinch
end
1598
 
1599 19 robfinch
`ifdef TLB
1600 13 robfinch
if (Random==Wired)
1601 19 robfinch
        Random <= 3'd7;
1602 13 robfinch
else
1603 19 robfinch
        Random <= Random - 3'd1;
1604
`endif
1605 13 robfinch
 
1606
tick <= tick + 64'd1;
1607
 
1608
prev_nmi <= nmi_i;
1609
if (!prev_nmi & nmi_i)
1610
        nmi_edge <= 1'b1;
1611
 
1612
 
1613
// A store by any device in the system to a reserved address blcok
1614
// clears the reservation.
1615
 
1616
if (sys_adv && sys_adr[63:5]==resv_address)
1617
        resv_address <= 59'd0;
1618
 
1619
//---------------------------------------------------------
1620
// TRAILER:
1621
// - placeholder to allow the use of synchronous register
1622
//   memory
1623
//---------------------------------------------------------
1624
if (advanceT) begin
1625
        tRt <= 9'd0;
1626
        tData <= 64'd0;
1627
end
1628
 
1629
//---------------------------------------------------------
1630
// WRITEBACK:
1631
// - update the register file with results
1632
// - record exception address and type
1633
// - jump to exception handler routine (below)
1634
//---------------------------------------------------------
1635
if (advanceW) begin
1636
        textype <= wextype;
1637
        wextype <= `EX_NON;
1638
        tRt <= wRt;
1639
        tData <= wData;
1640 16 robfinch
        if (wRt!=5'd0)
1641
                $display("Writing regfile[%d:%d] with %h", wRt[8:5],wRt[4:0], wData);
1642 13 robfinch
        wRt <= 9'd0;
1643
        wData <= 64'd0;
1644 14 robfinch
        if (|whwxtype) begin
1645
                dhwxtype <= 2'b00;
1646
                xhwxtype <= 2'b00;
1647
                m1hwxtype <= 2'b00;
1648
                m2hwxtype <= 2'b00;
1649
                whwxtype <= 2'b00;
1650 13 robfinch
        end
1651
        clk_en <= 1'b1;
1652
        if (wclkoff)
1653
                clk_en <= 1'b0;
1654
        wclkoff <= 1'b0;
1655
        m1clkoff <= 1'b0;
1656
        m2clkoff <= 1'b0;
1657
        if (wFip) begin
1658
                wFip <= 1'b0;
1659
                m2Fip <= 1'b0;
1660
                m1Fip <= 1'b0;
1661
                xFip <= 1'b0;
1662
                dFip <= 1'b0;
1663
        end
1664
end
1665
 
1666
//---------------------------------------------------------
1667
// MEMORY:
1668
//---------------------------------------------------------
1669 14 robfinch
if (advanceM2) begin
1670
        wData <= m2Data;
1671
        whwxtype <= m2hwxtype;
1672
        wextype <= m2extype;
1673
        wRt <= m2Rt;
1674
        wpc <= m2pc;
1675 16 robfinch
        wpcv <= m2pcv;
1676 14 robfinch
        wclkoff <= m2clkoff;
1677
        wFip <= m2Fip;
1678 13 robfinch
 
1679 14 robfinch
        m2Rt <= 9'd0;
1680
        m2Opcode <= `NOPI;
1681
        m2Func <= 7'd0;
1682
        m2Addr <= 64'd0;
1683
        m2Data <= 64'd0;
1684
        m2clkoff <= 1'b0;
1685
        m2pc <= 64'd0;
1686
        m2extype <= `EX_NON;
1687
        if (m2extype==`EX_NON) begin
1688
                case(m2Opcode)
1689
                `SH,`SC,`SB,`SW,`SWC:
1690 13 robfinch
                        begin
1691
                                cyc_o <= 1'b0;
1692
                                stb_o <= 1'b0;
1693 14 robfinch
                                we_o <= 1'b0;
1694 13 robfinch
                                sel_o <= 4'h0;
1695
                        end
1696 14 robfinch
                `LH:
1697 13 robfinch
                        begin
1698
                                cyc_o <= 1'b0;
1699
                                stb_o <= 1'b0;
1700 14 robfinch
                                sel_o <= 8'h00;
1701 19 robfinch
                                wData <= sel_o[7] ? {{32{dat_i[63]}},dat_i[63:32]}:{{32{dat_i[31]}},dat_i[31: 0]};
1702 13 robfinch
                        end
1703
                `LW,`LWR:
1704
                        begin
1705 14 robfinch
                                cyc_o <= 1'b0;
1706
                                stb_o <= 1'b0;
1707
                                sel_o <= 8'h00;
1708 19 robfinch
                                wData <= dat_i;
1709 13 robfinch
                        end
1710
                `LHU:
1711
                        begin
1712 14 robfinch
                                cyc_o <= 1'b0;
1713
                                stb_o <= 1'b0;
1714
                                sel_o <= 8'h00;
1715 19 robfinch
                                wData <= sel_o[7] ? dat_i[63:32] : dat_i[31: 0];
1716 13 robfinch
                        end
1717
                `LC:
1718
                        begin
1719 14 robfinch
                                cyc_o <= 1'b0;
1720
                                stb_o <= 1'b0;
1721
                                sel_o <= 8'h00;
1722
                                case(sel_o)
1723 19 robfinch
                                8'b00000011:    wData <= {{48{dat_i[15]}},dat_i[15: 0]};
1724
                                8'b00001100:    wData <= {{48{dat_i[31]}},dat_i[31:16]};
1725
                                8'b00110000:    wData <= {{48{dat_i[47]}},dat_i[47:32]};
1726
                                8'b11000000:    wData <= {{48{dat_i[63]}},dat_i[63:48]};
1727
                                default:        wData <= 64'hDEADDEADDEADDEAD;
1728 14 robfinch
                                endcase
1729 13 robfinch
                        end
1730
                `LCU:
1731
                        begin
1732 14 robfinch
                                cyc_o <= 1'b0;
1733
                                stb_o <= 1'b0;
1734
                                sel_o <= 8'h00;
1735
                                case(sel_o)
1736 19 robfinch
                                8'b00000011:    wData <= dat_i[15: 0];
1737
                                8'b00001100:    wData <= dat_i[31:16];
1738
                                8'b00110000:    wData <= dat_i[47:32];
1739
                                8'b11000000:    wData <= dat_i[63:48];
1740
                                default:        wData <= 64'hDEADDEADDEADDEAD;
1741 14 robfinch
                                endcase
1742 13 robfinch
                        end
1743
                `LB:
1744
                        begin
1745 14 robfinch
                                cyc_o <= 1'b0;
1746
                                stb_o <= 1'b0;
1747
                                sel_o <= 8'h00;
1748
                                case(sel_o)
1749 19 robfinch
                                8'b00000001:    wData <= {{56{dat_i[ 7]}},dat_i[ 7: 0]};
1750
                                8'b00000010:    wData <= {{56{dat_i[15]}},dat_i[15: 8]};
1751
                                8'b00000100:    wData <= {{56{dat_i[23]}},dat_i[23:16]};
1752
                                8'b00001000:    wData <= {{56{dat_i[31]}},dat_i[31:24]};
1753
                                8'b00010000:    wData <= {{56{dat_i[39]}},dat_i[39:32]};
1754
                                8'b00100000:    wData <= {{56{dat_i[47]}},dat_i[47:40]};
1755
                                8'b01000000:    wData <= {{56{dat_i[55]}},dat_i[55:48]};
1756
                                8'b10000000:    wData <= {{56{dat_i[63]}},dat_i[63:56]};
1757
                                default:        wData <= 64'hDEADDEADDEADDEAD;
1758 14 robfinch
                                endcase
1759 13 robfinch
                        end
1760
                `LBU:
1761
                        begin
1762 14 robfinch
                                cyc_o <= 1'b0;
1763
                                stb_o <= 1'b0;
1764
                                sel_o <= 8'h00;
1765
                                case(sel_o)
1766 19 robfinch
                                8'b00000001:    wData <= dat_i[ 7: 0];
1767
                                8'b00000010:    wData <= dat_i[15: 8];
1768
                                8'b00000100:    wData <= dat_i[23:16];
1769
                                8'b00001000:    wData <= dat_i[31:24];
1770
                                8'b00010000:    wData <= dat_i[39:32];
1771
                                8'b00100000:    wData <= dat_i[47:40];
1772
                                8'b01000000:    wData <= dat_i[55:48];
1773
                                8'b10000000:    wData <= dat_i[63:56];
1774
                                default:        wData <= 64'hDEADDEADDEADDEAD;
1775 14 robfinch
                                endcase
1776 13 robfinch
                        end
1777
                default:        ;
1778
                endcase
1779
        end
1780
end
1781
 
1782
wrhit <= 1'b0;
1783
//---------------------------------------------------------
1784
// MEMORY:
1785 14 robfinch
// - I/O instructions are finished
1786
// - store instructions are started
1787
// - missed loads are started
1788 13 robfinch
// On a data cache hit for a load, the load is essentially
1789 14 robfinch
// finished in this stage. We switch the opcode to 'NOPI'
1790 13 robfinch
// to cause the pipeline to advance as if a NOPs were
1791
// present.
1792
//---------------------------------------------------------
1793
if (advanceM1) begin
1794
        m2Opcode <= m1Opcode;
1795
        m2Func <= m1Func;
1796
        m2Addr <= pea;
1797
        m2Data <= m1Data;
1798 14 robfinch
        m2hwxtype <= m1hwxtype;
1799 13 robfinch
        m2extype <= m1extype;
1800
        m2Rt <= m1Rt;
1801
        m2pc <= m1pc;
1802 16 robfinch
        m2pcv <= m1pcv;
1803 13 robfinch
        m2clkoff <= m1clkoff;
1804
        m2Fip <= m1Fip;
1805
 
1806
        m1Rt <= 9'd0;
1807
        m1Opcode <= `NOPI;
1808
        m1Func <= 7'd0;
1809
        m1Data <= 64'd0;
1810
        m1clkoff <= 1'b0;
1811
        m1pc <= 64'd0;
1812
        m1IsCacheElement <= 1'b0;
1813
        m1extype <= `EX_NON;
1814
 
1815
        if (m1extype == `EX_NON) begin
1816
                case(m1Opcode)
1817
                `MISC:
1818
                        case(m1Func)
1819 19 robfinch
`ifdef TLB
1820 14 robfinch
                        `TLBP:
1821
                                begin
1822
                                        Index[63] <= ~|DMatch;
1823
                                end
1824 13 robfinch
                        `TLBR:
1825
                                begin
1826
                                        TLBPageMask <= ITLBPageMask[i];
1827
                                        TLBVirtPage <= ITLBVirtPage[i];
1828 14 robfinch
                                        TLBPhysPage0 <= ITLBPhysPage0[i];
1829
                                        TLBPhysPage1 <= ITLBPhysPage1[i];
1830 13 robfinch
                                        TLBASID <= ITLBASID[i];
1831
                                        TLBG <= ITLBG[i];
1832 14 robfinch
                                        TLBD <= ITLBD[i];
1833
                                        TLBValid <= ITLBValid[i];
1834 13 robfinch
                                end
1835
                        `TLBWI,`TLBWR:
1836
                                begin
1837 14 robfinch
                                        ITLBValid[i] <= TLBValid;
1838 13 robfinch
                                        ITLBVirtPage[i] <= TLBVirtPage;
1839 14 robfinch
                                        ITLBPhysPage0[i] <= TLBPhysPage0;
1840
                                        ITLBPhysPage1[i] <= TLBPhysPage1;
1841 13 robfinch
                                        ITLBPageMask[i] <= TLBPageMask;
1842
                                        ITLBASID[i] <= TLBASID;
1843 14 robfinch
                                        ITLBD[i] <= TLBD;
1844
                                        ITLBG[i] <= TLBG;
1845 13 robfinch
                                end
1846 19 robfinch
`endif
1847 13 robfinch
                        endcase
1848
                `INW:
1849
                        begin
1850 14 robfinch
                                cyc_o <= 1'b0;
1851 13 robfinch
                                stb_o <= 1'b0;
1852 14 robfinch
                                sel_o <= 8'h00;
1853
                                m2Data <= dat_i;
1854
                                m2Opcode <= `NOPI;
1855 13 robfinch
                        end
1856
                `INH:
1857
                        begin
1858
                                cyc_o <= 1'b0;
1859
                                stb_o <= 1'b0;
1860 14 robfinch
                                sel_o <= 8'h00;
1861
                                m2Data <= sel_o[7] ? {{32{dat_i[63]}},dat_i[63:32]}:{{32{dat_i[31]}},dat_i[31: 0]};
1862
                                m2Opcode <= `NOPI;
1863 13 robfinch
                        end
1864 14 robfinch
                `INHU:
1865
                        begin
1866
                                cyc_o <= 1'b0;
1867
                                stb_o <= 1'b0;
1868
                                sel_o <= 8'h00;
1869
                                m2Data <= sel_o[7] ? dat_i[63:32] : dat_i[31: 0];
1870
                                m2Opcode <= `NOPI;
1871
                        end
1872 13 robfinch
                `INCH:
1873
                        begin
1874
                                cyc_o <= 1'b0;
1875
                                stb_o <= 1'b0;
1876 14 robfinch
                                sel_o <= 8'h00;
1877 13 robfinch
                                case(sel_o)
1878 14 robfinch
                                8'b00000011:    m2Data <= {{48{dat_i[15]}},dat_i[15: 0]};
1879
                                8'b00001100:    m2Data <= {{48{dat_i[31]}},dat_i[31:16]};
1880
                                8'b00110000:    m2Data <= {{48{dat_i[47]}},dat_i[47:32]};
1881
                                8'b11000000:    m2Data <= {{48{dat_i[63]}},dat_i[63:48]};
1882 13 robfinch
                                default:        m2Data <= 64'hDEADDEADDEADDEAD;
1883
                                endcase
1884 14 robfinch
                                m2Opcode <= `NOPI;
1885 13 robfinch
                        end
1886 14 robfinch
                `INCU:
1887
                        begin
1888
                                cyc_o <= 1'b0;
1889
                                stb_o <= 1'b0;
1890
                                sel_o <= 8'h00;
1891
                                case(sel_o)
1892
                                8'b00000011:    m2Data <= dat_i[15: 0];
1893
                                8'b00001100:    m2Data <= dat_i[31:16];
1894
                                8'b00110000:    m2Data <= dat_i[47:32];
1895
                                8'b11000000:    m2Data <= dat_i[63:48];
1896
                                default:        m2Data <= 64'hDEADDEADDEADDEAD;
1897
                                endcase
1898
                                m2Opcode <= `NOPI;
1899
                        end
1900 13 robfinch
                `INB:
1901
                        begin
1902
                                cyc_o <= 1'b0;
1903
                                stb_o <= 1'b0;
1904 14 robfinch
                                sel_o <= 8'h00;
1905 13 robfinch
                                case(sel_o)
1906 14 robfinch
                                8'b00000001:    m2Data <= {{56{dat_i[ 7]}},dat_i[ 7: 0]};
1907
                                8'b00000010:    m2Data <= {{56{dat_i[15]}},dat_i[15: 8]};
1908
                                8'b00000100:    m2Data <= {{56{dat_i[23]}},dat_i[23:16]};
1909
                                8'b00001000:    m2Data <= {{56{dat_i[31]}},dat_i[31:24]};
1910
                                8'b00010000:    m2Data <= {{56{dat_i[39]}},dat_i[39:32]};
1911
                                8'b00100000:    m2Data <= {{56{dat_i[47]}},dat_i[47:40]};
1912
                                8'b01000000:    m2Data <= {{56{dat_i[55]}},dat_i[55:48]};
1913
                                8'b10000000:    m2Data <= {{56{dat_i[63]}},dat_i[63:56]};
1914 13 robfinch
                                default:        m2Data <= 64'hDEADDEADDEADDEAD;
1915
                                endcase
1916 14 robfinch
                                m2Opcode <= `NOPI;
1917 13 robfinch
                        end
1918 14 robfinch
                `INBU:
1919 13 robfinch
                        begin
1920 14 robfinch
                                cyc_o <= 1'b0;
1921 13 robfinch
                                stb_o <= 1'b0;
1922 14 robfinch
                                sel_o <= 8'h00;
1923
                                case(sel_o)
1924
                                8'b00000001:    m2Data <= dat_i[ 7: 0];
1925
                                8'b00000010:    m2Data <= dat_i[15: 8];
1926
                                8'b00000100:    m2Data <= dat_i[23:16];
1927
                                8'b00001000:    m2Data <= dat_i[31:24];
1928
                                8'b00010000:    m2Data <= dat_i[39:32];
1929
                                8'b00100000:    m2Data <= dat_i[47:40];
1930
                                8'b01000000:    m2Data <= dat_i[55:48];
1931
                                8'b10000000:    m2Data <= dat_i[63:56];
1932
                                default:        m2Data <= 64'hDEADDEADDEADDEAD;
1933
                                endcase
1934
                                m2Opcode <= `NOPI;
1935 13 robfinch
                        end
1936 14 robfinch
                `OUTW,`OUTH,`OUTC,`OUTB:
1937 13 robfinch
                        begin
1938
                                cyc_o <= 1'b0;
1939
                                stb_o <= 1'b0;
1940
                                we_o <= 1'b0;
1941 14 robfinch
                                sel_o <= 8'h00;
1942
                                m2Opcode <= `NOPI;
1943 13 robfinch
                        end
1944 14 robfinch
 
1945 13 robfinch
                `LW:
1946
                        if (!m1IsCacheElement) begin
1947 14 robfinch
                                cyc_o <= 1'b1;
1948
                                stb_o <= 1'b1;
1949
                                sel_o <= 8'hFF;
1950
                                adr_o <= {pea[63:3],3'b000};
1951
                                m2Addr <= {pea[63:3],3'b000};
1952 13 robfinch
                        end
1953
                        else if (dhit) begin
1954 14 robfinch
                                m2Opcode <= `NOPI;
1955 13 robfinch
                                m2Data <= cdat;
1956
                        end
1957 14 robfinch
 
1958 13 robfinch
                `LWR:
1959
                        if (!m1IsCacheElement) begin
1960
                                rsv_o <= 1'b1;
1961
                                resv_address <= pea[63:5];
1962 14 robfinch
                                cyc_o <= 1'b1;
1963
                                stb_o <= 1'b1;
1964
                                sel_o <= 8'hFF;
1965
                                adr_o <= {pea[63:3],3'b000};
1966
                                m2Addr <= {pea[63:3],3'b000};
1967 13 robfinch
                        end
1968
                        else if (dhit) begin
1969 14 robfinch
                                m2Opcode <= `NOPI;
1970 13 robfinch
                                m2Data <= cdat;
1971
                                rsv_o <= 1'b1;
1972
                                resv_address <= pea[63:5];
1973
                        end
1974 14 robfinch
 
1975 13 robfinch
                `LH:
1976
                        if (!m1IsCacheElement) begin
1977 14 robfinch
                                cyc_o <= 1'b1;
1978
                                stb_o <= 1'b1;
1979
                                sel_o <= pea[2] ? 8'b11110000 : 8'b00001111;
1980
                                adr_o <= {pea[63:2],2'b00};
1981
                                m2Addr <= {pea[63:2],2'b00};
1982 13 robfinch
                        end
1983
                        else if (dhit) begin
1984 14 robfinch
                                m2Opcode <= `NOPI;
1985 13 robfinch
                                if (pea[1])
1986
                                        m2Data <= {{32{cdat[31]}},cdat[31:0]};
1987
                                else
1988
                                        m2Data <= {{32{cdat[63]}},cdat[63:32]};
1989
                        end
1990 14 robfinch
 
1991 13 robfinch
                `LHU:
1992
                        if (!m1IsCacheElement) begin
1993 14 robfinch
                                cyc_o <= 1'b1;
1994
                                stb_o <= 1'b1;
1995
                                sel_o <= pea[2] ? 8'b11110000 : 8'b00001111;
1996
                                adr_o <= {pea[63:2],2'b00};
1997
                                m2Addr <= {pea[63:2],2'b00};
1998 13 robfinch
                        end
1999
                        else if (dhit) begin
2000 14 robfinch
                                m2Opcode <= `NOPI;
2001 13 robfinch
                                if (pea[1])
2002
                                        m2Data <= {32'd0,cdat};
2003
                                else
2004
                                        m2Data <= {32'd0,cdat[63:32]};
2005
                        end
2006 14 robfinch
 
2007 13 robfinch
                `LC:
2008
                        if (!m1IsCacheElement) begin
2009 14 robfinch
                                cyc_o <= 1'b1;
2010
                                stb_o <= 1'b1;
2011
                                case(pea[2:1])
2012
                                2'b00:  sel_o <= 8'b00000011;
2013
                                2'b01:  sel_o <= 8'b00001100;
2014
                                2'b10:  sel_o <= 8'b00110000;
2015
                                2'b11:  sel_o <= 8'b11000000;
2016
                                endcase
2017
                                adr_o <= {pea[63:1],1'b0};
2018
                                m2Addr <= {pea[63:1],1'b0};
2019 13 robfinch
                        end
2020
                        else if (dhit) begin
2021 14 robfinch
                                m2Opcode <= `NOPI;
2022 13 robfinch
                                case(pea[2:1])
2023
                                2'd0:   m2Data <= {{48{cdat[15]}},cdat[15:0]};
2024
                                2'd1:   m2Data <= {{48{cdat[31]}},cdat[31:16]};
2025
                                2'd2:   m2Data <= {{48{cdat[47]}},cdat[47:32]};
2026
                                2'd3:   m2Data <= {{48{cdat[63]}},cdat[63:48]};
2027
                                endcase
2028
                        end
2029 14 robfinch
 
2030 13 robfinch
                `LCU:
2031
                        if (!m1IsCacheElement) begin
2032 14 robfinch
                                cyc_o <= 1'b1;
2033
                                stb_o <= 1'b1;
2034
                                case(pea[2:1])
2035
                                2'b00:  sel_o <= 8'b00000011;
2036
                                2'b01:  sel_o <= 8'b00001100;
2037
                                2'b10:  sel_o <= 8'b00110000;
2038
                                2'b11:  sel_o <= 8'b11000000;
2039
                                endcase
2040
                                adr_o <= {pea[63:1],1'b0};
2041
                                m2Addr <= {pea[63:1],1'b0};
2042 13 robfinch
                        end
2043
                        else if (dhit) begin
2044 14 robfinch
                                m2Opcode <= `NOPI;
2045 13 robfinch
                                case(pea[2:1])
2046
                                2'd0:   m2Data <= {48'd0,cdat[15: 0]};
2047
                                2'd1:   m2Data <= {48'd0,cdat[31:16]};
2048
                                2'd2:   m2Data <= {48'd0,cdat[47:32]};
2049
                                2'd3:   m2Data <= {48'd0,cdat[63:48]};
2050
                                endcase
2051
                        end
2052 14 robfinch
 
2053 13 robfinch
                `LB:
2054
                        if (!m1IsCacheElement) begin
2055 14 robfinch
                                $display("Load byte:");
2056
                                cyc_o <= 1'b1;
2057
                                stb_o <= 1'b1;
2058
                                case(pea[2:0])
2059
                                3'b000: sel_o <= 8'b00000001;
2060
                                3'b001: sel_o <= 8'b00000010;
2061
                                3'b010: sel_o <= 8'b00000100;
2062
                                3'b011: sel_o <= 8'b00001000;
2063
                                3'b100: sel_o <= 8'b00010000;
2064
                                3'b101: sel_o <= 8'b00100000;
2065
                                3'b110: sel_o <= 8'b01000000;
2066
                                3'b111: sel_o <= 8'b10000000;
2067
                                endcase
2068
                                adr_o <= pea;
2069
                                m2Addr <= pea;
2070 13 robfinch
                        end
2071
                        else if (dhit) begin
2072 14 robfinch
                                m2Opcode <= `NOPI;
2073 13 robfinch
                                case(pea[2:0])
2074
                                3'b000: m2Data <= {{56{cdat[ 7]}},cdat[ 7: 0]};
2075
                                3'b001: m2Data <= {{56{cdat[15]}},cdat[15: 8]};
2076
                                3'b010: m2Data <= {{56{cdat[23]}},cdat[23:16]};
2077
                                3'b011: m2Data <= {{56{cdat[31]}},cdat[31:24]};
2078
                                3'b100: m2Data <= {{56{cdat[39]}},cdat[39:32]};
2079
                                3'b101: m2Data <= {{56{cdat[47]}},cdat[47:40]};
2080
                                3'b110: m2Data <= {{56{cdat[55]}},cdat[55:48]};
2081
                                3'b111: m2Data <= {{56{cdat[63]}},cdat[63:56]};
2082
                                endcase
2083
                        end
2084 14 robfinch
 
2085 13 robfinch
                `LBU:
2086
                        if (!m1IsCacheElement) begin
2087 14 robfinch
                                cyc_o <= 1'b1;
2088
                                stb_o <= 1'b1;
2089
                                case(pea[2:0])
2090
                                3'b000: sel_o <= 8'b00000001;
2091
                                3'b001: sel_o <= 8'b00000010;
2092
                                3'b010: sel_o <= 8'b00000100;
2093
                                3'b011: sel_o <= 8'b00001000;
2094
                                3'b100: sel_o <= 8'b00010000;
2095
                                3'b101: sel_o <= 8'b00100000;
2096
                                3'b110: sel_o <= 8'b01000000;
2097
                                3'b111: sel_o <= 8'b10000000;
2098
                                endcase
2099
                                adr_o <= pea;
2100
                                m2Addr <= pea;
2101 13 robfinch
                        end
2102
                        else if (dhit) begin
2103 14 robfinch
                                m2Opcode <= `NOPI;
2104 13 robfinch
                                case(pea[2:0])
2105
                                3'b000: m2Data <= {56'd0,cdat[ 7: 0]};
2106
                                3'b001: m2Data <= {56'd0,cdat[15: 8]};
2107
                                3'b010: m2Data <= {56'd0,cdat[23:16]};
2108
                                3'b011: m2Data <= {56'd0,cdat[31:23]};
2109
                                3'b100: m2Data <= {56'd0,cdat[39:32]};
2110
                                3'b101: m2Data <= {56'd0,cdat[47:40]};
2111
                                3'b110: m2Data <= {56'd0,cdat[55:48]};
2112
                                3'b111: m2Data <= {56'd0,cdat[63:56]};
2113
                                endcase
2114
                        end
2115 14 robfinch
 
2116
                `SW:
2117 13 robfinch
                        begin
2118 14 robfinch
                                m2Addr <= {pea[63:3],3'b000};
2119 13 robfinch
                                wrhit <= dhit;
2120 19 robfinch
`ifdef TLB
2121
                                if (!m1UnmappedDataArea & !q[3])
2122
                                        ITLBD[{q[2:0],pea[15:13]}] <= 1'b1;
2123
`endif
2124 13 robfinch
                                if (resv_address==pea[63:5])
2125
                                        resv_address <= 59'd0;
2126 14 robfinch
                                cyc_o <= 1'b1;
2127
                                stb_o <= 1'b1;
2128
                                we_o <= 1'b1;
2129
                                sel_o <= 8'hFF;
2130
                                adr_o <= {pea[63:3],3'b000};
2131 19 robfinch
                                dat_o <= m1Data;
2132 13 robfinch
                        end
2133 14 robfinch
 
2134
                `SH:
2135
                        begin
2136
                                wrhit <= dhit;
2137
                                m2Addr <= {pea[63:2],2'b00};
2138 19 robfinch
`ifdef TLB
2139
                                if (!m1UnmappedDataArea & !q[3])
2140
                                        ITLBD[{q[2:0],pea[15:13]}] <= 1'b1;
2141
`endif
2142 14 robfinch
                                if (resv_address==pea[63:5])
2143
                                        resv_address <= 59'd0;
2144
                                cyc_o <= 1'b1;
2145
                                stb_o <= 1'b1;
2146
                                we_o <= 1'b1;
2147
                                sel_o <= pea[2] ? 8'b11110000 : 8'b00001111;
2148
                                adr_o <= {pea[63:2],2'b00};
2149 19 robfinch
                                dat_o <= {2{m1Data[31:0]}};
2150 14 robfinch
                        end
2151
 
2152 13 robfinch
                `SC:
2153
                        begin
2154
                                $display("Storing char to %h, ea=%h",pea,ea);
2155
                                wrhit <= dhit;
2156
                                m2Addr <= {pea[63:2],2'b00};
2157 19 robfinch
`ifdef TLB
2158
                                if (!m1UnmappedDataArea & !q[3])
2159
                                        ITLBD[{q[2:0],pea[15:13]}] <= 1'b1;
2160
`endif
2161 13 robfinch
                                if (resv_address==pea[63:5])
2162
                                        resv_address <= 59'd0;
2163 14 robfinch
                                cyc_o <= 1'b1;
2164
                                stb_o <= 1'b1;
2165
                                we_o <= 1'b1;
2166
                                case(pea[2:1])
2167
                                2'b00:  sel_o <= 8'b00000011;
2168
                                2'b01:  sel_o <= 8'b00001100;
2169
                                2'b10:  sel_o <= 8'b00110000;
2170
                                2'b11:  sel_o <= 8'b11000000;
2171
                                endcase
2172
                                adr_o <= {pea[63:1],1'b0};
2173 19 robfinch
                                dat_o <= {4{m1Data[15:0]}};
2174 13 robfinch
                        end
2175 14 robfinch
 
2176 13 robfinch
                `SB:
2177
                        begin
2178
                                wrhit <= dhit;
2179
                                m2Addr <= {pea[63:2],2'b00};
2180
                                if (resv_address==pea[63:5])
2181
                                        resv_address <= 59'd0;
2182 19 robfinch
`ifdef TLB
2183
                                if (!m1UnmappedDataArea & !q[3])
2184
                                        ITLBD[{q[2:0],pea[15:13]}] <= 1'b1;
2185
`endif
2186 14 robfinch
                                cyc_o <= 1'b1;
2187
                                stb_o <= 1'b1;
2188
                                we_o <= 1'b1;
2189
                                case(pea[2:0])
2190
                                3'b000: sel_o <= 8'b00000001;
2191
                                3'b001: sel_o <= 8'b00000010;
2192
                                3'b010: sel_o <= 8'b00000100;
2193
                                3'b011: sel_o <= 8'b00001000;
2194
                                3'b100: sel_o <= 8'b00010000;
2195
                                3'b101: sel_o <= 8'b00100000;
2196
                                3'b110: sel_o <= 8'b01000000;
2197
                                3'b111: sel_o <= 8'b10000000;
2198
                                endcase
2199
                                adr_o <= {pea[63:2],2'b00};
2200 19 robfinch
                                dat_o <= {8{m1Data[7:0]}};
2201 13 robfinch
                        end
2202 14 robfinch
 
2203 13 robfinch
                `SWC:
2204
                        begin
2205
                                rsf <= 1'b0;
2206
                                if (resv_address==pea[63:5]) begin
2207 19 robfinch
`ifdef TLB
2208
                                        if (!m1UnmappedDataArea & !q[3])
2209
                                                ITLBD[{q[2:0],pea[15:13]}] <= 1'b1;
2210
`endif
2211 13 robfinch
                                        wrhit <= dhit;
2212 14 robfinch
                                        m2Addr <= {pea[63:3],3'b00};
2213
                                        cyc_o <= 1'b1;
2214
                                        stb_o <= 1'b1;
2215
                                        we_o <= 1'b1;
2216
                                        sel_o <= 8'hFF;
2217
                                        adr_o <= {pea[63:3],3'b000};
2218 19 robfinch
                                        dat_o <= m1Data;
2219 13 robfinch
                                        resv_address <= 59'd0;
2220
                                        rsf <= 1'b1;
2221
                                end
2222
                                else
2223
                                        m2Opcode <= `NOPI;
2224
                        end
2225
                endcase
2226
        end
2227
end
2228
 
2229
//---------------------------------------------------------
2230
// EXECUTE:
2231
// - perform datapath operation
2232 14 robfinch
// - perform virtual to physical address translation.
2233 13 robfinch
//---------------------------------------------------------
2234
if (advanceX) begin
2235 14 robfinch
        m1hwxtype <= xhwxtype;
2236 13 robfinch
        m1Fip <= xFip;
2237
        m1extype <= xextype;
2238
        m1Opcode <= xOpcode;
2239
        m1Func <= xFunc;
2240
        m1Rt <= xRt;
2241
        m1Data <= xData;
2242
        m1IsCacheElement <= xisCacheElement;
2243
        if (xOpcode==`MOVZ && !aeqz) begin
2244
                m1Rt <= 9'd0;
2245
                m1Data <= 64'd0;
2246
        end
2247
        if (xOpcode==`MOVNZ && aeqz) begin
2248
                m1Rt <= 9'd0;
2249
                m1Data <= 64'd0;
2250
        end
2251
        m1pc <= xpc;
2252 16 robfinch
        m1pcv <= xpcv;
2253 13 robfinch
        xRt <= 9'd0;
2254
        a <= 64'd0;
2255
        b <= 64'd0;
2256
        imm <= 64'd0;
2257
        xextype <= `EX_NON;
2258
        if (xOpcode[6:4]!=`IMM) begin
2259
                xIR <= `NOP_INSN;
2260
        end
2261
//      xpc <= 64'd0;
2262
        case(xOpcode)
2263
        `MISC:
2264
                case(xFunc)
2265
                `WAIT:  m1clkoff <= 1'b1;
2266 19 robfinch
                `ICACHE_ON:             ICacheOn <= 1'b1;
2267
                `ICACHE_OFF:    ICacheOn <= 1'b0;
2268
`ifdef TLB
2269 14 robfinch
                `TLBP:  ea <= TLBVirtPage;
2270 13 robfinch
                `TLBR,`TLBWI:
2271
                        begin
2272 19 robfinch
                                i <= {Index[2:0],TLBVirtPage[15:13]};
2273 13 robfinch
                        end
2274
                `TLBWR:
2275
                        begin
2276 19 robfinch
                                i <= {Random,TLBVirtPage[15:13]};
2277 13 robfinch
                        end
2278 19 robfinch
`endif
2279 13 robfinch
                default:        ;
2280
                endcase
2281
        `R:
2282
                case(xFunc)
2283
                `MTSPR:
2284
                        case(xIR[12:7])
2285 19 robfinch
`ifdef TLB
2286
                        `Wired:                 Wired <= a[2:0];
2287
                        `TLBIndex:              Index <= a[2:0];
2288
                        `TLBVirtPage:   TLBVirtPage <= a[63:13];
2289
                        `TLBPhysPage0:  TLBPhysPage0 <= a[63:13];
2290
                        `TLBPhysPage1:  TLBPhysPage1 <= a[63:13];
2291
                        `TLBPageMask:   TLBPageMask <= a[24:13];
2292 14 robfinch
                        `TLBASID:               begin
2293 19 robfinch
                                                        TLBValid <= a[0];
2294
                                                        TLBD <= a[1];
2295
                                                        TLBG <= a[2];
2296
                                                        TLBASID <= a[15:8];
2297 14 robfinch
                                                        end
2298 19 robfinch
                        `PageTableAddr: PageTableAddr <= a[63:13];
2299
                        `BadVAddr:              BadVAddr <= a[63:13];
2300
`endif
2301
                        `ASID:                  ASID <= a[7:0];
2302
                        `EPC:                   EPC <= a;
2303
                        `TBA:                   TBA <= {a[63:12],12'h000};
2304
                        `AXC:                   AXC <= a[3:0];
2305
                        `NON_ICACHE_SEG:        nonICacheSeg <= a[63:32];
2306 13 robfinch
                        default:        ;
2307
                        endcase
2308
                `OMG:   mutex_gate[a[5:0]] <= 1'b1;
2309
                `CMG:   mutex_gate[a[5:0]] <= 1'b0;
2310
                `OMGI:  mutex_gate[xIR[12:7]] <= 1'b1;
2311
                `CMGI:  mutex_gate[xIR[12:7]] <= 1'b0;
2312
                default:        ;
2313
                endcase
2314
        `CALL:  m1Data <= fnIncPC(xpc);
2315
        `INW:
2316
                        begin
2317
                        cyc_o <= 1'b1;
2318
                        stb_o <= 1'b1;
2319 14 robfinch
                        sel_o <= 8'hFF;
2320 13 robfinch
                        adr_o <= {xData[63:3],3'b000};
2321
                        end
2322 14 robfinch
        `INH,`INHU:
2323 13 robfinch
                        begin
2324
                        cyc_o <= 1'b1;
2325
                        stb_o <= 1'b1;
2326 14 robfinch
                        sel_o <= xData[2] ? 8'b11110000 : 8'b00001111;
2327 13 robfinch
                        adr_o <= {xData[63:2],2'b00};
2328
                        end
2329 14 robfinch
        `INCH,`INCU:
2330 13 robfinch
                        begin
2331
                        cyc_o <= 1'b1;
2332
                        stb_o <= 1'b1;
2333 14 robfinch
                        case(xData[2:1])
2334
                        2'b00:  sel_o <= 8'b00000011;
2335
                        2'b01:  sel_o <= 8'b00001100;
2336
                        2'b10:  sel_o <= 8'b00110000;
2337
                        2'b11:  sel_o <= 8'b11000000;
2338 13 robfinch
                        endcase
2339
                        adr_o <= {xData[63:1],1'b0};
2340
                        end
2341 14 robfinch
        `INB,`INBU:
2342 13 robfinch
                        begin
2343
                        cyc_o <= 1'b1;
2344
                        stb_o <= 1'b1;
2345 14 robfinch
                        case(xData[2:0])
2346
                        3'b000: sel_o <= 8'b00000001;
2347
                        3'b001: sel_o <= 8'b00000010;
2348
                        3'b010: sel_o <= 8'b00000100;
2349
                        3'b011: sel_o <= 8'b00001000;
2350
                        3'b100: sel_o <= 8'b00010000;
2351
                        3'b101: sel_o <= 8'b00100000;
2352
                        3'b110: sel_o <= 8'b01000000;
2353
                        3'b111: sel_o <= 8'b10000000;
2354 13 robfinch
                        endcase
2355
                        adr_o <= xData;
2356
                        end
2357
        `OUTW:
2358
                        begin
2359
                        cyc_o <= 1'b1;
2360
                        stb_o <= 1'b1;
2361
                        we_o <= 1'b1;
2362 14 robfinch
                        sel_o <= 8'hFF;
2363 13 robfinch
                        adr_o <= {xData[63:3],3'b000};
2364 14 robfinch
                        dat_o <= b;
2365 13 robfinch
                        end
2366
        `OUTH:
2367
                        begin
2368
                        cyc_o <= 1'b1;
2369
                        stb_o <= 1'b1;
2370
                        we_o <= 1'b1;
2371 14 robfinch
                        sel_o <= xData[2] ? 8'b11110000 : 8'b00001111;
2372 13 robfinch
                        adr_o <= {xData[63:2],2'b00};
2373 14 robfinch
                        dat_o <= {2{b[31:0]}};
2374 13 robfinch
                        end
2375
        `OUTC:
2376
                        begin
2377
                        cyc_o <= 1'b1;
2378
                        stb_o <= 1'b1;
2379
                        we_o <= 1'b1;
2380 14 robfinch
                        case(xData[2:1])
2381
                        2'b00:  sel_o <= 8'b00000011;
2382
                        2'b01:  sel_o <= 8'b00001100;
2383
                        2'b10:  sel_o <= 8'b00110000;
2384
                        2'b11:  sel_o <= 8'b11000000;
2385 13 robfinch
                        endcase
2386
                        adr_o <= {xData[63:1],1'b0};
2387 14 robfinch
                        dat_o <= {4{b[15:0]}};
2388 13 robfinch
                        end
2389
        `OUTB:
2390
                        begin
2391
                        cyc_o <= 1'b1;
2392
                        stb_o <= 1'b1;
2393
                        we_o <= 1'b1;
2394 14 robfinch
                        case(xData[2:0])
2395
                        3'b000: sel_o <= 8'b00000001;
2396
                        3'b001: sel_o <= 8'b00000010;
2397
                        3'b010: sel_o <= 8'b00000100;
2398
                        3'b011: sel_o <= 8'b00001000;
2399
                        3'b100: sel_o <= 8'b00010000;
2400
                        3'b101: sel_o <= 8'b00100000;
2401
                        3'b110: sel_o <= 8'b01000000;
2402
                        3'b111: sel_o <= 8'b10000000;
2403 13 robfinch
                        endcase
2404
                        adr_o <= xData;
2405 14 robfinch
                        dat_o <= {8{b[7:0]}};
2406 13 robfinch
                        end
2407
        `LB,`LBU,`LC,`LCU,`LH,`LHU,`LW,`LWR,`SW,`SH,`SC,`SB,`SWC:
2408
                        begin
2409 19 robfinch
                        m1Data <= b;
2410 13 robfinch
                        ea <= xData;
2411
                        end
2412
        `MEMNDX:
2413
                        begin
2414
                        m1Opcode <= xFunc;
2415 19 robfinch
                        m1Data <= c;
2416 13 robfinch
                        ea <= xData;
2417
                        end
2418
        `DIVSI,`DIVUI:
2419
                if (b==64'd0) begin
2420
                        xextype <= `EX_DBZ;
2421
                end
2422
        default:        ;
2423
        endcase
2424 19 robfinch
`ifndef BRANCH_PREDICTION_SIMPLE
2425 13 robfinch
        // Update the branch history
2426
        if (isxBranch) begin
2427
                gbl_branch_hist <= {gbl_branch_hist,takb};
2428
                branch_history_table[bht_wa] <= xbits_new;
2429
        end
2430 19 robfinch
`endif
2431 13 robfinch
end
2432
 
2433
//---------------------------------------------------------
2434
// RFETCH:
2435
// Register fetch stage
2436
//---------------------------------------------------------
2437
if (advanceR) begin
2438 14 robfinch
        xAXC <= dAXC;
2439
        xhwxtype <= dhwxtype;
2440 13 robfinch
        xFip <= dFip;
2441
        xextype <= dextype;
2442
        xIR <= dIR;
2443
        xpc <= dpc;
2444 16 robfinch
        xpcv <= dpcv;
2445 13 robfinch
        xbranch_taken <= dbranch_taken;
2446
        dbranch_taken <= 1'b0;
2447
        dextype <= `EX_NON;
2448
        if (dOpcode[6:4]!=`IMM) // IMM is "sticky"
2449
                dIR <= `NOP_INSN;
2450
        dRa <= 9'd0;
2451
        dRb <= 9'd0;
2452
 
2453
        // Result forward muxes
2454
        casex(dRa)
2455
        9'bxxxx00000:   a <= 64'd0;
2456
        xRt:    a <= xData;
2457
        m1Rt:   a <= m1Data;
2458
        m2Rt:   a <= m2Data;
2459
        wRt:    a <= wData;
2460
        tRt:    a <= tData;
2461
        default:        a <= rfoa;
2462
        endcase
2463
        casex(dRb)
2464
        9'bxxxx00000:   b <= 64'd0;
2465
        xRt:    b <= disRightShift ? -xData[5:0] : xData;
2466
        m1Rt:   b <= disRightShift ? -m1Data[5:0] : m1Data;
2467
        m2Rt:   b <= disRightShift ? -m2Data[5:0] : m2Data;
2468
        wRt:    b <= disRightShift ? -wData[5:0] : wData;
2469
        tRt:    b <= disRightShift ? -tData[5:0] : tData;
2470
        default:        b <= disRightShift ? -rfob[5:0] : rfob;
2471
        endcase
2472
        if (dOpcode==`SHFTI)
2473
                case(dFunc)
2474
                `RORI:          b <= {58'd0,~dIR[24:19]+6'd1};
2475
                default:        b <= {58'd0,dIR[24:19]};
2476
                endcase
2477
        casex(dRc)
2478
        9'bxxxx00000:   c <= 64'd0;
2479
        xRt:    c <= xData;
2480
        m1Rt:   c <= m1Data;
2481
        m2Rt:   c <= m2Data;
2482
        wRt:    c <= wData;
2483
        tRt:    c <= tData;
2484
        default:        c <= rfoc;
2485
        endcase
2486
 
2487
        // Set the target register
2488 14 robfinch
        casex(dOpcode)
2489
        `SETLO:         xRt <= {dAXC,dIR[36:32]};
2490
        `SETHI:         xRt <= {dAXC,dIR[36:32]};
2491
        `RR:            xRt <= {dAXC,dIR[24:20]};
2492 13 robfinch
        `BTRI:          xRt <= 9'd0;
2493
        `BTRR:          xRt <= 9'd0;
2494
        `TRAPcc:        xRt <= 9'd0;
2495
        `TRAPcci:       xRt <= 9'd0;
2496
        `JMP:           xRt <= 9'd00;
2497 14 robfinch
        `CALL:          xRt <= {dAXC,5'd31};
2498
        `RET:           xRt <= {dAXC,dIR[24:20]};
2499 13 robfinch
        `MEMNDX:
2500
                case(dFunc)
2501
                `SW,`SH,`SC,`SB,`OUTW,`OUTH,`OUTC,`OUTB:
2502
                                xRt <= 9'd0;
2503 14 robfinch
                default:        xRt <= {dAXC,dIR[24:20]};
2504 13 robfinch
                endcase
2505
        `SW,`SH,`SC,`SB,`OUTW,`OUTH,`OUTC,`OUTB:
2506
                                xRt <= 9'd0;
2507
        `NOPI:          xRt <= 9'd0;
2508
        `BEQI,`BNEI,`BLTI,`BLEI,`BGTI,`BGEI,`BLTUI,`BLEUI,`BGTUI,`BGEUI:
2509
                                xRt <= 9'd0;
2510 14 robfinch
        default:        xRt <= {dAXC,dIR[29:25]};
2511 13 robfinch
        endcase
2512
        if (dOpcode[6:4]==`IMM)
2513
                xRt <= 9'd0;
2514
 
2515
        // Set immediate value
2516
        if (xOpcode[6:4]==`IMM) begin
2517
                imm <= {xIR[38:0],dIR[24:0]};
2518
        end
2519
        else
2520
                case(dOpcode)
2521
                `BTRI:  imm <= {{44{dIR[19]}},dIR[19:0]};
2522
                `BEQI,`BNEI,`BLTI,`BLEI,`BGTI,`BGEI,`BLTUI,`BLEUI,`BGTUI,`BGEUI:
2523
                        imm <= {{46{dIR[17]}},dIR[17:0]};
2524
                `ANDI:  imm <= {39'h7FFFFFFFFF,dIR[24:0]};
2525
                `ORI:   imm <= {39'h0000000000,dIR[24:0]};
2526
                `XORI:  imm <= {39'h0000000000,dIR[24:0]};
2527
                `RET:   imm <= {44'h00000000000,dIR[19:0]};
2528
                `MEMNDX:        imm <= {{51{dIR[19]}},dIR[19:7]};
2529
                default:        imm <= {{39{dIR[24]}},dIR[24:0]};
2530
                endcase
2531
        case(dOpcode)
2532
 
2533
        `MISC:
2534
                case(dFunc)
2535
                `SEI:   im <= 1'b1;
2536
                `CLI:   im <= 1'b0;
2537
                endcase
2538
        endcase
2539
 
2540
end
2541
 
2542
//---------------------------------------------------------
2543
// IFETCH:
2544
// - check for external hardware interrupt
2545
// - fetch instruction
2546
// - increment PC
2547
// - set special register defaults for some instructions
2548
//---------------------------------------------------------
2549
if (advanceI) begin
2550 14 robfinch
        dAXC <= AXC;
2551 13 robfinch
        dextype <= `EX_NON;
2552 14 robfinch
        if (nmi_edge & !StatusHWI) begin
2553
                $display("*****************");
2554
                $display("NMI edge detected");
2555
                $display("*****************");
2556
                StatusHWI <= 1'b1;
2557 13 robfinch
                nmi_edge <= 1'b0;
2558 14 robfinch
                dhwxtype <= 2'b01;
2559 13 robfinch
                dIR <= `NOP_INSN;
2560
                dextype <= `EX_NMI;
2561
        end
2562 14 robfinch
        else if (irq_i & !im & !StatusHWI) begin
2563 16 robfinch
                im <= 1'b1;
2564 14 robfinch
                StatusHWI <= 1'b1;
2565
                dhwxtype <= 2'b10;
2566 13 robfinch
                dIR <= `NOP_INSN;
2567
                dextype <= `EX_IRQ;
2568
        end
2569
        // Are we filling the pipeline with NOP's as a result of a previous
2570
        // hardware interrupt ?
2571 14 robfinch
        else if (|dhwxtype|dFip) begin
2572 13 robfinch
                dIR <= `NOP_INSN;
2573
        end
2574 19 robfinch
`ifdef TLB
2575 14 robfinch
        else if (ITLBMiss)
2576
                dIR <= `NOP_INSN;
2577 19 robfinch
`endif
2578 13 robfinch
        else begin
2579
                dIR <= insn;
2580 14 robfinch
`include "insn_dumpsc.v"
2581 13 robfinch
        end
2582
        nopI <= 1'b0;
2583
        if (dOpcode[6:4]!=`IMM) begin
2584
                dpc <= pc;
2585 16 robfinch
                dpcv <= 1'b1;
2586 13 robfinch
        end
2587 14 robfinch
        casex(iOpcode)
2588
        `SETLO:         dRa <= {AXC,insn[36:32]};
2589
        `SETHI:         dRa <= {AXC,insn[36:32]};
2590
        default:        dRa <= {AXC,insn[34:30]};
2591
        endcase
2592
        dRb <= {AXC,insn[29:25]};
2593
        dRc <= {AXC,insn[24:20]};
2594 19 robfinch
`ifdef TLB
2595 13 robfinch
        if (ITLBMiss) begin
2596 14 robfinch
                $display("TLB miss on instruction fetch.");
2597 13 robfinch
                CauseCode <= `EX_TLBI;
2598
                StatusEXL <= 1'b1;
2599
                BadVAddr <= pc[63:13];
2600
                pc <= `ITLB_MissHandler;
2601
                EPC <= pc;
2602
        end
2603 19 robfinch
        else
2604
`endif
2605
        begin
2606 13 robfinch
                dbranch_taken <= 1'b0;
2607
                pc <= fnIncPC(pc);
2608
                case(iOpcode)
2609
                `MISC:
2610
                        case(iFunc)
2611
                        `FIP:   dFip <= 1'b1;
2612
                        default:        ;
2613
                        endcase
2614 19 robfinch
                // We predict the return address by storing it in a return address stack
2615
                // during a call instruction, then popping it off the stack in a return
2616
                // instruction. The prediction will not always be correct, if it's wrong
2617
                // it's corrected by the EX stage branching to the right address.
2618
                `CALL:
2619 13 robfinch
                        begin
2620 19 robfinch
`ifdef RAS_PREDICTION
2621
                                ras[ras_sp] <= fnIncPC(pc);
2622
                                ras_sp <= ras_sp - 6'd1;
2623
`endif
2624 13 robfinch
                                dbranch_taken <= 1'b1;
2625
                                pc <= jmp_tgt;
2626
                        end
2627 19 robfinch
                `RET:
2628
                        begin
2629
`ifdef RAS_PREDICTION
2630
//                              $display("predicted return address=%h.%h",{ras[ras_sp + 6'd1][63:4],4'b0000},ras[ras_sp + 6'd1][3:2]);
2631
                                pc <= ras[ras_sp + 6'd1];
2632
                                ras_sp <= ras_sp + 6'd1;
2633
`endif
2634
                        end
2635
                `JMP:
2636
                        begin
2637
                                dbranch_taken <= 1'b1;
2638
                                pc <= jmp_tgt;
2639
                        end
2640 13 robfinch
                `BTRR:
2641
                        case(insn[4:0])
2642
                        `BEQ,`BNE,`BLT,`BLE,`BGT,`BGE,`BLTU,`BLEU,`BGTU,`BGEU,`BAND,`BOR,`BNR:
2643
                                if (predict_taken) begin
2644 19 robfinch
//                                      $display("Taking predicted branch: %h",{pc[63:4] + {{42{insn[24]}},insn[24:7]},insn[6:5],2'b00});
2645 13 robfinch
                                        dbranch_taken <= 1'b1;
2646
                                        pc <= {pc[63:4] + {{42{insn[24]}},insn[24:7]},insn[6:5],2'b00};
2647
                                end
2648
                        default:        ;
2649
                        endcase
2650 19 robfinch
`ifdef BTB
2651
                `BTRI:
2652
                        if (predict_taken) begin
2653
                                dbranch_taken <= 1'b1;
2654
                                pc <= btb[pc[7:2]];
2655
                        end
2656
`endif
2657 13 robfinch
                `BEQI,`BNEI,`BLTI,`BLEI,`BGTI,`BGEI,`BLTUI,`BLEUI,`BGTUI,`BGEUI:
2658
                        begin
2659
                                if (predict_taken) begin
2660
                                        dbranch_taken <= 1'b1;
2661
                                        pc <= {pc[63:4] + {{50{insn[29]}},insn[29:20]},insn[19:18],2'b00};
2662
                                end
2663
                        end
2664
                `TRAPcc:        if (predict_taken) begin pc <= {TBA[63:13],`GEN_TRAP_OFFSET}; dbranch_taken <= 1'b1; end
2665
                `TRAPcci:       if (predict_taken) begin pc <= {TBA[63:13],`GEN_TRAP_OFFSET}; dbranch_taken <= 1'b1; end
2666
                default:        ;
2667
                endcase
2668
        end
2669
end
2670
 
2671
//`include "RPSTAGE.v"
2672
//---------------------------------------------------------
2673
// EXECUTE - part two:
2674
// - override the default program counter increment for
2675
//   control flow instructions
2676
// - NOP out the instructions following a branch in the
2677
//   pipeline
2678
//---------------------------------------------------------
2679
if (advanceX) begin
2680
        case(xOpcode)
2681
        `MISC:
2682
                case(xFunc)
2683 14 robfinch
                `IRET:
2684
                        if (StatusHWI) begin
2685
                                StatusHWI <= 1'b0;
2686 16 robfinch
                                im <= 1'b0;
2687 14 robfinch
                                pc <= IPC;
2688
                                dIR <= `NOP_INSN;
2689
                                xIR <= `NOP_INSN;
2690
                                xRt <= 9'd0;
2691 16 robfinch
                                xpcv <= 1'b0;
2692
                                dpcv <= 1'b0;
2693 14 robfinch
                        end
2694
                `ERET:
2695
                        if (StatusEXL) begin
2696
                                StatusEXL <= 1'b0;
2697
                                pc <= EPC;
2698
                                dIR <= `NOP_INSN;
2699
                                xIR <= `NOP_INSN;
2700
                                xRt <= 9'd0;
2701 16 robfinch
                                xpcv <= 1'b0;
2702
                                dpcv <= 1'b0;
2703 14 robfinch
                        end
2704 13 robfinch
                default:        ;
2705
                endcase
2706 19 robfinch
        `R:
2707
                case(xFunc)
2708
                `EXEC:
2709
                        begin
2710
                                pc <= fnIncPC(xpc);
2711
                                dIR <= b;
2712
                                xIR <= `NOP_INSN;
2713
                                xRt <= 9'd0;
2714
                                xpcv <= 1'b0;
2715
                                dpcv <= 1'b0;
2716
                        end
2717
                default:        ;
2718
                endcase
2719 13 robfinch
        `BTRR:
2720
                case(xIR[4:0])
2721
        // BEQ r1,r2,label
2722
                `BEQ,`BNE,`BLT,`BLE,`BGT,`BGE,`BLTU,`BLEU,`BGTU,`BGEU,`BAND,`BOR,`BNR:
2723 14 robfinch
                        if (!takb & xbranch_taken) begin
2724
                                $display("Taking mispredicted branch %h",fnIncPC(xpc));
2725
                                pc <= fnIncPC(xpc);
2726
                                dIR <= `NOP_INSN;
2727
                                xIR <= `NOP_INSN;
2728
                                xRt <= 9'd0;
2729 16 robfinch
                                xpcv <= 1'b0;
2730
                                dpcv <= 1'b0;
2731 14 robfinch
                        end
2732
                        else if (takb & !xbranch_taken) begin
2733
                                $display("Taking branch %h.%h",{xpc[63:4] + {{42{xIR[24]}},xIR[24:7]},4'b0000},xIR[6:5]);
2734 13 robfinch
                                pc[63:4] <= xpc[63:4] + {{42{xIR[24]}},xIR[24:7]};
2735
                                pc[3:2] <= xIR[6:5];
2736
                                dIR <= `NOP_INSN;
2737
                                xIR <= `NOP_INSN;
2738
                                xRt <= 9'd0;
2739 16 robfinch
                                xpcv <= 1'b0;
2740
                                dpcv <= 1'b0;
2741 13 robfinch
                        end
2742
        // BEQ r1,r2,r10
2743
                `BEQR,`BNER,`BLTR,`BLER,`BGTR,`BGER,`BLTUR,`BLEUR,`BGTUR,`BGEUR://,`BANDR,`BORR,`BNRR:
2744
                        if (takb) begin
2745
                                pc[63:2] <= c[63:2];
2746
                                pc[1:0] <= 2'b00;
2747 19 robfinch
`ifdef BTB
2748
                                btb[xpc[7:2]] <= c;
2749
`endif
2750 13 robfinch
                                dIR <= `NOP_INSN;
2751
                                xIR <= `NOP_INSN;
2752
                                xRt <= 9'd0;
2753 16 robfinch
                                xpcv <= 1'b0;
2754
                                dpcv <= 1'b0;
2755 13 robfinch
                        end
2756
                default:        ;
2757
                endcase
2758
        // JMP and CALL change the program counter immediately in the IF stage.
2759
        // There's no work to do here. The pipeline does not need to be cleared.
2760
        `JMP:   ;
2761
        `CALL:  ;
2762 14 robfinch
        `JAL:
2763
                begin
2764
                        pc[63:2] <= a[63:2] + imm[63:2];
2765
                        dIR <= `NOP_INSN;
2766
                        xIR <= `NOP_INSN;
2767
                        xRt <= 9'd0;
2768 16 robfinch
                        xpcv <= 1'b0;
2769
                        dpcv <= 1'b0;
2770 14 robfinch
                end
2771 19 robfinch
 
2772
        // Check the pc of the instruction after the RET instruction (the dpc), to
2773
        // see if it's equal to the RET target. If it's the same as the target then
2774
        // we predicted the RET return correctly, so there's nothing to do. Otherwise
2775
        // we need to branch to the RET location.
2776 14 robfinch
        `RET:
2777 19 robfinch
`ifdef RAS_PREDICTION
2778
                if (dpc[63:2]!=b[63:2]) begin
2779
`else
2780 14 robfinch
                begin
2781 19 robfinch
`endif
2782
//                      $display("returning to: %h.%h", {b[63:4],4'b0},b[3:2]);
2783 14 robfinch
                        pc[63:2] <= b[63:2];
2784
                        dIR <= `NOP_INSN;
2785
                        xIR <= `NOP_INSN;
2786
                        xRt <= 9'd0;
2787 16 robfinch
                        xpcv <= 1'b0;
2788
                        dpcv <= 1'b0;
2789 14 robfinch
                end
2790 19 robfinch
//              else
2791
//                      $display("RET address %h predicted correctly.", {b[63:4],4'b0},b[3:2]);
2792 13 robfinch
        // BEQ r1,#3,r10
2793
        `BTRI:
2794 19 robfinch
`ifdef BTB
2795 13 robfinch
                if (takb) begin
2796 19 robfinch
                        if ((xbranch_taken && b!=btb[xpc[7:2]]) ||      // took branch, but not to right target
2797
                                !xbranch_taken) begin                                   // didn't take branch, and were supposed to
2798
                                pc[63:2] <= b[63:2];
2799
                                pc[1:0] <= 2'b00;
2800
                                btb[xpc[7:2]] <= b;
2801
                                dIR <= `NOP_INSN;
2802
                                xIR <= `NOP_INSN;
2803
                                xRt <= 9'd0;
2804
                                xpcv <= 1'b0;
2805
                                dpcv <= 1'b0;
2806
                        end
2807
                end
2808
                else if (xbranch_taken) begin   // took the branch, and weren't supposed to
2809
                        pc <= fnIncPC(xpc);
2810
                        dIR <= `NOP_INSN;
2811
                        xIR <= `NOP_INSN;
2812
                        xRt <= 9'd0;
2813
                        xpcv <= 1'b0;
2814
                        dpcv <= 1'b0;
2815
                end
2816
`else
2817
                if (takb) begin
2818 13 robfinch
                        pc[63:2] <= b[63:2];
2819
                        pc[1:0] <= 2'b00;
2820
                        dIR <= `NOP_INSN;
2821
                        xIR <= `NOP_INSN;
2822
                        xRt <= 9'd0;
2823 16 robfinch
                        xpcv <= 1'b0;
2824
                        dpcv <= 1'b0;
2825 13 robfinch
                end
2826 19 robfinch
`endif
2827 13 robfinch
        // BEQI r1,#3,label
2828
        `BEQI,`BNEI,`BLTI,`BLEI,`BGTI,`BGEI,`BLTUI,`BLEUI,`BGTUI,`BGEUI:
2829
                if (takb) begin
2830
                        if (!xbranch_taken) begin
2831
                                pc[63:4] <= xpc[63:4] + {{50{xIR[29]}},xIR[29:20]};
2832
                                pc[3:2] <= xIR[19:18];
2833
                                dIR <= `NOP_INSN;
2834
                                xIR <= `NOP_INSN;
2835
                                xRt <= 9'd0;
2836 16 robfinch
                                xpcv <= 1'b0;
2837
                                dpcv <= 1'b0;
2838 13 robfinch
                        end
2839
                end
2840 14 robfinch
                else begin
2841
                        if (xbranch_taken) begin
2842 19 robfinch
//                              $display("Taking mispredicted branch %h",fnIncPC(xpc));
2843 14 robfinch
                                pc <= fnIncPC(xpc);
2844
                                dIR <= `NOP_INSN;
2845
                                xIR <= `NOP_INSN;
2846
                                xRt <= 9'd0;
2847 16 robfinch
                                xpcv <= 1'b0;
2848
                                dpcv <= 1'b0;
2849 14 robfinch
                        end
2850
                end
2851
        `TRAPcc,`TRAPcci:
2852 13 robfinch
                if (takb) begin
2853
                        StatusEXL <= 1'b1;
2854
                        CauseCode <= `EX_TRAP;
2855
                        EPC <= xpc;
2856
                        if (!xbranch_taken) begin
2857
                                pc <= {TBA[63:13],`GEN_TRAP_OFFSET};
2858
                                dIR <= `NOP_INSN;
2859
                                xIR <= `NOP_INSN;
2860
                                xRt <= 9'd0;
2861 16 robfinch
                                xpcv <= 1'b0;
2862
                                dpcv <= 1'b0;
2863 13 robfinch
                        end
2864
                end
2865 14 robfinch
                else begin
2866
                        if (xbranch_taken) begin
2867 19 robfinch
//                              $display("Taking mispredicted branch %h",fnIncPC(xpc));
2868 14 robfinch
                                pc <= fnIncPC(xpc);
2869 13 robfinch
                                dIR <= `NOP_INSN;
2870
                                xIR <= `NOP_INSN;
2871
                                xRt <= 9'd0;
2872 16 robfinch
                                xpcv <= 1'b0;
2873
                                dpcv <= 1'b0;
2874 13 robfinch
                        end
2875
                end
2876
        default:        ;
2877
        endcase
2878 14 robfinch
 
2879 13 robfinch
        if (dbz_error) begin
2880
                $display("Divide by zero error");
2881
                CauseCode <= `EX_DBZ;
2882
                StatusEXL <= 1'b1;
2883
                EPC <= xpc;
2884
                pc <= {TBA[63:13],`DBZ_TRAP_OFFSET};
2885
                dIR <= `NOP_INSN;
2886
                xIR <= `NOP_INSN;
2887
                xRt <= 9'd0;
2888 16 robfinch
                xpcv <= 1'b0;
2889
                dpcv <= 1'b0;
2890 13 robfinch
        end
2891 14 robfinch
        else if (ovr_error) begin
2892 13 robfinch
                $display("Overflow error");
2893
                CauseCode <= `EX_OFL;
2894
                StatusEXL <= 1'b1;
2895
                EPC <= xpc;
2896
                pc <= {TBA[63:13],`OFL_TRAP_OFFSET};
2897
                dIR <= `NOP_INSN;
2898
                xIR <= `NOP_INSN;
2899
                xRt <= 9'd0;
2900 16 robfinch
                xpcv <= 1'b0;
2901
                dpcv <= 1'b0;
2902 13 robfinch
        end
2903 14 robfinch
        else if (priv_violation) begin
2904
                $display("Priviledge violation");
2905
                CauseCode <= `EX_PRIV;
2906
                StatusEXL <= 1'b1;
2907
                EPC <= xpc;
2908
                pc <= {TBA[63:13],`PRIV_OFFSET};
2909
                dIR <= `NOP_INSN;
2910
                xIR <= `NOP_INSN;
2911
                xRt <= 9'd0;
2912 16 robfinch
                xpcv <= 1'b0;
2913
                dpcv <= 1'b0;
2914 14 robfinch
        end
2915 13 robfinch
end
2916
 
2917
//---------------------------------------------------------
2918
// MEMORY1 (M1') - part two:
2919
// Check for a TLB miss.
2920
//---------------------------------------------------------
2921 19 robfinch
`ifdef TLB
2922 13 robfinch
if (advanceM1) begin
2923
        if (m1IsLoad|m1IsStore) begin
2924
                if (DTLBMiss) begin
2925
                        $display("DTLB miss on address: %h",ea);
2926
                        m1extype <= `EX_TLBD;
2927
                        CauseCode <= `EX_TLBD;
2928
                        StatusEXL <= 1'b1;
2929
                        BadVAddr <= ea[63:13];
2930
                        EPC <= m1pc;
2931
                        pc <= `DTLB_MissHandler;
2932
                        m1Opcode <= `NOPI;
2933
                        m1Rt <= 9'd0;
2934
                        xIR <= `NOP_INSN;
2935
                        xRt <= 9'd0;
2936
                        dIR <= `NOP_INSN;
2937 16 robfinch
                        m1pcv <= 1'b0;
2938
                        xpcv <= 1'b0;
2939
                        dpcv <= 1'b0;
2940 13 robfinch
                end
2941
        end
2942
end
2943 19 robfinch
`endif
2944 13 robfinch
 
2945
//---------------------------------------------------------
2946
// MEMORY2 (M2')
2947
//---------------------------------------------------------
2948
if (advanceM2) begin
2949
end
2950
 
2951
//---------------------------------------------------------
2952
// WRITEBACK (WB') - part two:
2953
// - vector to exception handler address
2954
// In the case of a hardware interrupt (NMI/IRQ) we know
2955
// the pipeline following the interrupt is filled with
2956
// NOP instructions. This means there is no need to 
2957
// invalidate the pipeline.
2958 14 robfinch
//              Also, we have to wait until the WB stage before
2959
// vectoring so that the pc setting doesn't get trashed
2960
// by a branch or other exception.
2961 16 robfinch
//              Tricky because we have to find the first valid
2962
// PC to record in the IPC register. The interrupt might
2963
// have occurred in a branch shadow, in which case the
2964
// current PC isn't valid.
2965 13 robfinch
//---------------------------------------------------------
2966
if (advanceW) begin
2967 14 robfinch
        case(wextype)
2968 16 robfinch
        `EX_RST:        begin
2969
                                pc <= `RESET_VECTOR;
2970
                                case(1'b1)
2971
                                wpcv:   IPC <= wpc;
2972
                                m2pcv:  IPC <= m2pc;
2973
                                m1pcv:  IPC <= m1pc;
2974
                                xpcv:   IPC <= xpc;
2975
                                dpcv:   IPC <= dpc;
2976
                                default:        IPC <= pc;
2977
                                endcase
2978
                                end
2979
        `EX_NMI:        begin
2980
                                pc <= `NMI_VECTOR;
2981
                                case(1'b1)
2982
                                wpcv:   IPC <= wpc;
2983
                                m2pcv:  IPC <= m2pc;
2984
                                m1pcv:  IPC <= m1pc;
2985
                                xpcv:   IPC <= xpc;
2986
                                dpcv:   IPC <= dpc;
2987
                                default:        IPC <= pc;
2988
                                endcase
2989
                                end
2990
        `EX_IRQ:        begin
2991
                                pc <= `IRQ_VECTOR;
2992
                                case(1'b1)
2993
                                wpcv:   IPC <= wpc;
2994
                                m2pcv:  IPC <= m2pc;
2995
                                m1pcv:  IPC <= m1pc;
2996
                                xpcv:   IPC <= xpc;
2997
                                dpcv:   IPC <= dpc;
2998
                                default:        IPC <= pc;
2999
                                endcase
3000
                                end
3001 14 robfinch
        default:        ;
3002
        endcase
3003 13 robfinch
end
3004
 
3005
 
3006
//---------------------------------------------------------
3007
// Trailer (TR')
3008
// - no exceptions
3009
//---------------------------------------------------------
3010
if (advanceT) begin
3011
end
3012
 
3013
 
3014
//---------------------------------------------------------
3015
// Cache loader
3016
//---------------------------------------------------------
3017
if (rst_i) begin
3018
        cstate <= IDLE;
3019
end
3020
else begin
3021
case(cstate)
3022
IDLE:
3023 14 robfinch
        if (triggerDCacheLoad) begin
3024
                dcaccess <= 1'b1;
3025
                bte_o <= 2'b00;                 // linear burst
3026
                cti_o <= 3'b010;                // burst access
3027
                bl_o <= 5'd8;
3028
                cyc_o <= 1'b1;
3029
                stb_o <= 1'b1;
3030
                adr_o <= {pea[63:6],6'h00};
3031
                cstate <= DCACT;
3032 13 robfinch
        end
3033 14 robfinch
        else if (triggerICacheLoad) begin
3034
                icaccess <= 1'b1;
3035
                bte_o <= 2'b00;                 // linear burst
3036
                cti_o <= 3'b010;                // burst access
3037
                cyc_o <= 1'b1;
3038
                stb_o <= 1'b1;
3039 19 robfinch
                if (ICacheAct) begin
3040
                        bl_o <= 5'd8;
3041
                        adr_o <= {ppc[63:6],6'h00};
3042
                        cstate <= ICACT1;
3043
                end
3044
                else begin
3045
                        bl_o <= 5'd2;
3046
                        adr_o <= {ppc[63:4],4'b0000};
3047
                        cstate <= ICACT2;
3048
                end
3049 13 robfinch
        end
3050
// WISHBONE burst accesses
3051
//
3052
ICACT1:
3053
        if (ack_i) begin
3054 14 robfinch
                adr_o[5:3] <= adr_o[5:3] + 3'd1;
3055 19 robfinch
                if (adr_o[5:3]==3'd6)
3056 13 robfinch
                        cti_o <= 3'b111;        // Last cycle ahead
3057 19 robfinch
                else if (adr_o[5:3]==3'd7) begin
3058 13 robfinch
                        cti_o <= 3'b000;        // back to non-burst mode
3059
                        cyc_o <= 1'b0;
3060
                        stb_o <= 1'b0;
3061 14 robfinch
                        tmem[adr_o[12:6]] <= {1'b1,adr_o[63:13]};       // This will cause ihit to go high
3062
                        tvalid[adr_o[12:6]] <= 1'b1;
3063
                        icaccess <= 1'b0;
3064 13 robfinch
                        cstate <= IDLE;
3065
                end
3066
        end
3067 19 robfinch
ICACT2:
3068
        if (ack_i) begin
3069
                adr_o <= adr_o + 64'd8;
3070
                if (adr_o[3]==1'b0) begin
3071
                        cti_o <= 3'b111;        // Last cycle ahead
3072
                        tmpbuf <= dat_i;
3073
                end
3074
                else begin
3075
                        insnbuf <= {dat_i,tmpbuf};
3076
                        cti_o <= 3'b000;        // back to non-burst mode
3077
                        cyc_o <= 1'b0;
3078
                        stb_o <= 1'b0;
3079
                        icaccess <= 1'b0;
3080
                        ibuftag <= adr_o[63:4];
3081
                        cstate <= IDLE;
3082
                end
3083
        end
3084
 
3085 13 robfinch
DCACT:
3086 14 robfinch
        if (ack_i) begin
3087
                adr_o[5:3] <= adr_o[5:3] + 3'd1;
3088
                if (adr_o[5:3]==3'h6)
3089
                        cti_o <= 3'b111;        // Last cycle ahead
3090
                if (adr_o[5:3]==3'h7) begin
3091
                        cti_o <= 3'b000;        // back to non-burst mode
3092
                        cyc_o <= 1'b0;
3093
                        stb_o <= 1'b0;
3094
                        dcaccess <= 1'b0;
3095
                        cstate <= IDLE;
3096 13 robfinch
                end
3097
        end
3098 14 robfinch
 
3099 13 robfinch
endcase
3100
end
3101
 
3102
end
3103
 
3104
endmodule

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.