summaryrefslogtreecommitdiff
path: root/device.c
diff options
context:
space:
mode:
Diffstat (limited to 'device.c')
-rw-r--r--device.c51
1 files changed, 20 insertions, 31 deletions
diff --git a/device.c b/device.c
index bb39ea7..b3d0e85 100644
--- a/device.c
+++ b/device.c
@@ -99,18 +99,6 @@ device_type_get(const char *tname)
return NULL;
}
-void device_lock(void)
-{
- __devlock++;
-}
-
-void device_unlock(void)
-{
- __devlock--;
- if (!__devlock)
- device_free_unused(NULL);
-}
-
static int device_vlan_len(struct kvlist *kv, const void *data)
{
return sizeof(unsigned int);
@@ -895,14 +883,27 @@ device_free(struct device *dev)
}
static void
-__device_free_unused(struct device *dev)
+__device_free_unused(struct uloop_timeout *timeout)
{
- if (!safe_list_empty(&dev->users) ||
- !safe_list_empty(&dev->aliases) ||
- dev->current_config || __devlock)
- return;
+ struct device *dev, *tmp;
+
+ avl_for_each_element_safe(&devices, dev, avl, tmp) {
+ if (!safe_list_empty(&dev->users) ||
+ !safe_list_empty(&dev->aliases) ||
+ dev->current_config)
+ continue;
+
+ device_free(dev);
+ }
+}
+
+void device_free_unused(void)
+{
+ static struct uloop_timeout free_timer = {
+ .cb = __device_free_unused,
+ };
- device_free(dev);
+ uloop_timeout_set(&free_timer, 1);
}
void device_remove_user(struct device_user *dep)
@@ -919,19 +920,7 @@ void device_remove_user(struct device_user *dep)
safe_list_del(&dep->list);
dep->dev = NULL;
D(DEVICE, "Remove user for device '%s', refcount=%d\n", dev->ifname, device_refcount(dev));
- __device_free_unused(dev);
-}
-
-void
-device_free_unused(struct device *dev)
-{
- struct device *tmp;
-
- if (dev)
- return __device_free_unused(dev);
-
- avl_for_each_element_safe(&devices, dev, avl, tmp)
- __device_free_unused(dev);
+ device_free_unused();
}
void