From b22db1d2d2456e0a122f8c53c3dde2260dcf0c6e Mon Sep 17 00:00:00 2001 From: Alex Forencich Date: Sun, 14 Jan 2024 19:17:00 -0800 Subject: [PATCH] Add CRC state registers where possible to 10G/25G MAC modules Signed-off-by: Alex Forencich --- rtl/axis_baser_tx_64.v | 49 ++++++++++++++++++++++++++---------------- rtl/axis_xgmii_tx_32.v | 38 +++++++++++++++++++------------- rtl/axis_xgmii_tx_64.v | 49 ++++++++++++++++++++++++++---------------- 3 files changed, 83 insertions(+), 53 deletions(-) diff --git a/rtl/axis_baser_tx_64.v b/rtl/axis_baser_tx_64.v index 2fc0b634..dce320d7 100644 --- a/rtl/axis_baser_tx_64.v +++ b/rtl/axis_baser_tx_64.v @@ -212,9 +212,8 @@ reg m_axis_ptp_ts_valid_reg = 1'b0, m_axis_ptp_ts_valid_next; reg m_axis_ptp_ts_valid_int_reg = 1'b0, m_axis_ptp_ts_valid_int_next; reg m_axis_ptp_ts_borrow_reg = 1'b0, m_axis_ptp_ts_borrow_next; -reg [31:0] crc_state = 32'hFFFFFFFF; - -wire [31:0] crc_next[7:0]; +reg [31:0] crc_state_reg[7:0]; +wire [31:0] crc_state_next[7:0]; reg [DATA_WIDTH-1:0] encoded_tx_data_reg = {{8{CTRL_IDLE}}, BLOCK_TYPE_CTRL}; reg [HDR_WIDTH-1:0] encoded_tx_hdr_reg = SYNC_CTRL; @@ -252,9 +251,9 @@ generate ) eth_crc ( .data_in(s_tdata_reg[0 +: 8*(n+1)]), - .state_in(crc_state), + .state_in(crc_state_reg[7]), .data_out(), - .state_out(crc_next[n]) + .state_out(crc_state_next[n]) ); end @@ -288,57 +287,57 @@ end always @* begin casez (s_empty_reg) 3'd7: begin - fcs_output_data_0 = {24'd0, ~crc_next[0][31:0], s_tdata_reg[7:0]}; + fcs_output_data_0 = {24'd0, ~crc_state_next[0][31:0], s_tdata_reg[7:0]}; fcs_output_data_1 = 64'd0; fcs_output_type_0 = OUTPUT_TYPE_TERM_5; fcs_output_type_1 = OUTPUT_TYPE_IDLE; ifg_offset = 8'd3; end 3'd6: begin - fcs_output_data_0 = {16'd0, ~crc_next[1][31:0], s_tdata_reg[15:0]}; + fcs_output_data_0 = {16'd0, ~crc_state_next[1][31:0], s_tdata_reg[15:0]}; fcs_output_data_1 = 64'd0; fcs_output_type_0 = OUTPUT_TYPE_TERM_6; fcs_output_type_1 = OUTPUT_TYPE_IDLE; ifg_offset = 8'd2; end 3'd5: begin - fcs_output_data_0 = {8'd0, ~crc_next[2][31:0], s_tdata_reg[23:0]}; + fcs_output_data_0 = {8'd0, ~crc_state_next[2][31:0], s_tdata_reg[23:0]}; fcs_output_data_1 = 64'd0; fcs_output_type_0 = OUTPUT_TYPE_TERM_7; fcs_output_type_1 = OUTPUT_TYPE_IDLE; ifg_offset = 8'd1; end 3'd4: begin - fcs_output_data_0 = {~crc_next[3][31:0], s_tdata_reg[31:0]}; + fcs_output_data_0 = {~crc_state_next[3][31:0], s_tdata_reg[31:0]}; fcs_output_data_1 = 64'd0; fcs_output_type_0 = OUTPUT_TYPE_DATA; fcs_output_type_1 = OUTPUT_TYPE_TERM_0; ifg_offset = 8'd8; end 3'd3: begin - fcs_output_data_0 = {~crc_next[4][23:0], s_tdata_reg[39:0]}; - fcs_output_data_1 = {56'd0, ~crc_next[4][31:24]}; + fcs_output_data_0 = {~crc_state_next[4][23:0], s_tdata_reg[39:0]}; + fcs_output_data_1 = {56'd0, ~crc_state_reg[4][31:24]}; fcs_output_type_0 = OUTPUT_TYPE_DATA; fcs_output_type_1 = OUTPUT_TYPE_TERM_1; ifg_offset = 8'd7; end 3'd2: begin - fcs_output_data_0 = {~crc_next[5][15:0], s_tdata_reg[47:0]}; - fcs_output_data_1 = {48'd0, ~crc_next[5][31:16]}; + fcs_output_data_0 = {~crc_state_next[5][15:0], s_tdata_reg[47:0]}; + fcs_output_data_1 = {48'd0, ~crc_state_reg[5][31:16]}; fcs_output_type_0 = OUTPUT_TYPE_DATA; fcs_output_type_1 = OUTPUT_TYPE_TERM_2; ifg_offset = 8'd6; end 3'd1: begin - fcs_output_data_0 = {~crc_next[6][7:0], s_tdata_reg[55:0]}; - fcs_output_data_1 = {40'd0, ~crc_next[6][31:8]}; + fcs_output_data_0 = {~crc_state_next[6][7:0], s_tdata_reg[55:0]}; + fcs_output_data_1 = {40'd0, ~crc_state_reg[6][31:8]}; fcs_output_type_0 = OUTPUT_TYPE_DATA; fcs_output_type_1 = OUTPUT_TYPE_TERM_3; ifg_offset = 8'd5; end 3'd0: begin fcs_output_data_0 = s_tdata_reg; - fcs_output_data_1 = {32'd0, ~crc_next[7][31:0]}; + fcs_output_data_1 = {32'd0, ~crc_state_reg[7][31:0]}; fcs_output_type_0 = OUTPUT_TYPE_DATA; fcs_output_type_1 = OUTPUT_TYPE_TERM_4; ifg_offset = 8'd4; @@ -531,6 +530,8 @@ always @* begin output_data_next = fcs_output_data_0; output_type_next = fcs_output_type_0; + update_crc = 1'b1; + ifg_count_next = (cfg_ifg > 8'd12 ? cfg_ifg : 8'd12) - ifg_offset + (swap_lanes_reg ? 8'd4 : 8'd0) + deficit_idle_count_reg; if (s_empty_reg <= 4) begin state_next = STATE_FCS_2; @@ -768,10 +769,20 @@ always @(posedge clk) begin end endcase + crc_state_reg[0] <= crc_state_next[0]; + crc_state_reg[1] <= crc_state_next[1]; + crc_state_reg[2] <= crc_state_next[2]; + crc_state_reg[3] <= crc_state_next[3]; + crc_state_reg[4] <= crc_state_next[4]; + crc_state_reg[5] <= crc_state_next[5]; + crc_state_reg[6] <= crc_state_next[6]; + + if (update_crc) begin + crc_state_reg[7] <= crc_state_next[7]; + end + if (reset_crc) begin - crc_state <= 32'hFFFFFFFF; - end else if (update_crc) begin - crc_state <= crc_next[7]; + crc_state_reg[7] <= 32'hFFFFFFFF; end if (rst) begin diff --git a/rtl/axis_xgmii_tx_32.v b/rtl/axis_xgmii_tx_32.v index a5933061..86e504ec 100644 --- a/rtl/axis_xgmii_tx_32.v +++ b/rtl/axis_xgmii_tx_32.v @@ -155,9 +155,8 @@ reg [PTP_TS_WIDTH-1:0] m_axis_ptp_ts_reg = 0, m_axis_ptp_ts_next; reg [PTP_TAG_WIDTH-1:0] m_axis_ptp_ts_tag_reg = 0, m_axis_ptp_ts_tag_next; reg m_axis_ptp_ts_valid_reg = 1'b0, m_axis_ptp_ts_valid_next; -reg [31:0] crc_state = 32'hFFFFFFFF; - -wire [31:0] crc_next[3:0]; +reg [31:0] crc_state_reg[3:0]; +wire [31:0] crc_state_next[3:0]; reg [DATA_WIDTH-1:0] xgmii_txd_reg = {CTRL_WIDTH{XGMII_IDLE}}, xgmii_txd_next; reg [CTRL_WIDTH-1:0] xgmii_txc_reg = {CTRL_WIDTH{1'b1}}, xgmii_txc_next; @@ -192,9 +191,9 @@ generate ) eth_crc ( .data_in(s_tdata_reg[0 +: 8*(n+1)]), - .state_in(crc_state), + .state_in(crc_state_reg[3]), .data_out(), - .state_out(crc_next[n]) + .state_out(crc_state_next[n]) ); end @@ -224,24 +223,24 @@ end always @* begin casez (s_empty_reg) 2'd3: begin - fcs_output_txd_0 = {~crc_next[0][23:0], s_tdata_reg[7:0]}; - fcs_output_txd_1 = {{2{XGMII_IDLE}}, XGMII_TERM, ~crc_next[0][31:24]}; + fcs_output_txd_0 = {~crc_state_next[0][23:0], s_tdata_reg[7:0]}; + fcs_output_txd_1 = {{2{XGMII_IDLE}}, XGMII_TERM, ~crc_state_reg[0][31:24]}; fcs_output_txc_0 = 4'b0000; fcs_output_txc_1 = 4'b1110; ifg_offset = 8'd3; extra_cycle = 1'b0; end 2'd2: begin - fcs_output_txd_0 = {~crc_next[1][15:0], s_tdata_reg[15:0]}; - fcs_output_txd_1 = {XGMII_IDLE, XGMII_TERM, ~crc_next[1][31:16]}; + fcs_output_txd_0 = {~crc_state_next[1][15:0], s_tdata_reg[15:0]}; + fcs_output_txd_1 = {XGMII_IDLE, XGMII_TERM, ~crc_state_reg[1][31:16]}; fcs_output_txc_0 = 4'b0000; fcs_output_txc_1 = 4'b1100; ifg_offset = 8'd2; extra_cycle = 1'b0; end 2'd1: begin - fcs_output_txd_0 = {~crc_next[2][7:0], s_tdata_reg[23:0]}; - fcs_output_txd_1 = {XGMII_TERM, ~crc_next[2][31:8]}; + fcs_output_txd_0 = {~crc_state_next[2][7:0], s_tdata_reg[23:0]}; + fcs_output_txd_1 = {XGMII_TERM, ~crc_state_reg[2][31:8]}; fcs_output_txc_0 = 4'b0000; fcs_output_txc_1 = 4'b1000; ifg_offset = 8'd1; @@ -249,7 +248,7 @@ always @* begin end 2'd0: begin fcs_output_txd_0 = s_tdata_reg; - fcs_output_txd_1 = ~crc_next[3]; + fcs_output_txd_1 = ~crc_state_reg[3]; fcs_output_txc_0 = 4'b0000; fcs_output_txc_1 = 4'b0000; ifg_offset = 8'd4; @@ -323,6 +322,7 @@ always @* begin end STATE_PREAMBLE: begin // send preamble + reset_crc = 1'b1; s_tdata_next = s_axis_tdata_masked; s_empty_next = keep2empty(s_axis_tkeep); @@ -415,6 +415,8 @@ always @* begin xgmii_txd_next = fcs_output_txd_0; xgmii_txc_next = fcs_output_txc_0; + update_crc = 1'b1; + ifg_count_next = (cfg_ifg > 8'd12 ? cfg_ifg : 8'd12) - ifg_offset + deficit_idle_count_reg; state_next = STATE_FCS_2; end @@ -533,10 +535,16 @@ always @(posedge clk) begin m_axis_ptp_ts_tag_reg <= m_axis_ptp_ts_tag_next; m_axis_ptp_ts_valid_reg <= m_axis_ptp_ts_valid_next; + crc_state_reg[0] <= crc_state_next[0]; + crc_state_reg[1] <= crc_state_next[1]; + crc_state_reg[2] <= crc_state_next[2]; + + if (update_crc) begin + crc_state_reg[3] <= crc_state_next[3]; + end + if (reset_crc) begin - crc_state <= 32'hFFFFFFFF; - end else if (update_crc) begin - crc_state <= crc_next[3]; + crc_state_reg[3] <= 32'hFFFFFFFF; end xgmii_txd_reg <= xgmii_txd_next; diff --git a/rtl/axis_xgmii_tx_64.v b/rtl/axis_xgmii_tx_64.v index c7ee3fd5..c1c3714f 100644 --- a/rtl/axis_xgmii_tx_64.v +++ b/rtl/axis_xgmii_tx_64.v @@ -160,9 +160,8 @@ reg m_axis_ptp_ts_valid_reg = 1'b0, m_axis_ptp_ts_valid_next; reg m_axis_ptp_ts_valid_int_reg = 1'b0, m_axis_ptp_ts_valid_int_next; reg m_axis_ptp_ts_borrow_reg = 1'b0, m_axis_ptp_ts_borrow_next; -reg [31:0] crc_state = 32'hFFFFFFFF; - -wire [31:0] crc_next[7:0]; +reg [31:0] crc_state_reg[7:0]; +wire [31:0] crc_state_next[7:0]; reg [DATA_WIDTH-1:0] xgmii_txd_reg = {CTRL_WIDTH{XGMII_IDLE}}, xgmii_txd_next; reg [CTRL_WIDTH-1:0] xgmii_txc_reg = {CTRL_WIDTH{1'b1}}, xgmii_txc_next; @@ -197,9 +196,9 @@ generate ) eth_crc ( .data_in(s_tdata_reg[0 +: 8*(n+1)]), - .state_in(crc_state), + .state_in(crc_state_reg[7]), .data_out(), - .state_out(crc_next[n]) + .state_out(crc_state_next[n]) ); end @@ -233,57 +232,57 @@ end always @* begin casez (s_empty_reg) 3'd7: begin - fcs_output_txd_0 = {{2{XGMII_IDLE}}, XGMII_TERM, ~crc_next[0][31:0], s_tdata_reg[7:0]}; + fcs_output_txd_0 = {{2{XGMII_IDLE}}, XGMII_TERM, ~crc_state_next[0][31:0], s_tdata_reg[7:0]}; fcs_output_txd_1 = {8{XGMII_IDLE}}; fcs_output_txc_0 = 8'b11100000; fcs_output_txc_1 = 8'b11111111; ifg_offset = 8'd3; end 3'd6: begin - fcs_output_txd_0 = {XGMII_IDLE, XGMII_TERM, ~crc_next[1][31:0], s_tdata_reg[15:0]}; + fcs_output_txd_0 = {XGMII_IDLE, XGMII_TERM, ~crc_state_next[1][31:0], s_tdata_reg[15:0]}; fcs_output_txd_1 = {8{XGMII_IDLE}}; fcs_output_txc_0 = 8'b11000000; fcs_output_txc_1 = 8'b11111111; ifg_offset = 8'd2; end 3'd5: begin - fcs_output_txd_0 = {XGMII_TERM, ~crc_next[2][31:0], s_tdata_reg[23:0]}; + fcs_output_txd_0 = {XGMII_TERM, ~crc_state_next[2][31:0], s_tdata_reg[23:0]}; fcs_output_txd_1 = {8{XGMII_IDLE}}; fcs_output_txc_0 = 8'b10000000; fcs_output_txc_1 = 8'b11111111; ifg_offset = 8'd1; end 3'd4: begin - fcs_output_txd_0 = {~crc_next[3][31:0], s_tdata_reg[31:0]}; + fcs_output_txd_0 = {~crc_state_next[3][31:0], s_tdata_reg[31:0]}; fcs_output_txd_1 = {{7{XGMII_IDLE}}, XGMII_TERM}; fcs_output_txc_0 = 8'b00000000; fcs_output_txc_1 = 8'b11111111; ifg_offset = 8'd8; end 3'd3: begin - fcs_output_txd_0 = {~crc_next[4][23:0], s_tdata_reg[39:0]}; - fcs_output_txd_1 = {{6{XGMII_IDLE}}, XGMII_TERM, ~crc_next[4][31:24]}; + fcs_output_txd_0 = {~crc_state_next[4][23:0], s_tdata_reg[39:0]}; + fcs_output_txd_1 = {{6{XGMII_IDLE}}, XGMII_TERM, ~crc_state_reg[4][31:24]}; fcs_output_txc_0 = 8'b00000000; fcs_output_txc_1 = 8'b11111110; ifg_offset = 8'd7; end 3'd2: begin - fcs_output_txd_0 = {~crc_next[5][15:0], s_tdata_reg[47:0]}; - fcs_output_txd_1 = {{5{XGMII_IDLE}}, XGMII_TERM, ~crc_next[5][31:16]}; + fcs_output_txd_0 = {~crc_state_next[5][15:0], s_tdata_reg[47:0]}; + fcs_output_txd_1 = {{5{XGMII_IDLE}}, XGMII_TERM, ~crc_state_reg[5][31:16]}; fcs_output_txc_0 = 8'b00000000; fcs_output_txc_1 = 8'b11111100; ifg_offset = 8'd6; end 3'd1: begin - fcs_output_txd_0 = {~crc_next[6][7:0], s_tdata_reg[55:0]}; - fcs_output_txd_1 = {{4{XGMII_IDLE}}, XGMII_TERM, ~crc_next[6][31:8]}; + fcs_output_txd_0 = {~crc_state_next[6][7:0], s_tdata_reg[55:0]}; + fcs_output_txd_1 = {{4{XGMII_IDLE}}, XGMII_TERM, ~crc_state_reg[6][31:8]}; fcs_output_txc_0 = 8'b00000000; fcs_output_txc_1 = 8'b11111000; ifg_offset = 8'd5; end 3'd0: begin fcs_output_txd_0 = s_tdata_reg; - fcs_output_txd_1 = {{3{XGMII_IDLE}}, XGMII_TERM, ~crc_next[7][31:0]}; + fcs_output_txd_1 = {{3{XGMII_IDLE}}, XGMII_TERM, ~crc_state_reg[7][31:0]}; fcs_output_txc_0 = 8'b00000000; fcs_output_txc_1 = 8'b11110000; ifg_offset = 8'd4; @@ -480,6 +479,8 @@ always @* begin xgmii_txd_next = fcs_output_txd_0; xgmii_txc_next = fcs_output_txc_0; + update_crc = 1'b1; + ifg_count_next = (cfg_ifg > 8'd12 ? cfg_ifg : 8'd12) - ifg_offset + (swap_lanes_reg ? 8'd4 : 8'd0) + deficit_idle_count_reg; if (s_empty_reg <= 4) begin state_next = STATE_FCS_2; @@ -622,10 +623,20 @@ always @(posedge clk) begin m_axis_ptp_ts_valid_int_reg <= m_axis_ptp_ts_valid_int_next; m_axis_ptp_ts_borrow_reg <= m_axis_ptp_ts_borrow_next; + crc_state_reg[0] <= crc_state_next[0]; + crc_state_reg[1] <= crc_state_next[1]; + crc_state_reg[2] <= crc_state_next[2]; + crc_state_reg[3] <= crc_state_next[3]; + crc_state_reg[4] <= crc_state_next[4]; + crc_state_reg[5] <= crc_state_next[5]; + crc_state_reg[6] <= crc_state_next[6]; + + if (update_crc) begin + crc_state_reg[7] <= crc_state_next[7]; + end + if (reset_crc) begin - crc_state <= 32'hFFFFFFFF; - end else if (update_crc) begin - crc_state <= crc_next[7]; + crc_state_reg[7] <= 32'hFFFFFFFF; end swap_txd <= xgmii_txd_next[63:32];