util_axis_fifo: Add room and level outputs
Add a room output on the input side that reports how many free entries the FIFO has and a level output on the output side that reports how many valid entries are in the FIFO. Note that the level output is only accurate if the output of the FIFO is not registered, otherwise it might be off by one. Signed-off-by: Lars-Peter Clausen <lars@metafoo.de>main
parent
ae4e7a0c37
commit
762fa3290b
|
@ -42,13 +42,15 @@ module fifo_address_gray (
|
||||||
input m_axis_ready,
|
input m_axis_ready,
|
||||||
output reg m_axis_valid,
|
output reg m_axis_valid,
|
||||||
output [C_ADDRESS_WIDTH-1:0] m_axis_raddr_next,
|
output [C_ADDRESS_WIDTH-1:0] m_axis_raddr_next,
|
||||||
|
output reg [C_ADDRESS_WIDTH:0] m_axis_level,
|
||||||
|
|
||||||
input s_axis_aclk,
|
input s_axis_aclk,
|
||||||
input s_axis_aresetn,
|
input s_axis_aresetn,
|
||||||
output reg s_axis_ready,
|
output reg s_axis_ready,
|
||||||
input s_axis_valid,
|
input s_axis_valid,
|
||||||
output reg s_axis_empty,
|
output reg s_axis_empty,
|
||||||
output [C_ADDRESS_WIDTH-1:0] s_axis_waddr
|
output [C_ADDRESS_WIDTH-1:0] s_axis_waddr,
|
||||||
|
output reg [C_ADDRESS_WIDTH:0] s_axis_room
|
||||||
);
|
);
|
||||||
|
|
||||||
parameter C_ADDRESS_WIDTH = 4;
|
parameter C_ADDRESS_WIDTH = 4;
|
||||||
|
|
|
@ -43,13 +43,15 @@ module fifo_address_gray_pipelined (
|
||||||
output reg m_axis_valid,
|
output reg m_axis_valid,
|
||||||
output [C_ADDRESS_WIDTH-1:0] m_axis_raddr_next,
|
output [C_ADDRESS_WIDTH-1:0] m_axis_raddr_next,
|
||||||
output [C_ADDRESS_WIDTH-1:0] m_axis_raddr,
|
output [C_ADDRESS_WIDTH-1:0] m_axis_raddr,
|
||||||
|
output reg [C_ADDRESS_WIDTH:0] m_axis_level,
|
||||||
|
|
||||||
input s_axis_aclk,
|
input s_axis_aclk,
|
||||||
input s_axis_aresetn,
|
input s_axis_aresetn,
|
||||||
output reg s_axis_ready,
|
output reg s_axis_ready,
|
||||||
input s_axis_valid,
|
input s_axis_valid,
|
||||||
output reg s_axis_empty,
|
output reg s_axis_empty,
|
||||||
output [C_ADDRESS_WIDTH-1:0] s_axis_waddr
|
output [C_ADDRESS_WIDTH-1:0] s_axis_waddr,
|
||||||
|
output reg [C_ADDRESS_WIDTH:0] s_axis_room
|
||||||
);
|
);
|
||||||
|
|
||||||
parameter C_ADDRESS_WIDTH = 4;
|
parameter C_ADDRESS_WIDTH = 4;
|
||||||
|
@ -127,19 +129,23 @@ begin
|
||||||
if (s_axis_aresetn == 1'b0) begin
|
if (s_axis_aresetn == 1'b0) begin
|
||||||
s_axis_ready <= 1'b1;
|
s_axis_ready <= 1'b1;
|
||||||
s_axis_empty <= 1'b1;
|
s_axis_empty <= 1'b1;
|
||||||
|
s_axis_room <= 2**C_ADDRESS_WIDTH;
|
||||||
end else begin
|
end else begin
|
||||||
s_axis_ready <= (_s_axis_raddr[C_ADDRESS_WIDTH] == _s_axis_waddr_next[C_ADDRESS_WIDTH] ||
|
s_axis_ready <= (_s_axis_raddr[C_ADDRESS_WIDTH] == _s_axis_waddr_next[C_ADDRESS_WIDTH] ||
|
||||||
_s_axis_raddr[C_ADDRESS_WIDTH-1:0] != _s_axis_waddr_next[C_ADDRESS_WIDTH-1:0]);
|
_s_axis_raddr[C_ADDRESS_WIDTH-1:0] != _s_axis_waddr_next[C_ADDRESS_WIDTH-1:0]);
|
||||||
s_axis_empty <= _s_axis_raddr == _s_axis_waddr_next;
|
s_axis_empty <= _s_axis_raddr == _s_axis_waddr_next;
|
||||||
|
s_axis_room <= _s_axis_raddr - _s_axis_waddr_next + 2**C_ADDRESS_WIDTH;
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
always @(posedge m_axis_aclk)
|
always @(posedge m_axis_aclk)
|
||||||
begin
|
begin
|
||||||
if (s_axis_aresetn == 1'b0)
|
if (s_axis_aresetn == 1'b0) begin
|
||||||
m_axis_valid <= 1'b0;
|
m_axis_valid <= 1'b0;
|
||||||
else begin
|
m_axis_level <= 'h00;
|
||||||
|
end else begin
|
||||||
m_axis_valid <= _m_axis_waddr != _m_axis_raddr_next;
|
m_axis_valid <= _m_axis_waddr != _m_axis_raddr_next;
|
||||||
|
m_axis_level <= _m_axis_waddr - _m_axis_raddr_next;
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|
|
@ -44,18 +44,24 @@ module fifo_address_sync (
|
||||||
output reg m_axis_valid,
|
output reg m_axis_valid,
|
||||||
output reg [C_ADDRESS_WIDTH-1:0] m_axis_raddr,
|
output reg [C_ADDRESS_WIDTH-1:0] m_axis_raddr,
|
||||||
output reg [C_ADDRESS_WIDTH-1:0] m_axis_raddr_next,
|
output reg [C_ADDRESS_WIDTH-1:0] m_axis_raddr_next,
|
||||||
|
output [C_ADDRESS_WIDTH:0] m_axis_level,
|
||||||
|
|
||||||
output reg s_axis_ready,
|
output reg s_axis_ready,
|
||||||
input s_axis_valid,
|
input s_axis_valid,
|
||||||
output reg s_axis_empty,
|
output reg s_axis_empty,
|
||||||
output reg [C_ADDRESS_WIDTH-1:0] s_axis_waddr
|
output reg [C_ADDRESS_WIDTH-1:0] s_axis_waddr,
|
||||||
|
output [C_ADDRESS_WIDTH:0] s_axis_room
|
||||||
);
|
);
|
||||||
|
|
||||||
parameter C_ADDRESS_WIDTH = 4;
|
parameter C_ADDRESS_WIDTH = 4;
|
||||||
|
|
||||||
reg [C_ADDRESS_WIDTH:0] level;
|
reg [C_ADDRESS_WIDTH:0] room = 2**C_ADDRESS_WIDTH;
|
||||||
|
reg [C_ADDRESS_WIDTH:0] level = 'h00;
|
||||||
reg [C_ADDRESS_WIDTH:0] level_next;
|
reg [C_ADDRESS_WIDTH:0] level_next;
|
||||||
|
|
||||||
|
assign s_axis_room = room;
|
||||||
|
assign m_axis_level = level;
|
||||||
|
|
||||||
wire read = m_axis_ready & m_axis_valid;
|
wire read = m_axis_ready & m_axis_valid;
|
||||||
wire write = s_axis_ready & s_axis_valid;
|
wire write = s_axis_ready & s_axis_valid;
|
||||||
|
|
||||||
|
@ -94,8 +100,12 @@ begin
|
||||||
if (resetn == 1'b0) begin
|
if (resetn == 1'b0) begin
|
||||||
m_axis_valid <= 1'b0;
|
m_axis_valid <= 1'b0;
|
||||||
s_axis_ready <= 1'b0;
|
s_axis_ready <= 1'b0;
|
||||||
|
level <= 'h00;
|
||||||
|
room <= 2**C_ADDRESS_WIDTH;
|
||||||
|
s_axis_empty <= 'h00;
|
||||||
end else begin
|
end else begin
|
||||||
level <= level_next;
|
level <= level_next;
|
||||||
|
room <= 2**C_ADDRESS_WIDTH - level_next;
|
||||||
m_axis_valid <= level_next != 0;
|
m_axis_valid <= level_next != 0;
|
||||||
s_axis_ready <= level_next != 2**C_ADDRESS_WIDTH;
|
s_axis_ready <= level_next != 2**C_ADDRESS_WIDTH;
|
||||||
s_axis_empty <= level_next == 0;
|
s_axis_empty <= level_next == 0;
|
||||||
|
|
|
@ -42,13 +42,15 @@ module util_axis_fifo (
|
||||||
input m_axis_ready,
|
input m_axis_ready,
|
||||||
output m_axis_valid,
|
output m_axis_valid,
|
||||||
output [C_DATA_WIDTH-1:0] m_axis_data,
|
output [C_DATA_WIDTH-1:0] m_axis_data,
|
||||||
|
output [C_ADDRESS_WIDTH:0] m_axis_level,
|
||||||
|
|
||||||
input s_axis_aclk,
|
input s_axis_aclk,
|
||||||
input s_axis_aresetn,
|
input s_axis_aresetn,
|
||||||
output s_axis_ready,
|
output s_axis_ready,
|
||||||
input s_axis_valid,
|
input s_axis_valid,
|
||||||
input [C_DATA_WIDTH-1:0] s_axis_data,
|
input [C_DATA_WIDTH-1:0] s_axis_data,
|
||||||
output s_axis_empty
|
output s_axis_empty,
|
||||||
|
output [C_ADDRESS_WIDTH:0] s_axis_room
|
||||||
);
|
);
|
||||||
|
|
||||||
parameter C_DATA_WIDTH = 64;
|
parameter C_DATA_WIDTH = 64;
|
||||||
|
@ -86,8 +88,10 @@ sync_bits #(
|
||||||
);
|
);
|
||||||
|
|
||||||
assign m_axis_valid = m_axis_raddr != m_axis_waddr;
|
assign m_axis_valid = m_axis_raddr != m_axis_waddr;
|
||||||
|
assign m_axis_level = m_axis_valid;
|
||||||
assign s_axis_ready = s_axis_raddr == s_axis_waddr;
|
assign s_axis_ready = s_axis_raddr == s_axis_waddr;
|
||||||
assign s_axis_empty = s_axis_raddr == s_axis_waddr;
|
assign s_axis_empty = s_axis_ready;
|
||||||
|
assign s_axis_room = s_axis_ready;
|
||||||
|
|
||||||
always @(posedge s_axis_aclk) begin
|
always @(posedge s_axis_aclk) begin
|
||||||
if (s_axis_ready)
|
if (s_axis_ready)
|
||||||
|
@ -131,17 +135,18 @@ fifo_address_gray_pipelined #(
|
||||||
) i_address_gray (
|
) i_address_gray (
|
||||||
.m_axis_aclk(m_axis_aclk),
|
.m_axis_aclk(m_axis_aclk),
|
||||||
.m_axis_aresetn(m_axis_aresetn),
|
.m_axis_aresetn(m_axis_aresetn),
|
||||||
|
|
||||||
.m_axis_ready(_m_axis_ready),
|
.m_axis_ready(_m_axis_ready),
|
||||||
.m_axis_valid(_m_axis_valid),
|
.m_axis_valid(_m_axis_valid),
|
||||||
.m_axis_raddr(m_axis_raddr),
|
.m_axis_raddr(m_axis_raddr),
|
||||||
|
.m_axis_level(m_axis_level),
|
||||||
|
|
||||||
.s_axis_aclk(s_axis_aclk),
|
.s_axis_aclk(s_axis_aclk),
|
||||||
.s_axis_aresetn(s_axis_aresetn),
|
.s_axis_aresetn(s_axis_aresetn),
|
||||||
.s_axis_ready(s_axis_ready),
|
.s_axis_ready(s_axis_ready),
|
||||||
.s_axis_valid(s_axis_valid),
|
.s_axis_valid(s_axis_valid),
|
||||||
.s_axis_empty(s_axis_empty),
|
.s_axis_empty(s_axis_empty),
|
||||||
.s_axis_waddr(s_axis_waddr)
|
.s_axis_waddr(s_axis_waddr),
|
||||||
|
.s_axis_room(s_axis_room)
|
||||||
);
|
);
|
||||||
|
|
||||||
end else begin
|
end else begin
|
||||||
|
@ -151,15 +156,16 @@ fifo_address_sync #(
|
||||||
) i_address_sync (
|
) i_address_sync (
|
||||||
.clk(m_axis_aclk),
|
.clk(m_axis_aclk),
|
||||||
.resetn(m_axis_aresetn),
|
.resetn(m_axis_aresetn),
|
||||||
|
|
||||||
.m_axis_ready(_m_axis_ready),
|
.m_axis_ready(_m_axis_ready),
|
||||||
.m_axis_valid(_m_axis_valid),
|
.m_axis_valid(_m_axis_valid),
|
||||||
.m_axis_raddr(m_axis_raddr),
|
.m_axis_raddr(m_axis_raddr),
|
||||||
|
.m_axis_level(m_axis_level),
|
||||||
|
|
||||||
.s_axis_ready(s_axis_ready),
|
.s_axis_ready(s_axis_ready),
|
||||||
.s_axis_valid(s_axis_valid),
|
.s_axis_valid(s_axis_valid),
|
||||||
.s_axis_empty(s_axis_empty),
|
.s_axis_empty(s_axis_empty),
|
||||||
.s_axis_waddr(s_axis_waddr)
|
.s_axis_waddr(s_axis_waddr),
|
||||||
|
.s_axis_room(s_axis_room)
|
||||||
);
|
);
|
||||||
|
|
||||||
end
|
end
|
||||||
|
|
Loading…
Reference in New Issue