diff options
Diffstat (limited to 'net/8021q')
-rw-r--r-- | net/8021q/vlan.c | 46 | ||||
-rw-r--r-- | net/8021q/vlan.h | 5 |
2 files changed, 51 insertions, 0 deletions
diff --git a/net/8021q/vlan.c b/net/8021q/vlan.c index cf8d810a130d..92966016a221 100644 --- a/net/8021q/vlan.c +++ b/net/8021q/vlan.c | |||
@@ -32,6 +32,7 @@ | |||
32 | #include <linux/rtnetlink.h> | 32 | #include <linux/rtnetlink.h> |
33 | #include <linux/notifier.h> | 33 | #include <linux/notifier.h> |
34 | #include <net/net_namespace.h> | 34 | #include <net/net_namespace.h> |
35 | #include <net/netns/generic.h> | ||
35 | 36 | ||
36 | #include <linux/if_vlan.h> | 37 | #include <linux/if_vlan.h> |
37 | #include "vlan.h" | 38 | #include "vlan.h" |
@@ -41,6 +42,8 @@ | |||
41 | 42 | ||
42 | /* Global VLAN variables */ | 43 | /* Global VLAN variables */ |
43 | 44 | ||
45 | int vlan_net_id; | ||
46 | |||
44 | /* Our listing of VLAN group(s) */ | 47 | /* Our listing of VLAN group(s) */ |
45 | static struct hlist_head vlan_group_hash[VLAN_GRP_HASH_SIZE]; | 48 | static struct hlist_head vlan_group_hash[VLAN_GRP_HASH_SIZE]; |
46 | 49 | ||
@@ -625,6 +628,41 @@ out: | |||
625 | return err; | 628 | return err; |
626 | } | 629 | } |
627 | 630 | ||
631 | static int vlan_init_net(struct net *net) | ||
632 | { | ||
633 | int err; | ||
634 | struct vlan_net *vn; | ||
635 | |||
636 | err = -ENOMEM; | ||
637 | vn = kzalloc(sizeof(struct vlan_net), GFP_KERNEL); | ||
638 | if (vn == NULL) | ||
639 | goto err_alloc; | ||
640 | |||
641 | err = net_assign_generic(net, vlan_net_id, vn); | ||
642 | if (err < 0) | ||
643 | goto err_assign; | ||
644 | |||
645 | return 0; | ||
646 | |||
647 | err_assign: | ||
648 | kfree(vn); | ||
649 | err_alloc: | ||
650 | return err; | ||
651 | } | ||
652 | |||
653 | static void vlan_exit_net(struct net *net) | ||
654 | { | ||
655 | struct vlan_net *vn; | ||
656 | |||
657 | vn = net_generic(net, vlan_net_id); | ||
658 | kfree(vn); | ||
659 | } | ||
660 | |||
661 | static struct pernet_operations vlan_net_ops = { | ||
662 | .init = vlan_init_net, | ||
663 | .exit = vlan_exit_net, | ||
664 | }; | ||
665 | |||
628 | static int __init vlan_proto_init(void) | 666 | static int __init vlan_proto_init(void) |
629 | { | 667 | { |
630 | int err; | 668 | int err; |
@@ -632,6 +670,10 @@ static int __init vlan_proto_init(void) | |||
632 | pr_info("%s v%s %s\n", vlan_fullname, vlan_version, vlan_copyright); | 670 | pr_info("%s v%s %s\n", vlan_fullname, vlan_version, vlan_copyright); |
633 | pr_info("All bugs added by %s\n", vlan_buggyright); | 671 | pr_info("All bugs added by %s\n", vlan_buggyright); |
634 | 672 | ||
673 | err = register_pernet_gen_device(&vlan_net_id, &vlan_net_ops); | ||
674 | if (err < 0) | ||
675 | goto err0; | ||
676 | |||
635 | err = vlan_proc_init(); | 677 | err = vlan_proc_init(); |
636 | if (err < 0) | 678 | if (err < 0) |
637 | goto err1; | 679 | goto err1; |
@@ -653,6 +695,8 @@ err3: | |||
653 | err2: | 695 | err2: |
654 | vlan_proc_cleanup(); | 696 | vlan_proc_cleanup(); |
655 | err1: | 697 | err1: |
698 | unregister_pernet_gen_device(vlan_net_id, &vlan_net_ops); | ||
699 | err0: | ||
656 | return err; | 700 | return err; |
657 | } | 701 | } |
658 | 702 | ||
@@ -673,6 +717,8 @@ static void __exit vlan_cleanup_module(void) | |||
673 | 717 | ||
674 | vlan_proc_cleanup(); | 718 | vlan_proc_cleanup(); |
675 | 719 | ||
720 | unregister_pernet_gen_device(vlan_net_id, &vlan_net_ops); | ||
721 | |||
676 | synchronize_net(); | 722 | synchronize_net(); |
677 | } | 723 | } |
678 | 724 | ||
diff --git a/net/8021q/vlan.h b/net/8021q/vlan.h index 51271aea402b..f27d8d6f3625 100644 --- a/net/8021q/vlan.h +++ b/net/8021q/vlan.h | |||
@@ -50,4 +50,9 @@ static inline int is_vlan_dev(struct net_device *dev) | |||
50 | return dev->priv_flags & IFF_802_1Q_VLAN; | 50 | return dev->priv_flags & IFF_802_1Q_VLAN; |
51 | } | 51 | } |
52 | 52 | ||
53 | extern int vlan_net_id; | ||
54 | |||
55 | struct vlan_net { | ||
56 | }; | ||
57 | |||
53 | #endif /* !(__BEN_VLAN_802_1Q_INC__) */ | 58 | #endif /* !(__BEN_VLAN_802_1Q_INC__) */ |