File: chdr_strip_header.sv

package info (click to toggle)
uhd 4.9.0.0%2Bds1-1
  • links: PTS, VCS
  • area: main
  • in suites: forky, sid
  • size: 184,180 kB
  • sloc: cpp: 262,887; python: 112,011; ansic: 102,670; vhdl: 57,031; tcl: 19,924; xml: 8,581; makefile: 3,028; sh: 2,812; pascal: 230; javascript: 120; csh: 94; asm: 20; perl: 11
file content (158 lines) | stat: -rw-r--r-- 4,373 bytes parent folder | download | duplicates (2)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
//
// Copyright 2022 Ettus Research, a National Instruments Brand
//
// SPDX-License-Identifier: LGPL-3.0-or-later
//
// Module: chdr_strip_header
//
// Description:
//
//   Removes the CHDR header depending on the state of strip_en on the first
//   word of the packet.
//

`default_nettype none


module chdr_strip_header #(
  parameter  CHDR_W = 64,
  localparam USER_W = 16
) (
  // Clock and reset
  input wire clk,
  input wire rst,

  // Strip enable, sampled when the first word of the packet is transferred
  input wire strip_en,

  // CHDR input packet
  input  wire  [CHDR_W-1:0] s_chdr_tdata,
  input  wire               s_chdr_tlast,
  input  wire               s_chdr_tvalid,
  output logic              s_chdr_tready,

  // Output packet (with or without header)
  output logic [CHDR_W-1:0] m_tdata,
  output logic [USER_W-1:0] m_tuser,
  output logic              m_tlast,
  output logic              m_tvalid,
  input  wire               m_tready
);

  `include "../core/rfnoc_chdr_utils.vh"

  enum {
    ST_HDR,   // CHDR header
    ST_STRIP, // Strip header
    ST_PASS   // Pass packet through
  } state;

  localparam COUNT_W = (CHDR_W == 64) ?
    6 : // Max count is timestamp + metadata
    5;  // Max count is metadata only (timestamp is in the first word)

  // The number of CHDR words we need to skip to get to the payload, minus one.
  logic [COUNT_W-1:0] skip_length;
  // Counter to track where we are in the header.
  logic [COUNT_W-1:0] skip_count;

  // Total length of the header, including timestamp and metadata, minus 1.
  logic [COUNT_W-1:0] hdr_length;

  // Register to hold the new packet length, in bytes
  logic [15:0] packet_length;

  //---------------------------------------------------------------------------
  // State Machine Registers
  //---------------------------------------------------------------------------

  always_ff @(posedge clk) begin : sm_reg
    case (state)
      ST_HDR : begin
        skip_count    <= 1;
        skip_length   <= hdr_length;
        packet_length <= chdr_get_length(s_chdr_tdata) - (CHDR_W/8);

        if (s_chdr_tvalid && s_chdr_tready) begin
          if (hdr_length > 0 && strip_en) begin
            state <= ST_STRIP;
          end else begin
            state <= ST_PASS;
          end
        end
      end
      ST_STRIP : begin
        if (s_chdr_tvalid && s_chdr_tready) begin
          packet_length <= packet_length - (CHDR_W/8);
          skip_count <= skip_count + 1;
          if (s_chdr_tlast) begin
            state <= ST_HDR;
          end else if (skip_count == skip_length) begin
            state <= ST_PASS;
          end
        end
      end
      ST_PASS : begin
        if (s_chdr_tvalid && s_chdr_tready && s_chdr_tlast) begin
          state <= ST_HDR;
        end
      end
    endcase

    if (rst) begin
      state <= ST_HDR;
    end
  end : sm_reg

  //---------------------------------------------------------------------------
  // State Machine Combinatorial Logic
  //---------------------------------------------------------------------------

  always_comb begin : sm_comb
    // Default assignments
    m_tdata       = s_chdr_tdata;
    m_tlast       = s_chdr_tlast;
    m_tvalid      = 0;
    m_tuser       = packet_length;
    s_chdr_tready = 1;

    // Calculate the length of the header, including timestamp and metadata,
    // minus 1.
    if (CHDR_W == 64 && chdr_get_pkt_type(s_chdr_tdata) == CHDR_PKT_TYPE_DATA_TS) begin
      hdr_length = chdr_get_num_mdata(s_chdr_tdata) + 1;
    end else begin
      hdr_length = chdr_get_num_mdata(s_chdr_tdata);
    end

    // Drive m_tvalid and s_chdr_tready
    case (state)
      ST_HDR : begin
        m_tuser = chdr_get_length(s_chdr_tdata);
        if (strip_en) begin
          // Drop header word
          m_tvalid      = 0;
          s_chdr_tready = 1;
        end else begin
          // Pass header through
          m_tvalid      = s_chdr_tvalid;
          s_chdr_tready = m_tready;
        end
      end
      ST_STRIP : begin
        // Drop incoming words
        m_tvalid      = 0;
        s_chdr_tready = 1;
      end
      ST_PASS : begin
        // Pass words through
        m_tvalid      = s_chdr_tvalid;
        m_tuser       = packet_length;
        s_chdr_tready = m_tready;
      end
    endcase
  end : sm_comb

endmodule : chdr_strip_header


`default_nettype wire