出现了问题,写32个数,读31个数,第一个数显示4个X,从第二个数开始读发生了错位,找不到原因
//async_fifo
module async_fifo #(
parameter DATA_WIDTH = 16,
parameter FIFO_DEPTH = 32,
parameter ADDR_WIDTH = 5
)(
//write
input wire wck,
input wire wrst_b,
input wire winc,
input wire [DATA_WIDTH-1:0] wdata,
output wire wfull
//read
input wire rck,
input wire rrst_b,
input wire rinc,
output reg [DATA_WIDTH-1:0] rdata,
output wire rempty
);
//
reg [DATA_WIDTH-1:0] mem [0:31];
reg [ADDR_WIDTH:0] wptr, rptr;
wire [ADDR_WIDTH:0] wptr_gray, rptr_gray;
reg [ADDR_WIDTH:0] wptr_sync0,wptr_sync1,rptr_sync0,rptr_sync1;
//write ptr control
always @(posedge wck or negedge wrst_b) begin
if (!wrst_b) begin
wptr <= 0;
end else if (winc &&!wfull) begin
mem[wptr[ADDR_WIDTH-1:0]] <= wdata;
wptr <=wptr +1;
end
end
//read ptr control
always @(posedge rck or negedge rrst_b) begin
if (!rrst_b) begin
rptr <= 0;
rdata <= 0;
end else if (rinc &&!rempty) begin
rdata <= mem [rptr[ADDR_WIDTH-1:0]]
rptr <= rptr +1;
end
end
//write ptr to read clk
always @(posedge wck or negedge wrst_b) begin
if (!wrst_b) begin
{rptr_sync1,rptr_sync0} <= 0;
end
else begin
rptr_sync0 <= rptr_gray;
rptr_sync1 <= rptr_sync0;
end
end
//read ptr to write clk
always @(posedge rck or negedge rrst_b) begin
if (!rrst_b) {wptr_sync1,wptr_sync0} <= 0;
else begin
wptr_sync0 <= wptr_gray;
wptr_sync1 <= wptr_sync0;
end
end
//gray
assign wptr_gray = wptr ^ (wptr >> 1);
assign rptr_gray = rptr ^ (rptr >> 1);
//
assign wfull =(wptr_gray == {~rptr_sync1[ADDR_WIDTH:ADDR_WIDTH-1],rptr_sync1[ADDR_WIDTH-2:0]});
//
assign rempty = (rptr_gary == wptr_sync1);
//
endmodule
'timescale 1ns/1ps
//async_fifo_testbench
module async_fifo_testbench;
//
reg wck;
reg rck;
reg wrst_b;
reg rrst_b;
reg winc;
reg rinc;
wire wfull;
wire rempty;
reg [15:0] wdata;
wire [15:0] rdata;
reg wdata_txt;
reg rdata_txt;
//
initial begin
wck = 0;
forever #5 wck = ~wck;
end
//
initial begin
rck = 0;
forever #19 rck = ~rck;
end
//
initial begin
wdata_txt = $fopen("wdata_txt");
rdata_txt = $fopen("rdata_txt");
end
//
initial begin
wck = 1'b0;
rck = 1'b0;
wrst_b = 1'b0;
rrst_b = 1'b0;
winc = 1'b0;
rinc = 1'b0;
#100
wrst_b = 1'b1;
rrst_b = 1'b1;
winc = 1'b1;
#1500
winc = 1'b0;
rinc = 1'b0;
#2500
rinc = 1'b0;
// $fclose(wdata_txt);
// $fclose(rdata_txt);
$display ("Simulation finished");
$finish;
end
always @(posedge wck) begin
if (winc && !wfull) begin
wdata <= $random;
end
end
//
always @(posedge wck) begin
if (winc && !wfull) begin
#1
$fwrite(wdata_txt, "%h\n", wdata);
$display("Write data: %h", wdata);
end
end
//
always @(posedge rck) begin
if (rinc && !rempty) begin
#1
$fwrite(rdata_txt, "%h\n", rdata);
$display("Rrite data: %h", rdata);
end
end
//
initial begin
$fsdbDumpfile("wave.fsdb");
$fsdbDumpvars(0,"async_fifo_testbench");
end
//
async_fifo u_async_fifo(
.wck(wck),
.rck(rck),
.wrst_b(wrst_b),
.rrst_b(rrst_b),
.winc(winc),
.rinc(rinc),
.wdata(wdata),
.rdata(rdata),
.wfull(wfull),
.rempty(rempty)
);
endmodule