aboutsummaryrefslogtreecommitdiffstats
path: root/net/ipv6
diff options
context:
space:
mode:
authorDaniel Lezcano <dlezcano@fr.ibm.com>2008-03-26 19:52:32 -0400
committerDavid S. Miller <davem@davemloft.net>2008-03-26 19:52:32 -0400
commit6ab57e7e7fa316552d0f94eaebf1def1d49f18da (patch)
tree5e0f5d2d9d302758a6c3bebd91ff0c11b110f5a1 /net/ipv6
parenta233352506be35aafd49c0ba8c88ca96ebde1c3d (diff)
[NETNS][IPV6] anycast - handle several network namespace
Make use of the network namespace information to have this protocol to handle several network namespace. Signed-off-by: Daniel Lezcano <dlezcano@fr.ibm.com> Signed-off-by: Benjamin Thery <benjamin.thery@bull.net> Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'net/ipv6')
-rw-r--r--net/ipv6/af_inet6.c12
-rw-r--r--net/ipv6/anycast.c38
-rw-r--r--net/ipv6/ndisc.c2
3 files changed, 29 insertions, 23 deletions
diff --git a/net/ipv6/af_inet6.c b/net/ipv6/af_inet6.c
index 12f04e9d3e88..1731b0abf7f5 100644
--- a/net/ipv6/af_inet6.c
+++ b/net/ipv6/af_inet6.c
@@ -862,11 +862,16 @@ static int inet6_net_init(struct net *net)
862 err = tcp6_proc_init(net); 862 err = tcp6_proc_init(net);
863 if (err) 863 if (err)
864 goto proc_tcp6_fail; 864 goto proc_tcp6_fail;
865 err = ac6_proc_init(net);
866 if (err)
867 goto proc_ac6_fail;
865out: 868out:
866#endif 869#endif
867 return err; 870 return err;
868 871
869#ifdef CONFIG_PROC_FS 872#ifdef CONFIG_PROC_FS
873proc_ac6_fail:
874 tcp6_proc_exit(net);
870proc_tcp6_fail: 875proc_tcp6_fail:
871 udp6_proc_exit(net); 876 udp6_proc_exit(net);
872 goto out; 877 goto out;
@@ -878,6 +883,7 @@ static void inet6_net_exit(struct net *net)
878#ifdef CONFIG_PROC_FS 883#ifdef CONFIG_PROC_FS
879 udp6_proc_exit(net); 884 udp6_proc_exit(net);
880 tcp6_proc_exit(net); 885 tcp6_proc_exit(net);
886 ac6_proc_exit(net);
881#endif 887#endif
882} 888}
883 889
@@ -965,9 +971,6 @@ static int __init inet6_init(void)
965 goto proc_udplite6_fail; 971 goto proc_udplite6_fail;
966 if (ipv6_misc_proc_init()) 972 if (ipv6_misc_proc_init())
967 goto proc_misc6_fail; 973 goto proc_misc6_fail;
968
969 if (ac6_proc_init())
970 goto proc_anycast6_fail;
971 if (if6_proc_init()) 974 if (if6_proc_init())
972 goto proc_if6_fail; 975 goto proc_if6_fail;
973#endif 976#endif
@@ -1039,8 +1042,6 @@ ip6_route_fail:
1039#ifdef CONFIG_PROC_FS 1042#ifdef CONFIG_PROC_FS
1040 if6_proc_exit(); 1043 if6_proc_exit();
1041proc_if6_fail: 1044proc_if6_fail:
1042 ac6_proc_exit();
1043proc_anycast6_fail:
1044 ipv6_misc_proc_exit(); 1045 ipv6_misc_proc_exit();
1045proc_misc6_fail: 1046proc_misc6_fail:
1046 udplite6_proc_exit(); 1047 udplite6_proc_exit();
@@ -1101,7 +1102,6 @@ static void __exit inet6_exit(void)
1101 1102
1102 /* Cleanup code parts. */ 1103 /* Cleanup code parts. */
1103 if6_proc_exit(); 1104 if6_proc_exit();
1104 ac6_proc_exit();
1105 ipv6_misc_proc_exit(); 1105 ipv6_misc_proc_exit();
1106 udplite6_proc_exit(); 1106 udplite6_proc_exit();
1107 raw6_proc_exit(); 1107 raw6_proc_exit();
diff --git a/net/ipv6/anycast.c b/net/ipv6/anycast.c
index 96868b994b37..463bd95d6b13 100644
--- a/net/ipv6/anycast.c
+++ b/net/ipv6/anycast.c
@@ -82,6 +82,7 @@ int ipv6_sock_ac_join(struct sock *sk, int ifindex, struct in6_addr *addr)
82 struct net_device *dev = NULL; 82 struct net_device *dev = NULL;
83 struct inet6_dev *idev; 83 struct inet6_dev *idev;
84 struct ipv6_ac_socklist *pac; 84 struct ipv6_ac_socklist *pac;
85 struct net *net = sock_net(sk);
85 int ishost = !ipv6_devconf.forwarding; 86 int ishost = !ipv6_devconf.forwarding;
86 int err = 0; 87 int err = 0;
87 88
@@ -89,7 +90,7 @@ int ipv6_sock_ac_join(struct sock *sk, int ifindex, struct in6_addr *addr)
89 return -EPERM; 90 return -EPERM;
90 if (ipv6_addr_is_multicast(addr)) 91 if (ipv6_addr_is_multicast(addr))
91 return -EINVAL; 92 return -EINVAL;
92 if (ipv6_chk_addr(&init_net, addr, NULL, 0)) 93 if (ipv6_chk_addr(net, addr, NULL, 0))
93 return -EINVAL; 94 return -EINVAL;
94 95
95 pac = sock_kmalloc(sk, sizeof(struct ipv6_ac_socklist), GFP_KERNEL); 96 pac = sock_kmalloc(sk, sizeof(struct ipv6_ac_socklist), GFP_KERNEL);
@@ -101,7 +102,7 @@ int ipv6_sock_ac_join(struct sock *sk, int ifindex, struct in6_addr *addr)
101 if (ifindex == 0) { 102 if (ifindex == 0) {
102 struct rt6_info *rt; 103 struct rt6_info *rt;
103 104
104 rt = rt6_lookup(&init_net, addr, NULL, 0, 0); 105 rt = rt6_lookup(net, addr, NULL, 0, 0);
105 if (rt) { 106 if (rt) {
106 dev = rt->rt6i_dev; 107 dev = rt->rt6i_dev;
107 dev_hold(dev); 108 dev_hold(dev);
@@ -112,10 +113,10 @@ int ipv6_sock_ac_join(struct sock *sk, int ifindex, struct in6_addr *addr)
112 } else { 113 } else {
113 /* router, no matching interface: just pick one */ 114 /* router, no matching interface: just pick one */
114 115
115 dev = dev_get_by_flags(&init_net, IFF_UP, IFF_UP|IFF_LOOPBACK); 116 dev = dev_get_by_flags(net, IFF_UP, IFF_UP|IFF_LOOPBACK);
116 } 117 }
117 } else 118 } else
118 dev = dev_get_by_index(&init_net, ifindex); 119 dev = dev_get_by_index(net, ifindex);
119 120
120 if (dev == NULL) { 121 if (dev == NULL) {
121 err = -ENODEV; 122 err = -ENODEV;
@@ -176,6 +177,7 @@ int ipv6_sock_ac_drop(struct sock *sk, int ifindex, struct in6_addr *addr)
176 struct ipv6_pinfo *np = inet6_sk(sk); 177 struct ipv6_pinfo *np = inet6_sk(sk);
177 struct net_device *dev; 178 struct net_device *dev;
178 struct ipv6_ac_socklist *pac, *prev_pac; 179 struct ipv6_ac_socklist *pac, *prev_pac;
180 struct net *net = sock_net(sk);
179 181
180 write_lock_bh(&ipv6_sk_ac_lock); 182 write_lock_bh(&ipv6_sk_ac_lock);
181 prev_pac = NULL; 183 prev_pac = NULL;
@@ -196,7 +198,7 @@ int ipv6_sock_ac_drop(struct sock *sk, int ifindex, struct in6_addr *addr)
196 198
197 write_unlock_bh(&ipv6_sk_ac_lock); 199 write_unlock_bh(&ipv6_sk_ac_lock);
198 200
199 dev = dev_get_by_index(&init_net, pac->acl_ifindex); 201 dev = dev_get_by_index(net, pac->acl_ifindex);
200 if (dev) { 202 if (dev) {
201 ipv6_dev_ac_dec(dev, &pac->acl_addr); 203 ipv6_dev_ac_dec(dev, &pac->acl_addr);
202 dev_put(dev); 204 dev_put(dev);
@@ -210,6 +212,7 @@ void ipv6_sock_ac_close(struct sock *sk)
210 struct ipv6_pinfo *np = inet6_sk(sk); 212 struct ipv6_pinfo *np = inet6_sk(sk);
211 struct net_device *dev = NULL; 213 struct net_device *dev = NULL;
212 struct ipv6_ac_socklist *pac; 214 struct ipv6_ac_socklist *pac;
215 struct net *net = sock_net(sk);
213 int prev_index; 216 int prev_index;
214 217
215 write_lock_bh(&ipv6_sk_ac_lock); 218 write_lock_bh(&ipv6_sk_ac_lock);
@@ -224,7 +227,7 @@ void ipv6_sock_ac_close(struct sock *sk)
224 if (pac->acl_ifindex != prev_index) { 227 if (pac->acl_ifindex != prev_index) {
225 if (dev) 228 if (dev)
226 dev_put(dev); 229 dev_put(dev);
227 dev = dev_get_by_index(&init_net, pac->acl_ifindex); 230 dev = dev_get_by_index(net, pac->acl_ifindex);
228 prev_index = pac->acl_ifindex; 231 prev_index = pac->acl_ifindex;
229 } 232 }
230 if (dev) 233 if (dev)
@@ -422,14 +425,15 @@ static int ipv6_chk_acast_dev(struct net_device *dev, struct in6_addr *addr)
422/* 425/*
423 * check if given interface (or any, if dev==0) has this anycast address 426 * check if given interface (or any, if dev==0) has this anycast address
424 */ 427 */
425int ipv6_chk_acast_addr(struct net_device *dev, struct in6_addr *addr) 428int ipv6_chk_acast_addr(struct net *net, struct net_device *dev,
429 struct in6_addr *addr)
426{ 430{
427 int found = 0; 431 int found = 0;
428 432
429 if (dev) 433 if (dev)
430 return ipv6_chk_acast_dev(dev, addr); 434 return ipv6_chk_acast_dev(dev, addr);
431 read_lock(&dev_base_lock); 435 read_lock(&dev_base_lock);
432 for_each_netdev(&init_net, dev) 436 for_each_netdev(net, dev)
433 if (ipv6_chk_acast_dev(dev, addr)) { 437 if (ipv6_chk_acast_dev(dev, addr)) {
434 found = 1; 438 found = 1;
435 break; 439 break;
@@ -441,6 +445,7 @@ int ipv6_chk_acast_addr(struct net_device *dev, struct in6_addr *addr)
441 445
442#ifdef CONFIG_PROC_FS 446#ifdef CONFIG_PROC_FS
443struct ac6_iter_state { 447struct ac6_iter_state {
448 struct seq_net_private p;
444 struct net_device *dev; 449 struct net_device *dev;
445 struct inet6_dev *idev; 450 struct inet6_dev *idev;
446}; 451};
@@ -451,9 +456,10 @@ static inline struct ifacaddr6 *ac6_get_first(struct seq_file *seq)
451{ 456{
452 struct ifacaddr6 *im = NULL; 457 struct ifacaddr6 *im = NULL;
453 struct ac6_iter_state *state = ac6_seq_private(seq); 458 struct ac6_iter_state *state = ac6_seq_private(seq);
459 struct net *net = seq_file_net(seq);
454 460
455 state->idev = NULL; 461 state->idev = NULL;
456 for_each_netdev(&init_net, state->dev) { 462 for_each_netdev(net, state->dev) {
457 struct inet6_dev *idev; 463 struct inet6_dev *idev;
458 idev = in6_dev_get(state->dev); 464 idev = in6_dev_get(state->dev);
459 if (!idev) 465 if (!idev)
@@ -551,8 +557,8 @@ static const struct seq_operations ac6_seq_ops = {
551 557
552static int ac6_seq_open(struct inode *inode, struct file *file) 558static int ac6_seq_open(struct inode *inode, struct file *file)
553{ 559{
554 return seq_open_private(file, &ac6_seq_ops, 560 return seq_open_net(inode, file, &ac6_seq_ops,
555 sizeof(struct ac6_iter_state)); 561 sizeof(struct ac6_iter_state));
556} 562}
557 563
558static const struct file_operations ac6_seq_fops = { 564static const struct file_operations ac6_seq_fops = {
@@ -560,20 +566,20 @@ static const struct file_operations ac6_seq_fops = {
560 .open = ac6_seq_open, 566 .open = ac6_seq_open,
561 .read = seq_read, 567 .read = seq_read,
562 .llseek = seq_lseek, 568 .llseek = seq_lseek,
563 .release = seq_release_private, 569 .release = seq_release_net,
564}; 570};
565 571
566int __init ac6_proc_init(void) 572int ac6_proc_init(struct net *net)
567{ 573{
568 if (!proc_net_fops_create(&init_net, "anycast6", S_IRUGO, &ac6_seq_fops)) 574 if (!proc_net_fops_create(net, "anycast6", S_IRUGO, &ac6_seq_fops))
569 return -ENOMEM; 575 return -ENOMEM;
570 576
571 return 0; 577 return 0;
572} 578}
573 579
574void ac6_proc_exit(void) 580void ac6_proc_exit(struct net *net)
575{ 581{
576 proc_net_remove(&init_net, "anycast6"); 582 proc_net_remove(net, "anycast6");
577} 583}
578#endif 584#endif
579 585
diff --git a/net/ipv6/ndisc.c b/net/ipv6/ndisc.c
index 79af57f586e8..b4d8e331432e 100644
--- a/net/ipv6/ndisc.c
+++ b/net/ipv6/ndisc.c
@@ -773,7 +773,7 @@ static void ndisc_recv_ns(struct sk_buff *skb)
773 return; 773 return;
774 } 774 }
775 775
776 if (ipv6_chk_acast_addr(dev, &msg->target) || 776 if (ipv6_chk_acast_addr(dev_net(dev), dev, &msg->target) ||
777 (idev->cnf.forwarding && 777 (idev->cnf.forwarding &&
778 (ipv6_devconf.proxy_ndp || idev->cnf.proxy_ndp) && 778 (ipv6_devconf.proxy_ndp || idev->cnf.proxy_ndp) &&
779 (pneigh = pneigh_lookup(&nd_tbl, dev_net(dev), 779 (pneigh = pneigh_lookup(&nd_tbl, dev_net(dev),