OpenCores
URL https://opencores.org/ocsvn/6809_6309_compatible_core/6809_6309_compatible_core/trunk

Subversion Repositories 6809_6309_compatible_core

[/] [6809_6309_compatible_core/] [trunk/] [rtl/] [verilog/] [regblock.v] - Diff between revs 6 and 9

Go to most recent revision | Show entire file | Details | Blame | View Log

Rev 6 Rev 9
Line 28... Line 28...
        input wire set_e,
        input wire set_e,
        input wire clear_e,
        input wire clear_e,
        output wire [7:0] CCR_o,
        output wire [7:0] CCR_o,
        output reg [15:0] path_left_data,
        output reg [15:0] path_left_data,
        output reg [15:0] path_right_data,
        output reg [15:0] path_right_data,
        output reg [15:0] eamem_addr,
        output wire [15:0] eamem_addr_o,
        output wire [15:0] reg_pc,
        output wire [15:0] reg_pc,
        output wire [7:0] reg_dp,
        output wire [7:0] reg_dp,
        output wire [15:0] reg_su
        output wire [15:0] reg_su
        );
        );
 
 
Line 48... Line 48...
reg [7:0] DP;
reg [7:0] DP;
`define CCR { eflag, fflag, hflag, intff, nff, zff, vff, cff }
`define CCR { eflag, fflag, hflag, intff, nff, zff, vff, cff }
 
 
reg eflag, fflag, hflag;
reg eflag, fflag, hflag;
reg intff, nff, zff, vff, cff;
reg intff, nff, zff, vff, cff;
reg [15:0] ea_reg, ea_reg_post;
wire [15:0] eamem_addr, ea_reg_post;
 
 
assign CCR_o = `CCR;
assign CCR_o = `CCR;
assign reg_pc = PC;
assign reg_pc = PC;
assign reg_dp = DP;
assign reg_dp = DP;
assign reg_su = (use_s) ? SS:SU; /* stack pointer */
assign reg_su = (use_s) ? SS:SU; /* stack pointer */
 
 
 
calc_ea ea(eapostbyte,
 
                        offset16,
 
                        ACCA,
 
                        ACCB,
 
                        IX,
 
                        IY,
 
                        SS,
 
                        SU,
 
                        PC,
 
                        eamem_addr,
 
                        ea_reg_post);
 
 
 
assign eamem_addr_o = eamem_addr;
 
 
// left path output, always 16 bits
// left path output, always 16 bits
always @(*)
always @(*)
        begin
        begin
                case (path_left_addr)
                case (path_left_addr)
                        `RN_ACCA:       path_left_data = { 8'hff, ACCA };
                        `RN_ACCA:       path_left_data = { 8'hff, ACCA };
Line 84... Line 99...
                        `RN_ACCD:       path_right_data = `ACCD;
                        `RN_ACCD:       path_right_data = `ACCD;
                        `RN_IX:         path_right_data = IX;
                        `RN_IX:         path_right_data = IX;
                        `RN_IY:         path_right_data = IY;
                        `RN_IY:         path_right_data = IY;
                        `RN_U:          path_right_data = SU;
                        `RN_U:          path_right_data = SU;
                        `RN_S:          path_right_data = SS;
                        `RN_S:          path_right_data = SS;
 
                        `RN_PC:         path_right_data = PC;
                        `RN_DP:         path_right_data = { DP, DP };
                        `RN_DP:         path_right_data = { DP, DP };
                        `RN_CC:         path_right_data = { `CCR, `CCR };
                        `RN_CC:         path_right_data = { `CCR, `CCR };
                        default:
                        default:
                                path_right_data = 16'hFFFF;
                                path_right_data = 16'hFFFF;
                endcase
                endcase
        end
        end
 
 
 
wire [15:0] left, right;
 
wire [3:0] right_reg;
 
wire [15:0] pc_plus_1;
 
assign pc_plus_1 = PC + 16'h0001;
 
 
 
assign left = (write_tfr | write_exg) ? path_left_data:data_w;
 
 
 
assign right = (inc_pc) ? pc_plus_1:path_right_data;
 
 
 
assign right_reg = (inc_pc | write_pc) ? `RN_PC:exg_dest_r;
 
 
 
always @(posedge clk_in)
 
        begin
 
                if (write_exg | inc_pc | write_pc)
 
                        case (right_reg)
 
                                0: `ACCD <= right;
 
                                1: IX <= right;
 
                                2: IY <= right;
 
                                3: SU <= right;
 
                                4: SS <= right;
 
                                5: PC <= right;
 
                                8: ACCA <= right[7:0];
 
                                9: ACCB <= right[7:0];
 
                                10: `CCR <= right[7:0];
 
                                11: DP <= right[7:0];
 
                        endcase
 
                if (write_tfr | write_exg | write_reg)
 
                        case (write_reg_addr)
 
                                0: `ACCD <= left;
 
                                1: IX <= left;
 
                                2: IY <= left;
 
                                3: SU <= left;
 
                                4: SS <= left;
 
                                5: PC <= left;
 
                                8: ACCA <= left[7:0];
 
                                9: ACCB <= left[7:0];
 
                                10: `CCR <= left[7:0];
 
                                11: DP <= left[7:0];
 
                        endcase
 
                if (write_post) // write back predecrement/postincremented values
 
                        begin
 
                                case (eapostbyte[6:5])
 
                                        2'b00: IX <= ea_reg_post;
 
                                        2'b01: IY <= ea_reg_post;
 
                                        2'b10: SU <= ea_reg_post;
 
                                        2'b11: SS <= ea_reg_post;
 
                                endcase
 
                        end
 
                if (write_flags)
 
                        begin
 
                                `CCR <= CCR_in;
 
                        end
 
                if (set_e | clear_e) eflag <= set_e;
 
                //if (clear_e) eflag <= 0;
 
                if (write_pc) PC <= new_pc;
 
                //if (inc_pc) PC <= PC + 16'h1;
 
                if (inc_su)
 
                        if (use_s) SS <= SS + 16'h1;
 
                        else SU <= SU + 16'h1;
 
                if (dec_su)
 
                        if (use_s) SS <= SS - 16'h1;
 
                        else SU <= SU - 16'h1;
 
        end
 
 
 
`ifdef SIMULATION
 
initial
 
        begin
 
                PC = 16'hfffe;
 
                DP = 8'h00;
 
                IX = 16'h0;
 
                `CCR = 0;
 
                IY = 16'hA55A;
 
                SS = 16'h0f00;
 
                SU = 16'h0e00;
 
        end
 
`endif
 
endmodule
 
 
 
 
 
module calc_ea(
 
        input wire [7:0] eapostbyte,
 
        input wire [15:0] offset16,
 
        input wire [7:0] acca,
 
        input wire [7:0] accb,
 
        input wire [15:0] ix,
 
        input wire [15:0] iy,
 
        input wire [15:0] s,
 
        input wire [15:0] u,
 
        input wire [15:0] pc,
 
        output wire [15:0] eamem_addr_o,
 
        output wire [15:0] ea_reg_post_o
 
        );
 
 
 
reg [15:0] ea_reg, ea_reg_post, eamem_addr;
 
 
 
assign eamem_addr_o = eamem_addr;
 
assign ea_reg_post_o = ea_reg_post;
 
 
always @(*)
always @(*)
        begin
        begin
                case (eapostbyte[6:5])
                case (eapostbyte[6:5])
                        2'b00: ea_reg = IX;
                        2'b00: ea_reg = ix;
                        2'b01: ea_reg = IY;
                        2'b01: ea_reg = iy;
                        2'b10: ea_reg = SU;
                        2'b10: ea_reg = u;
                        2'b11: ea_reg = SS;
                        2'b11: ea_reg = s;
                endcase
                endcase
        end
        end
// pre-decrement/postincrement
// pre-decrement/postincrement
always @(*)
always @(*)
        begin
        begin
                ea_reg_post = ea_reg;
                case (eapostbyte[1:0])
                casex (eapostbyte)
                        2'b00: ea_reg_post = ea_reg + 16'h1;
                        8'b1xxx0000: ea_reg_post = ea_reg + 16'h1;
                        2'b01: ea_reg_post = ea_reg + 16'h2;
                        8'b1xxx0001: ea_reg_post = ea_reg + 16'h2;
                        2'b10: ea_reg_post = ea_reg - 16'h1;
                        8'b1xxx0010: ea_reg_post = ea_reg - 16'h1;
                        2'b11: ea_reg_post = ea_reg - 16'h2;
                        8'b1xxx0011: ea_reg_post = ea_reg - 16'h2;
 
                        //default: ea_reg_post = ea_reg;
 
                endcase
                endcase
        end
        end
 
 
/* EA calculation
/* EA calculation
 * postbyte  bytes  assembler
 * postbyte  bytes  assembler
Line 152... Line 264...
                                eamem_addr = ea_reg;
                                eamem_addr = ea_reg;
                        8'b1xx_x_0010, // pre decrement
                        8'b1xx_x_0010, // pre decrement
                        8'b1xx_x_0011: // pre decrement
                        8'b1xx_x_0011: // pre decrement
                                eamem_addr = ea_reg_post; // gets precalculated pre-decremented address
                                eamem_addr = ea_reg_post; // gets precalculated pre-decremented address
                        8'b1xx_x_0101: // B,R
                        8'b1xx_x_0101: // B,R
                                eamem_addr = ea_reg + { {8{ACCB[7]}}, ACCB };
                                eamem_addr = ea_reg + { {8{accb[7]}}, accb };
                        8'b1xx_x_0110: // A,R
                        8'b1xx_x_0110: // A,R
                                eamem_addr = ea_reg + { {8{ACCA[7]}}, ACCA };
                                eamem_addr = ea_reg + { {8{acca[7]}}, acca };
                        8'b1xx_x_1011: // D,R
                        8'b1xx_x_1011: // D,R
                                eamem_addr = ea_reg + `ACCD;
                                eamem_addr = ea_reg + { acca, accb };
                        8'b1xx_x_1000: // n,R 8 bit offset
                        8'b1xx_x_1000: // n,R 8 bit offset
                                eamem_addr = ea_reg + { offset16[7] ? 8'hff:8'h0, offset16[7:0] }; // from postbyte1
                                eamem_addr = ea_reg + { offset16[7] ? 8'hff:8'h0, offset16[7:0] }; // from postbyte1
                        8'b1xx_x_1001: // n,R // 16 bit offset
                        8'b1xx_x_1001: // n,R // 16 bit offset
                                eamem_addr = ea_reg + offset16;
                                eamem_addr = ea_reg + offset16;
                        8'b1xx_x_1100: // n,PC
                        8'b1xx_x_1100: // n,PC
                                eamem_addr = PC + { offset16[7] ? 8'hff:8'h0, offset16[7:0] };
                                eamem_addr = pc + { offset16[7] ? 8'hff:8'h0, offset16[7:0] };
                        8'b1xx_x_1101: // n,PC
                        8'b1xx_x_1101: // n,PC
                                eamem_addr = PC + offset16;
                                eamem_addr = pc + offset16;
                endcase
                endcase
        end
        end
 
 
wire [15:0] left;
 
 
 
assign left = (write_tfr | write_exg) ? path_left_data:data_w;
 
 
 
//wire [15:0] new_su, old_su;
 
 
 
//assign old_su = (use_s) ? SS:SU;
 
//assign new_su = (inc_su) ? old_su + 16'h1:(dec_su) ? old_su - 16'h1:old_su;
 
 
 
always @(posedge clk_in)
 
        begin
 
                if (write_exg)
 
                        case (exg_dest_r)
 
                                0: `ACCD <= path_right_data;
 
                                1: IX <= path_right_data;
 
                                2: IY <= path_right_data;
 
                                3: SU <= path_right_data;
 
                                4: SS <= path_right_data;
 
                                5: PC <= path_right_data;
 
                                8: ACCA <= path_right_data[7:0];
 
                                9: ACCB <= path_right_data[7:0];
 
                                10: `CCR <= path_right_data[7:0];
 
                                11: DP <= path_right_data[7:0];
 
                        endcase
 
                if (write_tfr | write_exg | write_reg)
 
                        case (write_reg_addr)
 
                                0: `ACCD <= left;
 
                                1: IX <= left;
 
                                2: IY <= left;
 
                                3: SU <= left;
 
                                4: SS <= left;
 
                                5: PC <= left;
 
                                8: ACCA <= left[7:0];
 
                                9: ACCB <= left[7:0];
 
                                10: `CCR <= left[7:0];
 
                                11: DP <= left[7:0];
 
                        endcase
 
                if (write_post) // write back predecrement/postincremented values
 
                        begin
 
                                case (eapostbyte[6:5])
 
                                        2'b00: IX <= ea_reg_post;
 
                                        2'b01: IY <= ea_reg_post;
 
                                        2'b10: SU <= ea_reg_post;
 
                                        2'b11: SS <= ea_reg_post;
 
                                endcase
 
                        end
 
                if (write_flags)
 
                        begin
 
                                `CCR <= CCR_in;
 
                        end
 
                if (set_e) eflag <= 1;
 
                if (clear_e) eflag <= 0;
 
                if (write_pc) PC <= new_pc;
 
                if (inc_pc) PC <= PC + 16'h1;
 
/*
 
                if (inc_su | dec_su)
 
                        begin
 
                                if (use_s) SS <= new_su;
 
                                else SU <= new_su;
 
                        end
 
*/
 
                if (inc_su)
 
                        if (use_s) SS <= SS + 16'h1;
 
                        else SU <= SU + 16'h1;
 
                if (dec_su)
 
                        if (use_s) SS <= SS - 16'h1;
 
                        else SU <= SU - 16'h1;
 
        end
 
 
 
`ifdef SIMULATION
 
initial
 
        begin
 
                PC = 16'hfffe;
 
                DP = 8'h00;
 
                IX = 16'h0;
 
                `CCR = 0;
 
                IY = 16'hA55A;
 
                SS = 16'h0f00;
 
                SU = 16'h0e00;
 
        end
 
`endif
 
endmodule
endmodule
 
 
 No newline at end of file
 No newline at end of file

powered by: WebSVN 2.1.0

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