顶层文件:module dcfifo(
wclk,
rclk,
wrst_n,
rrst_n,
wpush,
rpop,
wfull,
rempty,
wdata,
rdata
);
input wclk;
input rclk;
input wrst_n;
input rrst_n;
input wpush;
input rpop;
input [31:0]wdata;
output wfull;
output rempty;
output reg[31:0]rdata;
wire w_en;
wire r_en;
wire wfull;
wire rempty;
wire [3:0]waddr;//写地址
wire [3:0]raddr;//读地址
wire [4:0]wptr_gray;
wire [4:0]rptr_gray;
reg [4:0]wptr;//写指针
reg [4:0]rptr;//读指针
reg [4:0]wptr_rclk1;
reg [4:0]wptr_rclk2;
reg [4:0]rptr_wclk1;
reg [4:0]rptr_wclk2;
reg [31:0]mem[15:0];
reg [4:0]tempi;
parameter memsize = 16;
assign w_en = wpush& (!wfull);
assign r_en = rpop & (!rempty);
//写指针变化
always@(posedge wclk,negedge wrst_n)
if(!wrst_n)
wptr <= 0;
else if(w_en)
wptr <= wptr + 1'b1;
else
wptr <= wptr;
//读指针变化
always@(posedge rclk,negedge rrst_n)
if(!rrst_n)
rptr <= 0;
else if(r_en)
rptr <= rptr + 1'b1;
else
rptr <= rptr;
assign waddr = wptr[3:0];
assign raddr = rptr[3:0];
//二进制转格雷码
assign wptr_gray = (wptr >> 1) ^ wptr;
assign rptr_gray = (rptr >> 1) ^ rptr;
//读指针同步到写时钟域
always@(posedge wclk,negedge wrst_n)
if(!wrst_n)begin
rptr_wclk1 <= 0;
rptr_wclk2 <= 0;
end
else begin
rptr_wclk1 <= rptr_gray;
rptr_wclk2 <= rptr_wclk1;
end
//写指针同步到读时钟域
always@(posedge rclk,negedge rrst_n)
if(!rrst_n)begin
wptr_rclk1 <= 0;
wptr_rclk2 <= 0;
end
else begin
wptr_rclk1 <= wptr_gray;
wptr_rclk2 <= wptr_rclk1;
end
//空满判断
assign rempty = (wptr_rclk2 == rptr_gray)?1:0;
assign wfull = ({!rptr_wclk2[4],!rptr_wclk2[3],rptr_wclk2[1:0]} == wptr_gray)?1:0;
//读写memory
always@(posedge wclk,negedge wrst_n)
if(!wrst_n)
for(tempi=0;tempi<memsize;tempi=tempi+1)
mem[tempi] <= 0;
else if(w_en)
mem[waddr] <= wdata;
always@(posedge rclk,negedge rrst_n)
if(!rrst_n)
rdata <= 0;
else
rdata <= mem[raddr];
endmodule
testbench:
`timescale 1ns/1ps
module dcfifo_tb;
//source define
reg wclk;
reg rclk;
reg wrst_n;
reg rrst_n;
reg wpush;
reg rpop;
reg [31:0]wdata;
//probe define
wire wfull;
wire rempty;
wire [31:0]rdata;
parameter CYCLE_W = 20,CYCLE_R = 200;
//instant user module
dcfifo dcfifo1(
.wclk(wclk),
.rclk(rclk),
.wrst_n(wrst_n),
.rrst_n(rrst_n),
.wpush(wpush),
.rpop(rpop),
.wfull(wfull),
.rempty(rempty),
.wdata(wdata),
.rdata(rdata)
);
//产生时钟
initial begin
wclk = 0;
forever
#(CYCLE_W/2) wclk = ~wclk;
end
initial begin
rclk = 0;
forever
#(CYCLE_R/2) rclk = ~rclk;
end
//产生复位
initial begin
wrst_n = 1;
#2 wrst_n = 0;
#(CYCLE_W*3) wrst_n = 1;
end
initial begin
rrst_n = 1;
#2 rrst_n = 0;
#(CYCLE_R*2) rrst_n = 1;
end
//
initial begin
#40000 $stop;
end
always@(posedge wclk or negedge wrst_n)
if(!wrst_n)
wpush <= 0;
else
wpush <= {$random}%2;
always@(posedge rclk or negedge rrst_n)
if(!rrst_n)
rpop <= 0;
else
rpop <= $random;
always@(*)
if(wpush)
wdata <= $random;
else
wdata <= 0;
endmodule
modelsim错误截图:
[size=0.83em]image.png (349.36 KB, 下载次数: 0)
下载附件 [url=]保存到相册[/url]
[color=rgb(153, 153, 153) !important]4 分钟前 上传
错误原因貌似是说我例化的端口在原模块中不存在,可是我明明是直接把原模块端口粘过来的,不存在错误,所以请大家看看问题出在哪。
|