From ee3a520a1fb6c9c27f2df648df25afa209ed944c Mon Sep 17 00:00:00 2001 From: Kevin Kim Date: Fri, 17 Feb 2023 09:51:49 -0800 Subject: [PATCH] alu looks at BSelect, added BSelect one hot signal --- src/ieu/alu.sv | 61 ++++++++++++++++++++++++++++-------------- src/ieu/bmu/bmuctrl.sv | 3 ++- src/ieu/controller.sv | 7 ++--- 3 files changed, 47 insertions(+), 24 deletions(-) diff --git a/src/ieu/alu.sv b/src/ieu/alu.sv index 9311c1bc..3bb6ba34 100644 --- a/src/ieu/alu.sv +++ b/src/ieu/alu.sv @@ -42,6 +42,7 @@ module alu #(parameter WIDTH=32) ( // CondInvB = ~B when subtracting, B otherwise. Shift = shift result. SLT/U = result of a slt/u instruction. // FullResult = ALU result before adjusting for a RV64 w-suffix instruction. logic [WIDTH-1:0] CondInvB, Shift, SLT, SLTU, FullResult,ALUResult, ZBCResult, CondMaskB; // Intermediate results + logic [WIDTH-1:0] MaskB; logic Carry, Neg; // Flags: carry out, negative logic LT, LTU; // Less than, Less than unsigned logic W64; // RV64 W-type instruction @@ -51,13 +52,16 @@ module alu #(parameter WIDTH=32) ( logic Rotate; - decoder #($clog2(WIDTH)) maskgen (B[$clog2(WIDTH)-1:0], CondMaskB); + if (`ZBS_SUPPORTED) begin: zbsdec + decoder #($clog2(WIDTH)) maskgen (B[$clog2(WIDTH)-1:0], MaskB); + assign CondMaskB = (BSelect[0]) ? MaskB : B; + end else assign CondMaskB = B; // Extract control signals from ALUControl. assign {W64, SubArith, ALUOp} = ALUControl; // Addition - assign CondInvB = SubArith ? ~B : B; + assign CondInvB = SubArith ? ~CondMaskB : CondMaskB; assign {Carry, Sum} = A + CondInvB + {{(WIDTH-1){1'b0}}, SubArith}; // Shifts @@ -78,17 +82,35 @@ module alu #(parameter WIDTH=32) ( assign SLTU = {{(WIDTH-1){1'b0}}, LTU}; // Select appropriate ALU Result - always_comb - if (~ALUOp) FullResult = Sum; // Always add for ALUOp = 0 (address generation) - else casez (ALUSelect) // Otherwise check Funct3 NOTE: change signal name to ALUSelect - 3'b000: FullResult = Sum; // add or sub - 3'b?01: FullResult = Shift; // sll, sra, or srl - 3'b010: FullResult = SLT; // slt - 3'b011: FullResult = SLTU; // sltu - 3'b100: FullResult = A ^ B; // xor - 3'b110: FullResult = A | B; // or - 3'b111: FullResult = A & B; // and - endcase + if (`ZBS_SUPPORTED) begin + always_comb + if (~ALUOp) FullResult = Sum; // Always add for ALUOp = 0 (address generation) + else casez (ALUSelect) // Otherwise check Funct3 NOTE: change signal name to ALUSelect + 3'b000: FullResult = Sum; // add or sub + 3'b001: FullResult = Shift; // sll, sra, or srl + 3'b010: FullResult = SLT; // slt + 3'b011: FullResult = SLTU; // sltu + 3'b100: FullResult = A ^ B; // xor, binv + 3'b110: FullResult = A | B; // or, bset + 3'b111: FullResult = A & B; // and, bclr + 3'b101: FullResult = {{(WIDTH-1){1'b0}},{|(A & B)}};// bext + endcase + end + else begin + always_comb + if (~ALUOp) FullResult = Sum; // Always add for ALUOp = 0 (address generation) + else casez (ALUSelect) // Otherwise check Funct3 NOTE: change signal name to ALUSelect + 3'b000: FullResult = Sum; // add or sub + 3'b?01: FullResult = Shift; // sll, sra, or srl + 3'b010: FullResult = SLT; // slt + 3'b011: FullResult = SLTU; // sltu + 3'b100: FullResult = A ^ B; // xor + 3'b110: FullResult = A | B; // or + 3'b111: FullResult = A & B; // and + endcase + + end + // Support RV64I W-type addw/subw/addiw/shifts that discard upper 32 bits and sign-extend 32-bit result to 64 bits if (WIDTH == 64) assign ALUResult = W64 ? {{32{FullResult[31]}}, FullResult[31:0]} : FullResult; @@ -99,15 +121,14 @@ module alu #(parameter WIDTH=32) ( zbc #(WIDTH) ZBC(.A(A), .B(B), .Funct3(Funct3), .ZBCResult(ZBCResult)); end else assign ZBCResult = 0; - //NOTE: Unoptimized, eventually want to look at ZBCop/ZBSop/ZBAop/ZBBop from decoder to select from a B instruction or the ALU - if (`ZBC_SUPPORTED) begin : zbcdecoder + if (`ZBC_SUPPORTED | `ZBS_SUPPORTED) begin : zbdecoder always_comb - case ({Funct7, Funct3}) - 10'b0000101_001: Result = ZBCResult; - 10'b0000101_011: Result = ZBCResult; - 10'b0000101_010: Result = ZBCResult; - default: Result = ALUResult; + case (BSelect) + //ZBA_ZBB_ZBC_ZBS + 4'b0001: Result = FullResult; + 4'b0010: Result = ZBCResult; + default: Result = ALUResult; endcase end else assign Result = ALUResult; endmodule \ No newline at end of file diff --git a/src/ieu/bmu/bmuctrl.sv b/src/ieu/bmu/bmuctrl.sv index 7c95f06c..8b051e73 100644 --- a/src/ieu/bmu/bmuctrl.sv +++ b/src/ieu/bmu/bmuctrl.sv @@ -36,6 +36,7 @@ module bmuctrl( input logic StallD, FlushD, // Stall, flush Decode stage input logic [31:0] InstrD, // Instruction in Decode stage output logic [2:0] ALUSelectD, // ALU Mux select signal + output logic [3:0] BSelectD, // Indicates if ZBA_ZBB_ZBC_ZBS instruction in one-hot encoding in Decode stage // Execute stage control signals input logic StallE, FlushE, // Stall, flush Execute stage output logic [6:0] Funct7E, // Instruction's funct7 field (note: eventually want to get rid of this) @@ -47,7 +48,6 @@ module bmuctrl( logic [2:0] Funct3D; // Funct3 field in Decode stage logic [6:0] Funct7D; // Funct7 field in Decode stage logic [4:0] Rs1D; // Rs1 source register in Decode stage - logic [3:0] BSelectD; // Indicates if ZBA_ZBB_ZBC_ZBS instruction decode stage `define BMUCTRLW 7 @@ -73,6 +73,7 @@ module bmuctrl( 17'b0110011_011010?_001: BMUControlsD = `BMUCTRLW'b100_0001; // binv 17'b0110011_001010?_001: BMUControlsD = `BMUCTRLW'b110_0001; // bset 17'b0110011_0?00000_?01: BMUControlsD = `BMUCTRLW'b001_0001; // sra, srl, sll + 17'b0110011_0000101_???: BMUControlsD = `BMUCTRLW'b001_0010; // ZBC instruction default: BMUControlsD = {Funct3D, {4'b0}}; // not B instruction or shift endcase diff --git a/src/ieu/controller.sv b/src/ieu/controller.sv index 0ed3d727..e24a5e5f 100644 --- a/src/ieu/controller.sv +++ b/src/ieu/controller.sv @@ -116,6 +116,7 @@ module controller( logic FenceD, FenceE, FenceM; // Fence instruction logic SFenceVmaD; // sfence.vma instruction logic IntDivM; // Integer divide instruction + logic [3:0] BSelectD; // One-Hot encoding if it's ZBA_ZBB_ZBC_ZBS instruction in decode stage // Extract fields @@ -152,7 +153,7 @@ module controller( ControlsD = `CTRLW'b1_101_01_11_001_0_0_0_0_0_0_0_0_0_10_0; // amo end else ControlsD = `CTRLW'b0_000_00_00_000_0_0_0_0_0_0_0_0_0_00_1; // Non-implemented instruction - 7'b0110011: if (Funct7D == 7'b0000000 | Funct7D == 7'b0100000 | (Funct7D == 7'b0000101 & `ZBC_SUPPORTED)) + 7'b0110011: if (Funct7D == 7'b0000000 | Funct7D == 7'b0100000 | (BSelectD[1] | BSelectD[0])) ControlsD = `CTRLW'b1_000_00_00_000_0_1_0_0_0_0_0_0_0_00_0; // R-type else if (Funct7D == 7'b0000001 & `M_SUPPORTED) ControlsD = `CTRLW'b1_000_00_00_011_0_0_0_0_0_0_0_0_1_00_0; // Multiply/divide @@ -198,11 +199,11 @@ module controller( assign sltuD = (Funct3D == 3'b011); assign subD = (Funct3D == 3'b000 & Funct7D[5] & OpD[5]); // OpD[5] needed to distinguish sub from addi assign sraD = (Funct3D == 3'b101 & Funct7D[5]); - assign SubArithD = ALUOpD & (subD | sraD | sltD | sltuD | (`ZBS_SUPPORTED & BSelectE[0] & ALUSelectD == 3'b101)); // TRUE for R-type subtracts and sra, slt, sltu, bext + assign SubArithD = ALUOpD & (subD | sraD | sltD | sltuD | (`ZBS_SUPPORTED & BSelectD[0] && (ALUSelectD == 3'b101 | ALUSelectD == 3'b111))); // TRUE for R-type subtracts and sra, slt, sltu, bext assign ALUControlD = {W64D, SubArithD, ALUOpD}; if (`ZBS_SUPPORTED) begin: bitmanipi //change the conditional expression to OR any Z supported flags - bmuctrl bmuctrl(.clk, .reset, .StallD, .FlushD, .InstrD, .ALUSelectD, .StallE, .FlushE, .Funct7E, .ALUSelectE, BSelectE); + bmuctrl bmuctrl(.clk, .reset, .StallD, .FlushD, .InstrD, .ALUSelectD, .BSelectD, .StallE, .FlushE, .Funct7E, .ALUSelectE, .BSelectE); end else begin: bitmanipi assign ALUSelectD = Funct3D; assign ALUSelectE = Funct3E;