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

Subversion Repositories rtf65002

[/] [rtf65002/] [trunk/] [rtl/] [verilog/] [rtf65002d.v] - Blame information for rev 36

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

Line No. Rev Author Line
1 10 robfinch
`timescale 1ns / 1ps
2
// ============================================================================
3
//        __
4
//   \\__/ o\    (C) 2013  Robert Finch, Stratford
5
//    \  __ /    All rights reserved.
6
//     \/_//     robfinch<remove>@opencores.org
7
//       ||
8
//
9
// rtf65002.v
10
//  - 32 bit CPU
11
//
12
// This source file is free software: you can redistribute it and/or modify 
13
// it under the terms of the GNU Lesser General Public License as published 
14
// by the Free Software Foundation, either version 3 of the License, or     
15
// (at your option) any later version.                                      
16
//                                                                          
17
// This source file is distributed in the hope that it will be useful,      
18
// but WITHOUT ANY WARRANTY; without even the implied warranty of           
19
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the            
20
// GNU General Public License for more details.                             
21
//                                                                          
22
// You should have received a copy of the GNU General Public License        
23
// along with this program.  If not, see <http://www.gnu.org/licenses/>.    
24
//                                                                          
25
// ============================================================================
26
//
27 30 robfinch
`include "rtf65002_defines.v"
28 5 robfinch
 
29 35 robfinch
module rtf65002d(rst_md, rst_i, clk_i, nmi_i, irq_i, irq_vect, bte_o, cti_o, bl_o, lock_o, cyc_o, stb_o, ack_i, rty_i, err_i, we_o, sel_o, adr_o, dat_i, dat_o, km_o);
30 30 robfinch
parameter RESET1 = 6'd0;
31
parameter IFETCH = 6'd1;
32
parameter DECODE = 6'd2;
33
parameter STORE1 = 6'd3;
34
parameter STORE2 = 6'd4;
35 32 robfinch
parameter CALC = 6'd5;
36
parameter JSR161 = 6'd6;
37
parameter RTS1 = 6'd7;
38
parameter IY3 = 6'd8;
39
parameter BSR1 = 6'd9;
40
parameter BYTE_IX5 = 6'd10;
41
parameter BYTE_IY5 = 6'd11;
42
parameter WAIT_DHIT = 6'd12;
43
parameter RESET2 = 6'd13;
44
parameter MULDIV1 = 6'd14;
45
parameter MULDIV2 = 6'd15;
46
parameter BYTE_DECODE = 6'd16;
47
parameter BYTE_CALC = 6'd17;
48
parameter BUS_ERROR = 6'd18;
49 35 robfinch
parameter LOAD_MAC1 = 6'd19;
50
parameter LOAD_MAC2 = 6'd20;
51
parameter LOAD_MAC3 = 6'd21;
52
parameter MVN3 = 6'd22;
53
parameter PUSHA1 = 6'd23;
54
parameter POPA1 = 6'd24;
55
parameter BYTE_IFETCH = 6'd25;
56
parameter LOAD_DCACHE = 6'd26;
57
parameter LOAD_ICACHE = 6'd27;
58
parameter LOAD_IBUF1 = 6'd28;
59
parameter LOAD_IBUF2 = 6'd29;
60
parameter LOAD_IBUF3 = 6'd30;
61
parameter ICACHE1 = 6'd31;
62
parameter IBUF1 = 6'd32;
63
parameter DCACHE1 = 6'd33;
64
parameter CMPS1 = 6'd34;
65 5 robfinch
 
66 21 robfinch
input rst_md;           // reset mode, 1=emulation mode, 0=native mode
67 5 robfinch
input rst_i;
68
input clk_i;
69
input nmi_i;
70
input irq_i;
71 13 robfinch
input [8:0] irq_vect;
72 5 robfinch
output reg [1:0] bte_o;
73
output reg [2:0] cti_o;
74
output reg [5:0] bl_o;
75
output reg lock_o;
76
output reg cyc_o;
77
output reg stb_o;
78
input ack_i;
79 35 robfinch
input rty_i;
80 21 robfinch
input err_i;
81 5 robfinch
output reg we_o;
82
output reg [3:0] sel_o;
83
output reg [33:0] adr_o;
84
input [31:0] dat_i;
85
output reg [31:0] dat_o;
86
 
87 32 robfinch
output km_o;
88
 
89 30 robfinch
reg [5:0] state;
90
reg [5:0] retstate;
91 21 robfinch
wire [63:0] insn;
92
reg [63:0] ibuf;
93 5 robfinch
reg [31:0] bufadr;
94 25 robfinch
reg [63:0] exbuf;
95 5 robfinch
 
96 35 robfinch
integer n;
97 5 robfinch
reg cf,nf,zf,vf,bf,im,df,em;
98 32 robfinch
reg tf;         // trace mode flag
99
reg ttrig;      // trace trigger
100 5 robfinch
reg em1;
101 32 robfinch
reg gie;        // global interrupt enable (set when sp is loaded)
102 25 robfinch
reg hwi;        // hardware interrupt indicator
103 5 robfinch
reg nmoi;       // native mode on interrupt
104 32 robfinch
wire [31:0] sr = {nf,vf,em,tf,23'b0,bf,df,im,zf,cf};
105 5 robfinch
wire [7:0] sr8 = {nf,vf,1'b0,bf,df,im,zf,cf};
106
reg nmi1,nmi_edge;
107
reg wai;
108 36 robfinch
reg wrrf;               // write register file
109 5 robfinch
reg [31:0] acc;
110
reg [31:0] x;
111
reg [31:0] y;
112
reg [7:0] sp;
113 13 robfinch
reg [31:0] spage;        // stack page
114 5 robfinch
wire [7:0] acc8 = acc[7:0];
115
wire [7:0] x8 = x[7:0];
116
wire [7:0] y8 = y[7:0];
117
reg [31:0] isp;          // interrupt stack pointer
118 35 robfinch
reg [31:0] oisp; // original isp for bus retry
119 12 robfinch
wire [63:0] prod;
120
wire [31:0] q,r;
121
reg [31:0] tick;
122 5 robfinch
wire [7:0] sp_dec = sp - 8'd1;
123
wire [7:0] sp_inc = sp + 8'd1;
124
wire [31:0] isp_dec = isp - 32'd1;
125
wire [31:0] isp_inc = isp + 32'd1;
126 25 robfinch
reg [3:0] suppress_pcinc;
127 5 robfinch
reg [31:0] pc;
128 23 robfinch
reg [31:0] opc;
129 35 robfinch
wire [3:0] pc_inc;
130
wire [3:0] pc_inc8;
131 30 robfinch
wire [31:0] pcp2 = pc + (32'd2 & suppress_pcinc);        // for branches
132
wire [31:0] pcp4 = pc + (32'd4 & suppress_pcinc);        // for branches
133
wire [31:0] pcp8 = pc + 32'd8;                                           // cache controller needs this
134 13 robfinch
reg [31:0] abs8; // 8 bit mode absolute address register
135
reg [31:0] vbr;          // vector table base register
136 5 robfinch
wire bhit=pc==bufadr;
137 35 robfinch
reg [2:0] bcnt;          // burst count for cache controller
138 5 robfinch
reg [31:0] regfile [15:0];
139 21 robfinch
reg [63:0] ir;
140 32 robfinch
reg pg2;
141
wire [8:0] ir9 = {pg2,ir[7:0]};
142 5 robfinch
wire [3:0] Ra = ir[11:8];
143
wire [3:0] Rb = ir[15:12];
144
reg [31:0] rfoa;
145
reg [31:0] rfob;
146
always @(Ra or x or y or acc)
147
case(Ra)
148
4'h0:   rfoa <= 32'd0;
149
4'h1:   rfoa <= acc;
150
4'h2:   rfoa <= x;
151
4'h3:   rfoa <= y;
152
default:        rfoa <= regfile[Ra];
153
endcase
154
always @(Rb or x or y or acc)
155
case(Rb)
156
4'h0:   rfob <= 32'd0;
157
4'h1:   rfob <= acc;
158
4'h2:   rfob <= x;
159
4'h3:   rfob <= y;
160
default:        rfob <= regfile[Rb];
161
endcase
162
reg [3:0] Rt;
163
reg [33:0] ea;
164
reg first_ifetch;
165 12 robfinch
reg [31:0] lfsr;
166
wire lfsr_fb;
167
xnor(lfsr_fb,lfsr[0],lfsr[1],lfsr[21],lfsr[31]);
168 5 robfinch
reg [31:0] a, b;
169 32 robfinch
wire signed [31:0] as = a;
170
wire signed [31:0] bs = b;
171
wire lt = as < bs;
172
wire eq = a==b;
173
wire ltu = a < b;
174
 
175 5 robfinch
reg [7:0] b8;
176 32 robfinch
wire [32:0] alu_out;
177 5 robfinch
reg [32:0] res;
178
reg [8:0] res8;
179
wire resv8,resv32;
180
wire resc8 = res8[8];
181
wire resc32 = res[32];
182
wire resz8 = res8[7:0]==8'h00;
183
wire resz32 = res[31:0]==32'd0;
184
wire resn8 = res8[7];
185
wire resn32 = res[31];
186
 
187 35 robfinch
reg [33:0] vect;
188 5 robfinch
reg [31:0] ia;                   // temporary reg to hold indirect address
189
reg isInsnCacheLoad;
190
reg isDataCacheLoad;
191 10 robfinch
reg isCacheReset;
192 5 robfinch
wire hit0,hit1;
193 30 robfinch
`ifdef SUPPORT_DCACHE
194 5 robfinch
wire dhit;
195 30 robfinch
`else
196
wire dhit = 1'b0;
197
`endif
198 10 robfinch
reg write_allocate;
199 32 robfinch
wire wr;
200 5 robfinch
reg [3:0] wrsel;
201
reg [31:0] radr;
202
reg [1:0] radr2LSB;
203
wire [33:0] radr34 = {radr,radr2LSB};
204
wire [33:0] radr34p1 = radr34 + 34'd1;
205
reg [31:0] wadr;
206
reg [1:0] wadr2LSB;
207
reg [31:0] wdat;
208
wire [31:0] rdat;
209 32 robfinch
reg [4:0] load_what;
210
reg [5:0] store_what;
211 35 robfinch
reg [8:0] intno;                 // interrupt number to take
212 23 robfinch
reg [31:0] derr_address;
213 5 robfinch
reg imiss;
214
reg dmiss;
215
reg icacheOn,dcacheOn;
216 30 robfinch
`ifdef SUPPORT_DCACHE
217 20 robfinch
wire unCachedData = radr[31:20]==12'hFFD || !dcacheOn;  // I/O area is uncached
218 30 robfinch
`else
219
wire unCachedData = 1'b1;
220
`endif
221
`ifdef SUPPORT_ICACHE
222 20 robfinch
wire unCachedInsn = pc[31:13]==19'h0 || !icacheOn;              // The lowest 8kB is uncached.
223 30 robfinch
`else
224
wire unCachedInsn = 1'b1;
225
`endif
226 32 robfinch
`ifdef ICACHE_2WAY
227
reg [31:0] clfsr;
228
wire clfsr_fb;
229
xnor(clfsr_fb,clfsr[0],clfsr[1],clfsr[21],clfsr[31]);
230
wire [1:0] whichrd;
231
wire whichwr=clfsr[0];
232
`endif
233 35 robfinch
reg [31:0] ilfsr;
234
wire ilfsr_fb;
235
xnor(ilfsr_fb,ilfsr[0],ilfsr[1],ilfsr[21],ilfsr[31]);
236 32 robfinch
reg km;                 // kernel mode indicator
237
assign km_o = km;
238 5 robfinch
 
239 35 robfinch
`ifdef DEBUG
240 32 robfinch
reg [31:0] history_buf [127:0];
241
reg [6:0] history_ndx;
242 30 robfinch
reg hist_capture;
243 35 robfinch
`endif
244 30 robfinch
 
245 32 robfinch
reg isBusErr;
246 30 robfinch
reg isBrk,isMove,isSts;
247
reg isRTI,isRTL,isRTS;
248
reg isOrb,isStb;
249
reg isRMW;
250
reg isSub,isSub8;
251 32 robfinch
reg isJsrIndx,isJsrInd;
252
reg ldMuldiv;
253
reg isPusha,isPopa;
254 30 robfinch
 
255 32 robfinch
wire isCmp = ir9==`CPX_ZPX || ir9==`CPX_ABS || ir9==`CPX_IMM32 ||
256
                         ir9==`CPY_ZPX || ir9==`CPY_ABS || ir9==`CPY_IMM32;
257 5 robfinch
wire isRMW32 =
258 32 robfinch
                         ir9==`ASL_ZPX || ir9==`ROL_ZPX || ir9==`LSR_ZPX || ir9==`ROR_ZPX || ir9==`INC_ZPX || ir9==`DEC_ZPX ||
259
                         ir9==`ASL_ABS || ir9==`ROL_ABS || ir9==`LSR_ABS || ir9==`ROR_ABS || ir9==`INC_ABS || ir9==`DEC_ABS ||
260
                         ir9==`ASL_ABSX || ir9==`ROL_ABSX || ir9==`LSR_ABSX || ir9==`ROR_ABSX || ir9==`INC_ABSX || ir9==`DEC_ABSX ||
261
                         ir9==`TRB_ZP || ir9==`TRB_ZPX || ir9==`TRB_ABS || ir9==`TSB_ZP || ir9==`TSB_ZPX || ir9==`TSB_ABS ||
262
                         ir9==`BMS_ZPX || ir9==`BMS_ABS || ir9==`BMS_ABSX ||
263
                         ir9==`BMC_ZPX || ir9==`BMC_ABS || ir9==`BMC_ABSX ||
264
                         ir9==`BMF_ZPX || ir9==`BMF_ABS || ir9==`BMF_ABSX
265 5 robfinch
                         ;
266
wire isRMW8 =
267 32 robfinch
                         ir9==`ASL_ZP || ir9==`ROL_ZP || ir9==`LSR_ZP || ir9==`ROR_ZP || ir9==`INC_ZP || ir9==`DEC_ZP ||
268
                         ir9==`ASL_ZPX || ir9==`ROL_ZPX || ir9==`LSR_ZPX || ir9==`ROR_ZPX || ir9==`INC_ZPX || ir9==`DEC_ZPX ||
269
                         ir9==`ASL_ABS || ir9==`ROL_ABS || ir9==`LSR_ABS || ir9==`ROR_ABS || ir9==`INC_ABS || ir9==`DEC_ABS ||
270
                         ir9==`ASL_ABSX || ir9==`ROL_ABSX || ir9==`LSR_ABSX || ir9==`ROR_ABSX || ir9==`INC_ABSX || ir9==`DEC_ABSX ||
271
                         ir9==`TRB_ZP || ir9==`TRB_ZPX || ir9==`TRB_ABS || ir9==`TSB_ZP || ir9==`TSB_ZPX || ir9==`TSB_ABS;
272 5 robfinch
                         ;
273 30 robfinch
 
274
// Registerable decodes
275
// The following decodes can be registered because they aren't needed until at least the cycle after
276
// the DECODE stage.
277
 
278
always @(posedge clk)
279 32 robfinch
        if (state==DECODE||state==BYTE_DECODE) begin
280
                isSub <= ir9==`SUB_ZPX || ir9==`SUB_IX || ir9==`SUB_IY ||
281
                         ir9==`SUB_ABS || ir9==`SUB_ABSX || ir9==`SUB_IMM8 || ir9==`SUB_IMM16 || ir9==`SUB_IMM32;
282
                isSub8 <= ir9==`SBC_ZP || ir9==`SBC_ZPX || ir9==`SBC_IX || ir9==`SBC_IY || ir9==`SBC_I ||
283
                         ir9==`SBC_ABS || ir9==`SBC_ABSX || ir9==`SBC_ABSY || ir9==`SBC_IMM;
284 30 robfinch
                isRMW <= em ? isRMW8 : isRMW32;
285 32 robfinch
                isOrb <= ir9==`ORB_ZPX || ir9==`ORB_IX || ir9==`ORB_IY || ir9==`ORB_ABS || ir9==`ORB_ABSX;
286
                isStb <= ir9==`STB_ZPX || ir9==`STB_ABS || ir9==`STB_ABSX;
287
                isRTI <= ir9==`RTI;
288
                isRTL <= ir9==`RTL;
289
                isRTS <= ir9==`RTS;
290
                isBrk <= ir9==`BRK;
291
                isMove <= ir9==`MVP || ir9==`MVN;
292
                isSts <= ir9==`STS;
293
                isJsrIndx <= ir9==`JSR_INDX;
294
                isJsrInd <= ir9==`JSR_IND;
295 35 robfinch
                ldMuldiv <= ir9==`MUL_IMM8 || ir9==`MUL_IMM16 || ir9==`MUL_IMM32 ||
296
                        ir9==`DIV_IMM8 || ir9==`MOD_IMM8 || ir9==`DIV_IMM16 || ir9==`DIV_IMM32 || ir9==`MOD_IMM16 || ir9==`MOD_IMM32 ||
297
                        (ir9==`RR && (
298 32 robfinch
                        ir[23:20]==`MUL_RR || ir[23:20]==`MULS_RR || ir[23:20]==`DIV_RR || ir[23:20]==`DIVS_RR || ir[23:20]==`MOD_RR || ir[23:20]==`MODS_RR));
299
                isPusha <= ir9==`PUSHA;
300
                isPopa <= ir9==`POPA;
301 30 robfinch
        end
302 32 robfinch
        else
303
                ldMuldiv <= 1'b0;
304 30 robfinch
 
305
`ifdef SUPPORT_EXEC
306 32 robfinch
wire isExec = ir9==`EXEC;
307
wire isAtni = ir9==`ATNI;
308 30 robfinch
`else
309
wire isExec = 1'b0;
310
wire isAtni = 1'b0;
311
`endif
312 12 robfinch
wire md_done;
313
wire clk;
314 21 robfinch
reg isIY;
315 12 robfinch
 
316 30 robfinch
rtf65002_pcinc upci1
317
(
318 32 robfinch
        .opcode(ir9),
319 30 robfinch
        .suppress_pcinc(suppress_pcinc),
320
        .inc(pc_inc)
321
);
322
 
323 32 robfinch
rtf65002_pcinc8 upci2
324
(
325
        .opcode(ir[7:0]),
326
        .suppress_pcinc(suppress_pcinc),
327
        .inc(pc_inc8)
328
);
329 35 robfinch
 
330 12 robfinch
mult_div umd1
331
(
332 30 robfinch
        .rst(rst_i),
333 12 robfinch
        .clk(clk),
334 32 robfinch
        .ld(ldMuldiv),
335
        .op(ir9),
336
        .fn(ir[23:20]),
337
        .a(a),
338
        .b(b),
339 12 robfinch
        .p(prod),
340
        .q(q),
341
        .r(r),
342
        .done(md_done)
343
);
344 30 robfinch
 
345 32 robfinch
`ifdef SUPPORT_ICACHE
346
`ifdef ICACHE_2WAY
347
rtf65002_icachemem2way icm0 (
348
        .whichrd(whichrd),
349
        .whichwr(whichwr),
350
        .wclk(clk),
351
        .wr(ack_i & isInsnCacheLoad),
352
        .adr(adr_o),
353
        .dat(dat_i),
354
        .rclk(~clk),
355
        .pc(pc),
356
        .insn(insn)
357
);
358
 
359
rtf65002_itagmem2way tgm0 (
360
        .whichrd(whichrd),
361
        .whichwr(isCacheReset ? adr_o[13]: whichwr),
362
        .wclk(clk),
363
        .wr((ack_i & isInsnCacheLoad)|isCacheReset),
364
        .adr({adr_o[31:1],!isCacheReset}),
365
        .rclk(~clk),
366
        .pc(pc),
367
        .hit0(hit0),
368
        .hit1(hit1)
369
);
370
`else
371
`ifdef ICACHE_4K
372
rtf65002_icachemem4k icm0 (
373
        .wclk(clk),
374
        .wr(ack_i & isInsnCacheLoad),
375
        .adr(adr_o),
376
        .dat(dat_i),
377
        .rclk(~clk),
378
        .pc(pc),
379
        .insn(insn)
380
);
381
 
382
rtf65002_itagmem4k tgm0 (
383
        .wclk(clk),
384
        .wr((ack_i & isInsnCacheLoad)|isCacheReset),
385 35 robfinch
        .adr({adr_o[33:1],!isCacheReset}),
386 32 robfinch
        .rclk(~clk),
387
        .pc(pc),
388
        .hit0(hit0),
389
        .hit1(hit1)
390
);
391
`endif
392
`ifdef ICACHE_8K
393
rtf65002_icachemem8k icm0 (
394
        .wclk(clk),
395
        .wr(ack_i & isInsnCacheLoad),
396
        .adr(adr_o),
397
        .dat(dat_i),
398
        .rclk(~clk),
399
        .pc(pc),
400
        .insn(insn)
401
);
402
 
403
rtf65002_itagmem8k tgm0 (
404
        .wclk(clk),
405
        .wr((ack_i & isInsnCacheLoad)|isCacheReset),
406 35 robfinch
        .adr({adr_o[33:1],!isCacheReset}),
407 32 robfinch
        .rclk(~clk),
408
        .pc(pc),
409
        .hit0(hit0),
410
        .hit1(hit1)
411
);
412
`endif
413
`ifdef ICACHE_16K
414 30 robfinch
rtf65002_icachemem icm0 (
415 12 robfinch
        .wclk(clk),
416 5 robfinch
        .wr(ack_i & isInsnCacheLoad),
417
        .adr(adr_o),
418
        .dat(dat_i),
419 30 robfinch
        .rclk(~clk),
420 5 robfinch
        .pc(pc),
421
        .insn(insn)
422
);
423
 
424 30 robfinch
rtf65002_itagmem tgm0 (
425 12 robfinch
        .wclk(clk),
426 10 robfinch
        .wr((ack_i & isInsnCacheLoad)|isCacheReset),
427
        .adr({adr_o[31:1],!isCacheReset}),
428 30 robfinch
        .rclk(~clk),
429 5 robfinch
        .pc(pc),
430
        .hit0(hit0),
431
        .hit1(hit1)
432
);
433 32 robfinch
`endif
434
`endif  // ICACHE_2WAY
435 5 robfinch
 
436
wire ihit = (hit0 & hit1);//(pc[2:0] > 3'd1 ? hit1 : 1'b1));
437 30 robfinch
`else
438
wire ihit = 1'b0;
439
`endif
440 5 robfinch
 
441 30 robfinch
`ifdef SUPPORT_DCACHE
442 32 robfinch
assign wr = state==STORE2 && dhit && ack_i;
443
 
444 30 robfinch
rtf65002_dcachemem dcm0 (
445 12 robfinch
        .wclk(clk),
446 5 robfinch
        .wr(wr | (ack_i & isDataCacheLoad)),
447 32 robfinch
        .sel(sel_o),
448
        .wadr(adr_o[33:2]),
449
        .wdat(wr ? dat_o : dat_i),
450 30 robfinch
        .rclk(~clk),
451 5 robfinch
        .radr(radr),
452
        .rdat(rdat)
453
);
454
 
455 30 robfinch
rtf65002_dtagmem dtm0 (
456 12 robfinch
        .wclk(clk),
457 32 robfinch
        .wr(wr | (ack_i & isDataCacheLoad) | isCacheReset),
458
        .wadr(adr_o[33:2]),
459
        .cr(!isCacheReset),
460 30 robfinch
        .rclk(~clk),
461 5 robfinch
        .radr(radr),
462
        .hit(dhit)
463
);
464 30 robfinch
`endif
465 5 robfinch
 
466
overflow uovr1 (
467
        .op(isSub),
468
        .a(a[31]),
469
        .b(b[31]),
470
        .s(res[31]),
471
        .v(resv32)
472
);
473
 
474
overflow uovr2 (
475
        .op(isSub8),
476
        .a(acc8[7]),
477
        .b(b8[7]),
478
        .s(res8[7]),
479
        .v(resv8)
480
);
481
 
482
wire [7:0] bcaio;
483
wire [7:0] bcao;
484
wire [7:0] bcsio;
485
wire [7:0] bcso;
486
wire bcaico,bcaco,bcsico,bcsco;
487
 
488 30 robfinch
`ifdef SUPPORT_BCD
489 5 robfinch
BCDAdd ubcdai1 (.ci(cf),.a(acc8),.b(ir[15:8]),.o(bcaio),.c(bcaico));
490
BCDAdd ubcda2 (.ci(cf),.a(acc8),.b(b8),.o(bcao),.c(bcaco));
491
BCDSub ubcdsi1 (.ci(cf),.a(acc8),.b(ir[15:8]),.o(bcsio),.c(bcsico));
492
BCDSub ubcds2 (.ci(cf),.a(acc8),.b(b8),.o(bcso),.c(bcsco));
493 30 robfinch
`endif
494 5 robfinch
 
495
reg [7:0] dati;
496
always @(radr2LSB or dat_i)
497
case(radr2LSB)
498
2'd0:   dati <= dat_i[7:0];
499
2'd1:   dati <= dat_i[15:8];
500
2'd2:   dati <= dat_i[23:16];
501
2'd3:   dati <= dat_i[31:24];
502
endcase
503 35 robfinch
`ifdef SUPPORT_DCACHE
504 5 robfinch
reg [7:0] rdat8;
505
always @(radr2LSB or rdat)
506
case(radr2LSB)
507
2'd0:   rdat8 <= rdat[7:0];
508
2'd1:   rdat8 <= rdat[15:8];
509
2'd2:   rdat8 <= rdat[23:16];
510
2'd3:   rdat8 <= rdat[31:24];
511
endcase
512 35 robfinch
`endif
513 5 robfinch
 
514 32 robfinch
// Evaluate branches
515
// 
516 5 robfinch
reg takb;
517 32 robfinch
always @(ir9 or cf or vf or nf or zf)
518
case(ir9)
519 5 robfinch
`BEQ:   takb <= zf;
520
`BNE:   takb <= !zf;
521
`BPL:   takb <= !nf;
522
`BMI:   takb <= nf;
523
`BCS:   takb <= cf;
524
`BCC:   takb <= !cf;
525
`BVS:   takb <= vf;
526
`BVC:   takb <= !vf;
527
`BRA:   takb <= 1'b1;
528
`BRL:   takb <= 1'b1;
529 30 robfinch
`BHI:   takb <= cf & !zf;
530
`BLS:   takb <= !cf | zf;
531
`BGE:   takb <= (nf & vf)|(!nf & !vf);
532
`BLT:   takb <= (nf & !vf)|(!nf & vf);
533
`BGT:   takb <= (nf & vf & !zf) + (!nf & !vf & !zf);
534
`BLE:   takb <= zf | (nf & !vf)|(!nf & vf);
535 5 robfinch
default:        takb <= 1'b0;
536
endcase
537
 
538 32 robfinch
wire [31:0] iapy8                        = ia + y8;      // Don't add in abs8, already included with ia
539
wire [31:0] zp_address           = {abs8[31:16],8'h00,ir[15:8]};
540
wire [31:0] zpx_address  = {abs8[31:16],8'h00,ir[15:8]} + x8;
541
wire [31:0] zpy_address          = {abs8[31:16],8'h00,ir[15:8]} + y8;
542
wire [31:0] abs_address  = {abs8[31:16],ir[23:8]};
543
wire [31:0] absx_address         = {abs8[31:16],ir[23:8] + {8'h0,x8}};   // simulates 64k bank wrap-around
544
wire [31:0] absy_address         = {abs8[31:16],ir[23:8] + {8'h0,y8}};
545 30 robfinch
wire [31:0] zpx32xy_address      = ir[23:12] + rfoa;
546
wire [31:0] absx32xy_address     = ir[47:16] + rfob;
547
wire [31:0] zpx32_address                = ir[31:20] + rfob;
548
wire [31:0] absx32_address               = ir[55:24] + rfob;
549 5 robfinch
 
550 32 robfinch
rtf65002_alu ualu1
551
(
552
        .clk(clk),
553
        .state(state),
554
        .resin(res),
555
        .pg2(pg2),
556
        .ir(ir),
557
        .acc(acc),
558
        .x(x),
559
        .y(y),
560
        .isp(isp),
561
        .rfoa(rfoa),
562
        .rfob(rfob),
563
        .a(a),
564
        .b(b),
565
        .b8(b8),
566
        .Rt(Rt),
567
        .icacheOn(icacheOn),
568
        .dcacheOn(dcacheOn),
569
        .write_allocate(write_allocate),
570
        .prod(prod),
571
        .tick(tick),
572
        .lfsr(lfsr),
573
        .abs8(abs8),
574
        .vbr(vbr),
575
        .nmoi(nmoi),
576
        .derr_address(derr_address),
577
        .history_buf(history_buf[history_ndx]),
578
        .spage(spage),
579
        .sp(sp),
580
        .df(df),
581
        .cf(cf),
582
        .res(alu_out)
583
);
584 30 robfinch
 
585
 
586 5 robfinch
//-----------------------------------------------------------------------------
587
// Clock control
588
// - reset or NMI reenables the clock
589
// - this circuit must be under the clk_i domain
590
//-----------------------------------------------------------------------------
591
//
592
reg cpu_clk_en;
593
reg clk_en;
594
BUFGCE u20 (.CE(cpu_clk_en), .I(clk_i), .O(clk) );
595
 
596
always @(posedge clk_i)
597
if (rst_i) begin
598
        cpu_clk_en <= 1'b1;
599
        nmi1 <= 1'b0;
600
end
601
else begin
602
        nmi1 <= nmi_i;
603
        if (nmi_i)
604
                cpu_clk_en <= 1'b1;
605
        else
606
                cpu_clk_en <= clk_en;
607
end
608
 
609
always @(posedge clk)
610
if (rst_i) begin
611
        bte_o <= 2'b00;
612
        cti_o <= 3'b000;
613
        bl_o <= 6'd0;
614
        cyc_o <= 1'b0;
615
        stb_o <= 1'b0;
616
        we_o <= 1'b0;
617
        sel_o <= 4'h0;
618
        adr_o <= 34'd0;
619
        dat_o <= 32'd0;
620
        nmi_edge <= 1'b0;
621
        wai <= 1'b0;
622
        cf <= 1'b0;
623 30 robfinch
        ir <= 64'hEAEAEAEAEAEAEAEA;
624 5 robfinch
        imiss <= `FALSE;
625
        dmiss <= `FALSE;
626
        dcacheOn <= 1'b0;
627
        icacheOn <= 1'b1;
628 10 robfinch
        write_allocate <= 1'b0;
629 5 robfinch
        nmoi <= 1'b1;
630 10 robfinch
        state <= RESET1;
631 21 robfinch
        if (rst_md) begin
632
                pc <= 32'h0000FFF0;             // set high-order pc to zero
633
                vect <= `BYTE_RST_VECT;
634
                em <= 1'b1;
635
        end
636
        else begin
637
                vect <= `RST_VECT;
638
                em <= 1'b0;
639
                pc <= 32'hFFFFFFF0;
640
        end
641 25 robfinch
        suppress_pcinc <= 4'hF;
642
        exbuf <= 64'd0;
643 13 robfinch
        spage <= 32'h00000100;
644 5 robfinch
        bufadr <= 32'd0;
645 13 robfinch
        abs8 <= 32'd0;
646 5 robfinch
        clk_en <= 1'b1;
647 10 robfinch
        isCacheReset <= `TRUE;
648
        gie <= 1'b0;
649 12 robfinch
        tick <= 32'd0;
650 21 robfinch
        isIY <= 1'b0;
651 30 robfinch
        load_what <= `NOTHING;
652 35 robfinch
`ifdef DEBUG
653 30 robfinch
        hist_capture <= `TRUE;
654
        history_ndx <= 6'd0;
655 35 robfinch
`endif
656 32 robfinch
        pg2 <= `FALSE;
657
        tf <= `FALSE;
658
        km <= `TRUE;
659 36 robfinch
        wrrf <= 1'b0;
660 5 robfinch
end
661
else begin
662 36 robfinch
wrrf <= 1'b0;
663 12 robfinch
tick <= tick + 32'd1;
664 35 robfinch
ilfsr <= {ilfsr,ilfsr_fb};
665 5 robfinch
if (nmi_i & !nmi1)
666
        nmi_edge <= 1'b1;
667
if (nmi_i|nmi1)
668
        clk_en <= 1'b1;
669
case(state)
670 32 robfinch
// Loop in this state until all the cache address tage have been flagged as
671
// invalid.
672
//
673 10 robfinch
RESET1:
674 5 robfinch
        begin
675 10 robfinch
                adr_o <= adr_o + 32'd4;
676
                if (adr_o[13:4]==10'h3FF) begin
677
                        state <= RESET2;
678
                        isCacheReset <= `FALSE;
679
                end
680
        end
681
RESET2:
682
        begin
683 5 robfinch
                radr <= vect[31:2];
684 21 robfinch
                radr2LSB <= vect[1:0];
685
                load_what <= em ? `PC_70 : `PC_310;
686
                state <= LOAD_MAC1;
687 5 robfinch
        end
688
 
689 20 robfinch
`include "ifetch.v"
690 30 robfinch
`ifdef SUPPORT_EM8
691 32 robfinch
`include "byte_ifetch.v"
692 20 robfinch
`include "byte_decode.v"
693 30 robfinch
`include "byte_calc.v"
694
`endif
695 10 robfinch
 
696 21 robfinch
`include "load_mac.v"
697 20 robfinch
`include "store.v"
698 10 robfinch
 
699 32 robfinch
// This state waits for a data hit before continuing. It's used after a store 
700
// operation when write allocation is taking place.
701 10 robfinch
WAIT_DHIT:
702
        if (dhit)
703
                state <= retstate;
704 5 robfinch
 
705 32 robfinch
DECODE: decode_tsk();
706
CALC:   calc_tsk();
707 5 robfinch
 
708 32 robfinch
MULDIV1:        state <= MULDIV2;
709
MULDIV2:
710
        if (md_done) begin
711 10 robfinch
                state <= IFETCH;
712 32 robfinch
                case(ir9)
713
                `RR:
714
                        case(ir[23:20])
715
                        `MUL_RR:        begin res <= prod[31:0]; end
716
                        `MULS_RR:       begin res <= prod[31:0]; end
717
`ifdef SUPPORT_DIVMOD
718
                        `DIV_RR:        begin res <= q; end
719
                        `DIVS_RR:       begin res <= q; end
720
                        `MOD_RR:        begin res <= r; end
721
                        `MODS_RR:       begin res <= r; end
722 30 robfinch
`endif
723 32 robfinch
                        endcase
724
                `MUL_IMM8,`MUL_IMM16,`MUL_IMM32:        res <= prod[31:0];
725
`ifdef SUPPORT_DIVMOD
726
                `DIV_IMM8,`DIV_IMM16,`DIV_IMM32:        res <= q;
727
                `MOD_IMM8,`MOD_IMM16,`MOD_IMM32:        res <= r;
728 30 robfinch
`endif
729 12 robfinch
                endcase
730
        end
731
 
732 30 robfinch
`ifdef SUPPORT_BERR
733 21 robfinch
BUS_ERROR:
734
        begin
735 32 robfinch
                pg2 <= `FALSE;
736
                ir <= {8{`BRK}};
737 35 robfinch
`ifdef DEBUG
738 32 robfinch
                hist_capture <= `FALSE;
739 35 robfinch
`endif
740 21 robfinch
                radr <= isp_dec;
741
                wadr <= isp_dec;
742 32 robfinch
                isp <= isp_dec;
743
                store_what <= `STW_OPC;
744 35 robfinch
                vect <= {vbr[31:9],intno,2'b00};
745 25 robfinch
                hwi <= `TRUE;
746 32 robfinch
                isBusErr <= `TRUE;
747
                state <= STORE1;
748 21 robfinch
        end
749 30 robfinch
`endif
750
 
751 32 robfinch
`include "rtf65002_string.v"
752 5 robfinch
`include "cache_controller.v"
753
 
754 32 robfinch
endcase
755 36 robfinch
 
756
if (wrrf || state==IFETCH || state==LOAD_MAC3) begin
757
        regfile[Rt] <= res[31:0];
758
        case(Rt)
759
        4'h1:   acc <= res[31:0];
760
        4'h2:   x <= res[31:0];
761
        4'h3:   y <= res[31:0];
762
        default:        ;
763
        endcase
764 5 robfinch
end
765 36 robfinch
 
766
end
767
 
768
 
769 32 robfinch
`include "decode.v"
770
`include "calc.v"
771
`include "load_tsk.v"
772 35 robfinch
`include "wb_task.v"
773 32 robfinch
 
774 35 robfinch
task next_state;
775
input [5:0] nxt;
776
begin
777
        state <= nxt;
778
end
779
endtask
780
 
781 36 robfinch
function [127:0] fnStateName;
782
input [5:0] state;
783
case(state)
784
RESET1: fnStateName = "RESET1     ";
785
RESET2: fnStateName = "RESET2     ";
786
IFETCH: fnStateName = "IFETCH     ";
787
DECODE: fnStateName = "DECODE     ";
788
STORE1: fnStateName = "STORE1     ";
789
STORE2: fnStateName = "STORE2     ";
790
CALC:   fnStateName = "CALC       ";
791
RTS1:   fnStateName = "RTS1       ";
792
IY3:    fnStateName = "IY3        ";
793
BYTE_IX5:       fnStateName = "BYTE_IX5   ";
794
BYTE_IY5:       fnStateName = "BYTE_IY5   ";
795
WAIT_DHIT:      fnStateName = "WAIT_DHIT  ";
796
MULDIV1:        fnStateName = "MULDIV1    ";
797
MULDIV2:        fnStateName = "MULDIV2    ";
798
BYTE_DECODE:    fnStateName = "BYTE_DECODE";
799
BYTE_CALC:      fnStateName = "BYTE_CALC  ";
800
BUS_ERROR:      fnStateName = "BUS_ERROR  ";
801
LOAD_MAC1:      fnStateName = "LOAD_MAC1  ";
802
LOAD_MAC2:      fnStateName = "LOAD_MAC2  ";
803
LOAD_MAC3:      fnStateName = "LOAD_MAC3  ";
804
MVN3:           fnStateName = "MVN3       ";
805
PUSHA1:         fnStateName = "PUSHA1     ";
806
POPA1:          fnStateName = "POPA1      ";
807
BYTE_IFETCH:    fnStateName = "BYTE_IFETCH";
808
LOAD_DCACHE:    fnStateName = "LOAD_DCACHE";
809
LOAD_ICACHE:    fnStateName = "LOAD_ICACHE";
810
LOAD_IBUF1:             fnStateName = "LOAD_IBUF1 ";
811
LOAD_IBUF2:             fnStateName = "LOAD_IBUF2 ";
812
LOAD_IBUF3:             fnStateName = "LOAD_IBUF3 ";
813
ICACHE1:                fnStateName = "ICACHE1    ";
814
IBUF1:                  fnStateName = "IBUF1      ";
815
DCACHE1:                fnStateName = "DCACHE1    ";
816
CMPS1:                  fnStateName = "CMPS1      ";
817
default:                fnStateName = "UNKNOWN    ";
818
endcase
819
endfunction
820
 
821 5 robfinch
endmodule

powered by: WebSVN 2.1.0

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