ALU8bit
ALU8bit
v Project: 8bitALU
1 module ALU8bit (
2 input [7:0] A, // the first operand
3 input [7:0] B, // the second operand
4 input [2:0] Opcode, // operation code
5 output reg [7:0] Result, // result
6 output reg zero_flag,
7 output reg carry_flag,
8 output reg overflow_flag,
9 output reg multiplication_overflow_flag
10 );
11
12 // define the operation code
13 localparam OP_AND = 3'b000;
14 localparam OP_OR = 3'b001;
15 localparam OP_XOR = 3'b010;
16 localparam OP_ADD = 3'b011;
17 localparam OP_SUB = 3'b100;
18 localparam OP_MUL = 3'b101;
19 localparam OP_SHIFT = 3'b110;
20 localparam OP_ROTATE = 3'b111;
21
22 // Calculate the absolute and negative value of B and the number of shift/rotation bits
23 wire [7:0] B_neg = (~B + 1); //2's Complement of B, this will be used in the latter
calculation and determination of overflow status of SUB operation
24 wire [7:0] B_abs = B[7] ? (~B + 1) : B; // calculate the absolute value of B
25 wire [2:0] shift_rotate_amount = B_abs[7:3] ? 8 : B_abs[2:0] ; // if the abs value
of B is greater than 7, shift_rotate_amount will be set to 8
26 reg [8:0] AddResult; // 9-bit addition result
27 reg [8:0] SubResult; // 9-bit subtraction result
28 reg [15:0] MulResult; // 16-bit multiplication result
29
30
31 always @(*) begin
32 case (Opcode)
33 // basic logic operation
34 OP_AND: Result = A & B;
35 OP_OR: Result = A | B;
36 OP_XOR: Result = A ^ B;
37
38 // arithmetic operation
39 OP_ADD: begin
40 AddResult = A + B;
41 Result = AddResult[7:0]; // Take the lower 8 digits
42 carry_flag = AddResult[8]; // set the carry flag
43 //overflow_flag = (A[7] == B[7]) && (Result[7] != A[7]); // another way
to determine overflow flag
44 overflow_flag = (Result[7]&(~A[7])&(~B[7]))|((~Result[7])&A[7]&B[7]);
//two situations: the sum of two positive number is a negative number, the sum of two
negative number is a positive number
45 end
46
47 OP_SUB: begin
48 SubResult = A + B_neg;
49 Result = SubResult[7:0];
50 carry_flag = SubResult[8];
51 overflow_flag = (Result[7]&(~A[7])&(~B_neg[7]))|((~Result[7])&A[7]&B_neg[7
]); //two situations: a pos num - a neg num = a neg num, vise versa
52 end
53
54 OP_MUL: begin
55 MulResult = A * B;
56 Result = MulResult[7:0];
57 multiplication_overflow_flag = |MulResult[15:8];
58 end
59
60 // Shift
61 OP_SHIFT: begin
62 if (B[7]) // Left shift (B is negative)
63 Result = A << shift_rotate_amount;
64 else // Right shift (B is positive)
65 Result = A >> shift_rotate_amount;
66 end