Branch data Line data Source code
1 : :
2 : : /* SPDX-License-Identifier: BSD-3-Clause
3 : : * Copyright(c) 2023 Intel Corporation
4 : : */
5 : :
6 : : #ifndef _GRO_TCP_INTERNAL_H_
7 : : #define _GRO_TCP_INTERNAL_H_
8 : :
9 : : static inline uint32_t
10 : : find_an_empty_item(struct gro_tcp_item *items,
11 : : uint32_t max_item_num)
12 : : {
13 : : uint32_t i;
14 : :
15 [ # # # # ]: 0 : for (i = 0; i < max_item_num; i++)
16 [ # # # # ]: 0 : if (items[i].firstseg == NULL)
17 : : return i;
18 : : return INVALID_ARRAY_INDEX;
19 : : }
20 : :
21 : : static inline uint32_t
22 : 0 : insert_new_tcp_item(struct rte_mbuf *pkt,
23 : : struct gro_tcp_item *items,
24 : : uint32_t *item_num,
25 : : uint32_t max_item_num,
26 : : uint64_t start_time,
27 : : uint32_t prev_idx,
28 : : uint32_t sent_seq,
29 : : uint16_t ip_id,
30 : : uint8_t is_atomic)
31 : : {
32 : : uint32_t item_idx;
33 : :
34 : : item_idx = find_an_empty_item(items, max_item_num);
35 [ # # # # ]: 0 : if (item_idx == INVALID_ARRAY_INDEX)
36 : : return INVALID_ARRAY_INDEX;
37 : :
38 : 0 : items[item_idx].firstseg = pkt;
39 : 0 : items[item_idx].lastseg = rte_pktmbuf_lastseg(pkt);
40 : 0 : items[item_idx].start_time = start_time;
41 : 0 : items[item_idx].next_pkt_idx = INVALID_ARRAY_INDEX;
42 : 0 : items[item_idx].sent_seq = sent_seq;
43 : 0 : items[item_idx].l3.ip_id = ip_id;
44 : 0 : items[item_idx].nb_merged = 1;
45 : 0 : items[item_idx].is_atomic = is_atomic;
46 : 0 : (*item_num) += 1;
47 : :
48 : : /* if the previous packet exists, chain them together. */
49 [ # # ]: 0 : if (prev_idx != INVALID_ARRAY_INDEX) {
50 : 0 : items[item_idx].next_pkt_idx =
51 : 0 : items[prev_idx].next_pkt_idx;
52 : 0 : items[prev_idx].next_pkt_idx = item_idx;
53 : : }
54 : :
55 : : return item_idx;
56 : : }
57 : :
58 : : static inline uint32_t
59 : : delete_tcp_item(struct gro_tcp_item *items, uint32_t item_idx,
60 : : uint32_t *item_num,
61 : : uint32_t prev_item_idx)
62 : : {
63 : 0 : uint32_t next_idx = items[item_idx].next_pkt_idx;
64 : :
65 : : /* NULL indicates an empty item */
66 : 0 : items[item_idx].firstseg = NULL;
67 [ # # ]: 0 : (*item_num) -= 1;
68 : : if (prev_item_idx != INVALID_ARRAY_INDEX)
69 : : items[prev_item_idx].next_pkt_idx = next_idx;
70 : :
71 : : return next_idx;
72 : : }
73 : :
74 : : static inline int32_t
75 : 0 : process_tcp_item(struct rte_mbuf *pkt,
76 : : struct rte_tcp_hdr *tcp_hdr,
77 : : int32_t tcp_dl,
78 : : struct gro_tcp_item *items,
79 : : uint32_t item_idx,
80 : : uint32_t *item_num,
81 : : uint32_t max_item_num,
82 : : uint16_t ip_id,
83 : : uint8_t is_atomic,
84 : : uint64_t start_time)
85 : : {
86 : : uint32_t cur_idx;
87 : : uint32_t prev_idx;
88 : : int cmp;
89 : : uint32_t sent_seq;
90 : :
91 [ # # ]: 0 : sent_seq = rte_be_to_cpu_32(tcp_hdr->sent_seq);
92 : : /*
93 : : * Check all packets in the flow and try to find a neighbor for
94 : : * the input packet.
95 : : */
96 : : cur_idx = item_idx;
97 : : prev_idx = cur_idx;
98 : : do {
99 : 0 : cmp = check_seq_option(&items[cur_idx], tcp_hdr,
100 : 0 : sent_seq, ip_id, pkt->l4_len, tcp_dl, 0,
101 : : is_atomic);
102 [ # # ]: 0 : if (cmp) {
103 [ # # ]: 0 : if (merge_two_tcp_packets(&items[cur_idx],
104 : 0 : pkt, cmp, sent_seq, tcp_hdr->tcp_flags, ip_id, 0))
105 : : return 1;
106 : : /*
107 : : * Fail to merge the two packets, as the packet
108 : : * length is greater than the max value. Store
109 : : * the packet into the flow.
110 : : */
111 [ # # ]: 0 : if (insert_new_tcp_item(pkt, items, item_num, max_item_num,
112 : : start_time, cur_idx, sent_seq, ip_id, is_atomic) ==
113 : : INVALID_ARRAY_INDEX)
114 : : return -1;
115 : 0 : return 0;
116 : : }
117 : : prev_idx = cur_idx;
118 : 0 : cur_idx = items[cur_idx].next_pkt_idx;
119 [ # # ]: 0 : } while (cur_idx != INVALID_ARRAY_INDEX);
120 : :
121 : : /* Fail to find a neighbor, so store the packet into the flow. */
122 [ # # ]: 0 : if (insert_new_tcp_item(pkt, items, item_num, max_item_num, start_time, prev_idx, sent_seq,
123 : : ip_id, is_atomic) == INVALID_ARRAY_INDEX)
124 : 0 : return -1;
125 : :
126 : : return 0;
127 : : }
128 : : #endif
|