]> git.ipfire.org Git - thirdparty/openwrt.git/blob
607f21a665e2b1c83eea4f2d736179d90f78cb62
[thirdparty/openwrt.git] /
1 From 7516b27c555c1711ec17a5d891befb6986e573a3 Mon Sep 17 00:00:00 2001
2 From: Felix Fietkau <nbd@nbd.name>
3 Date: Thu, 2 May 2024 10:44:46 +0200
4 Subject: [PATCH 5/6] net: create tcp_gro_header_pull helper function
5
6 Pull the code out of tcp_gro_receive in order to access the tcp header
7 from tcp4/6_gro_receive.
8
9 Acked-by: Paolo Abeni <pabeni@redhat.com>
10 Reviewed-by: Eric Dumazet <edumazet@google.com>
11 Signed-off-by: Felix Fietkau <nbd@nbd.name>
12 Reviewed-by: David Ahern <dsahern@kernel.org>
13 Reviewed-by: Willem de Bruijn <willemb@google.com>
14 Signed-off-by: Paolo Abeni <pabeni@redhat.com>
15 ---
16 include/net/tcp.h | 4 ++-
17 net/ipv4/tcp_offload.c | 55 +++++++++++++++++++++++++---------------
18 net/ipv6/tcpv6_offload.c | 18 +++++++++----
19 3 files changed, 50 insertions(+), 27 deletions(-)
20
21 --- a/include/net/tcp.h
22 +++ b/include/net/tcp.h
23 @@ -2101,8 +2101,10 @@ void tcp_v4_destroy_sock(struct sock *sk
24
25 struct sk_buff *tcp_gso_segment(struct sk_buff *skb,
26 netdev_features_t features);
27 +struct tcphdr *tcp_gro_pull_header(struct sk_buff *skb);
28 struct sk_buff *tcp_gro_lookup(struct list_head *head, struct tcphdr *th);
29 -struct sk_buff *tcp_gro_receive(struct list_head *head, struct sk_buff *skb);
30 +struct sk_buff *tcp_gro_receive(struct list_head *head, struct sk_buff *skb,
31 + struct tcphdr *th);
32 INDIRECT_CALLABLE_DECLARE(int tcp4_gro_complete(struct sk_buff *skb, int thoff));
33 INDIRECT_CALLABLE_DECLARE(struct sk_buff *tcp4_gro_receive(struct list_head *head, struct sk_buff *skb));
34 INDIRECT_CALLABLE_DECLARE(int tcp6_gro_complete(struct sk_buff *skb, int thoff));
35 --- a/net/ipv4/tcp_offload.c
36 +++ b/net/ipv4/tcp_offload.c
37 @@ -272,40 +272,46 @@ struct sk_buff *tcp_gro_lookup(struct li
38 return NULL;
39 }
40
41 -struct sk_buff *tcp_gro_receive(struct list_head *head, struct sk_buff *skb)
42 +struct tcphdr *tcp_gro_pull_header(struct sk_buff *skb)
43 {
44 - struct sk_buff *pp = NULL;
45 - struct sk_buff *p;
46 + unsigned int thlen, hlen, off;
47 struct tcphdr *th;
48 - struct tcphdr *th2;
49 - unsigned int len;
50 - unsigned int thlen;
51 - __be32 flags;
52 - unsigned int mss = 1;
53 - unsigned int hlen;
54 - unsigned int off;
55 - int flush = 1;
56 - int i;
57
58 off = skb_gro_offset(skb);
59 hlen = off + sizeof(*th);
60 th = skb_gro_header(skb, hlen, off);
61 if (unlikely(!th))
62 - goto out;
63 + return NULL;
64
65 thlen = th->doff * 4;
66 if (thlen < sizeof(*th))
67 - goto out;
68 + return NULL;
69
70 hlen = off + thlen;
71 if (skb_gro_header_hard(skb, hlen)) {
72 th = skb_gro_header_slow(skb, hlen, off);
73 if (unlikely(!th))
74 - goto out;
75 + return NULL;
76 }
77
78 skb_gro_pull(skb, thlen);
79
80 + return th;
81 +}
82 +
83 +struct sk_buff *tcp_gro_receive(struct list_head *head, struct sk_buff *skb,
84 + struct tcphdr *th)
85 +{
86 + unsigned int thlen = th->doff * 4;
87 + struct sk_buff *pp = NULL;
88 + struct sk_buff *p;
89 + struct tcphdr *th2;
90 + unsigned int len;
91 + __be32 flags;
92 + unsigned int mss = 1;
93 + int flush = 1;
94 + int i;
95 +
96 len = skb_gro_len(skb);
97 flags = tcp_flag_word(th);
98
99 @@ -384,7 +390,6 @@ out_check_final:
100 if (p && (!NAPI_GRO_CB(skb)->same_flow || flush))
101 pp = p;
102
103 -out:
104 NAPI_GRO_CB(skb)->flush |= (flush != 0);
105
106 return pp;
107 @@ -411,15 +416,23 @@ EXPORT_SYMBOL(tcp_gro_complete);
108 INDIRECT_CALLABLE_SCOPE
109 struct sk_buff *tcp4_gro_receive(struct list_head *head, struct sk_buff *skb)
110 {
111 + struct tcphdr *th;
112 +
113 /* Don't bother verifying checksum if we're going to flush anyway. */
114 if (!NAPI_GRO_CB(skb)->flush &&
115 skb_gro_checksum_validate(skb, IPPROTO_TCP,
116 - inet_gro_compute_pseudo)) {
117 - NAPI_GRO_CB(skb)->flush = 1;
118 - return NULL;
119 - }
120 + inet_gro_compute_pseudo))
121 + goto flush;
122
123 - return tcp_gro_receive(head, skb);
124 + th = tcp_gro_pull_header(skb);
125 + if (!th)
126 + goto flush;
127 +
128 + return tcp_gro_receive(head, skb, th);
129 +
130 +flush:
131 + NAPI_GRO_CB(skb)->flush = 1;
132 + return NULL;
133 }
134
135 INDIRECT_CALLABLE_SCOPE int tcp4_gro_complete(struct sk_buff *skb, int thoff)
136 --- a/net/ipv6/tcpv6_offload.c
137 +++ b/net/ipv6/tcpv6_offload.c
138 @@ -16,15 +16,23 @@
139 INDIRECT_CALLABLE_SCOPE
140 struct sk_buff *tcp6_gro_receive(struct list_head *head, struct sk_buff *skb)
141 {
142 + struct tcphdr *th;
143 +
144 /* Don't bother verifying checksum if we're going to flush anyway. */
145 if (!NAPI_GRO_CB(skb)->flush &&
146 skb_gro_checksum_validate(skb, IPPROTO_TCP,
147 - ip6_gro_compute_pseudo)) {
148 - NAPI_GRO_CB(skb)->flush = 1;
149 - return NULL;
150 - }
151 + ip6_gro_compute_pseudo))
152 + goto flush;
153 +
154 + th = tcp_gro_pull_header(skb);
155 + if (!th)
156 + goto flush;
157 +
158 + return tcp_gro_receive(head, skb, th);
159
160 - return tcp_gro_receive(head, skb);
161 +flush:
162 + NAPI_GRO_CB(skb)->flush = 1;
163 + return NULL;
164 }
165
166 INDIRECT_CALLABLE_SCOPE int tcp6_gro_complete(struct sk_buff *skb, int thoff)