我看到未定义的输出序列在模拟中读取内存

问题描述

我有一个与时钟 SRAM 存储器的实现有关的问题,该存储器应该存储用户写入的数据,然后显示存储器内容。此外,我创建了一个名为 display 的模块,它简化了读取过程,这样就不需要通过在每次读取后递增一个寄存器来提供应从中提取数据的内存地址。然而,当我模拟电路时,我看不到正确的输出;因此,当我读取内存时,我注意到一些未定义的输出序列。我把相应的代码贴在下面。

//stores output data
module sram_1port_data(
    input clk,//clocked memory
    input wr_en,//when high,data is written,otherwise is read
    input [15:0] address_in,//suppose timer cannout count more than 13ms
    input [3:0] wr_data,//memory does not sotre values greater than 13(ms)
    output reg [3:0] rd_data
);

reg [3:0] memory [2 ** 15 - 1 : 0];

always @(posedge clk) begin
    if(wr_en) memory[address_in] <= wr_data;
    else rd_data <= memory[address_in];
end

endmodule

//display interfacedesigned for the second memory
module display(
    input clk,input wr_en,input [15:0] address_in,input [3:0] wr_data,output [3:0] rd_data
);

reg [15:0] pointer,address;

initial pointer = 16'd0;

sram_1port_data i0(.clk(clk),.wr_en(wr_en),.address_in(address),.wr_data(wr_data),.rd_data(rd_data));

always @(posedge clk) begin
    if(!wr_en) begin
        address <= pointer;
        pointer <= pointer + 1;
    end 
    else address <= address_in;
end

endmodule

//tb for display
module display_tb(
    output reg clk,output reg wr_en,output reg [15:0] address_in,output reg [3:0] wr_data,output [3:0] rd_data
);

display i0(.clk(clk),.address_in(address_in),.rd_data(rd_data));

initial $dumpvars(0,display_tb);

initial begin
    clk = 1'd1;
    repeat (2000)
    #100 clk = ~clk;
end

initial begin
    wr_en = 1'd1;
    #100000 wr_en = 1'd0;
end

integer i;

initial begin
    wr_data = 3'd0;
    for(i = 1;i < 500;i = i + 1) begin
    #200 wr_data = i;
    end
end

initial begin
    address_in = 16'd0;
    for(i = 1;i < 500;i = i + 1) begin
    #200 address_in = i;
    end
end

endmodule

解决方法

当我查看波形时,我发现 rd_data 每次读取时都是未知的 (X)。查看内部地址信号,我发现未知数仅适用于偶数地址。在模拟的早期,您只写入偶数地址。

在您的测试平台中,您在 2 个不同的 i 循环中使用相同的变量 (for)。在您的第二个 for 循环中,使用不同的变量名称(例如,j):

integer j;
initial begin
    address_in = 16'd0;
    for(j = 1;j < 500;j = j + 1) begin
    #200 address_in = j;
    end
end

现在,所有读取都有已知值,因为它写入所有地址(偶数和奇数)。


您还可以在与写入数据相同的 for 循环中设置地址。在这种情况下,这可能是更好的方法。

initial begin
    wr_data    =  3'd0;
    address_in = 16'd0;
    for(i = 1;i < 500;i = i + 1) begin
        #200;
        wr_data    = i;
        address_in = i;
    end
end

相关问答

错误1:Request method ‘DELETE‘ not supported 错误还原:...
错误1:启动docker镜像时报错:Error response from daemon:...
错误1:private field ‘xxx‘ is never assigned 按Alt...
报错如下,通过源不能下载,最后警告pip需升级版本 Requirem...