I'm creating a simple register file in SystemVerilog, with a total of 6 registers that can be written to/read from. When I run a simulation in ModelSim, the output never shows the correct data - it stays at 0
and ignores any read signals. This led me to believe that either a) the values I'm writing to the registers may not be getting stored, so when I try to read a value from one of the registers they don't output anything, or b) data is being written to the registers, but I'm not pulling the data from those registers correctly.
Here is my .sv file:
module register_file#(parameter bits = 16, registers = 6)(clock, write_enable, write_reg, data_in, read_reg0, read_reg1, data_out0, data_out1);
input clock, write_enable;
input [2:0] write_reg, read_reg0, read_reg1;
input [bits-1:0] data_in;
output [bits-1:0] data_out0, data_out1;
wire [bits-1:0] data_out0_wire, data_out1_wire;
reg [bits-1:0] data_out0_reg, data_out1_reg;
reg [bits-1:0] r1, r2, r3, r4, r5, r6;
assign data_out0 = data_out0_reg;
assign data_out1 = data_out1_reg;
always @(posedge clock)
begin
if(write_enable)
case(write_reg)
1: r1 = data_in;
2: r2 = data_in;
3: r3 = data_in;
4: r4 = data_in;
5: r5 = data_in;
6: r6 = data_in;
endcase
data_out0_reg <= data_out0_wire;
data_out1_reg <= data_out1_wire;
end
always @(read_reg0)
case(read_reg0)
1: data_out0_wire = r1;
2: data_out0_wire = r2;
3: data_out0_wire = r3;
4: data_out0_wire = r4;
5: data_out0_wire = r5;
6: data_out0_wire = r6;
endcase
always @(read_reg1)
case(read_reg1)
1: data_out1_wire = r1;
2: data_out1_wire = r2;
3: data_out1_wire = r3;
4: data_out1_wire = r4;
5: data_out1_wire = r5;
6: data_out1_wire = r6;
endcase
endmodule
Here is my testbench:
`timescale 1ns / 1ps
module test_partC();
reg clk,write_enable;
reg [2:0] write_reg, read_reg0, read_reg1;
reg [15:0] data_in;
reg [15:0] data_out0, data_out1;
register_file dut (clock, write_enable, write_reg, data_in, read_reg0, read_reg1, data_out0, data_out1);
// Toggle the clock every 10 ns
initial
begin
clk = 0;
forever #10 clk = !clk;
end
initial
begin
write_reg = 1;
write_enable = 1;
data_in = 10;
#20;
write_reg = 2;
write_enable = 1;
data_in = 15;
#20;
write_reg = 3;
write_enable = 1;
data_in = 20;
#20;
read_reg0 = 1;
write_enable = 0;
#20;
read_reg0 = 2;
read_reg1 = 3;
#20;
read_reg0 = 1;
write_reg = 1;
write_enable = 1;
data_in = 30;
end
endmodule
I added an extra set of registers from the data_out
signals in trying to find a potential solution to the problem I'm having, but I'm not sure if that changes anything.
What I was trying to do was, based on the number from the read_reg
signal, read the value from the corresponding register, which sends the signal down the data_out_wire
, stores it in a data_out
register, and then sends the signal out via a wire (output data_out
).
I'm new to SystemVerilog, and I'm struggling to figure out where I went wrong; any help is greatly appreciated.
wire
.. Is it even required for me to have the extra wires/reg for the output variables? Or could I have just passed the register values to the output signals in the case blocks? (i.e.1: data_out0 = r1;
) That is what I originally had, but the simulation didn't behave any differently. \$\endgroup\$