#include <linux/device.h>
#include <linux/etherdevice.h>
#include <linux/rtnetlink.h>
+#include <linux/sched.h>
#include <net/genetlink.h>
#include <net/cfg80211.h>
#include "nl80211.h"
/* for debugfs */
static struct dentry *ieee80211_debugfs_dir;
+/* for the cleanup, scan and event works */
+struct workqueue_struct *cfg80211_wq;
+
/* requires cfg80211_mutex to be held! */
struct cfg80211_registered_device *cfg80211_rdev_by_wiphy_idx(int wiphy_idx)
{
break;
case NETDEV_DOWN:
dev_hold(dev);
- schedule_work(&wdev->cleanup_work);
+ queue_work(cfg80211_wq, &wdev->cleanup_work);
break;
case NETDEV_UP:
/*
mutex_unlock(&rdev->devlist_mtx);
dev_put(dev);
}
-#ifdef CONFIG_CFG80211_WEXT
cfg80211_lock_rdev(rdev);
mutex_lock(&rdev->devlist_mtx);
+#ifdef CONFIG_CFG80211_WEXT
wdev_lock(wdev);
switch (wdev->iftype) {
case NL80211_IFTYPE_ADHOC:
break;
}
wdev_unlock(wdev);
+#endif
rdev->opencount++;
mutex_unlock(&rdev->devlist_mtx);
cfg80211_unlock_rdev(rdev);
-#endif
break;
case NETDEV_UNREGISTER:
/*
if (err)
goto out_fail_reg;
+ cfg80211_wq = create_singlethread_workqueue("cfg80211");
+ if (!cfg80211_wq)
+ goto out_fail_wq;
+
return 0;
+out_fail_wq:
+ regulatory_exit();
out_fail_reg:
debugfs_remove(ieee80211_debugfs_dir);
out_fail_nl80211:
wiphy_sysfs_exit();
regulatory_exit();
unregister_pernet_device(&cfg80211_pernet_ops);
+ destroy_workqueue(cfg80211_wq);
}
module_exit(cfg80211_exit);