diff options
author | Eric W. Biederman <ebiederm@xmission.com> | 2007-09-27 01:10:56 -0400 |
---|---|---|
committer | David S. Miller <davem@sunset.davemloft.net> | 2007-10-10 19:52:49 -0400 |
commit | 2774c7aba6c97a2535be3309a2209770953780b3 (patch) | |
tree | 9327c795707f6d723c6395c31e1c060e70b5e0db /drivers/net/loopback.c | |
parent | 0cc217e16cb8ca8ef2544363571fce94259900e0 (diff) |
[NET]: Make the loopback device per network namespace.
This patch makes loopback_dev per network namespace. Adding
code to create a different loopback device for each network
namespace and adding the code to free a loopback device
when a network namespace exits.
This patch modifies all users the loopback_dev so they
access it as init_net.loopback_dev, keeping all of the
code compiling and working. A later pass will be needed to
update the users to use something other than the initial network
namespace.
Signed-off-by: Eric W. Biederman <ebiederm@xmission.com>
Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'drivers/net/loopback.c')
-rw-r--r-- | drivers/net/loopback.c | 26 |
1 files changed, 21 insertions, 5 deletions
diff --git a/drivers/net/loopback.c b/drivers/net/loopback.c index f3018bb7570d..0f9d8c60c964 100644 --- a/drivers/net/loopback.c +++ b/drivers/net/loopback.c | |||
@@ -57,6 +57,7 @@ | |||
57 | #include <linux/ip.h> | 57 | #include <linux/ip.h> |
58 | #include <linux/tcp.h> | 58 | #include <linux/tcp.h> |
59 | #include <linux/percpu.h> | 59 | #include <linux/percpu.h> |
60 | #include <net/net_namespace.h> | ||
60 | 61 | ||
61 | struct pcpu_lstats { | 62 | struct pcpu_lstats { |
62 | unsigned long packets; | 63 | unsigned long packets; |
@@ -252,7 +253,7 @@ static void loopback_setup(struct net_device *dev) | |||
252 | } | 253 | } |
253 | 254 | ||
254 | /* Setup and register the loopback device. */ | 255 | /* Setup and register the loopback device. */ |
255 | static int __init loopback_init(void) | 256 | static int loopback_net_init(struct net *net) |
256 | { | 257 | { |
257 | struct net_device *dev; | 258 | struct net_device *dev; |
258 | int err; | 259 | int err; |
@@ -262,12 +263,13 @@ static int __init loopback_init(void) | |||
262 | if (!dev) | 263 | if (!dev) |
263 | goto out; | 264 | goto out; |
264 | 265 | ||
266 | dev->nd_net = net; | ||
265 | err = register_netdev(dev); | 267 | err = register_netdev(dev); |
266 | if (err) | 268 | if (err) |
267 | goto out_free_netdev; | 269 | goto out_free_netdev; |
268 | 270 | ||
269 | err = 0; | 271 | err = 0; |
270 | loopback_dev = dev; | 272 | net->loopback_dev = dev; |
271 | 273 | ||
272 | out: | 274 | out: |
273 | if (err) | 275 | if (err) |
@@ -279,7 +281,21 @@ out_free_netdev: | |||
279 | goto out; | 281 | goto out; |
280 | } | 282 | } |
281 | 283 | ||
282 | fs_initcall(loopback_init); | 284 | static void loopback_net_exit(struct net *net) |
285 | { | ||
286 | struct net_device *dev = net->loopback_dev; | ||
287 | |||
288 | unregister_netdev(dev); | ||
289 | } | ||
290 | |||
291 | static struct pernet_operations loopback_net_ops = { | ||
292 | .init = loopback_net_init, | ||
293 | .exit = loopback_net_exit, | ||
294 | }; | ||
295 | |||
296 | static int __init loopback_init(void) | ||
297 | { | ||
298 | return register_pernet_device(&loopback_net_ops); | ||
299 | } | ||
283 | 300 | ||
284 | struct net_device *loopback_dev; | 301 | fs_initcall(loopback_init); |
285 | EXPORT_SYMBOL(loopback_dev); | ||