1
0
mirror of https://github.com/corundum/corundum.git synced 2025-01-16 08:12:53 +08:00

merged changes in eth

This commit is contained in:
Alex Forencich 2021-10-13 16:41:04 -07:00
commit 74a7cc08e5
22 changed files with 842 additions and 579 deletions

View File

@ -504,10 +504,9 @@ axis_async_fifo #(
.DROP_WHEN_FULL(1)
)
max_rx_fifo (
.async_rst(rst | qsfp1_mac_1_rx_rst),
// AXI input
.s_clk(qsfp1_mac_1_rx_clk),
.s_rst(qsfp1_mac_1_rx_rst),
.s_axis_tdata(qsfp1_mac_1_rx_axis_tdata),
.s_axis_tkeep(qsfp1_mac_1_rx_axis_tkeep),
.s_axis_tvalid(qsfp1_mac_1_rx_axis_tvalid),
@ -519,6 +518,7 @@ max_rx_fifo (
// AXI output
.m_clk(clk),
.m_rst(rst),
.m_axis_tdata(rx_axis_tdata),
.m_axis_tkeep(rx_axis_tkeep),
.m_axis_tvalid(rx_axis_tvalid),
@ -554,10 +554,9 @@ axis_async_fifo #(
.DROP_WHEN_FULL(0)
)
max_tx_fifo (
.async_rst(rst | qsfp1_mac_1_tx_rst),
// AXI input
.s_clk(clk),
.s_rst(rst),
.s_axis_tdata(tx_axis_tdata),
.s_axis_tkeep(tx_axis_tkeep),
.s_axis_tvalid(tx_axis_tvalid),
@ -569,6 +568,7 @@ max_tx_fifo (
// AXI output
.m_clk(qsfp1_mac_1_tx_clk),
.m_rst(qsfp1_mac_1_tx_rst),
.m_axis_tdata(qsfp1_mac_1_tx_axis_tdata),
.m_axis_tkeep(qsfp1_mac_1_tx_axis_tkeep),
.m_axis_tvalid(qsfp1_mac_1_tx_axis_tvalid),

View File

@ -94,6 +94,6 @@ constrain_sync_reset_inst "qsfp1_eth_xcvr_phy_quad|eth_xcvr_phy_4|phy_tx_rst_res
constrain_sync_reset_inst "qsfp1_eth_xcvr_phy_quad|eth_xcvr_phy_4|phy_rx_rst_reset_sync_inst"
# 10G MAC
constrain_eth_mac_fifo_inst "core_inst|eth_mac_10g_inst"
constrain_eth_mac_fifo_inst "core_inst|eth_mac_10g_fifo_inst"
constrain_axis_async_fifo_inst "core_inst|eth_mac_10g_fifo_inst|rx_fifo|fifo_inst"
constrain_axis_async_fifo_inst "core_inst|eth_mac_10g_fifo_inst|tx_fifo|fifo_inst"

View File

@ -78,15 +78,11 @@ module axis_async_fifo #
parameter DROP_WHEN_FULL = 0
)
(
/*
* Common asynchronous reset
*/
input wire async_rst,
/*
* AXI input
*/
input wire s_clk,
input wire s_rst,
input wire [DATA_WIDTH-1:0] s_axis_tdata,
input wire [KEEP_WIDTH-1:0] s_axis_tkeep,
input wire s_axis_tvalid,
@ -100,6 +96,7 @@ module axis_async_fifo #
* AXI output
*/
input wire m_clk,
input wire m_rst,
output wire [DATA_WIDTH-1:0] m_axis_tdata,
output wire [KEEP_WIDTH-1:0] m_axis_tkeep,
output wire m_axis_tvalid,
@ -214,9 +211,7 @@ reg mem_read_data_valid_reg = 1'b0;
wire [WIDTH-1:0] s_axis;
(* SHREG_EXTRACT = "NO" *)
reg [WIDTH-1:0] m_axis_pipe_reg[PIPELINE_OUTPUT-1:0];
(* SHREG_EXTRACT = "NO" *)
reg [PIPELINE_OUTPUT-1:0] m_axis_tvalid_pipe_reg = 1'b0;
// full when first TWO MSBs do NOT match, but rest matches
@ -233,12 +228,18 @@ reg write;
reg read;
reg store_output;
reg s_frame_reg = 1'b0;
reg m_frame_reg = 1'b0;
reg drop_frame_reg = 1'b0;
reg send_frame_reg = 1'b0;
reg overflow_reg = 1'b0;
reg bad_frame_reg = 1'b0;
reg good_frame_reg = 1'b0;
reg m_drop_frame_reg = 1'b0;
reg m_terminate_frame_reg = 1'b0;
reg overflow_sync1_reg = 1'b0;
reg overflow_sync2_reg = 1'b0;
reg overflow_sync3_reg = 1'b0;
@ -263,14 +264,23 @@ generate
if (USER_ENABLE) assign s_axis[USER_OFFSET +: USER_WIDTH] = s_axis_tuser;
endgenerate
assign m_axis_tvalid = m_axis_tvalid_pipe_reg[PIPELINE_OUTPUT-1];
wire m_axis_tvalid_pipe = m_axis_tvalid_pipe_reg[PIPELINE_OUTPUT-1];
assign m_axis_tdata = m_axis_pipe_reg[PIPELINE_OUTPUT-1][DATA_WIDTH-1:0];
assign m_axis_tkeep = KEEP_ENABLE ? m_axis_pipe_reg[PIPELINE_OUTPUT-1][KEEP_OFFSET +: KEEP_WIDTH] : {KEEP_WIDTH{1'b1}};
assign m_axis_tlast = LAST_ENABLE ? m_axis_pipe_reg[PIPELINE_OUTPUT-1][LAST_OFFSET] : 1'b1;
assign m_axis_tid = ID_ENABLE ? m_axis_pipe_reg[PIPELINE_OUTPUT-1][ID_OFFSET +: ID_WIDTH] : {ID_WIDTH{1'b0}};
assign m_axis_tdest = DEST_ENABLE ? m_axis_pipe_reg[PIPELINE_OUTPUT-1][DEST_OFFSET +: DEST_WIDTH] : {DEST_WIDTH{1'b0}};
assign m_axis_tuser = USER_ENABLE ? m_axis_pipe_reg[PIPELINE_OUTPUT-1][USER_OFFSET +: USER_WIDTH] : {USER_WIDTH{1'b0}};
wire [DATA_WIDTH-1:0] m_axis_tdata_pipe = m_axis_pipe_reg[PIPELINE_OUTPUT-1][DATA_WIDTH-1:0];
wire [KEEP_WIDTH-1:0] m_axis_tkeep_pipe = KEEP_ENABLE ? m_axis_pipe_reg[PIPELINE_OUTPUT-1][KEEP_OFFSET +: KEEP_WIDTH] : {KEEP_WIDTH{1'b1}};
wire m_axis_tlast_pipe = LAST_ENABLE ? m_axis_pipe_reg[PIPELINE_OUTPUT-1][LAST_OFFSET] : 1'b1;
wire [ID_WIDTH-1:0] m_axis_tid_pipe = ID_ENABLE ? m_axis_pipe_reg[PIPELINE_OUTPUT-1][ID_OFFSET +: ID_WIDTH] : {ID_WIDTH{1'b0}};
wire [DEST_WIDTH-1:0] m_axis_tdest_pipe = DEST_ENABLE ? m_axis_pipe_reg[PIPELINE_OUTPUT-1][DEST_OFFSET +: DEST_WIDTH] : {DEST_WIDTH{1'b0}};
wire [USER_WIDTH-1:0] m_axis_tuser_pipe = USER_ENABLE ? m_axis_pipe_reg[PIPELINE_OUTPUT-1][USER_OFFSET +: USER_WIDTH] : {USER_WIDTH{1'b0}};
assign m_axis_tvalid = m_axis_tvalid_pipe;
assign m_axis_tdata = m_axis_tdata_pipe;
assign m_axis_tkeep = m_axis_tkeep_pipe;
assign m_axis_tlast = (m_terminate_frame_reg ? 1'b1 : m_axis_tlast_pipe);
assign m_axis_tid = m_axis_tid_pipe;
assign m_axis_tdest = m_axis_tdest_pipe;
assign m_axis_tuser = (m_terminate_frame_reg ? USER_BAD_FRAME_VALUE : m_axis_tuser_pipe);
assign s_status_overflow = overflow_reg;
assign s_status_bad_frame = bad_frame_reg;
@ -281,30 +291,32 @@ assign m_status_bad_frame = bad_frame_sync3_reg ^ bad_frame_sync4_reg;
assign m_status_good_frame = good_frame_sync3_reg ^ good_frame_sync4_reg;
// reset synchronization
always @(posedge s_clk or posedge async_rst) begin
if (async_rst) begin
always @(posedge m_clk or posedge m_rst) begin
if (m_rst) begin
s_rst_sync1_reg <= 1'b1;
s_rst_sync2_reg <= 1'b1;
s_rst_sync3_reg <= 1'b1;
end else begin
s_rst_sync1_reg <= 1'b0;
s_rst_sync2_reg <= s_rst_sync1_reg || m_rst_sync1_reg;
s_rst_sync3_reg <= s_rst_sync2_reg;
end
end
always @(posedge m_clk or posedge async_rst) begin
if (async_rst) begin
always @(posedge s_clk) begin
s_rst_sync2_reg <= s_rst_sync1_reg;
s_rst_sync3_reg <= s_rst_sync2_reg;
end
always @(posedge s_clk or posedge s_rst) begin
if (s_rst) begin
m_rst_sync1_reg <= 1'b1;
m_rst_sync2_reg <= 1'b1;
m_rst_sync3_reg <= 1'b1;
end else begin
m_rst_sync1_reg <= 1'b0;
m_rst_sync2_reg <= s_rst_sync1_reg || m_rst_sync1_reg;
m_rst_sync3_reg <= m_rst_sync2_reg;
end
end
always @(posedge m_clk) begin
m_rst_sync2_reg <= m_rst_sync1_reg;
m_rst_sync3_reg <= m_rst_sync2_reg;
end
// Write logic
always @(posedge s_clk) begin
overflow_reg <= 1'b0;
@ -321,14 +333,39 @@ always @(posedge s_clk) begin
end
end
if (s_axis_tready && s_axis_tvalid && LAST_ENABLE) begin
// track input frame status
s_frame_reg <= !s_axis_tlast;
end
if (s_rst_sync3_reg && LAST_ENABLE) begin
// if sink side is reset during transfer, drop partial frame
if (s_frame_reg && !(s_axis_tready && s_axis_tvalid && s_axis_tlast)) begin
drop_frame_reg <= 1'b1;
end
if (s_axis_tready && s_axis_tvalid && !s_axis_tlast) begin
drop_frame_reg <= 1'b1;
end
end
if (s_axis_tready && s_axis_tvalid) begin
// transfer in
if (!FRAME_FIFO) begin
// normal FIFO mode
mem[wr_ptr_reg[ADDR_WIDTH-1:0]] <= s_axis;
wr_ptr_temp = wr_ptr_reg + 1;
wr_ptr_reg <= wr_ptr_temp;
wr_ptr_gray_reg <= wr_ptr_temp ^ (wr_ptr_temp >> 1);
if (drop_frame_reg && LAST_ENABLE) begin
// currently dropping frame
// (only for frame transfers interrupted by sink reset)
if (s_axis_tlast) begin
// end of frame, clear drop flag
drop_frame_reg <= 1'b0;
end
end else begin
// update pointers
wr_ptr_temp = wr_ptr_reg + 1;
wr_ptr_reg <= wr_ptr_temp;
wr_ptr_gray_reg <= wr_ptr_temp ^ (wr_ptr_temp >> 1);
end
end else if ((full_cur && DROP_WHEN_FULL) || (full_wr && DROP_OVERSIZE_FRAME) || drop_frame_reg) begin
// full, packet overflow, or currently dropping frame
// drop frame
@ -403,6 +440,19 @@ always @(posedge s_clk) begin
wr_ptr_update_valid_reg <= 1'b0;
wr_ptr_update_reg <= 1'b0;
end
if (s_rst) begin
wr_ptr_reg <= {ADDR_WIDTH+1{1'b0}};
wr_ptr_cur_reg <= {ADDR_WIDTH+1{1'b0}};
wr_ptr_gray_reg <= {ADDR_WIDTH+1{1'b0}};
wr_ptr_sync_gray_reg <= {ADDR_WIDTH+1{1'b0}};
wr_ptr_cur_gray_reg <= {ADDR_WIDTH+1{1'b0}};
wr_ptr_update_valid_reg <= 1'b0;
wr_ptr_update_reg <= 1'b0;
s_frame_reg <= 1'b0;
drop_frame_reg <= 1'b0;
send_frame_reg <= 1'b0;
@ -419,7 +469,7 @@ always @(posedge s_clk) begin
wr_ptr_update_ack_sync1_reg <= wr_ptr_update_sync3_reg;
wr_ptr_update_ack_sync2_reg <= wr_ptr_update_ack_sync1_reg;
if (s_rst_sync3_reg) begin
if (s_rst) begin
rd_ptr_gray_sync1_reg <= {ADDR_WIDTH+1{1'b0}};
rd_ptr_gray_sync2_reg <= {ADDR_WIDTH+1{1'b0}};
wr_ptr_update_ack_sync1_reg <= 1'b0;
@ -438,7 +488,7 @@ always @(posedge m_clk) begin
wr_ptr_update_sync2_reg <= wr_ptr_update_sync1_reg;
wr_ptr_update_sync3_reg <= wr_ptr_update_sync2_reg;
if (m_rst_sync3_reg) begin
if (m_rst) begin
wr_ptr_gray_sync1_reg <= {ADDR_WIDTH+1{1'b0}};
wr_ptr_gray_sync2_reg <= {ADDR_WIDTH+1{1'b0}};
wr_ptr_update_sync1_reg <= 1'b0;
@ -453,7 +503,7 @@ always @(posedge s_clk) begin
bad_frame_sync1_reg <= bad_frame_sync1_reg ^ bad_frame_reg;
good_frame_sync1_reg <= good_frame_sync1_reg ^ good_frame_reg;
if (s_rst_sync3_reg) begin
if (s_rst) begin
overflow_sync1_reg <= 1'b0;
bad_frame_sync1_reg <= 1'b0;
good_frame_sync1_reg <= 1'b0;
@ -471,7 +521,7 @@ always @(posedge m_clk) begin
good_frame_sync3_reg <= good_frame_sync2_reg;
good_frame_sync4_reg <= good_frame_sync3_reg;
if (m_rst_sync3_reg) begin
if (m_rst) begin
overflow_sync2_reg <= 1'b0;
overflow_sync3_reg <= 1'b0;
overflow_sync4_reg <= 1'b0;
@ -491,6 +541,7 @@ always @(posedge m_clk) begin
if (m_axis_tready) begin
// output ready; invalidate stage
m_axis_tvalid_pipe_reg[PIPELINE_OUTPUT-1] <= 1'b0;
m_terminate_frame_reg <= 1'b0;
end
for (j = PIPELINE_OUTPUT-1; j > 0; j = j - 1) begin
@ -506,7 +557,7 @@ always @(posedge m_clk) begin
// output ready or bubble in pipeline; read new data from FIFO
m_axis_tvalid_pipe_reg[0] <= 1'b0;
m_axis_pipe_reg[0] <= mem[rd_ptr_reg[ADDR_WIDTH-1:0]];
if (!empty) begin
if (!empty && !m_rst_sync3_reg && !m_drop_frame_reg) begin
// not empty, increment pointer
m_axis_tvalid_pipe_reg[0] <= 1'b1;
rd_ptr_temp = rd_ptr_reg + 1;
@ -515,10 +566,50 @@ always @(posedge m_clk) begin
end
end
if (m_axis_tvalid && LAST_ENABLE) begin
// track output frame status
if (m_axis_tlast && m_axis_tready) begin
m_frame_reg <= 1'b0;
end else begin
m_frame_reg <= 1'b1;
end
end
if (m_drop_frame_reg && (m_axis_tready || !m_axis_tvalid_pipe) && LAST_ENABLE) begin
// terminate frame
// (only for frame transfers interrupted by source reset)
m_axis_tvalid_pipe_reg[PIPELINE_OUTPUT-1] <= 1'b1;
m_terminate_frame_reg <= 1'b1;
m_drop_frame_reg <= 1'b0;
end
if (m_rst_sync3_reg && LAST_ENABLE) begin
// if source side is reset during transfer, drop partial frame
// empty output pipeline, except for last stage
if (PIPELINE_OUTPUT > 1) begin
m_axis_tvalid_pipe_reg[PIPELINE_OUTPUT-2:0] <= 0;
end
if (m_frame_reg && (!m_axis_tvalid || (m_axis_tvalid && !m_axis_tlast)) &&
!(m_drop_frame_reg || m_terminate_frame_reg)) begin
// terminate frame
m_drop_frame_reg <= 1'b1;
end
end
if (m_rst_sync3_reg) begin
rd_ptr_reg <= {ADDR_WIDTH+1{1'b0}};
rd_ptr_gray_reg <= {ADDR_WIDTH+1{1'b0}};
end
if (m_rst) begin
rd_ptr_reg <= {ADDR_WIDTH+1{1'b0}};
rd_ptr_gray_reg <= {ADDR_WIDTH+1{1'b0}};
m_axis_tvalid_pipe_reg <= {PIPELINE_OUTPUT{1'b0}};
m_frame_reg <= 1'b0;
m_drop_frame_reg <= 1'b0;
m_terminate_frame_reg <= 1'b0;
end
end

View File

@ -321,10 +321,9 @@ axis_async_fifo #(
.DROP_WHEN_FULL(DROP_WHEN_FULL)
)
fifo_inst (
// Common reset
.async_rst(s_rst | m_rst),
// AXI input
.s_clk(s_clk),
.s_rst(s_rst),
.s_axis_tdata(pre_fifo_axis_tdata),
.s_axis_tkeep(pre_fifo_axis_tkeep),
.s_axis_tvalid(pre_fifo_axis_tvalid),
@ -335,6 +334,7 @@ fifo_inst (
.s_axis_tuser(pre_fifo_axis_tuser),
// AXI output
.m_clk(m_clk),
.m_rst(m_rst),
.m_axis_tdata(post_fifo_axis_tdata),
.m_axis_tkeep(post_fifo_axis_tkeep),
.m_axis_tvalid(post_fifo_axis_tvalid),

View File

@ -83,7 +83,7 @@ module axis_pipeline_fifo #
output wire [USER_WIDTH-1:0] m_axis_tuser
);
parameter FIFO_ADDR_WIDTH = LENGTH < 2 ? 3 : $clog2(LENGTH*4);
parameter FIFO_ADDR_WIDTH = LENGTH < 2 ? 3 : $clog2(LENGTH*4+1);
generate

View File

@ -26,12 +26,12 @@ proc constrain_axis_async_fifo_inst { inst } {
# reset synchronization
set_false_path -from * -to [get_registers "$inst|s_rst_sync*_reg $inst|m_rst_sync*_reg"]
if {[get_collection_size [get_registers -nowarn "$inst|s_rst_sync2_reg"]]} {
set_max_delay -from [get_registers "$inst|s_rst_sync2_reg"] -to [get_registers "$inst|s_rst_sync3_reg"] 8.000
if {[get_collection_size [get_registers -nowarn "$inst|s_rst_sync1_reg"]]} {
set_max_delay -from [get_registers "$inst|s_rst_sync1_reg"] -to [get_registers "$inst|s_rst_sync2_reg"] 8.000
}
if {[get_collection_size [get_registers -nowarn "$inst|m_rst_sync2_reg"]]} {
set_max_delay -from [get_registers "$inst|m_rst_sync2_reg"] -to [get_registers "$inst|m_rst_sync3_reg"] 8.000
if {[get_collection_size [get_registers -nowarn "$inst|m_rst_sync1_reg"]]} {
set_max_delay -from [get_registers "$inst|m_rst_sync1_reg"] -to [get_registers "$inst|m_rst_sync2_reg"] 8.000
}
# pointer synchronization

View File

@ -26,12 +26,12 @@ proc constrain_axis_async_fifo_inst { inst } {
# reset synchronization
set_false_path -from * -to [get_registers "$inst|s_rst_sync*_reg $inst|m_rst_sync*_reg"]
if {[get_collection_size [get_registers -nowarn "$inst|s_rst_sync2_reg"]]} {
set_data_delay -from [get_registers "$inst|s_rst_sync2_reg"] -to [get_registers "$inst|s_rst_sync3_reg"] -override -get_value_from_clock_period min_clock_period -value_multiplier 0.8
if {[get_collection_size [get_registers -nowarn "$inst|s_rst_sync1_reg"]]} {
set_data_delay -from [get_registers "$inst|s_rst_sync1_reg"] -to [get_registers "$inst|s_rst_sync2_reg"] -override -get_value_from_clock_period min_clock_period -value_multiplier 0.8
}
if {[get_collection_size [get_registers -nowarn "$inst|m_rst_sync2_reg"]]} {
set_data_delay -from [get_registers "$inst|m_rst_sync2_reg"] -to [get_registers "$inst|m_rst_sync3_reg"] -override -get_value_from_clock_period min_clock_period -value_multiplier 0.8
if {[get_collection_size [get_registers -nowarn "$inst|m_rst_sync1_reg"]]} {
set_data_delay -from [get_registers "$inst|m_rst_sync1_reg"] -to [get_registers "$inst|m_rst_sync2_reg"] -override -get_value_from_clock_period min_clock_period -value_multiplier 0.8
}
# pointer synchronization

View File

@ -33,21 +33,34 @@ foreach fifo_inst [get_cells -hier -filter {(ORIG_REF_NAME == axis_async_fifo ||
set min_clk_period [expr $read_clk_period < $write_clk_period ? $read_clk_period : $write_clk_period]
# reset synchronization
set reset_ffs [get_cells -quiet -hier -regexp ".*/(s|m)_rst_sync\[123\]_reg_reg" -filter "PARENT == $fifo_inst"]
set reset_ffs [get_cells -quiet -hier -regexp ".*/s_rst_sync\[123\]_reg_reg" -filter "PARENT == $fifo_inst"]
if {[llength $reset_ffs]} {
set_property ASYNC_REG TRUE $reset_ffs
set_false_path -to [get_pins -of_objects $reset_ffs -filter {IS_PRESET || IS_RESET}]
# hunt down source
set dest [get_cells $fifo_inst/s_rst_sync2_reg_reg]
set dest_pins [get_pins -of_objects $dest -filter {REF_PIN_NAME == D}]
set net [get_nets -segments -of_objects $dest_pins]
set source_pins [get_pins -of_objects $net -filter {IS_LEAF && DIRECTION == OUT}]
set source [get_cells -of_objects $source_pins]
set_max_delay -from $source -to $dest -datapath_only $read_clk_period
}
if {[llength [get_cells -quiet $fifo_inst/s_rst_sync2_reg_reg]]} {
set_false_path -to [get_pins $fifo_inst/s_rst_sync2_reg_reg/D]
set_max_delay -from [get_cells $fifo_inst/s_rst_sync2_reg_reg] -to [get_cells $fifo_inst/s_rst_sync3_reg_reg] $min_clk_period
}
set reset_ffs [get_cells -quiet -hier -regexp ".*/m_rst_sync\[123\]_reg_reg" -filter "PARENT == $fifo_inst"]
if {[llength [get_cells -quiet $fifo_inst/m_rst_sync2_reg_reg]]} {
set_false_path -to [get_pins $fifo_inst/m_rst_sync2_reg_reg/D]
set_max_delay -from [get_cells $fifo_inst/m_rst_sync2_reg_reg] -to [get_cells $fifo_inst/m_rst_sync3_reg_reg] $min_clk_period
if {[llength $reset_ffs]} {
set_property ASYNC_REG TRUE $reset_ffs
# hunt down source
set dest [get_cells $fifo_inst/m_rst_sync2_reg_reg]
set dest_pins [get_pins -of_objects $dest -filter {REF_PIN_NAME == D}]
set net [get_nets -segments -of_objects $dest_pins]
set source_pins [get_pins -of_objects $net -filter {IS_LEAF && DIRECTION == OUT}]
set source [get_cells -of_objects $source_pins]
set_max_delay -from $source -to $dest -datapath_only $write_clk_period
}
# pointer synchronization

View File

@ -46,11 +46,14 @@ class TB(object):
self.log = logging.getLogger("cocotb.tb")
self.log.setLevel(logging.DEBUG)
cocotb.fork(Clock(dut.s_clk, 10, units="ns").start())
cocotb.fork(Clock(dut.m_clk, 11, units="ns").start())
s_clk = int(os.getenv("S_CLK", "10"))
m_clk = int(os.getenv("M_CLK", "11"))
self.source = AxiStreamSource(AxiStreamBus.from_prefix(dut, "s_axis"), dut.s_clk, dut.async_rst)
self.sink = AxiStreamSink(AxiStreamBus.from_prefix(dut, "m_axis"), dut.m_clk, dut.async_rst)
cocotb.fork(Clock(dut.s_clk, s_clk, units="ns").start())
cocotb.fork(Clock(dut.m_clk, m_clk, units="ns").start())
self.source = AxiStreamSource(AxiStreamBus.from_prefix(dut, "s_axis"), dut.s_clk, dut.s_rst)
self.sink = AxiStreamSink(AxiStreamBus.from_prefix(dut, "m_axis"), dut.m_clk, dut.m_rst)
def set_idle_generator(self, generator=None):
if generator:
@ -61,16 +64,41 @@ class TB(object):
self.sink.set_pause_generator(generator())
async def reset(self):
self.dut.async_rst.setimmediatevalue(0)
self.dut.m_rst.setimmediatevalue(0)
self.dut.s_rst.setimmediatevalue(0)
for k in range(10):
await RisingEdge(self.dut.s_clk)
self.dut.async_rst <= 1
self.dut.m_rst <= 1
self.dut.s_rst <= 1
for k in range(10):
await RisingEdge(self.dut.s_clk)
self.dut.async_rst <= 0
self.dut.m_rst <= 0
self.dut.s_rst <= 0
for k in range(10):
await RisingEdge(self.dut.s_clk)
async def reset_source(self):
self.dut.s_rst.setimmediatevalue(0)
for k in range(10):
await RisingEdge(self.dut.s_clk)
self.dut.s_rst <= 1
for k in range(10):
await RisingEdge(self.dut.s_clk)
self.dut.s_rst <= 0
for k in range(10):
await RisingEdge(self.dut.s_clk)
async def reset_sink(self):
self.dut.m_rst.setimmediatevalue(0)
for k in range(10):
await RisingEdge(self.dut.m_clk)
self.dut.m_rst <= 1
for k in range(10):
await RisingEdge(self.dut.m_clk)
self.dut.m_rst <= 0
for k in range(10):
await RisingEdge(self.dut.m_clk)
async def run_test(dut, payload_lengths=None, payload_data=None, idle_inserter=None, backpressure_inserter=None):
@ -187,7 +215,179 @@ async def run_test_init_sink_pause_reset(dut):
for k in range(64):
await RisingEdge(dut.s_clk)
assert tb.sink.empty()
assert tb.sink.idle()
await RisingEdge(dut.s_clk)
await RisingEdge(dut.s_clk)
async def run_test_init_sink_pause_source_reset(dut):
tb = TB(dut)
await tb.reset()
tb.sink.pause = True
test_data = bytearray(itertools.islice(itertools.cycle(range(256)), 32))
test_frame = AxiStreamFrame(test_data)
await tb.source.send(test_frame)
for k in range(64):
await RisingEdge(dut.s_clk)
await tb.reset_source()
tb.sink.pause = False
for k in range(64):
await RisingEdge(dut.s_clk)
rx_frame = await tb.sink.recv()
assert rx_frame.tuser
assert tb.sink.idle()
await RisingEdge(dut.s_clk)
await RisingEdge(dut.s_clk)
async def run_test_init_sink_pause_sink_reset(dut):
tb = TB(dut)
await tb.reset()
tb.sink.pause = True
test_data = bytearray(itertools.islice(itertools.cycle(range(256)), 32))
test_frame = AxiStreamFrame(test_data)
await tb.source.send(test_frame)
for k in range(64):
await RisingEdge(dut.s_clk)
await tb.reset_sink()
tb.sink.pause = False
for k in range(64):
await RisingEdge(dut.s_clk)
assert tb.sink.idle()
await RisingEdge(dut.s_clk)
await RisingEdge(dut.s_clk)
async def run_test_shift_in_source_reset(dut):
tb = TB(dut)
await tb.reset()
test_data = bytearray(itertools.islice(itertools.cycle(range(256)), 256))
test_frame = AxiStreamFrame(test_data)
await tb.source.send(test_frame)
for k in range(8):
await RisingEdge(dut.s_clk)
await tb.reset_source()
for k in range(64):
await RisingEdge(dut.s_clk)
if int(os.getenv("PARAM_FRAME_FIFO")):
assert tb.sink.empty()
else:
rx_frame = await tb.sink.recv()
assert rx_frame.tuser
assert tb.sink.empty()
assert tb.sink.idle()
await RisingEdge(dut.s_clk)
await RisingEdge(dut.s_clk)
async def run_test_shift_in_sink_reset(dut):
tb = TB(dut)
await tb.reset()
test_data = bytearray(itertools.islice(itertools.cycle(range(256)), 256))
test_frame = AxiStreamFrame(test_data)
await tb.source.send(test_frame)
for k in range(8):
await RisingEdge(dut.s_clk)
await tb.reset_sink()
for k in range(64):
await RisingEdge(dut.s_clk)
assert tb.sink.idle()
await RisingEdge(dut.s_clk)
await RisingEdge(dut.s_clk)
async def run_test_shift_out_source_reset(dut):
tb = TB(dut)
await tb.reset()
test_data = bytearray(itertools.islice(itertools.cycle(range(256)), 256))
test_frame = AxiStreamFrame(test_data)
await tb.source.send(test_frame)
await RisingEdge(dut.m_axis_tvalid)
for k in range(8):
await RisingEdge(dut.s_clk)
await tb.reset_source()
for k in range(64):
await RisingEdge(dut.s_clk)
rx_frame = await tb.sink.recv()
assert rx_frame.tuser
assert tb.sink.idle()
await RisingEdge(dut.s_clk)
await RisingEdge(dut.s_clk)
async def run_test_shift_out_sink_reset(dut):
tb = TB(dut)
await tb.reset()
test_data = bytearray(itertools.islice(itertools.cycle(range(256)), 256))
test_frame = AxiStreamFrame(test_data)
await tb.source.send(test_frame)
await RisingEdge(dut.m_axis_tvalid)
for k in range(8):
await RisingEdge(dut.s_clk)
await tb.reset_sink()
for k in range(64):
await RisingEdge(dut.s_clk)
assert tb.sink.idle()
await RisingEdge(dut.s_clk)
await RisingEdge(dut.s_clk)
@ -291,7 +491,19 @@ if cocotb.SIM_NAME:
factory.add_option("backpressure_inserter", [None, cycle_pause])
factory.generate_tests()
for test in [run_test_tuser_assert, run_test_init_sink_pause, run_test_init_sink_pause_reset, run_test_overflow]:
for test in [
run_test_tuser_assert,
run_test_init_sink_pause,
run_test_init_sink_pause_reset,
run_test_init_sink_pause_source_reset,
run_test_init_sink_pause_sink_reset,
run_test_shift_in_source_reset,
run_test_shift_in_sink_reset,
run_test_shift_out_source_reset,
run_test_shift_out_sink_reset,
run_test_overflow
]:
factory = TestFactory(test)
factory.generate_tests()
@ -307,10 +519,13 @@ tests_dir = os.path.dirname(__file__)
rtl_dir = os.path.abspath(os.path.join(tests_dir, '..', '..', 'rtl'))
@pytest.mark.parametrize(("s_clk", "m_clk"), [(10, 10), (10, 11), (11, 10)])
@pytest.mark.parametrize(("frame_fifo", "drop_oversize_frame", "drop_bad_frame", "drop_when_full"),
[(0, 0, 0, 0), (1, 0, 0, 0), (1, 1, 0, 0), (1, 1, 1, 0)])
@pytest.mark.parametrize("data_width", [8, 16, 32, 64])
def test_axis_async_fifo(request, data_width, frame_fifo, drop_oversize_frame, drop_bad_frame, drop_when_full):
def test_axis_async_fifo(request, data_width, frame_fifo, drop_oversize_frame, drop_bad_frame,
drop_when_full, s_clk, m_clk):
dut = "axis_async_fifo"
module = os.path.splitext(os.path.basename(__file__))[0]
toplevel = dut
@ -342,6 +557,9 @@ def test_axis_async_fifo(request, data_width, frame_fifo, drop_oversize_frame, d
extra_env = {f'PARAM_{k}': str(v) for k, v in parameters.items()}
extra_env['S_CLK'] = str(s_clk)
extra_env['M_CLK'] = str(m_clk)
sim_build = os.path.join(tests_dir, "sim_build",
request.node.name.replace('[', '-').replace(']', ''))

View File

@ -74,6 +74,28 @@ class TB(object):
for k in range(10):
await RisingEdge(self.dut.s_clk)
async def reset_source(self):
self.dut.s_rst.setimmediatevalue(0)
for k in range(10):
await RisingEdge(self.dut.s_clk)
self.dut.s_rst <= 1
for k in range(10):
await RisingEdge(self.dut.s_clk)
self.dut.s_rst <= 0
for k in range(10):
await RisingEdge(self.dut.s_clk)
async def reset_sink(self):
self.dut.m_rst.setimmediatevalue(0)
for k in range(10):
await RisingEdge(self.dut.m_clk)
self.dut.m_rst <= 1
for k in range(10):
await RisingEdge(self.dut.m_clk)
self.dut.m_rst <= 0
for k in range(10):
await RisingEdge(self.dut.m_clk)
async def run_test(dut, payload_lengths=None, payload_data=None, idle_inserter=None, backpressure_inserter=None):
@ -190,7 +212,179 @@ async def run_test_init_sink_pause_reset(dut):
for k in range(64):
await RisingEdge(dut.s_clk)
assert tb.sink.empty()
assert tb.sink.idle()
await RisingEdge(dut.s_clk)
await RisingEdge(dut.s_clk)
async def run_test_init_sink_pause_source_reset(dut):
tb = TB(dut)
await tb.reset()
tb.sink.pause = True
test_data = bytearray(itertools.islice(itertools.cycle(range(256)), 32))
test_frame = AxiStreamFrame(test_data)
await tb.source.send(test_frame)
for k in range(64):
await RisingEdge(dut.s_clk)
await tb.reset_source()
tb.sink.pause = False
for k in range(64):
await RisingEdge(dut.s_clk)
rx_frame = await tb.sink.recv()
assert rx_frame.tuser
assert tb.sink.idle()
await RisingEdge(dut.s_clk)
await RisingEdge(dut.s_clk)
async def run_test_init_sink_pause_sink_reset(dut):
tb = TB(dut)
await tb.reset()
tb.sink.pause = True
test_data = bytearray(itertools.islice(itertools.cycle(range(256)), 32))
test_frame = AxiStreamFrame(test_data)
await tb.source.send(test_frame)
for k in range(64):
await RisingEdge(dut.s_clk)
await tb.reset_sink()
tb.sink.pause = False
for k in range(64):
await RisingEdge(dut.s_clk)
assert tb.sink.idle()
await RisingEdge(dut.s_clk)
await RisingEdge(dut.s_clk)
async def run_test_shift_in_source_reset(dut):
tb = TB(dut)
await tb.reset()
test_data = bytearray(itertools.islice(itertools.cycle(range(256)), 256))
test_frame = AxiStreamFrame(test_data)
await tb.source.send(test_frame)
for k in range(8):
await RisingEdge(dut.s_clk)
await tb.reset_source()
for k in range(64):
await RisingEdge(dut.s_clk)
if int(os.getenv("PARAM_FRAME_FIFO")):
assert tb.sink.empty()
else:
rx_frame = await tb.sink.recv()
assert rx_frame.tuser
assert tb.sink.empty()
assert tb.sink.idle()
await RisingEdge(dut.s_clk)
await RisingEdge(dut.s_clk)
async def run_test_shift_in_sink_reset(dut):
tb = TB(dut)
await tb.reset()
test_data = bytearray(itertools.islice(itertools.cycle(range(256)), 256))
test_frame = AxiStreamFrame(test_data)
await tb.source.send(test_frame)
for k in range(8):
await RisingEdge(dut.s_clk)
await tb.reset_sink()
for k in range(64):
await RisingEdge(dut.s_clk)
assert tb.sink.idle()
await RisingEdge(dut.s_clk)
await RisingEdge(dut.s_clk)
async def run_test_shift_out_source_reset(dut):
tb = TB(dut)
await tb.reset()
test_data = bytearray(itertools.islice(itertools.cycle(range(256)), 256))
test_frame = AxiStreamFrame(test_data)
await tb.source.send(test_frame)
await RisingEdge(dut.m_axis_tvalid)
for k in range(8):
await RisingEdge(dut.s_clk)
await tb.reset_source()
for k in range(64):
await RisingEdge(dut.s_clk)
rx_frame = await tb.sink.recv()
assert rx_frame.tuser
assert tb.sink.idle()
await RisingEdge(dut.s_clk)
await RisingEdge(dut.s_clk)
async def run_test_shift_out_sink_reset(dut):
tb = TB(dut)
await tb.reset()
test_data = bytearray(itertools.islice(itertools.cycle(range(256)), 256))
test_frame = AxiStreamFrame(test_data)
await tb.source.send(test_frame)
await RisingEdge(dut.m_axis_tvalid)
for k in range(8):
await RisingEdge(dut.s_clk)
await tb.reset_sink()
for k in range(64):
await RisingEdge(dut.s_clk)
assert tb.sink.idle()
await RisingEdge(dut.s_clk)
await RisingEdge(dut.s_clk)
@ -294,7 +488,19 @@ if cocotb.SIM_NAME:
factory.add_option("backpressure_inserter", [None, cycle_pause])
factory.generate_tests()
for test in [run_test_tuser_assert, run_test_init_sink_pause, run_test_init_sink_pause_reset, run_test_overflow]:
for test in [
run_test_tuser_assert,
run_test_init_sink_pause,
run_test_init_sink_pause_reset,
run_test_init_sink_pause_source_reset,
run_test_init_sink_pause_sink_reset,
run_test_shift_in_source_reset,
run_test_shift_in_sink_reset,
run_test_shift_out_source_reset,
run_test_shift_out_sink_reset,
run_test_overflow
]:
factory = TestFactory(test)
factory.generate_tests()

View File

@ -290,7 +290,13 @@ if cocotb.SIM_NAME:
factory.add_option("backpressure_inserter", [None, cycle_pause])
factory.generate_tests()
for test in [run_test_tuser_assert, run_test_init_sink_pause, run_test_init_sink_pause_reset, run_test_overflow]:
for test in [
run_test_tuser_assert,
run_test_init_sink_pause,
run_test_init_sink_pause_reset,
run_test_overflow
]:
factory = TestFactory(test)
factory.generate_tests()

View File

@ -290,7 +290,13 @@ if cocotb.SIM_NAME:
factory.add_option("backpressure_inserter", [None, cycle_pause])
factory.generate_tests()
for test in [run_test_tuser_assert, run_test_init_sink_pause, run_test_init_sink_pause_reset, run_test_overflow]:
for test in [
run_test_tuser_assert,
run_test_init_sink_pause,
run_test_init_sink_pause_reset,
run_test_overflow
]:
factory = TestFactory(test)
factory.generate_tests()

View File

@ -273,7 +273,13 @@ if cocotb.SIM_NAME:
factory.add_option("backpressure_inserter", [None, cycle_pause])
factory.generate_tests()
for test in [run_test_tuser_assert, run_test_init_sink_pause, run_test_init_sink_pause_reset, run_test_overflow]:
for test in [
run_test_tuser_assert,
run_test_init_sink_pause,
run_test_init_sink_pause_reset,
run_test_overflow
]:
factory = TestFactory(test)
factory.generate_tests()

View File

@ -131,6 +131,90 @@ async def run_test_tuser_assert(dut):
await RisingEdge(dut.clk)
async def run_test_init_sink_pause(dut):
tb = TB(dut)
await tb.reset()
tb.sink.pause = True
test_data = bytearray(itertools.islice(itertools.cycle(range(256)), 32))
test_frame = AxiStreamFrame(test_data)
await tb.source.send(test_frame)
for k in range(64):
await RisingEdge(dut.clk)
tb.sink.pause = False
rx_frame = await tb.sink.recv()
assert rx_frame.tdata == test_data
assert not rx_frame.tuser
assert tb.sink.empty()
await RisingEdge(dut.clk)
await RisingEdge(dut.clk)
async def run_test_init_sink_pause_reset(dut):
tb = TB(dut)
await tb.reset()
tb.sink.pause = True
test_data = bytearray(itertools.islice(itertools.cycle(range(256)), 32))
test_frame = AxiStreamFrame(test_data)
await tb.source.send(test_frame)
for k in range(64):
await RisingEdge(dut.clk)
await tb.reset()
tb.sink.pause = False
for k in range(64):
await RisingEdge(dut.clk)
assert tb.sink.empty()
await RisingEdge(dut.clk)
await RisingEdge(dut.clk)
async def run_test_overflow(dut):
tb = TB(dut)
await tb.reset()
tb.sink.pause = True
test_data = bytearray(itertools.islice(itertools.cycle(range(256)), 2048))
test_frame = AxiStreamFrame(test_data)
await tb.source.send(test_frame)
for k in range(2048):
await RisingEdge(dut.clk)
tb.sink.pause = False
rx_frame = await tb.sink.recv()
assert rx_frame.tdata == test_data
assert not rx_frame.tuser
assert tb.sink.empty()
await RisingEdge(dut.clk)
await RisingEdge(dut.clk)
async def run_stress_test(dut, idle_inserter=None, backpressure_inserter=None):
tb = TB(dut)
@ -196,7 +280,13 @@ if cocotb.SIM_NAME:
factory.add_option("backpressure_inserter", [None, cycle_pause])
factory.generate_tests()
for test in [run_test_tuser_assert]:
for test in [
run_test_tuser_assert,
run_test_init_sink_pause,
run_test_init_sink_pause_reset,
run_test_overflow
]:
factory = TestFactory(test)
factory.generate_tests()

View File

@ -280,7 +280,13 @@ if cocotb.SIM_NAME:
factory.add_option("backpressure_inserter", [None, cycle_pause])
factory.generate_tests()
for test in [run_test_tuser_assert, run_test_init_sink_pause, run_test_init_sink_pause_reset, run_test_overflow]:
for test in [
run_test_tuser_assert,
run_test_init_sink_pause,
run_test_init_sink_pause_reset,
run_test_overflow
]:
factory = TestFactory(test)
factory.generate_tests()

View File

@ -45,7 +45,7 @@ module eth_mac_10g #
parameter TX_PTP_TAG_WIDTH = 16,
parameter RX_PTP_TS_ENABLE = 0,
parameter RX_PTP_TS_WIDTH = 96,
parameter TX_USER_WIDTH = (TX_PTP_TAG_ENABLE ? TX_PTP_TAG_WIDTH : 0) + 1,
parameter TX_USER_WIDTH = (TX_PTP_TS_ENABLE && TX_PTP_TAG_ENABLE ? TX_PTP_TAG_WIDTH : 0) + 1,
parameter RX_USER_WIDTH = (RX_PTP_TS_ENABLE ? RX_PTP_TS_WIDTH : 0) + 1
)
(

View File

@ -57,10 +57,11 @@ module eth_mac_10g_fifo #
parameter TX_PTP_TS_ENABLE = 0,
parameter RX_PTP_TS_ENABLE = 0,
parameter TX_PTP_TS_FIFO_DEPTH = 64,
parameter RX_PTP_TS_FIFO_DEPTH = 64,
parameter PTP_TS_WIDTH = 96,
parameter TX_PTP_TAG_ENABLE = 0,
parameter PTP_TAG_WIDTH = 16
parameter PTP_TAG_WIDTH = 16,
parameter TX_USER_WIDTH = (TX_PTP_TS_ENABLE && TX_PTP_TAG_ENABLE ? PTP_TAG_WIDTH : 0) + 1,
parameter RX_USER_WIDTH = (RX_PTP_TS_ENABLE ? PTP_TS_WIDTH : 0) + 1
)
(
input wire rx_clk,
@ -79,14 +80,7 @@ module eth_mac_10g_fifo #
input wire tx_axis_tvalid,
output wire tx_axis_tready,
input wire tx_axis_tlast,
input wire tx_axis_tuser,
/*
* Transmit timestamp tag input
*/
input wire [PTP_TAG_WIDTH-1:0] s_axis_tx_ptp_ts_tag,
input wire s_axis_tx_ptp_ts_valid,
output wire s_axis_tx_ptp_ts_ready,
input wire [TX_USER_WIDTH-1:0] tx_axis_tuser,
/*
* Transmit timestamp output
@ -104,14 +98,7 @@ module eth_mac_10g_fifo #
output wire rx_axis_tvalid,
input wire rx_axis_tready,
output wire rx_axis_tlast,
output wire rx_axis_tuser,
/*
* Receive timestamp output
*/
output wire [PTP_TS_WIDTH-1:0] m_axis_rx_ptp_ts_96,
output wire m_axis_rx_ptp_ts_valid,
input wire m_axis_rx_ptp_ts_ready,
output wire [RX_USER_WIDTH-1:0] rx_axis_tuser,
/*
* XGMII interface
@ -148,9 +135,6 @@ module eth_mac_10g_fifo #
parameter KEEP_WIDTH = DATA_WIDTH/8;
localparam TX_USER_WIDTH = (TX_PTP_TS_ENABLE && TX_PTP_TAG_ENABLE ? PTP_TAG_WIDTH : 0) + 1;
localparam RX_USER_WIDTH = (RX_PTP_TS_ENABLE ? PTP_TS_WIDTH : 0) + 1;
wire [DATA_WIDTH-1:0] tx_fifo_axis_tdata;
wire [KEEP_WIDTH-1:0] tx_fifo_axis_tkeep;
wire tx_fifo_axis_tvalid;
@ -158,21 +142,12 @@ wire tx_fifo_axis_tready;
wire tx_fifo_axis_tlast;
wire [TX_USER_WIDTH-1:0] tx_fifo_axis_tuser;
wire [AXIS_DATA_WIDTH-1:0] tx_axis_tdata_int;
wire [AXIS_KEEP_WIDTH-1:0] tx_axis_tkeep_int;
wire tx_axis_tvalid_int;
wire tx_axis_tready_int;
wire tx_axis_tlast_int;
wire [TX_USER_WIDTH-1:0] tx_axis_tuser_int;
wire [DATA_WIDTH-1:0] rx_fifo_axis_tdata;
wire [KEEP_WIDTH-1:0] rx_fifo_axis_tkeep;
wire rx_fifo_axis_tvalid;
wire rx_fifo_axis_tlast;
wire [RX_USER_WIDTH-1:0] rx_fifo_axis_tuser;
wire [RX_USER_WIDTH-1:0] rx_axis_tuser_int;
wire [PTP_TS_WIDTH-1:0] tx_ptp_ts_96;
wire [PTP_TS_WIDTH-1:0] rx_ptp_ts_96;
@ -180,9 +155,6 @@ wire [PTP_TS_WIDTH-1:0] tx_axis_ptp_ts_96;
wire [PTP_TAG_WIDTH-1:0] tx_axis_ptp_ts_tag;
wire tx_axis_ptp_ts_valid;
wire [PTP_TS_WIDTH-1:0] rx_axis_ptp_ts_96;
wire rx_axis_ptp_ts_valid;
// synchronize MAC status signals into logic clock domain
wire tx_error_underflow_int;
@ -269,146 +241,52 @@ if (TX_PTP_TS_ENABLE) begin
.locked()
);
if (TX_PTP_TAG_ENABLE) begin
axis_async_fifo #(
.DEPTH(TX_PTP_TS_FIFO_DEPTH),
.DATA_WIDTH(PTP_TS_WIDTH),
.KEEP_ENABLE(0),
.LAST_ENABLE(0),
.ID_ENABLE(TX_PTP_TAG_ENABLE),
.ID_WIDTH(PTP_TAG_WIDTH),
.DEST_ENABLE(0),
.USER_ENABLE(0),
.FRAME_FIFO(0)
)
tx_ptp_ts_fifo (
.async_rst(logic_rst | tx_rst),
ptp_tag_insert #(
.DATA_WIDTH(AXIS_DATA_WIDTH),
.KEEP_WIDTH(AXIS_KEEP_WIDTH),
.TAG_WIDTH(PTP_TAG_WIDTH),
.TAG_OFFSET(1),
.USER_WIDTH(TX_USER_WIDTH)
)
tx_ptp_tag_insert (
.clk(logic_clk),
.rst(logic_rst),
// AXI input
.s_clk(tx_clk),
.s_axis_tdata(tx_axis_ptp_ts_96),
.s_axis_tkeep(0),
.s_axis_tvalid(tx_axis_ptp_ts_valid),
.s_axis_tready(),
.s_axis_tlast(0),
.s_axis_tid(tx_axis_ptp_ts_tag),
.s_axis_tdest(0),
.s_axis_tuser(0),
// AXI stream input
.s_axis_tdata(tx_axis_tdata),
.s_axis_tkeep(tx_axis_tkeep),
.s_axis_tvalid(tx_axis_tvalid),
.s_axis_tready(tx_axis_tready),
.s_axis_tlast(tx_axis_tlast),
.s_axis_tuser(tx_axis_tuser),
// AXI output
.m_clk(logic_clk),
.m_axis_tdata(m_axis_tx_ptp_ts_96),
.m_axis_tkeep(),
.m_axis_tvalid(m_axis_tx_ptp_ts_valid),
.m_axis_tready(m_axis_tx_ptp_ts_ready),
.m_axis_tlast(),
.m_axis_tid(m_axis_tx_ptp_ts_tag),
.m_axis_tdest(),
.m_axis_tuser(),
// AXI stream input
.m_axis_tdata(tx_axis_tdata_int),
.m_axis_tkeep(tx_axis_tkeep_int),
.m_axis_tvalid(tx_axis_tvalid_int),
.m_axis_tready(tx_axis_tready_int),
.m_axis_tlast(tx_axis_tlast_int),
.m_axis_tuser(tx_axis_tuser_int),
// Tag input
.s_axis_tag(s_axis_tx_ptp_ts_tag),
.s_axis_tag_valid(s_axis_tx_ptp_ts_valid),
.s_axis_tag_ready(s_axis_tx_ptp_ts_ready)
);
axis_async_fifo #(
.DEPTH(TX_PTP_TS_FIFO_DEPTH),
.DATA_WIDTH(PTP_TAG_WIDTH+PTP_TS_WIDTH),
.KEEP_ENABLE(0),
.LAST_ENABLE(0),
.ID_ENABLE(0),
.DEST_ENABLE(0),
.USER_ENABLE(0),
.FRAME_FIFO(0)
)
tx_ptp_ts_fifo (
.async_rst(logic_rst | tx_rst),
// AXI input
.s_clk(tx_clk),
.s_axis_tdata({tx_axis_ptp_ts_tag, tx_axis_ptp_ts_96}),
.s_axis_tkeep(0),
.s_axis_tvalid(tx_axis_ptp_ts_valid),
.s_axis_tready(),
.s_axis_tlast(0),
.s_axis_tid(0),
.s_axis_tdest(0),
.s_axis_tuser(0),
// AXI output
.m_clk(logic_clk),
.m_axis_tdata({m_axis_tx_ptp_ts_tag, m_axis_tx_ptp_ts_96}),
.m_axis_tkeep(),
.m_axis_tvalid(m_axis_tx_ptp_ts_valid),
.m_axis_tready(m_axis_tx_ptp_ts_ready),
.m_axis_tlast(),
.m_axis_tid(),
.m_axis_tdest(),
.m_axis_tuser(),
// Status
.s_status_overflow(),
.s_status_bad_frame(),
.s_status_good_frame(),
.m_status_overflow(),
.m_status_bad_frame(),
.m_status_good_frame()
);
end else begin
assign tx_axis_tdata_int = tx_axis_tdata;
assign tx_axis_tkeep_int = tx_axis_tkeep;
assign tx_axis_tvalid_int = tx_axis_tvalid;
assign tx_axis_tready = tx_axis_tready_int;
assign tx_axis_tlast_int = tx_axis_tlast;
assign tx_axis_tuser_int = tx_axis_tuser;
axis_async_fifo #(
.DEPTH(TX_PTP_TS_FIFO_DEPTH),
.DATA_WIDTH(PTP_TS_WIDTH),
.KEEP_ENABLE(0),
.LAST_ENABLE(0),
.ID_ENABLE(0),
.DEST_ENABLE(0),
.USER_ENABLE(0),
.FRAME_FIFO(0)
)
tx_ptp_ts_fifo (
.async_rst(logic_rst | tx_rst),
// AXI input
.s_clk(tx_clk),
.s_axis_tdata(tx_axis_ptp_ts_96),
.s_axis_tkeep(0),
.s_axis_tvalid(tx_axis_ptp_ts_valid),
.s_axis_tready(),
.s_axis_tlast(0),
.s_axis_tid(0),
.s_axis_tdest(0),
.s_axis_tuser(0),
// AXI output
.m_clk(logic_clk),
.m_axis_tdata(m_axis_tx_ptp_ts_96),
.m_axis_tkeep(),
.m_axis_tvalid(m_axis_tx_ptp_ts_valid),
.m_axis_tready(m_axis_tx_ptp_ts_ready),
.m_axis_tlast(),
.m_axis_tid(),
.m_axis_tdest(),
.m_axis_tuser(),
// Status
.s_status_overflow(),
.s_status_bad_frame(),
.s_status_good_frame(),
.m_status_overflow(),
.m_status_bad_frame(),
.m_status_good_frame()
);
assign s_axis_tx_ptp_ts_ready = 1'b0;
assign m_axis_tx_ptp_ts_tag = {PTP_TAG_WIDTH{1'b0}};
end
// Status
.s_status_overflow(),
.s_status_bad_frame(),
.s_status_good_frame(),
.m_status_overflow(),
.m_status_bad_frame(),
.m_status_good_frame()
);
end else begin
assign s_axis_tx_ptp_ts_ready = 1'b0;
assign m_axis_tx_ptp_ts_96 = {PTP_TS_WIDTH{1'b0}};
assign m_axis_tx_ptp_ts_tag = {PTP_TAG_WIDTH{1'b0}};
@ -416,13 +294,6 @@ end else begin
assign tx_ptp_ts_96 = {PTP_TS_WIDTH{1'b0}};
assign tx_axis_tdata_int = tx_axis_tdata;
assign tx_axis_tkeep_int = tx_axis_tkeep;
assign tx_axis_tvalid_int = tx_axis_tvalid;
assign tx_axis_tready = tx_axis_tready_int;
assign tx_axis_tlast_int = tx_axis_tlast;
assign tx_axis_tuser_int = tx_axis_tuser;
end
if (RX_PTP_TS_ENABLE) begin
@ -447,76 +318,12 @@ if (RX_PTP_TS_ENABLE) begin
.locked()
);
axis_fifo #(
.DEPTH(RX_PTP_TS_FIFO_DEPTH),
.DATA_WIDTH(PTP_TS_WIDTH),
.KEEP_ENABLE(0),
.LAST_ENABLE(0),
.ID_ENABLE(0),
.DEST_ENABLE(0),
.USER_ENABLE(0),
.FRAME_FIFO(0)
)
rx_ptp_ts_fifo (
.clk(logic_clk),
.rst(logic_rst),
// AXI input
.s_axis_tdata(rx_axis_ptp_ts_96),
.s_axis_tkeep(0),
.s_axis_tvalid(rx_axis_ptp_ts_valid),
.s_axis_tready(),
.s_axis_tlast(0),
.s_axis_tid(0),
.s_axis_tdest(0),
.s_axis_tuser(0),
// AXI output
.m_axis_tdata(m_axis_rx_ptp_ts_96),
.m_axis_tkeep(),
.m_axis_tvalid(m_axis_rx_ptp_ts_valid),
.m_axis_tready(m_axis_rx_ptp_ts_ready),
.m_axis_tlast(),
.m_axis_tid(),
.m_axis_tdest(),
.m_axis_tuser(),
// Status
.status_overflow(),
.status_bad_frame(),
.status_good_frame()
);
ptp_ts_extract #(
.TS_WIDTH(PTP_TS_WIDTH),
.TS_OFFSET(1),
.USER_WIDTH(RX_USER_WIDTH)
)
rx_ptp_ts_extract (
.clk(logic_clk),
.rst(logic_rst),
// AXI stream input
.s_axis_tvalid(rx_axis_tvalid && rx_axis_tready),
.s_axis_tlast(rx_axis_tlast),
.s_axis_tuser(rx_axis_tuser_int),
// Timestamp output
.m_axis_ts(rx_axis_ptp_ts_96),
.m_axis_ts_valid(rx_axis_ptp_ts_valid)
);
end else begin
assign m_axis_rx_ptp_ts_96 = {PTP_TS_WIDTH{1'b0}};
assign m_axis_rx_ptp_ts_valid = 1'b0;
assign rx_ptp_ts_96 = {PTP_TS_WIDTH{1'b0}};
end
assign rx_axis_tuser = rx_axis_tuser_int[0];
endgenerate
eth_mac_10g #(
@ -585,8 +392,8 @@ axis_async_fifo_adapter #(
.ID_ENABLE(0),
.DEST_ENABLE(0),
.USER_ENABLE(1),
.PIPELINE_OUTPUT(TX_FIFO_PIPELINE_OUTPUT),
.USER_WIDTH(TX_USER_WIDTH),
.PIPELINE_OUTPUT(TX_FIFO_PIPELINE_OUTPUT),
.FRAME_FIFO(TX_FRAME_FIFO),
.USER_BAD_FRAME_VALUE(1'b1),
.USER_BAD_FRAME_MASK(1'b1),
@ -598,14 +405,14 @@ tx_fifo (
// AXI input
.s_clk(logic_clk),
.s_rst(logic_rst),
.s_axis_tdata(tx_axis_tdata_int),
.s_axis_tkeep(tx_axis_tkeep_int),
.s_axis_tvalid(tx_axis_tvalid_int),
.s_axis_tready(tx_axis_tready_int),
.s_axis_tlast(tx_axis_tlast_int),
.s_axis_tdata(tx_axis_tdata),
.s_axis_tkeep(tx_axis_tkeep),
.s_axis_tvalid(tx_axis_tvalid),
.s_axis_tready(tx_axis_tready),
.s_axis_tlast(tx_axis_tlast),
.s_axis_tid(0),
.s_axis_tdest(0),
.s_axis_tuser(tx_axis_tuser_int),
.s_axis_tuser(tx_axis_tuser),
// AXI output
.m_clk(tx_clk),
.m_rst(tx_rst),
@ -637,8 +444,8 @@ axis_async_fifo_adapter #(
.ID_ENABLE(0),
.DEST_ENABLE(0),
.USER_ENABLE(1),
.PIPELINE_OUTPUT(RX_FIFO_PIPELINE_OUTPUT),
.USER_WIDTH(RX_USER_WIDTH),
.PIPELINE_OUTPUT(RX_FIFO_PIPELINE_OUTPUT),
.FRAME_FIFO(RX_FRAME_FIFO),
.USER_BAD_FRAME_VALUE(1'b1),
.USER_BAD_FRAME_MASK(1'b1),
@ -668,7 +475,7 @@ rx_fifo (
.m_axis_tlast(rx_axis_tlast),
.m_axis_tid(),
.m_axis_tdest(),
.m_axis_tuser(rx_axis_tuser_int),
.m_axis_tuser(rx_axis_tuser),
// Status
.s_status_overflow(),
.s_status_bad_frame(),

View File

@ -65,10 +65,11 @@ module eth_mac_phy_10g_fifo #
parameter TX_PTP_TS_ENABLE = 0,
parameter RX_PTP_TS_ENABLE = 0,
parameter TX_PTP_TS_FIFO_DEPTH = 64,
parameter RX_PTP_TS_FIFO_DEPTH = 64,
parameter PTP_TS_WIDTH = 96,
parameter TX_PTP_TAG_ENABLE = 0,
parameter PTP_TAG_WIDTH = 16
parameter PTP_TAG_WIDTH = 16,
parameter TX_USER_WIDTH = (TX_PTP_TS_ENABLE && TX_PTP_TAG_ENABLE ? PTP_TAG_WIDTH : 0) + 1,
parameter RX_USER_WIDTH = (RX_PTP_TS_ENABLE ? PTP_TS_WIDTH : 0) + 1
)
(
input wire rx_clk,
@ -87,14 +88,7 @@ module eth_mac_phy_10g_fifo #
input wire tx_axis_tvalid,
output wire tx_axis_tready,
input wire tx_axis_tlast,
input wire tx_axis_tuser,
/*
* Transmit timestamp tag input
*/
input wire [PTP_TAG_WIDTH-1:0] s_axis_tx_ptp_ts_tag,
input wire s_axis_tx_ptp_ts_valid,
output wire s_axis_tx_ptp_ts_ready,
input wire [TX_USER_WIDTH-1:0] tx_axis_tuser,
/*
* Transmit timestamp output
@ -112,14 +106,7 @@ module eth_mac_phy_10g_fifo #
output wire rx_axis_tvalid,
input wire rx_axis_tready,
output wire rx_axis_tlast,
output wire rx_axis_tuser,
/*
* Receive timestamp output
*/
output wire [PTP_TS_WIDTH-1:0] m_axis_rx_ptp_ts_96,
output wire m_axis_rx_ptp_ts_valid,
input wire m_axis_rx_ptp_ts_ready,
output wire [RX_USER_WIDTH-1:0] rx_axis_tuser,
/*
* SERDES interface
@ -162,9 +149,6 @@ module eth_mac_phy_10g_fifo #
parameter KEEP_WIDTH = DATA_WIDTH/8;
localparam TX_USER_WIDTH = (TX_PTP_TS_ENABLE && TX_PTP_TAG_ENABLE ? PTP_TAG_WIDTH : 0) + 1;
localparam RX_USER_WIDTH = (RX_PTP_TS_ENABLE ? PTP_TS_WIDTH : 0) + 1;
wire [DATA_WIDTH-1:0] tx_fifo_axis_tdata;
wire [KEEP_WIDTH-1:0] tx_fifo_axis_tkeep;
wire tx_fifo_axis_tvalid;
@ -172,21 +156,12 @@ wire tx_fifo_axis_tready;
wire tx_fifo_axis_tlast;
wire [TX_USER_WIDTH-1:0] tx_fifo_axis_tuser;
wire [AXIS_DATA_WIDTH-1:0] tx_axis_tdata_int;
wire [AXIS_KEEP_WIDTH-1:0] tx_axis_tkeep_int;
wire tx_axis_tvalid_int;
wire tx_axis_tready_int;
wire tx_axis_tlast_int;
wire [TX_USER_WIDTH-1:0] tx_axis_tuser_int;
wire [DATA_WIDTH-1:0] rx_fifo_axis_tdata;
wire [KEEP_WIDTH-1:0] rx_fifo_axis_tkeep;
wire rx_fifo_axis_tvalid;
wire rx_fifo_axis_tlast;
wire [RX_USER_WIDTH-1:0] rx_fifo_axis_tuser;
wire [RX_USER_WIDTH-1:0] rx_axis_tuser_int;
wire [PTP_TS_WIDTH-1:0] tx_ptp_ts_96;
wire [PTP_TS_WIDTH-1:0] rx_ptp_ts_96;
@ -194,9 +169,6 @@ wire [PTP_TS_WIDTH-1:0] tx_axis_ptp_ts_96;
wire [PTP_TAG_WIDTH-1:0] tx_axis_ptp_ts_tag;
wire tx_axis_ptp_ts_valid;
wire [PTP_TS_WIDTH-1:0] rx_axis_ptp_ts_96;
wire rx_axis_ptp_ts_valid;
// synchronize MAC status signals into logic clock domain
wire tx_error_underflow_int;
@ -286,146 +258,52 @@ if (TX_PTP_TS_ENABLE) begin
.locked()
);
if (TX_PTP_TAG_ENABLE) begin
axis_async_fifo #(
.DEPTH(TX_PTP_TS_FIFO_DEPTH),
.DATA_WIDTH(PTP_TS_WIDTH),
.KEEP_ENABLE(0),
.LAST_ENABLE(0),
.ID_ENABLE(TX_PTP_TAG_ENABLE),
.ID_WIDTH(PTP_TAG_WIDTH),
.DEST_ENABLE(0),
.USER_ENABLE(0),
.FRAME_FIFO(0)
)
tx_ptp_ts_fifo (
.async_rst(logic_rst | tx_rst),
ptp_tag_insert #(
.DATA_WIDTH(AXIS_DATA_WIDTH),
.KEEP_WIDTH(AXIS_KEEP_WIDTH),
.TAG_WIDTH(PTP_TAG_WIDTH),
.TAG_OFFSET(1),
.USER_WIDTH(TX_USER_WIDTH)
)
tx_ptp_tag_insert (
.clk(logic_clk),
.rst(logic_rst),
// AXI input
.s_clk(tx_clk),
.s_axis_tdata(tx_axis_ptp_ts_96),
.s_axis_tkeep(0),
.s_axis_tvalid(tx_axis_ptp_ts_valid),
.s_axis_tready(),
.s_axis_tlast(0),
.s_axis_tid(tx_axis_ptp_ts_tag),
.s_axis_tdest(0),
.s_axis_tuser(0),
// AXI stream input
.s_axis_tdata(tx_axis_tdata),
.s_axis_tkeep(tx_axis_tkeep),
.s_axis_tvalid(tx_axis_tvalid),
.s_axis_tready(tx_axis_tready),
.s_axis_tlast(tx_axis_tlast),
.s_axis_tuser(tx_axis_tuser),
// AXI output
.m_clk(logic_clk),
.m_axis_tdata(m_axis_tx_ptp_ts_96),
.m_axis_tkeep(),
.m_axis_tvalid(m_axis_tx_ptp_ts_valid),
.m_axis_tready(m_axis_tx_ptp_ts_ready),
.m_axis_tlast(),
.m_axis_tid(m_axis_tx_ptp_ts_tag),
.m_axis_tdest(),
.m_axis_tuser(),
// AXI stream input
.m_axis_tdata(tx_axis_tdata_int),
.m_axis_tkeep(tx_axis_tkeep_int),
.m_axis_tvalid(tx_axis_tvalid_int),
.m_axis_tready(tx_axis_tready_int),
.m_axis_tlast(tx_axis_tlast_int),
.m_axis_tuser(tx_axis_tuser_int),
// Tag input
.s_axis_tag(s_axis_tx_ptp_ts_tag),
.s_axis_tag_valid(s_axis_tx_ptp_ts_valid),
.s_axis_tag_ready(s_axis_tx_ptp_ts_ready)
);
axis_async_fifo #(
.DEPTH(TX_PTP_TS_FIFO_DEPTH),
.DATA_WIDTH(PTP_TAG_WIDTH+PTP_TS_WIDTH),
.KEEP_ENABLE(0),
.LAST_ENABLE(0),
.ID_ENABLE(0),
.DEST_ENABLE(0),
.USER_ENABLE(0),
.FRAME_FIFO(0)
)
tx_ptp_ts_fifo (
.async_rst(logic_rst | tx_rst),
// AXI input
.s_clk(tx_clk),
.s_axis_tdata({tx_axis_ptp_ts_tag, tx_axis_ptp_ts_96}),
.s_axis_tkeep(0),
.s_axis_tvalid(tx_axis_ptp_ts_valid),
.s_axis_tready(),
.s_axis_tlast(0),
.s_axis_tid(0),
.s_axis_tdest(0),
.s_axis_tuser(0),
// AXI output
.m_clk(logic_clk),
.m_axis_tdata({m_axis_tx_ptp_ts_tag, m_axis_tx_ptp_ts_96}),
.m_axis_tkeep(),
.m_axis_tvalid(m_axis_tx_ptp_ts_valid),
.m_axis_tready(m_axis_tx_ptp_ts_ready),
.m_axis_tlast(),
.m_axis_tid(),
.m_axis_tdest(),
.m_axis_tuser(),
// Status
.s_status_overflow(),
.s_status_bad_frame(),
.s_status_good_frame(),
.m_status_overflow(),
.m_status_bad_frame(),
.m_status_good_frame()
);
end else begin
assign tx_axis_tdata_int = tx_axis_tdata;
assign tx_axis_tkeep_int = tx_axis_tkeep;
assign tx_axis_tvalid_int = tx_axis_tvalid;
assign tx_axis_tready = tx_axis_tready_int;
assign tx_axis_tlast_int = tx_axis_tlast;
assign tx_axis_tuser_int = tx_axis_tuser;
axis_async_fifo #(
.DEPTH(TX_PTP_TS_FIFO_DEPTH),
.DATA_WIDTH(PTP_TS_WIDTH),
.KEEP_ENABLE(0),
.LAST_ENABLE(0),
.ID_ENABLE(0),
.DEST_ENABLE(0),
.USER_ENABLE(0),
.FRAME_FIFO(0)
)
tx_ptp_ts_fifo (
.async_rst(logic_rst | tx_rst),
// AXI input
.s_clk(tx_clk),
.s_axis_tdata(tx_axis_ptp_ts_96),
.s_axis_tkeep(0),
.s_axis_tvalid(tx_axis_ptp_ts_valid),
.s_axis_tready(),
.s_axis_tlast(0),
.s_axis_tid(0),
.s_axis_tdest(0),
.s_axis_tuser(0),
// AXI output
.m_clk(logic_clk),
.m_axis_tdata(m_axis_tx_ptp_ts_96),
.m_axis_tkeep(),
.m_axis_tvalid(m_axis_tx_ptp_ts_valid),
.m_axis_tready(m_axis_tx_ptp_ts_ready),
.m_axis_tlast(),
.m_axis_tid(),
.m_axis_tdest(),
.m_axis_tuser(),
// Status
.s_status_overflow(),
.s_status_bad_frame(),
.s_status_good_frame(),
.m_status_overflow(),
.m_status_bad_frame(),
.m_status_good_frame()
);
assign s_axis_tx_ptp_ts_ready = 1'b0;
assign m_axis_tx_ptp_ts_tag = {PTP_TAG_WIDTH{1'b0}};
end
// Status
.s_status_overflow(),
.s_status_bad_frame(),
.s_status_good_frame(),
.m_status_overflow(),
.m_status_bad_frame(),
.m_status_good_frame()
);
end else begin
assign s_axis_tx_ptp_ts_ready = 1'b0;
assign m_axis_tx_ptp_ts_96 = {PTP_TS_WIDTH{1'b0}};
assign m_axis_tx_ptp_ts_tag = {PTP_TAG_WIDTH{1'b0}};
@ -433,13 +311,6 @@ end else begin
assign tx_ptp_ts_96 = {PTP_TS_WIDTH{1'b0}};
assign tx_axis_tdata_int = tx_axis_tdata;
assign tx_axis_tkeep_int = tx_axis_tkeep;
assign tx_axis_tvalid_int = tx_axis_tvalid;
assign tx_axis_tready = tx_axis_tready_int;
assign tx_axis_tlast_int = tx_axis_tlast;
assign tx_axis_tuser_int = tx_axis_tuser;
end
if (RX_PTP_TS_ENABLE) begin
@ -464,76 +335,12 @@ if (RX_PTP_TS_ENABLE) begin
.locked()
);
axis_fifo #(
.DEPTH(RX_PTP_TS_FIFO_DEPTH),
.DATA_WIDTH(PTP_TS_WIDTH),
.KEEP_ENABLE(0),
.LAST_ENABLE(0),
.ID_ENABLE(0),
.DEST_ENABLE(0),
.USER_ENABLE(0),
.FRAME_FIFO(0)
)
rx_ptp_ts_fifo (
.clk(logic_clk),
.rst(logic_rst),
// AXI input
.s_axis_tdata(rx_axis_ptp_ts_96),
.s_axis_tkeep(0),
.s_axis_tvalid(rx_axis_ptp_ts_valid),
.s_axis_tready(),
.s_axis_tlast(0),
.s_axis_tid(0),
.s_axis_tdest(0),
.s_axis_tuser(0),
// AXI output
.m_axis_tdata(m_axis_rx_ptp_ts_96),
.m_axis_tkeep(),
.m_axis_tvalid(m_axis_rx_ptp_ts_valid),
.m_axis_tready(m_axis_rx_ptp_ts_ready),
.m_axis_tlast(),
.m_axis_tid(),
.m_axis_tdest(),
.m_axis_tuser(),
// Status
.status_overflow(),
.status_bad_frame(),
.status_good_frame()
);
ptp_ts_extract #(
.TS_WIDTH(PTP_TS_WIDTH),
.TS_OFFSET(1),
.USER_WIDTH(RX_USER_WIDTH)
)
rx_ptp_ts_extract (
.clk(logic_clk),
.rst(logic_rst),
// AXI stream input
.s_axis_tvalid(rx_axis_tvalid && rx_axis_tready),
.s_axis_tlast(rx_axis_tlast),
.s_axis_tuser(rx_axis_tuser_int),
// Timestamp output
.m_axis_ts(rx_axis_ptp_ts_96),
.m_axis_ts_valid(rx_axis_ptp_ts_valid)
);
end else begin
assign m_axis_rx_ptp_ts_96 = {PTP_TS_WIDTH{1'b0}};
assign m_axis_rx_ptp_ts_valid = 1'b0;
assign rx_ptp_ts_96 = {PTP_TS_WIDTH{1'b0}};
end
assign rx_axis_tuser = rx_axis_tuser_int[0];
endgenerate
eth_mac_phy_10g #(
@ -617,8 +424,8 @@ axis_async_fifo_adapter #(
.ID_ENABLE(0),
.DEST_ENABLE(0),
.USER_ENABLE(1),
.PIPELINE_OUTPUT(TX_FIFO_PIPELINE_OUTPUT),
.USER_WIDTH(TX_USER_WIDTH),
.PIPELINE_OUTPUT(TX_FIFO_PIPELINE_OUTPUT),
.FRAME_FIFO(TX_FRAME_FIFO),
.USER_BAD_FRAME_VALUE(1'b1),
.USER_BAD_FRAME_MASK(1'b1),
@ -630,14 +437,14 @@ tx_fifo (
// AXI input
.s_clk(logic_clk),
.s_rst(logic_rst),
.s_axis_tdata(tx_axis_tdata_int),
.s_axis_tkeep(tx_axis_tkeep_int),
.s_axis_tvalid(tx_axis_tvalid_int),
.s_axis_tready(tx_axis_tready_int),
.s_axis_tlast(tx_axis_tlast_int),
.s_axis_tdata(tx_axis_tdata),
.s_axis_tkeep(tx_axis_tkeep),
.s_axis_tvalid(tx_axis_tvalid),
.s_axis_tready(tx_axis_tready),
.s_axis_tlast(tx_axis_tlast),
.s_axis_tid(0),
.s_axis_tdest(0),
.s_axis_tuser(tx_axis_tuser_int),
.s_axis_tuser(tx_axis_tuser),
// AXI output
.m_clk(tx_clk),
.m_rst(tx_rst),
@ -669,8 +476,8 @@ axis_async_fifo_adapter #(
.ID_ENABLE(0),
.DEST_ENABLE(0),
.USER_ENABLE(1),
.PIPELINE_OUTPUT(RX_FIFO_PIPELINE_OUTPUT),
.USER_WIDTH(RX_USER_WIDTH),
.PIPELINE_OUTPUT(RX_FIFO_PIPELINE_OUTPUT),
.FRAME_FIFO(RX_FRAME_FIFO),
.USER_BAD_FRAME_VALUE(1'b1),
.USER_BAD_FRAME_MASK(1'b1),
@ -700,7 +507,7 @@ rx_fifo (
.m_axis_tlast(rx_axis_tlast),
.m_axis_tid(),
.m_axis_tdest(),
.m_axis_tuser(rx_axis_tuser_int),
.m_axis_tuser(rx_axis_tuser),
// Status
.s_status_overflow(),
.s_status_bad_frame(),

View File

@ -268,7 +268,7 @@ def test_eth_mac_10g(request, data_width, enable_dic):
parameters['TX_PTP_TAG_WIDTH'] = 16
parameters['RX_PTP_TS_ENABLE'] = 0
parameters['RX_PTP_TS_WIDTH'] = 96
parameters['TX_USER_WIDTH'] = (parameters['TX_PTP_TAG_WIDTH'] if parameters['TX_PTP_TAG_ENABLE'] else 0) + 1
parameters['TX_USER_WIDTH'] = (parameters['TX_PTP_TAG_WIDTH'] if parameters['TX_PTP_TS_ENABLE'] and parameters['TX_PTP_TAG_ENABLE'] else 0) + 1
parameters['RX_USER_WIDTH'] = (parameters['RX_PTP_TS_WIDTH'] if parameters['RX_PTP_TS_ENABLE'] else 0) + 1
extra_env = {f'PARAM_{k}': str(v) for k, v in parameters.items()}

View File

@ -67,10 +67,13 @@ export PARAM_PTP_USE_SAMPLE_CLOCK ?= 0
export PARAM_TX_PTP_TS_ENABLE ?= 0
export PARAM_RX_PTP_TS_ENABLE ?= 0
export PARAM_TX_PTP_TS_FIFO_DEPTH ?= 64
export PARAM_RX_PTP_TS_FIFO_DEPTH ?= 64
export PARAM_PTP_TS_WIDTH ?= 96
export PARAM_TX_PTP_TAG_ENABLE ?= 0
export PARAM_PTP_TAG_WIDTH ?= 16
# export PARAM_TX_USER_WIDTH ?= (parameters['TX_PTP_TAG_WIDTH'] if parameters['TX_PTP_TAG_ENABLE'] else 0) + 1
export PARAM_TX_USER_WIDTH ?= 1
# export PARAM_RX_USER_WIDTH ?= (parameters['RX_PTP_TS_WIDTH'] if parameters['RX_PTP_TS_ENABLE'] else 0) + 1
export PARAM_RX_USER_WIDTH ?= 1
ifeq ($(SIM), icarus)
PLUSARGS += -fst
@ -101,10 +104,11 @@ ifeq ($(SIM), icarus)
COMPILE_ARGS += -P $(TOPLEVEL).TX_PTP_TS_ENABLE=$(PARAM_TX_PTP_TS_ENABLE)
COMPILE_ARGS += -P $(TOPLEVEL).RX_PTP_TS_ENABLE=$(PARAM_RX_PTP_TS_ENABLE)
COMPILE_ARGS += -P $(TOPLEVEL).TX_PTP_TS_FIFO_DEPTH=$(PARAM_TX_PTP_TS_FIFO_DEPTH)
COMPILE_ARGS += -P $(TOPLEVEL).RX_PTP_TS_FIFO_DEPTH=$(PARAM_RX_PTP_TS_FIFO_DEPTH)
COMPILE_ARGS += -P $(TOPLEVEL).PTP_TS_WIDTH=$(PARAM_PTP_TS_WIDTH)
COMPILE_ARGS += -P $(TOPLEVEL).TX_PTP_TAG_ENABLE=$(PARAM_TX_PTP_TAG_ENABLE)
COMPILE_ARGS += -P $(TOPLEVEL).PTP_TAG_WIDTH=$(PARAM_PTP_TAG_WIDTH)
COMPILE_ARGS += -P $(TOPLEVEL).TX_USER_WIDTH=$(PARAM_TX_USER_WIDTH)
COMPILE_ARGS += -P $(TOPLEVEL).RX_USER_WIDTH=$(PARAM_RX_USER_WIDTH)
ifeq ($(WAVES), 1)
VERILOG_SOURCES += iverilog_dump.v
@ -139,10 +143,11 @@ else ifeq ($(SIM), verilator)
COMPILE_ARGS += -GTX_PTP_TS_ENABLE=$(PARAM_TX_PTP_TS_ENABLE)
COMPILE_ARGS += -GRX_PTP_TS_ENABLE=$(PARAM_RX_PTP_TS_ENABLE)
COMPILE_ARGS += -GTX_PTP_TS_FIFO_DEPTH=$(PARAM_TX_PTP_TS_FIFO_DEPTH)
COMPILE_ARGS += -GRX_PTP_TS_FIFO_DEPTH=$(PARAM_RX_PTP_TS_FIFO_DEPTH)
COMPILE_ARGS += -GPTP_TS_WIDTH=$(PARAM_PTP_TS_WIDTH)
COMPILE_ARGS += -GTX_PTP_TAG_ENABLE=$(PARAM_TX_PTP_TAG_ENABLE)
COMPILE_ARGS += -GPTP_TAG_WIDTH=$(PARAM_PTP_TAG_WIDTH)
COMPILE_ARGS += -GTX_USER_WIDTH=$(PARAM_TX_USER_WIDTH)
COMPILE_ARGS += -GRX_USER_WIDTH=$(PARAM_RX_USER_WIDTH)
ifeq ($(WAVES), 1)
COMPILE_ARGS += --trace-fst

View File

@ -290,10 +290,11 @@ def test_eth_mac_10g_fifo(request, data_width, enable_dic):
parameters['TX_PTP_TS_ENABLE'] = 0
parameters['RX_PTP_TS_ENABLE'] = 0
parameters['TX_PTP_TS_FIFO_DEPTH'] = 64
parameters['RX_PTP_TS_FIFO_DEPTH'] = 64
parameters['PTP_TS_WIDTH'] = 96
parameters['TX_PTP_TAG_ENABLE'] = 0
parameters['PTP_TAG_WIDTH'] = 16
parameters['TX_USER_WIDTH'] = (parameters['TX_PTP_TAG_WIDTH'] if parameters['TX_PTP_TS_ENABLE'] and parameters['TX_PTP_TAG_ENABLE'] else 0) + 1
parameters['RX_USER_WIDTH'] = (parameters['RX_PTP_TS_WIDTH'] if parameters['RX_PTP_TS_ENABLE'] else 0) + 1
extra_env = {f'PARAM_{k}': str(v) for k, v in parameters.items()}

View File

@ -27,7 +27,8 @@ commands =
testpaths =
tb
example
norecursedirs =
lib
addopts =
--ignore-glob=tb/test_*.py
--ignore-glob=*lib*
--import-mode importlib