`timescale 1ns / 1ps
module snfifo1(
input clk,
input rst_n,
input[3:0] data_in,
input write,
input read,
output[3:0] data_out,
output full,
output emty
);
reg[3:0] fifo_reg[3:0];//depth4
reg[1:0] w_head,R_tail;
reg[1:0] count;
reg [3:0] dout;
reg f,e;
parameter MAX = 3;
//*************update w_head*************
always @ (posedge clk)
if(!rst_n)
w_head <= 2'd0;
else if(write && !full)
w_head <= w_head + 1'b1;
//else if(full) w_head <= 3'd0;
//*************update R_tail*************
always @ (posedge clk)
if(!rst_n)
R_tail <= 2'd0;
else if(read && !emty)
R_tail <= R_tail + 1'b1;
//else if(emty) R_tail <= 3'd0;
//**************count************
always @(posedge clk)
if(!rst_n)
begin
count <= 2'd0;
end
else
case({read,write})
2'b00:
count <= count;
2'b01:
if(count != MAX)
count <= count + 1'b1;
2'b10:
if(count != 0)
count <= count - 1'b1;
2'b11:
; // count <= count;
endcase
//************read**********
always @(posedge clk)
if(!rst_n)
dout <= 4'd0;
else if(read && !emty)
dout <= fifo_reg[R_tail];
///***************write**********
always @(posedge clk)
if(write && !full)
fifo_reg[w_head] <= data_in;
always @ (posedge clk)
if(count==0)
e <= 1'b1;
else e <= 1'b0;
always @ (posedge clk)
if(count==MAX)
f <= 1'b1;
else f <= 1'b0;
assign full = f;
assign emty = e;
//-----------------------------
//assign full = (count == MAX); //? 1'b1:1'b0;
//assign emty = (count == 0 );// ? 1'b1:1'b0;
/*always @ (count)
if(count==0)
emty <= 1'b1;
else emty <= 1'b0;
always @ (count)
if(count==MAX)
full <= 1'b1;
else full <= 1'b0;
*/
assign data_out = dout;
endmodule
以下是TB
`timescale 1ns / 1ps
module txt();
reg clk;
reg rst_n;
reg write,read;
reg [3:0] data_in;
wire [3:0] data_out;
wire full,emty;
initial
begin
clk =0;
rst_n =0;
#100
rst_n = 1;
write =0;
read = 0;
#20
write = 1;
// #20
data_in = 4'd1;
#20
data_in = 4'd2;
#20
data_in = 4'd3;
#20
data_in = 4'd4;
#20
write =1;
#20
write =0;
read =1;
#100;
read = 0;
write = 1;
// #20
data_in = 4'd6;
#20
data_in = 4'd7;
read = 1;
#20
data_in = 4'd8;
#20
data_in = 4'd9;
#20
write = 1;
// #20read
data_in = 4'd5;
#20
data_in = 4'd2;
#20
read =0;
data_in = 4'd3;
#20
data_in = 4'd4;
#20
write =0;
read =1;
#20 $stop;
end
always #10 clk =~clk;
snfifo1 snfifo1_inst(
.clk,
.rst_n,
.write,
.read,
.data_in,
.data_out,
.full,
.emty
);
endmodule