0
\$\begingroup\$

I have written the following code in Verilog which for the time being caters to only a subset of R-type, load word and store word instructions in the single cycle implementation based on the diagram given in Computer Organization & design (3rd Edition).

 //32 bit instruction memory module
module instructionMemory(readAddr,clk,instruction);
input [31:0] readAddr;
input clk;
output reg [31:0] instruction;

reg [31:0] memory [255:0];

always @(posedge clk) 
begin
    assign instruction=memory[readAddr];
end
endmodule//instruction memory module

//32 bit memory module
module dataMemory(address,clk,writeData,memRead,memWrite,readData);
input [31:0] address;
input [31:0] writeData;
input clk;
input memRead;
input memWrite;
output reg [31:0] readData;

reg [31:0] memory [255:0];

always @(posedge clk) begin
    if (memRead)
        readData = memory[address];
    if (memWrite)
        memory[address] = writeData;
end
 endmodule //32 bit memory module

//ALU control unit module
module aluControlUnit(aluOp,funcField,aluControl);
input [1:0] aluOp;
input [5:0] funcField;
output reg [3:0] aluControl;

wire [7:0] aluControlIn;
assign aluControlIn={aluOp,funcField};
always @(aluControlIn)
casex(aluControlIn)
    8'b00xxxxxx: aluControl = 4'b0010;
    8'bx1xxxxxx: aluControl = 4'b0110;
    8'b1xxx0000: aluControl = 4'b0010; 
    8'b1xxx0010: aluControl = 4'b0110; 
    8'b1xxx0100: aluControl = 4'b0000; 
    8'b1xxx0101: aluControl = 4'b0001; 
    8'b1xxx1010: aluControl = 4'b0111; 
endcase
endmodule//ALU Control module  

//Control Unit module
module controlUnit(opCode,regDst,branch,memRead,memWrite,memToReg,regWrite,aluSrc,aluOp);
input [5:0] opCode;
output reg regDst;
output reg branch;
output reg memRead;
output reg memWrite;
output reg memToReg;
output reg regWrite;
output reg aluSrc;
output reg [1:0] aluOp;

//logic for different opcodes
always @(opCode)
case(opCode)
//R-Type
6'b000000: begin 
regDst = 1'b1;
aluSrc = 1'b0;
memToReg = 1'b0;
regWrite = 1'b1;
memRead = 1'b0;
memWrite = 1'b0;
branch = 1'b0;
aluOp = 2'b10;
end 
//Load
6'b100011: begin 
regDst = 1'b0;
aluSrc = 1'b1;
memToReg = 1'b1;
regWrite = 1'b1;
memRead = 1'b1;
memWrite = 1'b0;
branch = 1'b0;
aluOp = 2'b00;
end 
//Store
6'b000100: begin 
regDst = 1'bx;
aluSrc = 1'b1;
memToReg = 1'bx;
regWrite = 1'b0;
memRead = 1'b0;
memWrite = 1'b1;
branch = 1'b0;
aluOp = 2'b00;
end 
endcase
endmodule//Control Unit Module

//---------------Register File Module--------------
//2 to 4 decoder module
module decoder2x4(in,out);
input [1:0] in;
output [3:0] out;

assign out[0]= (~in[1]) & (~in[0]);
assign out[1]= (~in[1]) & (in[0]);
assign out[2]= (in[1]) & (~in[0]);
assign out[3]= (in[1]) & (in[0]);

endmodule//2 to 4 decoder

//3 to 8 decoder module
module decoder3x8(in,en,out);
input [2:0] in;
input en;
output [7:0] out;

assign out[0]= (en) & (~in[2]) & (~in[1]) & (~in[0]);
assign out[1]= (en) & (~in[2]) & (~in[1]) & (in[0]);
assign out[2]= (en) & (~in[2]) & (in[1]) & (~in[0]);
assign out[3]= (en) & (~in[2]) & (in[1]) & (in[0]);
assign out[4]= (en) & (in[2]) & (~in[1]) & (~in[0]);
assign out[5]= (en) & (in[2]) & (~in[1]) & (in[0]);
assign out[6]= (en) & (in[2]) & (in[1]) & (~in[0]);
assign out[7]= (en) & (in[2]) & (in[1]) & (in[0]);
endmodule//3 to 8 decoder

//5 to 32 decoder module
module decoder5x32(in,out);
input [4:0] in;
output [31:0] out;

wire [3:0] dec24Out;

decoder2x4 dec24(.in(in[4:3]),.out(dec24Out));

decoder3x8 dec38_0(.in(in[2:0]),.en(dec24Out[0]),.out(out[7:0]));
decoder3x8 dec38_1(.in(in[2:0]),.en(dec24Out[1]),.out(out[15:8]));
decoder3x8 dec38_2(.in(in[2:0]),.en(dec24Out[2]),.out(out[23:16]));
decoder3x8 dec38_3(.in(in[2:0]),.en(dec24Out[3]),.out(out[31:24]));
endmodule//5 to 32 decoder

//32 bit register module
module reg32 (reset, regWrite, decOut, CLK, writeData, outBus);

input reset;
input CLK;
input regWrite;
input decOut;
input  [31:0]  writeData;

output reg [31:0]  outBus;

always @(posedge CLK)
if (reset)
outBus = 0;
else if(regWrite == 1 && decOut==1)
outBus = writeData;
endmodule // reg32

module destRegSelector(destReg,rst,clk,write,writeData,bus0,bus1,bus2,bus3,bus4,bus5,bus6,bus7,bus8,bus9,bus10,bus11,bus12,bus13,bus14,bus15,bus16,bus17,bus18,bus19,bus20,bus21,bus22,bus23,bus24,bus25,bus26,bus27,bus28,bus29,bus30,bus31);
//common wires,inputs,outputs
input [4:0] destReg;
wire  [31:0] decOut;

input rst;
input clk;
input write;
input  [31:0]  writeData;


output [31:0]  bus0;
output [31:0]  bus1;
output [31:0]  bus2;
output [31:0]  bus3;
output [31:0]  bus4;
output [31:0]  bus5;
output [31:0]  bus6;
output [31:0]  bus7;
output [31:0]  bus8;
output [31:0]  bus9;
output [31:0]  bus10;
output [31:0]  bus11;
output [31:0]  bus12;
output [31:0]  bus13;
output [31:0]  bus14;
output [31:0]  bus15;
output [31:0]  bus16;
output [31:0]  bus17;
output [31:0]  bus18;
output [31:0]  bus19;
output [31:0]  bus20;
output [31:0]  bus21;
output [31:0]  bus22;
output [31:0]  bus23;
output [31:0]  bus24;
output [31:0]  bus25;
output [31:0]  bus26;
output [31:0]  bus27;
output [31:0]  bus28;
output [31:0]  bus29;
output [31:0]  bus30;
output [31:0]  bus31;
//decoder instance
decoder5x32 dec(.in(destReg),.out(decOut));

//register instances
reg32 r0(.reset(rst),.regWrite(write),.decOut(decOut[0]),.CLK(clk),.writeData(writeData),.outBus(bus0));
reg32 r1(.reset(rst),.regWrite(write),.decOut(decOut[1]),.CLK(clk),.writeData(writeData),.outBus(bus1));
reg32 r2(.reset(rst),.regWrite(write),.decOut(decOut[2]),.CLK(clk),.writeData(writeData),.outBus(bus2));
reg32 r3(.reset(rst),.regWrite(write),.decOut(decOut[3]),.CLK(clk),.writeData(writeData),.outBus(bus3));
reg32 r4(.reset(rst),.regWrite(write),.decOut(decOut[4]),.CLK(clk),.writeData(writeData),.outBus(bus4));
reg32 r5(.reset(rst),.regWrite(write),.decOut(decOut[5]),.CLK(clk),.writeData(writeData),.outBus(bus5));
reg32 r6(.reset(rst),.regWrite(write),.decOut(decOut[6]),.CLK(clk),.writeData(writeData),.outBus(bus6));
reg32 r7(.reset(rst),.regWrite(write),.decOut(decOut[7]),.CLK(clk),.writeData(writeData),.outBus(bus7));
reg32 r8(.reset(rst),.regWrite(write),.decOut(decOut[8]),.CLK(clk),.writeData(writeData),.outBus(bus8));
reg32 r9(.reset(rst),.regWrite(write),.decOut(decOut[9]),.CLK(clk),.writeData(writeData),.outBus(bus9));
reg32 r10(.reset(rst),.regWrite(write),.decOut(decOut[10]),.CLK(clk),.writeData(writeData),.outBus(bus10));
reg32 r11(.reset(rst),.regWrite(write),.decOut(decOut[11]),.CLK(clk),.writeData(writeData),.outBus(bus11));
reg32 r12(.reset(rst),.regWrite(write),.decOut(decOut[12]),.CLK(clk),.writeData(writeData),.outBus(bus12));
reg32 r13(.reset(rst),.regWrite(write),.decOut(decOut[13]),.CLK(clk),.writeData(writeData),.outBus(bus13));
reg32 r14(.reset(rst),.regWrite(write),.decOut(decOut[14]),.CLK(clk),.writeData(writeData),.outBus(bus14));
reg32 r15(.reset(rst),.regWrite(write),.decOut(decOut[15]),.CLK(clk),.writeData(writeData),.outBus(bus15));
reg32 r16(.reset(rst),.regWrite(write),.decOut(decOut[16]),.CLK(clk),.writeData(writeData),.outBus(bus16));
reg32 r17(.reset(rst),.regWrite(write),.decOut(decOut[17]),.CLK(clk),.writeData(writeData),.outBus(bus17));
reg32 r18(.reset(rst),.regWrite(write),.decOut(decOut[18]),.CLK(clk),.writeData(writeData),.outBus(bus18));
reg32 r19(.reset(rst),.regWrite(write),.decOut(decOut[19]),.CLK(clk),.writeData(writeData),.outBus(bus19));
reg32 r20(.reset(rst),.regWrite(write),.decOut(decOut[20]),.CLK(clk),.writeData(writeData),.outBus(bus20));
reg32 r21(.reset(rst),.regWrite(write),.decOut(decOut[21]),.CLK(clk),.writeData(writeData),.outBus(bus21));
reg32 r22(.reset(rst),.regWrite(write),.decOut(decOut[22]),.CLK(clk),.writeData(writeData),.outBus(bus22));
reg32 r23(.reset(rst),.regWrite(write),.decOut(decOut[23]),.CLK(clk),.writeData(writeData),.outBus(bus23));
reg32 r24(.reset(rst),.regWrite(write),.decOut(decOut[24]),.CLK(clk),.writeData(writeData),.outBus(bus24));
reg32 r25(.reset(rst),.regWrite(write),.decOut(decOut[25]),.CLK(clk),.writeData(writeData),.outBus(bus25));
reg32 r26(.reset(rst),.regWrite(write),.decOut(decOut[26]),.CLK(clk),.writeData(writeData),.outBus(bus26));
reg32 r27(.reset(rst),.regWrite(write),.decOut(decOut[27]),.CLK(clk),.writeData(writeData),.outBus(bus27));
reg32 r28(.reset(rst),.regWrite(write),.decOut(decOut[28]),.CLK(clk),.writeData(writeData),.outBus(bus28));
reg32 r29(.reset(rst),.regWrite(write),.decOut(decOut[29]),.CLK(clk),.writeData(writeData),.outBus(bus29));
reg32 r30(.reset(rst),.regWrite(write),.decOut(decOut[30]),.CLK(clk),.writeData(writeData),.outBus(bus30));
reg32 r31(.reset(rst),.regWrite(write),.decOut(decOut[31]),.CLK(clk),.writeData(writeData),.outBus(bus31));
endmodule//destRegSelector

//32 to 1 multiplexer
module mux32x1(select,in0,in1,in2,in3,in4,in5,in6,in7,in8,in9,in10,in11,in12,in13,in14,in15,in16,in17,in18,in19,in20,in21,in22,in23,in24,in25,in26,in27,in28,in29,in30,in31,out);
input [4:0] select;
input [31:0] in0;
input [31:0] in1;
input [31:0] in2;
input [31:0] in3;
input [31:0] in4;
input [31:0] in5;
input [31:0] in6;
input [31:0] in7;
input [31:0] in8;
input [31:0] in9;
input [31:0] in10;
input [31:0] in11;
input [31:0] in12;
input [31:0] in13;
input [31:0] in14;
input [31:0] in15;
input [31:0] in16;
input [31:0] in17;
input [31:0] in18;
input [31:0] in19;
input [31:0] in20;
input [31:0] in21;
input [31:0] in22;
input [31:0] in23;
input [31:0] in24;
input [31:0] in25;
input [31:0] in26;
input [31:0] in27;
input [31:0] in28;
input [31:0] in29;
input [31:0] in30;
input [31:0] in31;

output reg [31:0] out;

//switch mux logic
always @(select) 
case (select)
5'b00000:   out = in0;
5'b00001:   out = in1;
5'b00010:   out = in2;
5'b00011:   out = in3;
5'b00100:   out = in4;
5'b00101:   out = in5;
5'b00110:   out = in6;
5'b00111:   out = in7;
5'b01000:   out = in8;
5'b01001:   out = in9;
5'b01010:   out = in10;
5'b01011:   out = in11;
5'b01100:   out = in12;
5'b01101:   out = in13;
5'b01110:   out = in14;
5'b01111:   out = in15;
5'b10000:   out = in16;
5'b10001:   out = in17;
5'b10010:   out = in18;
5'b10011:   out = in19;
5'b10100:   out = in20;
5'b10101:   out = in21;
5'b10110:   out = in22;
5'b10111:   out = in23;
5'b11000:   out = in24;
5'b11001:   out = in25;
5'b11010:   out = in26;
5'b11011:   out = in27;
5'b11100:   out = in28;
5'b11101:   out = in29;
5'b11110:   out = in30;
5'b11111:   out = in31;
default: out = 32'hxxxxx;
endcase
endmodule//mux32x1

//register file
module registerFile( input clk,input reset,input regWrite,input [4:0] srcRegA,input [4:0] srcRegB,input [4:0] destReg,input [31:0] writeData,output [31:0] outBusA,output [31:0] outBusB);
//register output buses
wire [31:0] outR0;
wire [31:0] outR1;
wire [31:0] outR2;
wire [31:0] outR3;
wire [31:0] outR4;
wire [31:0] outR5;
wire [31:0] outR6;
wire [31:0] outR7;
wire [31:0] outR8;
wire [31:0] outR9;
wire [31:0] outR10;
wire [31:0] outR11;
wire [31:0] outR12;
wire [31:0] outR13;
wire [31:0] outR14;
wire [31:0] outR15;
wire [31:0] outR16;
wire [31:0] outR17;
wire [31:0] outR18;
wire [31:0] outR19;
wire [31:0] outR20;
wire [31:0] outR21;
wire [31:0] outR22;
wire [31:0] outR23;
wire [31:0] outR24;
wire [31:0] outR25;
wire [31:0] outR26;
wire [31:0] outR27;
wire [31:0] outR28;
wire [31:0] outR29;
wire [31:0] outR30;
wire [31:0] outR31;

//destination register selector module
destRegSelector destRegSel(.destReg(destReg),.rst(reset),.clk(clk),.write(regWrite),.writeData(writeData),.bus0(outR0),.bus1(outR1),.bus2(outR2),.bus3(outR3),.bus4(outR4),.bus5(outR5),.bus6(outR6),.bus7(outR7),.bus8(outR8),.bus9(outR9),.bus10(outR10),.bus11(outR11),.bus12(outR12),.bus13(outR13),.bus14(outR14),.bus15(outR15),.bus16(outR16),.bus17(outR17),.bus18(outR18),.bus19(outR19),.bus20(outR20),.bus21(outR21),.bus22(outR22),.bus23(outR23),.bus24(outR24),.bus25(outR25),.bus26(outR26),.bus27(outR27),.bus28(outR28),.bus29(outR29),.bus30(outR30),.bus31(outR31));

//32x1 MUX to select source register A
mux32x1 muxSrcA(.select(srcRegA),.in0(outR0),.in1(outR1),.in2(outR2),.in3(outR3),.in4(outR4),.in5(outR5),.in6(outR6),.in7(outR7),.in8(outR8),.in9(outR9),.in10(outR10),.in11(outR11),.in12(outR12),.in13(outR13),.in14(outR14),.in15(outR15),.in16(outR16),.in17(outR17),.in18(outR18),.in19(outR19),.in20(outR20),.in21(outR21),.in22(outR22),.in23(outR23),.in24(outR24),.in25(outR25),.in26(outR26),.in27(outR27),.in28(outR28),.in29(outR29),.in30(outR30),.in31(outR31),.out(outBusA));

//32x1 MUX to select source register B
mux32x1 muxSrcB(.select(srcRegB),.in0(outR0),.in1(outR1),.in2(outR2),.in3(outR3),.in4(outR4),.in5(outR5),.in6(outR6),.in7(outR7),.in8(outR8),.in9(outR9),.in10(outR10),.in11(outR11),.in12(outR12),.in13(outR13),.in14(outR14),.in15(outR15),.in16(outR16),.in17(outR17),.in18(outR18),.in19(outR19),.in20(outR20),.in21(outR21),.in22(outR22),.in23(outR23),.in24(outR24),.in25(outR25),.in26(outR26),.in27(outR27),.in28(outR28),.in29(outR29),.in30(outR30),.in31(outR31),.out(outBusB));

endmodule//register file
//---------------Register File Module--------------

//ALU module (add,sub,and,or,slt)
module ALU(srcA,srcB,aluControl,result);
input [31:0] srcA;
input [31:0] srcB;
input [3:0] aluControl;

output reg [31:0] result;
always @(aluControl)
begin
if(aluControl==4'b0010) result=srcA + srcB;
if(aluControl==4'b0110) result=srcA - srcB;
if(aluControl==4'b0000) result=srcA && srcB;
if(aluControl==4'b0001) result=srcA || srcB;
if(aluControl==4'b0111) result=(srcA < srcB) ? 32'd1 : 32'd0;
end
endmodule//ALU module (add,sub,and,or,slt)

//regDest 2-to-1 MUX
module regDestMux(select,in0,in1,out);
input select;
input [4:0] in0;
input [4:0] in1;
output reg [4:0] out;

always @(select)
case(select)
1'b0: out=in0;
1'b1: out=in1;
endcase
endmodule////regDest 2-to-1 MUX

//32 bit input 2-to-1 MUX
module MUX32(select,in0,in1,out);
input select;
input [31:0] in0;
input [31:0] in1;
output reg [31:0] out;

always @(select)
case(select)
1'b0: out=in0;
1'b1: out=in1;
endcase
endmodule////regDest 2-to-1 MUX

//16-32 sign extender module
module signXtend(in,out);
input [15:0] in;
output reg [31:0] out;
always @(*)
begin
case(in[15])
1'b1: out = {16'd65535,in};
1'b0: out = {16'd0,in};
endcase
end
endmodule//16-32 sign extender module

//MIPS instuction processor (add,sub,and,or,slt)
module processorMIPS(progCtr,clk,reset);
input [31:0] progCtr;
input clk;
input reset;

wire [31:0] instr;
wire regDst;
wire branch;
wire memRead;
wire memWrite;
wire memToReg;
wire regWrite;
wire aluSrc;
wire [1:0] aluOp;
wire [3:0] aluControl;
wire [4:0] rDestMUXOut;
wire [31:0] writeData,reg1Data,reg2Data,signXtended,aluMUXOut,aluRes,readData;

//instruction memory
instructionMemory iMem(.readAddr(progCtr),.clk(clk),.instruction(instr));

//control unit
controlUnit ctrl(.opCode(instr[31:26]),.regDst(regDst),.branch(branch),.memRead(memRead),.memWrite(memWrite),.memToReg(memToReg),.regWrite(regWrite),.aluSrc(aluSrc),.aluOp(aluOp));

//destination reg MUX
regDestMux rDestMUX(.select(regDst),.in0(instr[20:16]),.in1(instr[15:11]),.out(rDestMUXOut));

//32 bit register file
registerFile regFile(.clk(clk),.reset(reset),.regWrite(regWrite),.srcRegA(instr[25:21]),.srcRegB(instr[20:16]),.destReg(rDestMUXOut),.writeData(writeData),.outBusA(reg1Data),.outBusB(reg2Data));

//16-32 sign extender
signXtend extender(.in(instr[15:0]),.out(signXtended));

//ALU Control
aluControlUnit aluCtrl(.aluOp(aluOp),.funcField(instr[5:0]),.aluControl(aluControl));

//ALU src B MUX
MUX32 aluMUX(.select(aluSrc),.in0(reg2Data),.in1(signXtended),.out(aluMUXOut));

//ALU
ALU alu32(.srcA(reg1Data),.srcB(aluMUXOut),.aluControl(aluControl),.result(aluRes));

//data memory
dataMemory dataMem(.address(aluRes),.clk(clk),.writeData(reg2Data),.memRead(memRead),.memWrite(memWrite),.readData(readData));

//data MUX
MUX32 dataMUX(.select(memToReg),.in0(aluRes),.in1(readData),.out(writeData));


endmodule//MIPS instuction processor

//tester module
module testModule(progCtr,reset,clk);
input [31:0] progCtr;
input clk;
input reset;

//processor module for MIPS
processorMIPS mips(.progCtr(progCtr),.clk(clk),.reset(reset));

initial
begin
mips.dataMem.memory[200]=32'd15;
mips.dataMem.memory[205]=32'd10;

mips.iMem.memory[248]=32'b10001100000011110000000011001000 ;//lw r15 mem(200) 
mips.iMem.memory[249]=32'b10001100000010100000000011001101 ;//lw r10 mem(205)
mips.iMem.memory[250]=32'b00000001111010100001000000100000;//add r15 r10 r2
end

endmodule

However, when I simulate the test module and run the instructions, I don't get the ALU result. I have checked the ALU inputs and ALU Control bits and they are all okay. I have even simulated the ALU separately and it works fine. I have even tried combining the ALU with the ALU control module but that doesn't work too. (BTW I'm using ModelSim) Please help me out here.

\$\endgroup\$
  • 1
    \$\begingroup\$ "I don't get the ALU result" is not a helpful description of the problem. Show the simulation and explain exactly what you see and how it differs from your expected result. \$\endgroup\$ – Kevin Kruse Feb 4 at 12:27
  • \$\begingroup\$ I mean to say that the ALU receives the srcA and srcB inputs along with the aluControl input correctly, but it does not output any result, although when I simulate the ALU module separately, it does give the desired result \$\endgroup\$ – Soumyadipto Banerjee Feb 4 at 14:47
  • \$\begingroup\$ The standard debug approach is to trace the signals in your waveform viewer to see what is happening. In your case you can even compare the two waveforms and see where the diverge. \$\endgroup\$ – Oldfart Feb 4 at 15:46
  • \$\begingroup\$ A few suggestions: (1) don't use procedural continuous assignment (aka assign inside an always/initial). (2) use non-blocking (<=) assignments on synchronous logic (clock triggered always blocks). (3) uses always @* for conbinational always blocks, otherwise you risk an incomplete sensitivity list, such as always @(aluControl) which misses changes on inputs srcA and srcB. (4) don't use casex, use casez for wild card \$\endgroup\$ – Greg Feb 8 at 19:56

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Browse other questions tagged or ask your own question.