summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorFlorian Westphal <fw@strlen.de>2019-03-29 16:16:31 -0400
committerSteffen Klassert <steffen.klassert@secunet.com>2019-04-08 03:15:17 -0400
commit4c145dce26013763490df88f2473714f5bc7857d (patch)
tree4c04664251930847a954536f24e0a5f9bcb08768
parent733a5fac2f15b55b9059230d098ed04341d2d884 (diff)
xfrm: make xfrm modes builtin
after previous changes, xfrm_mode contains no function pointers anymore and all modules defining such struct contain no code except an init/exit functions to register the xfrm_mode struct with the xfrm core. Just place the xfrm modes core and remove the modules, the run-time xfrm_mode register/unregister functionality is removed. Before: text data bss dec filename 7523 200 2364 10087 net/xfrm/xfrm_input.o 40003 628 440 41071 net/xfrm/xfrm_state.o 15730338 6937080 4046908 26714326 vmlinux 7389 200 2364 9953 net/xfrm/xfrm_input.o 40574 656 440 41670 net/xfrm/xfrm_state.o 15730084 6937068 4046908 26714060 vmlinux The xfrm*_mode_{transport,tunnel,beet} modules are gone. v2: replace CONFIG_INET6_XFRM_MODE_* IS_ENABLED guards with CONFIG_IPV6 ones rather than removing them. Signed-off-by: Florian Westphal <fw@strlen.de> Reviewed-by: Sabrina Dubroca <sd@queasysnail.net> Signed-off-by: Steffen Klassert <steffen.klassert@secunet.com>
-rw-r--r--include/net/xfrm.h13
-rw-r--r--net/ipv4/Kconfig29
-rw-r--r--net/ipv4/Makefile3
-rw-r--r--net/ipv4/ip_vti.c2
-rw-r--r--net/ipv4/xfrm4_mode_beet.c41
-rw-r--r--net/ipv4/xfrm4_mode_transport.c36
-rw-r--r--net/ipv4/xfrm4_mode_tunnel.c38
-rw-r--r--net/ipv6/Kconfig35
-rw-r--r--net/ipv6/Makefile4
-rw-r--r--net/ipv6/ip6_vti.c2
-rw-r--r--net/ipv6/xfrm6_mode_beet.c42
-rw-r--r--net/ipv6/xfrm6_mode_ro.c55
-rw-r--r--net/ipv6/xfrm6_mode_transport.c37
-rw-r--r--net/ipv6/xfrm6_mode_tunnel.c45
-rw-r--r--net/xfrm/xfrm_input.c13
-rw-r--r--net/xfrm/xfrm_interface.c2
-rw-r--r--net/xfrm/xfrm_output.c15
-rw-r--r--net/xfrm/xfrm_policy.c2
-rw-r--r--net/xfrm/xfrm_state.c158
-rw-r--r--tools/testing/selftests/net/config2
20 files changed, 81 insertions, 493 deletions
diff --git a/include/net/xfrm.h b/include/net/xfrm.h
index 8d1c9506bcf6..4ca79cdc3460 100644
--- a/include/net/xfrm.h
+++ b/include/net/xfrm.h
@@ -234,9 +234,9 @@ struct xfrm_state {
234 /* Reference to data common to all the instances of this 234 /* Reference to data common to all the instances of this
235 * transformer. */ 235 * transformer. */
236 const struct xfrm_type *type; 236 const struct xfrm_type *type;
237 struct xfrm_mode *inner_mode; 237 const struct xfrm_mode *inner_mode;
238 struct xfrm_mode *inner_mode_iaf; 238 const struct xfrm_mode *inner_mode_iaf;
239 struct xfrm_mode *outer_mode; 239 const struct xfrm_mode *outer_mode;
240 240
241 const struct xfrm_type_offload *type_offload; 241 const struct xfrm_type_offload *type_offload;
242 242
@@ -347,7 +347,6 @@ struct xfrm_state_afinfo {
347 struct module *owner; 347 struct module *owner;
348 const struct xfrm_type *type_map[IPPROTO_MAX]; 348 const struct xfrm_type *type_map[IPPROTO_MAX];
349 const struct xfrm_type_offload *type_offload_map[IPPROTO_MAX]; 349 const struct xfrm_type_offload *type_offload_map[IPPROTO_MAX];
350 struct xfrm_mode *mode_map[XFRM_MODE_MAX];
351 350
352 int (*init_flags)(struct xfrm_state *x); 351 int (*init_flags)(struct xfrm_state *x);
353 void (*init_tempsel)(struct xfrm_selector *sel, 352 void (*init_tempsel)(struct xfrm_selector *sel,
@@ -423,7 +422,6 @@ int xfrm_register_type_offload(const struct xfrm_type_offload *type, unsigned sh
423int xfrm_unregister_type_offload(const struct xfrm_type_offload *type, unsigned short family); 422int xfrm_unregister_type_offload(const struct xfrm_type_offload *type, unsigned short family);
424 423
425struct xfrm_mode { 424struct xfrm_mode {
426 struct module *owner;
427 u8 encap; 425 u8 encap;
428 u8 family; 426 u8 family;
429 u8 flags; 427 u8 flags;
@@ -434,9 +432,6 @@ enum {
434 XFRM_MODE_FLAG_TUNNEL = 1, 432 XFRM_MODE_FLAG_TUNNEL = 1,
435}; 433};
436 434
437int xfrm_register_mode(struct xfrm_mode *mode);
438void xfrm_unregister_mode(struct xfrm_mode *mode);
439
440static inline int xfrm_af2proto(unsigned int family) 435static inline int xfrm_af2proto(unsigned int family)
441{ 436{
442 switch(family) { 437 switch(family) {
@@ -449,7 +444,7 @@ static inline int xfrm_af2proto(unsigned int family)
449 } 444 }
450} 445}
451 446
452static inline struct xfrm_mode *xfrm_ip2inner_mode(struct xfrm_state *x, int ipproto) 447static inline const struct xfrm_mode *xfrm_ip2inner_mode(struct xfrm_state *x, int ipproto)
453{ 448{
454 if ((ipproto == IPPROTO_IPIP && x->props.family == AF_INET) || 449 if ((ipproto == IPPROTO_IPIP && x->props.family == AF_INET) ||
455 (ipproto == IPPROTO_IPV6 && x->props.family == AF_INET6)) 450 (ipproto == IPPROTO_IPV6 && x->props.family == AF_INET6))
diff --git a/net/ipv4/Kconfig b/net/ipv4/Kconfig
index 32cae39cdff6..8108e97d4285 100644
--- a/net/ipv4/Kconfig
+++ b/net/ipv4/Kconfig
@@ -304,7 +304,7 @@ config NET_IPVTI
304 tristate "Virtual (secure) IP: tunneling" 304 tristate "Virtual (secure) IP: tunneling"
305 select INET_TUNNEL 305 select INET_TUNNEL
306 select NET_IP_TUNNEL 306 select NET_IP_TUNNEL
307 depends on INET_XFRM_MODE_TUNNEL 307 select XFRM
308 ---help--- 308 ---help---
309 Tunneling means encapsulating data of one protocol type within 309 Tunneling means encapsulating data of one protocol type within
310 another protocol and sending it over a channel that understands the 310 another protocol and sending it over a channel that understands the
@@ -396,33 +396,6 @@ config INET_TUNNEL
396 tristate 396 tristate
397 default n 397 default n
398 398
399config INET_XFRM_MODE_TRANSPORT
400 tristate "IP: IPsec transport mode"
401 default y
402 select XFRM
403 ---help---
404 Support for IPsec transport mode.
405
406 If unsure, say Y.
407
408config INET_XFRM_MODE_TUNNEL
409 tristate "IP: IPsec tunnel mode"
410 default y
411 select XFRM
412 ---help---
413 Support for IPsec tunnel mode.
414
415 If unsure, say Y.
416
417config INET_XFRM_MODE_BEET
418 tristate "IP: IPsec BEET mode"
419 default y
420 select XFRM
421 ---help---
422 Support for IPsec BEET mode.
423
424 If unsure, say Y.
425
426config INET_DIAG 399config INET_DIAG
427 tristate "INET: socket monitoring interface" 400 tristate "INET: socket monitoring interface"
428 default y 401 default y
diff --git a/net/ipv4/Makefile b/net/ipv4/Makefile
index 58629314eae9..000a61994c8f 100644
--- a/net/ipv4/Makefile
+++ b/net/ipv4/Makefile
@@ -37,10 +37,7 @@ obj-$(CONFIG_INET_ESP) += esp4.o
37obj-$(CONFIG_INET_ESP_OFFLOAD) += esp4_offload.o 37obj-$(CONFIG_INET_ESP_OFFLOAD) += esp4_offload.o
38obj-$(CONFIG_INET_IPCOMP) += ipcomp.o 38obj-$(CONFIG_INET_IPCOMP) += ipcomp.o
39obj-$(CONFIG_INET_XFRM_TUNNEL) += xfrm4_tunnel.o 39obj-$(CONFIG_INET_XFRM_TUNNEL) += xfrm4_tunnel.o
40obj-$(CONFIG_INET_XFRM_MODE_BEET) += xfrm4_mode_beet.o
41obj-$(CONFIG_INET_TUNNEL) += tunnel4.o 40obj-$(CONFIG_INET_TUNNEL) += tunnel4.o
42obj-$(CONFIG_INET_XFRM_MODE_TRANSPORT) += xfrm4_mode_transport.o
43obj-$(CONFIG_INET_XFRM_MODE_TUNNEL) += xfrm4_mode_tunnel.o
44obj-$(CONFIG_IP_PNP) += ipconfig.o 41obj-$(CONFIG_IP_PNP) += ipconfig.o
45obj-$(CONFIG_NETFILTER) += netfilter.o netfilter/ 42obj-$(CONFIG_NETFILTER) += netfilter.o netfilter/
46obj-$(CONFIG_INET_DIAG) += inet_diag.o 43obj-$(CONFIG_INET_DIAG) += inet_diag.o
diff --git a/net/ipv4/ip_vti.c b/net/ipv4/ip_vti.c
index 3f3f6d6be318..91926c9a3bc9 100644
--- a/net/ipv4/ip_vti.c
+++ b/net/ipv4/ip_vti.c
@@ -107,7 +107,7 @@ static int vti_rcv_cb(struct sk_buff *skb, int err)
107 struct net_device *dev; 107 struct net_device *dev;
108 struct pcpu_sw_netstats *tstats; 108 struct pcpu_sw_netstats *tstats;
109 struct xfrm_state *x; 109 struct xfrm_state *x;
110 struct xfrm_mode *inner_mode; 110 const struct xfrm_mode *inner_mode;
111 struct ip_tunnel *tunnel = XFRM_TUNNEL_SKB_CB(skb)->tunnel.ip4; 111 struct ip_tunnel *tunnel = XFRM_TUNNEL_SKB_CB(skb)->tunnel.ip4;
112 u32 orig_mark = skb->mark; 112 u32 orig_mark = skb->mark;
113 int ret; 113 int ret;
diff --git a/net/ipv4/xfrm4_mode_beet.c b/net/ipv4/xfrm4_mode_beet.c
deleted file mode 100644
index ba84b278e627..000000000000
--- a/net/ipv4/xfrm4_mode_beet.c
+++ /dev/null
@@ -1,41 +0,0 @@
1/*
2 * xfrm4_mode_beet.c - BEET mode encapsulation for IPv4.
3 *
4 * Copyright (c) 2006 Diego Beltrami <diego.beltrami@gmail.com>
5 * Miika Komu <miika@iki.fi>
6 * Herbert Xu <herbert@gondor.apana.org.au>
7 * Abhinav Pathak <abhinav.pathak@hiit.fi>
8 * Jeff Ahrenholz <ahrenholz@gmail.com>
9 */
10
11#include <linux/init.h>
12#include <linux/kernel.h>
13#include <linux/module.h>
14#include <linux/skbuff.h>
15#include <linux/stringify.h>
16#include <net/dst.h>
17#include <net/ip.h>
18#include <net/xfrm.h>
19
20
21static struct xfrm_mode xfrm4_beet_mode = {
22 .owner = THIS_MODULE,
23 .encap = XFRM_MODE_BEET,
24 .flags = XFRM_MODE_FLAG_TUNNEL,
25 .family = AF_INET,
26};
27
28static int __init xfrm4_beet_init(void)
29{
30 return xfrm_register_mode(&xfrm4_beet_mode);
31}
32
33static void __exit xfrm4_beet_exit(void)
34{
35 xfrm_unregister_mode(&xfrm4_beet_mode);
36}
37
38module_init(xfrm4_beet_init);
39module_exit(xfrm4_beet_exit);
40MODULE_LICENSE("GPL");
41MODULE_ALIAS_XFRM_MODE(AF_INET, XFRM_MODE_BEET);
diff --git a/net/ipv4/xfrm4_mode_transport.c b/net/ipv4/xfrm4_mode_transport.c
deleted file mode 100644
index 397863ea762b..000000000000
--- a/net/ipv4/xfrm4_mode_transport.c
+++ /dev/null
@@ -1,36 +0,0 @@
1/*
2 * xfrm4_mode_transport.c - Transport mode encapsulation for IPv4.
3 *
4 * Copyright (c) 2004-2006 Herbert Xu <herbert@gondor.apana.org.au>
5 */
6
7#include <linux/init.h>
8#include <linux/kernel.h>
9#include <linux/module.h>
10#include <linux/skbuff.h>
11#include <linux/stringify.h>
12#include <net/dst.h>
13#include <net/ip.h>
14#include <net/xfrm.h>
15#include <net/protocol.h>
16
17static struct xfrm_mode xfrm4_transport_mode = {
18 .owner = THIS_MODULE,
19 .encap = XFRM_MODE_TRANSPORT,
20 .family = AF_INET,
21};
22
23static int __init xfrm4_transport_init(void)
24{
25 return xfrm_register_mode(&xfrm4_transport_mode);
26}
27
28static void __exit xfrm4_transport_exit(void)
29{
30 xfrm_unregister_mode(&xfrm4_transport_mode);
31}
32
33module_init(xfrm4_transport_init);
34module_exit(xfrm4_transport_exit);
35MODULE_LICENSE("GPL");
36MODULE_ALIAS_XFRM_MODE(AF_INET, XFRM_MODE_TRANSPORT);
diff --git a/net/ipv4/xfrm4_mode_tunnel.c b/net/ipv4/xfrm4_mode_tunnel.c
deleted file mode 100644
index b2b132c800fc..000000000000
--- a/net/ipv4/xfrm4_mode_tunnel.c
+++ /dev/null
@@ -1,38 +0,0 @@
1/*
2 * xfrm4_mode_tunnel.c - Tunnel mode encapsulation for IPv4.
3 *
4 * Copyright (c) 2004-2006 Herbert Xu <herbert@gondor.apana.org.au>
5 */
6
7#include <linux/gfp.h>
8#include <linux/init.h>
9#include <linux/kernel.h>
10#include <linux/module.h>
11#include <linux/skbuff.h>
12#include <linux/stringify.h>
13#include <net/dst.h>
14#include <net/inet_ecn.h>
15#include <net/ip.h>
16#include <net/xfrm.h>
17
18static struct xfrm_mode xfrm4_tunnel_mode = {
19 .owner = THIS_MODULE,
20 .encap = XFRM_MODE_TUNNEL,
21 .flags = XFRM_MODE_FLAG_TUNNEL,
22 .family = AF_INET,
23};
24
25static int __init xfrm4_mode_tunnel_init(void)
26{
27 return xfrm_register_mode(&xfrm4_tunnel_mode);
28}
29
30static void __exit xfrm4_mode_tunnel_exit(void)
31{
32 xfrm_unregister_mode(&xfrm4_tunnel_mode);
33}
34
35module_init(xfrm4_mode_tunnel_init);
36module_exit(xfrm4_mode_tunnel_exit);
37MODULE_LICENSE("GPL");
38MODULE_ALIAS_XFRM_MODE(AF_INET, XFRM_MODE_TUNNEL);
diff --git a/net/ipv6/Kconfig b/net/ipv6/Kconfig
index 613282c65a10..cd915e332c98 100644
--- a/net/ipv6/Kconfig
+++ b/net/ipv6/Kconfig
@@ -135,44 +135,11 @@ config INET6_TUNNEL
135 tristate 135 tristate
136 default n 136 default n
137 137
138config INET6_XFRM_MODE_TRANSPORT
139 tristate "IPv6: IPsec transport mode"
140 default IPV6
141 select XFRM
142 ---help---
143 Support for IPsec transport mode.
144
145 If unsure, say Y.
146
147config INET6_XFRM_MODE_TUNNEL
148 tristate "IPv6: IPsec tunnel mode"
149 default IPV6
150 select XFRM
151 ---help---
152 Support for IPsec tunnel mode.
153
154 If unsure, say Y.
155
156config INET6_XFRM_MODE_BEET
157 tristate "IPv6: IPsec BEET mode"
158 default IPV6
159 select XFRM
160 ---help---
161 Support for IPsec BEET mode.
162
163 If unsure, say Y.
164
165config INET6_XFRM_MODE_ROUTEOPTIMIZATION
166 tristate "IPv6: MIPv6 route optimization mode"
167 select XFRM
168 ---help---
169 Support for MIPv6 route optimization mode.
170
171config IPV6_VTI 138config IPV6_VTI
172tristate "Virtual (secure) IPv6: tunneling" 139tristate "Virtual (secure) IPv6: tunneling"
173 select IPV6_TUNNEL 140 select IPV6_TUNNEL
174 select NET_IP_TUNNEL 141 select NET_IP_TUNNEL
175 depends on INET6_XFRM_MODE_TUNNEL 142 select XFRM
176 ---help--- 143 ---help---
177 Tunneling means encapsulating data of one protocol type within 144 Tunneling means encapsulating data of one protocol type within
178 another protocol and sending it over a channel that understands the 145 another protocol and sending it over a channel that understands the
diff --git a/net/ipv6/Makefile b/net/ipv6/Makefile
index e0026fa1261b..8ccf35514015 100644
--- a/net/ipv6/Makefile
+++ b/net/ipv6/Makefile
@@ -35,10 +35,6 @@ obj-$(CONFIG_INET6_ESP_OFFLOAD) += esp6_offload.o
35obj-$(CONFIG_INET6_IPCOMP) += ipcomp6.o 35obj-$(CONFIG_INET6_IPCOMP) += ipcomp6.o
36obj-$(CONFIG_INET6_XFRM_TUNNEL) += xfrm6_tunnel.o 36obj-$(CONFIG_INET6_XFRM_TUNNEL) += xfrm6_tunnel.o
37obj-$(CONFIG_INET6_TUNNEL) += tunnel6.o 37obj-$(CONFIG_INET6_TUNNEL) += tunnel6.o
38obj-$(CONFIG_INET6_XFRM_MODE_TRANSPORT) += xfrm6_mode_transport.o
39obj-$(CONFIG_INET6_XFRM_MODE_TUNNEL) += xfrm6_mode_tunnel.o
40obj-$(CONFIG_INET6_XFRM_MODE_ROUTEOPTIMIZATION) += xfrm6_mode_ro.o
41obj-$(CONFIG_INET6_XFRM_MODE_BEET) += xfrm6_mode_beet.o
42obj-$(CONFIG_IPV6_MIP6) += mip6.o 38obj-$(CONFIG_IPV6_MIP6) += mip6.o
43obj-$(CONFIG_IPV6_ILA) += ila/ 39obj-$(CONFIG_IPV6_ILA) += ila/
44obj-$(CONFIG_NETFILTER) += netfilter/ 40obj-$(CONFIG_NETFILTER) += netfilter/
diff --git a/net/ipv6/ip6_vti.c b/net/ipv6/ip6_vti.c
index 369803c581b7..71ec5e60cf8f 100644
--- a/net/ipv6/ip6_vti.c
+++ b/net/ipv6/ip6_vti.c
@@ -342,7 +342,7 @@ static int vti6_rcv_cb(struct sk_buff *skb, int err)
342 struct net_device *dev; 342 struct net_device *dev;
343 struct pcpu_sw_netstats *tstats; 343 struct pcpu_sw_netstats *tstats;
344 struct xfrm_state *x; 344 struct xfrm_state *x;
345 struct xfrm_mode *inner_mode; 345 const struct xfrm_mode *inner_mode;
346 struct ip6_tnl *t = XFRM_TUNNEL_SKB_CB(skb)->tunnel.ip6; 346 struct ip6_tnl *t = XFRM_TUNNEL_SKB_CB(skb)->tunnel.ip6;
347 u32 orig_mark = skb->mark; 347 u32 orig_mark = skb->mark;
348 int ret; 348 int ret;
diff --git a/net/ipv6/xfrm6_mode_beet.c b/net/ipv6/xfrm6_mode_beet.c
deleted file mode 100644
index 1c4a76bdd889..000000000000
--- a/net/ipv6/xfrm6_mode_beet.c
+++ /dev/null
@@ -1,42 +0,0 @@
1/*
2 * xfrm6_mode_beet.c - BEET mode encapsulation for IPv6.
3 *
4 * Copyright (c) 2006 Diego Beltrami <diego.beltrami@gmail.com>
5 * Miika Komu <miika@iki.fi>
6 * Herbert Xu <herbert@gondor.apana.org.au>
7 * Abhinav Pathak <abhinav.pathak@hiit.fi>
8 * Jeff Ahrenholz <ahrenholz@gmail.com>
9 */
10
11#include <linux/init.h>
12#include <linux/kernel.h>
13#include <linux/module.h>
14#include <linux/skbuff.h>
15#include <linux/stringify.h>
16#include <net/dsfield.h>
17#include <net/dst.h>
18#include <net/inet_ecn.h>
19#include <net/ipv6.h>
20#include <net/xfrm.h>
21
22static struct xfrm_mode xfrm6_beet_mode = {
23 .owner = THIS_MODULE,
24 .encap = XFRM_MODE_BEET,
25 .flags = XFRM_MODE_FLAG_TUNNEL,
26 .family = AF_INET6,
27};
28
29static int __init xfrm6_beet_init(void)
30{
31 return xfrm_register_mode(&xfrm6_beet_mode);
32}
33
34static void __exit xfrm6_beet_exit(void)
35{
36 xfrm_unregister_mode(&xfrm6_beet_mode);
37}
38
39module_init(xfrm6_beet_init);
40module_exit(xfrm6_beet_exit);
41MODULE_LICENSE("GPL");
42MODULE_ALIAS_XFRM_MODE(AF_INET6, XFRM_MODE_BEET);
diff --git a/net/ipv6/xfrm6_mode_ro.c b/net/ipv6/xfrm6_mode_ro.c
deleted file mode 100644
index d0a6a4dbd689..000000000000
--- a/net/ipv6/xfrm6_mode_ro.c
+++ /dev/null
@@ -1,55 +0,0 @@
1/*
2 * xfrm6_mode_ro.c - Route optimization mode for IPv6.
3 *
4 * Copyright (C)2003-2006 Helsinki University of Technology
5 * Copyright (C)2003-2006 USAGI/WIDE Project
6 *
7 * This program is free software; you can redistribute it and/or modify
8 * it under the terms of the GNU General Public License as published by
9 * the Free Software Foundation; either version 2 of the License, or
10 * (at your option) any later version.
11 *
12 * This program is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 * GNU General Public License for more details.
16 *
17 * You should have received a copy of the GNU General Public License
18 * along with this program; if not, see <http://www.gnu.org/licenses/>.
19 */
20/*
21 * Authors:
22 * Noriaki TAKAMIYA @USAGI
23 * Masahide NAKAMURA @USAGI
24 */
25
26#include <linux/init.h>
27#include <linux/kernel.h>
28#include <linux/module.h>
29#include <linux/skbuff.h>
30#include <linux/spinlock.h>
31#include <linux/stringify.h>
32#include <linux/time.h>
33#include <net/ipv6.h>
34#include <net/xfrm.h>
35
36static struct xfrm_mode xfrm6_ro_mode = {
37 .owner = THIS_MODULE,
38 .encap = XFRM_MODE_ROUTEOPTIMIZATION,
39 .family = AF_INET6,
40};
41
42static int __init xfrm6_ro_init(void)
43{
44 return xfrm_register_mode(&xfrm6_ro_mode);
45}
46
47static void __exit xfrm6_ro_exit(void)
48{
49 xfrm_unregister_mode(&xfrm6_ro_mode);
50}
51
52module_init(xfrm6_ro_init);
53module_exit(xfrm6_ro_exit);
54MODULE_LICENSE("GPL");
55MODULE_ALIAS_XFRM_MODE(AF_INET6, XFRM_MODE_ROUTEOPTIMIZATION);
diff --git a/net/ipv6/xfrm6_mode_transport.c b/net/ipv6/xfrm6_mode_transport.c
deleted file mode 100644
index d90c934c2f1a..000000000000
--- a/net/ipv6/xfrm6_mode_transport.c
+++ /dev/null
@@ -1,37 +0,0 @@
1/*
2 * xfrm6_mode_transport.c - Transport mode encapsulation for IPv6.
3 *
4 * Copyright (C) 2002 USAGI/WIDE Project
5 * Copyright (c) 2004-2006 Herbert Xu <herbert@gondor.apana.org.au>
6 */
7
8#include <linux/init.h>
9#include <linux/kernel.h>
10#include <linux/module.h>
11#include <linux/skbuff.h>
12#include <linux/stringify.h>
13#include <net/dst.h>
14#include <net/ipv6.h>
15#include <net/xfrm.h>
16#include <net/protocol.h>
17
18static struct xfrm_mode xfrm6_transport_mode = {
19 .owner = THIS_MODULE,
20 .encap = XFRM_MODE_TRANSPORT,
21 .family = AF_INET6,
22};
23
24static int __init xfrm6_transport_init(void)
25{
26 return xfrm_register_mode(&xfrm6_transport_mode);
27}
28
29static void __exit xfrm6_transport_exit(void)
30{
31 xfrm_unregister_mode(&xfrm6_transport_mode);
32}
33
34module_init(xfrm6_transport_init);
35module_exit(xfrm6_transport_exit);
36MODULE_LICENSE("GPL");
37MODULE_ALIAS_XFRM_MODE(AF_INET6, XFRM_MODE_TRANSPORT);
diff --git a/net/ipv6/xfrm6_mode_tunnel.c b/net/ipv6/xfrm6_mode_tunnel.c
deleted file mode 100644
index e5c928dd70e3..000000000000
--- a/net/ipv6/xfrm6_mode_tunnel.c
+++ /dev/null
@@ -1,45 +0,0 @@
1/*
2 * xfrm6_mode_tunnel.c - Tunnel mode encapsulation for IPv6.
3 *
4 * Copyright (C) 2002 USAGI/WIDE Project
5 * Copyright (c) 2004-2006 Herbert Xu <herbert@gondor.apana.org.au>
6 */
7
8#include <linux/gfp.h>
9#include <linux/init.h>
10#include <linux/kernel.h>
11#include <linux/module.h>
12#include <linux/skbuff.h>
13#include <linux/stringify.h>
14#include <net/dsfield.h>
15#include <net/dst.h>
16#include <net/inet_ecn.h>
17#include <net/ip6_route.h>
18#include <net/ipv6.h>
19#include <net/xfrm.h>
20
21/* Add encapsulation header.
22 *
23 * The top IP header will be constructed per RFC 2401.
24 */
25static struct xfrm_mode xfrm6_tunnel_mode = {
26 .owner = THIS_MODULE,
27 .encap = XFRM_MODE_TUNNEL,
28 .flags = XFRM_MODE_FLAG_TUNNEL,
29 .family = AF_INET6,
30};
31
32static int __init xfrm6_mode_tunnel_init(void)
33{
34 return xfrm_register_mode(&xfrm6_tunnel_mode);
35}
36
37static void __exit xfrm6_mode_tunnel_exit(void)
38{
39 xfrm_unregister_mode(&xfrm6_tunnel_mode);
40}
41
42module_init(xfrm6_mode_tunnel_init);
43module_exit(xfrm6_mode_tunnel_exit);
44MODULE_LICENSE("GPL");
45MODULE_ALIAS_XFRM_MODE(AF_INET6, XFRM_MODE_TUNNEL);
diff --git a/net/xfrm/xfrm_input.c b/net/xfrm/xfrm_input.c
index 74b53c13279b..b5a31c8e2088 100644
--- a/net/xfrm/xfrm_input.c
+++ b/net/xfrm/xfrm_input.c
@@ -351,7 +351,7 @@ xfrm_inner_mode_encap_remove(struct xfrm_state *x,
351 351
352static int xfrm_prepare_input(struct xfrm_state *x, struct sk_buff *skb) 352static int xfrm_prepare_input(struct xfrm_state *x, struct sk_buff *skb)
353{ 353{
354 struct xfrm_mode *inner_mode = x->inner_mode; 354 const struct xfrm_mode *inner_mode = x->inner_mode;
355 const struct xfrm_state_afinfo *afinfo; 355 const struct xfrm_state_afinfo *afinfo;
356 int err = -EAFNOSUPPORT; 356 int err = -EAFNOSUPPORT;
357 357
@@ -394,7 +394,6 @@ static int xfrm_prepare_input(struct xfrm_state *x, struct sk_buff *skb)
394 */ 394 */
395static int xfrm4_transport_input(struct xfrm_state *x, struct sk_buff *skb) 395static int xfrm4_transport_input(struct xfrm_state *x, struct sk_buff *skb)
396{ 396{
397#if IS_ENABLED(CONFIG_INET_XFRM_MODE_TRANSPORT)
398 int ihl = skb->data - skb_transport_header(skb); 397 int ihl = skb->data - skb_transport_header(skb);
399 398
400 if (skb->transport_header != skb->network_header) { 399 if (skb->transport_header != skb->network_header) {
@@ -405,14 +404,11 @@ static int xfrm4_transport_input(struct xfrm_state *x, struct sk_buff *skb)
405 ip_hdr(skb)->tot_len = htons(skb->len + ihl); 404 ip_hdr(skb)->tot_len = htons(skb->len + ihl);
406 skb_reset_transport_header(skb); 405 skb_reset_transport_header(skb);
407 return 0; 406 return 0;
408#else
409 return -EOPNOTSUPP;
410#endif
411} 407}
412 408
413static int xfrm6_transport_input(struct xfrm_state *x, struct sk_buff *skb) 409static int xfrm6_transport_input(struct xfrm_state *x, struct sk_buff *skb)
414{ 410{
415#if IS_ENABLED(CONFIG_INET6_XFRM_MODE_TRANSPORT) 411#if IS_ENABLED(CONFIG_IPV6)
416 int ihl = skb->data - skb_transport_header(skb); 412 int ihl = skb->data - skb_transport_header(skb);
417 413
418 if (skb->transport_header != skb->network_header) { 414 if (skb->transport_header != skb->network_header) {
@@ -425,7 +421,8 @@ static int xfrm6_transport_input(struct xfrm_state *x, struct sk_buff *skb)
425 skb_reset_transport_header(skb); 421 skb_reset_transport_header(skb);
426 return 0; 422 return 0;
427#else 423#else
428 return -EOPNOTSUPP; 424 WARN_ON_ONCE(1);
425 return -EAFNOSUPPORT;
429#endif 426#endif
430} 427}
431 428
@@ -458,12 +455,12 @@ int xfrm_input(struct sk_buff *skb, int nexthdr, __be32 spi, int encap_type)
458{ 455{
459 const struct xfrm_state_afinfo *afinfo; 456 const struct xfrm_state_afinfo *afinfo;
460 struct net *net = dev_net(skb->dev); 457 struct net *net = dev_net(skb->dev);
458 const struct xfrm_mode *inner_mode;
461 int err; 459 int err;
462 __be32 seq; 460 __be32 seq;
463 __be32 seq_hi; 461 __be32 seq_hi;
464 struct xfrm_state *x = NULL; 462 struct xfrm_state *x = NULL;
465 xfrm_address_t *daddr; 463 xfrm_address_t *daddr;
466 struct xfrm_mode *inner_mode;
467 u32 mark = skb->mark; 464 u32 mark = skb->mark;
468 unsigned int family = AF_UNSPEC; 465 unsigned int family = AF_UNSPEC;
469 int decaps = 0; 466 int decaps = 0;
diff --git a/net/xfrm/xfrm_interface.c b/net/xfrm/xfrm_interface.c
index 93efb0965e7d..4fc49dbf3edf 100644
--- a/net/xfrm/xfrm_interface.c
+++ b/net/xfrm/xfrm_interface.c
@@ -244,8 +244,8 @@ static void xfrmi_scrub_packet(struct sk_buff *skb, bool xnet)
244 244
245static int xfrmi_rcv_cb(struct sk_buff *skb, int err) 245static int xfrmi_rcv_cb(struct sk_buff *skb, int err)
246{ 246{
247 const struct xfrm_mode *inner_mode;
247 struct pcpu_sw_netstats *tstats; 248 struct pcpu_sw_netstats *tstats;
248 struct xfrm_mode *inner_mode;
249 struct net_device *dev; 249 struct net_device *dev;
250 struct xfrm_state *x; 250 struct xfrm_state *x;
251 struct xfrm_if *xi; 251 struct xfrm_if *xi;
diff --git a/net/xfrm/xfrm_output.c b/net/xfrm/xfrm_output.c
index 17c4f58d28ea..3cb2a328a8ab 100644
--- a/net/xfrm/xfrm_output.c
+++ b/net/xfrm/xfrm_output.c
@@ -61,7 +61,6 @@ static struct dst_entry *skb_dst_pop(struct sk_buff *skb)
61 */ 61 */
62static int xfrm4_transport_output(struct xfrm_state *x, struct sk_buff *skb) 62static int xfrm4_transport_output(struct xfrm_state *x, struct sk_buff *skb)
63{ 63{
64#if IS_ENABLED(CONFIG_INET_XFRM_MODE_TRANSPORT)
65 struct iphdr *iph = ip_hdr(skb); 64 struct iphdr *iph = ip_hdr(skb);
66 int ihl = iph->ihl * 4; 65 int ihl = iph->ihl * 4;
67 66
@@ -74,10 +73,6 @@ static int xfrm4_transport_output(struct xfrm_state *x, struct sk_buff *skb)
74 __skb_pull(skb, ihl); 73 __skb_pull(skb, ihl);
75 memmove(skb_network_header(skb), iph, ihl); 74 memmove(skb_network_header(skb), iph, ihl);
76 return 0; 75 return 0;
77#else
78 WARN_ON_ONCE(1);
79 return -EOPNOTSUPP;
80#endif
81} 76}
82 77
83/* Add encapsulation header. 78/* Add encapsulation header.
@@ -87,7 +82,7 @@ static int xfrm4_transport_output(struct xfrm_state *x, struct sk_buff *skb)
87 */ 82 */
88static int xfrm6_transport_output(struct xfrm_state *x, struct sk_buff *skb) 83static int xfrm6_transport_output(struct xfrm_state *x, struct sk_buff *skb)
89{ 84{
90#if IS_ENABLED(CONFIG_INET6_XFRM_MODE_TRANSPORT) 85#if IS_ENABLED(CONFIG_IPV6)
91 struct ipv6hdr *iph; 86 struct ipv6hdr *iph;
92 u8 *prevhdr; 87 u8 *prevhdr;
93 int hdr_len; 88 int hdr_len;
@@ -107,7 +102,7 @@ static int xfrm6_transport_output(struct xfrm_state *x, struct sk_buff *skb)
107 return 0; 102 return 0;
108#else 103#else
109 WARN_ON_ONCE(1); 104 WARN_ON_ONCE(1);
110 return -EOPNOTSUPP; 105 return -EAFNOSUPPORT;
111#endif 106#endif
112} 107}
113 108
@@ -118,7 +113,7 @@ static int xfrm6_transport_output(struct xfrm_state *x, struct sk_buff *skb)
118 */ 113 */
119static int xfrm6_ro_output(struct xfrm_state *x, struct sk_buff *skb) 114static int xfrm6_ro_output(struct xfrm_state *x, struct sk_buff *skb)
120{ 115{
121#if IS_ENABLED(CONFIG_INET6_XFRM_MODE_ROUTEOPTIMIZATION) 116#if IS_ENABLED(CONFIG_IPV6)
122 struct ipv6hdr *iph; 117 struct ipv6hdr *iph;
123 u8 *prevhdr; 118 u8 *prevhdr;
124 int hdr_len; 119 int hdr_len;
@@ -140,7 +135,7 @@ static int xfrm6_ro_output(struct xfrm_state *x, struct sk_buff *skb)
140 return 0; 135 return 0;
141#else 136#else
142 WARN_ON_ONCE(1); 137 WARN_ON_ONCE(1);
143 return -EOPNOTSUPP; 138 return -EAFNOSUPPORT;
144#endif 139#endif
145} 140}
146 141
@@ -624,7 +619,7 @@ EXPORT_SYMBOL_GPL(xfrm_output);
624static int xfrm_inner_extract_output(struct xfrm_state *x, struct sk_buff *skb) 619static int xfrm_inner_extract_output(struct xfrm_state *x, struct sk_buff *skb)
625{ 620{
626 const struct xfrm_state_afinfo *afinfo; 621 const struct xfrm_state_afinfo *afinfo;
627 struct xfrm_mode *inner_mode; 622 const struct xfrm_mode *inner_mode;
628 int err = -EAFNOSUPPORT; 623 int err = -EAFNOSUPPORT;
629 624
630 if (x->sel.family == AF_UNSPEC) 625 if (x->sel.family == AF_UNSPEC)
diff --git a/net/xfrm/xfrm_policy.c b/net/xfrm/xfrm_policy.c
index 67122beb116c..1a5fd2296556 100644
--- a/net/xfrm/xfrm_policy.c
+++ b/net/xfrm/xfrm_policy.c
@@ -2546,10 +2546,10 @@ static struct dst_entry *xfrm_bundle_create(struct xfrm_policy *policy,
2546 struct dst_entry *dst) 2546 struct dst_entry *dst)
2547{ 2547{
2548 const struct xfrm_state_afinfo *afinfo; 2548 const struct xfrm_state_afinfo *afinfo;
2549 const struct xfrm_mode *inner_mode;
2549 struct net *net = xp_net(policy); 2550 struct net *net = xp_net(policy);
2550 unsigned long now = jiffies; 2551 unsigned long now = jiffies;
2551 struct net_device *dev; 2552 struct net_device *dev;
2552 struct xfrm_mode *inner_mode;
2553 struct xfrm_dst *xdst_prev = NULL; 2553 struct xfrm_dst *xdst_prev = NULL;
2554 struct xfrm_dst *xdst0 = NULL; 2554 struct xfrm_dst *xdst0 = NULL;
2555 int i = 0; 2555 int i = 0;
diff --git a/net/xfrm/xfrm_state.c b/net/xfrm/xfrm_state.c
index 358b09f0d018..ace26f6dc790 100644
--- a/net/xfrm/xfrm_state.c
+++ b/net/xfrm/xfrm_state.c
@@ -330,92 +330,67 @@ static void xfrm_put_type_offload(const struct xfrm_type_offload *type)
330 module_put(type->owner); 330 module_put(type->owner);
331} 331}
332 332
333static DEFINE_SPINLOCK(xfrm_mode_lock); 333static const struct xfrm_mode xfrm4_mode_map[XFRM_MODE_MAX] = {
334int xfrm_register_mode(struct xfrm_mode *mode) 334 [XFRM_MODE_BEET] = {
335{ 335 .encap = XFRM_MODE_BEET,
336 struct xfrm_state_afinfo *afinfo; 336 .flags = XFRM_MODE_FLAG_TUNNEL,
337 struct xfrm_mode **modemap; 337 .family = AF_INET,
338 int err; 338 },
339 339 [XFRM_MODE_TRANSPORT] = {
340 if (unlikely(mode->encap >= XFRM_MODE_MAX)) 340 .encap = XFRM_MODE_TRANSPORT,
341 return -EINVAL; 341 .family = AF_INET,
342 342 },
343 afinfo = xfrm_state_get_afinfo(mode->family); 343 [XFRM_MODE_TUNNEL] = {
344 if (unlikely(afinfo == NULL)) 344 .encap = XFRM_MODE_TUNNEL,
345 return -EAFNOSUPPORT; 345 .flags = XFRM_MODE_FLAG_TUNNEL,
346 346 .family = AF_INET,
347 err = -EEXIST; 347 },
348 modemap = afinfo->mode_map; 348};
349 spin_lock_bh(&xfrm_mode_lock); 349
350 if (modemap[mode->encap]) 350static const struct xfrm_mode xfrm6_mode_map[XFRM_MODE_MAX] = {
351 goto out; 351 [XFRM_MODE_BEET] = {
352 352 .encap = XFRM_MODE_BEET,
353 err = -ENOENT; 353 .flags = XFRM_MODE_FLAG_TUNNEL,
354 if (!try_module_get(afinfo->owner)) 354 .family = AF_INET6,
355 goto out; 355 },
356 356 [XFRM_MODE_ROUTEOPTIMIZATION] = {
357 modemap[mode->encap] = mode; 357 .encap = XFRM_MODE_ROUTEOPTIMIZATION,
358 err = 0; 358 .family = AF_INET6,
359 359 },
360out: 360 [XFRM_MODE_TRANSPORT] = {
361 spin_unlock_bh(&xfrm_mode_lock); 361 .encap = XFRM_MODE_TRANSPORT,
362 rcu_read_unlock(); 362 .family = AF_INET6,
363 return err; 363 },
364} 364 [XFRM_MODE_TUNNEL] = {
365EXPORT_SYMBOL(xfrm_register_mode); 365 .encap = XFRM_MODE_TUNNEL,
366 366 .flags = XFRM_MODE_FLAG_TUNNEL,
367void xfrm_unregister_mode(struct xfrm_mode *mode) 367 .family = AF_INET6,
368{ 368 },
369 struct xfrm_state_afinfo *afinfo; 369};
370 struct xfrm_mode **modemap; 370
371 371static const struct xfrm_mode *xfrm_get_mode(unsigned int encap, int family)
372 afinfo = xfrm_state_get_afinfo(mode->family); 372{
373 if (WARN_ON_ONCE(!afinfo)) 373 const struct xfrm_mode *mode;
374 return;
375
376 modemap = afinfo->mode_map;
377 spin_lock_bh(&xfrm_mode_lock);
378 if (likely(modemap[mode->encap] == mode)) {
379 modemap[mode->encap] = NULL;
380 module_put(afinfo->owner);
381 }
382
383 spin_unlock_bh(&xfrm_mode_lock);
384 rcu_read_unlock();
385}
386EXPORT_SYMBOL(xfrm_unregister_mode);
387
388static struct xfrm_mode *xfrm_get_mode(unsigned int encap, int family)
389{
390 struct xfrm_state_afinfo *afinfo;
391 struct xfrm_mode *mode;
392 int modload_attempted = 0;
393 374
394 if (unlikely(encap >= XFRM_MODE_MAX)) 375 if (unlikely(encap >= XFRM_MODE_MAX))
395 return NULL; 376 return NULL;
396 377
397retry: 378 switch (family) {
398 afinfo = xfrm_state_get_afinfo(family); 379 case AF_INET:
399 if (unlikely(afinfo == NULL)) 380 mode = &xfrm4_mode_map[encap];
400 return NULL; 381 if (mode->family == family)
401 382 return mode;
402 mode = READ_ONCE(afinfo->mode_map[encap]); 383 break;
403 if (unlikely(mode && !try_module_get(mode->owner))) 384 case AF_INET6:
404 mode = NULL; 385 mode = &xfrm6_mode_map[encap];
405 386 if (mode->family == family)
406 rcu_read_unlock(); 387 return mode;
407 if (!mode && !modload_attempted) { 388 break;
408 request_module("xfrm-mode-%d-%d", family, encap); 389 default:
409 modload_attempted = 1; 390 break;
410 goto retry;
411 } 391 }
412 392
413 return mode; 393 return NULL;
414}
415
416static void xfrm_put_mode(struct xfrm_mode *mode)
417{
418 module_put(mode->owner);
419} 394}
420 395
421void xfrm_state_free(struct xfrm_state *x) 396void xfrm_state_free(struct xfrm_state *x)
@@ -436,12 +411,6 @@ static void ___xfrm_state_destroy(struct xfrm_state *x)
436 kfree(x->coaddr); 411 kfree(x->coaddr);
437 kfree(x->replay_esn); 412 kfree(x->replay_esn);
438 kfree(x->preplay_esn); 413 kfree(x->preplay_esn);
439 if (x->inner_mode)
440 xfrm_put_mode(x->inner_mode);
441 if (x->inner_mode_iaf)
442 xfrm_put_mode(x->inner_mode_iaf);
443 if (x->outer_mode)
444 xfrm_put_mode(x->outer_mode);
445 if (x->type_offload) 414 if (x->type_offload)
446 xfrm_put_type_offload(x->type_offload); 415 xfrm_put_type_offload(x->type_offload);
447 if (x->type) { 416 if (x->type) {
@@ -2235,8 +2204,8 @@ int xfrm_state_mtu(struct xfrm_state *x, int mtu)
2235 2204
2236int __xfrm_init_state(struct xfrm_state *x, bool init_replay, bool offload) 2205int __xfrm_init_state(struct xfrm_state *x, bool init_replay, bool offload)
2237{ 2206{
2238 struct xfrm_state_afinfo *afinfo; 2207 const struct xfrm_mode *inner_mode;
2239 struct xfrm_mode *inner_mode; 2208 const struct xfrm_state_afinfo *afinfo;
2240 int family = x->props.family; 2209 int family = x->props.family;
2241 int err; 2210 int err;
2242 2211
@@ -2262,24 +2231,21 @@ int __xfrm_init_state(struct xfrm_state *x, bool init_replay, bool offload)
2262 goto error; 2231 goto error;
2263 2232
2264 if (!(inner_mode->flags & XFRM_MODE_FLAG_TUNNEL) && 2233 if (!(inner_mode->flags & XFRM_MODE_FLAG_TUNNEL) &&
2265 family != x->sel.family) { 2234 family != x->sel.family)
2266 xfrm_put_mode(inner_mode);
2267 goto error; 2235 goto error;
2268 }
2269 2236
2270 x->inner_mode = inner_mode; 2237 x->inner_mode = inner_mode;
2271 } else { 2238 } else {
2272 struct xfrm_mode *inner_mode_iaf; 2239 const struct xfrm_mode *inner_mode_iaf;
2273 int iafamily = AF_INET; 2240 int iafamily = AF_INET;
2274 2241
2275 inner_mode = xfrm_get_mode(x->props.mode, x->props.family); 2242 inner_mode = xfrm_get_mode(x->props.mode, x->props.family);
2276 if (inner_mode == NULL) 2243 if (inner_mode == NULL)
2277 goto error; 2244 goto error;
2278 2245
2279 if (!(inner_mode->flags & XFRM_MODE_FLAG_TUNNEL)) { 2246 if (!(inner_mode->flags & XFRM_MODE_FLAG_TUNNEL))
2280 xfrm_put_mode(inner_mode);
2281 goto error; 2247 goto error;
2282 } 2248
2283 x->inner_mode = inner_mode; 2249 x->inner_mode = inner_mode;
2284 2250
2285 if (x->props.family == AF_INET) 2251 if (x->props.family == AF_INET)
@@ -2289,8 +2255,6 @@ int __xfrm_init_state(struct xfrm_state *x, bool init_replay, bool offload)
2289 if (inner_mode_iaf) { 2255 if (inner_mode_iaf) {
2290 if (inner_mode_iaf->flags & XFRM_MODE_FLAG_TUNNEL) 2256 if (inner_mode_iaf->flags & XFRM_MODE_FLAG_TUNNEL)
2291 x->inner_mode_iaf = inner_mode_iaf; 2257 x->inner_mode_iaf = inner_mode_iaf;
2292 else
2293 xfrm_put_mode(inner_mode_iaf);
2294 } 2258 }
2295 } 2259 }
2296 2260
diff --git a/tools/testing/selftests/net/config b/tools/testing/selftests/net/config
index e9c860d00416..474040448601 100644
--- a/tools/testing/selftests/net/config
+++ b/tools/testing/selftests/net/config
@@ -7,9 +7,7 @@ CONFIG_NET_L3_MASTER_DEV=y
7CONFIG_IPV6=y 7CONFIG_IPV6=y
8CONFIG_IPV6_MULTIPLE_TABLES=y 8CONFIG_IPV6_MULTIPLE_TABLES=y
9CONFIG_VETH=y 9CONFIG_VETH=y
10CONFIG_INET_XFRM_MODE_TUNNEL=y
11CONFIG_NET_IPVTI=y 10CONFIG_NET_IPVTI=y
12CONFIG_INET6_XFRM_MODE_TUNNEL=y
13CONFIG_IPV6_VTI=y 11CONFIG_IPV6_VTI=y
14CONFIG_DUMMY=y 12CONFIG_DUMMY=y
15CONFIG_BRIDGE=y 13CONFIG_BRIDGE=y