URL
https://opencores.org/ocsvn/m32632/m32632/trunk
Subversion Repositories m32632
Compare Revisions
- This comparison shows the changes necessary to convert path
/
- from Rev 10 to Rev 11
- ↔ Reverse comparison
Rev 10 → Rev 11
/m32632/trunk/rtl/ICACHE_SM.v
36,14 → 36,14
// 1. KOLDETECT Collision Detection Unit |
// 2. ICACHE_SM Instruction Cache State Machine |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// |
// 1. KOLDETECT Collision Detection Unit |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module KOLDETECT ( BCLK, BRESET, DRAM_WR, CVALID, ADDR, TAG0, TAG1 , CFG , C_VALID, READ_I, ACC_OK, |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module KOLDETECT ( BCLK, BRESET, DRAM_WR, CVALID, ADDR, TAG0, TAG1 , CFG , C_VALID, READ_I, ACC_OK, HOLD, KDET, INVAL_A, ENA_HK, |
NEWCVAL, KOLLISION, STOP_ICRD, RUN_ICRD, KILL, KILLADR, ICTODC, STOP_CINV ); |
|
input BCLK; |
96,7 → 96,7
wire free,ende; |
wire init_b; |
|
always @(posedge BCLK) do_koll <= DRAM_WR & CFG[0]; // one cycle pulse, without Cache Enable no col |
always @(posedge BCLK) do_koll <= DRAM_WR & CFG[0]; // one cycle pulse, without Cache Enable no collision |
always @(posedge BCLK) addr_r <= ADDR; |
|
// similar logic like in CA_MATCH |
158,7 → 158,7
|
// Control |
|
assign last_match = counter[2] & (fifo_c == {addr_r[11:4],found_1}); // if Match with last Entry no |
assign last_match = counter[2] & (fifo_c == {addr_r[11:4],found_1}); // if Match with last Entry no new Entry |
|
assign wr_entry = kolli & ~last_match; |
|
168,7 → 168,7
6'b1_00_xxx : counter <= counter; |
6'b1_11_xxx : counter <= counter; |
6'b1_10_000 : counter <= 3'b100; |
6'b1_10_1xx : counter <= (counter[1:0] == 2'b11) ? 3'b111 : {counter[2],(counter[1:0] + 2'b01)}; |
6'b1_10_1xx : counter <= (counter[1:0] == 2'b11) ? 3'b111 : {counter[2],(counter[1:0] + 2'b01)}; // Overflow avoid |
6'b1_01_1xx : counter <= (counter[1:0] == 2'b00) ? 3'b000 : {counter[2],(counter[1:0] + 2'b11)}; |
default : counter <= counter; |
endcase |
210,7 → 210,7
|
assign RUN_ICRD = ~(STOP_ICRD | pipe); // Release for IC_READ |
|
always @(posedge BCLK) do_kill <= STOP_ICRD & ~dma_mode & ~do_kill; // Write pulse in Cache Valid R |
always @(posedge BCLK) do_kill <= STOP_ICRD & ~dma_mode & ~do_kill; // Write pulse in Cache Valid RAM, 1 cycle on, 1 cycle off |
|
assign KILL = do_kill | (KDET & dma_kolli); |
|
243,11 → 243,11
|
endmodule |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// |
// 2. ICACHE_SM Instruction Cache State Machine |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module ICACHE_SM ( BCLK, BRESET, IO_SPACE, MDONE, IO_READY, MMU_HIT, CA_HIT, READ, PTE_ACC, |
USE_CA, PTB_WR, PTB_SEL, USER, PROT_ERROR, |
DRAM_ACC, IO_RD, IO_ACC, IC_PREQ, ACC_OK, HIT_ALL, CUPDATE, AUX_DAT, NEW_PTB, PTB_ONE ); |
328,7 → 328,7
|
always @(posedge BCLK) rd_rdy <= card_flag & MDONE; |
|
// The cache RAM can not provide fast enough the data after an Update. In this case a secondary dat |
// The cache RAM can not provide fast enough the data after an Update. In this case a secondary data path is activated |
assign AUX_DAT = rd_rdy; |
|
// DRAM Interface : |
343,9 → 343,9
if (IO_ACC) IO_RD <= READ; else IO_RD <= IO_RD & ~IO_READY & BRESET; |
end |
|
assign io_busy = IO_RD | rd_done; // access is gone in next clock cycle, therefore blocked with "rd |
assign io_busy = IO_RD | rd_done; // access is gone in next clock cycle, therefore blocked with "rd_done" |
|
always @(posedge BCLK) rd_done <= READ & IO_READY; // For READ one clock later for data to come thr |
always @(posedge BCLK) rd_done <= READ & IO_READY; // For READ one clock later for data to come through |
|
// global feedback to opcode fetch unit : you can continue |
|
/m32632/trunk/rtl/ICACHE.v
35,10 → 35,10
// Modules contained in this file: |
// ICACHE the instruction cache of M32632 |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
|
module ICACHE( BCLK, MCLK, MDONE, BRESET, READ_I, IO_READY, PSR_USER, DATA_HOLD, PTB_WR, PTB_SEL, DR |
KDET, HOLD, CFG, DRAM_Q, CINVAL, IC_SIGS, IO_Q, IVAR, KOLLI_A, MCR_FLAGS, MMU_DIN, VADR, WADDR |
module ICACHE( BCLK, MCLK, MDONE, BRESET, READ_I, IO_READY, PSR_USER, DATA_HOLD, PTB_WR, PTB_SEL, DRAM_WR, |
KDET, HOLD, CFG, DRAM_Q, CINVAL, IC_SIGS, IO_Q, IVAR, KOLLI_A, MCR_FLAGS, MMU_DIN, VADR, WADDR, |
WCTRL, IO_RD, DRAM_ACC, INIT_RUN, PROT_ERROR, ACC_OK, IC_PREQ, KOLLISION, ENA_HK, STOP_CINV, |
DRAM_A, IC_DQ, IC_VA, ICTODC, IO_A, ENDRAM ); |
|
/m32632/trunk/rtl/example_mods.v
41,13 → 41,13
// 6. ex_copro Coprocessor |
// 7. ex_dram_emul DRAM Emulator |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// |
// 1. ex_io_bus_ctrl Input/Output Bus controller |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module ex_io_bus_ctrl( CLK, RESET_N, RST_N, IO_WR, IO_RD, IO_A, IO_BE, IO_Q, IO_READY, |
W_OUT_REG, IN_DAT, BOOT_DAT, STAT_DAT, ENDRAM ); |
|
100,11 → 100,11
|
endmodule |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// |
// 2. ex_in_reg Input Register |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module ex_in_reg( CLK, IN_REG, IN_DAT); |
|
parameter in_width = 7; |
124,11 → 124,11
|
endmodule |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// |
// 3. ex_out_reg Output Register |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module ex_out_reg( CLK, W_OUT_REG, DIN, OUT_REG); |
|
parameter out_width = 7; |
143,11 → 143,11
|
endmodule |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// |
// 4. ex_boot_rom Boot ROM |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module ex_boot_rom( CLK, ADDR, DATA); |
|
input CLK; |
166,11 → 166,11
|
endmodule |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// |
// 5. ex_statcou Statistic Counters |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module ex_statcou( CLK, RST_N, STATSIGS, ADDR, DATA); |
|
input CLK; |
193,11 → 193,11
|
endmodule |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// |
// 6. ex_copro Coprocessor |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module ex_copro( CLK, COP_GO, COP_OP, COP_INP, COP_DONE, COP_OUTP); |
|
input CLK; |
210,17 → 210,17
|
always @(posedge CLK) |
COP_OUTP <= COP_OP[8] ? {COP_INP[71:64],COP_INP[79:72],COP_INP[87:80],COP_INP[95:88],32'd0} |
: {COP_INP[7:0],COP_INP[15:8],COP_INP[23:16],COP_INP[31:24],COP_INP[71:64],COP_INP[79:72],COP_I |
: {COP_INP[7:0],COP_INP[15:8],COP_INP[23:16],COP_INP[31:24],COP_INP[71:64],COP_INP[79:72],COP_INP[87:80],COP_INP[95:88]}; |
|
always @(posedge CLK) COP_DONE <= COP_GO; |
|
endmodule |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// |
// 7. ex_dram_emul DRAM Emulator |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module ex_dram_emul ( MCLK, RST_N, IC_ACC, IDRAM_ADR, DC_ACC, DC_WR, DRAM_ADR, DRAM_DI, |
IC_MDONE, DC_MDONE, ENWR, WAMUX, WADDR, MEM_Q, IWCTRL, DWCTRL ); |
|
292,7 → 292,7
assign din_2 = fifo_q[34] ? fifo_q[23:16] : MEM_Q[23:16]; |
assign din_3 = fifo_q[35] ? fifo_q[31:24] : MEM_Q[31:24]; |
|
always @(posedge MCLK) if (write) EDRAM[raddr] <= {din_3,din_2,din_1,din_0}; // WRITE on rising edg |
always @(posedge MCLK) if (write) EDRAM[raddr] <= {din_3,din_2,din_1,din_0}; // WRITE on rising edge |
|
// +++++++++++++++++++++++++ Controllogic +++++++++++++++++++ |
|
330,7 → 330,7
else |
if (state[1]) nibble <= {nibble[1],~nibble[0]}; |
|
assign raddr = write ? fifo_q[addr_msb+34:36] : (start ? (DC_ACC ? DRAM_ADR[addr_msb:2] : IDRAM_ADR |
assign raddr = write ? fifo_q[addr_msb+34:36] : (start ? (DC_ACC ? DRAM_ADR[addr_msb:2] : IDRAM_ADR[addr_msb:2]) : {addr,nibble}); |
|
always @(negedge MCLK) lsb <= raddr[3:2]; |
|
/m32632/trunk/rtl/DP_FPU.v
44,13 → 44,13
// 9. DP_LOGIK Control logic and result path for different functions |
// 10. DP_FPU Top level of long operations datapath |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// |
// 1. PREPDATA Prepare data for the big multiplier |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module PREPDATA ( START, MEI, DFLOAT, BWD, SRC1, SRC2, |
MSD_1, MSD_2, LSD_1, LSD_2, LOAD_MSD, LOAD_LSD1, LOAD_LSD2 ); |
|
88,11 → 88,11
|
endmodule |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// |
// 2. BCDADDER 4 bit BCD adder |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module BCDADDER ( A_IN, B_IN, CY_IN, SUBP, OUT, CY_OUT ); |
|
input [3:0] A_IN,B_IN; |
116,12 → 116,12
|
endmodule |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// |
// 3. DFPU_BCD Binary coded decimal (BCD) adder and subtractor |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module DFPU_BCD ( BCLK, BRESET, START, DO_BCD, BWD, SRC1, SRC2, CY_IN, SUBP, BCD_Q, CY_OUT, BCD_DONE |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module DFPU_BCD ( BCLK, BRESET, START, DO_BCD, BWD, SRC1, SRC2, CY_IN, SUBP, BCD_Q, CY_OUT, BCD_DONE ); |
|
// Byte : 3 cycles in shortest case REG-REG, Word : 4 cycles and Double : 6 cycles |
input BCLK; |
182,12 → 182,12
|
endmodule |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// |
// 4. DFPU_ADDSUB Double precision floating point adder and subtractor |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module DFPU_ADDSUB ( BCLK, START, SRC1, SRC2, MAN1, MAN2, SRCFLAGS, BWD, SELECT, OUT, IOUT, CMPRES ) |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module DFPU_ADDSUB ( BCLK, START, SRC1, SRC2, MAN1, MAN2, SRCFLAGS, BWD, SELECT, OUT, IOUT, CMPRES ); |
|
input BCLK; |
input [1:0] START; |
226,11 → 226,11
endcase |
|
// This pipeline stage for better timing |
always @(posedge BCLK) movif <= movdat[31] ? (32'h0 - {movdat,SRC1[7:0]}) : {movdat,SRC1[7:0]}; // |
always @(posedge BCLK) movif <= movdat[31] ? (32'h0 - {movdat,SRC1[7:0]}) : {movdat,SRC1[7:0]}; // -2^31 is kept ! |
|
always @(posedge BCLK) sign_movif <= movdat[31]; |
|
// ROUNDLi/TRUNCLi/FLOORLi : 1. pipeline stage : can Opcode-Decoder deliver direct the 64 bit opera |
// ROUNDLi/TRUNCLi/FLOORLi : 1. pipeline stage : can Opcode-Decoder deliver direct the 64 bit operand ? From register "yes" |
|
reg ovflag,ovflag2; |
reg rovfl; |
238,7 → 238,7
wire [11:0] rexdiff,rexo; |
wire ganzklein; // Flag for 0 |
|
assign rexdiff = 12'h41D - {1'b0,SRC1[30:20]}; // 4..0 is the right shift value : like Single FP sa |
assign rexdiff = 12'h41D - {1'b0,SRC1[30:20]}; // 4..0 is the right shift value : like Single FP same value space |
|
// ovflag2 at the end of rounding : Check for Overflow |
always @(posedge BCLK) rovfl <= (ovflag | ovflag2) & (SELECT[1:0] == 2'b11) & ~minint; |
279,7 → 279,7
wire [52:0] muxsrc1; |
wire [32:0] lowdiff; |
|
assign nan = (SELECT[1:0] == 2'b11) ? SRCFLAGS[1] : (~SELECT[1] & (SRCFLAGS[3] | SRCFLAGS[1])); // |
assign nan = (SELECT[1:0] == 2'b11) ? SRCFLAGS[1] : (~SELECT[1] & (SRCFLAGS[3] | SRCFLAGS[1])); // used at the end |
|
assign exdiff = {1'b0,SRC2[30:20]} - {1'b0,SRC1[30:20]}; // Difference of Exponents |
assign madiff = {1'b0,SRC2[19:0]} - {1'b0,SRC1[19:0]}; // Difference of Mantissa |
333,7 → 333,7
// CMPF : 1. Pipeline Stage : first result : is stored one level higer in Reg |
|
assign CMPRES[1] = ~CMPRES[0] & (switch ? ~sign1 : sign2); // look table above |
assign CMPRES[0] = (ex_null & ma_null & (sign1 == sign2) & (lowdiff == 33'h0)) | (SRCFLAGS[2] & SRC |
assign CMPRES[0] = (ex_null & ma_null & (sign1 == sign2) & (lowdiff == 33'h0)) | (SRCFLAGS[2] & SRCFLAGS[0]); |
|
// ++++++++++++++++++++++++++++++++++ |
// ADD/SUB + ROUND/TRUNC : 2. Step : Barrelshifter to the right --> |
361,12 → 361,12
wire restbits; |
|
assign restbits = (brshiftf[23:0] != 24'h0); |
assign inex = {brshiftf[24],restbits}; // Inexact-Flag-Data transfered to multiplexer at the e |
assign inex = {brshiftf[24],restbits}; // Inexact-Flag-Data transfered to multiplexer at the end |
|
always @(SELECT or sign1 or brshiftf or restbits or inex or ganzklein) |
casex (SELECT[3:2]) |
2'b00 : car_ry = sign1 ^ (((brshiftf[25:24] == 2'b11) & ~restbits) | (inex == 2'b11)); // ROUN |
2'b1x : car_ry = sign1 ? (~ganzklein & (inex == 2'b00)) : 1'b0; // +numbers like TRUNCLi, -num |
2'b00 : car_ry = sign1 ^ (((brshiftf[25:24] == 2'b11) & ~restbits) | (inex == 2'b11)); // ROUNDLi |
2'b1x : car_ry = sign1 ? (~ganzklein & (inex == 2'b00)) : 1'b0; // +numbers like TRUNCLi, -numbers to "-infinity" round |
default : car_ry = sign1; // TRUNCLi , simple cut off |
endcase |
|
393,9 → 393,9
wire [65:0] add_q; |
|
// The central adder : the subtraction needs 3 Guard-Bits after LSB for correct rounding |
assign result = {1'b0,muxsrc2,3'b000} + (addflag ? {12'h0,brshiftf} : {12'hFFF,~brshiftf}) + {67'd0 |
assign result = {1'b0,muxsrc2,3'b000} + (addflag ? {12'h0,brshiftf} : {12'hFFF,~brshiftf}) + {67'd0,~addflag}; |
|
assign blshifti = SELECT[1] ? {movif,24'h0} : result[55:0]; // Feeding of MOViL, comes from Registe |
assign blshifti = SELECT[1] ? {movif,24'h0} : result[55:0]; // Feeding of MOViL, comes from Register |
|
assign shiftl = SELECT[1] ? 13'h041E : {1'b0,result[67:56]}; // MOViL |
|
447,11 → 447,11
|
endmodule |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// |
// 5. DFPU_MISC Double precision floating point miscellaneous operations |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module DFPU_MISC ( BCLK, START, SRC1, SRC2, SRCFLAG, MIMUX, MODE, OUT ); |
|
input BCLK; |
508,12 → 508,12
assign posi_1 = ~shift_l2[9]; |
assign shift_l = posi_1 ? {shift_l2[7:0],1'b0} : shift_l2[8:0]; // top bit is hidden "1" |
|
assign calc_exp = 5'h08 - {1'b0,posi_8,posi_4,posi_2,posi_1}; // Minimum is "F" = for exponent +/-1 |
assign calc_exp = 5'h08 - {1'b0,posi_8,posi_4,posi_2,posi_1}; // Minimum is "F" = for exponent +/-1 <=> 2^0 |
|
// exponent is set one level higher for F and L |
assign logb_exp = MODE[1] ? {{4{~calc_exp[4]}},{3{calc_exp[4]}}} : {~calc_exp[4],{6{calc_exp[4]}}}; |
|
assign logb_res = logb_null ? {70'h10_0000_0000_0000_0000} : {2'b00,~daten[62],2'b00,logb_exp,calc_ |
assign logb_res = logb_null ? {70'h10_0000_0000_0000_0000} : {2'b00,~daten[62],2'b00,logb_exp,calc_exp[3:0],shift_l,45'h0}; |
|
// ++++++++++++++++++++++++ SCALBf ++++++++++++++++++++++++++++++++++ |
|
528,15 → 528,15
|
// ++++++++++++++++++++++++ Output ++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
|
always @(posedge BCLK) OUT <= MODE[3] ? (MODE[2] ? logb_res : scalb_res) : fl_lf ; // LOGB/SCALB : |
always @(posedge BCLK) OUT <= MODE[3] ? (MODE[2] ? logb_res : scalb_res) : fl_lf ; // LOGB/SCALB : MOVLF/MOVFL |
|
endmodule |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// |
// 6. DFPU_MUL Double precision floating point multiplier |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module DFPU_MUL ( BCLK, SRC1, SRC2, START, MRESULT, SRCFLAGS, OUT ); |
|
input BCLK; |
573,11 → 573,11
|
endmodule |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// |
// 7. DIVI_PREP Prepare data for the divider |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module DIVI_PREP (SRC, BWD, NOT_DEI, EXTDATA, DOUT, MSB, NULL, MINUS); |
|
input [31:0] SRC; |
610,7 → 610,7
|
assign MINUS = double[31] & NOT_DEI; |
|
assign DOUT = ({32{MINUS}} ^ double) + {31'h0,MINUS}; // assign DOUT = MINUS ? (32'd0 - double) : d |
assign DOUT = ({32{MINUS}} ^ double) + {31'h0,MINUS}; // assign DOUT = MINUS ? (32'd0 - double) : double; |
|
// now find most significant set bit : FFS |
|
629,12 → 629,12
|
endmodule |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// |
// 8. DFPU_DIV The divider for all divide opcodes : double, single and integer |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module DFPU_DIV ( BCLK, BRST, START, SRC1, SRC2, MAN1, MAN2, SRCFLAGS, FL, BWD, OPCODE, OUT, DONE, D |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module DFPU_DIV ( BCLK, BRST, START, SRC1, SRC2, MAN1, MAN2, SRCFLAGS, FL, BWD, OPCODE, OUT, DONE, DIVI_OUT, DVZ_TRAP, DEI_OVF ); |
|
// This version needs for Double 28+1 cycles if MAN1<MAN2 otherwise 28+2. |
// For Single it needs 13+1 cyckes or 13+2. |
761,7 → 761,7
default : addoff = {valdata, 1'b0, 1'b0}; |
endcase |
|
always @(posedge BCLK) next_msb2 <= extdata & ist_null & divi_pipe1; // Special case at DEI : MSD = |
always @(posedge BCLK) next_msb2 <= extdata & ist_null & divi_pipe1; // Special case at DEI : MSD = 0 |
|
always @(posedge BCLK) |
if (divi_pipe1) msb_src2 <= {addoff[2],(addoff[1:0] | i_out[36:35]),i_out[34:32]}; |
789,7 → 789,7
assign shift_16 = shift_r[4] ? shift_8 : {shift_8[46:0],16'b0}; // Result is 63 Bit wide |
|
// 65 Bit result because of DEI |
assign shift_32 = shift_r[5] ? {1'b0,pipe_reg,ivalue} : {shift_16,2'b00}; // special case DEI : 32 |
assign shift_32 = shift_r[5] ? {1'b0,pipe_reg,ivalue} : {shift_16,2'b00}; // special case DEI : 32 times shift |
|
always @(posedge BCLK or negedge BRST) // Flag for rounding, only if DEST <>0 |
if (!BRST) divi_pipe3 <= 1'b0; |
819,16 → 819,16
case (OPCODE[1:0]) |
2'b00 : divi_result = {neg_flag,divsr[31:0]}; // QUO |
2'b01 : divi_result = {neg_src2,divreg[33:2]}; // REM |
2'b10 : divi_result = {neg_src1,((sub_case & ~rest_null) ? (save1[31:0] - divreg[33:2]) : divreg |
2'b10 : divi_result = {neg_src1,((sub_case & ~rest_null) ? (save1[31:0] - divreg[33:2]) : divreg[33:2])}; // MOD |
2'b11 : divi_result = {neg_flag,divsr[31:0]}; // DIV |
endcase |
|
always @(posedge BCLK) negativ <= divi_result[32]; |
|
assign plus_1 = (OPCODE[1:0] == 2'b11) ? (negativ & rest_null) : negativ; // Special case Rest=0 at |
assign plus_1 = (OPCODE[1:0] == 2'b11) ? (negativ & rest_null) : negativ; // Special case Rest=0 at DIV |
|
always @(posedge BCLK) |
if (divi_pipe4) DIVI_OUT[63:32] <= not_dei ? (({32{negativ}} ^ divi_result[31:0]) + {31'd0,plus_1} |
if (divi_pipe4) DIVI_OUT[63:32] <= not_dei ? (({32{negativ}} ^ divi_result[31:0]) + {31'd0,plus_1}) : dei_result; |
|
always @(posedge BCLK) if (divi_pipe4) DIVI_OUT[31:0] <= divreg[33:2]; |
|
854,7 → 854,7
assign load_src1 = START[2] | divi_pipe1; |
|
// *2 + *1 |
always @(posedge BCLK) if (load_src1) dreimal <= {1'b0,man_1,src_1,1'b0} + {2'b00,man_1,src_1}; // |
always @(posedge BCLK) if (load_src1) dreimal <= {1'b0,man_1,src_1,1'b0} + {2'b00,man_1,src_1}; // 54 Bit Reg |
|
always @(posedge BCLK) if (load_src1) save1 <= src_1; |
|
865,7 → 865,7
assign load_src2 = START[2] | divi_pipe2; |
|
always @(posedge BCLK) |
if (load_src2) divreg <= divi_pipe2 ? {23'h0,shift_32[64:32]} : ( FL ? {34'h0_0000_0001,SRC2[22:0] |
if (load_src2) divreg <= divi_pipe2 ? {23'h0,shift_32[64:32]} : ( FL ? {34'h0_0000_0001,SRC2[22:0]} : {3'b0,MAN2,SRC2,1'b0}); |
else |
begin |
casex ({sub3[56],sub2[56],sub1[56]}) |
896,7 → 896,7
// Overflow Detection for DEI : serial calculation |
always @(posedge BCLK) |
if (load_src2) DEI_OVF[0] <= 1'b0; |
else DEI_OVF[0] <= DEI_OVF[0] | (BWD[1] ? |divsr[33:32] : (BWD[0] ? |divsr[17:16] : |divsr[9:8]) |
else DEI_OVF[0] <= DEI_OVF[0] | (BWD[1] ? |divsr[33:32] : (BWD[0] ? |divsr[17:16] : |divsr[9:8])); |
|
always @(posedge BCLK) DEI_OVF[1] <= divi_pipe4; // Timing pulse for OVF inclusiv for DIV and QUO |
|
925,8 → 925,8
always @(posedge BCLK) |
if (ende && runflag) |
casex ({FL,divsr[26],divsr[56]}) |
3'b11x : OUT <= {nan,zero,sign,expoh[9:8],expoh[7],expoh[7],expoh[7],expoh[7:0],divsr[25:3],28'b |
3'b10x : OUT <= {nan,zero,sign,expol[9:8],expol[7],expol[7],expol[7],expol[7:0],divsr[24:2],28'b |
3'b11x : OUT <= {nan,zero,sign,expoh[9:8],expoh[7],expoh[7],expoh[7],expoh[7:0],divsr[25:3],28'b0,divsr[3:2],restlow}; |
3'b10x : OUT <= {nan,zero,sign,expol[9:8],expol[7],expol[7],expol[7],expol[7:0],divsr[24:2],28'b0,divsr[2:1],restlsb}; |
3'b0x1 : OUT <= {nan,zero,sign,expoh,divsr[55:3],resthigh}; |
3'b0x0 : OUT <= {nan,zero,sign,expol,divsr[54:2],restlow}; |
endcase |
933,14 → 933,14
|
endmodule |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// |
// 9. DP_LOGIK Control logic and result path for different functions |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module DP_LOGIK ( BCLK, BRESET, OPCODE, SRC1, SRC2, FSR, START, MRESULT, BWD, FL, MAN1, MAN2, WR_REG |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module DP_LOGIK ( BCLK, BRESET, OPCODE, SRC1, SRC2, FSR, START, MRESULT, BWD, FL, MAN1, MAN2, WR_REG, CY_IN, |
COP_DONE, COP_OP, COP_IN, |
DOUT, TT_DP, DP_CMP, OVF_BCD, MEI, DFLOAT, DONE, UP_DP, CLR_LSB, WREN_L, LD_OUT_L, DVZ_TRAP, C |
DOUT, TT_DP, DP_CMP, OVF_BCD, MEI, DFLOAT, DONE, UP_DP, CLR_LSB, WREN_L, LD_OUT_L, DVZ_TRAP, COP_GO ); |
|
// Definition of output word OUT of sub-moduls : the hidden-bit of the mantissa is already gone |
// |
1051,15 → 1051,15
assign go_divi = divi_ops & (OPCODE[2] ? START[1] : START[0]); // DEI starts with START[0] |
assign bcd_ops = (OPCODE == 8'h6F) | (OPCODE == 8'h6B); // ADDP , SUBP |
|
assign man_ops = (OPCODE == 8'hB1) | (OPCODE == 8'hB5) | (OPCODE == 8'hB9) | (OPCODE == 8'hBD); // |
assign man_ops = (OPCODE == 8'hB1) | (OPCODE == 8'hB5) | (OPCODE == 8'hB9) | (OPCODE == 8'hBD); // MOVf,NEGf,XXXf,ABSf |
|
assign DFLOAT = (select[3] | copop) & ~FL; // all Double Floating Point Operations for PREPDATA |
assign make_i = (select[2:0] == 3'b011) | divi_ops | bcd_ops; // ROUND/TRUNC/FLOOR for output mul |
assign make_i = (select[2:0] == 3'b011) | divi_ops | bcd_ops; // ROUND/TRUNC/FLOOR for output multiplexer |
assign op_cmp = (OPCODE == 8'hB2) & ~FL; |
always @(posedge BCLK) misc_op <= select[4]; // for OUT-Multiplexer |
|
assign copop = (OPCODE == 8'hDD); |
assign copwr = (COP_OP[18:17] == 2'd0) & (COP_OP[13:11] == 3'b111) & (COP_OP[7:5] == 3'b001); // Cu |
assign copwr = (COP_OP[18:17] == 2'd0) & (COP_OP[13:11] == 3'b111) & (COP_OP[7:5] == 3'b001); // Custom Convert |
|
// very special solution for SCALBL |
assign scalbl = START[0] & ~FL & (OPCODE == 8'hB6); |
1090,8 → 1090,8
always @(posedge BCLK) // NaN |
if (START[1]) |
casex ({START[0],select[6:5]}) |
3'b0xx : srcflags[3] <= preflags[5] | (preflags[4] & (~preflags[3] | SRC2[31] | ~zexp2 | ~zman |
3'b111 : srcflags[3] <= (SRC2[30:23] == 8'hFF) | ((SRC2[30:23] == 8'd0) & ((SRC2[22:20] != 3'd |
3'b0xx : srcflags[3] <= preflags[5] | (preflags[4] & (~preflags[3] | SRC2[31] | ~zexp2 | ~zman2)); |
3'b111 : srcflags[3] <= (SRC2[30:23] == 8'hFF) | ((SRC2[30:23] == 8'd0) & ((SRC2[22:20] != 3'd0) | ~zman2)); // F:SRC2 = NaN |
default : srcflags[3] <= 1'b0; |
endcase |
|
1106,9 → 1106,9
always @(posedge BCLK) // NaN |
if (START[1]) |
casex ({START[0],select[6:5]}) |
3'b0xx : srcflags[1] <= preflags[2] | (preflags[1] & (~preflags[0] | SRC1[31] | ~zexp1 | ~zman |
3'b1x1 : srcflags[1] <= (SRC1[30:23] == 8'hFF) | ((SRC1[30:23] == 8'd0) & ((SRC1[22:20] != 3'd |
3'b110 : srcflags[1] <= znan1 | (zexp1 & (~zman1 | SRC2[31] | ~zexp2 | ~zman2)); // L:(SRC1,SR |
3'b0xx : srcflags[1] <= preflags[2] | (preflags[1] & (~preflags[0] | SRC1[31] | ~zexp1 | ~zman1)); |
3'b1x1 : srcflags[1] <= (SRC1[30:23] == 8'hFF) | ((SRC1[30:23] == 8'd0) & ((SRC1[22:20] != 3'd0) | ~zman1)); // F:SRC1 = NaN |
3'b110 : srcflags[1] <= znan1 | (zexp1 & (~zman1 | SRC2[31] | ~zexp2 | ~zman2)); // L:(SRC1,SRC2) = NaN , SRC1 = MSB |
default : srcflags[1] <= 1'b0; |
endcase |
|
1131,14 → 1131,14
DFPU_MUL mul_inst ( .BCLK(BCLK), .SRC1(SRC1), .SRC2(SRC2), .START(START[0]), .MRESULT(MRESULT), |
.OUT(mulout), .SRCFLAGS(srcflags) ); |
|
DFPU_DIV div_inst ( .BCLK(BCLK), .BRST(BRESET), .START({go_divi,go_divf,START}), .SRC1(SRC1), .SRC2 |
DFPU_DIV div_inst ( .BCLK(BCLK), .BRST(BRESET), .START({go_divi,go_divf,START}), .SRC1(SRC1), .SRC2(SRC2), |
.MAN1(MAN1), .MAN2(MAN2), .SRCFLAGS(srcflags), .FL(FL), .OUT(divout), .DONE(div_done), |
.BWD(BWD), .OPCODE(OPCODE[2:0]), .DIVI_OUT(divi_out), .DVZ_TRAP(DVZ_TRAP), .DEI_OVF(dei_ovf) |
.BWD(BWD), .OPCODE(OPCODE[2:0]), .DIVI_OUT(divi_out), .DVZ_TRAP(DVZ_TRAP), .DEI_OVF(dei_ovf) ); |
|
DFPU_MISC misc_inst ( .BCLK(BCLK), .START(go_misc), .SRC1(SRC1), .SRC2(SRC2), .SRCFLAG(srcflags[2]) |
DFPU_MISC misc_inst ( .BCLK(BCLK), .START(go_misc), .SRC1(SRC1), .SRC2(SRC2), .SRCFLAG(srcflags[2]), |
.MIMUX(misc_mux), .MODE({OPCODE[5],OPCODE[0],FL,OPCODE[1]}), .OUT(miscout) ); |
|
DFPU_BCD bcd_inst ( .BCLK(BCLK), .BRESET(BRESET), .START(START[1]), .DO_BCD(bcd_ops), .BWD(BWD), .S |
DFPU_BCD bcd_inst ( .BCLK(BCLK), .BRESET(BRESET), .START(START[1]), .DO_BCD(bcd_ops), .BWD(BWD), .SRC1(SRC1), .SRC2(SRC2), |
.CY_IN(CY_IN), .SUBP(~OPCODE[2]), .BCD_Q(bcd_q), .CY_OUT(bcd_carry), .BCD_DONE(bcd_done) ); |
|
// FP - path : selection of result and rounding : |
1179,7 → 1179,7
default : tt = 3'b000; // no error |
endcase |
|
assign TT_DP = man_ops ? 5'd0 : {(inexact & ~op_cmp),(underflow & ~op_cmp),tt}; // at ABSf/NEGf no |
assign TT_DP = man_ops ? 5'd0 : {(inexact & ~op_cmp),(underflow & ~op_cmp),tt}; // at ABSf/NEGf no error : different to NS32381 ! |
|
assign fp_res = FL ? {fpout[67],rund[61:31],rund[33:2]} |
: {fpout[67],rund[64:2]}; // lower 32 bits identical |
1189,13 → 1189,13
|
// 63..32 goes to memory if Word or Byte ! Also in ODD Register , 31..0 goes in EVEN Register |
// DEI comes without WR_REG information |
always @(make_i or copop or MEI or BWD or WR_REG or MRESULT or COP_IN or i_out or fp_out or divi_op |
always @(make_i or copop or MEI or BWD or WR_REG or MRESULT or COP_IN or i_out or fp_out or divi_ops or divi_out or bcd_ops or bcd_q) |
casex ({make_i,copop,MEI,BWD}) |
5'b00100 : DOUT = {MRESULT[31:8], (WR_REG ? MRESULT[15:8] : MRESULT[7:0]), MRESULT[31:0]}; // L |
5'b00100 : DOUT = {MRESULT[31:8], (WR_REG ? MRESULT[15:8] : MRESULT[7:0]), MRESULT[31:0]}; // LSD always the same |
5'b00101 : DOUT = {MRESULT[31:16],(WR_REG ? MRESULT[31:16] : MRESULT[15:0]),MRESULT[31:0]}; |
5'b0011x : DOUT = MRESULT[63:0]; |
5'b01xxx : DOUT = COP_IN; // true alignment in Coprocessor |
5'b1xxxx : DOUT = divi_ops ? divi_out : {(bcd_ops ? bcd_q : i_out),fp_out[31:0]}; // MSD is writ |
5'b1xxxx : DOUT = divi_ops ? divi_out : {(bcd_ops ? bcd_q : i_out),fp_out[31:0]}; // MSD is written first |
default : DOUT = fp_out; |
endcase |
|
1232,7 → 1232,7
default : wctrl = 5'b0; |
endcase |
|
assign done_i = wctrl[4] ? (div_done | bcd_done | COP_DONE) : ( (wctrl[3] | ~WR_REG) ? sequ[2] : se |
assign done_i = wctrl[4] ? (div_done | bcd_done | COP_DONE) : ( (wctrl[3] | ~WR_REG) ? sequ[2] : sequ[1] ); |
assign DONE = ~START[1] & done_i; // DONE is valid for all opcodes |
|
assign wr_part1 = DONE & WR_REG & wctrl[0]; |
1244,7 → 1244,7
assign LD_OUT_L = DONE & ~WR_REG; // meaning is "Load Out-Reg from Long-Path" |
|
always @(posedge BCLK) up_flag <= DONE & ~wctrl[0]; // DONE one cycle later |
assign UP_DP = (select[3] & (wctrl[0] ? DONE : up_flag)) | man_ops; // Update FSR Trap etc. : al |
assign UP_DP = (select[3] & (wctrl[0] ? DONE : up_flag)) | man_ops; // Update FSR Trap etc. : all FPU opcodes of DP_FPU |
|
// Overflow Trap for Division : DEI, QUO, DIV |
assign quo_div = (OPCODE == 8'h7C) | (OPCODE == 8'h7F); |
1262,12 → 1262,12
|
endmodule |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// |
// 10. DP_FPU Top level of long operations datapath |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module DP_FPU( BCLK, FL, BRESET, LD_LDQ, WR_REG, BWD, FSR, OPCODE, SRC1, SRC2, START, DONE, UP_DP, W |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module DP_FPU( BCLK, FL, BRESET, LD_LDQ, WR_REG, BWD, FSR, OPCODE, SRC1, SRC2, START, DONE, UP_DP, WREN_L, |
CLR_LSB, LD_OUT_L, DVZ_TRAP, DP_CMP, DP_OUT, DP_Q, TT_DP, CY_IN, OVF_BCD, COP_GO, COP_OP, |
COP_IN, COP_DONE, COP_OUT ); |
|
/m32632/trunk/rtl/TOP_MISC.v
36,14 → 36,14
// 1. IO_SWITCH Switch between ICACHE and DCACHE to IO Path |
// 2. MAKE_STAT Generate Statistic Signals |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// |
// 1. IO_SWITCH Switch between ICACHE and DCACHE to IO Path |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module IO_SWITCH ( BCLK, BRESET, I_IOA, D_IOA, I_IORD, D_IORD, D_IOWR, IO_READY, GENSTAT, D_IOBE, IL |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module IO_SWITCH ( BCLK, BRESET, I_IOA, D_IOA, I_IORD, D_IORD, D_IOWR, IO_READY, GENSTAT, D_IOBE, ILO_SIG, DCWACC, |
IO_A, IO_RD, IO_WR, IO_BE, I_IORDY, D_IORDY, STATUS, ILO ); |
|
input BCLK,BRESET; |
130,12 → 130,12
|
endmodule |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// |
// 2. MAKE_STAT Generate Statistic Signals |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module MAKE_STAT ( BCLK, READ, DACC_OK, DC_ACC, DPTE_ACC, DC_MDONE, DRAM_WR, IC_READ, IACC_OK, DATA_ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module MAKE_STAT ( BCLK, READ, DACC_OK, DC_ACC, DPTE_ACC, DC_MDONE, DRAM_WR, IC_READ, IACC_OK, DATA_HOLD, |
IC_ACC, IPTE_ACC, IC_MDONE, KOLLISION, STATSIGS ); |
|
input BCLK; |
/m32632/trunk/rtl/ALIGNER.v
36,13 → 36,13
// 1. WR_ALINGER alignes write data to cache and external devices |
// 2. RD_ALINGER alignes read data for the data path |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// |
// 1. WR_ALINGER alignes write data to cache and external devices |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module WR_ALIGNER ( PACKET, DP_Q, SIZE, WRDATA, ENBYTE ); |
|
input [3:0] PACKET; // [3:2] Paketnumber , [1:0] Startaddress |
167,11 → 167,11
|
endmodule |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// |
// 2. RD_ALINGER alignes read data for the data path |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module RD_ALIGNER ( BCLK, ACC_OK, PACKET, SIZE, REG_OUT, RDDATA, CA_HIT, DP_DI, AUX_QW ); |
|
input BCLK; |
196,7 → 196,7
// Bytes from memory : 1 - 4 - 3 - . |
// ACC_DONE : _______/----\__ |
// + 1 cycle ____/-- |
// at the end 2 cycles lost. ACC_DONE informs the Op-Dec that data is available and sent one clock c |
// at the end 2 cycles lost. ACC_DONE informs the Op-Dec that data is available and sent one clock cycle later |
// the LSD of QWORD access. (ACC_DONE -> REG_OUT is happening in ADDR_UNIT.) |
// |
// SIZE PACKET ADR : Output data ACC_OK |
/m32632/trunk/rtl/STEUERUNG.v
35,12 → 35,12
// Modules contained in this file: |
// STEUERUNG The control logic of M32632 |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
|
module STEUERUNG( BCLK, BRESET, DC_ACC_DONE, ACB_ZERO, DONE, INT_N, NMI_N, DC_ABORT, IC_INIT, DC_INI |
IACC_STAT, PROT_ERROR, IC_DIN, PC_NEW, PSR, STRING, TRAPS, IC_READ, DATA_HOLD, LD_DIN, LD_IMME |
module STEUERUNG( BCLK, BRESET, DC_ACC_DONE, ACB_ZERO, DONE, INT_N, NMI_N, DC_ABORT, IC_INIT, DC_INIT, SAVE_PC, CFG, |
IACC_STAT, PROT_ERROR, IC_DIN, PC_NEW, PSR, STRING, TRAPS, IC_READ, DATA_HOLD, LD_DIN, LD_IMME, |
WREN, WR_REG, GENSTAT, ILO, COP_OP, IC_USER, ACC_FELD, DISP, IC_TEX, IMME_Q, INFO_AU, LD_OUT, |
DETOIP, MMU_UPDATE, OPER, PC_ARCHI, PC_ICACHE, RDAA, RDAB, START, WMASKE, WRADR, RWVAL, Y_INIT |
DETOIP, MMU_UPDATE, OPER, PC_ARCHI, PC_ICACHE, RDAA, RDAB, START, WMASKE, WRADR, RWVAL, Y_INIT, |
ENA_HK, STOP_CINV ); |
|
input BCLK; |
/m32632/trunk/rtl/I_PFAD.v
41,13 → 41,13
// 6. SCHALE Enclosure for Adder/Subtractor |
// 7. I_PFAD The Integer Datapath |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// |
// 1. BITMASK Mask Generator , was a ROM on falling edge in early days |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module BITMASK (AA, DOUT); |
|
// 0 : FFFFFFFF; Masktype 1 , Zero from right |
108,11 → 108,11
|
endmodule |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// |
// 2. MULFILTER Filter for Multiplier Input Data |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module MULFILTER (BWD, FLOAT, SRC1, SRC2, DEST1, DEST2); |
|
input [1:0] BWD; |
149,11 → 149,11
|
endmodule |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// |
// 3. SIGNMUL Signed Multiplier for Integer Multiplication |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module SIGNMUL (dataa, datab, result); |
|
input signed [31:0] dataa,datab; |
163,11 → 163,11
|
endmodule |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// |
// 4. SHIFTER Barrel Shifter for all Shift Opcodes |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module SHIFTER ( MASKE,ROT,LSH,ASH,SIZE,SH_VAL,SH_DAT,SH_OUT,MASK_SEL); |
|
input [31:0] MASKE; |
201,7 → 201,7
|
// Rotation logic |
|
assign sh_dat_0 = shift[0] ? {sh_dat_in[30:0],sh_dat_in[31]} : sh_dat_in; // Rotation of 1 bit posi |
assign sh_dat_0 = shift[0] ? {sh_dat_in[30:0],sh_dat_in[31]} : sh_dat_in; // Rotation of 1 bit position |
assign sh_dat_1 = shift[1] ? {sh_dat_0[29:0],sh_dat_0[31:30]} : sh_dat_0; // 2 |
assign sh_dat_2 = shift[2] ? {sh_dat_1[27:0],sh_dat_1[31:28]} : sh_dat_1; // 4 |
assign sh_dat_3 = shift[3] ? {sh_dat_2[23:0],sh_dat_2[31:24]} : sh_dat_2; // 8 |
238,11 → 238,11
|
endmodule |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// |
// 5. FFS_LOGIK Logic for FFS opcode |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module FFS_LOGIK (SRC1, SRC2, BWD, FLAG, DOUT); |
|
input [31:0] SRC1; |
317,11 → 317,11
|
endmodule |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// |
// 6. SCHALE Enclosure for Adder/Subtractor |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module SCHALE (dataa, datab, cin, add_sub, bwd, result, cout, overflow); |
|
input [31:0] dataa,datab; |
359,13 → 359,13
|
endmodule |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// |
// 7. I_PFAD The Integer Datapath |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module I_PFAD ( BCLK, BRESET, SFP_DAT, FSR, DP_OUT, SRC1, SRC2, BMASKE, ADDR, MRESULT, OPCODE, BWD, |
WREN, WRADR, RDAA, DETOIP, BITSEL, OVF_BCD, DISP, RWVFLAG, DSR, I_OUT, PSR, BMCODE, OV_FLAG, ACB |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module I_PFAD ( BCLK, BRESET, SFP_DAT, FSR, DP_OUT, SRC1, SRC2, BMASKE, ADDR, MRESULT, OPCODE, BWD, FL, SP_CMP, DP_CMP, LD_OUT, |
WREN, WRADR, RDAA, DETOIP, BITSEL, OVF_BCD, DISP, RWVFLAG, DSR, I_OUT, PSR, BMCODE, OV_FLAG, ACB_ZERO, STRING); |
|
input BCLK,BRESET; |
input [31:0] SFP_DAT,FSR,DP_OUT; |
405,7 → 405,7
|
// +++++++++++++ Global Output Multiplexer ++++++++++++++++++++++++++++ |
|
always @(OPCODE or pfad_4 or pfad_5 or pfad_6 or pfad_7 or pfad_8 or DP_OUT or FL or SFP_DAT or FSR |
always @(OPCODE or pfad_4 or pfad_5 or pfad_6 or pfad_7 or pfad_8 or DP_OUT or FL or SFP_DAT or FSR or pfad_11) |
casex (OPCODE[7:3]) |
5'b0100_x : I_OUT = pfad_4; |
5'b0101_x : I_OUT = pfad_5; // String opcodes |
440,7 → 440,7
wire save_psr,pop_psr; |
wire [4:0] selbits; |
// Bits from DETOIP; |
wire cmps_op,ph_match,until,kill_opt,inss_op,exin_cmd,extract,bit_reg,kurz_st,dw_info,acb_reg,t2p |
wire cmps_op,ph_match,until,kill_opt,inss_op,exin_cmd,extract,bit_reg,kurz_st,dw_info,acb_reg,t2p; |
wire bcd_op,bcd_carry; |
|
assign cmps_op = DETOIP[11]; // for CMPS |
464,14 → 464,14
// LD_OUT[1] is coming out of DECODER for this purpose |
assign up_psr = bcd_op | ((cmp_op | bit_op | ari_op | neg_op | ffs_op | chk_op) & LD_OUT); |
|
assign cmp_op = (OPCODE == 8'h41) | ((OPCODE == 8'hB2) & (FL ? ~SP_CMP[2] : ~DP_CMP[2])); // CMPi o |
assign bit_op = ((OPCODE[7:4] == 4'h6) & ((~OPCODE[3] & OPCODE[1]) | OPCODE[3:0] == 4'hE)) // the |
assign cmp_op = (OPCODE == 8'h41) | ((OPCODE == 8'hB2) & (FL ? ~SP_CMP[2] : ~DP_CMP[2])); // CMPi or (CMPf & ~NAN) |
assign bit_op = ((OPCODE[7:4] == 4'h6) & ((~OPCODE[3] & OPCODE[1]) | OPCODE[3:0] == 4'hE)) // the last term is for IBIT |
| (OPCODE == 8'h4D) | str_op | rwv_op; // TBIT or CMPS or RDVAL/WRVAL |
assign ari_op = (OPCODE[7:4] == 4'h4) & (OPCODE[1:0] == 2'b0) & ~dw_info; // ADDi,ADDCi,SUBi,SUBCi |
assign ari_op = (OPCODE[7:4] == 4'h4) & (OPCODE[1:0] == 2'b0) & ~dw_info; // ADDi,ADDCi,SUBi,SUBCi - special case ADJSPi no flags |
assign neg_op = (OPCODE[7:4] == 4'h6) & (OPCODE[3] & (OPCODE[1:0] == 2'b0)); // ABSi,NEGi |
assign ffs_op = (OPCODE == 8'h85); // FFS |
assign chk_op = (OPCODE == 8'h83); // CHECK |
assign str_op = (OPCODE[7:4] == 4'h5) & (OPCODE[3:2] == 2'b0) & ~kurz_st; // String-"S" opcodes : F |
assign str_op = (OPCODE[7:4] == 4'h5) & (OPCODE[3:2] == 2'b0) & ~kurz_st; // String-"S" opcodes : F-Flag to 0, at start always |
assign abs_op = (OPCODE == 8'h6C); // ABSi : Carry is not affected ! |
assign rwv_op = (OPCODE[7:4] == 4'hE) & (OPCODE[3:1] == 3'b0); // RDVAL + WRVAL |
|
484,7 → 484,7
endcase |
|
assign ACB_ZERO = (addsub_q == 32'h0); // is used for ACBi opcode too |
assign f_flag = str_op ? 1'b0 : (rwv_op ? RWVFLAG : (bit_op ? SRC2[selbits] : (acb_reg ? PSR[5] : o |
assign f_flag = str_op ? 1'b0 : (rwv_op ? RWVFLAG : (bit_op ? SRC2[selbits] : (acb_reg ? PSR[5] : over_flow))); |
assign fp_nz = FL ? SP_CMP[1:0] : DP_CMP[1:0]; |
assign z_flag = OPCODE[1] ? fp_nz[0] : ACB_ZERO; |
assign nl_flags = OPCODE[1] ? {fp_nz[1],1'b0} : nl_int; |
491,7 → 491,7
|
always @(*) // Bits : N Z F V - L T C |
casex ({cmp_op,bcd_op,bit_op,(ffs_op | chk_op)}) |
4'b0000 : psr_new = {PSR[7:6], f_flag,PSR[4:1],((acb_reg | abs_op) ? PSR[0] : cy_out)}; |
4'b0000 : psr_new = {PSR[7:6], f_flag,PSR[4:1],((acb_reg | abs_op) ? PSR[0] : cy_out)}; // arithmetic Op : CY and F |
4'b0001 : psr_new = {PSR[7:6],(ffs_op ? ffs_flag : chk_flag),PSR[4:0]}; // FFS or CHECK |
4'b001x : psr_new = (cmps_op & str_op) ? |
{2'b01, f_flag,PSR[4:3],1'b0,PSR[1:0]} // Init CMPS |
504,7 → 504,7
|
always @(save_psr or pop_psr or OPCODE or PSR or SRC1) |
casex ({save_psr,pop_psr,OPCODE[6],OPCODE[2]}) |
4'b10xx : calc_psr = PSR & {~OPCODE[0],11'h0ED}; // clear P S U V T and the I-Bit at Interrupt & |
4'b10xx : calc_psr = PSR & {~OPCODE[0],11'h0ED}; // clear P S U V T and the I-Bit at Interrupt & ABORT |
4'b11xx : calc_psr = SRC1[27:16]; |
4'b0x00 : calc_psr = PSR & ~SRC1[11:0]; // BICPSR : Opcode = h32 |
4'b0x01 : calc_psr = PSR | SRC1[11:0]; // BISPSR h36 |
534,7 → 534,7
end |
|
// Register for storage of PSR at Entry of Exception |
always @(posedge BCLK) if (save_psr) push_psr <= {PSR[11],(~OPCODE[1] & PSR[10]),PSR[9:0]}; // P-Fl |
always @(posedge BCLK) if (save_psr) push_psr <= {PSR[11],(~OPCODE[1] & PSR[10]),PSR[9:0]}; // P-Flag modified |
|
assign PSR = {psr_high,psr_low}; |
|
583,7 → 583,7
default : bwd_daten1 = SRC1; |
endcase |
|
assign add_flag = ~OPCODE[3] & ~OPCODE[1] & ~OPCODE[0]; // Only ADDi and ADDCi otherwise subtract i |
assign add_flag = ~OPCODE[3] & ~OPCODE[1] & ~OPCODE[0]; // Only ADDi and ADDCi otherwise subtract in SCHALE |
|
always @(PSR or OPCODE) // more effort due to ABSi und NEGi : Format 6 |
casex ({OPCODE[5],OPCODE[3:2]}) |
593,10 → 593,10
default : cy_in = 1'b1; // SUB + ABS + NEG : BORROW must be 1 for normal Adder |
endcase |
|
SCHALE addsub_ipfad (.dataa(bwd_daten2), .datab(bwd_daten1), .cin(cy_in), .add_sub(add_flag), |
SCHALE addsub_ipfad (.dataa(bwd_daten2), .datab(bwd_daten1), .cin(cy_in), .add_sub(add_flag), .bwd(BWD), |
.result(addsub_q), .cout(cy_out), .overflow(over_flow) ); |
|
always @(posedge BCLK) get_psr <= (RDAA == 8'h9D) | (RDAA == 8'h90) | (RDAA == 8'h93); // PSR or US |
always @(posedge BCLK) get_psr <= (RDAA == 8'h9D) | (RDAA == 8'h90) | (RDAA == 8'h93); // PSR or US or DSR is read |
always @(posedge BCLK) rd_psr <= (RDAA[1:0] == 2'b01); |
always @(posedge BCLK) rd_dsr <= (RDAA[1:0] == 2'b11); |
|
603,7 → 603,7
always @(OPCODE or SRC1 or SRC2 or get_psr or rd_psr or rd_dsr or DSR or PSR or ADDR) |
casex (OPCODE[3:1]) |
3'b001 : pfad_4a = SRC2 & ~SRC1; // BIC |
3'bx10 : pfad_4a = get_psr ? {({4{rd_dsr}} & DSR),16'd0,({4{rd_psr}} & PSR[11:8]),({8{~rd_dsr}} |
3'bx10 : pfad_4a = get_psr ? {({4{rd_dsr}} & DSR),16'd0,({4{rd_psr}} & PSR[11:8]),({8{~rd_dsr}} & PSR[7:0])} : SRC1; // MOV |
3'b011 : pfad_4a = SRC2 | SRC1; // OR |
3'b101 : pfad_4a = SRC2 & SRC1; // AND |
3'b111 : pfad_4a = SRC2 ^ SRC1; // XOR |
622,7 → 622,7
|
assign op_str = (OPCODE[7:3] == 5'b0101_0); |
|
// This logic is for detection if an accelerated MOVS/MOVM inside a page is possible - Backward is |
// This logic is for detection if an accelerated MOVS/MOVM inside a page is possible - Backward is not possible |
always @(posedge BCLK) |
if (op_str) |
begin |
669,7 → 669,7
|
assign weiter = mehr | (pfad_5[3:0] != 4'h0); |
|
assign STRING = {1'b0,ACB_ZERO,weiter,( op_str ? todo[9:8] : todo_reg[9:8] )}; // ACB_ZERO is delay |
assign STRING = {1'b0,ACB_ZERO,weiter,( op_str ? todo[9:8] : todo_reg[9:8] )}; // ACB_ZERO is delayed 1 cycle extern |
|
// +++++++++++++ Format 6 opcodes : ADDP + SUBP are done in DP_FPU ++++++++++++++++++++ |
|
685,9 → 685,9
|
assign rot = (OPCODE[3:0] == 4'h0); |
assign ash = (OPCODE[3:0] == 4'h1); |
assign lsh = (OPCODE[3:1] == 3'b010); // 5 is LSH , but 4 is Trap(UND) and is used for right-shift |
assign lsh = (OPCODE[3:1] == 3'b010); // 5 is LSH , but 4 is Trap(UND) and is used for right-shift of Offset ! |
|
assign eis_op = (OPCODE == 8'h73) | (OPCODE[7] & ~OPCODE[1] & inss_op); // EXTSi | INSSi at OPCODE= |
assign eis_op = (OPCODE == 8'h73) | (OPCODE[7] & ~OPCODE[1] & inss_op); // EXTSi | INSSi at OPCODE=80h |
assign exin_op = exin_cmd & (OPCODE[7:4] == 4'h8); // identifies EXT/INS |
assign exin_op2 = (exin_cmd | inss_op) & (OPCODE[7:4] == 4'h6); // identifies LSH |
|
698,15 → 698,15
assign selbits = (bit_reg | eis_op | exin_op) ? (exin_op ? disp_reg : SRC1[4:0]) : {2'b00,BITSEL}; |
|
assign shval_ei = inss_op ? {2'b00,offs_reg} : (bit_reg ? SRC1[4:0] : {2'b00,SRC1[2:0]}); |
assign sh_exin[4:0] = extract ? (5'd0 - shval_ei) : shval_ei; // EXT : right shift, INS : left shi |
assign sh_exin[7:5] = (shval_ei == 5'd0) ? 3'b000 : {3{extract}}; // Special case : 0 has no negati |
assign sh_exin[4:0] = extract ? (5'd0 - shval_ei) : shval_ei; // EXT : right shift, INS : left shift |
assign sh_exin[7:5] = (shval_ei == 5'd0) ? 3'b000 : {3{extract}}; // Special case : 0 has no negativ sign ! |
|
// LSH shift by 16 bit to right |
assign sh_count = (OPCODE[3:0] == 4'h4) ? 8'hF0 : (exin_op2 ? sh_exin : SRC1[7:0]); |
|
assign BMCODE = (bit_op | eis_op | exin_op) ? {(eis_op | exin_op),(bit_op | exin_op),selbits} : {2' |
assign BMCODE = (bit_op | eis_op | exin_op) ? {(eis_op | exin_op),(bit_op | exin_op),selbits} : {2'b00,shcode}; |
|
SHIFTER shift_inst (.MASKE(BMASKE), .ROT(rot), .ASH(ash), .LSH(lsh), .SH_DAT(SRC2), .SH_VAL(sh_cou |
SHIFTER shift_inst (.MASKE(BMASKE), .ROT(rot), .ASH(ash), .LSH(lsh), .SH_DAT(SRC2), .SH_VAL(sh_count), |
.MASK_SEL(shcode), .SIZE(BWD), .SH_OUT(shdat) ); |
|
always @(BWD or SRC2 or neg_op or dw_info) |
825,11 → 825,11
|
always @(*) |
casex (OPCODE[3:0]) // CVTP (81) has no OPCODE ! |
4'b000x : pfad_8 = (extract ? SRC2 : 32'hFFFF_FFFF) & BMASKE; // EXT, the other form is for INS |
4'b0010 : pfad_8 = (SRC1 & ins_maske) | (SRC2 & ~ins_maske); // INS ins_maske[] ? SRC1[] : SRC2[ |
4'b000x : pfad_8 = (extract ? SRC2 : 32'hFFFF_FFFF) & BMASKE; // EXT, the other form is for INS to get the mask |
4'b0010 : pfad_8 = (SRC1 & ins_maske) | (SRC2 & ~ins_maske); // INS ins_maske[] ? SRC1[] : SRC2[] |
4'b0011 : pfad_8 = BWD[1] ? addsub_q : {16'h0,chk_low}; |
4'b0101 : pfad_8 = {24'hxx_xxxx,3'b000,ffs_out}; |
default : pfad_8 = {4'hx,push_psr,SRC1[15:0]}; // Opcode x'87-x'8F is used at CXP and therefore |
default : pfad_8 = {4'hx,push_psr,SRC1[15:0]}; // Opcode x'87-x'8F is used at CXP and therefore in Exception-Processing |
endcase |
|
// ++++++++++++++ Format 11 : Floating-Point Datapath +++++++++++++++++++++++++++++++ |
/m32632/trunk/rtl/STEUER_MISC.v
39,14 → 39,14
// 4. ILL_UNDEF Illegal and Undefined Opcodes Detection |
// 5. GRUPPE_2 Decoder and State Machine for GRUPPE_2 Opcodes |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// |
// 1. OPDEC_REG Central Instruction Register |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module OPDEC_REG ( BCLK, BRESET, NEW, ACC_STAT, PROT_ERROR, ALSB, USED, IC_DIN, IC_INIT, DC_INIT, Y_ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module OPDEC_REG ( BCLK, BRESET, NEW, ACC_STAT, PROT_ERROR, ALSB, USED, IC_DIN, IC_INIT, DC_INIT, Y_INIT, RESTART, STOP_IC, |
OPREG, ANZ_VAL, IC_READ, NEW_PC, NEXT_ADR, DATA_HOLD, ABORT, IC_TEX, INIT_DONE); |
|
input BCLK,BRESET; |
98,12 → 98,12
if (!BRESET) ABORT <= 1'b0; |
else ABORT <= (acc_err & ~(new_restart | pre_new)) | (ABORT & ~NEW_PC); |
|
always @(posedge BCLK) if (acc_err) IC_TEX <= (ACC_STAT[3] | PROT_ERROR) ? {nseq_flag,2'b11} : {nse |
always @(posedge BCLK) if (acc_err) IC_TEX <= (ACC_STAT[3] | PROT_ERROR) ? {nseq_flag,2'b11} : {nseq_flag,~ACC_STAT[2],ACC_STAT[2]}; |
|
always @(posedge BCLK) nseq_flag <= NEW_PC | (nseq_flag & ~acc_ok); // for MMU Status Register |
|
always @(posedge BCLK) abort_flag <= acc_err; |
assign acc_ende = ~IC_READ | acc_ok | abort_flag; // abort_flag one cycle later is ok ! If no ICach |
assign acc_ende = ~IC_READ | acc_ok | abort_flag; // abort_flag one cycle later is ok ! If no ICache access always end |
|
assign new_restart = NEW | RESTART; // They are pulses |
|
112,7 → 112,7
|
assign NEW_PC = (new_restart | pre_new) & acc_ende; // At the end of access geenerate new address ! |
|
// There are 2 "NEW/RESTART" : "new_restart" combinatorical out of DECODER, "pre_new" out of Regist |
// There are 2 "NEW/RESTART" : "new_restart" combinatorical out of DECODER, "pre_new" out of Register |
always @(posedge BCLK) new_reg <= new_restart | pre_new | (new_reg & ~acc_ende & BRESET); |
|
always @(USED or OPREG) // Data first shift to the right |
155,7 → 155,7
4'b00_1_1 : ANZ_VAL <= new_anz; |
endcase |
|
assign NEXT_ADR = new_reg ? (acc_ok & ~pre_new) : (acc_ok & ~new_anz[2]); // switches MUX at PC res |
assign NEXT_ADR = new_reg ? (acc_ok & ~pre_new) : (acc_ok & ~new_anz[2]); // switches MUX at PC resp. ICACHE |
|
// Instruction CACHE Control : READ is coming after all INITs are done |
|
167,7 → 167,7
if (!BRESET) stop_init <= 1'b0; |
else stop_init <= stop_init | IC_READ; |
|
// The INIT_DONE should come after Reset. But it comes too at LMR PTB therefore extra enable after |
// The INIT_DONE should come after Reset. But it comes too at LMR PTB therefore extra enable after Reset ! |
always @(posedge BCLK or negedge BRESET) |
if (!BRESET) IC_READ <= 1'b0; |
else IC_READ <= (IC_READ & ~acc_err & ~(STOP_IC & acc_ok)) | NEW_PC | (INIT_DONE & ~stop_init); |
177,12 → 177,12
|
endmodule |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// |
// 2. PROG_COUNTER Program Counters |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module PROG_COUNTER ( BCLK, BRESET, NEW, LOAD_PC, NEW_PC, NEXT_ADR, NEXT_PCA, DISP, PC_NEW, USED, US |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module PROG_COUNTER ( BCLK, BRESET, NEW, LOAD_PC, NEW_PC, NEXT_ADR, NEXT_PCA, DISP, PC_NEW, USED, USER, SAVE_PC, FPU_TRAP, |
ADIVAR, PC_ARCHI, PC_ICACHE, PC_SAVE, ALSB, IC_USER); |
|
input BCLK,BRESET; |
239,9 → 239,9
else |
pc_ic_reg <= pc_icache_i; |
|
// NEW is only one cycle long - but in pc_adduse is the PC stored when ACC_OK is not there and ther |
// NEW is only one cycle long - but in pc_adduse is the PC stored when ACC_OK is not there and therefore NEW_PC |
// is used to initiate a new access in ICACHE |
assign pc_icache_i = NEW_PC ? (NEW ? pc_jump : pc_adduse) : (NEXT_ADR ? ({pc_ic_reg[31:2],2'b00} + |
assign pc_icache_i = NEW_PC ? (NEW ? pc_jump : pc_adduse) : (NEXT_ADR ? ({pc_ic_reg[31:2],2'b00} + 32'h0000_0004) : pc_ic_reg); |
|
// This MUX is extra for LMR IVAR,... and CINV build in |
assign PC_ICACHE = {(ADIVAR ? PC_NEW[31:4] : pc_icache_i[31:4]),pc_icache_i[3:0]}; |
256,11 → 256,11
|
endmodule |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// |
// 3. REG_LIST Register List Evaluation |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module REG_LIST ( DIN, IPOS, INIT, OPOS, VALID); |
|
// Detects set bits in register list for SAVE/RESTORE & ENTER/EXIT |
298,11 → 298,11
|
endmodule |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// |
// 4. ILL_UNDEF Illegal and Undefined Opcodes Detection |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module ILL_UNDEF (OPREG, ANZ_VAL, USER, CFG, ILL, UNDEF ); |
|
input [23:0] OPREG; |
326,7 → 326,7
parameter imode = 5'b10100; // Immediate Addressing Mode |
|
// [2]= minimum 3, [1]= minimum 2, [0]=minimum 1 |
assign valid = {(ANZ_VAL[2] | (ANZ_VAL[1:0] == 2'b11)),(ANZ_VAL[2:1] != 2'b00),(ANZ_VAL != 3'b000)} |
assign valid = {(ANZ_VAL[2] | (ANZ_VAL[1:0] == 2'b11)),(ANZ_VAL[2:1] != 2'b00),(ANZ_VAL != 3'b000)}; |
assign lsbes = (OPREG[1:0] == 2'b10); // Tag of all 3 Byte opcodes |
|
// +++++++++++++++++++++++++ Detect illegale opcodes +++++++++++++++++++ |
355,7 → 355,7
16'b1xx_01_xxxx_0000_111 : undef_opc = 1'b1; // Format 5 : 01xx |
16'b1xx_01_00xx_0100_111 : undef_opc = 1'b1; // Format 6 : 0100 |
16'b1xx_10_10xx_x100_111 : undef_opc = 1'b1; // Format 6/7 : 1010 |
16'b1xx_xx_xxxx_x011_111 : undef_opc = ~CFG[1]; // Format 9/11 : FPU Befehle wie MOVif etc. und |
16'b1xx_xx_xxxx_x011_111 : undef_opc = ~CFG[1]; // Format 9/11 : FPU Befehle wie MOVif etc. und ADDf etc. |
16'b1xx_xx_xxxx_1111_111 : undef_opc = ~CFG[1]; // Format 12 : FPU Befehle wie POLYf etc. |
16'b1xx_x1_xxxx_0001_111 : undef_opc = 1'b1; // Format 14 : x1xx |
16'b1xx_10_00xx_0001_111 : undef_opc = 1'b1; // Format 14 : 1000 |
381,9 → 381,9
assign gen23 = (OPREG[18:14] == udef_amode); |
|
always @(OPREG or valid or gen12 or gen22 or gen13 or gen23) |
if (valid[2] && (OPREG[7:5] != 3'b000) && (OPREG[3:0] == 4'b1110)) undef_am = gen13 | gen23; // ne |
if (valid[2] && (OPREG[7:5] != 3'b000) && (OPREG[3:0] == 4'b1110)) undef_am = gen13 | gen23; // nearly all 3 Byte opcodes |
else |
undef_am = valid[1] & gen12 & (OPREG[1:0] != 2'b10) & ((OPREG[3:2] != 2'b11) & gen22); // all |
undef_am = valid[1] & gen12 & (OPREG[1:0] != 2'b10) & ((OPREG[3:2] != 2'b11) & gen22); // all 2 Byte opcodes |
|
// 3. When is Immediate not allowed ? |
|
394,11 → 394,11
|
always @(*) |
casex ({valid[2:1],OPREG[13:2],lsbes}) |
15'bx1_xxxxxx_x0xx11_0 : undef_im = igen12 & (OPREG[5:4] != 2'b01); // Format 2 : ADDQD,SPR,Sco |
15'bx1_xxxxxx_x0xx11_0 : undef_im = igen12 & (OPREG[5:4] != 2'b01); // Format 2 : ADDQD,SPR,Scond |
15'bx1_xxxxxx_x10111_0 : undef_im = igen12; // Format 2 : ACB,MOVQ |
15'bx1_xxxxx0_011111_0 : undef_im = igen12; // Format 3 : CXPD,JUMP,JSR |
15'bx1_xxxxxx_xxxxx0_0 : undef_im = igen22; // Format 4 |
15'bx1_xxxxxx_xxxx01_0 : undef_im = (igen12 & (OPREG[5:4] == 2'b10)) // Format 4 : SRC1 - not AD |
15'bx1_xxxxxx_xxxx01_0 : undef_im = (igen12 & (OPREG[5:4] == 2'b10)) // Format 4 : SRC1 - not ADDR |
|(igen22 & (OPREG[5:4] != 2'b00)); // Format 4 : SRC2 - CMP |
15'b1x_xxxxxx_x10011_1 : undef_im = igen23; // Format 6+7 |
15'b1x_xxx0xx_0x1011_1 : undef_im = igen13 | igen23; // Format 8 EXT,CVTP |
420,12 → 420,12
|
endmodule |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// |
// 5. GRUPPE_2 Decoder and State Machine for GRUPPE_2 Opcodes |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module GRUPPE_2 ( BCLK, PHASE_0, OPREG, PHASE, SRC_1, SRC_2, REGA1, REGA2, IRRW1, IRRW2, ADRD1, ADRD |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module GRUPPE_2 ( BCLK, PHASE_0, OPREG, PHASE, SRC_1, SRC_2, REGA1, REGA2, IRRW1, IRRW2, ADRD1, ADRD2, EXR12, EXR22, |
PHRD1, PHRD2, NXRD1, NXRW2, ACCA, OPERA, |
STATE_0, STATE_GROUP_50, STATE_GROUP_60 ); |
|
472,9 → 472,9
parameter disp2ea = 19'bxx_0010_0000_0_0000_0010; // pass DISP |
parameter case_op = 19'bxx_0010_1000_0_0000_0001; // SRC1 add to PC_ARCHI |
parameter read_byb = 19'b00_1011_11xx_0_0000_0011; // read of SRC2 for Bit opcodes |
parameter exr11 = {2'b10 ,4'b1011,4'h0 ,9'h080}; // 2. access External with Mem.-Pointer + 4* Dis |
parameter exr11 = {2'b10 ,4'b1011,4'h0 ,9'h080}; // 2. access External with Mem.-Pointer + 4* Disp |
parameter adrcvtp = 19'bxx_0010_0111_0_0000_0000; // for CVTP |
parameter addone = 19'bxx_0010_0100_0_0000_0000; // for INDEX : SRC1 + SRC2 , simple Add without Fl |
parameter addone = 19'bxx_0010_0100_0_0000_0000; // for INDEX : SRC1 + SRC2 , simple Add without Flags |
parameter addind = 19'bxx_0010_0100_0_0000_0011; // for INDEX : SRC1 + EA |
parameter src_x = 7'hxx; |
parameter dest_x = 6'hxx; |
560,7 → 560,7
assign op_kust = {1'bx,OPERA[9:8],8'h7A}; // Special-Opcode for MOVM/CMPM |
assign op_bwd = {1'bx,OPERA[9:8],8'h45}; // for CASE and Bit opcodes |
|
assign re_wr = {EXR22[18:17],4'b0101,4'h0, 9'h003}; // REUSE Address : Write of rmw , top 2 Bits |
assign re_wr = {EXR22[18:17],4'b0101,4'h0, 9'h003}; // REUSE Address : Write of rmw , top 2 Bits contain size |
|
always @(posedge BCLK) tbit_flag <= ~OPERA[1]; // due to Timing ... |
always @(posedge BCLK) size_dw <= OPERA[9]; |
578,9 → 578,9
|
always @(*) |
casex (op_reg) |
5'b1_0000 : // MOVS Phase 0 : Entry 1. Pointer "in Page"-test prepare, 2. test for R0=0 , then jum |
5'b1_0000 : // MOVS Phase 0 : Entry 1. Pointer "in Page"-test prepare, 2. test for R0=0 , then jump to x'C0 |
begin |
STATE_0 = { addr_nop,8'h67, 7'h01, 7'h02, 1'b0,dest_x,op_stpr, 2'b00,2'b00,4'h0 }; // String |
STATE_0 = { addr_nop,8'h67, 7'h01, 7'h02, 1'b0,dest_x,op_stpr, 2'b00,2'b00,4'h0 }; // String-Pointer prepare |
state_50 = dont_care; |
state_53 = dont_care; |
state_54 = dont_care; |
596,8 → 596,8
state_53 = { ADRD2, phsrc2,IRRW2, REGA2, 1'b1,temp_h,op_adr, 2'b00,2'b00,NXRW2 }; |
state_54 = dont_care; |
state_55 = dont_care; |
state_58 = { disp2ea, 8'h65, src_x, src_x, 1'b1,temp_1,op_adr, 2'b00,2'b00,4'b1110 }; // Read |
state_59 = { addr_nop,8'h67, rtmph, rtmp1, 1'b0,dest_x,op_stpr, 2'b00,2'b00,4'h0 }; // String |
state_58 = { disp2ea, 8'h65, src_x, src_x, 1'b1,temp_1,op_adr, 2'b00,2'b00,4'b1110 }; // Read of DISP for count |
state_59 = { addr_nop,8'h67, rtmph, rtmp1, 1'b0,dest_x,op_stpr, 2'b00,2'b00,4'h0 }; // String-Pointer prepare |
state_5A = dont_care; |
end |
5'b1_0010 : // JUMP/JSR |
626,7 → 626,7
begin |
STATE_0 = { ADRD1, phsrc1,src_x, REGA1, 1'b0,dest_x,op_mov, 2'b00,2'b00,NXRD1 }; |
state_50 = { ADRD1, phsrc1,IRRW1, REGA1, 1'b0,dest_x,op_mov, 2'b00,2'b00,NXRD1 }; |
state_53 = { addr_nop,8'h00, src_x, src_x, 1'b0,dest_x,op_rwv, 2'b00,2'b10,4'h0 }; // LD_OU |
state_53 = { addr_nop,8'h00, src_x, src_x, 1'b0,dest_x,op_rwv, 2'b00,2'b10,4'h0 }; // LD_OUT set because of "F" |
state_54 = dont_care; |
state_55 = dont_care; |
state_58 = dont_care; |
638,7 → 638,7
STATE_0 = ACCA[3] ? // _M... |
{ ADRD1, phsrc1,src_x, REGA1, 1'b0,dest_x,op_mov, 2'b00,2'b00,NXRD1 } |
: { case_op, 8'h54, SRC_1, src_x, 1'b0,dest_x,op_bwd, 2'b00,2'b00,4'h0 }; |
state_50 = { ADRD1, phsrc1,IRRW1, REGA1, 1'b0,dest_x,op_mov, 2'b00,2'b00,NXRD1 }; // only |
state_50 = { ADRD1, phsrc1,IRRW1, REGA1, 1'b0,dest_x,op_mov, 2'b00,2'b00,NXRD1 }; // only one operand in mem. |
state_53 = { case_op, 8'h54, imme, src_x, 1'b0,dest_x,op_bwd, 2'b00,2'b00,4'h0 }; |
state_54 = { addr_nop,8'h66, src_x, src_x, 1'b1,temp_h,op_adr, 2'b00,2'b00,4'h0 }; |
state_55 = dont_care; |
646,7 → 646,7
state_59 = dont_care; |
state_5A = dont_care; |
end |
5'b1_0100 : // all Bit opcodes with Bit in memory. RMW Test in Phase x'59 = Special case, otherwis |
5'b1_0100 : // all Bit opcodes with Bit in memory. RMW Test in Phase x'59 = Special case, otherwise x'58 |
begin |
STATE_0 = ACCA[3] ? // _M... |
{ ADRD1, phsrc1,src_x, REGA1, 1'b0,dest_x,op_mov, 2'b00,2'b00,NXRD1 } |
655,12 → 655,12
{ ADRD1, phsrc1,IRRW1, REGA1, 1'b0,dest_x,op_mov, 2'b00,2'b00,NXRD1 } |
: { addr_nop,8'h54, SRC_1, src_x, 1'b1,temp_h,op_mov, 2'b00,2'b00,4'h0 }; |
state_53 = { addr_nop,8'h54, imme, src_x, 1'b1,temp_h,op_mov, 2'b00,2'b00,4'h0 }; |
state_54 = { ADRD2, phsrc2,IRRW2, REGA2, 1'b0,dest_x,op_mov, 2'b00,2'b00,NXRW2 }; // here S |
state_54 = { ADRD2, phsrc2,IRRW2, REGA2, 1'b0,dest_x,op_mov, 2'b00,2'b00,NXRW2 }; // here SRC1 => TEMP_H |
state_55 = dont_care; |
state_58 = { read_byb,8'h59, rtmph, src_x, 1'b0,dest_x,op_bwd, 2'b00,2'b00,4'h1 }; // next re |
state_58 = { read_byb,8'h59, rtmph, src_x, 1'b0,dest_x,op_bwd, 2'b00,2'b00,4'h1 }; // next read of Byte |
state_59 = tbit_flag ? |
{ addr_nop,8'h00, src_x, imme, 1'b0,dest_x,OPERA, 2'b00,2'b10,4'h0 } // TBIT end |
: { re_wr, 8'h27, src_x, imme, 1'b0,dest_x,OPERA, 2'b00,2'b10,4'h1 }; // CBIT/SBIT/IBIT |
: { re_wr, 8'h27, src_x, imme, 1'b0,dest_x,OPERA, 2'b00,2'b10,4'h1 }; // CBIT/SBIT/IBIT end |
state_5A = dont_care; |
end |
5'b1_0101 : // EXTS : BASE Operand => TEMP, calculate address of Destination |
673,13 → 673,13
: { addr_nop,8'h54, SRC_1, src_x, 1'b1,temp_h,op_mov, 2'b00,2'b00,4'h0 }; |
state_53 = { addr_nop,8'h54, imme, src_x, 1'b1,temp_h,op_mov, 2'b00,2'b00,4'h0 }; |
state_54 = ACCA[1] ? |
{ ADRD2, phsrc2,IRRW2, REGA2, 1'b0,dest_x,op_mov, 2'b00,2'b00,NXRW2 } // here Adr(DEST) |
: { addr_nop,8'h59, src_x, src_x, 1'b0,dest_x,op_mov, 2'b00,2'b00,4'h8 }; // 1 Byte Immedi |
{ ADRD2, phsrc2,IRRW2, REGA2, 1'b0,dest_x,op_mov, 2'b00,2'b00,NXRW2 } // here Adr(DEST) => EA |
: { addr_nop,8'h59, src_x, src_x, 1'b0,dest_x,op_mov, 2'b00,2'b00,4'h8 }; // 1 Byte Immediate read |
state_55 = dont_care; |
state_58 = { addr_nop,8'h59, src_x, src_x, 1'b0,dest_x,op_mov, 2'b00,2'b00,4'h8 }; // 1 Byte |
state_58 = { addr_nop,8'h59, src_x, src_x, 1'b0,dest_x,op_mov, 2'b00,2'b00,4'h8 }; // 1 Byte Immediate read |
state_59 = ACCA[1] ? // _..M. |
{ re_wr, 8'h27, imme, rtmph, 1'b0,dest_x,OPERA, 2'b00,2'b10,4'h1 } // result in memory |
: { addr_nop,8'h00, imme, rtmph, 1'b1,dest_2,OPERA, 2'b00,2'b00,4'h0 }; // result in Regi |
: { addr_nop,8'h00, imme, rtmph, 1'b1,dest_2,OPERA, 2'b00,2'b00,4'h0 }; // result in Register |
state_5A = dont_care; |
end |
5'b1_1010 : // EXT : BASE Operand => TEMP, calculate address of Destination |
690,21 → 690,21
state_50 = ACCA[3] ? // _M... |
{ ADRD1, phsrc1,IRRW1, REGA1, 1'b0,dest_x,op_mov, 2'b00,2'b00,NXRD1 } |
: { addr_nop,8'h54, SRC_1, src_x, 1'b1,temp_h,op_mov, 2'b00,2'b00,4'h0 }; |
state_53 = { addr_nop,8'h55, src_x, src_x, 1'b0,dest_x,op_mov, 2'b00,2'b00,4'h0 }; // Addr = |
state_53 = { addr_nop,8'h55, src_x, src_x, 1'b0,dest_x,op_mov, 2'b00,2'b00,4'h0 }; // Addr => EA Reg |
state_54 = ACCA[1] ? |
( ACCA[3] ? |
{addr_nop,8'h5A, imme, src_x, 1'b1,temp_h,op_mov, 2'b00,2'b00,4'h0 } |
:{ADRD2, phsrc2,IRRW2, REGA2, 1'b0,dest_x,op_mov, 2'b00,2'b00,NXRW2 } ) // here Adr(DEST) |
:{ADRD2, phsrc2,IRRW2, REGA2, 1'b0,dest_x,op_mov, 2'b00,2'b00,NXRW2 } ) // here Adr(DEST) => EA |
: { addr_nop,8'h59, rd_reg,(ACCA[3] ? imme : rtmph), |
1'b1,temp_h,op_lsh, 2'b00,2'b00,4'hE }; // Displacement read |
state_55 = { exoffset,8'h54, rd_reg,src_x, 1'b0,dest_x,op_mov, 2'b00,2'b00,4'h1 }; // Read S |
state_58 = { addr_nop,8'h59, rd_reg,rtmph, 1'b1,temp_h,op_lsh, 2'b00,2'b00,4'hE }; // Displac |
state_55 = { exoffset,8'h54, rd_reg,src_x, 1'b0,dest_x,op_mov, 2'b00,2'b00,4'h1 }; // Read Source, EA reuse |
state_58 = { addr_nop,8'h59, rd_reg,rtmph, 1'b1,temp_h,op_lsh, 2'b00,2'b00,4'hE }; // Displacement read |
state_59 = ACCA[1] ? // _..M. |
{ re_wr, 8'h27, src_x, rtmph, 1'b0,dest_x,OPERA, 2'b00,2'b10,4'h1 } // result in memory |
: { addr_nop,8'h00, src_x, rtmph, 1'b1,dest_2,OPERA, 2'b00,2'b00,4'h0 }; // result in Regi |
state_5A = { ADRD2, phsrc2,IRRW2, REGA2, 1'b0,dest_x,op_mov, 2'b00,2'b00,NXRW2 }; // special |
: { addr_nop,8'h00, src_x, rtmph, 1'b1,dest_2,OPERA, 2'b00,2'b00,4'h0 }; // result in Register |
state_5A = { ADRD2, phsrc2,IRRW2, REGA2, 1'b0,dest_x,op_mov, 2'b00,2'b00,NXRW2 }; // special case Mem-Mem |
end |
5'b1_1011 : // INS/INSS : BASE Operand => TEMP, SRC2 read as Double ! RMW not tested (Phase x'6A) |
5'b1_1011 : // INS/INSS : BASE Operand => TEMP, SRC2 read as Double ! RMW not tested (Phase x'6A) but uncritical |
begin |
STATE_0 = ACCA[3] ? // _M... |
{ ADRD1, phsrc1,src_x, REGA1, 1'b0,dest_x,op_mov, 2'b00,2'b00,NXRD1 } |
712,16 → 712,16
state_50 = ACCA[3] ? // _M... |
{ ADRD1, phsrc1,IRRW1, REGA1, 1'b0,dest_x,op_mov, 2'b00,2'b00,NXRD1 } |
: { addr_nop,8'h54, SRC_1, src_x, 1'b1,temp_h,op_zext, 2'b00,2'b00,4'h0 }; |
state_53 = { addr_nop,8'h54, imme, src_x, 1'b1,temp_h,op_zext, 2'b00,2'b00,4'h0 }; // zext( |
state_53 = { addr_nop,8'h54, imme, src_x, 1'b1,temp_h,op_zext, 2'b00,2'b00,4'h0 }; // zext(SRC1) => TEMP |
state_54 = ACCA[1] ? |
{ ADRD2, phsrc2,IRRW2, REGA2, 1'b0,dest_x,op_mov, 2'b00,2'b00,NXRW2 } // here Adr(DEST) = |
: { addr_nop,8'h5A, SRC_2, src_x, 1'b1,temp_l,op_mov, 2'b00,2'b00,imdi }; // Imme./Disp. r |
state_55 = { exoffset,8'h6A, rd_reg,src_x, 1'b0,dest_x,op_mov, 2'b00,2'b00,4'h1 }; // Read S |
{ ADRD2, phsrc2,IRRW2, REGA2, 1'b0,dest_x,op_mov, 2'b00,2'b00,NXRW2 } // here Adr(DEST) => EA |
: { addr_nop,8'h5A, SRC_2, src_x, 1'b1,temp_l,op_mov, 2'b00,2'b00,imdi }; // Imme./Disp. read |
state_55 = { exoffset,8'h6A, rd_reg,src_x, 1'b0,dest_x,op_mov, 2'b00,2'b00,4'h1 }; // Read Source, EA reuse |
state_58 = { addr_nop,8'h55, src_x, src_x, 1'b0,dest_x,op_mov, 2'b00,2'b00,4'h0 }; // |
state_59 = ACCA[1] ? // _..M. |
{ re_wr, 8'h27, rtmph, rtmpl, 1'b0,dest_x,OPERA, 2'b00,2'b10,4'h1 } // result in memory |
: { addr_nop,8'h00, rtmph, rtmpl, 1'b1,dest_2,OPERA, 2'b00,2'b00,4'h0 }; // result in Regi |
state_5A = { addr_nop,8'h68, imme, src_x, 1'b1,temp_1,op_msk, 2'b00,2'b00,4'h0 }; // Mask ge |
: { addr_nop,8'h00, rtmph, rtmpl, 1'b1,dest_2,OPERA, 2'b00,2'b00,4'h0 }; // result in Register |
state_5A = { addr_nop,8'h68, imme, src_x, 1'b1,temp_1,op_msk, 2'b00,2'b00,4'h0 }; // Mask generate |
end |
5'b1_1101 : // INDEX : |
begin |
731,14 → 731,14
state_50 = ACCA[3] ? // _M... |
{ ADRD1, phsrc1,IRRW1, REGA1, 1'b0,dest_x,op_mov, 2'b00,2'b00,NXRD1 } |
: { addr_nop,8'h54, SRC_1, src_x, 1'b1,temp_h,op_zext, 2'b00,2'b00,4'h0 }; |
state_53 = { addr_nop,8'h54, imme, src_x, 1'b1,temp_h,op_zext, 2'b00,2'b00,4'h0 }; // zext( |
state_53 = { addr_nop,8'h54, imme, src_x, 1'b1,temp_h,op_zext, 2'b00,2'b00,4'h0 }; // zext(SRC1) => TEMP_H |
state_54 = ACCA[1] ? |
{ ADRD2, phsrc2,IRRW2, REGA2, 1'b0,dest_x,op_mov, 2'b00,2'b00,NXRW2 } // zext(SRC2) => TE |
{ ADRD2, phsrc2,IRRW2, REGA2, 1'b0,dest_x,op_mov, 2'b00,2'b00,NXRW2 } // zext(SRC2) => TEMP_L |
: { addr_nop,8'h55, SRC_2, src_x, 1'b1,temp_l,op_zext, 2'b00,2'b00,4'h0 }; |
state_55 = { addr_nop,8'h5A, rd_reg,rtmph, 1'b1,temp_h,op_mul, 2'b00,2'b00,4'h0 }; // Multip |
state_55 = { addr_nop,8'h5A, rd_reg,rtmph, 1'b1,temp_h,op_mul, 2'b00,2'b00,4'h0 }; // Multiplication |
state_58 = { addr_nop,8'h55, imme, src_x, 1'b1,temp_l,op_zext, 2'b00,2'b00,4'h0 }; // |
state_59 = { addind, 8'h60, rtmpl, src_x, 1'b0,dest_x,op_mov, 2'b00,2'b00,4'h0 }; // Add of |
state_5A = { addone, 8'h59, rd_reg,rtmph, 1'b0,dest_x,op_mov, 2'b00,2'b00,4'h0 }; // Add of |
state_59 = { addind, 8'h60, rtmpl, src_x, 1'b0,dest_x,op_mov, 2'b00,2'b00,4'h0 }; // Add of Index in EA |
state_5A = { addone, 8'h59, rd_reg,rtmph, 1'b0,dest_x,op_mov, 2'b00,2'b00,4'h0 }; // Add of EA (=+1) |
end |
5'b1_0111 : // DEI + MEI , both read 8B from DEST ! RMW critical ! |
begin |
750,12 → 750,12
: { addr_nop,8'h54, SRC_1, src_x, 1'b1,temp_h,op_mov, 2'b00,2'b00,4'h0 }; |
state_53 = { addr_nop,8'h54, imme, src_x, 1'b1,temp_h,op_mov, 2'b00,2'b00,4'h0 }; |
state_54 = ACCA[1] ? |
{ ADRD2, phsrc2,IRRW2, REGA2, 1'b0,dest_x,op_mov, 2'b00,2'b00,NXRW2 } // here SRC1 => TE |
: { addr_nop,8'h59, rtmph, SRC_2, 1'b0,dest_x,OPERA, 2'b01,2'b00,4'h0 }; // 1. part of Reg |
{ ADRD2, phsrc2,IRRW2, REGA2, 1'b0,dest_x,op_mov, 2'b00,2'b00,NXRW2 } // here SRC1 => TEMP_H |
: { addr_nop,8'h59, rtmph, SRC_2, 1'b0,dest_x,OPERA, 2'b01,2'b00,4'h0 }; // 1. part of Register |
state_55 = dont_care; |
state_58 = size_dw ? |
{ addr_nop,8'h59, rtmph, imme, 1'b0,dest_x,OPERA, 2'b01,2'b00,4'h0 } // D needs 2 accesse |
: { addr_nop,8'h1F, rtmph, imme, 1'b0,dest_x,OPERA, 2'b11,2'b00,4'h0 }; // B+W start at o |
{ addr_nop,8'h59, rtmph, imme, 1'b0,dest_x,OPERA, 2'b01,2'b00,4'h0 } // D needs 2 accesses |
: { addr_nop,8'h1F, rtmph, imme, 1'b0,dest_x,OPERA, 2'b11,2'b00,4'h0 }; // B+W start at once |
state_59 = { addr_nop,8'h1F, src_x, (ACCA[1] ? imme : src_2l), // SRC2 = memory or Reg |
~ACCA[1],dest_2,OPERA, 2'b10,2'b00,4'h0 }; |
state_5A = dont_care; |
762,28 → 762,28
end |
5'b1_1000 : // CHECK |
begin |
STATE_0 = { ADRD1, phsrc1,src_x, REGA1, 1'b0,dest_x,op_mov, 2'b00,2'b00,NXRD1 }; // No Re |
STATE_0 = { ADRD1, phsrc1,src_x, REGA1, 1'b0,dest_x,op_mov, 2'b00,2'b00,NXRD1 }; // No Register ! |
state_50 = { ADRD1, phsrc1,IRRW1, REGA1, 1'b0,dest_x,op_mov, 2'b00,2'b00,NXRD1 }; |
state_53 = { addr_nop,phchk, imme, src_x, 1'b1,temp_h,op_mov, 2'b00,2'b00,4'h0 }; // No Imm |
state_53 = { addr_nop,phchk, imme, src_x, 1'b1,temp_h,op_mov, 2'b00,2'b00,4'h0 }; // No Immediate ! |
state_54 = ACCA[1] ? |
{ ADRD2, phsrc2,IRRW2, REGA2, 1'b0,dest_x,op_mov, 2'b00,2'b00,NXRW2 } |
: ( size_dw ? |
{addr_nop,8'h5A, SRC_2, rtmpl, 1'b0,dest_x,OPERA, 2'b00,2'b10,4'h0 } // Upper Bound - point |
{addr_nop,8'h5A, SRC_2, rtmpl, 1'b0,dest_x,OPERA, 2'b00,2'b10,4'h0 } // Upper Bound - pointer |
: {addr_nop,8'h00, rtmph, SRC_2, 1'b1,chkreg,OPERA, 2'b00,2'b10,4'h0 } ); |
state_55 = { addr_nop,8'h54, imme, src_x, 1'b1,temp_l,op_mov, 2'b00,2'b00,4'h0 }; |
state_58 = size_dw ? |
{ addr_nop,8'h59, imme, src_x, 1'b1,temp_1,op_mov, 2'b00,2'b00,4'h0 } // here SRC2 => TEM |
{ addr_nop,8'h59, imme, src_x, 1'b1,temp_1,op_mov, 2'b00,2'b00,4'h0 } // here SRC2 => TEMP_1 |
: { addr_nop,8'h00, rtmph, imme, 1'b1,chkreg,OPERA, 2'b00,2'b10,4'h0 }; |
state_59 = { addr_nop,8'h5A, rtmp1, rtmpl, 1'b0,dest_x,OPERA, 2'b00,2'b10,4'h0 }; // Upper Bo |
state_59 = { addr_nop,8'h5A, rtmp1, rtmpl, 1'b0,dest_x,OPERA, 2'b00,2'b10,4'h0 }; // Upper Bound - pointer |
state_5A = { addr_nop,8'h00, rtmph, (ACCA[1] ? rtmp1 : SRC_2), |
1'b1,chkreg,OPERA, 2'b00,2'b10,4'h0 }; // pointer - Lower Bound |
end |
5'b1_1100 : // CVTP |
begin |
STATE_0 = { ADRD1, phsrc1,src_x, REGA1, 1'b0,dest_x,op_mov, 2'b00,2'b00,NXRD1 }; // Addre |
STATE_0 = { ADRD1, phsrc1,src_x, REGA1, 1'b0,dest_x,op_mov, 2'b00,2'b00,NXRD1 }; // Address |
state_50 = { ADRD1, phsrc1,IRRW1, REGA1, 1'b0,dest_x,op_mov, 2'b00,2'b00,NXRD1 }; |
state_53 = { addr_nop,8'h54, src_x, src_x, 1'b1,temp_h,op_adr, 2'b00,2'b00,4'h0 }; |
state_54 = { adrcvtp, 8'h73, rtmph, rd_reg,1'b0,dest_x,op_mov, 2'b00,2'b00,4'h0 }; // 8*TEMP |
state_54 = { adrcvtp, 8'h73, rtmph, rd_reg,1'b0,dest_x,op_mov, 2'b00,2'b00,4'h0 }; // 8*TEMP+Offset |
state_55 = dont_care; |
state_58 = dont_care; |
state_59 = dont_care; |
801,11 → 801,11
state_54 = ACCA[1] ? |
{ ADRD2, phsrc2,IRRW2, REGA2, 1'b0,dest_x,op_trul, 2'b00,2'b00,NXRW2 } |
: { addr_nop,8'h5A, src_x, src_x, 1'b0,temp_h,op_trul, 2'b00,2'b00,4'h0 }; |
state_55 = { addr_nop,8'h54, rtmph, imme, 1'b1,temp_h,op_trul, 2'b11,2'b00,4'h0 }; // 2. hal |
state_55 = { addr_nop,8'h54, rtmph, imme, 1'b1,temp_h,op_trul, 2'b11,2'b00,4'h0 }; // 2. half of external SRC1 |
state_58 = { addr_nop,8'h59, rtmph, imme, 1'b0,dest_2,OPERA, 2'b01,2'b00,4'h0 }; |
state_59 = { addr_nop,8'h1F, src_x, (ACCA[1] ? imme : src_2l), |
~ACCA[1],dest_2,OPERA, 2'b10,2'b00,4'h0 }; |
state_5A = { addr_nop,8'h59, rtmph, SRC_2, 1'b0,dest_2,OPERA, 2'b01,2'b00,4'h0 }; // empty cy |
state_5A = { addr_nop,8'h59, rtmph, SRC_2, 1'b0,dest_2,OPERA, 2'b01,2'b00,4'h0 }; // empty cycle for TRUNC => TEMP ! |
end |
5'b01_001 : // SCALBF : RMW critical ! |
begin |
875,7 → 875,7
state_55 = { ADRD2, phsrc2,IRRW2, REGA2, 1'b0,dest_x,op_mov, 2'b00,2'b00,NXRW2 }; |
state_58 = { addr_nop,8'h59, (ACCA[3] ? rtmph : SRC_1), //_M... |
imme, 1'b0,dest_x,op_mull, 2'b01,2'b00,get8b_d }; |
state_59 = { addr_nop,8'h5A, (ACCA[3] ? (ACCA[1] ? rtmpl : imme) : src_1l), (ACCA[1] ? imme : |
state_59 = { addr_nop,8'h5A, (ACCA[3] ? (ACCA[1] ? rtmpl : imme) : src_1l), (ACCA[1] ? imme : src_2l), |
1'b1,temp_h,op_mull, 2'b10,2'b00,4'h0 }; |
state_5A = { addr_nop,8'h61, rtmph, F0_h, 1'b0,temp_h,op_mull, 2'b01,2'b00,4'h0 }; |
end |
916,16 → 916,16
casex (PHASE) |
4'h0 : STATE_GROUP_50 = state_50; |
// Phase 51 : wait for data and Disp2 for External Address mode : part 2 EA = (MOD+4)+4*DISP1 |
4'h1 : STATE_GROUP_50 = {exr11, 8'h52, src_x,imme , 1'b0,dest_x, op_mov, 2'b00,2'b00, 4'b1111} |
4'h1 : STATE_GROUP_50 = {exr11, 8'h52, src_x,imme , 1'b0,dest_x, op_mov, 2'b00,2'b00, 4'b1111}; |
// Phase 52 : Memory-Pointer for Memory Relative and last access External |
4'h2 : STATE_GROUP_50 = {EXR12, 8'h53, IRRW1,imme , 1'b0,dest_x, op_mov, 2'b00,2'b00, 4'b1111} |
4'h2 : STATE_GROUP_50 = {EXR12, 8'h53, IRRW1,imme , 1'b0,dest_x, op_mov, 2'b00,2'b00, 4'b1111}; // atys[0] ! |
4'h3 : STATE_GROUP_50 = state_53; |
4'h4 : STATE_GROUP_50 = state_54; |
4'h5 : STATE_GROUP_50 = state_55; |
// Phase 56 : wait for data and Disp2 for External Address mode : part 2 EA = (MOD+4)+4*DISP1 |
4'h6 : STATE_GROUP_50 = {exr11, 8'h57, src_x,imme , 1'b0,dest_x, op_mov, 2'b00,2'b00, 4'b1111} |
4'h6 : STATE_GROUP_50 = {exr11, 8'h57, src_x,imme , 1'b0,dest_x, op_mov, 2'b00,2'b00, 4'b1111}; |
// Phase 57 : Memory-Pointer for Memory Relative and last access External |
4'h7 : STATE_GROUP_50 = {EXR22, 8'h58, IRRW2,imme , 1'b0,dest_x, op_mov, 2'b00,2'b00, 4'b1111} |
4'h7 : STATE_GROUP_50 = {EXR22, 8'h58, IRRW2,imme , 1'b0,dest_x, op_mov, 2'b00,2'b00, 4'b1111}; // atyd[0] ! |
4'h8 : STATE_GROUP_50 = state_58; |
4'h9 : STATE_GROUP_50 = state_59; |
4'hA : STATE_GROUP_50 = state_5A; |
934,23 → 934,23
|
always @(*) |
casex (PHASE) |
4'h0 : STATE_GROUP_60 = { addr_nop,8'h00, src_x, src_x, 1'b1,chkreg,op_adr, 2'b00,2'b00,4'h0 } |
4'h1 : STATE_GROUP_60 = { addr_nop,8'h62, rtmpl, F0, 1'b1,w_F0_h,op_addl, 2'b10,2'b00,4'h0 } |
4'h2 : STATE_GROUP_60 = { addr_nop,8'h00, src_x, src_x, 1'b0,w_F0_h,op_addl, 2'b00,2'b00,4'h0 } |
4'h3 : STATE_GROUP_60 = { addr_nop,8'h00, rtmph, F0, 1'b1,w_F0, op_addf, 2'b00,2'b00,4'h0 } |
4'h0 : STATE_GROUP_60 = { addr_nop,8'h00, src_x, src_x, 1'b1,chkreg,op_adr, 2'b00,2'b00,4'h0 }; // for INDEX |
4'h1 : STATE_GROUP_60 = { addr_nop,8'h62, rtmpl, F0, 1'b1,w_F0_h,op_addl, 2'b10,2'b00,4'h0 }; // for DOTL |
4'h2 : STATE_GROUP_60 = { addr_nop,8'h00, src_x, src_x, 1'b0,w_F0_h,op_addl, 2'b00,2'b00,4'h0 }; // for DOTL & POLYL ! |
4'h3 : STATE_GROUP_60 = { addr_nop,8'h00, rtmph, F0, 1'b1,w_F0, op_addf, 2'b00,2'b00,4'h0 }; // for DOTF |
4'h4 : STATE_GROUP_60 = ACCA[1] ? // ..M. |
{ ADRD2, phsrc2,IRRW2, REGA2, 1'b0,temp_h,op_mull, 2'b00,2'b00,NXRW2 } |
: { addr_nop,8'h59, SRC_2, rtmph, 1'b0,temp_h,op_addl, 2'b01,2'b00,4'h0 }; // for POLYL |
4'h5 : STATE_GROUP_60 = { addr_nop,8'h59, src_x, src_x, 1'b1,temp_l,op_kust, 2'b00,2'b00,4'h0 } |
4'h6 : STATE_GROUP_60 = { addr_nop,8'h01, rtmph, src_x, 1'b0,dest_x,op_mov, 2'b00,2'b00,4'h0 }; |
4'h7 : STATE_GROUP_60 = { addr_nop,8'hC0, (op_reg_reg[0] ? rtmpl : 7'h00), // Jump to Stri |
4'h5 : STATE_GROUP_60 = { addr_nop,8'h59, src_x, src_x, 1'b1,temp_l,op_kust, 2'b00,2'b00,4'h0 }; // for MOVM/CMPM |
4'h6 : STATE_GROUP_60 = { addr_nop,8'h01, rtmph, src_x, 1'b0,dest_x,op_mov, 2'b00,2'b00,4'h0 }; // for JUMP/JSR/CASE |
4'h7 : STATE_GROUP_60 = { addr_nop,8'hC0, (op_reg_reg[0] ? rtmpl : 7'h00), // Jump to String execution |
src_x, 1'b0,dest_x,OPERA, 2'b00,2'b10,4'h0 }; // LD_OUT set, CMPS F-Flag |
// for INS |
4'h8 : STATE_GROUP_60 = { addr_nop,8'h69, rd_reg,rtmph, 1'b1,temp_h,op_lsh, 2'b00,2'b00,4'h0 }; |
4'h9 : STATE_GROUP_60 = { addr_nop,8'h59, rd_reg,rtmp1, 1'b0,dest_x,op_lsh, 2'b00,2'b00,4'h0 }; |
4'hA : STATE_GROUP_60 = { addr_nop,8'h5A, imme, src_x, 1'b1,temp_l,op_mov, 2'b00,2'b00,imdi }; |
4'h8 : STATE_GROUP_60 = { addr_nop,8'h69, rd_reg,rtmph, 1'b1,temp_h,op_lsh, 2'b00,2'b00,4'h0 }; // SRC1 shift |
4'h9 : STATE_GROUP_60 = { addr_nop,8'h59, rd_reg,rtmp1, 1'b0,dest_x,op_lsh, 2'b00,2'b00,4'h0 }; // Mask shift |
4'hA : STATE_GROUP_60 = { addr_nop,8'h5A, imme, src_x, 1'b1,temp_l,op_mov, 2'b00,2'b00,imdi }; // Imme./Disp. read |
// for CXPD, this State is decoded explicitly in DECODER |
4'hB : STATE_GROUP_60 = { addr_nop,8'h39, imme, src_x, 1'b1,temp_l,op_mov, 2'b00,2'b00,4'h0 }; |
4'hB : STATE_GROUP_60 = { addr_nop,8'h39, imme, src_x, 1'b1,temp_l,op_mov, 2'b00,2'b00,4'h0 }; // pass PC |
default : STATE_GROUP_60 = dont_care; |
endcase |
|
/m32632/trunk/rtl/DATENPFAD.v
35,12 → 35,12
// Modules contained in this file: |
// DATENPFAD the data path of M32632 |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
|
module DATENPFAD( BCLK, BRESET, WREN, IO_READY, LD_DIN, LD_IMME, WR_REG, IC_USER, ACC_FELD, ACC_STAT |
IMME_Q, INFO_AU, LD_OUT, DETOIP, MMU_UPDATE, OPER, PC_ARCHI, PC_ICACHE, RDAA, RDAB, START, WMA |
WRADR, DONE, Y_INIT, WRITE_OUT, READ_OUT, ZTEST, RMW, ACC_DONE, REG_OUT, PTB_SEL, PTB_WR, ACB_ |
ABORT, SAVE_PC, CFG, CINV, DP_Q, IVAR, MCR, PACKET, PC_NEW, PSR, SIZE, STRING, TRAPS, VADR, RW |
module DATENPFAD( BCLK, BRESET, WREN, IO_READY, LD_DIN, LD_IMME, WR_REG, IC_USER, ACC_FELD, ACC_STAT, DIN, DISP, IC_TEX, |
IMME_Q, INFO_AU, LD_OUT, DETOIP, MMU_UPDATE, OPER, PC_ARCHI, PC_ICACHE, RDAA, RDAB, START, WMASKE, |
WRADR, DONE, Y_INIT, WRITE_OUT, READ_OUT, ZTEST, RMW, ACC_DONE, REG_OUT, PTB_SEL, PTB_WR, ACB_ZERO, |
ABORT, SAVE_PC, CFG, CINV, DP_Q, IVAR, MCR, PACKET, PC_NEW, PSR, SIZE, STRING, TRAPS, VADR, RWVFLAG, |
DBG_HIT, DBG_IN, COP_GO, COP_OP, COP_IN, COP_DONE, COP_OUT); |
|
input BCLK; |
171,9 → 171,9
|
always @(posedge BCLK) if (RDAA[7]) BYDIN <= ERGEBNIS; |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// Register Set 1 => SRC1 |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
REGISTER REG_SET_A( |
.BCLK(BCLK), |
.ENWR(ENWR), |
188,9 → 188,9
|
assign SRC1 = SELI_A ? OUT_I : OUT_A; |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// Register Set 2 => SRC2 |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
REGISTER REG_SET_B( |
.BCLK(BCLK), |
.ENWR(ENWR), |
222,9 → 222,9
.AA(BMCODE), |
.DOUT(BMASKE)); |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// The integer data path |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
I_PFAD GANZ_U( |
.FL(FL), |
.BRESET(BRESET), |
258,9 → 258,9
.DISP(DISP[4:0]), |
.RWVFLAG(RWVFLAG)); |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// The address unit |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
ADDR_UNIT ADDR_U( |
.BCLK(BCLK), |
.BRESET(BRESET), |
329,9 → 329,9
.DBG_HIT(DBG_HIT), |
.READ(READ_OUT) ); |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// The long operation unit |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
DP_FPU DOUBLE_U( |
.BCLK(BCLK), |
.FL(FL), |
362,9 → 362,9
.COP_GO(COP_GO), |
.COP_OUT(COP_OUT)); |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// The single precision floating point unit |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
SP_FPU SINGLE_U( |
.FL(FL), |
.BCLK(BCLK), |
/m32632/trunk/rtl/CACHE_LOGIK.v
40,13 → 40,13
// 5. CA_MATCH Cache tag match detector |
// 6. DCACHE_SM Data cache state machine |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// |
// 1. DEBUG_AE Debug unit for address compare in data cache |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module DEBUG_AE ( DBG_IN, READ, WRITE, USER, VIRTUELL, ACC_OK, VADR_R, MMU_Q, ENBYTE, DBG_HIT ); |
|
input [40:2] DBG_IN; |
89,11 → 89,11
|
endmodule |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// |
// 2. MMU_UP MMU memory update and initalization controller |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module MMU_UP ( BCLK, BRESET, NEW_PTB, PTB1, IVAR, WR_MRAM, VADR, VADR_R, MVALID, UPDATE, |
WE_MV, WADR_MV, RADR_MV, DAT_MV, NEW_PTB_RUN ); |
|
119,10 → 119,10
assign WE_MV = wr_flag | WR_MRAM | IVAR; // write on falling edge BCLK |
assign RADR_MV = run_over ? count : VADR; |
assign WADR_MV = wr_flag ? (count - 4'b0001) : VADR_R; |
assign DAT_MV = wr_flag ? {MVALID[31:16],new_val} : UPDATE; // Only the matching entries are clear |
assign DAT_MV = wr_flag ? {MVALID[31:16],new_val} : UPDATE; // Only the matching entries are cleared : PTB0/PTB1 |
|
// [31:16] Address-Space memory, [15:0] Valid memory |
assign new_val = neue_ptb ? (PTB1 ? (MVALID[15:0] & ~MVALID[31:16]) : (MVALID[15:0] & MVALID[31:16] |
assign new_val = neue_ptb ? (PTB1 ? (MVALID[15:0] & ~MVALID[31:16]) : (MVALID[15:0] & MVALID[31:16])) : 16'h0; |
|
always @(posedge BCLK or negedge BRESET) |
if (!BRESET) neue_ptb <= 1'b0; |
140,12 → 140,12
|
endmodule |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// |
// 3. DCA_CONTROL Data cache valid memory update and initalization controller |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module DCA_CONTROL ( BCLK, MCLK, BRESET, CUPDATE, DRAM_ACC, CA_SET, HIT_ALL, WRCFG, VADR_R, UPDATE, |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module DCA_CONTROL ( BCLK, MCLK, BRESET, CUPDATE, DRAM_ACC, CA_SET, HIT_ALL, WRCFG, VADR_R, UPDATE, INVAL_A, WRITE, |
WCTRL, KILL, WRCRAM0, WRCRAM1, WE_CV, WADR_CV, DAT_CV, INIT_CA_RUN, WRSET0, WRSET1 ); |
|
input BCLK; |
160,7 → 160,7
input [23:0] UPDATE; |
input INVAL_A; |
input WRITE; |
input [1:0] WCTRL; // [1] : Read Burst Signal from DRAM controller, MCLK aligned. [0] : Cache inh |
input [1:0] WCTRL; // [1] : Read Burst Signal from DRAM controller, MCLK aligned. [0] : Cache inhibit |
input KILL; // valid Ram must be updated because of collision ... or CINV |
|
output WRCRAM0,WRCRAM1; |
228,17 → 228,17
// 2 : 001 000 6 : 101 010 |
// 3 : 010 010 7 : 110 011 |
// 4 : 011 000 8 : 111 100 |
always @(posedge MCLK) if (zero) refer <= {(count == 3'd7),((count == 3'd5) | (count[1:0] == 2'b10) |
always @(posedge MCLK) if (zero) refer <= {(count == 3'd7),((count == 3'd5) | (count[1:0] == 2'b10)),(count[2] & ~count[0])}; |
|
always @(posedge MCLK) wr_puls <= (count == refer) | WRCFG; |
|
endmodule |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// |
// 4. MMU_MATCH MMU virtual address match detector |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module MMU_MATCH ( USER, READ, WRITE, RMW, MCR_FLAGS, MVALID, VADR_R, MMU_VA, IVAR, |
VIRTUELL, MMU_HIT , UPDATE, PROT_ERROR, CI, SEL_PTB1 ); |
|
289,19 → 289,19
|
assign VIRTUELL = USER ? MCR_FLAGS[0] : MCR_FLAGS[1]; |
|
assign adr_space = IVAR[1] ? IVAR[0] : (MCR_FLAGS[2] & USER); // adr_space = IVARx ? 1 or 0 : DualS |
assign adr_space = IVAR[1] ? IVAR[0] : (MCR_FLAGS[2] & USER); // adr_space = IVARx ? 1 or 0 : DualSpace & TU |
|
assign as_sorte = ((MVALID[31:16] & maske) != 16'h0); |
|
assign match = (VADR_R[31:20] == MMU_VA[31:20]) & (adr_space == as_sorte) & ((MVALID[15:0] & maske) |
assign match = (VADR_R[31:20] == MMU_VA[31:20]) & (adr_space == as_sorte) & ((MVALID[15:0] & maske) != 16'h0000); |
|
assign alles_ok = match & ( ~WRITE | MMU_VA[17] ) & ~PROT_ERROR; // Modified - Flag : reload the PT |
assign alles_ok = match & ( ~WRITE | MMU_VA[17] ) & ~PROT_ERROR; // Modified - Flag : reload the PTE |
|
// if MMU_HIT = 0 then there is no Write-Buffer access abd no update of cache ! |
assign MMU_HIT = zugriff ? ( VIRTUELL ? alles_ok : 1'b1 ) : 1'b0 ; // MMU off : then always HIT |
|
assign val_bits = IVAR[1] ? (MVALID[15:0] & (match ? ~maske : 16'hFFFF)) : (MVALID[15:0] | maske); |
assign as_bits = IVAR[1] ? MVALID[31:16] : (adr_space ? (MVALID[31:16] | maske) : (MVALID[31:16] & |
assign as_bits = IVAR[1] ? MVALID[31:16] : (adr_space ? (MVALID[31:16] | maske) : (MVALID[31:16] & ~maske)); |
|
assign UPDATE = {as_bits,val_bits}; |
|
321,12 → 321,12
|
endmodule |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// |
// 5. CA_MATCH Cache tag match detector |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module CA_MATCH ( CVALID, IOSEL, ADDR, TAG0, TAG1, CFG, WRITE, MMU_HIT, CI, INVAL_L, KDET, ENDRAM, D |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module CA_MATCH ( CVALID, IOSEL, ADDR, TAG0, TAG1, CFG, WRITE, MMU_HIT, CI, INVAL_L, KDET, ENDRAM, DC_ILO, |
CA_HIT, CA_SET, UPDATE, IO_SPACE, USE_CA, WB_ACC, KILL ); |
|
input [23:0] CVALID; |
380,7 → 380,7
assign CA_HIT = ((valid_0 & match_0) | (valid_1 & match_1)) & ~DC_ILO & CFG[0]; |
|
// which SET is written in cache miss ? If both are valid the last used is not taken |
assign select = (valid_1 & valid_0) ? ~((CVALID[23:16] & maske) != 8'h00) : valid_0; // Last-used f |
assign select = (valid_1 & valid_0) ? ~((CVALID[23:16] & maske) != 8'h00) : valid_0; // Last-used field = CVALID[23:16] |
|
assign CA_SET = CA_HIT ? (valid_1 & match_1) : select; |
|
387,9 → 387,9
assign clear = INVAL_L | KDET; // INVAL_L is from CINV |
|
assign update_0 = CA_SET ? CVALID[7:0] : (clear ? (CVALID[7:0] & ~maske) : (CVALID[7:0] | maske)); |
assign update_1 = CA_SET ? (clear ? (CVALID[15:8] & ~maske) : (CVALID[15:8] | maske)) : CVALID[15:8 |
assign update_1 = CA_SET ? (clear ? (CVALID[15:8] & ~maske) : (CVALID[15:8] | maske)) : CVALID[15:8]; |
|
assign lastinfo = CA_HIT ? (CA_SET ? (CVALID[23:16] | maske) : (CVALID[23:16] & ~maske)) : CVALID[2 |
assign lastinfo = CA_HIT ? (CA_SET ? (CVALID[23:16] | maske) : (CVALID[23:16] & ~maske)) : CVALID[23:16]; |
|
assign UPDATE = {lastinfo,update_1,update_0}; |
|
402,16 → 402,16
|
endmodule |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// |
// 6. DCACHE_SM Data cache state machine |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module DCACHE_SM ( BCLK, BRESET, IO_SPACE, MDONE, IO_READY, MMU_HIT, CA_HIT, READ, WRITE, ZTEST, RMW |
USE_CA, PTB_WR, PTB_SEL, SEL_PTB1, CPU_OUT, USER, PROT_ERROR, WB_ACC, ENWR, ADR_EQU, IC_PREQ, |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module DCACHE_SM ( BCLK, BRESET, IO_SPACE, MDONE, IO_READY, MMU_HIT, CA_HIT, READ, WRITE, ZTEST, RMW, CAPDAT, VADR_R, IC_VA, |
USE_CA, PTB_WR, PTB_SEL, SEL_PTB1, CPU_OUT, USER, PROT_ERROR, WB_ACC, ENWR, ADR_EQU, IC_PREQ, FILLRAM, ICTODC, |
RWVAL, VIRTUELL, |
DRAM_ACC, DRAM_WR, IO_ACC, IO_RD, IO_WR, PTE_MUX, PD_MUX, PKEEP, PTE_ADR, PTE_DAT, HIT_ALL, A |
ABORT, PROTECT, IACC_STAT, ABO_LEVEL1, WR_MRAM, CUPDATE, AUX_DAT, NEW_PTB, PTB_ONE, MMU_DIN, |
DRAM_ACC, DRAM_WR, IO_ACC, IO_RD, IO_WR, PTE_MUX, PD_MUX, PKEEP, PTE_ADR, PTE_DAT, HIT_ALL, ACC_OK, |
ABORT, PROTECT, IACC_STAT, ABO_LEVEL1, WR_MRAM, CUPDATE, AUX_DAT, NEW_PTB, PTB_ONE, MMU_DIN, IC_SIGS, KOMUX, |
KDET, DMA_MUX, HLDA, RWVFLAG, PTE_STAT ); |
|
input BCLK; |
518,7 → 518,7
assign mmu_hit_i = MMU_HIT & ~ZTEST; |
|
// WB_ACC is a successful WRITE access, ICTODC[0] is coherent Logik release : >=3 entries in FIFO |
assign wr_req = WB_ACC & ((ENWR & ICTODC[0]) | (DRAM_WR & ADR_EQU)); // release done by DRAM signal |
assign wr_req = WB_ACC & ((ENWR & ICTODC[0]) | (DRAM_WR & ADR_EQU)); // release done by DRAM signal ENWR |
|
assign rd_ende = CA_HIT | rd_rdy; // CA_HIT only when Cache activ ! |
|
541,7 → 541,7
or dma // DMA Request |
or dma_run ) // DMA running |
// #_# #_# #_# #_# |
casex ({zugriff,PROT_ERROR,IO_SPACE,io_busy,mmu_hit_i,READ,wr_req,rd_ende,DRAM_ACC,pte_acc,IC_PREQ |
casex ({zugriff,PROT_ERROR,IO_SPACE,io_busy,mmu_hit_i,READ,wr_req,rd_ende,DRAM_ACC,pte_acc,IC_PREQ,dma,dma_run}) |
// MMU Miss : PTE load from memory , valid too if WRITE and M=0 |
13'b10_xx_0xxx_x0_x_x0 : new_state = 7'b0001010; // start PTE access |
// IO-Address selected : external access starts if not busy because of WRITE |
552,7 → 552,7
13'b10_0x_101x_x0_x_x0 : new_state = 7'b0000100; |
// PTE Request ICACHE , IO access with WRITE is stored - parallel DRAM access possible |
13'b0x_xx_xxxx_x0_1_00 : new_state = 7'b0101010; // no access |
13'b10_0x_1101_x0_1_x0 : new_state = 7'b0101010; // if successful READ a PTE access can happen i |
13'b10_0x_1101_x0_1_x0 : new_state = 7'b0101010; // if successful READ a PTE access can happen in parallel |
// DMA access. Attention : no IO-Write access in background and no ICACHE PTE access ! |
13'b0x_x0_xxxx_xx_0_10 : new_state = 7'b1000000; // DMA access is started |
default : new_state = 7'b0; |
570,12 → 570,12
|
assign do_zt = ZTEST & ~icp_acc; |
|
// 0 is pass , 1 is blocked. RWVAL[0] is 1 if WRVAL. Level 1 can only be blocked, otherwise ABORT o |
always @(posedge BCLK) if (mem_done) rwv_bit <= level2 ? ~(cap_dat[2] & (~RWVAL[0] | cap_dat[1])) : |
// 0 is pass , 1 is blocked. RWVAL[0] is 1 if WRVAL. Level 1 can only be blocked, otherwise ABORT or Level 2 is following. |
always @(posedge BCLK) if (mem_done) rwv_bit <= level2 ? ~(cap_dat[2] & (~RWVAL[0] | cap_dat[1])) : 1'b1; |
|
assign RWVFLAG = VIRTUELL & rwv_bit; |
|
assign zt_ok = mem_done & (RWVAL[1] ? (~cap_dat[2] | (RWVAL[0] & ~cap_dat[1]) | level2) // Level 2 |
assign zt_ok = mem_done & (RWVAL[1] ? (~cap_dat[2] | (RWVAL[0] & ~cap_dat[1]) | level2) // Level 2 always ok |
: (cap_dat[0] & ~prot_i & level2) ); // "normal" access |
|
// PTE access logic, normal state machine |
614,11 → 614,11
assign level1 = ~pstate[1]; |
assign level2 = pstate[1]; |
|
assign valid_a = (ZTEST & RWVAL[1]) ? (cap_dat[2] & (cap_dat[1] | ~RWVAL[0]) & ~cap_dat[0] & level1 |
assign valid_a = (ZTEST & RWVAL[1]) ? (cap_dat[2] & (cap_dat[1] | ~RWVAL[0]) & ~cap_dat[0] & level1) |
: ~cap_dat[0]; // not do_zt because of icp_acc in ABORT |
|
assign ABORT = mem_done & valid_a & ~icp_acc; |
assign PROTECT = ((mem_done & prot_i & ~icp_acc) | PROT_ERROR) & ~(ZTEST & RWVAL[1]); // no Protec |
assign PROTECT = ((mem_done & prot_i & ~icp_acc) | PROT_ERROR) & ~(ZTEST & RWVAL[1]); // no Protection-Error at RDVAL/WRVAL |
|
assign IACC_STAT[1] = mem_done & ~cap_dat[0] & icp_acc; |
assign IACC_STAT[2] = level1; |
640,7 → 640,7
assign pte_puls = mem_done & pte_acc & ~pstate[1]; |
assign PTE_STAT = {(pte_puls & icp_acc),(pte_puls & ~icp_acc)}; // only for statistic |
|
assign PD_MUX = ((pstate == 3'd4) & mem_done & valid & ~refer) // switch data-MUX, write level 1 |
assign PD_MUX = ((pstate == 3'd4) & mem_done & valid & ~refer) // switch data-MUX, write level 1 too |
| ((pstate == 3'd6) & mem_done & valid & (~refer | modi)) // write level 2 |
| (((pstate == 3'd5) | (pstate == 3'd7)) & ~pte_run_wr); |
|
650,7 → 650,7
|
assign PKEEP = (pstate == 3'd6) | ((pstate == 3'd7) & ~pte_run_wr); // keep the DRAM address |
|
// If there is a PTE still in the data cache it must be deleted. If MMU Bits are set by the pte eng |
// If there is a PTE still in the data cache it must be deleted. If MMU Bits are set by the pte engine a following |
// READ would deliver wrong data if cache hit. Therefore access of the Tags. |
always @(posedge BCLK or negedge BRESET) |
if (!BRESET) ko_state <= 3'b000; |
670,7 → 670,7
assign KOMUX = ko_state[1] | DMA_MUX; |
assign KDET = ko_state[0] | dma_kdet; |
|
assign HIT_ALL = MMU_HIT & CA_HIT & run_dc & ~pte_acc; // for Update "Last-Set" , MMU_HIT contains |
assign HIT_ALL = MMU_HIT & CA_HIT & run_dc & ~pte_acc; // for Update "Last-Set" , MMU_HIT contains ZUGRIFF |
|
always @(posedge BCLK or negedge BRESET) |
if (!BRESET) card_flag <= 1'b0; |
680,7 → 680,7
|
always @(posedge BCLK) rd_rdy <= card_flag & MDONE; |
|
// The cache RAM can not provide fast enough the data after an Update. In this case a secondary dat |
// The cache RAM can not provide fast enough the data after an Update. In this case a secondary data path is activated |
assign AUX_DAT = rd_rdy; |
|
// DRAM interface : |
697,13 → 697,13
if (IO_ACC) IO_WR <= WRITE; else IO_WR <= IO_WR & ~IO_READY & BRESET; |
end |
|
assign io_busy = IO_RD | IO_WR | rd_done; // access is gone in next clock cycle, therefore blocked |
assign io_busy = IO_RD | IO_WR | rd_done; // access is gone in next clock cycle, therefore blocked with "rd_done" |
|
always @(posedge BCLK) rd_done <= IO_RD & IO_READY; // For READ one clock later for data to come th |
always @(posedge BCLK) rd_done <= IO_RD & IO_READY; // For READ one clock later for data to come through |
|
assign dma = ICTODC[2]; // external request HOLD after FF in ICACHE |
|
always @(posedge BCLK) dma_run <= (dma_go | (dma_run & dma)) & BRESET; // stops the data access unt |
always @(posedge BCLK) dma_run <= (dma_go | (dma_run & dma)) & BRESET; // stops the data access until HOLD becomes inactive |
|
assign HLDA = ~(ICTODC[1] & dma_run); // Signal for system that the CPU has stopped accesses |
|
713,7 → 713,7
// global feedback to ADDR_UNIT, early feedback to Op-Dec : you can continue |
|
assign ACC_OK = ZTEST ? (~VIRTUELL | zt_ok) |
: (IO_SPACE ? ((IO_ACC & WRITE) | rd_done) : (wr_dram | (READ & MMU_HIT & rd_ende & run_dc)) |
: (IO_SPACE ? ((IO_ACC & WRITE) | rd_done) : (wr_dram | (READ & MMU_HIT & rd_ende & run_dc)) ); |
|
// PTB1 and PTB0 |
|
733,7 → 733,7
assign virtual_adr = pte_sel ? IC_VA : VADR_R; |
|
// The 2 Address-LSB's : no full access : USE_CA = 0 |
assign PTE_ADR = rd_level2 ? {CAPDAT[27:12],virtual_adr[21:12],2'b00} : {ptb10,virtual_adr[31:22],2 |
assign PTE_ADR = rd_level2 ? {CAPDAT[27:12],virtual_adr[21:12],2'b00} : {ptb10,virtual_adr[31:22],2'b00}; |
|
// PTE_DAT[8] is used for update of MMU_RAM. |
assign pte_dat_8 = (level2 & WRITE & write_ok & ~icp_acc) | CAPDAT[8]; |
757,7 → 757,7
3'b00_x : pl_dat = 2'b00; |
endcase |
|
always @(USER or pl_dat) // is used if no PTE update is neccesary for M-Bit if writing is not allow |
always @(USER or pl_dat) // is used if no PTE update is neccesary for M-Bit if writing is not allowed |
casex ({USER,pl_dat}) |
3'b1_11 : write_ok = 1'b1; |
3'b0_1x : write_ok = 1'b1; |
/m32632/trunk/rtl/example.v
35,7 → 35,7
// Modules contained in this file: |
// example Your first system with the M32632 CPU |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
|
module example ( CLK, RESET_N, NMI_N, INT_N, IN_REG, OUT_REG); |
|
/m32632/trunk/rtl/M32632.v
35,7 → 35,7
// Modules contained in this file: |
// M32632 The top level of M32632 |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
|
module M32632( BCLK, MCLK, WRCFG, BRESET, NMI_N, INT_N, STATUS, ILO, STATSIGS, |
IO_WR, IO_RD, IO_A, IO_BE, IO_DI, IO_Q, IO_READY, |
172,9 → 172,9
wire DBG_HIT; |
wire [40:2] DBG_IN; |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// The Data Cache |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
DCACHE ARMS( |
.MCLK(MCLK), |
.BCLK(BCLK), |
234,9 → 234,9
.RWVAL(RWVAL), |
.RWVFLAG(RWVFLAG)); |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// The Datapath |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
DATENPFAD STOMACH( |
.WREN(WREN_REG), |
.BRESET(BRESET), |
298,9 → 298,9
.COP_GO(COP_GO), |
.COP_OUT(COP_OUT)); |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// The Instruction Cache |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
ICACHE LEGS( |
.MCLK(MCLK), |
.BCLK(BCLK), |
343,9 → 343,9
.STOP_CINV(STOP_CINV), |
.IO_A(I_IOA)); |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// The Control Unit |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
STEUERUNG BRAIN( |
.BCLK(BCLK), |
.BRESET(BRESET), |
397,9 → 397,9
.ILO(ILO_SIG), |
.RWVAL(RWVAL)); |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// The Input/Output Interface |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
IO_SWITCH ISWITCH( |
.I_IORD(I_IORD), |
.D_IOWR(D_IOWR), |
422,9 → 422,9
.DCWACC({DC_WR,DC_ACC}), |
.STATUS(STATUS)); |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// The Statistic Signal Generator |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
MAKE_STAT MKSTAT( |
.BCLK(BCLK), |
.READ(READ), |
/m32632/trunk/rtl/SP_FPU.v
38,13 → 38,13
// 3. SFPU_MUL Single Precision Floating Point Multiplier |
// 4. SP_FPU Top Level of Single Precision Floating Point Unit |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// |
// 1. ADDSUB Adder and Subtractor for 36 bit |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module ADDSUB (dataa, datab, add_sub, result); |
|
input [35:0] dataa,datab; |
55,11 → 55,11
|
endmodule |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// |
// 2. SFPU_ADDSUB Single Precision Floating Point Adder/Subtractor and Converter |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module SFPU_ADDSUB ( SRC1, SRC2, NZEXP, BWD, SELECT, OUT, IOUT, CMPRES ); |
|
input [31:0] SRC1,SRC2; // Input data |
130,7 → 130,7
assign madiff = {1'b0,SRC2[22:0]} - {1'b0,SRC1[22:0]}; // Difference of Mantissas |
|
// if exdiff = 0 the shifter to the right is not needed ! |
assign variante = (exdiff[8:1] == 8'h00) | (exdiff == 9'h1FF) | SELECT[1]; // MUX at the end, ROUND |
assign variante = (exdiff[8:1] == 8'h00) | (exdiff == 9'h1FF) | SELECT[1]; // MUX at the end, ROUND/TRUNC/MOViF uses case 1 |
|
// ++++++++++++++++++++++++++ 1. case works on MOViF +++++++++++++++++++++++++++++++++++++++ |
|
169,7 → 169,7
|
// CMPF : 1. step : what happend if Invalid Operand occurs - no Flag update ! |
|
assign CMPRES[1] = ~CMPRES[0] & (switch ? ~sign1 : sign2); // see table above : N-Bit=1 if SRC1 > |
assign CMPRES[1] = ~CMPRES[0] & (switch ? ~sign1 : sign2); // see table above : N-Bit=1 if SRC1 > SRC2 |
assign CMPRES[0] = (SRC1 == SRC2) | (~NZEXP[2] & ~NZEXP[1]); // Z-Bit : SRC1=SRC2, +0.0 = -0.0 |
|
// ++++++++++++++++++++++++++++++++++ |
234,7 → 234,7
wire [32:9] pipe1; // numbering special for Right Shifter |
wire [4:0] shift; |
|
// the difference between SRC1 and SRC2 is bigger/equal 4:1 => no Barrelshifter after ADDSUB neccess |
// the difference between SRC1 and SRC2 is bigger/equal 4:1 => no Barrelshifter after ADDSUB neccessary |
|
assign vswitch = exdiff[8]; // exchange ? |
|
242,10 → 242,10
assign exdiff12 = {1'b0,SRC1[30:23]} - {1'b0,SRC2[30:23]}; // caclulate already |
assign shift2 = (exdiff12[7:5] != 3'h0) ? 5'h1F : exdiff12[4:0]; |
|
assign muxsrc2 = vswitch ? {SRC1[30:23],1'b1,SRC1[22:0]} : {SRC2[30:23],1'b1,SRC2[22:0]}; // Includ |
assign muxsrc2 = vswitch ? {SRC1[30:23],1'b1,SRC1[22:0]} : {SRC2[30:23],1'b1,SRC2[22:0]}; // Including exponent |
assign muxsrc1 = vswitch ? {NZEXP[2],SRC2[22:0]} : {NZEXP[1],SRC1[22:0]}; |
|
assign pipe1 = SELECT[1] ? (ganzklein ? 24'h0 : {NZEXP[1],SRC1[22:0]}) : muxsrc1; // Feeding in R.T |
assign pipe1 = SELECT[1] ? (ganzklein ? 24'h0 : {NZEXP[1],SRC1[22:0]}) : muxsrc1; // Feeding in R.T.F. |
|
assign shift = SELECT[1] ? rexdiff[4:0] : (vswitch ? shift2 : shift1); |
|
277,7 → 277,7
always @(SELECT or sign1 or brshifte or inex or ganzklein) |
casex (SELECT[3:2]) |
2'b00 : car_ry = sign1 ^ ((brshifte[2:0] == 3'b110) | (inex == 2'b11)); // ROUNDLi |
2'b1x : car_ry = sign1 ? (~ganzklein & (inex == 2'b00)) : 1'b0; // +numbers like TRUNCLi, -num |
2'b1x : car_ry = sign1 ? (~ganzklein & (inex == 2'b00)) : 1'b0; // +numbers like TRUNCLi, -numbers round to "-infinity" |
default : car_ry = sign1; // TRUNCLi , simple cut |
endcase |
|
313,7 → 313,7
.datab({9'h0,brshifte[32:7],lsb}), .add_sub(addflag), |
.result(vresult) ); |
|
assign eminus1 = muxsrc2[31:24] - 8'h01; // a greater Underflow can not exist, because minimal Expo |
assign eminus1 = muxsrc2[31:24] - 8'h01; // a greater Underflow can not exist, because minimal Exponent = 0..01 |
|
// Case ADD : Bit 23 : LSB of exponent |
assign vadd_q = (muxsrc2[24] != vresult[27]) ? {vresult[35:3],(vresult[2:0] != 3'b000)} |
320,7 → 320,7
: {vresult[35:27],vresult[25:2],(vresult[1:0] != 2'b00)} ; |
|
// Case SUB : Bit 26 : "hidden" MSB of mantissa |
assign vsub_q = vresult[26] ? {vresult[35:27], vresult[25:2],(vresult[1:0] != 2'b00)} // like t |
assign vsub_q = vresult[26] ? {vresult[35:27], vresult[25:2],(vresult[1:0] != 2'b00)} // like the vadd_q "0" case |
: {vresult[35],eminus1,vresult[24:0]} ; |
|
// SELECT[1] has here no meaning |
333,11 → 333,11
|
endmodule |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// |
// 3. SFPU_MUL Single Precision Floating Point Multiplier |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module SFPU_MUL ( SRC1, SRC2, MRESULT, NZEXP, OUT); |
|
input [31:0] SRC1,SRC2; // only exponent of input data used |
366,12 → 366,12
|
endmodule |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// |
// 4. SP_FPU Top Level of Single Precision Floating Point Unit |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module SP_FPU (BCLK, OPCODE, SRC1, SRC2, FSR, MRESULT, BWD, FL, FP_OUT, I_OUT, TT_SP, SP_CMP, SP_MUX |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module SP_FPU (BCLK, OPCODE, SRC1, SRC2, FSR, MRESULT, BWD, FL, FP_OUT, I_OUT, TT_SP, SP_CMP, SP_MUX, LD_FSR, UP_SP); |
|
input BCLK; // is not used ! |
input [7:0] OPCODE; |
414,7 → 414,7
|
assign SP_MUX = select[3] & (select[1:0] != 2'b11) & FL; // Output multiplexer |
|
assign LD_FSR = (OPCODE[7:4] == 4'h9) & (OPCODE[3:1] == 3'b001); // LFSR does only Double (accordin |
assign LD_FSR = (OPCODE[7:4] == 4'h9) & (OPCODE[3:1] == 3'b001); // LFSR does only Double (according datasheet NS32016) |
assign UP_SP = select[3] & FL; // All FPU opcodes of SP_FPU |
assign op_cmp = (OPCODE == 8'hB2) & FL; |
|
/m32632/trunk/rtl/DECODER.v
35,12 → 35,12
// Modules contained in this file: |
// DECODER Instruction Decoding and Flow Control |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
|
module DECODER ( BCLK, BRESET, INT_N, NMI_N, ANZ_VAL, OPREG, CFG, PSR, ACC_DONE, DC_ABORT, IC_ABORT, |
module DECODER ( BCLK, BRESET, INT_N, NMI_N, ANZ_VAL, OPREG, CFG, PSR, ACC_DONE, DC_ABORT, IC_ABORT, ACB_ZERO, DONE, |
PC_SAVE, STRING, INIT_DONE, ILL, UNDEF, TRAPS, IC_READ, STOP_CINV, |
GENSTAT, DISP, IMME_Q, DISP_BR, USED, NEW, LOAD_PC, NEXT_PCA, RDAA, RDAB, OPER, START, LD_OUT, |
INFO_AU, ACC_FELD, WREN, WRADR, WMASKE, WR_REG, DETOIP, MMU_UPDATE, RESTART, STOP_IC, RWVAL, EN |
GENSTAT, DISP, IMME_Q, DISP_BR, USED, NEW, LOAD_PC, NEXT_PCA, RDAA, RDAB, OPER, START, LD_OUT, LD_DIN, LD_IMME, |
INFO_AU, ACC_FELD, WREN, WRADR, WMASKE, WR_REG, DETOIP, MMU_UPDATE, RESTART, STOP_IC, RWVAL, ENA_HK, ILO, COP_OP ); |
|
input BCLK,BRESET; |
input INT_N,NMI_N; // external inputs |
61,7 → 61,7
input STOP_CINV; // not to mix it up with STOP_IC |
|
output [2:0] GENSTAT; |
output [31:0] DISP,IMME_Q,DISP_BR; // three main data busses : Displacement, Immediate and Displace |
output [31:0] DISP,IMME_Q,DISP_BR; // three main data busses : Displacement, Immediate and Displacement for Branch |
output [2:0] USED; |
output NEW; |
output LOAD_PC; |
205,7 → 205,7
wire [4:0] src1_addr,src2_addr; |
wire [6:0] usp_1,usp_2; |
wire [33:0] tos_oper; |
wire [18:0] adrd1,exr11,exr12,adrd2,adwr2,exr22,exw22,re_wr,st_src,st_src2,st_dest,st_len,st_trde,s |
wire [18:0] adrd1,exr11,exr12,adrd2,adwr2,exr22,exw22,re_wr,st_src,st_src2,st_dest,st_len,st_trde,st_trs2; |
wire [7:0] phrd1,phrd2,phwr2; |
wire [6:0] rega1,irrw1,rega2,irrw2; |
wire [3:0] nxrd1,nxrw2; |
274,7 → 274,7
parameter save_sp = 19'b10_0000_0000_1_0000_0000; // u.a. RET : update of Stack |
parameter next_po = 19'b10_1011_0010_1_0000_1011; // RESTORE middle |
parameter dispmin = 19'b10_0010_0000_0_0100_0011; // Reuse for ENTER |
parameter rmod_rxp = 19'b10_1001_0000_1_0000_0100; // MODUL+0 read : SB , SP Update , therefore no |
parameter rmod_rxp = 19'b10_1001_0000_1_0000_0100; // MODUL+0 read : SB , SP Update , therefore no LDEA |
parameter rmod_rtt = 19'b10_1001_0000_0_0000_0100; // MODUL+0 read : SB , no LDEA |
parameter rmod_4 = 19'b10_1011_0000_0_0001_0100; // MODUL+4 read : Link Table Base |
parameter rmod_8 = 19'b10_1011_0000_0_0010_0100; // MODUL+8 read : Program Base |
284,7 → 284,7
parameter pop_ru = 19'b10_1010_0010_0_0000_1011; // RXP : EA Phase MOD POP |
parameter rd_icu = 19'b00_1001_0000_0_1100_0010; // Read ICU : Byte of fix address |
parameter get_vec = 19'b10_1001_0000_0_01xx_0000; // Read Exception-Vector : Index Exception No. |
parameter get_veci = 19'b10_1001_0110_0_0000_0000; // Read Exception-Vector : Index external Interr |
parameter get_veci = 19'b10_1001_0110_0_0000_0000; // Read Exception-Vector : Index external Interrupt |
parameter load_ea = 19'b10_0010_0000_0_0000_0000; // used for store of TEAR and MSR |
parameter save_msr = 19'b10_0010_0001_0_0000_0000; // used for store of TEAR and MSR |
parameter ivar_adr = 19'b10_0000_0100_0_0000_0010; // only pass SRC1 |
316,7 → 316,7
parameter op_zex = 11'h076; // Zero Extension for ICU Vector - is also used at String Option "T" |
parameter op_cop = 8'hDD; // Coprozessor Opcode |
|
// ++++++++++++++++++++++++++ The switch logic for the state machine ++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++ The switch logic for the state machine +++++++++++++++++++++++++++++ |
|
always @(ANZ_VAL) |
case (ANZ_VAL) |
370,7 → 370,7
assign dvz_trap = TRAPS[1]; |
assign fpu_trap = TRAPS[0]; |
|
always @(posedge BCLK) nmi_reg <= {nmi_reg[0],NMI_N}; // one clock sync and than falling edge detec |
always @(posedge BCLK) nmi_reg <= {nmi_reg[0],NMI_N}; // one clock sync and than falling edge detection |
|
always @(posedge BCLK or negedge BRESET) |
if (!BRESET) nmi_flag <= 1'b0; |
378,7 → 378,7
|
always @(posedge BCLK) int_flag <= PSR[11] & ~INT_N; // one clock to synchronise |
|
assign stop = (int_flag | nmi_flag) & PHASE_0 & ~stop_d; // neccesary if FPU_TRAP and INT at t |
assign stop = (int_flag | nmi_flag) & PHASE_0 & ~stop_d; // neccesary if FPU_TRAP and INT at the same time |
assign interrupt = (int_flag | nmi_flag) & (~PHASE_0 | stop_d); |
|
always @(posedge BCLK or negedge BRESET) |
400,9 → 400,9
assign abort = DC_ABORT | iabort; |
|
// that is the end of String loops where interrupts are checked : 8'hC7 & 8'hCF |
assign string_ende = (phase_reg[7:4] == 4'hC) & (phase_reg[2:0] == 3'b111); // attention : 8'hCF do |
assign string_ende = (phase_reg[7:4] == 4'hC) & (phase_reg[2:0] == 3'b111); // attention : 8'hCF does not exist |
|
always @(posedge BCLK) if (PHASE_0 || string_ende) type_nmi <= nmi_flag; // during processing kept |
always @(posedge BCLK) if (PHASE_0 || string_ende) type_nmi <= nmi_flag; // during processing kept stable |
|
assign svc_flag = (OPREG[7:0] == 8'hE2) & valid[0]; // Vector 5 : 0101 , Illegal Vector 4 : 0100 |
assign bpt_flag = (OPREG[7:0] == 8'hF2) & valid[0]; // Vector 8 : 1000 , Undefined Vec. 10 : 1010 |
419,12 → 419,12
assign exception = interrupt | svc_flag | bpt_flag | ILL | UNDEF | trac_flag | abbruch; |
|
// a TRACE Exception is done before the opcode execution |
assign misc_vectors = trac_flag ? 4'h9 : {(bpt_flag | UNDEF),(svc_flag | ILL),UNDEF,svc_flag}; // t |
assign misc_vectors = trac_flag ? 4'h9 : {(bpt_flag | UNDEF),(svc_flag | ILL),UNDEF,svc_flag}; // the vectors are exclusiv |
|
always @(posedge BCLK) |
if (PHASE_0 || abbruch) // ABORTs, fpu_trap, dvz_trap + ovf_flag can happen every time |
begin |
exc_vector <= abbruch ? (abbruch2 ? {ovf_flag,(dvz_trap | ovf_flag),~ovf_flag,(fpu_trap | ovf_fl |
exc_vector <= abbruch ? (abbruch2 ? {ovf_flag,(dvz_trap | ovf_flag),~ovf_flag,(fpu_trap | ovf_flag)} : 4'hE) |
: (interrupt ? {3'b0,nmi_flag} : misc_vectors); // misc_vectors is default |
end |
else |
432,19 → 432,19
else |
if (interrupt && string_ende) exc_vector <= {3'b0,nmi_flag}; |
|
assign psr_code[2] = ~psr_code[1]; // Absicht : codiert das Sichern des PSR bei Exception-Entr |
assign psr_code[1] = abort | ILL | UNDEF | trac_flag; // enable for reseting the P-Bit during write |
assign psr_code[2] = ~psr_code[1]; // Absicht : codiert das Sichern des PSR bei Exception-Entry |
assign psr_code[1] = abort | ILL | UNDEF | trac_flag; // enable for reseting the P-Bit during write of PSR to stack |
assign psr_code[0] = (interrupt & ~fpu_trap) | abort; // enable for reseting the I-Bit of new PSR |
|
// valid codes are x'89 to x'8F |
assign op_psr = {8'b0_00_1000_1,psr_code}; // is used during first clock cylce after exception, is |
assign op_psr = {8'b0_00_1000_1,psr_code}; // is used during first clock cylce after exception, is transfered as OPCODE to I_PFAD |
|
// Specialitiies : ABORT stores address & flags , the Interrrupts read vectors : all is used in big |
// Specialitiies : ABORT stores address & flags , the Interrrupts read vectors : all is used in big CASE |
assign abo_int = (exc_vector == 4'h2) | (exc_vector[3:1] == 3'b000); |
assign ai_next = (exc_vector == 4'h2) ? {load_ea,8'h84,4'h0} : {rd_icu,8'h82,4'h1}; |
|
assign save_pc = {7'b10_0010_0,dia_flag,7'b00_0_0000,dia_flag,3'b001}; // Exception : PC_ARCHI => E |
assign no_trap = ~fpu_trap & ~ovf_flag & ~dbg_flag; // suppresion of WREN and LD_OUT[1] and ADDR_UN |
assign save_pc = {7'b10_0010_0,dia_flag,7'b00_0_0000,dia_flag,3'b001}; // Exception : PC_ARCHI => EA, special case DIA |
assign no_trap = ~fpu_trap & ~ovf_flag & ~dbg_flag; // suppresion of WREN and LD_OUT[1] and ADDR_UNIT operation |
|
// ++++++++++++++++++++++++++ Overflow Trap ++++++++++++++ |
|
451,7 → 451,7
always @(posedge BCLK) |
if (ovf_flag || !PSR[4]) ovf_pipe <= 4'd0; |
else |
if (PHASE_0) ovf_pipe <= {ovf_pipe[2],(ovf_op & op_ok),ovf_pipe[0],(ovf2_op & op_ok)}; // V-Bit s |
if (PHASE_0) ovf_pipe <= {ovf_pipe[2],(ovf_op & op_ok),ovf_pipe[0],(ovf2_op & op_ok)}; // V-Bit switches on |
|
assign ovf_op = ( ((OPREG[6:2] == 5'b000_11) // ADDQi |
| (OPREG[3:2] == 2'b00)) & (OPREG[1:0] != 2'b10)) // ADDi,ADDCi,SUBi,SUBCi |
458,7 → 458,7
| ((OPREG[7:0] == 8'h4E) & OPREG[13] & (OPREG[11:10] == 2'b00)) // NEGi,ABSi |
| ((OPREG[7:0] == 8'hEE) & ~OPREG[10]); // CHECKi |
|
assign ovf2_op = ((OPREG[6:2] == 5'b100_11) & (OPREG[1:0] != 2'b10)) // ACBi, these overflows have |
assign ovf2_op = ((OPREG[6:2] == 5'b100_11) & (OPREG[1:0] != 2'b10)) // ACBi, these overflows have no FLAG |
| ((OPREG[13:10] == 4'h1) & (OPREG[7:0] == 8'h4E)) // ASHi |
| ( OPREG[13] & (OPREG[11] == OPREG[10]) & (OPREG[7:0] == 8'hCE)); // MULi,DEIi,QUOi,DIVi |
|
472,15 → 472,15
|
assign pc_match = dbg_en & TRAPS[3] & PHASE_0 & ~exception; // TRAPS[3] is only combinatorical |
|
always @(posedge BCLK) dbg_trap <= (pc_match | (addr_cmp & PHASE_0)) & TRAPS[5]; // TRAPS[5] = Enab |
always @(posedge BCLK) dbg_trap <= (pc_match | (addr_cmp & PHASE_0)) & TRAPS[5]; // TRAPS[5] = Enable Trap |
|
always @(posedge BCLK) addr_cmp <= TRAPS[4] | (addr_cmp & ~PHASE_0); // TRAPS[4] = CAR HIT |
|
// ++++++++++++++++++++++++++ Special case String Abort ++++++++++++++ |
|
// Flags cleared if entry and exit of string operation and during Abort sequence, not valid for MO |
// Flags cleared if entry and exit of string operation and during Abort sequence, not valid for MOVM/CMPM |
// special case UNTIL/WHILE : reset if exit (op_feld_reg[17] = 1 = UNTIL) |
assign clr_sflag = (phase_reg == 8'hC0) | (phase_reg == 8'hC7) | (phase_reg == 8'hC8) | (phase_ |
assign clr_sflag = (phase_reg == 8'hC0) | (phase_reg == 8'hC7) | (phase_reg == 8'hC8) | (phase_reg == 8'h81) |
| (((phase_reg == 8'hD7) | (phase_reg == 8'hDF)) & ~(STRING[3] ^ op_feld_reg[17])) ; |
assign set_src = (phase_reg == 8'hC1) | (phase_reg == 8'hC9); |
assign set_dest = (phase_reg == 8'hC4) | (phase_reg == 8'hCC); |
497,7 → 497,7
|
// ++++++++++++++++++++++++++ The one byte opcodes +++++++++++++++++++ |
|
// The one byte opcodes have a special case : one byte opcode but the second byte should be valid t |
// The one byte opcodes have a special case : one byte opcode but the second byte should be valid too |
// Used with SAVE, RESTORE, ENTER and EXIT with their reg list. |
// The advantage is that the reg list is store in op_feld_reg. |
|
550,18 → 550,18
dia_op <= OPREG[6]; // only difference between DIA and WAIT is important |
end |
|
always @(posedge BCLK) dia_flag <= dia_op & (phase_reg == 8'h88); // special case DIA compared to W |
always @(posedge BCLK) dia_flag <= dia_op & (phase_reg == 8'h88); // special case DIA compared to WAIT : Addr DIA to Stack |
|
always @(posedge BCLK) // Format 1 opcodes write always DWord to reg, the same is true for Exceptio |
always @(posedge BCLK) // Format 1 opcodes write always DWord to reg, the same is true for Exceptions |
if (PHASE_0 || abbruch) format1 <= (valid[0] & (OPREG[3:0] == 4'h2)) | exception; |
else |
if (flag_flag || (interrupt && string_ende)) format1 <= 1'b1; |
|
// Branch etc. CXP CXPD |
assign store_pc = (phase_reg == 8'd1) | (phase_reg == 8'h37) | (phase_reg == 8'h6B); // only save i |
assign store_pc = (phase_reg == 8'd1) | (phase_reg == 8'h37) | (phase_reg == 8'h6B); // only save in DIN Reg of DATENPFAD |
assign jump = (ex_br_op[0] & branch) | (acb_reg & ~ACB_ZERO) | ex_br_op[1]; |
|
always @(posedge BCLK) ldpc_phase <= (phase_reg == 8'h3E) // PC load at CXP/Traps , all one clock |
always @(posedge BCLK) ldpc_phase <= (phase_reg == 8'h3E) // PC load at CXP/Traps , all one clock cycle guaranted |
| (phase_reg == 8'h43) // PC load at RXP |
| ((phase_reg == 8'h49) & reti_flag) // PC load at RETI |
| (phase_reg == 8'h4E) // PC load at RETT |
569,7 → 569,7
| (phase_reg == 8'h7B); // PC load at DE = Direct Exception |
|
assign NEW = ((phase_reg == 8'd1) & jump & di_stat[0]) | LOAD_PC; |
assign LOAD_PC = ((phase_reg == 8'h2B) & di_stat[0]) // only one pulse, but DISP must be ok => di_s |
assign LOAD_PC = ((phase_reg == 8'h2B) & di_stat[0]) // only one pulse, but DISP must be ok => di_stat[0] (RET) |
| ldpc_phase; |
|
assign no_modul = de_flag ? {1'b0,dest_x} : {1'b1,modul[5:0]}; |
580,9 → 580,9
assign larger = PSR[2]; |
assign carry_psr = PSR[0]; |
|
assign rett_exc = ~reti_flag & (phase_reg == 8'h4B); // special case RETT : Stack can change during |
assign rett_exc = ~reti_flag & (phase_reg == 8'h4B); // special case RETT : Stack can change during opcode |
always @(posedge BCLK) phase_exc <= (phase_reg == 8'h80); // 1. Exception phase |
always @(negedge BCLK) if (PHASE_0 || phase_exc || rett_exc) s_user <= PSR[9]; // Select Bit for St |
always @(negedge BCLK) if (PHASE_0 || phase_exc || rett_exc) s_user <= PSR[9]; // Select Bit for Stack, delayed update |
always @(negedge BCLK) |
if (PHASE_0 || phase_exc) s_mod <= {PSR[9],~PSR[9]}; |
else |
617,13 → 617,13
else |
if (ACC_DONE || init_rlist) rpointer <= reg_nr; |
|
REG_LIST scanner ( .DIN(op_feld_reg[22:15]), .INIT(init_rlist), .IPOS(rpointer), .VALID(save_reg), |
REG_LIST scanner ( .DIN(op_feld_reg[22:15]), .INIT(init_rlist), .IPOS(rpointer), .VALID(save_reg), .OPOS(reg_nr) ); |
|
assign saver = {4'h0,reg_nr}; |
|
always @(posedge BCLK) if (ACC_DONE || init_rlist) resto <= {3'h0,~reg_nr}; // EXIT and RESTORE hav |
always @(posedge BCLK) if (ACC_DONE || init_rlist) resto <= {3'h0,~reg_nr}; // EXIT and RESTORE have the list mirrored : R0...R7 |
|
// ++++++++++++++++++++++++++ Processing of Displacement and Immediate Operand ++++++++++++++++++ |
// ++++++++++++++++++++++++++ Processing of Displacement and Immediate Operand +++++++++++++++++++ |
|
always @(posedge BCLK or negedge BRESET) // Flag for DISP and IMME access |
if (!BRESET) dim_feld[3] <= 1'b0; |
638,15 → 638,15
// special case QWORD, last term for security |
always @(posedge BCLK) qw_flag <= dim_feld[0] & ACC_DONE & (ACC_FELD[13:12] == 2'b11) & ~qw_flag; |
|
assign LD_IMME = (dim_feld[3] & (dim_feld[2:1] != 2'b11)) | short_op | store_pc; // Data multiplexe |
assign LD_DIN = (di_stat[0] & dim_feld[3] & (dim_feld[2:1] != 2'b11)) // Enable for DIN Regist |
| (ACC_DONE & dim_feld[0]) | qw_flag | short_op | store_pc; // next not possible : i.e. imme |
assign LD_IMME = (dim_feld[3] & (dim_feld[2:1] != 2'b11)) | short_op | store_pc; // Data multiplexer |
assign LD_DIN = (di_stat[0] & dim_feld[3] & (dim_feld[2:1] != 2'b11)) // Enable for DIN Register |
| (ACC_DONE & dim_feld[0]) | qw_flag | short_op | store_pc; // next not possible : i.e. immediate and disp parallel |
assign ld_disp = (dim_feld[3:1] == 3'b111); // Enable for DISP Register |
|
// Signal to ADDR_UNIT , only Displacement critical |
assign disp_ok = ld_disp ? di_stat[0] : 1'b1; |
|
always @(dim_feld or OPREG or valid or ANZ_VAL) // Bit 0 is "Data ok", the upper 3 bits are for USE |
always @(dim_feld or OPREG or valid or ANZ_VAL) // Bit 0 is "Data ok", the upper 3 bits are for USED |
casex ({dim_feld[2:1],OPREG[7:6]}) |
4'b00_xx : di_stat = {3'b001,valid[0]}; |
4'b01_xx : di_stat = {3'b010,(valid[1] & valid[0])}; |
696,7 → 696,7
if (!BRESET) new_spsel <= 1'b0; |
else new_spsel <= spupd | (new_spsel & ~PHASE_0 & ~fpu_trap & ~dvz_trap); |
|
always @(posedge BCLK) upd_info <= PHASE_0 & new_spsel; // one clock cycle earlier a change occurs, |
always @(posedge BCLK) upd_info <= PHASE_0 & new_spsel; // one clock cycle earlier a change occurs, i.e. ADDF TOS,F0 => fpu_trap |
|
assign do_xor = fpu_trap ? upd_info : (PHASE_0 & new_spsel); |
|
706,7 → 706,7
if (do_xor) stack_sel <= stack_sel ^ s_mod; |
|
// Special case RETT |
always @(posedge BCLK) if (!phase_reg[1]) old_su <= s_user; // is tested in state x'49 and used in |
always @(posedge BCLK) if (!phase_reg[1]) old_su <= s_user; // is tested in state x'49 and used in x'4B |
assign ttstak = {1'b0,((old_su == PSR[9]) ^ stack_sel[PSR[9]]),3'b110,PSR[9],1'b1}; |
|
// ++++++++++++++ 2 byte opcodes +++++++++++++++++ |
729,13 → 729,13
// [9:8] original BWD : B=00/W=01/D=11 |
// [7:0] opcode: operation code |
|
assign valid_size = (OPREG[1:0] != 2'b10) & (valid[1:0] == 2'b11); // valid size + valid OPREG-Byte |
assign valid_size = (OPREG[1:0] != 2'b10) & (valid[1:0] == 2'b11); // valid size + valid OPREG-Bytes |
|
assign hzl_a = (OPREG[1:0] == 2'b11) ? 2'b10 : OPREG[1:0]; // length field recoded |
assign hzl_b = {1'b0,OPREG[1:0]}; // standard Length field |
assign hzr_a = {3'b000,OPREG[13:11]}; // SRC2 or SRC1 regfield |
assign hzr_b = {3'b000,OPREG[8:6]}; // SRC2 regfield |
assign hzr_s = {((OPREG[15:11] == 5'h17) ^ stack_sel[s_user]),3'b110,s_user,1'b1}; // USER or SUPER |
assign hzr_s = {((OPREG[15:11] == 5'h17) ^ stack_sel[s_user]),3'b110,s_user,1'b1}; // USER or SUPERVISOR Stack, TOS special case |
// Special case LPR & SPR regfield: |
always @(OPREG or stack_sel or s_user) |
casex ({OPREG[10:7]}) |
745,55 → 745,55
default : hzr_c = {2'b01,OPREG[10:7]}; |
endcase |
|
// Unfortunately SETCFG must be implemented : it is transformed to a two byte opcode with one byte |
// Unfortunately SETCFG must be implemented : it is transformed to a two byte opcode with one byte IMM operand |
assign setcfg = (OPREG[13:0] == 14'h0B0E) & (valid[1:0] == 2'b11); |
|
always @(*) |
casex ({setcfg,OPREG[10:2]}) |
// Short-Op Codes , ACB is an ADD with following jump |
10'b0xxxx_x0011 : op2_feld = {6'o11,3'o3,6'hxx,hzr_a,hzl_a,hzl_a,5'h14,OPREG[15:11],2'b00,hzl_b,8' |
10'b0xxxx_00111 : op2_feld = {6'o11,3'o2,6'hxx,hzr_a,hzl_a,hzl_a,5'h14,OPREG[15:11],2'b00,hzl_b,8' |
10'b0xxxx_01011 : op2_feld = {6'o11,3'o1,hzr_c,hzr_a,hzl_a,hzl_a,5'h00,OPREG[15:11],2'b00,hzl_b,8' |
10'b0xxxx_x0011 : op2_feld = {6'o11,3'o3,6'hxx,hzr_a,hzl_a,hzl_a,5'h14,OPREG[15:11],2'b00,hzl_b,8'h40}; // ADDQ ACB |
10'b0xxxx_00111 : op2_feld = {6'o11,3'o2,6'hxx,hzr_a,hzl_a,hzl_a,5'h14,OPREG[15:11],2'b00,hzl_b,8'h41}; // CMPQ |
10'b0xxxx_01011 : op2_feld = {6'o11,3'o1,hzr_c,hzr_a,hzl_a,hzl_a,5'h00,OPREG[15:11],2'b00,hzl_b,8'h45}; // SPR |
// Scond is moving the SHORT operand in the Integer area as condition field |
10'b0xxxx_01111 : op2_feld = {6'o11,3'o1,6'hxx,hzr_a,hzl_a,hzl_a,5'h14,OPREG[15:11],2'b00,hzl_b,8' |
10'b0xxxx_10111 : op2_feld = {6'o11,3'o1,6'hxx,hzr_a,hzl_a,hzl_a,5'h14,OPREG[15:11],2'b00,hzl_b,8' |
10'b0xxxx_11011 : op2_feld = {6'o11,3'o1,hzr_a,hzr_c,hzl_a,2'b10,OPREG[15:11],5'h00,2'b00,hzl_b,8' |
10'b0xxxx_01111 : op2_feld = {6'o11,3'o1,6'hxx,hzr_a,hzl_a,hzl_a,5'h14,OPREG[15:11],2'b00,hzl_b,8'h7A}; // Format 7, A=(UNDEF) |
10'b0xxxx_10111 : op2_feld = {6'o11,3'o1,6'hxx,hzr_a,hzl_a,hzl_a,5'h14,OPREG[15:11],2'b00,hzl_b,8'h45}; // MOVQ |
10'b0xxxx_11011 : op2_feld = {6'o11,3'o1,hzr_a,hzr_c,hzl_a,2'b10,OPREG[15:11],5'h00,2'b00,hzl_b,8'h76}; // LPR => MOVZiD |
// Format 3 opcodes : |
10'b00x10_11111 : op2_feld = {6'o11,3'o1,hzr_a,6'h1D,hzl_a,hzl_a,OPREG[15:11],5'h00,2'b00,hzl_b,4' |
10'b0x100_11111 : op2_feld = {6'o61,3'o1,hzr_a,hzr_b,hzl_a,hzl_a,OPREG[15:11],5'h00,2'b10,hzl_b,4' |
10'b01110_11111 : op2_feld = {6'o11,3'o1,hzr_a,hzr_b,hzl_a,hzl_a,OPREG[15:11],5'h00,2'b10,hzl_b,4' |
10'b00x10_11111 : op2_feld = {6'o11,3'o1,hzr_a,6'h1D,hzl_a,hzl_a,OPREG[15:11],5'h00,2'b00,hzl_b,4'h3,OPREG[10:7]}; // BIC/SPSR |
10'b0x100_11111 : op2_feld = {6'o61,3'o1,hzr_a,hzr_b,hzl_a,hzl_a,OPREG[15:11],5'h00,2'b10,hzl_b,4'h3,OPREG[10:7]}; // JUMP/JSR |
10'b01110_11111 : op2_feld = {6'o11,3'o1,hzr_a,hzr_b,hzl_a,hzl_a,OPREG[15:11],5'h00,2'b10,hzl_b,4'h3,OPREG[10:7]}; // CASE |
// Format 4 opcodes : main group |
10'b0xxxx_xxxx0 : op2_feld = {6'o11,3'o3,hzr_a,hzr_b,hzl_a,hzl_a,OPREG[15:6], 2'b00,hzl_b,4'h4,OP |
10'b0xxxx_x0001 : op2_feld = {6'o11,3'o2,hzr_a,hzr_b,hzl_a,hzl_a,OPREG[15:6], 2'b00,hzl_b,4'h4,OP |
10'b0xxxx_x0101 : op2_feld = {6'o11,3'o1,hzr_a,hzr_b,hzl_a,hzl_a,OPREG[15:6], 2'b00,hzl_b,4'h4,OP |
10'b0xxxx_xxxx0 : op2_feld = {6'o11,3'o3,hzr_a,hzr_b,hzl_a,hzl_a,OPREG[15:6], 2'b00,hzl_b,4'h4,OPREG[5:2]}; |
10'b0xxxx_x0001 : op2_feld = {6'o11,3'o2,hzr_a,hzr_b,hzl_a,hzl_a,OPREG[15:6], 2'b00,hzl_b,4'h4,OPREG[5:2]}; //CMP no WR |
10'b0xxxx_x0101 : op2_feld = {6'o11,3'o1,hzr_a,hzr_b,hzl_a,hzl_a,OPREG[15:6], 2'b00,hzl_b,4'h4,OPREG[5:2]}; //MOV no 2.Op |
10'b0xxxx_x1101 : op2_feld = (OPREG[10:9] == 2'b00) ? // target is Register => standard flow |
{6'o11,3'o2,hzr_a,hzr_b,hzl_a,2'bxx,OPREG[15:6], 2'b00,hzl_b,4'h4,OPREG[5:2]} // TBIT |
: {6'o14,3'o2,hzr_a,hzr_b,hzl_a,2'b00,OPREG[15:6], 2'b10,hzl_b,4'h4,OPREG[5:2]}; |
// ADJSPi |
10'b01010_11111 : op2_feld = {6'o11,3'o3,hzr_a,hzr_s,hzl_a,2'b10,OPREG[15:11],5'h00,2'b00,hzl_b,8' |
10'b01010_11111 : op2_feld = {6'o11,3'o3,hzr_a,hzr_s,hzl_a,2'b10,OPREG[15:11],5'h00,2'b00,hzl_b,8'h48}; // is a SUBD |
// ADDR, length field not valid |
10'b0xxxx_x1001 : op2_feld = {6'o61,3'o1,hzr_a,hzr_b,hzl_a,hzl_a,OPREG[15:6], 2'b00,hzl_b,8'h49}; |
10'b00000_11111 : op2_feld = {6'o71,3'o1,hzr_a,hzr_b,hzl_a,hzl_a,OPREG[15:11],5'h00,2'b10,hzl_b,4' |
10'b00000_11111 : op2_feld = {6'o71,3'o1,hzr_a,hzr_b,hzl_a,hzl_a,OPREG[15:11],5'h00,2'b10,hzl_b,4'h3,OPREG[10:7]}; // CXPD no Opcode |
// SETCFG => MOV Befehl , SRC1 is genrated for 32 bit , target is Register temp_h |
10'b1xxxx_xxxxx : op2_feld = {40'b001001_001_000000_111101_00_10_10100_00000_00_011, 8'h76}; |
default : op2_feld = {40'hxx_xxxx_xxxx,4'hA,4'hx}; |
endcase |
|
assign op_2byte = (valid_size | setcfg) & ~op2_feld[7]; // it must be for sure shown "Invalid Opcod |
assign op_2byte = (valid_size | setcfg) & ~op2_feld[7]; // it must be for sure shown "Invalid Opcode" |
|
// Special case : the quick opcodes with the exception SPR and LPR |
assign short_op = ((~OPREG[5]) | (OPREG[6:4] == 3'b011)) & (OPREG[3:2] == 2'b11) & valid_size & PHA |
assign short_op = ((~OPREG[5]) | (OPREG[6:4] == 3'b011)) & (OPREG[3:2] == 2'b11) & valid_size & PHASE_0; |
always @(posedge BCLK) if (PHASE_0) short_op_reg <= short_op; |
assign short_def = PHASE_0 ? short_op : short_op_reg; // for the big state machine |
assign op_sho = (OPREG[6:4] == 3'b011) ? 11'h07A : op_mov; // Special case Scond at Index as Dest. |
assign op_sho = (OPREG[6:4] == 3'b011) ? 11'h07A : op_mov; // Special case Scond at Index as Dest. , used only in Phase 0 |
|
// 2. special case ACB |
assign acb_op = (OPREG[6:2] == 5'h13) & valid_size; |
always @(posedge BCLK) if (PHASE_0) acb_reg <= acb_op; |
assign acb_flag = PHASE_0 ? acb_op : acb_reg; |
assign goacb = acb_flag ? 8'h28 : 8'h00; // x'28 = 40 , wait jump at REG operation - short-op speci |
assign goacb = acb_flag ? 8'h28 : 8'h00; // x'28 = 40 , wait jump at REG operation - short-op special case |
|
// 3. special case load of PSR and Init-Done opcodes : because of U bit in PSR a restart must follo |
// 3. special case load of PSR and Init-Done opcodes : because of U bit in PSR a restart must follow, |
// CINV and LMR PTB must wait until Init-Done and than Restart. |
// All variants of LPR and BIC/S have an extra cycle due to TRACE operation |
always @(OPREG) |
826,10 → 826,10
|
always @(posedge BCLK) if (PHASE_0) jsr_flag <= (OPREG[10:2] == 9'b1100_11111); // JSR : for PUSH |
always @(posedge BCLK) // Bit opcodes to Register and EXT:SRC1 / INS:SRC2 |
if (PHASE_0) bit_reg <= ((OPREG[3] ? ((OPREG[7:6] == 2'd0) ? OPREG[23:22] : OPREG[18:17]) : OPREG |
always @(posedge BCLK) if (PHASE_0) exin_cmd <= (~OPREG[10] & (OPREG[6:0] == 7'h2E)) & (valid[2:0] |
if (PHASE_0) bit_reg <= ((OPREG[3] ? ((OPREG[7:6] == 2'd0) ? OPREG[23:22] : OPREG[18:17]) : OPREG[10:9]) == 2'b00); |
always @(posedge BCLK) if (PHASE_0) exin_cmd <= (~OPREG[10] & (OPREG[6:0] == 7'h2E)) & (valid[2:0] == 3'b111); |
always @(posedge BCLK) if (PHASE_0) extract <= ~OPREG[7]; |
always @(posedge BCLK) if (PHASE_0) inss_op <= (OPREG[13:10] == 4'h2) & (OPREG[7:0] == 8'hCE) & (va |
always @(posedge BCLK) if (PHASE_0) inss_op <= (OPREG[13:10] == 4'h2) & (OPREG[7:0] == 8'hCE) & (valid[2:0] == 3'b111); // INSS |
|
// ++++++++++++++ 3 byte opcodes +++++++++++++++++ |
|
857,11 → 857,11
assign hdo_e = {3'b011,OPREG[10]}; // Special codes for LOGB and SCALB due to DP_OUT datapath |
// Definitions of length |
assign hdl_a = {1'b0,OPREG[9:8]}; // i size, is used in OPER |
assign hdl_b = (OPREG[9:8] == 2'b11) ? 2'b10 : OPREG[9:8]; // recode length field, is used in ACC f |
assign hdl_b = (OPREG[9:8] == 2'b11) ? 2'b10 : OPREG[9:8]; // recode length field, is used in ACC field |
assign hdl_c = OPREG[10:8]; // FL + BWD |
assign hdl_d = {1'b1,~hdx_a}; // length FP |
assign hdl_e = {OPREG[8],2'bxx}; // BWD don't care |
assign hdl_f = (OPREG[18:17] == 2'b00) ? OPREG[9:8] : {OPREG[8],~(OPREG[9] ^ OPREG[8])}; // exclusi |
assign hdl_f = (OPREG[18:17] == 2'b00) ? OPREG[9:8] : {OPREG[8],~(OPREG[9] ^ OPREG[8])}; // exclusiv for DEI |
assign hdl_g = {(OPREG[9:8] != 2'b00),(OPREG[9:8] == 2'b00)}; // exclusiv for EXT/EXTS base operand |
assign hdl_h = {(OPREG[9:8] != 2'b00),(OPREG[9:8] != 2'b01)}; // exclusiv for CHECK bound operand |
// Register definitions |
876,48 → 876,48
|
always @(*) |
casex (OPREG[13:3]) |
11'b1000_xx_1100x : op3_feld = {6'o11,3'o3,hdr_a,hdr_b, hdl_b,hdl_b,OPREG[23:14],2'b00,hdl_a,4'h |
11'b000x_xx_0100x : op3_feld = {6'o11,3'o3,hdr_a,hdr_b, 2'b00,hdl_b,OPREG[23:14],2'b00,hdl_a,4'h |
11'b0101_xx_0100x : op3_feld = {6'o11,3'o3,hdr_a,hdr_b, 2'b00,hdl_b,OPREG[23:14],2'b00,hdl_a,4'h |
11'b1x0x_xx_0100x : op3_feld = {6'o11,3'o1,hdr_a,hdr_b, hdl_b,hdl_b,OPREG[23:14],2'b00,hdl_a,4'h |
11'b010x_xx_1100x : op3_feld = {6'o11,3'o1,hdr_a,hdr_b, hdl_b,2'b01,OPREG[23:14],2'b00,hdl_a,4'h |
11'b011x_xx_1100x : op3_feld = {6'o11,3'o1,hdr_a,hdr_b, hdl_b,2'b10,OPREG[23:14],2'b00,hdl_a,4'h |
11'b0001_xx_0110x : op3_feld = {6'o11,3'o3,hdr_a,hdr_b, hdl_b,2'b00,OPREG[23:14],2'b00,hdl_a,4'h |
11'b1000_xx_1100x : op3_feld = {6'o11,3'o3,hdr_a,hdr_b, hdl_b,hdl_b,OPREG[23:14],2'b00,hdl_a,4'h7,hdo_a}; // MULi |
11'b000x_xx_0100x : op3_feld = {6'o11,3'o3,hdr_a,hdr_b, 2'b00,hdl_b,OPREG[23:14],2'b00,hdl_a,4'h6,hdo_a}; // ROTi,ASHi |
11'b0101_xx_0100x : op3_feld = {6'o11,3'o3,hdr_a,hdr_b, 2'b00,hdl_b,OPREG[23:14],2'b00,hdl_a,4'h6,hdo_a}; // LSHi |
11'b1x0x_xx_0100x : op3_feld = {6'o11,3'o1,hdr_a,hdr_b, hdl_b,hdl_b,OPREG[23:14],2'b00,hdl_a,4'h6,hdo_a}; // NEGi,NOTi,ABSi,COMi |
11'b010x_xx_1100x : op3_feld = {6'o11,3'o1,hdr_a,hdr_b, hdl_b,2'b01,OPREG[23:14],2'b00,hdl_a,4'h7,hdo_a}; // MOVX/ZiW |
11'b011x_xx_1100x : op3_feld = {6'o11,3'o1,hdr_a,hdr_b, hdl_b,2'b10,OPREG[23:14],2'b00,hdl_a,4'h7,hdo_a}; // MOVX/ZiD |
11'b0001_xx_0110x : op3_feld = {6'o11,3'o3,hdr_a,hdr_b, hdl_b,2'b00,OPREG[23:14],2'b00,hdl_a,4'h8,hdo_c}; // FFSi |
// Floating Point opcodes |
11'b000x_xx_0011x : op3_feld = {6'o11,hdo_b,2'b01,hdr_a,hdr_d, hdl_b,hdl_d,OPREG[23:14],2'b00,hd |
11'b010x_xx_0011x : op3_feld = {6'o11, 3'o5,hdr_e,hdr_f, 2'b11,2'b10,OPREG[23:14],2'b00,hd |
11'b011x_xx_0011x : op3_feld = {6'o11, 3'o5,hdr_e,hdr_f, 2'b10,2'b11,OPREG[23:14],2'b00,hd |
11'b10xx_xx_0011x : op3_feld = {6'o11,hdo_b,2'b01,hdr_c,hdr_b, hdl_d,hdl_b,OPREG[23:14],2'b00,hd |
11'b111x_xx_00111 : op3_feld = {6'o11,hdo_b,2'b01,hdr_c,hdr_b, hdl_d,hdl_b,OPREG[23:14],2'b00,hd |
11'b111x_xx_00110 : op3_feld = {6'o11, 3'o5,hdr_c,hdr_b, hdl_d,hdl_b,OPREG[23:14],2'b00,hd |
11'b0x00_0x_10111 : op3_feld = {6'o11,hdo_b,2'b11,hdr_c,hdr_d, hdl_d,hdl_d,OPREG[23:14],2'b00,hd |
11'bxx00_0x_10110 : op3_feld = {6'o11, 3'o7,hdr_c,hdr_d, hdl_d,hdl_d,OPREG[23:14],2'b00,hd |
11'b1000_0x_10111 : op3_feld = {6'o11, 3'o7,hdr_c,hdr_d, hdl_d,hdl_d,OPREG[23:14],2'b00,hd |
11'b1100_0x_10111 : op3_feld = {6'o11,hdo_b,2'b11,hdr_c,hdr_d, hdl_d,hdl_d,OPREG[23:14],2'b00,hd |
11'b0010_0x_1011x : op3_feld = {6'o11,hdo_b,2'b10,hdr_c,hdr_d, hdl_d,hdl_d,OPREG[23:14],2'b00,hd |
11'b0001_0x_10111 : op3_feld = {6'o11, 3'o1,hdr_c,hdr_d, hdl_d,hdl_d,OPREG[23:14],2'b00,hd |
11'bx101_0x_10111 : op3_feld = {6'o11, 3'o1,hdr_c,hdr_d, hdl_d,hdl_d,OPREG[23:14],2'b00,hd |
11'b001x_11_00111 : op3_feld = {6'o11,3'o1,hdr_a,fsr_r, 2'b10,2'b10,OPREG[23:19],5'b0,2'b00,3'o3 |
11'b110x_11_00111 : op3_feld = {6'o11,3'o1,fsr_r,hdr_b, 2'b10,2'b10,5'b0,OPREG[18:14],2'b00,3'o3 |
11'b000x_xx_0011x : op3_feld = {6'o11,hdo_b,2'b01,hdr_a,hdr_d, hdl_b,hdl_d,OPREG[23:14],2'b00,hdl_c,4'h9,hdo_a}; // MOVif |
11'b010x_xx_0011x : op3_feld = {6'o11, 3'o5,hdr_e,hdr_f, 2'b11,2'b10,OPREG[23:14],2'b00,hdl_c,4'h9,hdo_a}; // MOVLF |
11'b011x_xx_0011x : op3_feld = {6'o11, 3'o5,hdr_e,hdr_f, 2'b10,2'b11,OPREG[23:14],2'b00,hdl_c,4'h9,hdo_a}; // MOVFL |
11'b10xx_xx_0011x : op3_feld = {6'o11,hdo_b,2'b01,hdr_c,hdr_b, hdl_d,hdl_b,OPREG[23:14],2'b00,hdl_c,4'h9,hdo_a}; // ROUNDi,TRUNCi |
11'b111x_xx_00111 : op3_feld = {6'o11,hdo_b,2'b01,hdr_c,hdr_b, hdl_d,hdl_b,OPREG[23:14],2'b00,hdl_c,4'h9,hdo_a}; // FLOORi |
11'b111x_xx_00110 : op3_feld = {6'o11, 3'o5,hdr_c,hdr_b, hdl_d,hdl_b,OPREG[23:14],2'b00,hdl_c,op_cop}; // SEARCH |
11'b0x00_0x_10111 : op3_feld = {6'o11,hdo_b,2'b11,hdr_c,hdr_d, hdl_d,hdl_d,OPREG[23:14],2'b00,hdl_e,4'hB,hdo_a}; // ADDf,SUBf |
11'bxx00_0x_10110 : op3_feld = {6'o11, 3'o7,hdr_c,hdr_d, hdl_d,hdl_d,OPREG[23:14],2'b00,hdl_e,op_cop}; // Coprocessor |
11'b1000_0x_10111 : op3_feld = {6'o11, 3'o7,hdr_c,hdr_d, hdl_d,hdl_d,OPREG[23:14],2'b00,hdl_e,4'hB,hdo_a}; // DIVf |
11'b1100_0x_10111 : op3_feld = {6'o11,hdo_b,2'b11,hdr_c,hdr_d, hdl_d,hdl_d,OPREG[23:14],2'b00,hdl_e,4'hB,hdo_a}; // MULf |
11'b0010_0x_1011x : op3_feld = {6'o11,hdo_b,2'b10,hdr_c,hdr_d, hdl_d,hdl_d,OPREG[23:14],2'b00,hdl_e,4'hB,hdo_a}; // CMPf |
11'b0001_0x_10111 : op3_feld = {6'o11, 3'o1,hdr_c,hdr_d, hdl_d,hdl_d,OPREG[23:14],2'b00,hdl_e,4'hB,hdo_a}; // MOVf |
11'bx101_0x_10111 : op3_feld = {6'o11, 3'o1,hdr_c,hdr_d, hdl_d,hdl_d,OPREG[23:14],2'b00,hdl_e,4'hB,hdo_a}; // NEGf,ABSf |
11'b001x_11_00111 : op3_feld = {6'o11,3'o1,hdr_a,fsr_r, 2'b10,2'b10,OPREG[23:19],5'b0,2'b00,3'o3,8'h92}; // LFSR |
11'b110x_11_00111 : op3_feld = {6'o11,3'o1,fsr_r,hdr_b, 2'b10,2'b10,5'b0,OPREG[18:14],2'b00,3'o3,8'h9C}; // SFSR |
// MMU opcodes |
11'b0010_11_0001x : op3_feld = {6'o11,3'o1,hdr_a,temp_h,2'b10,2'b10,OPREG[23:19],5'b0,2'b00, 3'o |
11'b0011_11_0001x : op3_feld = {6'o11,3'o1,hdr_m,hdr_a, 2'b10,2'b10,5'b0,OPREG[23:19],2'b00, 3'o |
11'b0010_11_0001x : op3_feld = {6'o11,3'o1,hdr_a,temp_h,2'b10,2'b10,OPREG[23:19],5'b0,2'b00, 3'o3,8'h45}; // LMR |
11'b0011_11_0001x : op3_feld = {6'o11,3'o1,hdr_m,hdr_a, 2'b10,2'b10,5'b0,OPREG[23:19],2'b00, 3'o3,8'h45}; // SMR |
// String opcodes |
11'b000x_xx_0000x : op3_feld = {6'o11,3'o0,6'hxx,6'hxx, 2'bxx,2'b10,OPREG[23:14], 2'b10,hdl_ |
11'b0011_xx_0000x : op3_feld = {6'o11,3'o0,6'hxx,6'hxx, 2'bxx,2'b10,OPREG[23:14], 2'b10,hdl_ |
11'b000x_xx_0000x : op3_feld = {6'o11,3'o0,6'hxx,6'hxx, 2'bxx,2'b10,OPREG[23:14], 2'b10,hdl_c,hdo_d}; // MOVS,CMPS |
11'b0011_xx_0000x : op3_feld = {6'o11,3'o0,6'hxx,6'hxx, 2'bxx,2'b10,OPREG[23:14], 2'b10,hdl_c,hdo_d}; // SKPS |
// Custom opcodes |
11'bxx01_0x_10110 : op3_feld = {6'o11, 3'o5,hdr_c,hdr_d, hdl_d,hdl_d,OPREG[23:14],2'b00,hd |
11'bxx01_0x_10110 : op3_feld = {6'o11, 3'o5,hdr_c,hdr_d, hdl_d,hdl_d,OPREG[23:14],2'b00,hdl_e,op_cop}; |
// Integer Divisionen : QUOi REMi DIVi MODi and DEIi + MEIi |
11'b11xx_xx_1100x : op3_feld = {6'o11,3'o7,hdr_a,hdr_b, hdl_b,hdl_b,OPREG[23:14],2'b00,hdl_a,4'h |
11'b10x1_xx_1100x : op3_feld = {6'o11,3'o7,hdr_a,hdr_g, hdl_b,hdl_f,OPREG[23:14],2'b10,hdl_a,4'h |
11'b11xx_xx_1100x : op3_feld = {6'o11,3'o7,hdr_a,hdr_b, hdl_b,hdl_b,OPREG[23:14],2'b00,hdl_a,4'h7,hdo_a}; |
11'b10x1_xx_1100x : op3_feld = {6'o11,3'o7,hdr_a,hdr_g, hdl_b,hdl_f,OPREG[23:14],2'b10,hdl_a,4'h7,hdo_a}; // DEI/MEI |
// Gruppe 2 opcodes |
11'b0x11_xx_1010x : op3_feld = {6'o77,3'o1,hdr_a,hdr_b, hdl_b,hdl_b,OPREG[23:14],2'b00,hdl_a,8'h |
11'b000x_xx_1100x : op3_feld = {6'o66,3'o0,hdr_a,hdr_b, 2'bxx,2'b10,OPREG[23:14],2'b10,hdl_c, hd |
11'b001x_0x_1111x : op3_feld = {6'o11,3'o0,hdr_c,hdr_d, hdl_d,hdl_d,OPREG[23:14],2'b10,hdl_e,4'h |
11'b0101_0x_1111x : op3_feld = {6'o11,3'o5,hdr_c,hdr_d, hdl_d,hdl_d,OPREG[23:14],2'b00,hdl_e,4'h |
11'b0100_0x_1111x : op3_feld = {6'o11,3'o0,hdr_c,hdr_d, hdl_d,hdl_d,OPREG[23:14],2'b10,hdl_e,4'h |
11'b0011_xx_1100x : op3_feld = {6'o50,3'o0,hdr_a,hdr_b, hdl_g,hdl_b,OPREG[23:14],2'b10,hdl_c,4'h |
11'bxxx0_xx_1110x : op3_feld = {6'o71,3'o0,hdr_a,hdr_b, hdl_h,hdl_b,OPREG[23:14],2'b10,hdl_c,4'h |
11'b0x11_xx_1010x : op3_feld = {6'o77,3'o1,hdr_a,hdr_b, hdl_b,hdl_b,OPREG[23:14],2'b00,hdl_a,8'h45}; // MOVUS,MOVSU |
11'b000x_xx_1100x : op3_feld = {6'o66,3'o0,hdr_a,hdr_b, 2'bxx,2'b10,OPREG[23:14],2'b10,hdl_c, hdo_d}; // MOVM/CMPM |
11'b001x_0x_1111x : op3_feld = {6'o11,3'o0,hdr_c,hdr_d, hdl_d,hdl_d,OPREG[23:14],2'b10,hdl_e,4'hC,hdo_a}; // DOTf,POLYf |
11'b0101_0x_1111x : op3_feld = {6'o11,3'o5,hdr_c,hdr_d, hdl_d,hdl_d,OPREG[23:14],2'b00,hdl_e,4'hB,hdo_e}; // LOGB |
11'b0100_0x_1111x : op3_feld = {6'o11,3'o0,hdr_c,hdr_d, hdl_d,hdl_d,OPREG[23:14],2'b10,hdl_e,4'hB,hdo_e}; // SCALB |
11'b0011_xx_1100x : op3_feld = {6'o50,3'o0,hdr_a,hdr_b, hdl_g,hdl_b,OPREG[23:14],2'b10,hdl_c,4'h7,hdo_a}; // EXTS |
11'bxxx0_xx_1110x : op3_feld = {6'o71,3'o0,hdr_a,hdr_b, hdl_h,hdl_b,OPREG[23:14],2'b10,hdl_c,4'h8,hdo_c}; // CHECK |
11'b0x1x_xx_0100x : op3_feld = (OPREG[18:17] == 2'b00) ? // target is register => standard flow |
{6'o11,3'o3,hdr_a,hdr_b, hdl_b,2'b10,OPREG[23:14],2'b00,hdl_a,4'h6,hdo_a} // SBIT/CBIT |
: {6'o14,3'o3,hdr_a,hdr_b, hdl_b,2'b00,OPREG[23:14],2'b10,hdl_a,4'h6,hdo_a}; |
924,20 → 924,20
11'b1110_xx_0100x : op3_feld = (OPREG[18:17] == 2'b00) ? // target is register => standard flow |
{6'o11,3'o3,hdr_a,hdr_b, hdl_b,2'b10,OPREG[23:14],2'b00,hdl_a,4'h6,hdo_a} // IBIT |
: {6'o14,3'o3,hdr_a,hdr_b, hdl_b,2'b00,OPREG[23:14],2'b10,hdl_a,4'h6,hdo_a}; |
11'b1x11_xx_0100x : op3_feld = {6'o11,3'o7,hdr_a,hdr_b, hdl_b,hdl_b,OPREG[23:14],2'b00,hdl_a,4'h |
11'bxxx0_xx_0010x : op3_feld = {6'o40,3'o0,hdr_a,hdr_b, hdl_g,hdl_b,OPREG[23:14],2'b10,hdl_c,4'h |
11'bxxx0_xx_1010x : op3_feld = {6'o14,3'o0,hdr_a,hdr_b, hdl_b,2'b10,OPREG[23:14],2'b10, 3'o3,4'h |
11'b0010_xx_1100x : op3_feld = {6'o14,3'o0,hdr_a,hdr_b, hdl_b,2'b10,OPREG[23:14],2'b10, 3'o3,4'h |
11'bxxx0_xx_0110x : op3_feld = {6'o61,3'o0,hdr_a,hdr_b, hdl_b,2'b10,OPREG[23:14],2'b10, 3'o3,4'h |
11'bxxx1_xx_0010x : op3_feld = {6'o11,3'o0,hdr_a,hdr_b, hdl_b,hdl_b,OPREG[23:14],2'b10, 3'o3,8'h |
// Gruppe 2 opcodes can have dedicated operation codes. Therefore the operation code definition her |
11'b000x_xx_0001x : op3_feld = {6'o70,3'o0,hdr_a,hdr_b, 2'b00,2'b10,OPREG[23:19],5'b0,2'b10,3'o0 |
11'b1001_11_0001x : op3_feld = {6'o11,3'o1,hdr_a,temp_h,2'b10,2'b10,OPREG[23:19],5'b0,2'b00,3'o3 |
11'b1x11_xx_0100x : op3_feld = {6'o11,3'o7,hdr_a,hdr_b, hdl_b,hdl_b,OPREG[23:14],2'b00,hdl_a,4'h6,hdo_a}; // ADDP,SUBP |
11'bxxx0_xx_0010x : op3_feld = {6'o40,3'o0,hdr_a,hdr_b, hdl_g,hdl_b,OPREG[23:14],2'b10,hdl_c,4'h8,hdo_c}; // EXT |
11'bxxx0_xx_1010x : op3_feld = {6'o14,3'o0,hdr_a,hdr_b, hdl_b,2'b10,OPREG[23:14],2'b10, 3'o3,4'h8,hdo_c}; // INS |
11'b0010_xx_1100x : op3_feld = {6'o14,3'o0,hdr_a,hdr_b, hdl_b,2'b10,OPREG[23:14],2'b10, 3'o3,4'h8,hdo_a}; // INSS |
11'bxxx0_xx_0110x : op3_feld = {6'o61,3'o0,hdr_a,hdr_b, hdl_b,2'b10,OPREG[23:14],2'b10, 3'o3,4'h8,hdo_c}; // CVTP no Opcode |
11'bxxx1_xx_0010x : op3_feld = {6'o11,3'o0,hdr_a,hdr_b, hdl_b,hdl_b,OPREG[23:14],2'b10, 3'o3,8'h84}; // INDEX |
// Gruppe 2 opcodes can have dedicated operation codes. Therefore the operation code definition here is "don't care" |
11'b000x_xx_0001x : op3_feld = {6'o70,3'o0,hdr_a,hdr_b, 2'b00,2'b10,OPREG[23:19],5'b0,2'b10,3'o0,8'h45}; // RDVAL+WRVAL |
11'b1001_11_0001x : op3_feld = {6'o11,3'o1,hdr_a,temp_h,2'b10,2'b10,OPREG[23:19],5'b0,2'b00,3'o3,8'h45}; // CINV |
|
default : op3_feld = {40'hxx_xxxx_xxxx,4'hA,4'hx}; |
endcase |
|
assign op_3byte = (valid[2:0] == 3'b111) & (OPREG[2:0] == 3'b110) & (op3_feld[7:4] != 4'hA); // val |
assign op_3byte = (valid[2:0] == 3'b111) & (OPREG[2:0] == 3'b110) & (op3_feld[7:4] != 4'hA); // valid for all incl. CUSTOM |
|
// +++++++++++++ Evaluation for 2 and 3 byte opcodes ++++++++++++++++++ |
|
944,7 → 944,7
// for one byte opcodes special treatmant neccessary |
assign opc_bits = op_3byte ? op3_feld : op2_feld; |
|
assign op_ok = (op_1byte | op_12byte | op_2byte | op_3byte | exception) & ~stop; // used for comput |
assign op_ok = (op_1byte | op_12byte | op_2byte | op_3byte | exception) & ~stop; // used for computation of USED |
|
always @(posedge BCLK) if (PHASE_0) op_feld_reg <= opc_bits; |
assign op_feld = PHASE_0 ? opc_bits : op_feld_reg; // constant for all following cycles |
961,15 → 961,15
assign src_2 = {1'b0,op_feld[32:27]}; |
assign src1_le = op_feld[26:25]; |
assign src2_le = op_feld[24:23]; |
assign acc1 = (op_feld[22:21] != 2'b00) | atys[1]; // external access Source1 or "addr" : Reg => ( |
assign acc2 = (op_feld[17:16] != 2'b00) | atyd[1]; // external access Source2 or "addr" : Reg => ( |
assign acc1 = (op_feld[22:21] != 2'b00) | atys[1]; // external access Source1 or "addr" : Reg => (Reg) |
assign acc2 = (op_feld[17:16] != 2'b00) | atyd[1]; // external access Source2 or "addr" : Reg => (Reg) |
assign wlor = dest_flag & ~acc2; |
assign idx_n = {1'b0,(op_feld[22:20] == 3'b111)} + {1'b0,(op_feld[17:15] == 3'b111)}; // Index : 0 |
assign idx_n = {1'b0,(op_feld[22:20] == 3'b111)} + {1'b0,(op_feld[17:15] == 3'b111)}; // Index : 0,1 or 2 |
assign idx = (idx_n != 2'b00); // Index is active |
assign n_idx = idx_n - 2'b01; |
|
// The field otype is used only in Phase 0 |
assign otype = exception ? 2'b11 : ((op_1byte | op_12byte) ? 2'b01 : opc_bits[12:11]); // string op |
assign otype = exception ? 2'b11 : ((op_1byte | op_12byte) ? 2'b01 : opc_bits[12:11]); // string opcodes use code 2'b10 |
|
assign opera = op_feld[10:0]; |
|
986,11 → 986,11
assign STOP_IC = (phase_reg == 8'h74) | (phase_reg == 8'h75); |
|
// CINV uses Register x'30 - x'37 : CINV = 110... , LMR = 001... otherwise CFG |
always @(posedge BCLK) if (PHASE_0) lmrreg <= op_3byte ? {{2{OPREG[13]}},~OPREG[13],OPREG[17:15]} : |
always @(posedge BCLK) if (PHASE_0) lmrreg <= op_3byte ? {{2{OPREG[13]}},~OPREG[13],OPREG[17:15]} : 6'h1C; |
|
always @(posedge BCLK) no_init <= (lmrreg[5:4] == 2'b00) & (lmrreg[3:1] != 3'b110); // LMR waits fo |
always @(posedge BCLK) no_init <= (lmrreg[5:4] == 2'b00) & (lmrreg[3:1] != 3'b110); // LMR waits for INIT at PTB0/1 |
// a_ivar = "Addresse IVAR0/1" |
always @(posedge BCLK) a_ivar <= STOP_IC; // Phase 74 & 75, is used at INFO_AU together with IC_RE |
always @(posedge BCLK) a_ivar <= STOP_IC; // Phase 74 & 75, is used at INFO_AU together with IC_READ |
|
// CINV detection for IC_CACHE |
always @(posedge BCLK) |
1017,21 → 1017,21
|
// +++++++++++++++++++++++++ Flags for CBIT/I+SBIT/I+IBIT +++++++++++++++++++++++ |
|
assign rw_bit = (op_feld_reg[7:4] == 4'd6) & ((~op_feld_reg[3] & op_feld_reg[1]) | (op_feld_reg[3:0 |
assign rw_bit = (op_feld_reg[7:4] == 4'd6) & ((~op_feld_reg[3] & op_feld_reg[1]) | (op_feld_reg[3:0] == 4'hE)); |
assign op_ilo = rw_bit & op_feld_reg[0]; // Interlocked : CBITI and SBITI |
|
// +++++++++++++++++++++++++++++ Operations for String processing +++++++++++++++++ |
// Address field : Size:2 RD WR LDEA FULLACC INDEX:4 SPUPD disp_val:4 POST CLRMSW SRC2SEL:2 |
|
assign st_src = {STRING[1:0],5'b1010_0,(op_feld_reg[15] & ~kurz_st),STRING[1:0],9'b0_0000_1000}; / |
assign st_src2 = {STRING[1:0],5'b1010_0,(op_feld_reg[15] & ~kurz_st),STRING[1:0],9'b0_0000_1011}; / |
assign st_dest = {STRING[1:0],5'b0110_0,(op_feld_reg[15] & ~kurz_st),STRING[1:0],9'b0_0000_1011}; / |
assign st_trde = {2'b00, 5'b0110_0, op_feld_reg[15], 2'b00, 9'b0_0000_1000}; / |
assign st_trs2 = {STRING[1:0],5'b1010_0, op_feld_reg[15], STRING[1:0],9'b0_0000_1000}; / |
assign st_src = {STRING[1:0],5'b1010_0,(op_feld_reg[15] & ~kurz_st),STRING[1:0],9'b0_0000_1000}; // [15] = BACKWARD |
assign st_src2 = {STRING[1:0],5'b1010_0,(op_feld_reg[15] & ~kurz_st),STRING[1:0],9'b0_0000_1011}; // Reuse EA |
assign st_dest = {STRING[1:0],5'b0110_0,(op_feld_reg[15] & ~kurz_st),STRING[1:0],9'b0_0000_1011}; // Reuse EA |
assign st_trde = {2'b00, 5'b0110_0, op_feld_reg[15], 2'b00, 9'b0_0000_1000}; // after Translate to Dest |
assign st_trs2 = {STRING[1:0],5'b1010_0, op_feld_reg[15], STRING[1:0],9'b0_0000_1000}; // after Match to SRC2 |
assign st_len = {STRING[1:0],17'b0000_0000_0_0000_0000}; // length important for qw_flag |
|
// Signals of DETOIP go to I_PFAD |
always @(posedge BCLK) if (PHASE_0) kill_opt <= ~OPREG[7] & (OPREG[17:15] != 3'b000); // watch diff |
always @(posedge BCLK) if (PHASE_0) kill_opt <= ~OPREG[7] & (OPREG[17:15] != 3'b000); // watch difference of MOVM and MOVS |
assign ph_match = (phase_reg[7:4] == 4'hD) & (phase_reg[2:0] == 3'd7); // Phase D7 and DF |
|
assign op_str = {op_feld_reg[10:8],6'b0101_00,op_feld_reg[1],1'b1}; // Opcode 8'h51 or 8'h53; |
1038,10 → 1038,10
assign op_scp = {op_feld_reg[10:8],8'h41}; // normal CMPi |
assign ph_str = {4'hC,op_feld_reg[1],3'b001}; // Phase 8'hC1 (MOVS/M) or 8'hC9 (CMPS/M) |
|
always @(posedge BCLK) kurz_st <= (phase_reg == 8'h65) | (kurz_st & ~PHASE_0); // Flag for MOVM/C |
always @(posedge BCLK) if (PHASE_0) cmps_flag <= ~OPREG[7] & (OPREG[11:10] == 2'b01); // Flag for C |
always @(posedge BCLK) if (PHASE_0) skps_flag <= ~OPREG[7] & (OPREG[11:10] == 2'b11); // Flag for S |
always @(posedge BCLK) if (PHASE_0) mt_flag <= ~OPREG[7] & (OPREG[17] | OPREG[15]); // Flag for Ma |
always @(posedge BCLK) kurz_st <= (phase_reg == 8'h65) | (kurz_st & ~PHASE_0); // Flag for MOVM/CMPM |
always @(posedge BCLK) if (PHASE_0) cmps_flag <= ~OPREG[7] & (OPREG[11:10] == 2'b01); // Flag for CMPS |
always @(posedge BCLK) if (PHASE_0) skps_flag <= ~OPREG[7] & (OPREG[11:10] == 2'b11); // Flag for SKPS |
always @(posedge BCLK) if (PHASE_0) mt_flag <= ~OPREG[7] & (OPREG[17] | OPREG[15]); // Flag for Match and Translate |
|
assign wstr0 = {{4{kurz_st}},2'b00}; |
assign wstr1 = {{4{kurz_st}},2'b01}; |
1064,7 → 1064,7
// 1. At short-op SRC1 is out of memory to use TEMP |
// 2. At SRC2 rmw suppresed TOS and changed it to (SP) |
// 3. The Long-operation path takes the dest_r address to write if WR_REG activ |
// 4. It is ok, that an extra cycle for the read of the index registers is needed - then data could |
// 4. It is ok, that an extra cycle for the read of the index registers is needed - then data could be written ins Out register |
|
// Source 1 |
|
1074,7 → 1074,7
assign usp_1 = src1_addr[0] ? stack : {5'b0_0110,src1_addr[1:0]}; |
assign src_1l = {src_1[6:1],1'b0}; |
assign pop_1 = {2'b00,src1_le,9'h108}; // SP update, DISP=0 and POST |
assign mpoi_1 = (src1_addr[4:2] == 3'b100) | (src1_addr == 5'h16); // Pointer in memory always DWor |
assign mpoi_1 = (src1_addr[4:2] == 3'b100) | (src1_addr == 5'h16); // Pointer in memory always DWord |
assign auop_s = atys[0] ? 4'b1011 : 4'b0010; // Only make effective address ? |
assign src1_tos = (op_feld[22:18] == 5'h17) ? 2'b11 : 2'b00; // Source 1 is true TOS |
|
1082,23 → 1082,23
// Address field : Size:2 RD WR LDEA FULLACC INDEX:4 SPUPD disp_val:4 POST CLRMSW SRC2SEL:2 |
always @(*) |
casex (src1_addr) // RWLF IDX ADDR_F NEUP SRC_REG NEXT |
// Special case which is only valid at INDEX or "addr" : REG -> ADDR , DISP=0 : starts immediate |
// Special case which is only valid at INDEX or "addr" : REG -> ADDR , DISP=0 : starts immediate at read |
5'b00xxx : gen_src1 = {auop_s, idx_1,9'h000,8'h07,4'h0,src1_addr[2:0],3'b000,atys[0]}; |
// Register relativ : 0(R0) |
5'b01xxx : gen_src1 = {auop_s, idx_1,9'h000,8'h07,4'h0,src1_addr[2:0],3'b111,atys[0]}; |
// Memory relativ : 0(0(SB)) |
5'b100xx : gen_src1 = {4'b1011,4'h0, 9'h000,8'h06,usp_1, 4'b1111}; // 1. access always ful |
5'b100xx : gen_src1 = {4'b1011,4'h0, 9'h000,8'h06,usp_1, 4'b1111}; // 1. access always full |
// Immediate |
5'b10100 : gen_src1 = (src1_le == 2'b11) ? |
{4'h0, 4'h0, 9'h000,8'h0B,src_x, 1'b1,2'b10,1'b0} // load in DWord pieces |
: {4'h0, 4'h0, 9'h000,8'h07,src_x, 1'b1,src1_le,1'b0}; |
5'b10101 : gen_src1 = {auop_s, idx_1,9'h002,8'h07,src_x, 3'b111,atys[0]}; // Absolut Address |
5'b10110 : gen_src1 = {4'b1011,4'h0, 9'h014,8'h05,7'h1F, 4'b0001}; // External with MOD Re |
5'b10101 : gen_src1 = {auop_s, idx_1,9'h002,8'h07,src_x, 3'b111,atys[0]}; // Absolut Addressing |
5'b10110 : gen_src1 = {4'b1011,4'h0, 9'h014,8'h05,7'h1F, 4'b0001}; // External with MOD Register +4 |
5'b10111 : gen_src1 = (idx_1[2] | atys[2]) ? // Access class "addr" ? |
{auop_s, idx_1,9'h000,8'h07,stack, 3'b000,atys[0]} // 0(SP) : no TOS flag |
: {4'b1011,pop_1, 8'h07,stack, 4'b0001}; // TOS |
// Memory Space : 0(SB) |
5'b110x0 : gen_src1 = {auop_s, idx_1,9'h000,8'h07,5'b0_0110,src1_addr[1:0],3'b111,atys[0]}; // S |
5'b110x0 : gen_src1 = {auop_s, idx_1,9'h000,8'h07,5'b0_0110,src1_addr[1:0],3'b111,atys[0]}; // SB+FP |
5'b11001 : gen_src1 = {auop_s, idx_1,9'h000,8'h07,stack, 3'b111,atys[0]}; // SP |
5'b11011 : gen_src1 = {auop_s, idx_1,9'h001,8'h07,src_x, 3'b111,atys[0]}; // PC relativ |
default : gen_src1 = 36'hx_xxxx_xxxx; // don't care |
1119,37 → 1119,37
assign src2_addr = idx_2[2] ? idx_feld[15:11] : op_feld[17:13]; |
assign usp_2 = src2_addr[0] ? stack : {5'b0_0110,src2_addr[1:0]}; |
assign src_2l = {src_2[6:1],1'b0}; |
assign mpoi_2 = (src2_addr[4:2] == 3'b100) | (src2_addr == 5'h16); // Pointer in memory always DWor |
assign mpoi_2 = (src2_addr[4:2] == 3'b100) | (src2_addr == 5'h16); // Pointer in memory always DWord |
assign auop_d = atyd[0] ? 4'b1011 : 4'b0010; // Only make effective address ? |
|
// The next assessment processes TOS separated for PUSH and POP |
assign tos_oper = src2_flag ? |
{2'b00,atyd[0],2'b01,atyd[0],2'b00,src2_le,7'b1_0000_10, src1_tos,4'h7,stack,3'b0,atyd[0]} |
: {1'b0,atyd[0],3'b001,atyd[0],4'h0, 1'b1,2'b10,src2_le,2'b0,src1_tos,4'h7,stack,3'b0,aty |
{2'b00,atyd[0],2'b01,atyd[0],2'b00,src2_le,7'b1_0000_10, src1_tos,4'h7,stack,3'b0,atyd[0]} // POP |
: {1'b0,atyd[0],3'b001,atyd[0],4'h0, 1'b1,2'b10,src2_le,2'b0,src1_tos,4'h7,stack,3'b0,atyd[0]}; // PUSH |
|
// Nextfield : 11=DISP read |
// Address field : Size:2 RD WR LDEA FULLACC INDEX:4 SPUPD disp_val:4 POST CLRMSW SRC2SEL:2 |
always @(*) |
casex (src2_addr) // RW:W RW:R LF IDX ADDR_F NEUP SRC_REG NEXT |
// Special case which is only valid at INDEX or "addr" : REG -> ADDR , DISP=0 : starts immediate |
5'b00xxx : gen_src2 = {1'b0,atyd[0],auop_d, idx_2,9'h000,4'h7,4'h0,src2_addr[2:0],3'b000,aty |
// Special case which is only valid at INDEX or "addr" : REG -> ADDR , DISP=0 : starts immediate at read |
5'b00xxx : gen_src2 = {1'b0,atyd[0],auop_d, idx_2,9'h000,4'h7,4'h0,src2_addr[2:0],3'b000,atyd[0]}; |
// Register relativ : 0(R0) |
5'b01xxx : gen_src2 = {1'b0,atyd[0],auop_d, idx_2,9'h000,4'h7,4'h0,src2_addr[2:0],3'b111,aty |
5'b01xxx : gen_src2 = {1'b0,atyd[0],auop_d, idx_2,9'h000,4'h7,4'h0,src2_addr[2:0],3'b111,atyd[0]}; |
// Memory relativ : 0(0(SB)) |
5'b100xx : gen_src2 = {2'b10,2'b10,2'b11,4'h0, 9'h000,4'h6,usp_2, 4'b1111}; // 1. access always |
5'b100xx : gen_src2 = {2'b10,2'b10,2'b11,4'h0, 9'h000,4'h6,usp_2, 4'b1111}; // 1. access always full |
// Immediate |
5'b10100 : gen_src2 = (src2_le == 2'b11) ? |
{2'b00,2'b00,2'b00,4'h0, 9'h000,4'hB,src_x, 1'b1,2'b10,1'b0} // load in DWord pieces |
: {2'b00,2'b00,2'b00,4'h0, 9'h000,4'h7,src_x, 1'b1,src2_le,1'b0}; |
5'b10101 : gen_src2 = {1'b0,atyd[0],auop_d, idx_2,9'h002,4'h7,src_x, 3'b111,atyd[0]}; // Ab |
5'b10110 : gen_src2 = {2'b10,2'b10,2'b11,4'h0, 9'h014,4'h5,7'h1F, 4'b0001}; // External with MO |
5'b10101 : gen_src2 = {1'b0,atyd[0],auop_d, idx_2,9'h002,4'h7,src_x, 3'b111,atyd[0]}; // Absolut with special coding |
5'b10110 : gen_src2 = {2'b10,2'b10,2'b11,4'h0, 9'h014,4'h5,7'h1F, 4'b0001}; // External with MOD Register +4 |
5'b10111 : gen_src2 = (idx_2[2] | rmw | atyd[2]) ? |
{1'b0,atyd[0],auop_d, idx_2,7'b0_0000_00,src1_tos,4'h7,stack, 3'b000,atyd[0]} // 0(SP) : TOS |
{1'b0,atyd[0],auop_d, idx_2,7'b0_0000_00,src1_tos,4'h7,stack, 3'b000,atyd[0]} // 0(SP) : TOS + DISP=0 |
: tos_oper; // TOS : 2 cases for PUSH and POP |
// Memory Space |
5'b110x0 : gen_src2 = {1'b0,atyd[0],auop_d, idx_2,9'h000,4'h7,5'b0_0110,src2_addr[1:0],3'b11 |
5'b110x0 : gen_src2 = {1'b0,atyd[0],auop_d, idx_2,9'h000,4'h7,5'b0_0110,src2_addr[1:0],3'b111,atyd[0]}; |
5'b11001 : gen_src2 = {1'b0,atyd[0],auop_d, idx_2,9'h000,4'h7,stack, 3'b111,atyd[0]}; |
5'b11011 : gen_src2 = {1'b0,atyd[0],auop_d, idx_2,9'h001,4'h7,src_x, 3'b111,atyd[0]}; // PC |
5'b11011 : gen_src2 = {1'b0,atyd[0],auop_d, idx_2,9'h001,4'h7,src_x, 3'b111,atyd[0]}; // PC relativ |
default : gen_src2 = 34'hx_xxxx_xxxx; // don't care |
endcase |
|
1161,8 → 1161,8
assign nxrw2 = gen_src2[3:0]; |
assign irrw2 = {4'b0,idx_feld[10:8]}; |
assign re_wr = {src2_le,4'b0101,4'h0, 9'h003}; // REUSE Address : Write of rmw |
assign exr22 = {src2_le,atyd[0],1'b0,1'b1,atyd[0],idx_2,9'h000}; // for Memory Relative and EXT in |
assign exw22 = {src2_le,1'b0,atyd[0],1'b1,atyd[0],idx_2,9'h000}; // for Memory Relative and EXT in |
assign exr22 = {src2_le,atyd[0],1'b0,1'b1,atyd[0],idx_2,9'h000}; // for Memory Relative and EXT in last step |
assign exw22 = {src2_le,1'b0,atyd[0],1'b1,atyd[0],idx_2,9'h000}; // for Memory Relative and EXT in last step |
|
// Special case : |
|
1213,7 → 1213,7
|
always @(*) // "_" "_" |
casex ({phase_ein,otype, idx,short_def,long,qword, acc1,acc2,src2_flag,dest_flag}) |
{8'h00,10'b00_1xxx_xxxx}: // Index must be loaded : phase 2 : in any case load TEMP for Short-Op an |
{8'h00,10'b00_1xxx_xxxx}: // Index must be loaded : phase 2 : in any case load TEMP for Short-Op and generate LD_OUT |
new_op = short_op ? // START LD_OUT |
{addr_nop,8'h02, imme, src_x, 1'b1,temp_h, op_sho, 2'b00,2'b10, 1'b1,n_idx,1'b0} |
: {addr_nop,8'h02, src_1,src_1l,1'b0,dest_x, opera, 2'b00,~src2_flag,2'b1_1,n_idx,1'b0}; |
1237,8 → 1237,8
new_op = {adrd2, phrd2, src_x,rega2, 1'b0,dest_x, opera, 2'b00,2'b00, nxrw2}; |
{8'h00,10'b00_0000_0101}: // Source 1 store in Dest : "pass through" for MOV,NEG,ABS |
new_op = {adwr2, phwr2, src_1,rega2, 1'b0,dest_x, opera, 2'b00,2'b10, nxrw2}; |
{8'h00,10'b00_0001_0101}: // Source 1 store in Dest : "pass through" for MOV,NEG,ABS for Long opera |
new_op = //(op_feld[17:13] == 5'h17) ? // TOS : special case , first 8B out of Reg and then r |
{8'h00,10'b00_0001_0101}: // Source 1 store in Dest : "pass through" for MOV,NEG,ABS for Long operands |
new_op = //(op_feld[17:13] == 5'h17) ? // TOS : special case , first 8B out of Reg and then read SP |
{addr_nop,8'h1C, src_1,src_1l,1'b0,dest_x, opera, 2'b00,2'b11, 4'h0}; |
{8'h00,10'b00_0010_0101}: // SRC1 -> DEST with short operands |
new_op = {addr_nop,8'h1F, src_1,src_x, 1'b0,dest_r, opera, 2'b11,2'b00, 4'h0}; |
1254,7 → 1254,7
new_op = {adrd1, phrd1, irrw1,rega1, 1'b0,dest_x, opera, 2'b00,2'b00, nxrd1}; |
{8'h02,10'bxx_x0xx_011x}: // Source 2 in memory - first to read |
new_op = {adrd2, phrd2, irrw2,rega2, 1'b0,dest_x, opera, 2'b00,2'b00, nxrw2}; |
{8'h02,10'bxx_x00x_0101}: // Source 1 store in Dest : "pass through" , data is already in Out-Regis |
{8'h02,10'bxx_x00x_0101}: // Source 1 store in Dest : "pass through" , data is already in Out-Register |
new_op = {adwr2, phwr2, irrw2,rega2, 1'b0,dest_x, opera, 2'b00,2'b00, nxrw2}; |
{8'h02,10'bxx_x010_0101}: // SRC1 -> DEST with short operands |
new_op = {addr_nop,8'h1F, src_1,src_x, 1'b0,dest_x, opera, 2'b11,2'b00, 4'h0}; |
1265,21 → 1265,21
|
// Phase 5 : wait for data and Disp2 for External addressing : part 2 EA = (MOD+4)+4*DISP1 |
// next phase fix : 6 |
{8'h05,10'bxx_xxxx_xxxx}: new_op = {exr11, 8'h06, src_x,imme , 1'b0,dest_x, opera, 2'b00,2'b00, |
{8'h05,10'bxx_xxxx_xxxx}: new_op = {exr11, 8'h06, src_x,imme , 1'b0,dest_x, opera, 2'b00,2'b00, 4'b1111}; |
// Phase 6 : Memory-Pointer for Memory Relative and last access External |
// next phase fix : 7 , add Index |
{8'h06,10'bxx_xxxx_xxxx}: new_op = {exr12, 8'h07, irrw1,imme , 1'b0,dest_x, opera, 2'b00,2'b00, |
{8'h06,10'bxx_xxxx_xxxx}: new_op = {exr12, 8'h07, irrw1,imme , 1'b0,dest_x, opera, 2'b00,2'b00, 3'b111,atys[0]}; |
|
// Phase 7 : wait for final data , direct from PHASE_0 if TOS without Index |
// next phase : if 8B data phase 8 is neccessary |
// if SRC2=REG execution started (otherwise store data in TEMP) and PHASE_0 |
{8'h07,10'bxx_xx00_x0xx}: // into Register , short operation execution , but LD_OUT for PSR Update |
{8'h07,10'bxx_xx00_x0xx}: // into Register , short operation execution , but LD_OUT for PSR Update ! dest_flag => WREN |
new_op = {addr_nop,endea, imme, src_2, dest_flag,dest_r,opera, 2'b00,2'b10, diacb}; |
{8'h07,10'bxx_xx01_x0xx}: // into Reg but with a step om between for ABSL etc. : phase 8 |
new_op = {addr_nop,8'h08, imme, src_x, 1'b1,dest_r, opera, 2'b00,2'b00, 4'h0}; |
{8'h07,10'bxx_xx10_x0xx}: // execute long operation , wait in phase 31 |
new_op = {addr_nop,8'h1F, imme, src_2, wlor,dest_r, opera, 2'b11,2'b00, 4'h0}; |
{8'h07,10'bxx_xx11_xx0x}: // execute long operation : 2. operand only Dest , load LSD , phase 24 , |
{8'h07,10'bxx_xx11_xx0x}: // execute long operation : 2. operand only Dest , load LSD , phase 24 , wait in phase 31 |
new_op = {addr_nop,8'h18, imme, src_x, 1'b1,temp_l, op_mov, 2'b01,2'b00, 4'h0}; |
{8'h07,10'bxx_xx11_x01x}: // lange Operation ausfuehren , LSD laden , phase 25 , warten in phase 31 |
new_op = {addr_nop,8'h19, imme, src_2, 1'b0,dest_r, opera, 2'b01,2'b00, 4'h0}; |
1287,19 → 1287,19
new_op = idx_2[2] ? |
{addr_nop,8'h0F, imme, src_x, 1'b1,temp_h, op_mov, 2'b00,2'b00, 4'h0} |
: {adrd2, phrd2, imme, rega2, 1'b1,temp_h, op_mov, 2'b00,2'b00, nxrw2}; |
{8'h07,10'bxx_xxx1_x11x}: // 8B data in TEMP , step in between then 2. Op read : phase 10 - can onl |
{8'h07,10'bxx_xxx1_x11x}: // 8B data in TEMP , step in between then 2. Op read : phase 10 - can only be "long" operation |
new_op = {addr_nop,8'h0A, imme, src_x, 1'b1,temp_h, op_mov, 2'b00,2'b00, 4'h0}; |
{8'h07,10'bxx_xx00_x101}: // something like ABSi , execute and store (LD_OUT) |
new_op = idx_2[2] ? |
{addr_nop,8'h10, imme, src_x, 1'b0,dest_x, opera, 2'b00,2'b10, 4'h0} |
: {adwr2, phwr2, imme, rega2, 1'b0,dest_x, opera, 2'b00,2'b10, nxrw2}; |
{8'h07,10'bxx_xx01_x101}: // ABS etc. : LSD data over SRC2 in 2. OUT-Reg , MSD data see opcode ABS/ |
{8'h07,10'bxx_xx01_x101}: // ABS etc. : LSD data over SRC2 in 2. OUT-Reg , MSD data see opcode ABS/NEG/MOV , phase 9 |
new_op = {addr_nop,8'h09, imme, src_x, 1'b0,dest_x, opera, 2'b00,2'b10, 4'h0}; |
{8'h07,10'bxx_xx10_x101}: // opcodes like MOVFL |
new_op = {addr_nop,8'h1F, imme, src_x, 1'b0,dest_x, opera, 2'b11,2'b00, 4'h0}; |
|
// Phase 8 : 2. part of 64 bit data : can be reached from PHASE_0 if 8B data |
{8'h08,10'bxx_xxxx_xxxx}: new_op = {addr_nop,endea, quei1,src_x, 1'b1,dest_rl, op_mov, 2'b00,2'b00, |
{8'h08,10'bxx_xxxx_xxxx}: new_op = {addr_nop,endea, quei1,src_x, 1'b1,dest_rl, op_mov, 2'b00,2'b00, diacb}; |
// Phase 9 : step in between to get data in OUT-Reg Low , SRC1 is not possible |
{8'h09,10'bxx_xxxx_xxxx}: // afterwards to data write |
new_op = {addr_nop,8'h10, src_x,imme , 1'b0,dest_x, op_mov, 2'b00,2'b01, 4'h0}; |
1314,32 → 1314,32
new_op = {addr_nop,8'h0C, imme, src_x, 1'b1,dest_r, opera, 2'b00,2'b00, 4'b1100}; |
{8'h0B,10'bxx_xx1x_x01x}: // execute long operation , load LSD , phase 25 , wait in phase 31 |
new_op = {addr_nop,8'h19, imme, src_2, 1'b0,dest_r, opera, 2'b01,2'b00, 4'b1100}; |
{8'h0B,10'bxx_xxxx_x11x}: // 8B data into TEMP , step in between then read 2. Op : phase 10 - can o |
{8'h0B,10'bxx_xxxx_x11x}: // 8B data into TEMP , step in between then read 2. Op : phase 10 - can only be "long" operation |
new_op = {addr_nop,8'h0A, imme, src_x, 1'b1,temp_h, op_mov, 2'b00,2'b00, 4'b1100}; |
{8'h0B,10'bxx_xx0x_x10x}: // ABS etc. : LSD data via SRC2 into 2. OUT-Reg , MSD data see opcode ABS |
{8'h0B,10'bxx_xx0x_x10x}: // ABS etc. : LSD data via SRC2 into 2. OUT-Reg , MSD data see opcode ABS/NEG/MOV , phase 9 |
new_op = {addr_nop,8'h09, imme, src_x, 1'b0,dest_x, opera, 2'b00,2'b10, 4'b1100}; |
{8'h0B,10'bxx_xx1x_xx0x}: // MOVLF with 8B IMME data ? Must be possible, the end in phase 24 like S |
{8'h0B,10'bxx_xx1x_xx0x}: // MOVLF with 8B IMME data ? Must be possible, the end in phase 24 like SRC1=MEM |
new_op = {addr_nop,8'h18, imme, src_x, 1'b1,temp_l, op_mov, 2'b01,2'b00, 4'b1100}; |
// Phase 12 : wait for 2. part of 64 bit IMME data : after phase 0 |
{8'h0C,10'bxx_xxxx_xxxx}: new_op = {addr_nop,endea, imme ,src_x, 1'b1,dest_rl, op_mov, 2'b00,2'b00, |
{8'h0C,10'bxx_xxxx_xxxx}: new_op = {addr_nop,endea, imme ,src_x, 1'b1,dest_rl, op_mov, 2'b00,2'b00, diacb}; |
|
// Phase 15 : secure in TEMP with Index continue and read 2. operand |
{8'h0F,10'bxx_xxxx_xxxx}: new_op = {adrd2, phrd2, irrw2,rega2, 1'b0,dest_x, opera, 2'b00,2'b00, |
{8'h0F,10'bxx_xxxx_xxxx}: new_op = {adrd2, phrd2, irrw2,rega2, 1'b0,dest_x, opera, 2'b00,2'b00, nxrw2}; |
// Phase 16 : after LD_OUT continue with Index and store 1. operand |
{8'h10,10'bxx_xxxx_xxxx}: new_op = {adwr2, phwr2, irrw2,rega2, 1'b0,dest_x, opera, 2'b00,2'b00, |
{8'h10,10'bxx_xxxx_xxxx}: new_op = {adwr2, phwr2, irrw2,rega2, 1'b0,dest_x, opera, 2'b00,2'b00, nxrw2}; |
|
// +++++++++++++++++ SRC2 operand loading : phase SRC1 + 16 +++++++++++++++++++ |
|
// Phase 21 : wait for data and Disp2 for external addressing : part 2 EA = (MOD+4)+4*DISP1 |
// next phase fix : 22 |
{8'h15,10'bxx_xxxx_xxxx}: new_op = {exr11, 8'h16, src_x,imme , 1'b0,dest_x, opera, 2'b00,2'b00, |
{8'h15,10'bxx_xxxx_xxxx}: new_op = {exr11, 8'h16, src_x,imme , 1'b0,dest_x, opera, 2'b00,2'b00, 4'b1111}; |
// Phase 22 : Memory-Pointer for Memory Relative and last access external |
// next phase fix : 23 , add Index |
{8'h16,10'bxx_xxxx_xxxx}: new_op = {exr22, 8'h17, irrw2,imme , 1'b0,dest_x, opera, 2'b00,2'b00, |
{8'h16,10'bxx_xxxx_xxxx}: new_op = {exr22, 8'h17, irrw2,imme , 1'b0,dest_x, opera, 2'b00,2'b00, 3'b111,atyd[0]}; |
|
// Phase 23 : wait for final data , direct from PHASE_0 if TOS without Index |
// next phase : if 8B data phase 24 is used |
{8'h17,10'bxx_xx0x_xxx1}: // execute short operation and write data into memory , no WREN -> phase |
{8'h17,10'bxx_xx0x_xxx1}: // execute short operation and write data into memory , no WREN -> phase 39 ACC_DONE |
new_op = {re_wr, 8'h27, quet1,imme , 1'b0,dest_r, opera, 2'b00,2'b10, 4'b0001}; |
{8'h17,10'bxx_xx0x_xxx0}: // execute short operation , no WREN -> phase 0 , CMP(+TBIT) |
new_op = {addr_nop,endea, quet1,imme , 1'b0,dest_r, opera, 2'b00,2'b10, diacb}; |
1347,10 → 1347,10
new_op = {addr_nop,8'h1F, quet1,imme , wlor,dest_r, opera, 2'b11,2'b00, 4'h0}; |
{8'h17,10'bxx_xx11_xxxx}: // execute long operation , load LSD in phase 24 |
new_op = {addr_nop,8'h18, quet1,imme , 1'b0,dest_r, opera, 2'b01,2'b00, 4'h0}; |
// Phase 24 : load 2. part of 64 bit data : with and without wait - from 28 the phase waits , from |
// Phase 24 : load 2. part of 64 bit data : with and without wait - from 28 the phase waits , from 23 not |
{8'h18,10'bxx_xxxx_0xxx}: // execute long operation , wait in phase 31 |
new_op = {addr_nop,8'h1F, src_1l,imme, wlor,dest_r, opera, 2'b10,2'b00, 4'h0}; |
{8'h18,10'bxx_xxxx_1xxx}: // execute long operation , wait in phase 31 , data from TEMP, used also |
{8'h18,10'bxx_xxxx_1xxx}: // execute long operation , wait in phase 31 , data from TEMP, used also for ROUNDLi |
new_op = {addr_nop,8'h1F, rtmpl,imme, wlor,dest_r, opera, 2'b10,2'b00, 4'h0}; |
// Phase 25 : load 2. part of 64 bit data : SRC1 from memory and SRC2 from Reg |
{8'h19,10'bxx_xxxx_xxxx}: // execute long operation , wait in phase 31 |
1374,7 → 1374,7
new_op = {addr_nop,8'h00, src_x,src_x, 1'b0,dest_r, opera, 2'b00,2'b10, 4'h0}; // no ACB |
{8'h1F,10'bxx_xxxx_x0x1}: // operation closed , data into register |
new_op = {addr_nop,8'h00, src_x,src_x, 1'b0,dest_r, opera, 2'b00,2'b00, 4'h0}; // no ACB |
{8'h1F,10'bxx_xxxx_x101}: // operation closed , data into memory - first calculate address phase 32 |
{8'h1F,10'bxx_xxxx_x101}: // operation closed , data into memory - first calculate address phase 32+x |
new_op = {adwr2, phwr2, irrw2,rega2, 1'b0,dest_r, opera, 2'b00,2'b00, nxrw2}; |
{8'h1F,10'bxx_xxxx_x111}: // operation closed , data into memory - address reuse phase 39 ACC_DONE |
new_op = {re_wr, 8'h27, src_x,src_x, 1'b0,dest_r, opera, 2'b00,2'b00, 4'b0001}; |
1382,10 → 1382,10
// Destination address calculate |
// Phase 37 : wait for data and Disp2 for External addressing : part 2 EA = (MOD+4)+4*DISP1 |
// next phase fix : 38 |
{8'h25,10'bxx_xxxx_xxxx}: new_op = {exr11, 8'h26, src_x,imme , 1'b0,dest_x, opera, 2'b00,2'b00, |
{8'h25,10'bxx_xxxx_xxxx}: new_op = {exr11, 8'h26, src_x,imme , 1'b0,dest_x, opera, 2'b00,2'b00, 4'b1111}; |
// Phase 38 : Memory-Pointer for Memory Relative and letzter Zugriff External |
// next phase fix : 39 , add Index and write |
{8'h26,10'bxx_xxxx_xxxx}: new_op = {exw22, 8'h27, irrw2,imme , 1'b0,dest_x, opera, 2'b00,2'b00, |
{8'h26,10'bxx_xxxx_xxxx}: new_op = {exw22, 8'h27, irrw2,imme , 1'b0,dest_x, opera, 2'b00,2'b00, 4'b1111}; |
|
// Phase 39 : wait for ACC_DONE : consequent numbering : 7+32 |
{8'h27,10'bxx_xxxx_xxxx}: // now operation closed , only ACB could follow |
1392,11 → 1392,11
new_op = {addr_nop,endea, src_x,src_x, 1'b0,dest_x, opera, 2'b00,2'b00, diacb}; |
|
// +++++++++++++++ special case : ACB to Reg is to fast ! One wait cycle for ZERO-Flag |
{8'h28,10'bxx_xxxx_xxxx}: new_op = {addr_nop,8'h01,src_x, src_x, 1'b0,dest_x, opera, 2'b00,2'b00, |
{8'h28,10'bxx_xxxx_xxxx}: new_op = {addr_nop,8'h01,src_x, src_x, 1'b0,dest_x, opera, 2'b00,2'b00, 4'b1110}; |
|
// +++++++++++++++ The other opcodes are following ++++++++++++++++++ |
|
{8'h00,10'b01_xxxx_xxxx}: new_op = {new_addr,new_ph,new_regs, 1'b0,dest_x, op_mov, new_nx}; |
{8'h00,10'b01_xxxx_xxxx}: new_op = {new_addr,new_ph,new_regs, 1'b0,dest_x, op_mov, new_nx}; // 1 Byte Opcodes |
|
// Phase 1 : used for Bcond and ACB : |
{8'h01,10'bxx_xxxx_xxxx}: new_op = (ex_br_op[1] | jsr_flag) ? // BSR or JSR ? |
1404,24 → 1404,24
: {addr_nop,8'h00, src_x,src_x, 1'b0,dest_x, op_mov, 2'b00,2'b00, 4'h0}; |
|
// Phase 42 : RET : read of PC from Stack and DIN via SRC1 to PC |
{8'h2A,10'bxx_xxxx_xxxx}: new_op = {adddisp, 8'h2B, imme, src_x, 1'b0,dest_x, op_mov, 2'b00,2'b00 |
// Phase 43 : RET : Displacement add to Stack. Attention : "imme" important to keep source constan |
{8'h2B,10'bxx_xxxx_xxxx}: new_op = {save_sp, 8'h2C, imme, src_x, 1'b0,dest_x, op_mov, 2'b00,2'b00 |
{8'h2A,10'bxx_xxxx_xxxx}: new_op = {adddisp, 8'h2B, imme, src_x, 1'b0,dest_x, op_mov, 2'b00,2'b00, 4'hE}; |
// Phase 43 : RET : Displacement add to Stack. Attention : "imme" important to keep source constant for PC |
{8'h2B,10'bxx_xxxx_xxxx}: new_op = {save_sp, 8'h2C, imme, src_x, 1'b0,dest_x, op_mov, 2'b00,2'b00, 4'h0}; |
// Phase 44 : RET : Update of Stack : fixed phase |
{8'h2C,10'bxx_xxxx_xxxx}: new_op = {addr_nop,8'h00, src_x,src_x, 1'b0,dest_x, op_mov, 2'b00,2'b00, |
{8'h2C,10'bxx_xxxx_xxxx}: new_op = {addr_nop,8'h00, src_x,src_x, 1'b0,dest_x, op_mov, 2'b00,2'b00, 4'h0}; |
|
// Phase 45 : ENTER Entry |
{8'h2D,10'bxx_xxxx_xxxx}: new_op = {dispmin, 8'h2E, src_x,src_x, 1'b1,temp_l, op_adr, 2'b00,2'b00, |
{8'h2D,10'bxx_xxxx_xxxx}: new_op = {dispmin, 8'h2E, src_x,src_x, 1'b1,temp_l, op_adr, 2'b00,2'b00, 4'hE}; |
// Phase 46 : ENTER Stack longer |
{8'h2E,10'bxx_xxxx_xxxx}: new_op = {save_sp ,8'h31, src_x,src_x, 1'b0,dest_x, op_mov, 2'b00,2'b00, |
{8'h2E,10'bxx_xxxx_xxxx}: new_op = {save_sp ,8'h31, src_x,src_x, 1'b0,dest_x, op_mov, 2'b00,2'b00, 4'h0}; |
// Phase 48 : SAVE/ENTER : Init phase , phases 48 & 49 very similar |
{8'h30,10'bxx_xxxx_xxxx}: new_op = save_reg ? |
{push_op, 8'h31, saver,stack, 1'b0,dest_x, op_mov, 2'b00,2'b10, 4'h1} // 1. load SP=>EA |
: {addr_nop,8'h00, rtmpl,src_x,new_fp,frame[5:0],op_mov, 2'b00,2'b00, 4'h0}; // At ENTER |
: {addr_nop,8'h00, rtmpl,src_x,new_fp,frame[5:0],op_mov, 2'b00,2'b00, 4'h0}; // At ENTER FP Update |
// Phase 49 : SAVE/ENTER : at the same time memory access and detection of next Reg |
{8'h31,10'bxx_xxxx_xxxx}: new_op = save_reg ? |
{push_ea, 8'h31, saver,src_x, 1'b0,dest_x, op_mov, 2'b00,2'b10, 4'h1} // one more |
: {addr_nop,8'h00, rtmpl,src_x,new_fp,frame[5:0],op_mov, 2'b00,2'b00, 4'h0}; // At ENTER |
: {addr_nop,8'h00, rtmpl,src_x,new_fp,frame[5:0],op_mov, 2'b00,2'b00, 4'h0}; // At ENTER FP Update |
|
// Phase 50 : RESTORE/EXIT Entry |
{8'h32,10'bxx_xxxx_xxxx}: new_op = save_reg ? |
1432,52 → 1432,52
{next_po, 8'h33, imme, src_x, 1'b1,resto, op_mov, 2'b00,2'b00, 4'h1} |
: {pop_fp, ppfp, imme, frame, 1'b1,resto, op_mov, 2'b00,2'b00, 3'h0,new_fp}; |
// Phase 52 : EXIT End |
{8'h34,10'bxx_xxxx_xxxx}: new_op = {addr_nop,8'h00, imme, src_x, 1'b1,frame[5:0], op_mov, 2'b00,2'b |
{8'h34,10'bxx_xxxx_xxxx}: new_op = {addr_nop,8'h00, imme, src_x, 1'b1,frame[5:0], op_mov, 2'b00,2'b00, 4'h0}; |
|
// Phase 53 : CXP Entry : this opcode needs 12 States and 16 cycles minimum ... |
{8'h35,10'bxx_xxxx_xxxx}: new_op = {addr_nop,8'h36, imme, src_x, 1'b1,temp_h, op_mov, 2'b00,2'b00, |
{8'h35,10'bxx_xxxx_xxxx}: new_op = {addr_nop,8'h36, imme, src_x, 1'b1,temp_h, op_mov, 2'b00,2'b00, 4'h0}; |
// Phase 54 : CXP : Store Address Link table |
{8'h36,10'bxx_xxxx_xxxx}: new_op = {rdltab, 8'h37, src_x,rtmph, 1'b0,dest_x, op_mov, 2'b00,2'b00, |
{8'h36,10'bxx_xxxx_xxxx}: new_op = {rdltab, 8'h37, src_x,rtmph, 1'b0,dest_x, op_mov, 2'b00,2'b00, 4'hE}; // EA Phase : DISP read |
// Phase 55 : CXP : DISP is worked on, the return address => temp_l |
{8'h37,10'bxx_xxxx_xxxx}: new_op = {addr_nop,8'h38, imme, rtmph, 1'b1,temp_l, op_mov, 2'b00,2'b00, |
{8'h37,10'bxx_xxxx_xxxx}: new_op = {addr_nop,8'h38, imme, rtmph, 1'b1,temp_l, op_mov, 2'b00,2'b00, 4'h1}; // Access |
// Phase 56 : CXP : Access to Link table => Result is MOD-Entry => store in temp_h |
{8'h38,10'bxx_xxxx_xxxx}: new_op = {addr_nop,8'h39, imme, src_x, 1'b1,temp_h, op_mov, 2'b00,2'b00, |
{8'h38,10'bxx_xxxx_xxxx}: new_op = {addr_nop,8'h39, imme, src_x, 1'b1,temp_h, op_mov, 2'b00,2'b00, 4'h0}; |
// Phase 57 : CXP : store and PUSH MOD prepare , Entry from Exception Processing |
{8'h39,10'bxx_xxxx_xxxx}: new_op = {push_op, 8'h3A, modul,stack, 1'b0,dest_x, op_wrp, 2'b00,2'b10, |
{8'h39,10'bxx_xxxx_xxxx}: new_op = {push_op, 8'h3A, modul,stack, 1'b0,dest_x, op_wrp, 2'b00,2'b10, 4'h1}; |
// Phase 58 : CXP : PUSH of MOD ongoing, PUSH PC prepare |
{8'h3A,10'bxx_xxxx_xxxx}: new_op = {ea_push, 8'h3B, rtmpl,src_x, 1'b0,dest_x, op_mov, 2'b00,2'b10, |
{8'h3A,10'bxx_xxxx_xxxx}: new_op = {ea_push, 8'h3B, rtmpl,src_x, 1'b0,dest_x, op_mov, 2'b00,2'b10, 4'h0}; |
// Phase 59 : CXP : New EA for PC |
{8'h3B,10'bxx_xxxx_xxxx}: new_op = {save_sp, 8'h3C, src_x,src_x, 1'b0,dest_x, op_mov, 2'b00,2'b00, |
{8'h3B,10'bxx_xxxx_xxxx}: new_op = {save_sp, 8'h3C, src_x,src_x, 1'b0,dest_x, op_mov, 2'b00,2'b00, 4'h1}; |
// Phase 60 : CXP : write of PC, calculate of Offset |
{8'h3C,10'bxx_xxxx_xxxx}: new_op = {rmod_8, 8'h3D, rtmph,rtmph, 1'b1,temp_l, op_flip,2'b00,2'b00, |
{8'h3C,10'bxx_xxxx_xxxx}: new_op = {rmod_8, 8'h3D, rtmph,rtmph, 1'b1,temp_l, op_flip,2'b00,2'b00, 4'h1}; |
// Phase 61 : CXP : read from (MOD:New+8) |
{8'h3D,10'bxx_xxxx_xxxx}: new_op = {ea_min8, 8'h3E, imme, rtmpl, 1'b1,temp_l, op_add, 2'b00,2'b00, |
{8'h3D,10'bxx_xxxx_xxxx}: new_op = {ea_min8, 8'h3E, imme, rtmpl, 1'b1,temp_l, op_add, 2'b00,2'b00, 4'h0}; // Reuse of EA |
// Phase 62 : CXP : EA Phase of SB read , new PC calculated |
{8'h3E,10'bxx_xxxx_xxxx}: new_op = {addr_nop,8'h3F, rtmpl,src_x, 1'b0,dest_x, op_mov, 2'b00,2'b00, |
{8'h3E,10'bxx_xxxx_xxxx}: new_op = {addr_nop,8'h3F, rtmpl,src_x, 1'b0,dest_x, op_mov, 2'b00,2'b00, 4'h1}; |
// Phase 63 : CXP : read of SB , new PC to ICache |
{8'h3F,10'bxx_xxxx_xxxx}: new_op = {addr_nop,8'h2F, imme, src_x, 1'b1,6'h1A, op_mov, 2'b00,2'b00, |
{8'h3F,10'bxx_xxxx_xxxx}: new_op = {addr_nop,8'h2F, imme, src_x, 1'b1,6'h1A, op_mov, 2'b00,2'b00, 4'h0}; // SB load |
// Phase 47 : CXP : Last phase update of MOD prepare |
{8'h2F,10'bxx_xxxx_xxxx}: new_op = {addr_nop,8'h00, rtmph,src_x, 1'b1,modul[5:0], op_mov, 2'b00,2'b |
{8'h2F,10'bxx_xxxx_xxxx}: new_op = {addr_nop,8'h00, rtmph,src_x, 1'b1,modul[5:0], op_mov, 2'b00,2'b00, 4'h0}; // MOD load |
|
// Phase 64 : RXP Entry : POP of PC , full Access |
{8'h40,10'bxx_xxxx_xxxx}: new_op = {pop_ru, 8'h41, imme, src_x, 1'b1,temp_h, op_mov, 2'b00,2'b00, |
{8'h40,10'bxx_xxxx_xxxx}: new_op = {pop_ru, 8'h41, imme, src_x, 1'b1,temp_h, op_mov, 2'b00,2'b00, 4'h0}; |
// Phase 65 : RXP : PC is read, next POP prepare |
{8'h41,10'bxx_xxxx_xxxx}: new_op = {adddisp, 8'h42, src_x,src_x, 1'b0,dest_x, op_mov, 2'b00,2'b00, |
{8'h41,10'bxx_xxxx_xxxx}: new_op = {adddisp, 8'h42, src_x,src_x, 1'b0,dest_x, op_mov, 2'b00,2'b00, 4'hF}; |
// Phase 66 : RXP : DISP is addeed to Stack and MOD is read |
{8'h42,10'bxx_xxxx_xxxx}: new_op = {addr_nop,8'h43, imme, src_x, 1'b1,modul[5:0], op_mov, 2'b00,2'b |
{8'h42,10'bxx_xxxx_xxxx}: new_op = {addr_nop,8'h43, imme, src_x, 1'b1,modul[5:0], op_mov, 2'b00,2'b00, 4'h0}; |
// Phase 67 : RXP : MOD is new |
{8'h43,10'bxx_xxxx_xxxx}: new_op = {rmod_rxp,8'h44, rtmph,modul, 1'b0,dest_x, op_mov, 2'b00,2'b00, |
{8'h43,10'bxx_xxxx_xxxx}: new_op = {rmod_rxp,8'h44, rtmph,modul, 1'b0,dest_x, op_mov, 2'b00,2'b00, 4'h1}; |
// Phase 68 : RXP : wait for SB data, parallel SP update |
{8'h44,10'bxx_xxxx_xxxx}: new_op = {addr_nop,8'h00, imme, src_x, 1'b1,6'h1A, op_mov, 2'b00,2'b00, |
{8'h44,10'bxx_xxxx_xxxx}: new_op = {addr_nop,8'h00, imme, src_x, 1'b1,6'h1A, op_mov, 2'b00,2'b00, 4'h0}; // SB load |
|
// Phase 69 : RETI : read of ICU for End-of-Interrupt Cycle , prepare read PC from Stack |
{8'h45,10'bxx_xxxx_xxxx}: new_op = {pop_op, 8'h46, src_x,stack, 1'b0,dest_x, op_mov, 2'b00,2'b00, |
{8'h45,10'bxx_xxxx_xxxx}: new_op = {pop_op, 8'h46, src_x,stack, 1'b0,dest_x, op_mov, 2'b00,2'b00, 4'h1}; |
// Phase 70 : RETI/ RETT Entry : POP of PC , full Access |
{8'h46,10'bxx_xxxx_xxxx}: new_op = {pop_ru, 8'h47, imme, src_x, 1'b1,temp_h, op_mov, 2'b00,2'b00, |
{8'h46,10'bxx_xxxx_xxxx}: new_op = {pop_ru, 8'h47, imme, src_x, 1'b1,temp_h, op_mov, 2'b00,2'b00, 4'h0}; |
// Phase 71 : RETI/RETT : PC is read, next POP prepare |
{8'h47,10'bxx_xxxx_xxxx}: new_op = {save_sp, 8'h48, src_x,src_x, 1'b0,dest_x, op_mov, 2'b00,2'b00, |
{8'h47,10'bxx_xxxx_xxxx}: new_op = {save_sp, 8'h48, src_x,src_x, 1'b0,dest_x, op_mov, 2'b00,2'b00, 4'h1}; |
// Phase 72 : RETI/RETT : DISP is added to Stack , PSR load and MOD is loaded if DE off |
{8'h48,10'bxx_xxxx_xxxx}: new_op = {addr_nop,8'h49, imme, src_x, no_modul, op_ldp, 2'b00,2'b00, 4' |
{8'h48,10'bxx_xxxx_xxxx}: new_op = {addr_nop,8'h49, imme, src_x, no_modul, op_ldp, 2'b00,2'b00, 4'h0}; |
// Phase 73 : RETI/RETT : different paths |
{8'h49,10'bxx_xxxx_xxxx}: new_op = de_flag ? |
( reti_flag ? |
1485,7 → 1485,7
: {addr_nop,8'h4B, src_x,src_x, 1'b0,dest_x, op_mov, 2'b00,2'b00, 4'h0} ) |
: {rmod_rtt,8'h4B, rtmph,modul, 1'b0,dest_x, op_mov, 2'b00,2'b00, 4'h1}; |
// Phase 74 : RETI/RETT : one pause cycle if DE on |
{8'h4A,10'bxx_xxxx_xxxx}: new_op = {addr_nop,8'h00, src_x,src_x, 1'b0,dest_x, op_mov, 2'b00,2'b00, |
{8'h4A,10'bxx_xxxx_xxxx}: new_op = {addr_nop,8'h00, src_x,src_x, 1'b0,dest_x, op_mov, 2'b00,2'b00, 4'h0}; |
// Phase 75 : RETI/RETT : SB read if DE off |
{8'h4B,10'bxx_xxxx_xxxx}: new_op = reti_flag ? |
{addr_nop,8'h00, imme, src_x, 1'b1,6'h1A, op_mov, 2'b00,2'b00, 4'h0} |
1493,14 → 1493,14
{adddispn,8'h4E, src_x,ttstak,1'b0,dest_x, op_mov, 2'b00,2'b00, 4'hE} |
: {adddispn,8'h4E, imme, ttstak,1'b1,6'h1A, op_mov, 2'b00,2'b00, 4'hE} ); |
// Phase 78 : RETT : SP update |
{8'h4E,10'bxx_xxxx_xxxx}: new_op = {save_sp, 8'h4A, rtmph,src_x, 1'b0,dest_x, op_mov, 2'b00,2'b00, |
{8'h4E,10'bxx_xxxx_xxxx}: new_op = {save_sp, 8'h4A, rtmph,src_x, 1'b0,dest_x, op_mov, 2'b00,2'b00, 4'h0}; |
|
// +++++++++++++++ special wait states for PSR and the Cache/MMU system +++++++++++ |
|
// Phase 76 : PSR in Word case simple delay of 2 cycles : 1. cycle does nothing |
{8'h4C,10'bxx_xxxx_xxxx}: new_op = {addr_nop,8'h4D, src_x,src_x, 1'b0,dest_x, op_mov, 2'b00,2'b00, |
// Phase 77 : PSR in Word case simple delay of 2 cycles : 2. cycle does Restart of instruction pro |
{8'h4D,10'bxx_xxxx_xxxx}: new_op = {addr_nop,8'h00, src_x,src_x, 1'b0,dest_x, op_mov, 2'b00,2'b00, |
{8'h4C,10'bxx_xxxx_xxxx}: new_op = {addr_nop,8'h4D, src_x,src_x, 1'b0,dest_x, op_mov, 2'b00,2'b00, 4'h0}; |
// Phase 77 : PSR in Word case simple delay of 2 cycles : 2. cycle does Restart of instruction processing |
{8'h4D,10'bxx_xxxx_xxxx}: new_op = {addr_nop,8'h00, src_x,src_x, 1'b0,dest_x, op_mov, 2'b00,2'b00, 4'h0}; |
// Phase 79 : Wait for INIT_DONE from Cachesystem |
{8'h4F,10'bxx_xxxx_xxxx}: new_op = (INIT_DONE | no_init) ? |
{addr_nop,8'h4D, src_x,src_x, 1'b0,dest_x, op_mov, 2'b00,2'b00, 4'h0} |
1509,16 → 1509,16
// +++++++++++++++ Direct Exception procession similar to CXP ++++++++++++++++++++ |
|
// Phase 121 : CXP : store and PUSH PSR prepare , Entry of Exception Processing |
{8'h79,10'bxx_xxxx_xxxx}: new_op = {push_op, 8'h7A, modul,stack, 1'b0,dest_x, op_wrp, 2'b00,2'b10, |
{8'h79,10'bxx_xxxx_xxxx}: new_op = {push_op, 8'h7A, modul,stack, 1'b0,dest_x, op_wrp, 2'b00,2'b10, 4'h1}; |
// Phase 122 : CXP : PUSH of PSR running, PUSH PC prepare - MOD like normal Exception-Flow |
{8'h7A,10'bxx_xxxx_xxxx}: new_op = {ea_push, 8'h7B, rtmpl,src_x, 1'b0,dest_x, op_mov, 2'b00,2'b10, |
// Phase 123 : CXP : New EA for PC , Output of Interrupt-Vector and LOAD_PC generation, continue a |
{8'h7B,10'bxx_xxxx_xxxx}: new_op = {save_sp, 8'h4A, rtmph,src_x, 1'b0,dest_x, op_mov, 2'b00,2'b00, |
{8'h7A,10'bxx_xxxx_xxxx}: new_op = {ea_push, 8'h7B, rtmpl,src_x, 1'b0,dest_x, op_mov, 2'b00,2'b10, 4'h0}; |
// Phase 123 : CXP : New EA for PC , Output of Interrupt-Vector and LOAD_PC generation, continue at standard exit |
{8'h7B,10'bxx_xxxx_xxxx}: new_op = {save_sp, 8'h4A, rtmph,src_x, 1'b0,dest_x, op_mov, 2'b00,2'b00, 4'h1}; |
|
// +++++++++++++++ here comes the general Exception Processing ++++++++++++++++++ |
|
// Phase 0 : Entry with saving of PC_ARCHI and PSR |
{8'h00,10'b11_xxxx_xxxx}: new_op = {save_pc, 8'h80, src_x,src_x, 1'b0,dest_x, op_psr, 2'b00,2'b00, |
{8'h00,10'b11_xxxx_xxxx}: new_op = {save_pc, 8'h80, src_x,src_x, 1'b0,dest_x, op_psr, 2'b00,2'b00, 4'h0}; |
// Phase 128 : different paths to three cases |
{8'h80,10'bxx_xxxx_xxxx}: new_op = abo_int ? |
{ai_next[30:4], src_x,src_x, 1'b1,temp_l, op_adr, 2'b00,2'b00, ai_next[3:0]} |
1528,7 → 1528,7
{addr_nop,8'h79, imme, src_x, 1'b1,temp_h, op_mov, 2'b00,2'b00, 4'h0} |
: {addr_nop,8'h39, imme, src_x, 1'b1,temp_h, op_mov, 2'b00,2'b00, 4'h0}; |
// Phase 130 : read of Interrupt-Vectors, Zero-Extension of Byte => TEMP_H |
{8'h82,10'bxx_xxxx_xxxx}: new_op = {addr_nop,8'h83, imme, src_x, 1'b1,temp_h, op_zex, 2'b00,2'b00, |
{8'h82,10'bxx_xxxx_xxxx}: new_op = {addr_nop,8'h83, imme, src_x, 1'b1,temp_h, op_zex, 2'b00,2'b00, 4'h0}; |
// Phase 131 : access of Exception-Vector |
{8'h83,10'bxx_xxxx_xxxx}: new_op = (type_nmi | ~ivec_flag) ? // NMI or non-vectored INT ? |
{get_vec, 8'h81, src_x,ibase, 1'b0,dest_x, op_mov, 2'b00,2'b00, 4'h1} |
1535,15 → 1535,15
: {get_veci,8'h81, rtmph,ibase, 1'b0,dest_x, op_mov, 2'b00,2'b00, 4'h1}; |
|
// Phase 132 : ABORT : store TEAR |
{8'h84,10'bxx_xxxx_xxxx}: new_op = {save_msr,8'h85, src_x,src_x, 1'b1,w_tear, op_adr, 2'b00,2'b00, |
{8'h84,10'bxx_xxxx_xxxx}: new_op = {save_msr,8'h85, src_x,src_x, 1'b1,w_tear, op_adr, 2'b00,2'b00, 4'h0}; |
// Phase 133 : store MSR |
{8'h85,10'bxx_xxxx_xxxx}: new_op = (ssrc_flag | sdest_flag) ? |
{addr_nop,rrepa, src_x,src_x, 1'b1,w_msr, op_adr, 2'b00,2'b00, 4'h0} |
: {get_vec ,8'h81, src_x,ibase, 1'b1,w_msr, op_adr, 2'b00,2'b00, 4'h1}; |
// Phase 134 : reload of pointers for string opcodes : R2 Dest |
{8'h86,10'bxx_xxxx_xxxx}: new_op = {addr_nop,8'h87, rtmp1,src_x, 1'b1,6'h02, op_mov, 2'b00,2'b00, |
{8'h86,10'bxx_xxxx_xxxx}: new_op = {addr_nop,8'h87, rtmp1,src_x, 1'b1,6'h02, op_mov, 2'b00,2'b00, 4'h0}; |
// Phase 135 : reload of pointers for string opcodes : R1 Source |
{8'h87,10'bxx_xxxx_xxxx}: new_op = {get_vec ,8'h81, rtmph,ibase, 1'b1,6'h01, op_mov, 2'b00,2'b00, |
{8'h87,10'bxx_xxxx_xxxx}: new_op = {get_vec ,8'h81, rtmph,ibase, 1'b1,6'h01, op_mov, 2'b00,2'b00, 4'h1}; |
|
// +++++++++++++++++ WAIT +++++++++++++++++++++++++++++++++ |
{8'h88,10'bxx_xxxx_xxxx}: new_op = interrupt ? |
1559,20 → 1559,20
|
{8'h00,10'b10_0xxx_xxxx}: new_op = state_0; |
// Now the case with Index , the Long Operand is copied to OUT |
{8'h00,10'b10_1xxx_xxxx}: new_op = {addr_nop,8'h50, src_1,src_1l,1'b0,dest_x, opera, 2'b00,~src2_f |
{8'h00,10'b10_1xxx_xxxx}: new_op = {addr_nop,8'h50, src_1,src_1l,1'b0,dest_x, opera, 2'b00,~src2_flag,2'b1_1,n_idx,1'b0}; |
|
{8'h5x,10'bxx_xxxx_xxxx}: new_op = state_group_50; // Gruppe 2 Opcodes |
{8'h6x,10'bxx_xxxx_xxxx}: new_op = state_group_60; // Gruppe 2 Opcodes |
|
// that is only for CVTP : |
{8'h73,10'bxx_xxxx_x0xx}: new_op = {addr_nop,8'h00, src_x,src_x, 1'b1,dest_r, op_adr, 2'b00,2'b00, |
{8'h73,10'bxx_xxxx_x1xx}: new_op = {adwr2, phwr2, irrw2,rega2, 1'b0,dest_x, op_adr, 2'b00,2'b10, |
{8'h73,10'bxx_xxxx_x0xx}: new_op = {addr_nop,8'h00, src_x,src_x, 1'b1,dest_r, op_adr, 2'b00,2'b00, 4'h0}; |
{8'h73,10'bxx_xxxx_x1xx}: new_op = {adwr2, phwr2, irrw2,rega2, 1'b0,dest_x, op_adr, 2'b00,2'b10, nxrw2}; |
|
// that is only for LMR and CINV : |
{8'h74,10'bxx_xxxx_xxxx}: new_op = (IC_READ | STOP_CINV) ? |
{ivar_adr,8'h74, rtmph,src_x, 1'b0,dest_x, op_mov, 2'b00,2'b00, 4'h0} // wait ... |
: {ivar_adr,8'h75, rtmph,src_x, 1'b1,lmrreg, op_lmr, 2'b00,2'b00, 4'h0}; // continue |
{8'h75,10'bxx_xxxx_xxxx}: new_op = {ivar_adr,8'h4F, rtmph,src_x, 1'b0,dest_x, op_mov, 2'b00,2'b00, |
{8'h75,10'bxx_xxxx_xxxx}: new_op = {ivar_adr,8'h4F, rtmph,src_x, 1'b0,dest_x, op_mov, 2'b00,2'b00, 4'h0}; |
|
// +++++++++++++++++ The String Opcodes +++++++++++++++++++++ |
|
1581,7 → 1581,7
{st_src, ph_str,rstr1,rstr1, ~kurz_st,temp_h, op_mov, 2'b00,2'b00, 4'h0} |
: {addr_nop,8'h00, src_x,src_x, 1'b0,dest_x, op_mov, 2'b00,2'b00, 4'h0}; |
// Phase 193 : 1. part read of SRC-Register => EA |
{8'hC1,10'bxx_xxxx_xxxx}: new_op = {st_len, 8'hC2, src_x,src_x, 1'b1,wstr1, op_adr, 2'b00,2'b00, |
{8'hC1,10'bxx_xxxx_xxxx}: new_op = {st_len, 8'hC2, src_x,src_x, 1'b1,wstr1, op_adr, 2'b00,2'b00, 4'h1}; |
// Phase 194 : memory operation : read |
{8'hC2,10'bxx_xxxx_xxxx}: new_op = mt_flag ? |
{addr_nop,8'hD3, imme, src_x, 1'b1,temp_2, (op_feld_reg[14] ? op_zex : op_mov), |
1588,11 → 1588,11
2'b00,2'b00, 4'h0} |
: {load_ea, 8'hC3, imme, rstr2, 1'b0,dest_x, op_mov, 2'b00,2'b10, 4'h0}; |
// Phase 195 : Data in output register and at the same time R2 to EA |
{8'hC3,10'bxx_xxxx_xxxx}: new_op = {st_dest, 8'hC4, rstr2,imme, ~kurz_st,temp_1, op_mov, 2'b00,2'b |
{8'hC3,10'bxx_xxxx_xxxx}: new_op = {st_dest, 8'hC4, rstr2,imme, ~kurz_st,temp_1, op_mov, 2'b00,2'b01, 4'h0}; |
// Phase 196 : 1. part reuse EA and LSD of 8B data to Out-Register |
{8'hC4,10'bxx_xxxx_xxxx}: new_op = {addr_nop,8'hC5, src_x,src_x, 1'b1,wstr2, op_adr, 2'b00,2'b00, |
{8'hC4,10'bxx_xxxx_xxxx}: new_op = {addr_nop,8'hC5, src_x,src_x, 1'b1,wstr2, op_adr, 2'b00,2'b00, 4'h1}; |
// Phase 197 : memory operation : write |
{8'hC5,10'bxx_xxxx_xxxx}: new_op = {addr_nop,8'hC7, rstr0,src_x, 1'b1,wstr0, op_str, 2'b00,2'b00, |
{8'hC5,10'bxx_xxxx_xxxx}: new_op = {addr_nop,8'hC7, rstr0,src_x, 1'b1,wstr0, op_str, 2'b00,2'b00, 4'h0}; |
// Phase 199 : Test for End and Interrupt |
{8'hC7,10'bxx_xxxx_xxxx}: new_op = (interrupt & ~kurz_st) ? |
{save_pc, 8'h80, src_x,src_x, 1'b0,dest_x, op_psr, 2'b00,2'b00, 4'h0} // Interrupt ! |
1601,7 → 1601,7
: {addr_nop,8'h00, src_x,src_x, 1'b0,dest_x, op_mov, 2'b00,2'b00, 4'h0} ); |
// String Compare : |
// Phase 201 : 1. part read of SRC-Register => EA |
{8'hC9,10'bxx_xxxx_xxxx}: new_op = {st_len, 8'hCA, src_x,src_x, 1'b1,wstr1, op_adr, 2'b00,2'b00, |
{8'hC9,10'bxx_xxxx_xxxx}: new_op = {st_len, 8'hCA, src_x,src_x, 1'b1,wstr1, op_adr, 2'b00,2'b00, 4'h1}; |
// Phase 202 : memory operation : read |
{8'hCA,10'bxx_xxxx_xxxx}: new_op = mt_flag ? |
{addr_nop,8'hDB, imme, src_x, 1'b1,temp_2, (op_feld_reg[14] ? op_zex : op_mov), |
1610,19 → 1610,19
{addr_nop,8'hC7, rstr0,src_x, 1'b1,wstr0, op_str, 2'b00,2'b00, 4'h0} |
: {load_ea, 8'hCB, imme, rstr2, 1'b1,temp_2, op_mov, 2'b00,2'b00, 4'h0} ); |
// Phase 203 : Data to output register and at the same time R2 to EA |
{8'hCB,10'bxx_xxxx_xxxx}: new_op = {st_src2, 8'hCC, rstr2,src_x, ~kurz_st,temp_1, op_mov, 2'b00,2'b |
{8'hCB,10'bxx_xxxx_xxxx}: new_op = {st_src2, 8'hCC, rstr2,src_x, ~kurz_st,temp_1, op_mov, 2'b00,2'b00, 4'h0}; |
// Phase 204 : 1. part reuse EA |
{8'hCC,10'bxx_xxxx_xxxx}: new_op = {addr_nop,8'hCD, src_x,src_x, 1'b1,wstr2, op_adr, 2'b00,2'b00, |
{8'hCC,10'bxx_xxxx_xxxx}: new_op = {addr_nop,8'hCD, src_x,src_x, 1'b1,wstr2, op_adr, 2'b00,2'b00, 4'h1}; |
// Phase 205 : memory operation : read and prepare compare |
{8'hCD,10'bxx_xxxx_xxxx}: new_op = {addr_nop,8'hCE, rtmp2,imme, 1'b0,dest_x, op_scp, 2'b00,2'b10, |
{8'hCD,10'bxx_xxxx_xxxx}: new_op = {addr_nop,8'hCE, rtmp2,imme, 1'b0,dest_x, op_scp, 2'b00,2'b10, 4'h0}; |
// Phase 206 : compare of data |
{8'hCE,10'bxx_xxxx_xxxx}: new_op = STRING[3] ? // Elements equal ? Same as ACB_ZERO without delay o |
{8'hCE,10'bxx_xxxx_xxxx}: new_op = STRING[3] ? // Elements equal ? Same as ACB_ZERO without delay of 1 cycle |
{addr_nop,8'hC7, rstr0,src_x, 1'b1,wstr0, op_str, 2'b00,2'b00, 4'h0} |
: ( kurz_st ? // at CMPM direct end |
{addr_nop,8'h00, src_x,src_x, 1'b0,dest_x, op_mov, 2'b00,2'b00, 4'h0} |
: {addr_nop,8'hC8, rtmph,src_x, 1'b1,6'h01, op_mov, 2'b00,2'b00, 4'h0} ); |
// Phase 200 : reload of R1 at CMPS, prepare reload of R2 |
{8'hC8,10'bxx_xxxx_xxxx}: new_op = {addr_nop,8'h00, rtmp1,src_x, 1'b1,6'h02, op_mov, 2'b00,2'b00, |
{8'hC8,10'bxx_xxxx_xxxx}: new_op = {addr_nop,8'h00, rtmp1,src_x, 1'b1,6'h02, op_mov, 2'b00,2'b00, 4'h0}; |
// String Options Match and Translate for MOVS |
// Phase 211 : Test if Translate |
{8'hD3,10'bxx_xxxx_xxxx}: new_op = op_feld_reg[14] ? // Translate ? Translate Base is Register 3 |
1629,15 → 1629,15
{st_trans,8'hD4, rtmp2,7'h03, 1'b0,dest_x, op_mov, 2'b00,2'b00, 4'h1} |
: {addr_nop,8'hD7, rtmp2,7'h04, 1'b0,dest_x, op_scp, 2'b00,2'b10, 4'h0}; // Match |
// Phase 212 : memory operation : read |
{8'hD4,10'bxx_xxxx_xxxx}: new_op = {addr_nop,8'hD5, imme, src_x, 1'b1,temp_2, op_mov, 2'b00,2'b10, |
{8'hD4,10'bxx_xxxx_xxxx}: new_op = {addr_nop,8'hD5, imme, src_x, 1'b1,temp_2, op_mov, 2'b00,2'b10, 4'h0}; |
// Phase 213 : Test if Match |
{8'hD5,10'bxx_xxxx_xxxx}: new_op = op_feld_reg[16] ? // Match ? Reference Value is Register 4 |
{addr_nop,8'hD7, rtmp2,7'h04, 1'b0,dest_x, op_scp, 2'b00,2'b10, 4'h0} |
: {st_trde, 8'hC4, 7'h02,7'h02, 1'b1,temp_1, op_mov, 2'b00,2'b00, 4'h0}; // back to MOVS |
// Phase 215 : Match result evaluation |
{8'hD7,10'bxx_xxxx_xxxx}: new_op = (STRING[3] ^ op_feld_reg[17]) ? // Not equal? (op_feld_reg[17] = |
{8'hD7,10'bxx_xxxx_xxxx}: new_op = (STRING[3] ^ op_feld_reg[17]) ? // Not equal? (op_feld_reg[17] = 1 = UNTIL) |
{load_ea, 8'hC3, rtmp2,7'h02, 1'b0,dest_x, op_mov, 2'b00,2'b10, 4'h0} // back to MOVS |
: {addr_nop,8'h00, rtmph,src_x, 1'b1,6'h01, op_mov, 2'b00,2'b00, 4'h0}; // Abort, R1 ba |
: {addr_nop,8'h00, rtmph,src_x, 1'b1,6'h01, op_mov, 2'b00,2'b00, 4'h0}; // Abort, R1 back |
// String Options Match and Translate for CMPS and SKPS - to many options to get it in one state |
// Phase 218 : Test if Translate |
{8'hDB,10'bxx_xxxx_xxxx}: new_op = op_feld_reg[14] ? // Translate ? Translate Base is Register 3 |
1644,19 → 1644,19
{st_trans,8'hDC, rtmp2,7'h03, 1'b0,dest_x, op_mov, 2'b00,2'b00, 4'h1} |
: {addr_nop,8'hDF, rtmp2,7'h04, 1'b0,dest_x, op_scp, 2'b00,2'b10, 4'h0}; // Match |
// Phase 220 : memory operation : read |
{8'hDC,10'bxx_xxxx_xxxx}: new_op = {addr_nop,8'hDD, imme, src_x, 1'b1,temp_2, op_mov, 2'b00,2'b10, |
{8'hDC,10'bxx_xxxx_xxxx}: new_op = {addr_nop,8'hDD, imme, src_x, 1'b1,temp_2, op_mov, 2'b00,2'b10, 4'h0}; |
// Phase 221 : Test if Match |
{8'hDD,10'bxx_xxxx_xxxx}: new_op = op_feld_reg[16] ? // Match ? Reference value is Register 4 |
{addr_nop,8'hDF, rtmp2,7'h04, 1'b0,dest_x, op_scp, 2'b00,2'b10, 4'h0} |
: ( skps_flag ? // SKPS read only String1 |
{addr_nop,8'hC7, 7'h00,src_x, 1'b1,6'h00, op_str, 2'b00,2'b00, 4'h0} // back to SKPS |
: {st_trs2, 8'hCC, 7'h02,7'h02, 1'b1,temp_1, op_mov, 2'b00,2'b00, 4'h0}); // back to CMP |
: {st_trs2, 8'hCC, 7'h02,7'h02, 1'b1,temp_1, op_mov, 2'b00,2'b00, 4'h0}); // back to CMPS |
// Phase 223 : Match result evaluation |
{8'hDF,10'bxx_xxxx_xxxx}: new_op = (STRING[3] ^ op_feld_reg[17]) ? // Not equal? (op_feld_reg[17] = |
{8'hDF,10'bxx_xxxx_xxxx}: new_op = (STRING[3] ^ op_feld_reg[17]) ? // Not equal? (op_feld_reg[17] = 1 = UNTIL) |
( skps_flag ? // SKPS read only String1 |
{addr_nop,8'hC7, 7'h00,src_x, 1'b1,6'h00, op_str, 2'b00,2'b00, 4'h0} // back to SKPS |
: {st_trs2, 8'hCC, 7'h02,7'h02, 1'b1,temp_1, op_mov, 2'b00,2'b00, 4'h0} ) // back to CMP |
: {addr_nop,8'h00, rtmph,src_x, 1'b1,6'h01, op_mov, 2'b00,2'b00, 4'h0}; // Abort, R1 ba |
: {st_trs2, 8'hCC, 7'h02,7'h02, 1'b1,temp_1, op_mov, 2'b00,2'b00, 4'h0} ) // back to CMPS |
: {addr_nop,8'h00, rtmph,src_x, 1'b1,6'h01, op_mov, 2'b00,2'b00, 4'h0}; // Abort, R1 back |
|
default : new_op = 67'hx_xxxx_xxxx_xxxx_xxxx; |
endcase |
1690,22 → 1690,22
|
always @(posedge BCLK) index_cmd <= (phase_reg == 8'h60); // that only for INDEX |
|
// WMASKE : SP always 32 Bit, opcodes in Format 1, Reg-Nr. >31 , INDEX opcodes and the CHECK operan |
assign WMASKE = {(spupd | format1 | wradr_i[5] | wmaske_i[1] | index_cmd | (oper_i[7:0] == 8'h83)), |
// WMASKE : SP always 32 Bit, opcodes in Format 1, Reg-Nr. >31 , INDEX opcodes and the CHECK operand too |
assign WMASKE = {(spupd | format1 | wradr_i[5] | wmaske_i[1] | index_cmd | (oper_i[7:0] == 8'h83)),wmaske_i[0]}; |
assign WRADR = spupd ? {~stack[5],stack[4:0]} : wradr_i; |
assign WREN = (spupd | wren_i) & no_trap; |
assign OPER = spupd ? op_adr : oper_i; |
|
always @(posedge BCLK) ACC_FELD[14] <= next & (new_op[64] | new_op[63] | new_op[62]); // NEWACC is |
always @(posedge BCLK) ACC_FELD[14] <= next & (new_op[64] | new_op[63] | new_op[62]); // NEWACC is important |
always @(posedge BCLK) ACC_FELD[9] <= next & new_op[62]; // LDEA is only one pulse |
|
always @(posedge BCLK) START <= next ? new_op[7:6] : 2'b00; |
always @(posedge BCLK) ldoreg <= next ? new_op[5:4] : 2'b00; // [1] = LD_OUT , [0] = LD_LDQ |
always @(posedge BCLK) wren_i <= next & new_op[25] & ~new_op[7]; // only if no START[1] from Long-O |
always @(posedge BCLK) wren_i <= next & new_op[25] & ~new_op[7]; // only if no START[1] from Long-Op |
|
assign LD_OUT = {(ldoreg[1] & no_trap),ldoreg[0]}; // [1] = LD_OUT (for CMP too) , [0] = LD_LDQ |
|
assign spupd = spupd_i & ~wren_i & ~ldoreg[1] & ~spu_block; // no Stack Update if OUT Register load |
assign spupd = spupd_i & ~wren_i & ~ldoreg[1] & ~spu_block; // no Stack Update if OUT Register load or already Write-Register |
|
assign do_long = new_op[7]; // START[1] for long_reg |
|
1712,7 → 1712,7
assign RDAA = {next,new_op[39:33]}; // Source 1 |
assign RDAB = {next,new_op[32:26]}; // Source 2 |
|
always @(posedge BCLK) if (next) WR_REG = new_op[25] & new_op[7]; // START[1] : if WR then LONG pat |
always @(posedge BCLK) if (next) WR_REG = new_op[25] & new_op[7]; // START[1] : if WR then LONG path has register as Destination |
|
// special case : example is POLYL F2,TOS |
always @(posedge BCLK) spu_block <= DONE & WR_REG; |
1721,20 → 1721,20
|
// only the real access gets USER Status : important for Memory Relative & External |
always @(posedge BCLK) // MOVUS MOVSU RDVAL/WRVAL |
if (ACC_FELD[14]) dc_user <= PSR[8] | (m_ussu & (m_usel ? (phase_reg == 8'h07) : (phase_reg == 8'h |
if (ACC_FELD[14]) dc_user <= PSR[8] | (m_ussu & (m_usel ? (phase_reg == 8'h07) : (phase_reg == 8'h27))) | RWVAL[1]; |
else dc_user <= dc_user & ~abort; |
|
always @(posedge BCLK) dc_ilo <= op_ilo & (phase_reg == 8'h59); |
always @(posedge BCLK) ILO <= op_ilo & ((phase_reg == 8'h59) | (phase_reg == 8'h27)); |
|
assign RWVAL = {dc_ilo,(rwval_flag & (phase_reg == 8'h53)),wrval_flag}; // is used for DCACHE ILO t |
assign RWVAL = {dc_ilo,(rwval_flag & (phase_reg == 8'h53)),wrval_flag}; // is used for DCACHE ILO too |
|
// Signals for the I_PATH + Debug |
assign DETOIP = {pc_match,cmps_flag,ph_match,op_feld_reg[17],kill_opt,inss_op,exin_cmd,extract,bit_ |
assign DETOIP = {pc_match,cmps_flag,ph_match,op_feld_reg[17],kill_opt,inss_op,exin_cmd,extract,bit_reg,kurz_st,dw_info,acb_reg,t2p}; |
|
// Signals for the ADDR_UNIT : [5]=RMW Signal |
assign chk_rmw = (phase_reg == 8'h17) | (phase_reg == 8'h58) | ((phase_reg == 8'h59) & rw_bit); // |
assign INFO_AU = {no_trap,chk_rmw,(op_feld_reg[40:39] == 2'b11),RWVAL[1],(a_ivar & ~IC_READ),dc_use |
assign chk_rmw = (phase_reg == 8'h17) | (phase_reg == 8'h58) | ((phase_reg == 8'h59) & rw_bit); // right Gruppe 2 opcodes |
assign INFO_AU = {no_trap,chk_rmw,(op_feld_reg[40:39] == 2'b11),RWVAL[1],(a_ivar & ~IC_READ),dc_user,disp_ok}; |
|
assign RESTART = (phase_reg == 8'h4D); |
|
1747,7 → 1747,7
|
GRUPPE_2 reste_ops (.BCLK(BCLK), .PHASE_0(PHASE_0), .OPREG(OPREG[13:0]), .PHASE(phase_ein[3:0]), |
.SRC_1(src_1), .SRC_2(src_2), .REGA1(rega1), .REGA2(rega2), .IRRW1(irrw1), .IRRW2(irrw2), |
.ADRD1(adrd1), .ADRD2(adrd2), .EXR12(exr12), .EXR22(exr22), .PHRD1(phrd1[3:0]), .PHRD2(phrd2[3 |
.ADRD1(adrd1), .ADRD2(adrd2), .EXR12(exr12), .EXR22(exr22), .PHRD1(phrd1[3:0]), .PHRD2(phrd2[3:0]), |
.NXRD1(nxrd1), .NXRW2(nxrw2), .ACCA({acc1,1'b0,acc2,1'b0}), .OPERA(opera), |
.STATE_0(state_0), .STATE_GROUP_50(state_group_50), .STATE_GROUP_60(state_group_60) ); |
|
/m32632/trunk/rtl/REGISTERS.v
37,14 → 37,14
// 2. FP_STAT_REG Floating Point Status Register |
// 3. REGISTER General Purpose Registers |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// |
// 1. CONFIG_REGS Configuration and Debug Registers |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module CONFIG_REGS ( BCLK, BRESET, WREN, LD_OUT, OPCODE, SRC1, WRADR, PC_ARCHI, USER, PCMATCH, DBG_H |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module CONFIG_REGS ( BCLK, BRESET, WREN, LD_OUT, OPCODE, SRC1, WRADR, PC_ARCHI, USER, PCMATCH, DBG_HIT, READ, |
CFG, MCR, PTB_WR, PTB_SEL, IVAR, CINV, Y_INIT, DSR, DBG_TRAPS, DBG_IN ); |
|
input BCLK,BRESET; |
105,7 → 105,7
// The Cache content will be invalid if the Enable-Bit is set to 0 |
always @(posedge BCLK) old_cfg <= {CFG[11],CFG[9]}; |
|
// Cache Invalidate : the Flags are coming out of the Short-field which is otherwise used for Regis |
// Cache Invalidate : the Flags are coming out of the Short-field which is otherwise used for Register selection |
always @(posedge BCLK) ci_all <= do_cinv & WRADR[2] ? WRADR[1:0] : 2'b0; // clear all |
always @(posedge BCLK) ci_line <= do_cinv & ~WRADR[2] ? WRADR[1:0] : 2'b0; // clear cache line |
|
145,7 → 145,7
always @(posedge BCLK) if (ld_car) car <= SRC1[31:2]; |
|
// DEN SD DEN UD CAE CRD CAE CWR VNP/CBE CAR |
assign DBG_IN = {(dcr[12] & dcr[11]),(dcr[12] & dcr[10]),(dcr[7] & dcr[6]),(dcr[7] & dcr[5]),dcr[4: |
assign DBG_IN = {(dcr[12] & dcr[11]),(dcr[12] & dcr[10]),(dcr[7] & dcr[6]),(dcr[7] & dcr[5]),dcr[4:0],car}; |
|
always @(posedge BCLK or negedge BRESET) |
if (!BRESET) DSR <= 4'd0; |
165,12 → 165,12
|
endmodule |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// |
// 2. FP_STAT_REG Floating Point Status Register |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module FP_STAT_REG ( BCLK, BRESET, LFSR, UP_SP, UP_DP, TT_SP, TT_DP, WREN, WRADR, DIN, FSR, TWREN, F |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module FP_STAT_REG ( BCLK, BRESET, LFSR, UP_SP, UP_DP, TT_SP, TT_DP, WREN, WRADR, DIN, FSR, TWREN, FPU_TRAP, SAVE_PC); |
|
input BCLK; |
input BRESET; |
258,11 → 258,11
|
endmodule |
|
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// |
// 3. REGISTER General Purpose Registers |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
module REGISTER( BCLK, ENWR, DOWR, BYDIN, DIN, RADR, WADR, WMASKE, DOUT, SELI ); |
|
input BCLK; |
/m32632/trunk/rtl/DCACHE.v
35,12 → 35,12
// Modules contained in this file: |
// DCACHE the data cache of M32632 |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
|
module DCACHE( BCLK, MCLK, WRCFG, MDONE, BRESET, PTB_WR, PTB_SEL, IO_READY, REG_OUT, PSR_USER, WRIT |
WAMUX, ENWR, IC_PREQ, FILLRAM, CFG, CINVAL, DMA_AA, DP_Q, DRAM_Q, IC_VA, ICTODC, IO_Q, IVAR, MCR |
PACKET, SIZE, VADR, WADDR, WCTRL, IO_RD, IO_WR, DRAM_ACC, DRAM_WR, INIT_RUN, PTE_STAT, KDET, HLD |
ACC_STAT, DP_DI, DRAM_A, DRAM_DI, IACC_STAT, IC_SIGS, IO_A, IO_BE, IO_DI, KOLLI_A, MMU_DIN, ZTES |
module DCACHE( BCLK, MCLK, WRCFG, MDONE, BRESET, PTB_WR, PTB_SEL, IO_READY, REG_OUT, PSR_USER, WRITE, READ, RMW, |
WAMUX, ENWR, IC_PREQ, FILLRAM, CFG, CINVAL, DMA_AA, DP_Q, DRAM_Q, IC_VA, ICTODC, IO_Q, IVAR, MCR_FLAGS, |
PACKET, SIZE, VADR, WADDR, WCTRL, IO_RD, IO_WR, DRAM_ACC, DRAM_WR, INIT_RUN, PTE_STAT, KDET, HLDA, |
ACC_STAT, DP_DI, DRAM_A, DRAM_DI, IACC_STAT, IC_SIGS, IO_A, IO_BE, IO_DI, KOLLI_A, MMU_DIN, ZTEST, |
RWVAL, RWVFLAG, DBG_IN, DBG_HIT, ENDRAM ); |
|
input BCLK; |
/m32632/trunk/rtl/ADDR_UNIT.v
35,11 → 35,11
// Modules contained in this file: |
// ADDR_UNIT generates data access addresses and controls data cache operation |
// |
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
|
module ADDR_UNIT ( BCLK, BRESET, READ, WRITE, LDEA, NEWACC, CLRMSW, POST, DISP_OK, FULLACC, SRC2SEL, |
DISP, PC_ARCHI, PC_ICACHE, IO_READY, ACC_STAT, MMU_UPDATE, IC_TEX, ABO_STAT, ADIVAR, RWVAL_1, |
NO_TRAP, FPU_TRAP, READ_OUT, WRITE_OUT, ZTEST, RMW, VADR, ADDR, SIZE, PACKET, ACC_DONE, ABORT |
module ADDR_UNIT ( BCLK, BRESET, READ, WRITE, LDEA, NEWACC, CLRMSW, POST, DISP_OK, FULLACC, SRC2SEL, INDEX, ASIZE, SRC1, SRC2, BWD, |
DISP, PC_ARCHI, PC_ICACHE, IO_READY, ACC_STAT, MMU_UPDATE, IC_TEX, ABO_STAT, ADIVAR, RWVAL_1, OP_RMW, PHASE_17, |
NO_TRAP, FPU_TRAP, READ_OUT, WRITE_OUT, ZTEST, RMW, VADR, ADDR, SIZE, PACKET, ACC_DONE, ABORT, REG_OUT, BITSEL ); |
|
input BCLK,BRESET; |
input READ,WRITE,LDEA; |
131,7 → 131,7
|
always @(posedge BCLK) ABORT <= acc_err; // Signal to Steuerung - only a pulse |
|
always @(posedge BCLK) if (acc_err) tex_feld <= ACC_STAT[3] ? 2'b11 : {~ACC_STAT[2],ACC_STAT[2]}; / |
always @(posedge BCLK) if (acc_err) tex_feld <= ACC_STAT[3] ? 2'b11 : {~ACC_STAT[2],ACC_STAT[2]}; // for MSR |
always @(posedge BCLK) if (acc_err) u_ddt <= {RMW,ABO_STAT[1],(WRITE_OUT | ZTEST)}; |
|
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ |
138,13 → 138,13
|
always @(SRC2SEL or CLRMSW or SRC2 or PC_ARCHI or ea_reg) |
case (SRC2SEL) |
2'b00 : source2 = {(CLRMSW ? 16'h0000 : SRC2[31:16]),SRC2[15:0]}; // base reg, External Addressi |
2'b00 : source2 = {(CLRMSW ? 16'h0000 : SRC2[31:16]),SRC2[15:0]}; // base reg, External Addressing with MOD |
2'b01 : source2 = PC_ARCHI; // PC relative |
2'b10 : source2 = 32'h0; // Absolute Addressing |
2'b11 : source2 = ea_reg; // REUSE : 2. TOS |
endcase |
|
assign index_sel = POST ? 4'h0 : INDEX; // Alternative application of Index for POST Adder : POP fr |
assign index_sel = POST ? 4'h0 : INDEX; // Alternative application of Index for POST Adder : POP from Stack |
|
always @(BWD or SRC1) |
casex (BWD) |
168,7 → 168,7
|
assign final_addr = reg_adder + DISP; // That's the final access address |
|
always @(posedge BCLK) if (LDEA && (index_sel[3:2] == 2'b11)) BITSEL <= SRC1[2:0]; // for Bit Opcod |
always @(posedge BCLK) if (LDEA && (index_sel[3:2] == 2'b11)) BITSEL <= SRC1[2:0]; // for Bit Opcodes in I_PFAD |
|
always @(INDEX) // SP POP Operation & String Backward |
case (INDEX[2:0]) |
209,7 → 209,7
assign ADDR = ea_reg; // used for ADDR opcode and TOS Addressing |
|
// This pulse stores all parameters of access |
assign init_acc = ((FULLACC ? (NEWACC & acc_ende) : acc_ende) | ~acc_run) & DISP_OK & (READ | WRITE |
assign init_acc = ((FULLACC ? (NEWACC & acc_ende) : acc_ende) | ~acc_run) & DISP_OK & (READ | WRITE) & ~ABORT & NO_TRAP; |
|
assign fa_out = init_acc | ADIVAR; // special case for LMR IVAR,... |
|
249,7 → 249,7
always @(posedge BCLK or negedge BRESET) |
if (!BRESET) write_reg <= 1'b0; |
else |
write_reg <= (init_acc ? (WRITE & ~RWVAL_1 & ~pg_test) : (write_reg & ~acc_ende & ~acc_err & ~FPU |
write_reg <= (init_acc ? (WRITE & ~RWVAL_1 & ~pg_test) : (write_reg & ~acc_ende & ~acc_err & ~FPU_TRAP)) | do_wr; |
|
assign WRITE_OUT = write_reg & ~FPU_TRAP; |
|
257,7 → 257,7
always @(posedge BCLK or negedge BRESET) |
if (!BRESET) ZTEST <= 1'b0; |
else |
ZTEST <= pg_op ? (~ZTEST | (~acc_pass & ~acc_err)) : (init_acc ? RWVAL_1 : (ZTEST & ~acc_ende & |
ZTEST <= pg_op ? (~ZTEST | (~acc_pass & ~acc_err)) : (init_acc ? RWVAL_1 : (ZTEST & ~acc_ende & ~acc_err)); |
|
always @(posedge BCLK or negedge BRESET) |
if (!BRESET) RMW <= 1'b0; |
278,7 → 278,7
|
assign inc_pack = (PACKET[1:0] == 2'b00) ? 2'b10 : {(SIZE[1] ^ SIZE[0]),(SIZE[1] & SIZE[0])}; |
|
// Counter for data packets 1 to 3 : special case aligned QWORD : only 2 packets. Additionally star |
// Counter for data packets 1 to 3 : special case aligned QWORD : only 2 packets. Additionally start address in bits 1 und 0. |
// special coding (00) -> [01] -> (10) , [01] optional by QWORD and (10) shows always the end |
always @(posedge BCLK) |
if (init_acc) PACKET <= {2'b00,final_addr[1:0]}; |
298,19 → 298,19
default : acc_ende = 1'b0; |
endcase |
|
assign in_page = (vadr_reg[11:3] != 9'h1FF); // Access inside a page ? During WRITE address is incr |
assign in_page = (vadr_reg[11:3] != 9'h1FF); // Access inside a page ? During WRITE address is increasing : 1. LSD 2. MSD |
|
always @(SIZE or vadr_reg or in_page or PACKET) |
casex (SIZE) |
2'b01 : frueh_ok = (vadr_reg[3:2] != 2'b11); //Word |
2'b10 : frueh_ok = (vadr_reg[3:2] != 2'b11); //DWord |
2'b11 : frueh_ok = (PACKET[1:0] == 2'b00) ? (~vadr_reg[3] | ~vadr_reg[2]) : ((PACKET[3:2] == 2'b |
2'b11 : frueh_ok = (PACKET[1:0] == 2'b00) ? (~vadr_reg[3] | ~vadr_reg[2]) : ((PACKET[3:2] == 2'b01) & (vadr_reg[3:2] != 2'b11)); |
default : frueh_ok = 1'b1; // Byte don't case |
endcase |
|
assign all_ok = SIZE[1] ? (PACKET[1:0] == 2'b00) : (PACKET[1:0] != 2'b11); // for DWord : Word |
|
always @(SIZE or READ_OUT or frueh_ok or PACKET or all_ok or io_acc or acc_ok or qwa_flag or io_rdy |
always @(SIZE or READ_OUT or frueh_ok or PACKET or all_ok or io_acc or acc_ok or qwa_flag or io_rdy or ca_hit) |
casex ({SIZE,READ_OUT,frueh_ok,PACKET[3],io_acc,all_ok}) |
7'b00_xxxx_x : acc_step = acc_ok; // Byte, all ok |
// |
326,7 → 326,7
// fast QWord READ : there would be a 2. acc_step if not ~PACK... |
7'b11_1xxx_x : acc_step = acc_ok & ( (qwa_flag & ~io_rdy & ca_hit) ? ~PACKET[3] : PACKET[3] ); |
7'b11_0x1x_x : acc_step = acc_ok; |
7'b11_0100_x : acc_step = acc_ok; // WRITE Adr. perfect - acc_step after 1. packet if not io_a |
7'b11_0100_x : acc_step = acc_ok; // WRITE Adr. perfect - acc_step after 1. packet if not io_acc |
default : acc_step = 1'b0; |
endcase |
|
338,7 → 338,7
// The final DONE Multiplexer |
assign ACC_DONE = acc_run ? (acc_step & ~no_done) : ea_ok; |
|
always @(posedge BCLK) reg_out_i <= ~acc_step & BRESET & ((qwa_flag & (io_rdy | ~ca_hit) & acc_ok) |
always @(posedge BCLK) reg_out_i <= ~acc_step & BRESET & ((qwa_flag & (io_rdy | ~ca_hit) & acc_ok) | reg_out_i); |
|
always @(posedge BCLK) io_rdy <= IO_READY & (WRITE_OUT | READ_OUT); |
|