diff options
Diffstat (limited to 'net/wireless/scan.c')
-rw-r--r-- | net/wireless/scan.c | 30 |
1 files changed, 27 insertions, 3 deletions
diff --git a/net/wireless/scan.c b/net/wireless/scan.c index 1625faf1de57..4f552c3f29a3 100644 --- a/net/wireless/scan.c +++ b/net/wireless/scan.c | |||
@@ -17,13 +17,21 @@ | |||
17 | 17 | ||
18 | #define IEEE80211_SCAN_RESULT_EXPIRE (10 * HZ) | 18 | #define IEEE80211_SCAN_RESULT_EXPIRE (10 * HZ) |
19 | 19 | ||
20 | void cfg80211_scan_done(struct cfg80211_scan_request *request, bool aborted) | 20 | void __cfg80211_scan_done(struct work_struct *wk) |
21 | { | 21 | { |
22 | struct cfg80211_registered_device *rdev; | ||
23 | struct cfg80211_scan_request *request; | ||
22 | struct net_device *dev; | 24 | struct net_device *dev; |
23 | #ifdef CONFIG_WIRELESS_EXT | 25 | #ifdef CONFIG_WIRELESS_EXT |
24 | union iwreq_data wrqu; | 26 | union iwreq_data wrqu; |
25 | #endif | 27 | #endif |
26 | 28 | ||
29 | rdev = container_of(wk, struct cfg80211_registered_device, | ||
30 | scan_done_wk); | ||
31 | |||
32 | mutex_lock(&rdev->mtx); | ||
33 | request = rdev->scan_req; | ||
34 | |||
27 | dev = dev_get_by_index(&init_net, request->ifidx); | 35 | dev = dev_get_by_index(&init_net, request->ifidx); |
28 | if (!dev) | 36 | if (!dev) |
29 | goto out; | 37 | goto out; |
@@ -35,7 +43,7 @@ void cfg80211_scan_done(struct cfg80211_scan_request *request, bool aborted) | |||
35 | */ | 43 | */ |
36 | cfg80211_sme_scan_done(dev); | 44 | cfg80211_sme_scan_done(dev); |
37 | 45 | ||
38 | if (aborted) | 46 | if (request->aborted) |
39 | nl80211_send_scan_aborted(wiphy_to_dev(request->wiphy), dev); | 47 | nl80211_send_scan_aborted(wiphy_to_dev(request->wiphy), dev); |
40 | else | 48 | else |
41 | nl80211_send_scan_done(wiphy_to_dev(request->wiphy), dev); | 49 | nl80211_send_scan_done(wiphy_to_dev(request->wiphy), dev); |
@@ -43,7 +51,7 @@ void cfg80211_scan_done(struct cfg80211_scan_request *request, bool aborted) | |||
43 | wiphy_to_dev(request->wiphy)->scan_req = NULL; | 51 | wiphy_to_dev(request->wiphy)->scan_req = NULL; |
44 | 52 | ||
45 | #ifdef CONFIG_WIRELESS_EXT | 53 | #ifdef CONFIG_WIRELESS_EXT |
46 | if (!aborted) { | 54 | if (!request->aborted) { |
47 | memset(&wrqu, 0, sizeof(wrqu)); | 55 | memset(&wrqu, 0, sizeof(wrqu)); |
48 | 56 | ||
49 | wireless_send_event(dev, SIOCGIWSCAN, &wrqu, NULL); | 57 | wireless_send_event(dev, SIOCGIWSCAN, &wrqu, NULL); |
@@ -53,8 +61,24 @@ void cfg80211_scan_done(struct cfg80211_scan_request *request, bool aborted) | |||
53 | dev_put(dev); | 61 | dev_put(dev); |
54 | 62 | ||
55 | out: | 63 | out: |
64 | cfg80211_unlock_rdev(rdev); | ||
56 | kfree(request); | 65 | kfree(request); |
57 | } | 66 | } |
67 | |||
68 | void cfg80211_scan_done(struct cfg80211_scan_request *request, bool aborted) | ||
69 | { | ||
70 | struct net_device *dev = dev_get_by_index(&init_net, request->ifidx); | ||
71 | if (WARN_ON(!dev)) { | ||
72 | kfree(request); | ||
73 | return; | ||
74 | } | ||
75 | |||
76 | WARN_ON(request != wiphy_to_dev(request->wiphy)->scan_req); | ||
77 | |||
78 | request->aborted = aborted; | ||
79 | schedule_work(&wiphy_to_dev(request->wiphy)->scan_done_wk); | ||
80 | dev_put(dev); | ||
81 | } | ||
58 | EXPORT_SYMBOL(cfg80211_scan_done); | 82 | EXPORT_SYMBOL(cfg80211_scan_done); |
59 | 83 | ||
60 | static void bss_release(struct kref *ref) | 84 | static void bss_release(struct kref *ref) |