diff options
-rw-r--r-- | interface.c | 16 | ||||
-rw-r--r-- | interface.h | 1 |
2 files changed, 17 insertions, 0 deletions
diff --git a/interface.c b/interface.c index 4c92f10..e66b58a 100644 --- a/interface.c +++ b/interface.c @@ -308,6 +308,13 @@ interface_set_link_state(struct interface *iface, bool new_state) } static void +interface_ext_cb(struct device_user *dep, enum device_event ev) +{ + if (ev == DEV_EVENT_REMOVE) + device_remove_user(dep); +} + +static void interface_cb(struct device_user *dep, enum device_event ev) { struct interface *iface; @@ -491,6 +498,8 @@ interface_claim_device(struct interface *iface) } else if (iface->ifname && !(iface->proto_handler->flags & PROTO_FLAG_NODEV)) { dev = device_get(iface->ifname, true); + } else { + dev = iface->ext_dev.dev; } if (dev) @@ -518,6 +527,8 @@ interface_cleanup(struct interface *iface) { struct interface_user *dep, *tmp; + device_remove_user(&iface->ext_dev); + if (iface->parent_iface.iface) interface_remove_user(&iface->parent_iface); @@ -653,6 +664,7 @@ interface_alloc(const char *name, struct blob_attr *config) iface->config_ip.enabled = false; iface->main_dev.cb = interface_cb; + iface->ext_dev.cb = interface_ext_cb; blobmsg_parse(iface_attrs, IFACE_ATTR_MAX, tb, blob_data(config), blob_len(config)); @@ -807,6 +819,9 @@ interface_remove_link(struct interface *iface, struct device *dev) if (mdev && mdev->hotplug_ops) return mdev->hotplug_ops->del(mdev, dev); + if (dev == iface->ext_dev.dev) + device_remove_user(&iface->ext_dev); + if (!iface->main_dev.hotplug) return UBUS_STATUS_INVALID_ARGUMENT; @@ -835,6 +850,7 @@ interface_add_link(struct interface *iface, struct device *dev) return UBUS_STATUS_NOT_SUPPORTED; } + device_add_user(&iface->ext_dev, dev); interface_set_main_dev(iface, dev); iface->main_dev.hotplug = true; return 0; diff --git a/interface.h b/interface.h index 6cfe264..1cd7e96 100644 --- a/interface.h +++ b/interface.h @@ -119,6 +119,7 @@ struct interface { /* main interface that the interface is bound to */ struct device_user main_dev; + struct device_user ext_dev; /* interface that layer 3 communication will go through */ struct device_user l3_dev; |