[하만]세미콘 아카데미/verilog

0529 Dedicated Processor ALU

내머리속은이런걸로 2024. 7. 9. 17:46

 

  1. R1 = 0
  2. R2 = 0
  3. R3 = 1
  4. R1 = R1 + R3 = 0 + 1 = 1
  5. R2 = R2 + R3 = 0 + 1 = 1
  6. R3 = R1 - R2 = 1 - 1 = 0
  7. R4 = R1 & R3 = 1 & 0 = 0
  8. R5 = R2 | R3 = 1 | 0 = 1
  9. R6 = R1 + R2 = 1 + 1 = 2
  10. R7 = R2 + R6 = 1 + 2  = 3
  11. output = R7

Control Signal Truth Table

Instruction state RFSrcMuxSel we waddr[2:0] raddr[2:0] raddr2[2:0] op[1:0] OutLoad
R1 = 0 S0 0 1 1 0 0 x 0
R2 = 0 S1 0 1 2 0 0 x 0
R3 = 1 S2 1 1 3 0 0 x 0
R1 = R1 + R3 S3 0 1 1 1 3 0 0
R2 = R2 + R3 S4 0 1 2 2 3 0 0
R3 = R1 - R2 S5 0 1 3 1 2 1 0
R4 = R1 & R3 S6 0 1 4 1 3 2 0
R5 = R2 | R3 S7 0 1 5 2 3 3 0
R6 = R1 + R2 S8 0 1 6 1 2 0 0
R7 = R2 + R6 S9 0 1 7 2 6 0 0
output = R7 S10 x 0 x 7 x x 1
halt S11 0 0 0 0 0 0 0

 

DataPath

`timescale 1ns / 1ps

module DataPath (
    input clk,
    input reset,
    input [1:0] op,
    input RFSrcMuxSel,
    input we,
    input [2:0] raddr1,
    input [2:0] raddr2,
    input [2:0] waddr,
    input OutLoad,
    //output Le10,
    output [7:0] outPort
);
    logic [7:0] w_AdderResult, w_RFSrcMuxOut, w_rdata1, w_rdata2;

    mux_2x1 U_RFSrcMus (
        .sel(RFSrcMuxSel),
        .a  (w_AdderResult),
        .b  (8'b1),
        .y  (w_RFSrcMuxOut)
    );

    RegisterFile U_RF (
        .clk   (clk),
        .we    (we),
        .waddr (waddr),
        .raddr1(raddr1),
        .raddr2(raddr2),
        .wdata (w_RFSrcMuxOut),
        .rdata1(w_rdata1),
        .rdata2(w_rdata2)
    );

    // adder U_Adder (
    //     .a(w_rdata1),
    //     .b(w_rdata2),
    //     .y(w_AdderResult)
    // );

    ALU U_ALU (
        .a(w_rdata1),
        .b(w_rdata2),
        .op(op),
        .y(w_AdderResult)
    );
    
    // comparator U_Comp (
    //     .a (w_rdata1),
    //     .b (8'd10),
    //     .le(Le10)
    // );

    register U_OutReg (
        .clk  (clk),
        .reset(reset),
        .load (OutLoad),
        .d    (w_rdata1),
        .q    (outPort)
    );

endmodule

module RegisterFile (
    input        clk,
    input        we,
    input  [2:0] waddr,
    input  [2:0] raddr1,
    input  [2:0] raddr2,
    input  [7:0] wdata,
    output [7:0] rdata1,
    output [7:0] rdata2
);
    logic [7:0] regFile[0:7];  // 8bit regFile 4

    always_ff @(posedge clk) begin
        if (we) regFile[waddr] <= wdata;
    end

    // If address is 0, rdata is 0.
    assign rdata1 = (raddr1 != 0) ? regFile[raddr1] : 0;
    assign rdata2 = (raddr2 != 0) ? regFile[raddr2] : 0;
endmodule

module mux_2x1 (
    input              sel,
    input        [7:0] a,
    input        [7:0] b,
    output logic [7:0] y     // logic = reg & wire
);
    always_comb begin : mux_2x1
        case (sel)
            1'b0: y = a;
            1'b1: y = b;
        endcase
    end
endmodule

module comparator (
    input [7:0] a,
    input [7:0] b,
    output le  // less than equal
);
    assign le = a <= b;
endmodule

module adder (
    input  [7:0] a,
    input  [7:0] b,
    output [7:0] y
);
    assign y = a + b;
endmodule

module register (
    input              clk,
    input              reset,
    input              load,
    input        [7:0] d,
    output logic [7:0] q
);
    always_ff @(posedge clk, posedge reset) begin : register
        if (reset) begin
            q <= 0;
        end else begin
            if (load) q <= d;
        end
    end : register  // end of register, don't have to write 
endmodule

module ALU (
    input [7:0] a,
    input [7:0] b,
    input [1:0] op, // +, -, and, or
    output logic [7:0] y
);
    always_comb begin
        case (op)
            2'b00: y = (a + b);
            2'b01: y = (a - b);
            2'b10: y = (a & b);
            2'b11: y = (a | b);
        endcase
    end
endmodule

 

ControlUnit.sv

`timescale 1ns / 1ps

module ControlUnit (
    input clk,
    input reset,

    //input Le10,
    output logic [1:0] op,
    output logic       RFSrcMuxSel,
    output logic       we,
    output logic [2:0] raddr1,
    output logic [2:0] raddr2,
    output logic [2:0] waddr,
    output logic       OutLoad
);

    enum logic [3:0] { S0, S1, S2, S3, S4, S5, S6, S7, S8, S9, S10, S11} state, state_next;


    always_ff @(posedge clk, posedge reset) begin
        if (reset) state <= S0;
        else state <= state_next;
    end

    always_comb begin
        state_next = state;
        case (state)
            S0: state_next = S1;
            S1: state_next = S2;
            S2: state_next = S3;
            S3: state_next = S4;
            S4: state_next = S5;
            S5: state_next = S6;
            S6: state_next = S7;
            S7: state_next = S8;
            S8: state_next = S9;
            S9: state_next = S10;
            S10: state_next = S11;
            S11: state_next = S11;
            default : state_next = state;
        endcase
    end

    always_comb begin
        RFSrcMuxSel = 1'b0;
        we          = 1'b0;
        waddr       = 3'd0;
        raddr1      = 3'd0;
        raddr2      = 3'd0;
        OutLoad     = 1'd0;
        op          = 2'd0;
        case (state)
            S0: begin
                RFSrcMuxSel = 1'b0;
                we          = 1'b1;
                waddr       = 3'd1;
                raddr1      = 3'd0;
                raddr2      = 3'd0;
                OutLoad     = 1'd0;
                op          = 2'd0;
            end
            S1: begin
                RFSrcMuxSel = 1'b0;
                we          = 1'b1;
                waddr       = 3'd2;
                raddr1      = 3'd0;
                raddr2      = 3'd0;
                OutLoad     = 1'd0;
                op          = 2'd0;
            end
            S2: begin
                RFSrcMuxSel = 1'b1;
                we          = 1'b1;
                waddr       = 3'd3;
                raddr1      = 3'd0;
                raddr2      = 3'd0;
                OutLoad     = 1'd0;
                op          = 2'd0;
            end
            S3: begin
                RFSrcMuxSel = 1'b0;
                we          = 1'b1;
                waddr       = 3'd1;
                raddr1      = 3'd1;
                raddr2      = 3'd3;
                OutLoad     = 1'd0;
                op          = 2'd0;
            end
            S4: begin
                RFSrcMuxSel = 1'b0;
                we          = 1'b1;
                waddr       = 3'd2;
                raddr1      = 3'd2;
                raddr2      = 3'd3;
                OutLoad     = 1'd0;
                op          = 2'd0;
            end
            S5: begin
                RFSrcMuxSel = 1'b0;
                we          = 1'b1;
                waddr       = 3'd3;
                raddr1      = 3'd1;
                raddr2      = 3'd2;
                OutLoad     = 1'd0;
                op          = 2'd1;
            end
            S6: begin
                RFSrcMuxSel = 1'b0;
                we          = 1'b1;
                waddr       = 3'd4;
                raddr1      = 3'd1;
                raddr2      = 3'd3;
                OutLoad     = 1'd0;
                op          = 2'd2;
            end
            S7: begin
                RFSrcMuxSel = 1'b0;
                we          = 1'b1;
                waddr       = 3'd5;
                raddr1      = 3'd2;
                raddr2      = 3'd3;
                OutLoad     = 1'd0;
                op          = 2'd3;
            end
            S8: begin
                RFSrcMuxSel = 1'b0;
                we          = 1'b1;
                waddr       = 3'd6;
                raddr1      = 3'd1;
                raddr2      = 3'd2;
                OutLoad     = 1'd0;
                op          = 2'd0;
            end
            S9: begin
                RFSrcMuxSel = 1'b0;
                we          = 1'b1;
                waddr       = 3'd7;
                raddr1      = 3'd2;
                raddr2      = 3'd6;
                OutLoad     = 1'd0;
                op          = 2'd0;
            end
            S10: begin
                RFSrcMuxSel = 1'b0;
                we          = 1'b0;
                waddr       = 3'd0;
                raddr1      = 3'd7;
                raddr2      = 3'd0;
                OutLoad     = 1'd1;
                op          = 2'd0;
            end
            S11: begin
                RFSrcMuxSel = 1'b0;
                we          = 1'b0;
                waddr       = 3'd0;
                raddr1      = 3'd0;
                raddr2      = 3'd0;
                OutLoad     = 1'd0;
                op          = 2'd0;
            end
        endcase
    end

endmodule

 

DedicatedProcessor.sv

`timescale 1ns / 1ps

module DedicatedProcessor(
    input clk,
    input reset,
    output [7:0] outPort
    );

    logic RFSrcMuxSel, we, OutLoad;
    logic [1:0] op;
    logic [2:0] waddr, raddr1, raddr2;

    ControlUnit U_ControlUnit(
        .*
    );

    DataPath U_DataPath(
        .*
    );

endmodule

 

schematic

tb_dp.sv

`timescale 1ns / 1ps

module tb_dp();

    logic clk;
    logic reset;
    logic [7:0] outPort;

    DedicatedProcessor dut(
        .clk(clk),
        .reset(reset),
        .outPort(outPort)
    );

    always #5 clk = ~clk;

    initial begin
        clk <= 1'b0;
        reset <= 1'b1;
        #40 reset <= 1'b0;
    end
endmodule

 

simulation