aboutsummaryrefslogtreecommitdiffstats
path: root/net/ipv6
diff options
context:
space:
mode:
authorAlexey Dobriyan <adobriyan@gmail.com>2010-02-16 04:05:04 -0500
committerDavid S. Miller <davem@davemloft.net>2010-02-16 17:55:25 -0500
commitd5aa407f59f5b83d2c50ec88f5bf56d40f1f8978 (patch)
tree664c30873708f0e361e5250835238043200f4b50 /net/ipv6
parentc2892f02712e9516d72841d5c019ed6916329794 (diff)
tunnels: fix netns vs proto registration ordering
Same stuff as in ip_gre patch: receive hook can be called before netns setup is done, oopsing in net_generic(). Signed-off-by: Alexey Dobriyan <adobriyan@gmail.com> Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'net/ipv6')
-rw-r--r--net/ipv6/ip6_tunnel.c28
-rw-r--r--net/ipv6/sit.c13
-rw-r--r--net/ipv6/xfrm6_tunnel.c55
3 files changed, 41 insertions, 55 deletions
diff --git a/net/ipv6/ip6_tunnel.c b/net/ipv6/ip6_tunnel.c
index fbd786981aa9..9b02492d8706 100644
--- a/net/ipv6/ip6_tunnel.c
+++ b/net/ipv6/ip6_tunnel.c
@@ -1461,27 +1461,29 @@ static int __init ip6_tunnel_init(void)
1461{ 1461{
1462 int err; 1462 int err;
1463 1463
1464 if (xfrm6_tunnel_register(&ip4ip6_handler, AF_INET)) { 1464 err = register_pernet_device(&ip6_tnl_net_ops);
1465 if (err < 0)
1466 goto out_pernet;
1467
1468 err = xfrm6_tunnel_register(&ip4ip6_handler, AF_INET);
1469 if (err < 0) {
1465 printk(KERN_ERR "ip6_tunnel init: can't register ip4ip6\n"); 1470 printk(KERN_ERR "ip6_tunnel init: can't register ip4ip6\n");
1466 err = -EAGAIN; 1471 goto out_ip4ip6;
1467 goto out;
1468 } 1472 }
1469 1473
1470 if (xfrm6_tunnel_register(&ip6ip6_handler, AF_INET6)) { 1474 err = xfrm6_tunnel_register(&ip6ip6_handler, AF_INET6);
1475 if (err < 0) {
1471 printk(KERN_ERR "ip6_tunnel init: can't register ip6ip6\n"); 1476 printk(KERN_ERR "ip6_tunnel init: can't register ip6ip6\n");
1472 err = -EAGAIN; 1477 goto out_ip6ip6;
1473 goto unreg_ip4ip6;
1474 } 1478 }
1475 1479
1476 err = register_pernet_device(&ip6_tnl_net_ops);
1477 if (err < 0)
1478 goto err_pernet;
1479 return 0; 1480 return 0;
1480err_pernet: 1481
1481 xfrm6_tunnel_deregister(&ip6ip6_handler, AF_INET6); 1482out_ip6ip6:
1482unreg_ip4ip6:
1483 xfrm6_tunnel_deregister(&ip4ip6_handler, AF_INET); 1483 xfrm6_tunnel_deregister(&ip4ip6_handler, AF_INET);
1484out: 1484out_ip4ip6:
1485 unregister_pernet_device(&ip6_tnl_net_ops);
1486out_pernet:
1485 return err; 1487 return err;
1486} 1488}
1487 1489
diff --git a/net/ipv6/sit.c b/net/ipv6/sit.c
index 10207cc8cc0e..52ffd29cb93f 100644
--- a/net/ipv6/sit.c
+++ b/net/ipv6/sit.c
@@ -1227,15 +1227,14 @@ static int __init sit_init(void)
1227 1227
1228 printk(KERN_INFO "IPv6 over IPv4 tunneling driver\n"); 1228 printk(KERN_INFO "IPv6 over IPv4 tunneling driver\n");
1229 1229
1230 if (xfrm4_tunnel_register(&sit_handler, AF_INET6) < 0) {
1231 printk(KERN_INFO "sit init: Can't add protocol\n");
1232 return -EAGAIN;
1233 }
1234
1235 err = register_pernet_device(&sit_net_ops); 1230 err = register_pernet_device(&sit_net_ops);
1236 if (err < 0) 1231 if (err < 0)
1237 xfrm4_tunnel_deregister(&sit_handler, AF_INET6); 1232 return err;
1238 1233 err = xfrm4_tunnel_register(&sit_handler, AF_INET6);
1234 if (err < 0) {
1235 unregister_pernet_device(&sit_net_ops);
1236 printk(KERN_INFO "sit init: Can't add protocol\n");
1237 }
1239 return err; 1238 return err;
1240} 1239}
1241 1240
diff --git a/net/ipv6/xfrm6_tunnel.c b/net/ipv6/xfrm6_tunnel.c
index d6f9aeec69f7..ddce21e3459b 100644
--- a/net/ipv6/xfrm6_tunnel.c
+++ b/net/ipv6/xfrm6_tunnel.c
@@ -84,23 +84,6 @@ static inline unsigned xfrm6_tunnel_spi_hash_byspi(u32 spi)
84 return spi % XFRM6_TUNNEL_SPI_BYSPI_HSIZE; 84 return spi % XFRM6_TUNNEL_SPI_BYSPI_HSIZE;
85} 85}
86 86
87
88static int __init xfrm6_tunnel_spi_init(void)
89{
90 xfrm6_tunnel_spi_kmem = kmem_cache_create("xfrm6_tunnel_spi",
91 sizeof(struct xfrm6_tunnel_spi),
92 0, SLAB_HWCACHE_ALIGN,
93 NULL);
94 if (!xfrm6_tunnel_spi_kmem)
95 return -ENOMEM;
96 return 0;
97}
98
99static void xfrm6_tunnel_spi_fini(void)
100{
101 kmem_cache_destroy(xfrm6_tunnel_spi_kmem);
102}
103
104static struct xfrm6_tunnel_spi *__xfrm6_tunnel_spi_lookup(struct net *net, xfrm_address_t *saddr) 87static struct xfrm6_tunnel_spi *__xfrm6_tunnel_spi_lookup(struct net *net, xfrm_address_t *saddr)
105{ 88{
106 struct xfrm6_tunnel_net *xfrm6_tn = xfrm6_tunnel_pernet(net); 89 struct xfrm6_tunnel_net *xfrm6_tn = xfrm6_tunnel_pernet(net);
@@ -375,42 +358,44 @@ static int __init xfrm6_tunnel_init(void)
375{ 358{
376 int rv; 359 int rv;
377 360
361 xfrm6_tunnel_spi_kmem = kmem_cache_create("xfrm6_tunnel_spi",
362 sizeof(struct xfrm6_tunnel_spi),
363 0, SLAB_HWCACHE_ALIGN,
364 NULL);
365 if (!xfrm6_tunnel_spi_kmem)
366 return -ENOMEM;
367 rv = register_pernet_subsys(&xfrm6_tunnel_net_ops);
368 if (rv < 0)
369 goto out_pernet;
378 rv = xfrm_register_type(&xfrm6_tunnel_type, AF_INET6); 370 rv = xfrm_register_type(&xfrm6_tunnel_type, AF_INET6);
379 if (rv < 0) 371 if (rv < 0)
380 goto err; 372 goto out_type;
381 rv = xfrm6_tunnel_register(&xfrm6_tunnel_handler, AF_INET6); 373 rv = xfrm6_tunnel_register(&xfrm6_tunnel_handler, AF_INET6);
382 if (rv < 0) 374 if (rv < 0)
383 goto unreg; 375 goto out_xfrm6;
384 rv = xfrm6_tunnel_register(&xfrm46_tunnel_handler, AF_INET); 376 rv = xfrm6_tunnel_register(&xfrm46_tunnel_handler, AF_INET);
385 if (rv < 0) 377 if (rv < 0)
386 goto dereg6; 378 goto out_xfrm46;
387 rv = xfrm6_tunnel_spi_init();
388 if (rv < 0)
389 goto dereg46;
390 rv = register_pernet_subsys(&xfrm6_tunnel_net_ops);
391 if (rv < 0)
392 goto deregspi;
393 return 0; 379 return 0;
394 380
395deregspi: 381out_xfrm46:
396 xfrm6_tunnel_spi_fini();
397dereg46:
398 xfrm6_tunnel_deregister(&xfrm46_tunnel_handler, AF_INET);
399dereg6:
400 xfrm6_tunnel_deregister(&xfrm6_tunnel_handler, AF_INET6); 382 xfrm6_tunnel_deregister(&xfrm6_tunnel_handler, AF_INET6);
401unreg: 383out_xfrm6:
402 xfrm_unregister_type(&xfrm6_tunnel_type, AF_INET6); 384 xfrm_unregister_type(&xfrm6_tunnel_type, AF_INET6);
403err: 385out_type:
386 unregister_pernet_subsys(&xfrm6_tunnel_net_ops);
387out_pernet:
388 kmem_cache_destroy(xfrm6_tunnel_spi_kmem);
404 return rv; 389 return rv;
405} 390}
406 391
407static void __exit xfrm6_tunnel_fini(void) 392static void __exit xfrm6_tunnel_fini(void)
408{ 393{
409 unregister_pernet_subsys(&xfrm6_tunnel_net_ops);
410 xfrm6_tunnel_spi_fini();
411 xfrm6_tunnel_deregister(&xfrm46_tunnel_handler, AF_INET); 394 xfrm6_tunnel_deregister(&xfrm46_tunnel_handler, AF_INET);
412 xfrm6_tunnel_deregister(&xfrm6_tunnel_handler, AF_INET6); 395 xfrm6_tunnel_deregister(&xfrm6_tunnel_handler, AF_INET6);
413 xfrm_unregister_type(&xfrm6_tunnel_type, AF_INET6); 396 xfrm_unregister_type(&xfrm6_tunnel_type, AF_INET6);
397 unregister_pernet_subsys(&xfrm6_tunnel_net_ops);
398 kmem_cache_destroy(xfrm6_tunnel_spi_kmem);
414} 399}
415 400
416module_init(xfrm6_tunnel_init); 401module_init(xfrm6_tunnel_init);