diff options
Diffstat (limited to 'net/8021q/vlan.c')
-rw-r--r-- | net/8021q/vlan.c | 17 |
1 files changed, 9 insertions, 8 deletions
diff --git a/net/8021q/vlan.c b/net/8021q/vlan.c index a292e8050ef2..addc578d5443 100644 --- a/net/8021q/vlan.c +++ b/net/8021q/vlan.c @@ -105,6 +105,8 @@ void unregister_vlan_dev(struct net_device *dev, struct list_head *head) */ unregister_netdevice_queue(dev, head); + netdev_upper_dev_unlink(real_dev, dev); + if (grp->nr_vlan_devs == 0) vlan_gvrp_uninit_applicant(real_dev); @@ -115,19 +117,12 @@ void unregister_vlan_dev(struct net_device *dev, struct list_head *head) int vlan_check_real_dev(struct net_device *real_dev, u16 vlan_id) { const char *name = real_dev->name; - const struct net_device_ops *ops = real_dev->netdev_ops; if (real_dev->features & NETIF_F_VLAN_CHALLENGED) { pr_info("VLANs not supported on %s\n", name); return -EOPNOTSUPP; } - if ((real_dev->features & NETIF_F_HW_VLAN_FILTER) && - (!ops->ndo_vlan_rx_add_vid || !ops->ndo_vlan_rx_kill_vid)) { - pr_info("Device %s has buggy VLAN hw accel\n", name); - return -EOPNOTSUPP; - } - if (vlan_find_dev(real_dev, vlan_id) != NULL) return -EEXIST; @@ -162,9 +157,13 @@ int register_vlan_dev(struct net_device *dev) if (err < 0) goto out_uninit_applicant; + err = netdev_upper_dev_link(real_dev, dev); + if (err) + goto out_uninit_applicant; + err = register_netdevice(dev); if (err < 0) - goto out_uninit_applicant; + goto out_upper_dev_unlink; /* Account for reference in struct vlan_dev_priv */ dev_hold(real_dev); @@ -180,6 +179,8 @@ int register_vlan_dev(struct net_device *dev) return 0; +out_upper_dev_unlink: + netdev_upper_dev_unlink(real_dev, dev); out_uninit_applicant: if (grp->nr_vlan_devs == 0) vlan_gvrp_uninit_applicant(real_dev); |