hc
2024-01-05 071106ecf68c401173c58808b1cf5f68cc50d390
kernel/include/net/udp.h
....@@ -1,3 +1,4 @@
1
+/* SPDX-License-Identifier: GPL-2.0-or-later */
12 /*
23 * INET An implementation of the TCP/IP protocol suite for the LINUX
34 * operating system. INET is implemented using the BSD Socket
....@@ -13,11 +14,6 @@
1314 * Fixes:
1415 * Alan Cox : Turned on udp checksums. I don't want to
1516 * chase 'memory corruption' bugs that aren't!
16
- *
17
- * This program is free software; you can redistribute it and/or
18
- * modify it under the terms of the GNU General Public License
19
- * as published by the Free Software Foundation; either version
20
- * 2 of the License, or (at your option) any later version.
2117 */
2218 #ifndef _UDP_H
2319 #define _UDP_H
....@@ -31,6 +27,7 @@
3127 #include <linux/ipv6.h>
3228 #include <linux/seq_file.h>
3329 #include <linux/poll.h>
30
+#include <linux/indirect_call_wrapper.h>
3431
3532 /**
3633 * struct udp_skb_cb - UDP(-Lite) private variables
....@@ -170,12 +167,19 @@
170167 typedef struct sock *(*udp_lookup_t)(struct sk_buff *skb, __be16 sport,
171168 __be16 dport);
172169
170
+INDIRECT_CALLABLE_DECLARE(struct sk_buff *udp4_gro_receive(struct list_head *,
171
+ struct sk_buff *));
172
+INDIRECT_CALLABLE_DECLARE(int udp4_gro_complete(struct sk_buff *, int));
173
+INDIRECT_CALLABLE_DECLARE(struct sk_buff *udp6_gro_receive(struct list_head *,
174
+ struct sk_buff *));
175
+INDIRECT_CALLABLE_DECLARE(int udp6_gro_complete(struct sk_buff *, int));
173176 struct sk_buff *udp_gro_receive(struct list_head *head, struct sk_buff *skb,
174
- struct udphdr *uh, udp_lookup_t lookup);
177
+ struct udphdr *uh, struct sock *sk);
175178 int udp_gro_complete(struct sk_buff *skb, int nhoff, udp_lookup_t lookup);
179
+void udp_v6_early_demux(struct sk_buff *skb);
176180
177181 struct sk_buff *__udp_gso_segment(struct sk_buff *gso_skb,
178
- netdev_features_t features);
182
+ netdev_features_t features, bool is_ipv6);
179183
180184 static inline struct udphdr *udp_gro_udphdr(struct sk_buff *skb)
181185 {
....@@ -252,19 +256,30 @@
252256 return sk_rmem_alloc_get(sk) - READ_ONCE(udp_sk(sk)->forward_deficit);
253257 }
254258
259
+static inline bool udp_sk_bound_dev_eq(struct net *net, int bound_dev_if,
260
+ int dif, int sdif)
261
+{
262
+#if IS_ENABLED(CONFIG_NET_L3_MASTER_DEV)
263
+ return inet_bound_dev_eq(!!READ_ONCE(net->ipv4.sysctl_udp_l3mdev_accept),
264
+ bound_dev_if, dif, sdif);
265
+#else
266
+ return inet_bound_dev_eq(true, bound_dev_if, dif, sdif);
267
+#endif
268
+}
269
+
255270 /* net/ipv4/udp.c */
256
-void udp_destruct_sock(struct sock *sk);
271
+void udp_destruct_common(struct sock *sk);
257272 void skb_consume_udp(struct sock *sk, struct sk_buff *skb, int len);
258273 int __udp_enqueue_schedule_skb(struct sock *sk, struct sk_buff *skb);
259274 void udp_skb_destructor(struct sock *sk, struct sk_buff *skb);
260275 struct sk_buff *__skb_recv_udp(struct sock *sk, unsigned int flags,
261
- int noblock, int *peeked, int *off, int *err);
276
+ int noblock, int *off, int *err);
262277 static inline struct sk_buff *skb_recv_udp(struct sock *sk, unsigned int flags,
263278 int noblock, int *err)
264279 {
265
- int peeked, off = 0;
280
+ int off = 0;
266281
267
- return __skb_recv_udp(sk, flags, noblock, &peeked, &off, err);
282
+ return __skb_recv_udp(sk, flags, noblock, &off, err);
268283 }
269284
270285 int udp_v4_early_demux(struct sk_buff *skb);
....@@ -272,7 +287,7 @@
272287 int udp_get_port(struct sock *sk, unsigned short snum,
273288 int (*saddr_cmp)(const struct sock *,
274289 const struct sock *));
275
-void udp_err(struct sk_buff *, u32);
290
+int udp_err(struct sk_buff *, u32);
276291 int udp_abort(struct sock *sk, int err);
277292 int udp_sendmsg(struct sock *sk, struct msghdr *msg, size_t len);
278293 int udp_push_pending_frames(struct sock *sk);
....@@ -292,7 +307,7 @@
292307 int udp_lib_getsockopt(struct sock *sk, int level, int optname,
293308 char __user *optval, int __user *optlen);
294309 int udp_lib_setsockopt(struct sock *sk, int level, int optname,
295
- char __user *optval, unsigned int optlen,
310
+ sockptr_t optval, unsigned int optlen,
296311 int (*push_pending_frames)(struct sock *));
297312 struct sock *udp4_lib_lookup(struct net *net, __be32 saddr, __be16 sport,
298313 __be32 daddr, __be16 dport, int dif);
....@@ -406,16 +421,23 @@
406421 } while(0)
407422
408423 #if IS_ENABLED(CONFIG_IPV6)
409
-#define __UDPX_INC_STATS(sk, field) \
410
-do { \
411
- if ((sk)->sk_family == AF_INET) \
412
- __UDP_INC_STATS(sock_net(sk), field, 0); \
413
- else \
414
- __UDP6_INC_STATS(sock_net(sk), field, 0); \
415
-} while (0)
424
+#define __UDPX_MIB(sk, ipv4) \
425
+({ \
426
+ ipv4 ? (IS_UDPLITE(sk) ? sock_net(sk)->mib.udplite_statistics : \
427
+ sock_net(sk)->mib.udp_statistics) : \
428
+ (IS_UDPLITE(sk) ? sock_net(sk)->mib.udplite_stats_in6 : \
429
+ sock_net(sk)->mib.udp_stats_in6); \
430
+})
416431 #else
417
-#define __UDPX_INC_STATS(sk, field) __UDP_INC_STATS(sock_net(sk), field, 0)
432
+#define __UDPX_MIB(sk, ipv4) \
433
+({ \
434
+ IS_UDPLITE(sk) ? sock_net(sk)->mib.udplite_statistics : \
435
+ sock_net(sk)->mib.udp_statistics; \
436
+})
418437 #endif
438
+
439
+#define __UDPX_INC_STATS(sk, field) \
440
+ __SNMP_INC_STATS(__UDPX_MIB(sk, (sk)->sk_family == AF_INET), field)
419441
420442 #ifdef CONFIG_PROC_FS
421443 struct udp_seq_afinfo {
....@@ -426,6 +448,7 @@
426448 struct udp_iter_state {
427449 struct seq_net_private p;
428450 int bucket;
451
+ struct udp_seq_afinfo *bpf_seq_afinfo;
429452 };
430453
431454 void *udp_seq_start(struct seq_file *seq, loff_t *pos);
....@@ -443,9 +466,57 @@
443466
444467 void udp_init(void);
445468
469
+DECLARE_STATIC_KEY_FALSE(udp_encap_needed_key);
446470 void udp_encap_enable(void);
471
+void udp_encap_disable(void);
447472 #if IS_ENABLED(CONFIG_IPV6)
473
+DECLARE_STATIC_KEY_FALSE(udpv6_encap_needed_key);
448474 void udpv6_encap_enable(void);
449475 #endif
450476
477
+static inline struct sk_buff *udp_rcv_segment(struct sock *sk,
478
+ struct sk_buff *skb, bool ipv4)
479
+{
480
+ netdev_features_t features = NETIF_F_SG;
481
+ struct sk_buff *segs;
482
+
483
+ /* Avoid csum recalculation by skb_segment unless userspace explicitly
484
+ * asks for the final checksum values
485
+ */
486
+ if (!inet_get_convert_csum(sk))
487
+ features |= NETIF_F_IP_CSUM | NETIF_F_IPV6_CSUM;
488
+
489
+ /* UDP segmentation expects packets of type CHECKSUM_PARTIAL or
490
+ * CHECKSUM_NONE in __udp_gso_segment. UDP GRO indeed builds partial
491
+ * packets in udp_gro_complete_segment. As does UDP GSO, verified by
492
+ * udp_send_skb. But when those packets are looped in dev_loopback_xmit
493
+ * their ip_summed CHECKSUM_NONE is changed to CHECKSUM_UNNECESSARY.
494
+ * Reset in this specific case, where PARTIAL is both correct and
495
+ * required.
496
+ */
497
+ if (skb->pkt_type == PACKET_LOOPBACK)
498
+ skb->ip_summed = CHECKSUM_PARTIAL;
499
+
500
+ /* the GSO CB lays after the UDP one, no need to save and restore any
501
+ * CB fragment
502
+ */
503
+ segs = __skb_gso_segment(skb, features, false);
504
+ if (IS_ERR_OR_NULL(segs)) {
505
+ int segs_nr = skb_shinfo(skb)->gso_segs;
506
+
507
+ atomic_add(segs_nr, &sk->sk_drops);
508
+ SNMP_ADD_STATS(__UDPX_MIB(sk, ipv4), UDP_MIB_INERRORS, segs_nr);
509
+ kfree_skb(skb);
510
+ return NULL;
511
+ }
512
+
513
+ consume_skb(skb);
514
+ return segs;
515
+}
516
+
517
+#ifdef CONFIG_BPF_STREAM_PARSER
518
+struct sk_psock;
519
+struct proto *udp_bpf_get_proto(struct sock *sk, struct sk_psock *psock);
520
+#endif /* BPF_STREAM_PARSER */
521
+
451522 #endif /* _UDP_H */