Improved ALU and added more INC and a DEC instruction

This commit is contained in:
(Tim) Efthimis Kritikos 2023-02-11 14:43:53 +00:00
parent be06244021
commit 85bf886223
4 changed files with 69 additions and 26 deletions

View File

@ -1,9 +1,16 @@
module ADDER16(input [15:0]A,input [15:0]B, input oe,output [15:0]OUT, output carry); `include "alu_header.v"
wire c;
wire [15:0]sum;
assign {c,sum} = A+B;
assign OUT = !oe ? sum : 16'hz; module ALU(input [15:0]A,input [15:0]B, input oe,output reg [15:0]OUT,input [`ALU_OP_BITS-1:0]op);
assign carry = !oe ? c : 'hz; reg C_FLAG;
always @ ( * ) begin
case (op)
`ALU_OP_ADD: {C_FLAG,OUT}=A+B;
`ALU_OP_SUB: {C_FLAG,OUT}=A-B;
`ALU_OP_AND: OUT=A&B;
`ALU_OP_OR: OUT=A|B;
`ALU_OP_XOR: OUT=A^B;
endcase
end
endmodule endmodule

6
cpu/alu_header.v Normal file
View File

@ -0,0 +1,6 @@
`define ALU_OP_BITS 3
`define ALU_OP_ADD 3'b000
`define ALU_OP_SUB 3'b001
`define ALU_OP_AND 3'b010
`define ALU_OP_OR 3'b011
`define ALU_OP_XOR 3'b100

View File

@ -4,5 +4,9 @@ MOV BX,#0x0000
ADD AX,#0xDEAD ADD AX,#0xDEAD
ADD CX,#0xBEEF ADD CX,#0xBEEF
ADD CX,#0x4111 ADD CX,#0x4111
mov AX,#0x00FF
inc AL
mov AX,#0x00FF
inc ax
ADD AX,#0x2200 ADD AX,#0x2200
HLT HLT

View File

@ -1,4 +1,5 @@
`include "proc_state_def.v" `include "proc_state_def.v"
`include "alu_header.v"
module mux4 (in1,in2,in3,in4, sel,out); module mux4 (in1,in2,in3,in4, sel,out);
input [0:1] sel; input [0:1] sel;
@ -39,7 +40,7 @@ always @(negedge reset) begin
reg_write_we=1; reg_write_we=1;
reg_read_oe=1; reg_read_oe=1;
unaligned_access=0; unaligned_access=0;
ALU_OUT=1; ALU_1OE=1;
@(posedge reset) @(posedge reset)
@(negedge clock); @(negedge clock);
state=`PROC_IF_STATE_ENTRY; state=`PROC_IF_STATE_ENTRY;
@ -60,11 +61,11 @@ register_file register_file(reg_write_addr,reg_write_data,reg_write_we,reg_read_
//ALU //ALU
mux4 #(.WIDTH(16)) MUX16_1A( mux4 #(.WIDTH(16)) MUX16_1A(
PARAM1, PARAM1,
16'b0, reg_read_data,
16'b0, 16'b0,
16'b0, 16'b0,
in1_sel, in1_sel,
ADDER16_1A); ALU_1A);
mux4 #(.WIDTH(16)) MUX16_1B( mux4 #(.WIDTH(16)) MUX16_1B(
PARAM2, PARAM2,
@ -72,15 +73,15 @@ mux4 #(.WIDTH(16)) MUX16_1B(
16'b0, 16'b0,
16'b0, 16'b0,
in2_sel, in2_sel,
ADDER16_1B); ALU_1B);
wire [15:0] ADDER16_1A; wire [15:0] ALU_1A;
wire [15:0] ADDER16_1B; wire [15:0] ALU_1B;
wire [15:0] ADDER16_1O; wire [15:0] ALU_1O;
wire ADDER16_1C; reg [`ALU_OP_BITS-1:0]ALU_1OP;
reg ALU_OUT; reg ALU_1OE;
reg [15:0] temp_out; //reg [15:0] temp_out;
ADDER16 ADDER16_1(ADDER16_1A,ADDER16_1B,ALU_OUT,ADDER16_1O,ADDER16_1C); ALU ALU(ALU_1A,ALU_1B,ALU_1OE,ALU_1O,ALU_1OP);
/*** Processor stages ***/ /*** Processor stages ***/
@ -131,7 +132,7 @@ always @(posedge clock) begin
write <= 1; write <= 1;
reg_read_oe=1; reg_read_oe=1;
reg_write_we=1; reg_write_we=1;
ALU_OUT=1; ALU_1OE=1;
state=`PROC_IF_WRITE_CIR; state=`PROC_IF_WRITE_CIR;
end end
`PROC_IF_STATE_EXTRA_FETCH_SET:begin `PROC_IF_STATE_EXTRA_FETCH_SET:begin
@ -154,7 +155,8 @@ always @(posedge clock) begin
reg_read_addr={CIR[8:8],3'b000}; reg_read_addr={CIR[8:8],3'b000};
reg_write_addr={CIR[8:8],3'b000}; reg_write_addr={CIR[8:8],3'b000};
reg_read_oe=0; reg_read_oe=0;
ALU_OUT=0; ALU_1OE=0;
ALU_1OP=`ALU_OP_ADD;
if(CIR[8:8]==1) if(CIR[8:8]==1)
state=`PROC_DE_LOAD_16_PARAM; state=`PROC_DE_LOAD_16_PARAM;
else begin else begin
@ -179,7 +181,8 @@ always @(posedge clock) begin
reg_read_addr={CIR[8:8],CIR[2:0]}; reg_read_addr={CIR[8:8],CIR[2:0]};
reg_write_addr={CIR[8:8],CIR[2:0]}; reg_write_addr={CIR[8:8],CIR[2:0]};
reg_read_oe=0; reg_read_oe=0;
ALU_OUT=0; ALU_1OE=0;
ALU_1OP=`ALU_OP_ADD;
state=`PROC_DE_LOAD_16_PARAM; state=`PROC_DE_LOAD_16_PARAM;
if(CIR[8:8]==1) if(CIR[8:8]==1)
state=`PROC_DE_LOAD_16_PARAM; state=`PROC_DE_LOAD_16_PARAM;
@ -206,7 +209,8 @@ always @(posedge clock) begin
reg_write_addr={1'b0,CIR[10:8]}; reg_write_addr={1'b0,CIR[10:8]};
PARAM1[7:0]=CIR[7:0]; PARAM1[7:0]=CIR[7:0];
PARAM2=0; PARAM2=0;
ALU_OUT=0; ALU_1OE=0;
ALU_1OP=`ALU_OP_ADD;
state=`PROC_EX_STATE_ENTRY; state=`PROC_EX_STATE_ENTRY;
end end
6'b101110, 6'b101110,
@ -217,10 +221,31 @@ always @(posedge clock) begin
in2_sel=2'b00; in2_sel=2'b00;
out_sel=2'b11; out_sel=2'b11;
reg_write_addr={1'b1,CIR[10:8]}; reg_write_addr={1'b1,CIR[10:8]};
ALU_OUT=0; ALU_1OE=0;
ALU_1OP=`ALU_OP_ADD;
PARAM2=0; PARAM2=0;
state=`PROC_DE_LOAD_16_PARAM; state=`PROC_DE_LOAD_16_PARAM;
end end
6'b010000,//INC
6'b010001,//INC
6'b010010,//DEC
6'b010011:begin//DEC
/*INC/DEC Register*/
unaligned_access=~unaligned_access;
in1_sel=2'b01;
in2_sel=2'b00;
out_sel=2'b11;
PARAM2=1;
reg_read_addr={1'b1,CIR[10:8]};
reg_write_addr={1'b1,CIR[10:8]};
reg_read_oe=0;
ALU_1OE=0;
if(CIR[11:11]==0)
ALU_1OP=`ALU_OP_ADD;
else
ALU_1OP=`ALU_OP_SUB;
state=`PROC_EX_STATE_ENTRY;
end
6'b111111 : begin 6'b111111 : begin
/* INC */ /* INC */
if (CIR[9:9] == 1 ) begin if (CIR[9:9] == 1 ) begin
@ -238,7 +263,8 @@ always @(posedge clock) begin
reg_read_addr={1'b0,CIR[2:0]}; reg_read_addr={1'b0,CIR[2:0]};
reg_write_addr={1'b0,CIR[2:0]}; reg_write_addr={1'b0,CIR[2:0]};
reg_read_oe=0; reg_read_oe=0;
ALU_OUT=0; ALU_1OE=0;
ALU_1OP=`ALU_OP_ADD;
state=`PROC_EX_STATE_ENTRY; state=`PROC_EX_STATE_ENTRY;
end end
default:begin default:begin
@ -286,7 +312,7 @@ always @(posedge clock) begin
state=`PROC_EX_STATE_ENTRY; state=`PROC_EX_STATE_ENTRY;
end end
`PROC_EX_STATE_ENTRY:begin `PROC_EX_STATE_ENTRY:begin
reg_write_data=ADDER16_1O; reg_write_data=ALU_1O;
state=`PROC_EX_STATE_EXIT; state=`PROC_EX_STATE_EXIT;
ERROR=0; ERROR=0;
end end