aboutsummaryrefslogtreecommitdiffstats
path: root/net/wireless
diff options
context:
space:
mode:
authorLinus Torvalds <torvalds@linux-foundation.org>2010-10-23 14:47:02 -0400
committerLinus Torvalds <torvalds@linux-foundation.org>2010-10-23 14:47:02 -0400
commit5f05647dd81c11a6a165ccc8f0c1370b16f3bcb0 (patch)
tree7851ef1c93aa1aba7ef327ca4b75fd35e6d10f29 /net/wireless
parent02f36038c568111ad4fc433f6fa760ff5e38fab4 (diff)
parentec37a48d1d16c30b655ac5280209edf52a6775d4 (diff)
Merge git://git.kernel.org/pub/scm/linux/kernel/git/davem/net-next-2.6
* git://git.kernel.org/pub/scm/linux/kernel/git/davem/net-next-2.6: (1699 commits) bnx2/bnx2x: Unsupported Ethtool operations should return -EINVAL. vlan: Calling vlan_hwaccel_do_receive() is always valid. tproxy: use the interface primary IP address as a default value for --on-ip tproxy: added IPv6 support to the socket match cxgb3: function namespace cleanup tproxy: added IPv6 support to the TPROXY target tproxy: added IPv6 socket lookup function to nf_tproxy_core be2net: Changes to use only priority codes allowed by f/w tproxy: allow non-local binds of IPv6 sockets if IP_TRANSPARENT is enabled tproxy: added tproxy sockopt interface in the IPV6 layer tproxy: added udp6_lib_lookup function tproxy: added const specifiers to udp lookup functions tproxy: split off ipv6 defragmentation to a separate module l2tp: small cleanup nf_nat: restrict ICMP translation for embedded header can: mcp251x: fix generation of error frames can: mcp251x: fix endless loop in interrupt handler if CANINTF_MERRF is set can-raw: add msg_flags to distinguish local traffic 9p: client code cleanup rds: make local functions/variables static ... Fix up conflicts in net/core/dev.c, drivers/net/pcmcia/smc91c92_cs.c and drivers/net/wireless/ath/ath9k/debug.c as per David
Diffstat (limited to 'net/wireless')
-rw-r--r--net/wireless/core.c66
-rw-r--r--net/wireless/core.h34
-rw-r--r--net/wireless/ibss.c21
-rw-r--r--net/wireless/mlme.c225
-rw-r--r--net/wireless/nl80211.c2189
-rw-r--r--net/wireless/nl80211.h14
-rw-r--r--net/wireless/radiotap.c61
-rw-r--r--net/wireless/reg.c22
-rw-r--r--net/wireless/scan.c12
-rw-r--r--net/wireless/sme.c11
-rw-r--r--net/wireless/sysfs.c18
-rw-r--r--net/wireless/util.c40
-rw-r--r--net/wireless/wext-compat.c42
-rw-r--r--net/wireless/wext-core.c2
-rw-r--r--net/wireless/wext-sme.c2
15 files changed, 1196 insertions, 1563 deletions
diff --git a/net/wireless/core.c b/net/wireless/core.c
index d6d046b9f6f2..9c21ebf9780e 100644
--- a/net/wireless/core.c
+++ b/net/wireless/core.c
@@ -253,11 +253,16 @@ int cfg80211_switch_netns(struct cfg80211_registered_device *rdev,
253 WARN_ON(err); 253 WARN_ON(err);
254 wdev->netdev->features |= NETIF_F_NETNS_LOCAL; 254 wdev->netdev->features |= NETIF_F_NETNS_LOCAL;
255 } 255 }
256
257 return err;
256 } 258 }
257 259
258 wiphy_net_set(&rdev->wiphy, net); 260 wiphy_net_set(&rdev->wiphy, net);
259 261
260 return err; 262 err = device_rename(&rdev->wiphy.dev, dev_name(&rdev->wiphy.dev));
263 WARN_ON(err);
264
265 return 0;
261} 266}
262 267
263static void cfg80211_rfkill_poll(struct rfkill *rfkill, void *data) 268static void cfg80211_rfkill_poll(struct rfkill *rfkill, void *data)
@@ -428,7 +433,7 @@ int wiphy_register(struct wiphy *wiphy)
428 433
429 /* sanity check ifmodes */ 434 /* sanity check ifmodes */
430 WARN_ON(!ifmodes); 435 WARN_ON(!ifmodes);
431 ifmodes &= ((1 << __NL80211_IFTYPE_AFTER_LAST) - 1) & ~1; 436 ifmodes &= ((1 << NUM_NL80211_IFTYPES) - 1) & ~1;
432 if (WARN_ON(ifmodes != wiphy->interface_modes)) 437 if (WARN_ON(ifmodes != wiphy->interface_modes))
433 wiphy->interface_modes = ifmodes; 438 wiphy->interface_modes = ifmodes;
434 439
@@ -683,8 +688,8 @@ static int cfg80211_netdev_notifier_call(struct notifier_block * nb,
683 INIT_WORK(&wdev->cleanup_work, wdev_cleanup_work); 688 INIT_WORK(&wdev->cleanup_work, wdev_cleanup_work);
684 INIT_LIST_HEAD(&wdev->event_list); 689 INIT_LIST_HEAD(&wdev->event_list);
685 spin_lock_init(&wdev->event_lock); 690 spin_lock_init(&wdev->event_lock);
686 INIT_LIST_HEAD(&wdev->action_registrations); 691 INIT_LIST_HEAD(&wdev->mgmt_registrations);
687 spin_lock_init(&wdev->action_registrations_lock); 692 spin_lock_init(&wdev->mgmt_registrations_lock);
688 693
689 mutex_lock(&rdev->devlist_mtx); 694 mutex_lock(&rdev->devlist_mtx);
690 list_add_rcu(&wdev->list, &rdev->netdev_list); 695 list_add_rcu(&wdev->list, &rdev->netdev_list);
@@ -724,6 +729,7 @@ static int cfg80211_netdev_notifier_call(struct notifier_block * nb,
724 dev->ethtool_ops = &cfg80211_ethtool_ops; 729 dev->ethtool_ops = &cfg80211_ethtool_ops;
725 730
726 if ((wdev->iftype == NL80211_IFTYPE_STATION || 731 if ((wdev->iftype == NL80211_IFTYPE_STATION ||
732 wdev->iftype == NL80211_IFTYPE_P2P_CLIENT ||
727 wdev->iftype == NL80211_IFTYPE_ADHOC) && !wdev->use_4addr) 733 wdev->iftype == NL80211_IFTYPE_ADHOC) && !wdev->use_4addr)
728 dev->priv_flags |= IFF_DONT_BRIDGE; 734 dev->priv_flags |= IFF_DONT_BRIDGE;
729 break; 735 break;
@@ -732,6 +738,7 @@ static int cfg80211_netdev_notifier_call(struct notifier_block * nb,
732 case NL80211_IFTYPE_ADHOC: 738 case NL80211_IFTYPE_ADHOC:
733 cfg80211_leave_ibss(rdev, dev, true); 739 cfg80211_leave_ibss(rdev, dev, true);
734 break; 740 break;
741 case NL80211_IFTYPE_P2P_CLIENT:
735 case NL80211_IFTYPE_STATION: 742 case NL80211_IFTYPE_STATION:
736 wdev_lock(wdev); 743 wdev_lock(wdev);
737#ifdef CONFIG_CFG80211_WEXT 744#ifdef CONFIG_CFG80211_WEXT
@@ -804,7 +811,7 @@ static int cfg80211_netdev_notifier_call(struct notifier_block * nb,
804 sysfs_remove_link(&dev->dev.kobj, "phy80211"); 811 sysfs_remove_link(&dev->dev.kobj, "phy80211");
805 list_del_rcu(&wdev->list); 812 list_del_rcu(&wdev->list);
806 rdev->devlist_generation++; 813 rdev->devlist_generation++;
807 cfg80211_mlme_purge_actions(wdev); 814 cfg80211_mlme_purge_registrations(wdev);
808#ifdef CONFIG_CFG80211_WEXT 815#ifdef CONFIG_CFG80211_WEXT
809 kfree(wdev->wext.keys); 816 kfree(wdev->wext.keys);
810#endif 817#endif
@@ -910,52 +917,3 @@ static void __exit cfg80211_exit(void)
910 destroy_workqueue(cfg80211_wq); 917 destroy_workqueue(cfg80211_wq);
911} 918}
912module_exit(cfg80211_exit); 919module_exit(cfg80211_exit);
913
914static int ___wiphy_printk(const char *level, const struct wiphy *wiphy,
915 struct va_format *vaf)
916{
917 if (!wiphy)
918 return printk("%s(NULL wiphy *): %pV", level, vaf);
919
920 return printk("%s%s: %pV", level, wiphy_name(wiphy), vaf);
921}
922
923int __wiphy_printk(const char *level, const struct wiphy *wiphy,
924 const char *fmt, ...)
925{
926 struct va_format vaf;
927 va_list args;
928 int r;
929
930 va_start(args, fmt);
931
932 vaf.fmt = fmt;
933 vaf.va = &args;
934
935 r = ___wiphy_printk(level, wiphy, &vaf);
936 va_end(args);
937
938 return r;
939}
940EXPORT_SYMBOL(__wiphy_printk);
941
942#define define_wiphy_printk_level(func, kern_level) \
943int func(const struct wiphy *wiphy, const char *fmt, ...) \
944{ \
945 struct va_format vaf; \
946 va_list args; \
947 int r; \
948 \
949 va_start(args, fmt); \
950 \
951 vaf.fmt = fmt; \
952 vaf.va = &args; \
953 \
954 r = ___wiphy_printk(kern_level, wiphy, &vaf); \
955 va_end(args); \
956 \
957 return r; \
958} \
959EXPORT_SYMBOL(func);
960
961define_wiphy_printk_level(wiphy_debug, KERN_DEBUG);
diff --git a/net/wireless/core.h b/net/wireless/core.h
index 63d57ae399c3..6583cca0e2ee 100644
--- a/net/wireless/core.h
+++ b/net/wireless/core.h
@@ -86,7 +86,7 @@ struct cfg80211_registered_device *wiphy_to_dev(struct wiphy *wiphy)
86static inline 86static inline
87bool wiphy_idx_valid(int wiphy_idx) 87bool wiphy_idx_valid(int wiphy_idx)
88{ 88{
89 return (wiphy_idx >= 0); 89 return wiphy_idx >= 0;
90} 90}
91 91
92 92
@@ -95,7 +95,10 @@ extern struct mutex cfg80211_mutex;
95extern struct list_head cfg80211_rdev_list; 95extern struct list_head cfg80211_rdev_list;
96extern int cfg80211_rdev_list_generation; 96extern int cfg80211_rdev_list_generation;
97 97
98#define assert_cfg80211_lock() WARN_ON(!mutex_is_locked(&cfg80211_mutex)) 98static inline void assert_cfg80211_lock(void)
99{
100 lockdep_assert_held(&cfg80211_mutex);
101}
99 102
100/* 103/*
101 * You can use this to mark a wiphy_idx as not having an associated wiphy. 104 * You can use this to mark a wiphy_idx as not having an associated wiphy.
@@ -202,8 +205,8 @@ static inline void wdev_unlock(struct wireless_dev *wdev)
202 mutex_unlock(&wdev->mtx); 205 mutex_unlock(&wdev->mtx);
203} 206}
204 207
205#define ASSERT_RDEV_LOCK(rdev) WARN_ON(!mutex_is_locked(&(rdev)->mtx)); 208#define ASSERT_RDEV_LOCK(rdev) lockdep_assert_held(&(rdev)->mtx)
206#define ASSERT_WDEV_LOCK(wdev) WARN_ON(!mutex_is_locked(&(wdev)->mtx)); 209#define ASSERT_WDEV_LOCK(wdev) lockdep_assert_held(&(wdev)->mtx)
207 210
208enum cfg80211_event_type { 211enum cfg80211_event_type {
209 EVENT_CONNECT_RESULT, 212 EVENT_CONNECT_RESULT,
@@ -331,16 +334,17 @@ void __cfg80211_connect_result(struct net_device *dev, const u8 *bssid,
331 const u8 *resp_ie, size_t resp_ie_len, 334 const u8 *resp_ie, size_t resp_ie_len,
332 u16 status, bool wextev, 335 u16 status, bool wextev,
333 struct cfg80211_bss *bss); 336 struct cfg80211_bss *bss);
334int cfg80211_mlme_register_action(struct wireless_dev *wdev, u32 snd_pid, 337int cfg80211_mlme_register_mgmt(struct wireless_dev *wdev, u32 snd_pid,
335 const u8 *match_data, int match_len); 338 u16 frame_type, const u8 *match_data,
336void cfg80211_mlme_unregister_actions(struct wireless_dev *wdev, u32 nlpid); 339 int match_len);
337void cfg80211_mlme_purge_actions(struct wireless_dev *wdev); 340void cfg80211_mlme_unregister_socket(struct wireless_dev *wdev, u32 nlpid);
338int cfg80211_mlme_action(struct cfg80211_registered_device *rdev, 341void cfg80211_mlme_purge_registrations(struct wireless_dev *wdev);
339 struct net_device *dev, 342int cfg80211_mlme_mgmt_tx(struct cfg80211_registered_device *rdev,
340 struct ieee80211_channel *chan, 343 struct net_device *dev,
341 enum nl80211_channel_type channel_type, 344 struct ieee80211_channel *chan,
342 bool channel_type_valid, 345 enum nl80211_channel_type channel_type,
343 const u8 *buf, size_t len, u64 *cookie); 346 bool channel_type_valid,
347 const u8 *buf, size_t len, u64 *cookie);
344 348
345/* SME */ 349/* SME */
346int __cfg80211_connect(struct cfg80211_registered_device *rdev, 350int __cfg80211_connect(struct cfg80211_registered_device *rdev,
@@ -371,7 +375,7 @@ bool cfg80211_sme_failed_reassoc(struct wireless_dev *wdev);
371/* internal helpers */ 375/* internal helpers */
372int cfg80211_validate_key_settings(struct cfg80211_registered_device *rdev, 376int cfg80211_validate_key_settings(struct cfg80211_registered_device *rdev,
373 struct key_params *params, int key_idx, 377 struct key_params *params, int key_idx,
374 const u8 *mac_addr); 378 bool pairwise, const u8 *mac_addr);
375void __cfg80211_disconnected(struct net_device *dev, const u8 *ie, 379void __cfg80211_disconnected(struct net_device *dev, const u8 *ie,
376 size_t ie_len, u16 reason, bool from_ap); 380 size_t ie_len, u16 reason, bool from_ap);
377void cfg80211_sme_scan_done(struct net_device *dev); 381void cfg80211_sme_scan_done(struct net_device *dev);
diff --git a/net/wireless/ibss.c b/net/wireless/ibss.c
index 27a8ce9343c3..f33fbb79437c 100644
--- a/net/wireless/ibss.c
+++ b/net/wireless/ibss.c
@@ -88,6 +88,25 @@ int __cfg80211_join_ibss(struct cfg80211_registered_device *rdev,
88 if (wdev->ssid_len) 88 if (wdev->ssid_len)
89 return -EALREADY; 89 return -EALREADY;
90 90
91 if (!params->basic_rates) {
92 /*
93 * If no rates were explicitly configured,
94 * use the mandatory rate set for 11b or
95 * 11a for maximum compatibility.
96 */
97 struct ieee80211_supported_band *sband =
98 rdev->wiphy.bands[params->channel->band];
99 int j;
100 u32 flag = params->channel->band == IEEE80211_BAND_5GHZ ?
101 IEEE80211_RATE_MANDATORY_A :
102 IEEE80211_RATE_MANDATORY_B;
103
104 for (j = 0; j < sband->n_bitrates; j++) {
105 if (sband->bitrates[j].flags & flag)
106 params->basic_rates |= BIT(j);
107 }
108 }
109
91 if (WARN_ON(wdev->connect_keys)) 110 if (WARN_ON(wdev->connect_keys))
92 kfree(wdev->connect_keys); 111 kfree(wdev->connect_keys);
93 wdev->connect_keys = connkeys; 112 wdev->connect_keys = connkeys;
@@ -141,7 +160,7 @@ static void __cfg80211_clear_ibss(struct net_device *dev, bool nowext)
141 */ 160 */
142 if (rdev->ops->del_key) 161 if (rdev->ops->del_key)
143 for (i = 0; i < 6; i++) 162 for (i = 0; i < 6; i++)
144 rdev->ops->del_key(wdev->wiphy, dev, i, NULL); 163 rdev->ops->del_key(wdev->wiphy, dev, i, false, NULL);
145 164
146 if (wdev->current_bss) { 165 if (wdev->current_bss) {
147 cfg80211_unhold_bss(wdev->current_bss); 166 cfg80211_unhold_bss(wdev->current_bss);
diff --git a/net/wireless/mlme.c b/net/wireless/mlme.c
index d1a3fb99fdf2..26838d903b9a 100644
--- a/net/wireless/mlme.c
+++ b/net/wireless/mlme.c
@@ -149,7 +149,7 @@ void __cfg80211_send_deauth(struct net_device *dev,
149 struct ieee80211_mgmt *mgmt = (struct ieee80211_mgmt *)buf; 149 struct ieee80211_mgmt *mgmt = (struct ieee80211_mgmt *)buf;
150 const u8 *bssid = mgmt->bssid; 150 const u8 *bssid = mgmt->bssid;
151 int i; 151 int i;
152 bool found = false; 152 bool found = false, was_current = false;
153 153
154 ASSERT_WDEV_LOCK(wdev); 154 ASSERT_WDEV_LOCK(wdev);
155 155
@@ -159,6 +159,7 @@ void __cfg80211_send_deauth(struct net_device *dev,
159 cfg80211_put_bss(&wdev->current_bss->pub); 159 cfg80211_put_bss(&wdev->current_bss->pub);
160 wdev->current_bss = NULL; 160 wdev->current_bss = NULL;
161 found = true; 161 found = true;
162 was_current = true;
162 } else for (i = 0; i < MAX_AUTH_BSSES; i++) { 163 } else for (i = 0; i < MAX_AUTH_BSSES; i++) {
163 if (wdev->auth_bsses[i] && 164 if (wdev->auth_bsses[i] &&
164 memcmp(wdev->auth_bsses[i]->pub.bssid, bssid, ETH_ALEN) == 0) { 165 memcmp(wdev->auth_bsses[i]->pub.bssid, bssid, ETH_ALEN) == 0) {
@@ -183,7 +184,7 @@ void __cfg80211_send_deauth(struct net_device *dev,
183 184
184 nl80211_send_deauth(rdev, dev, buf, len, GFP_KERNEL); 185 nl80211_send_deauth(rdev, dev, buf, len, GFP_KERNEL);
185 186
186 if (wdev->sme_state == CFG80211_SME_CONNECTED) { 187 if (wdev->sme_state == CFG80211_SME_CONNECTED && was_current) {
187 u16 reason_code; 188 u16 reason_code;
188 bool from_ap; 189 bool from_ap;
189 190
@@ -747,31 +748,53 @@ void cfg80211_new_sta(struct net_device *dev, const u8 *mac_addr,
747} 748}
748EXPORT_SYMBOL(cfg80211_new_sta); 749EXPORT_SYMBOL(cfg80211_new_sta);
749 750
750struct cfg80211_action_registration { 751struct cfg80211_mgmt_registration {
751 struct list_head list; 752 struct list_head list;
752 753
753 u32 nlpid; 754 u32 nlpid;
754 755
755 int match_len; 756 int match_len;
756 757
758 __le16 frame_type;
759
757 u8 match[]; 760 u8 match[];
758}; 761};
759 762
760int cfg80211_mlme_register_action(struct wireless_dev *wdev, u32 snd_pid, 763int cfg80211_mlme_register_mgmt(struct wireless_dev *wdev, u32 snd_pid,
761 const u8 *match_data, int match_len) 764 u16 frame_type, const u8 *match_data,
765 int match_len)
762{ 766{
763 struct cfg80211_action_registration *reg, *nreg; 767 struct wiphy *wiphy = wdev->wiphy;
768 struct cfg80211_registered_device *rdev = wiphy_to_dev(wiphy);
769 struct cfg80211_mgmt_registration *reg, *nreg;
764 int err = 0; 770 int err = 0;
771 u16 mgmt_type;
772
773 if (!wdev->wiphy->mgmt_stypes)
774 return -EOPNOTSUPP;
775
776 if ((frame_type & IEEE80211_FCTL_FTYPE) != IEEE80211_FTYPE_MGMT)
777 return -EINVAL;
778
779 if (frame_type & ~(IEEE80211_FCTL_FTYPE | IEEE80211_FCTL_STYPE))
780 return -EINVAL;
781
782 mgmt_type = (frame_type & IEEE80211_FCTL_STYPE) >> 4;
783 if (!(wdev->wiphy->mgmt_stypes[wdev->iftype].rx & BIT(mgmt_type)))
784 return -EINVAL;
765 785
766 nreg = kzalloc(sizeof(*reg) + match_len, GFP_KERNEL); 786 nreg = kzalloc(sizeof(*reg) + match_len, GFP_KERNEL);
767 if (!nreg) 787 if (!nreg)
768 return -ENOMEM; 788 return -ENOMEM;
769 789
770 spin_lock_bh(&wdev->action_registrations_lock); 790 spin_lock_bh(&wdev->mgmt_registrations_lock);
771 791
772 list_for_each_entry(reg, &wdev->action_registrations, list) { 792 list_for_each_entry(reg, &wdev->mgmt_registrations, list) {
773 int mlen = min(match_len, reg->match_len); 793 int mlen = min(match_len, reg->match_len);
774 794
795 if (frame_type != le16_to_cpu(reg->frame_type))
796 continue;
797
775 if (memcmp(reg->match, match_data, mlen) == 0) { 798 if (memcmp(reg->match, match_data, mlen) == 0) {
776 err = -EALREADY; 799 err = -EALREADY;
777 break; 800 break;
@@ -786,140 +809,212 @@ int cfg80211_mlme_register_action(struct wireless_dev *wdev, u32 snd_pid,
786 memcpy(nreg->match, match_data, match_len); 809 memcpy(nreg->match, match_data, match_len);
787 nreg->match_len = match_len; 810 nreg->match_len = match_len;
788 nreg->nlpid = snd_pid; 811 nreg->nlpid = snd_pid;
789 list_add(&nreg->list, &wdev->action_registrations); 812 nreg->frame_type = cpu_to_le16(frame_type);
813 list_add(&nreg->list, &wdev->mgmt_registrations);
814
815 if (rdev->ops->mgmt_frame_register)
816 rdev->ops->mgmt_frame_register(wiphy, wdev->netdev,
817 frame_type, true);
790 818
791 out: 819 out:
792 spin_unlock_bh(&wdev->action_registrations_lock); 820 spin_unlock_bh(&wdev->mgmt_registrations_lock);
821
793 return err; 822 return err;
794} 823}
795 824
796void cfg80211_mlme_unregister_actions(struct wireless_dev *wdev, u32 nlpid) 825void cfg80211_mlme_unregister_socket(struct wireless_dev *wdev, u32 nlpid)
797{ 826{
798 struct cfg80211_action_registration *reg, *tmp; 827 struct wiphy *wiphy = wdev->wiphy;
828 struct cfg80211_registered_device *rdev = wiphy_to_dev(wiphy);
829 struct cfg80211_mgmt_registration *reg, *tmp;
799 830
800 spin_lock_bh(&wdev->action_registrations_lock); 831 spin_lock_bh(&wdev->mgmt_registrations_lock);
801 832
802 list_for_each_entry_safe(reg, tmp, &wdev->action_registrations, list) { 833 list_for_each_entry_safe(reg, tmp, &wdev->mgmt_registrations, list) {
803 if (reg->nlpid == nlpid) { 834 if (reg->nlpid != nlpid)
804 list_del(&reg->list); 835 continue;
805 kfree(reg); 836
837 if (rdev->ops->mgmt_frame_register) {
838 u16 frame_type = le16_to_cpu(reg->frame_type);
839
840 rdev->ops->mgmt_frame_register(wiphy, wdev->netdev,
841 frame_type, false);
806 } 842 }
843
844 list_del(&reg->list);
845 kfree(reg);
807 } 846 }
808 847
809 spin_unlock_bh(&wdev->action_registrations_lock); 848 spin_unlock_bh(&wdev->mgmt_registrations_lock);
810} 849}
811 850
812void cfg80211_mlme_purge_actions(struct wireless_dev *wdev) 851void cfg80211_mlme_purge_registrations(struct wireless_dev *wdev)
813{ 852{
814 struct cfg80211_action_registration *reg, *tmp; 853 struct cfg80211_mgmt_registration *reg, *tmp;
815 854
816 spin_lock_bh(&wdev->action_registrations_lock); 855 spin_lock_bh(&wdev->mgmt_registrations_lock);
817 856
818 list_for_each_entry_safe(reg, tmp, &wdev->action_registrations, list) { 857 list_for_each_entry_safe(reg, tmp, &wdev->mgmt_registrations, list) {
819 list_del(&reg->list); 858 list_del(&reg->list);
820 kfree(reg); 859 kfree(reg);
821 } 860 }
822 861
823 spin_unlock_bh(&wdev->action_registrations_lock); 862 spin_unlock_bh(&wdev->mgmt_registrations_lock);
824} 863}
825 864
826int cfg80211_mlme_action(struct cfg80211_registered_device *rdev, 865int cfg80211_mlme_mgmt_tx(struct cfg80211_registered_device *rdev,
827 struct net_device *dev, 866 struct net_device *dev,
828 struct ieee80211_channel *chan, 867 struct ieee80211_channel *chan,
829 enum nl80211_channel_type channel_type, 868 enum nl80211_channel_type channel_type,
830 bool channel_type_valid, 869 bool channel_type_valid,
831 const u8 *buf, size_t len, u64 *cookie) 870 const u8 *buf, size_t len, u64 *cookie)
832{ 871{
833 struct wireless_dev *wdev = dev->ieee80211_ptr; 872 struct wireless_dev *wdev = dev->ieee80211_ptr;
834 const struct ieee80211_mgmt *mgmt; 873 const struct ieee80211_mgmt *mgmt;
874 u16 stype;
835 875
836 if (rdev->ops->action == NULL) 876 if (!wdev->wiphy->mgmt_stypes)
837 return -EOPNOTSUPP; 877 return -EOPNOTSUPP;
878
879 if (!rdev->ops->mgmt_tx)
880 return -EOPNOTSUPP;
881
838 if (len < 24 + 1) 882 if (len < 24 + 1)
839 return -EINVAL; 883 return -EINVAL;
840 884
841 mgmt = (const struct ieee80211_mgmt *) buf; 885 mgmt = (const struct ieee80211_mgmt *) buf;
842 if (!ieee80211_is_action(mgmt->frame_control)) 886
887 if (!ieee80211_is_mgmt(mgmt->frame_control))
843 return -EINVAL; 888 return -EINVAL;
844 if (mgmt->u.action.category != WLAN_CATEGORY_PUBLIC) { 889
845 /* Verify that we are associated with the destination AP */ 890 stype = le16_to_cpu(mgmt->frame_control) & IEEE80211_FCTL_STYPE;
891 if (!(wdev->wiphy->mgmt_stypes[wdev->iftype].tx & BIT(stype >> 4)))
892 return -EINVAL;
893
894 if (ieee80211_is_action(mgmt->frame_control) &&
895 mgmt->u.action.category != WLAN_CATEGORY_PUBLIC) {
896 int err = 0;
897
846 wdev_lock(wdev); 898 wdev_lock(wdev);
847 899
848 if (!wdev->current_bss || 900 switch (wdev->iftype) {
849 memcmp(wdev->current_bss->pub.bssid, mgmt->bssid, 901 case NL80211_IFTYPE_ADHOC:
850 ETH_ALEN) != 0 || 902 case NL80211_IFTYPE_STATION:
851 (wdev->iftype == NL80211_IFTYPE_STATION && 903 case NL80211_IFTYPE_P2P_CLIENT:
852 memcmp(wdev->current_bss->pub.bssid, mgmt->da, 904 if (!wdev->current_bss) {
853 ETH_ALEN) != 0)) { 905 err = -ENOTCONN;
854 wdev_unlock(wdev); 906 break;
855 return -ENOTCONN; 907 }
856 } 908
909 if (memcmp(wdev->current_bss->pub.bssid,
910 mgmt->bssid, ETH_ALEN)) {
911 err = -ENOTCONN;
912 break;
913 }
914
915 /*
916 * check for IBSS DA must be done by driver as
917 * cfg80211 doesn't track the stations
918 */
919 if (wdev->iftype == NL80211_IFTYPE_ADHOC)
920 break;
857 921
922 /* for station, check that DA is the AP */
923 if (memcmp(wdev->current_bss->pub.bssid,
924 mgmt->da, ETH_ALEN)) {
925 err = -ENOTCONN;
926 break;
927 }
928 break;
929 case NL80211_IFTYPE_AP:
930 case NL80211_IFTYPE_P2P_GO:
931 case NL80211_IFTYPE_AP_VLAN:
932 if (memcmp(mgmt->bssid, dev->dev_addr, ETH_ALEN))
933 err = -EINVAL;
934 break;
935 default:
936 err = -EOPNOTSUPP;
937 break;
938 }
858 wdev_unlock(wdev); 939 wdev_unlock(wdev);
940
941 if (err)
942 return err;
859 } 943 }
860 944
861 if (memcmp(mgmt->sa, dev->dev_addr, ETH_ALEN) != 0) 945 if (memcmp(mgmt->sa, dev->dev_addr, ETH_ALEN) != 0)
862 return -EINVAL; 946 return -EINVAL;
863 947
864 /* Transmit the Action frame as requested by user space */ 948 /* Transmit the Action frame as requested by user space */
865 return rdev->ops->action(&rdev->wiphy, dev, chan, channel_type, 949 return rdev->ops->mgmt_tx(&rdev->wiphy, dev, chan, channel_type,
866 channel_type_valid, buf, len, cookie); 950 channel_type_valid, buf, len, cookie);
867} 951}
868 952
869bool cfg80211_rx_action(struct net_device *dev, int freq, const u8 *buf, 953bool cfg80211_rx_mgmt(struct net_device *dev, int freq, const u8 *buf,
870 size_t len, gfp_t gfp) 954 size_t len, gfp_t gfp)
871{ 955{
872 struct wireless_dev *wdev = dev->ieee80211_ptr; 956 struct wireless_dev *wdev = dev->ieee80211_ptr;
873 struct wiphy *wiphy = wdev->wiphy; 957 struct wiphy *wiphy = wdev->wiphy;
874 struct cfg80211_registered_device *rdev = wiphy_to_dev(wiphy); 958 struct cfg80211_registered_device *rdev = wiphy_to_dev(wiphy);
875 struct cfg80211_action_registration *reg; 959 struct cfg80211_mgmt_registration *reg;
876 const u8 *action_data; 960 const struct ieee80211_txrx_stypes *stypes =
877 int action_data_len; 961 &wiphy->mgmt_stypes[wdev->iftype];
962 struct ieee80211_mgmt *mgmt = (void *)buf;
963 const u8 *data;
964 int data_len;
878 bool result = false; 965 bool result = false;
966 __le16 ftype = mgmt->frame_control &
967 cpu_to_le16(IEEE80211_FCTL_FTYPE | IEEE80211_FCTL_STYPE);
968 u16 stype;
879 969
880 /* frame length - min size excluding category */ 970 stype = (le16_to_cpu(mgmt->frame_control) & IEEE80211_FCTL_STYPE) >> 4;
881 action_data_len = len - (IEEE80211_MIN_ACTION_SIZE - 1);
882 971
883 /* action data starts with category */ 972 if (!(stypes->rx & BIT(stype)))
884 action_data = buf + IEEE80211_MIN_ACTION_SIZE - 1; 973 return false;
885 974
886 spin_lock_bh(&wdev->action_registrations_lock); 975 data = buf + ieee80211_hdrlen(mgmt->frame_control);
976 data_len = len - ieee80211_hdrlen(mgmt->frame_control);
977
978 spin_lock_bh(&wdev->mgmt_registrations_lock);
979
980 list_for_each_entry(reg, &wdev->mgmt_registrations, list) {
981 if (reg->frame_type != ftype)
982 continue;
887 983
888 list_for_each_entry(reg, &wdev->action_registrations, list) { 984 if (reg->match_len > data_len)
889 if (reg->match_len > action_data_len)
890 continue; 985 continue;
891 986
892 if (memcmp(reg->match, action_data, reg->match_len)) 987 if (memcmp(reg->match, data, reg->match_len))
893 continue; 988 continue;
894 989
895 /* found match! */ 990 /* found match! */
896 991
897 /* Indicate the received Action frame to user space */ 992 /* Indicate the received Action frame to user space */
898 if (nl80211_send_action(rdev, dev, reg->nlpid, freq, 993 if (nl80211_send_mgmt(rdev, dev, reg->nlpid, freq,
899 buf, len, gfp)) 994 buf, len, gfp))
900 continue; 995 continue;
901 996
902 result = true; 997 result = true;
903 break; 998 break;
904 } 999 }
905 1000
906 spin_unlock_bh(&wdev->action_registrations_lock); 1001 spin_unlock_bh(&wdev->mgmt_registrations_lock);
907 1002
908 return result; 1003 return result;
909} 1004}
910EXPORT_SYMBOL(cfg80211_rx_action); 1005EXPORT_SYMBOL(cfg80211_rx_mgmt);
911 1006
912void cfg80211_action_tx_status(struct net_device *dev, u64 cookie, 1007void cfg80211_mgmt_tx_status(struct net_device *dev, u64 cookie,
913 const u8 *buf, size_t len, bool ack, gfp_t gfp) 1008 const u8 *buf, size_t len, bool ack, gfp_t gfp)
914{ 1009{
915 struct wireless_dev *wdev = dev->ieee80211_ptr; 1010 struct wireless_dev *wdev = dev->ieee80211_ptr;
916 struct wiphy *wiphy = wdev->wiphy; 1011 struct wiphy *wiphy = wdev->wiphy;
917 struct cfg80211_registered_device *rdev = wiphy_to_dev(wiphy); 1012 struct cfg80211_registered_device *rdev = wiphy_to_dev(wiphy);
918 1013
919 /* Indicate TX status of the Action frame to user space */ 1014 /* Indicate TX status of the Action frame to user space */
920 nl80211_send_action_tx_status(rdev, dev, cookie, buf, len, ack, gfp); 1015 nl80211_send_mgmt_tx_status(rdev, dev, cookie, buf, len, ack, gfp);
921} 1016}
922EXPORT_SYMBOL(cfg80211_action_tx_status); 1017EXPORT_SYMBOL(cfg80211_mgmt_tx_status);
923 1018
924void cfg80211_cqm_rssi_notify(struct net_device *dev, 1019void cfg80211_cqm_rssi_notify(struct net_device *dev,
925 enum nl80211_cqm_rssi_threshold_event rssi_event, 1020 enum nl80211_cqm_rssi_threshold_event rssi_event,
diff --git a/net/wireless/nl80211.c b/net/wireless/nl80211.c
index 37902a54e9c1..c506241f8637 100644
--- a/net/wireless/nl80211.c
+++ b/net/wireless/nl80211.c
@@ -23,6 +23,11 @@
23#include "nl80211.h" 23#include "nl80211.h"
24#include "reg.h" 24#include "reg.h"
25 25
26static int nl80211_pre_doit(struct genl_ops *ops, struct sk_buff *skb,
27 struct genl_info *info);
28static void nl80211_post_doit(struct genl_ops *ops, struct sk_buff *skb,
29 struct genl_info *info);
30
26/* the netlink family */ 31/* the netlink family */
27static struct genl_family nl80211_fam = { 32static struct genl_family nl80211_fam = {
28 .id = GENL_ID_GENERATE, /* don't bother with a hardcoded ID */ 33 .id = GENL_ID_GENERATE, /* don't bother with a hardcoded ID */
@@ -31,6 +36,8 @@ static struct genl_family nl80211_fam = {
31 .version = 1, /* no particular meaning now */ 36 .version = 1, /* no particular meaning now */
32 .maxattr = NL80211_ATTR_MAX, 37 .maxattr = NL80211_ATTR_MAX,
33 .netnsok = true, 38 .netnsok = true,
39 .pre_doit = nl80211_pre_doit,
40 .post_doit = nl80211_post_doit,
34}; 41};
35 42
36/* internal helper: get rdev and dev */ 43/* internal helper: get rdev and dev */
@@ -86,6 +93,7 @@ static const struct nla_policy nl80211_policy[NL80211_ATTR_MAX+1] = {
86 [NL80211_ATTR_KEY_CIPHER] = { .type = NLA_U32 }, 93 [NL80211_ATTR_KEY_CIPHER] = { .type = NLA_U32 },
87 [NL80211_ATTR_KEY_DEFAULT] = { .type = NLA_FLAG }, 94 [NL80211_ATTR_KEY_DEFAULT] = { .type = NLA_FLAG },
88 [NL80211_ATTR_KEY_SEQ] = { .type = NLA_BINARY, .len = 8 }, 95 [NL80211_ATTR_KEY_SEQ] = { .type = NLA_BINARY, .len = 8 },
96 [NL80211_ATTR_KEY_TYPE] = { .type = NLA_U32 },
89 97
90 [NL80211_ATTR_BEACON_INTERVAL] = { .type = NLA_U32 }, 98 [NL80211_ATTR_BEACON_INTERVAL] = { .type = NLA_U32 },
91 [NL80211_ATTR_DTIM_PERIOD] = { .type = NLA_U32 }, 99 [NL80211_ATTR_DTIM_PERIOD] = { .type = NLA_U32 },
@@ -136,6 +144,8 @@ static const struct nla_policy nl80211_policy[NL80211_ATTR_MAX+1] = {
136 .len = sizeof(struct nl80211_sta_flag_update), 144 .len = sizeof(struct nl80211_sta_flag_update),
137 }, 145 },
138 [NL80211_ATTR_CONTROL_PORT] = { .type = NLA_FLAG }, 146 [NL80211_ATTR_CONTROL_PORT] = { .type = NLA_FLAG },
147 [NL80211_ATTR_CONTROL_PORT_ETHERTYPE] = { .type = NLA_U16 },
148 [NL80211_ATTR_CONTROL_PORT_NO_ENCRYPT] = { .type = NLA_FLAG },
139 [NL80211_ATTR_PRIVACY] = { .type = NLA_FLAG }, 149 [NL80211_ATTR_PRIVACY] = { .type = NLA_FLAG },
140 [NL80211_ATTR_CIPHER_SUITE_GROUP] = { .type = NLA_U32 }, 150 [NL80211_ATTR_CIPHER_SUITE_GROUP] = { .type = NLA_U32 },
141 [NL80211_ATTR_WPA_VERSIONS] = { .type = NLA_U32 }, 151 [NL80211_ATTR_WPA_VERSIONS] = { .type = NLA_U32 },
@@ -156,9 +166,10 @@ static const struct nla_policy nl80211_policy[NL80211_ATTR_MAX+1] = {
156 166
157 [NL80211_ATTR_WIPHY_TX_POWER_SETTING] = { .type = NLA_U32 }, 167 [NL80211_ATTR_WIPHY_TX_POWER_SETTING] = { .type = NLA_U32 },
158 [NL80211_ATTR_WIPHY_TX_POWER_LEVEL] = { .type = NLA_U32 }, 168 [NL80211_ATTR_WIPHY_TX_POWER_LEVEL] = { .type = NLA_U32 },
169 [NL80211_ATTR_FRAME_TYPE] = { .type = NLA_U16 },
159}; 170};
160 171
161/* policy for the attributes */ 172/* policy for the key attributes */
162static const struct nla_policy nl80211_key_policy[NL80211_KEY_MAX + 1] = { 173static const struct nla_policy nl80211_key_policy[NL80211_KEY_MAX + 1] = {
163 [NL80211_KEY_DATA] = { .type = NLA_BINARY, .len = WLAN_MAX_KEY_LEN }, 174 [NL80211_KEY_DATA] = { .type = NLA_BINARY, .len = WLAN_MAX_KEY_LEN },
164 [NL80211_KEY_IDX] = { .type = NLA_U8 }, 175 [NL80211_KEY_IDX] = { .type = NLA_U8 },
@@ -166,6 +177,7 @@ static const struct nla_policy nl80211_key_policy[NL80211_KEY_MAX + 1] = {
166 [NL80211_KEY_SEQ] = { .type = NLA_BINARY, .len = 8 }, 177 [NL80211_KEY_SEQ] = { .type = NLA_BINARY, .len = 8 },
167 [NL80211_KEY_DEFAULT] = { .type = NLA_FLAG }, 178 [NL80211_KEY_DEFAULT] = { .type = NLA_FLAG },
168 [NL80211_KEY_DEFAULT_MGMT] = { .type = NLA_FLAG }, 179 [NL80211_KEY_DEFAULT_MGMT] = { .type = NLA_FLAG },
180 [NL80211_KEY_TYPE] = { .type = NLA_U32 },
169}; 181};
170 182
171/* ifidx get helper */ 183/* ifidx get helper */
@@ -188,6 +200,47 @@ static int nl80211_get_ifidx(struct netlink_callback *cb)
188 return res; 200 return res;
189} 201}
190 202
203static int nl80211_prepare_netdev_dump(struct sk_buff *skb,
204 struct netlink_callback *cb,
205 struct cfg80211_registered_device **rdev,
206 struct net_device **dev)
207{
208 int ifidx = cb->args[0];
209 int err;
210
211 if (!ifidx)
212 ifidx = nl80211_get_ifidx(cb);
213 if (ifidx < 0)
214 return ifidx;
215
216 cb->args[0] = ifidx;
217
218 rtnl_lock();
219
220 *dev = __dev_get_by_index(sock_net(skb->sk), ifidx);
221 if (!*dev) {
222 err = -ENODEV;
223 goto out_rtnl;
224 }
225
226 *rdev = cfg80211_get_dev_from_ifindex(sock_net(skb->sk), ifidx);
227 if (IS_ERR(dev)) {
228 err = PTR_ERR(dev);
229 goto out_rtnl;
230 }
231
232 return 0;
233 out_rtnl:
234 rtnl_unlock();
235 return err;
236}
237
238static void nl80211_finish_netdev_dump(struct cfg80211_registered_device *rdev)
239{
240 cfg80211_unlock_rdev(rdev);
241 rtnl_unlock();
242}
243
191/* IE validation */ 244/* IE validation */
192static bool is_valid_ie_attr(const struct nlattr *attr) 245static bool is_valid_ie_attr(const struct nlattr *attr)
193{ 246{
@@ -255,6 +308,7 @@ static int nl80211_msg_put_channel(struct sk_buff *msg,
255struct key_parse { 308struct key_parse {
256 struct key_params p; 309 struct key_params p;
257 int idx; 310 int idx;
311 int type;
258 bool def, defmgmt; 312 bool def, defmgmt;
259}; 313};
260 314
@@ -285,6 +339,12 @@ static int nl80211_parse_key_new(struct nlattr *key, struct key_parse *k)
285 if (tb[NL80211_KEY_CIPHER]) 339 if (tb[NL80211_KEY_CIPHER])
286 k->p.cipher = nla_get_u32(tb[NL80211_KEY_CIPHER]); 340 k->p.cipher = nla_get_u32(tb[NL80211_KEY_CIPHER]);
287 341
342 if (tb[NL80211_KEY_TYPE]) {
343 k->type = nla_get_u32(tb[NL80211_KEY_TYPE]);
344 if (k->type < 0 || k->type >= NUM_NL80211_KEYTYPES)
345 return -EINVAL;
346 }
347
288 return 0; 348 return 0;
289} 349}
290 350
@@ -309,6 +369,12 @@ static int nl80211_parse_key_old(struct genl_info *info, struct key_parse *k)
309 k->def = !!info->attrs[NL80211_ATTR_KEY_DEFAULT]; 369 k->def = !!info->attrs[NL80211_ATTR_KEY_DEFAULT];
310 k->defmgmt = !!info->attrs[NL80211_ATTR_KEY_DEFAULT_MGMT]; 370 k->defmgmt = !!info->attrs[NL80211_ATTR_KEY_DEFAULT_MGMT];
311 371
372 if (info->attrs[NL80211_ATTR_KEY_TYPE]) {
373 k->type = nla_get_u32(info->attrs[NL80211_ATTR_KEY_TYPE]);
374 if (k->type < 0 || k->type >= NUM_NL80211_KEYTYPES)
375 return -EINVAL;
376 }
377
312 return 0; 378 return 0;
313} 379}
314 380
@@ -318,6 +384,7 @@ static int nl80211_parse_key(struct genl_info *info, struct key_parse *k)
318 384
319 memset(k, 0, sizeof(*k)); 385 memset(k, 0, sizeof(*k));
320 k->idx = -1; 386 k->idx = -1;
387 k->type = -1;
321 388
322 if (info->attrs[NL80211_ATTR_KEY]) 389 if (info->attrs[NL80211_ATTR_KEY])
323 err = nl80211_parse_key_new(info->attrs[NL80211_ATTR_KEY], k); 390 err = nl80211_parse_key_new(info->attrs[NL80211_ATTR_KEY], k);
@@ -382,7 +449,7 @@ nl80211_parse_connkeys(struct cfg80211_registered_device *rdev,
382 } else if (parse.defmgmt) 449 } else if (parse.defmgmt)
383 goto error; 450 goto error;
384 err = cfg80211_validate_key_settings(rdev, &parse.p, 451 err = cfg80211_validate_key_settings(rdev, &parse.p,
385 parse.idx, NULL); 452 parse.idx, false, NULL);
386 if (err) 453 if (err)
387 goto error; 454 goto error;
388 result->params[parse.idx].cipher = parse.p.cipher; 455 result->params[parse.idx].cipher = parse.p.cipher;
@@ -401,18 +468,17 @@ static int nl80211_key_allowed(struct wireless_dev *wdev)
401{ 468{
402 ASSERT_WDEV_LOCK(wdev); 469 ASSERT_WDEV_LOCK(wdev);
403 470
404 if (!netif_running(wdev->netdev))
405 return -ENETDOWN;
406
407 switch (wdev->iftype) { 471 switch (wdev->iftype) {
408 case NL80211_IFTYPE_AP: 472 case NL80211_IFTYPE_AP:
409 case NL80211_IFTYPE_AP_VLAN: 473 case NL80211_IFTYPE_AP_VLAN:
474 case NL80211_IFTYPE_P2P_GO:
410 break; 475 break;
411 case NL80211_IFTYPE_ADHOC: 476 case NL80211_IFTYPE_ADHOC:
412 if (!wdev->current_bss) 477 if (!wdev->current_bss)
413 return -ENOLINK; 478 return -ENOLINK;
414 break; 479 break;
415 case NL80211_IFTYPE_STATION: 480 case NL80211_IFTYPE_STATION:
481 case NL80211_IFTYPE_P2P_CLIENT:
416 if (wdev->sme_state != CFG80211_SME_CONNECTED) 482 if (wdev->sme_state != CFG80211_SME_CONNECTED)
417 return -ENOLINK; 483 return -ENOLINK;
418 break; 484 break;
@@ -437,6 +503,8 @@ static int nl80211_send_wiphy(struct sk_buff *msg, u32 pid, u32 seq, int flags,
437 struct ieee80211_rate *rate; 503 struct ieee80211_rate *rate;
438 int i; 504 int i;
439 u16 ifmodes = dev->wiphy.interface_modes; 505 u16 ifmodes = dev->wiphy.interface_modes;
506 const struct ieee80211_txrx_stypes *mgmt_stypes =
507 dev->wiphy.mgmt_stypes;
440 508
441 hdr = nl80211hdr_put(msg, pid, seq, flags, NL80211_CMD_NEW_WIPHY); 509 hdr = nl80211hdr_put(msg, pid, seq, flags, NL80211_CMD_NEW_WIPHY);
442 if (!hdr) 510 if (!hdr)
@@ -464,6 +532,9 @@ static int nl80211_send_wiphy(struct sk_buff *msg, u32 pid, u32 seq, int flags,
464 NLA_PUT_U16(msg, NL80211_ATTR_MAX_SCAN_IE_LEN, 532 NLA_PUT_U16(msg, NL80211_ATTR_MAX_SCAN_IE_LEN,
465 dev->wiphy.max_scan_ie_len); 533 dev->wiphy.max_scan_ie_len);
466 534
535 if (dev->wiphy.flags & WIPHY_FLAG_IBSS_RSN)
536 NLA_PUT_FLAG(msg, NL80211_ATTR_SUPPORT_IBSS_RSN);
537
467 NLA_PUT(msg, NL80211_ATTR_CIPHER_SUITES, 538 NLA_PUT(msg, NL80211_ATTR_CIPHER_SUITES,
468 sizeof(u32) * dev->wiphy.n_cipher_suites, 539 sizeof(u32) * dev->wiphy.n_cipher_suites,
469 dev->wiphy.cipher_suites); 540 dev->wiphy.cipher_suites);
@@ -471,6 +542,9 @@ static int nl80211_send_wiphy(struct sk_buff *msg, u32 pid, u32 seq, int flags,
471 NLA_PUT_U8(msg, NL80211_ATTR_MAX_NUM_PMKIDS, 542 NLA_PUT_U8(msg, NL80211_ATTR_MAX_NUM_PMKIDS,
472 dev->wiphy.max_num_pmkids); 543 dev->wiphy.max_num_pmkids);
473 544
545 if (dev->wiphy.flags & WIPHY_FLAG_CONTROL_PORT_PROTOCOL)
546 NLA_PUT_FLAG(msg, NL80211_ATTR_CONTROL_PORT_ETHERTYPE);
547
474 nl_modes = nla_nest_start(msg, NL80211_ATTR_SUPPORTED_IFTYPES); 548 nl_modes = nla_nest_start(msg, NL80211_ATTR_SUPPORTED_IFTYPES);
475 if (!nl_modes) 549 if (!nl_modes)
476 goto nla_put_failure; 550 goto nla_put_failure;
@@ -587,12 +661,13 @@ static int nl80211_send_wiphy(struct sk_buff *msg, u32 pid, u32 seq, int flags,
587 CMD(flush_pmksa, FLUSH_PMKSA); 661 CMD(flush_pmksa, FLUSH_PMKSA);
588 CMD(remain_on_channel, REMAIN_ON_CHANNEL); 662 CMD(remain_on_channel, REMAIN_ON_CHANNEL);
589 CMD(set_bitrate_mask, SET_TX_BITRATE_MASK); 663 CMD(set_bitrate_mask, SET_TX_BITRATE_MASK);
590 CMD(action, ACTION); 664 CMD(mgmt_tx, FRAME);
591 if (dev->wiphy.flags & WIPHY_FLAG_NETNS_OK) { 665 if (dev->wiphy.flags & WIPHY_FLAG_NETNS_OK) {
592 i++; 666 i++;
593 NLA_PUT_U32(msg, i, NL80211_CMD_SET_WIPHY_NETNS); 667 NLA_PUT_U32(msg, i, NL80211_CMD_SET_WIPHY_NETNS);
594 } 668 }
595 CMD(set_channel, SET_CHANNEL); 669 CMD(set_channel, SET_CHANNEL);
670 CMD(set_wds_peer, SET_WDS_PEER);
596 671
597#undef CMD 672#undef CMD
598 673
@@ -608,6 +683,55 @@ static int nl80211_send_wiphy(struct sk_buff *msg, u32 pid, u32 seq, int flags,
608 683
609 nla_nest_end(msg, nl_cmds); 684 nla_nest_end(msg, nl_cmds);
610 685
686 if (mgmt_stypes) {
687 u16 stypes;
688 struct nlattr *nl_ftypes, *nl_ifs;
689 enum nl80211_iftype ift;
690
691 nl_ifs = nla_nest_start(msg, NL80211_ATTR_TX_FRAME_TYPES);
692 if (!nl_ifs)
693 goto nla_put_failure;
694
695 for (ift = 0; ift < NUM_NL80211_IFTYPES; ift++) {
696 nl_ftypes = nla_nest_start(msg, ift);
697 if (!nl_ftypes)
698 goto nla_put_failure;
699 i = 0;
700 stypes = mgmt_stypes[ift].tx;
701 while (stypes) {
702 if (stypes & 1)
703 NLA_PUT_U16(msg, NL80211_ATTR_FRAME_TYPE,
704 (i << 4) | IEEE80211_FTYPE_MGMT);
705 stypes >>= 1;
706 i++;
707 }
708 nla_nest_end(msg, nl_ftypes);
709 }
710
711 nla_nest_end(msg, nl_ifs);
712
713 nl_ifs = nla_nest_start(msg, NL80211_ATTR_RX_FRAME_TYPES);
714 if (!nl_ifs)
715 goto nla_put_failure;
716
717 for (ift = 0; ift < NUM_NL80211_IFTYPES; ift++) {
718 nl_ftypes = nla_nest_start(msg, ift);
719 if (!nl_ftypes)
720 goto nla_put_failure;
721 i = 0;
722 stypes = mgmt_stypes[ift].rx;
723 while (stypes) {
724 if (stypes & 1)
725 NLA_PUT_U16(msg, NL80211_ATTR_FRAME_TYPE,
726 (i << 4) | IEEE80211_FTYPE_MGMT);
727 stypes >>= 1;
728 i++;
729 }
730 nla_nest_end(msg, nl_ftypes);
731 }
732 nla_nest_end(msg, nl_ifs);
733 }
734
611 return genlmsg_end(msg, hdr); 735 return genlmsg_end(msg, hdr);
612 736
613 nla_put_failure: 737 nla_put_failure:
@@ -644,28 +768,18 @@ static int nl80211_dump_wiphy(struct sk_buff *skb, struct netlink_callback *cb)
644static int nl80211_get_wiphy(struct sk_buff *skb, struct genl_info *info) 768static int nl80211_get_wiphy(struct sk_buff *skb, struct genl_info *info)
645{ 769{
646 struct sk_buff *msg; 770 struct sk_buff *msg;
647 struct cfg80211_registered_device *dev; 771 struct cfg80211_registered_device *dev = info->user_ptr[0];
648
649 dev = cfg80211_get_dev_from_info(info);
650 if (IS_ERR(dev))
651 return PTR_ERR(dev);
652 772
653 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL); 773 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
654 if (!msg) 774 if (!msg)
655 goto out_err; 775 return -ENOMEM;
656
657 if (nl80211_send_wiphy(msg, info->snd_pid, info->snd_seq, 0, dev) < 0)
658 goto out_free;
659 776
660 cfg80211_unlock_rdev(dev); 777 if (nl80211_send_wiphy(msg, info->snd_pid, info->snd_seq, 0, dev) < 0) {
778 nlmsg_free(msg);
779 return -ENOBUFS;
780 }
661 781
662 return genlmsg_reply(msg, info); 782 return genlmsg_reply(msg, info);
663
664 out_free:
665 nlmsg_free(msg);
666 out_err:
667 cfg80211_unlock_rdev(dev);
668 return -ENOBUFS;
669} 783}
670 784
671static const struct nla_policy txq_params_policy[NL80211_TXQ_ATTR_MAX + 1] = { 785static const struct nla_policy txq_params_policy[NL80211_TXQ_ATTR_MAX + 1] = {
@@ -709,7 +823,8 @@ static bool nl80211_can_set_dev_channel(struct wireless_dev *wdev)
709 wdev->iftype == NL80211_IFTYPE_AP || 823 wdev->iftype == NL80211_IFTYPE_AP ||
710 wdev->iftype == NL80211_IFTYPE_WDS || 824 wdev->iftype == NL80211_IFTYPE_WDS ||
711 wdev->iftype == NL80211_IFTYPE_MESH_POINT || 825 wdev->iftype == NL80211_IFTYPE_MESH_POINT ||
712 wdev->iftype == NL80211_IFTYPE_MONITOR; 826 wdev->iftype == NL80211_IFTYPE_MONITOR ||
827 wdev->iftype == NL80211_IFTYPE_P2P_GO;
713} 828}
714 829
715static int __nl80211_set_channel(struct cfg80211_registered_device *rdev, 830static int __nl80211_set_channel(struct cfg80211_registered_device *rdev,
@@ -753,38 +868,48 @@ static int __nl80211_set_channel(struct cfg80211_registered_device *rdev,
753 868
754static int nl80211_set_channel(struct sk_buff *skb, struct genl_info *info) 869static int nl80211_set_channel(struct sk_buff *skb, struct genl_info *info)
755{ 870{
756 struct cfg80211_registered_device *rdev; 871 struct cfg80211_registered_device *rdev = info->user_ptr[0];
757 struct net_device *netdev; 872 struct net_device *netdev = info->user_ptr[1];
758 int result;
759 873
760 rtnl_lock(); 874 return __nl80211_set_channel(rdev, netdev->ieee80211_ptr, info);
875}
761 876
762 result = get_rdev_dev_by_info_ifindex(info, &rdev, &netdev); 877static int nl80211_set_wds_peer(struct sk_buff *skb, struct genl_info *info)
763 if (result) 878{
764 goto unlock; 879 struct cfg80211_registered_device *rdev = info->user_ptr[0];
880 struct net_device *dev = info->user_ptr[1];
881 struct wireless_dev *wdev = dev->ieee80211_ptr;
882 const u8 *bssid;
765 883
766 result = __nl80211_set_channel(rdev, netdev->ieee80211_ptr, info); 884 if (!info->attrs[NL80211_ATTR_MAC])
885 return -EINVAL;
767 886
768 unlock: 887 if (netif_running(dev))
769 rtnl_unlock(); 888 return -EBUSY;
770 889
771 return result; 890 if (!rdev->ops->set_wds_peer)
891 return -EOPNOTSUPP;
892
893 if (wdev->iftype != NL80211_IFTYPE_WDS)
894 return -EOPNOTSUPP;
895
896 bssid = nla_data(info->attrs[NL80211_ATTR_MAC]);
897 return rdev->ops->set_wds_peer(wdev->wiphy, dev, bssid);
772} 898}
773 899
900
774static int nl80211_set_wiphy(struct sk_buff *skb, struct genl_info *info) 901static int nl80211_set_wiphy(struct sk_buff *skb, struct genl_info *info)
775{ 902{
776 struct cfg80211_registered_device *rdev; 903 struct cfg80211_registered_device *rdev;
777 struct net_device *netdev = NULL; 904 struct net_device *netdev = NULL;
778 struct wireless_dev *wdev; 905 struct wireless_dev *wdev;
779 int result, rem_txq_params = 0; 906 int result = 0, rem_txq_params = 0;
780 struct nlattr *nl_txq_params; 907 struct nlattr *nl_txq_params;
781 u32 changed; 908 u32 changed;
782 u8 retry_short = 0, retry_long = 0; 909 u8 retry_short = 0, retry_long = 0;
783 u32 frag_threshold = 0, rts_threshold = 0; 910 u32 frag_threshold = 0, rts_threshold = 0;
784 u8 coverage_class = 0; 911 u8 coverage_class = 0;
785 912
786 rtnl_lock();
787
788 /* 913 /*
789 * Try to find the wiphy and netdev. Normally this 914 * Try to find the wiphy and netdev. Normally this
790 * function shouldn't need the netdev, but this is 915 * function shouldn't need the netdev, but this is
@@ -811,8 +936,7 @@ static int nl80211_set_wiphy(struct sk_buff *skb, struct genl_info *info)
811 rdev = __cfg80211_rdev_from_info(info); 936 rdev = __cfg80211_rdev_from_info(info);
812 if (IS_ERR(rdev)) { 937 if (IS_ERR(rdev)) {
813 mutex_unlock(&cfg80211_mutex); 938 mutex_unlock(&cfg80211_mutex);
814 result = PTR_ERR(rdev); 939 return PTR_ERR(rdev);
815 goto unlock;
816 } 940 }
817 wdev = NULL; 941 wdev = NULL;
818 netdev = NULL; 942 netdev = NULL;
@@ -994,8 +1118,6 @@ static int nl80211_set_wiphy(struct sk_buff *skb, struct genl_info *info)
994 mutex_unlock(&rdev->mtx); 1118 mutex_unlock(&rdev->mtx);
995 if (netdev) 1119 if (netdev)
996 dev_put(netdev); 1120 dev_put(netdev);
997 unlock:
998 rtnl_unlock();
999 return result; 1121 return result;
1000} 1122}
1001 1123
@@ -1075,33 +1197,20 @@ static int nl80211_dump_interface(struct sk_buff *skb, struct netlink_callback *
1075static int nl80211_get_interface(struct sk_buff *skb, struct genl_info *info) 1197static int nl80211_get_interface(struct sk_buff *skb, struct genl_info *info)
1076{ 1198{
1077 struct sk_buff *msg; 1199 struct sk_buff *msg;
1078 struct cfg80211_registered_device *dev; 1200 struct cfg80211_registered_device *dev = info->user_ptr[0];
1079 struct net_device *netdev; 1201 struct net_device *netdev = info->user_ptr[1];
1080 int err;
1081
1082 err = get_rdev_dev_by_info_ifindex(info, &dev, &netdev);
1083 if (err)
1084 return err;
1085 1202
1086 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL); 1203 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
1087 if (!msg) 1204 if (!msg)
1088 goto out_err; 1205 return -ENOMEM;
1089 1206
1090 if (nl80211_send_iface(msg, info->snd_pid, info->snd_seq, 0, 1207 if (nl80211_send_iface(msg, info->snd_pid, info->snd_seq, 0,
1091 dev, netdev) < 0) 1208 dev, netdev) < 0) {
1092 goto out_free; 1209 nlmsg_free(msg);
1093 1210 return -ENOBUFS;
1094 dev_put(netdev); 1211 }
1095 cfg80211_unlock_rdev(dev);
1096 1212
1097 return genlmsg_reply(msg, info); 1213 return genlmsg_reply(msg, info);
1098
1099 out_free:
1100 nlmsg_free(msg);
1101 out_err:
1102 dev_put(netdev);
1103 cfg80211_unlock_rdev(dev);
1104 return -ENOBUFS;
1105} 1214}
1106 1215
1107static const struct nla_policy mntr_flags_policy[NL80211_MNTR_FLAG_MAX + 1] = { 1216static const struct nla_policy mntr_flags_policy[NL80211_MNTR_FLAG_MAX + 1] = {
@@ -1161,39 +1270,29 @@ static int nl80211_valid_4addr(struct cfg80211_registered_device *rdev,
1161 1270
1162static int nl80211_set_interface(struct sk_buff *skb, struct genl_info *info) 1271static int nl80211_set_interface(struct sk_buff *skb, struct genl_info *info)
1163{ 1272{
1164 struct cfg80211_registered_device *rdev; 1273 struct cfg80211_registered_device *rdev = info->user_ptr[0];
1165 struct vif_params params; 1274 struct vif_params params;
1166 int err; 1275 int err;
1167 enum nl80211_iftype otype, ntype; 1276 enum nl80211_iftype otype, ntype;
1168 struct net_device *dev; 1277 struct net_device *dev = info->user_ptr[1];
1169 u32 _flags, *flags = NULL; 1278 u32 _flags, *flags = NULL;
1170 bool change = false; 1279 bool change = false;
1171 1280
1172 memset(&params, 0, sizeof(params)); 1281 memset(&params, 0, sizeof(params));
1173 1282
1174 rtnl_lock();
1175
1176 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
1177 if (err)
1178 goto unlock_rtnl;
1179
1180 otype = ntype = dev->ieee80211_ptr->iftype; 1283 otype = ntype = dev->ieee80211_ptr->iftype;
1181 1284
1182 if (info->attrs[NL80211_ATTR_IFTYPE]) { 1285 if (info->attrs[NL80211_ATTR_IFTYPE]) {
1183 ntype = nla_get_u32(info->attrs[NL80211_ATTR_IFTYPE]); 1286 ntype = nla_get_u32(info->attrs[NL80211_ATTR_IFTYPE]);
1184 if (otype != ntype) 1287 if (otype != ntype)
1185 change = true; 1288 change = true;
1186 if (ntype > NL80211_IFTYPE_MAX) { 1289 if (ntype > NL80211_IFTYPE_MAX)
1187 err = -EINVAL; 1290 return -EINVAL;
1188 goto unlock;
1189 }
1190 } 1291 }
1191 1292
1192 if (info->attrs[NL80211_ATTR_MESH_ID]) { 1293 if (info->attrs[NL80211_ATTR_MESH_ID]) {
1193 if (ntype != NL80211_IFTYPE_MESH_POINT) { 1294 if (ntype != NL80211_IFTYPE_MESH_POINT)
1194 err = -EINVAL; 1295 return -EINVAL;
1195 goto unlock;
1196 }
1197 params.mesh_id = nla_data(info->attrs[NL80211_ATTR_MESH_ID]); 1296 params.mesh_id = nla_data(info->attrs[NL80211_ATTR_MESH_ID]);
1198 params.mesh_id_len = nla_len(info->attrs[NL80211_ATTR_MESH_ID]); 1297 params.mesh_id_len = nla_len(info->attrs[NL80211_ATTR_MESH_ID]);
1199 change = true; 1298 change = true;
@@ -1204,20 +1303,18 @@ static int nl80211_set_interface(struct sk_buff *skb, struct genl_info *info)
1204 change = true; 1303 change = true;
1205 err = nl80211_valid_4addr(rdev, dev, params.use_4addr, ntype); 1304 err = nl80211_valid_4addr(rdev, dev, params.use_4addr, ntype);
1206 if (err) 1305 if (err)
1207 goto unlock; 1306 return err;
1208 } else { 1307 } else {
1209 params.use_4addr = -1; 1308 params.use_4addr = -1;
1210 } 1309 }
1211 1310
1212 if (info->attrs[NL80211_ATTR_MNTR_FLAGS]) { 1311 if (info->attrs[NL80211_ATTR_MNTR_FLAGS]) {
1213 if (ntype != NL80211_IFTYPE_MONITOR) { 1312 if (ntype != NL80211_IFTYPE_MONITOR)
1214 err = -EINVAL; 1313 return -EINVAL;
1215 goto unlock;
1216 }
1217 err = parse_monitor_flags(info->attrs[NL80211_ATTR_MNTR_FLAGS], 1314 err = parse_monitor_flags(info->attrs[NL80211_ATTR_MNTR_FLAGS],
1218 &_flags); 1315 &_flags);
1219 if (err) 1316 if (err)
1220 goto unlock; 1317 return err;
1221 1318
1222 flags = &_flags; 1319 flags = &_flags;
1223 change = true; 1320 change = true;
@@ -1231,17 +1328,12 @@ static int nl80211_set_interface(struct sk_buff *skb, struct genl_info *info)
1231 if (!err && params.use_4addr != -1) 1328 if (!err && params.use_4addr != -1)
1232 dev->ieee80211_ptr->use_4addr = params.use_4addr; 1329 dev->ieee80211_ptr->use_4addr = params.use_4addr;
1233 1330
1234 unlock:
1235 dev_put(dev);
1236 cfg80211_unlock_rdev(rdev);
1237 unlock_rtnl:
1238 rtnl_unlock();
1239 return err; 1331 return err;
1240} 1332}
1241 1333
1242static int nl80211_new_interface(struct sk_buff *skb, struct genl_info *info) 1334static int nl80211_new_interface(struct sk_buff *skb, struct genl_info *info)
1243{ 1335{
1244 struct cfg80211_registered_device *rdev; 1336 struct cfg80211_registered_device *rdev = info->user_ptr[0];
1245 struct vif_params params; 1337 struct vif_params params;
1246 int err; 1338 int err;
1247 enum nl80211_iftype type = NL80211_IFTYPE_UNSPECIFIED; 1339 enum nl80211_iftype type = NL80211_IFTYPE_UNSPECIFIED;
@@ -1258,19 +1350,9 @@ static int nl80211_new_interface(struct sk_buff *skb, struct genl_info *info)
1258 return -EINVAL; 1350 return -EINVAL;
1259 } 1351 }
1260 1352
1261 rtnl_lock();
1262
1263 rdev = cfg80211_get_dev_from_info(info);
1264 if (IS_ERR(rdev)) {
1265 err = PTR_ERR(rdev);
1266 goto unlock_rtnl;
1267 }
1268
1269 if (!rdev->ops->add_virtual_intf || 1353 if (!rdev->ops->add_virtual_intf ||
1270 !(rdev->wiphy.interface_modes & (1 << type))) { 1354 !(rdev->wiphy.interface_modes & (1 << type)))
1271 err = -EOPNOTSUPP; 1355 return -EOPNOTSUPP;
1272 goto unlock;
1273 }
1274 1356
1275 if (type == NL80211_IFTYPE_MESH_POINT && 1357 if (type == NL80211_IFTYPE_MESH_POINT &&
1276 info->attrs[NL80211_ATTR_MESH_ID]) { 1358 info->attrs[NL80211_ATTR_MESH_ID]) {
@@ -1282,7 +1364,7 @@ static int nl80211_new_interface(struct sk_buff *skb, struct genl_info *info)
1282 params.use_4addr = !!nla_get_u8(info->attrs[NL80211_ATTR_4ADDR]); 1364 params.use_4addr = !!nla_get_u8(info->attrs[NL80211_ATTR_4ADDR]);
1283 err = nl80211_valid_4addr(rdev, NULL, params.use_4addr, type); 1365 err = nl80211_valid_4addr(rdev, NULL, params.use_4addr, type);
1284 if (err) 1366 if (err)
1285 goto unlock; 1367 return err;
1286 } 1368 }
1287 1369
1288 err = parse_monitor_flags(type == NL80211_IFTYPE_MONITOR ? 1370 err = parse_monitor_flags(type == NL80211_IFTYPE_MONITOR ?
@@ -1292,38 +1374,18 @@ static int nl80211_new_interface(struct sk_buff *skb, struct genl_info *info)
1292 nla_data(info->attrs[NL80211_ATTR_IFNAME]), 1374 nla_data(info->attrs[NL80211_ATTR_IFNAME]),
1293 type, err ? NULL : &flags, &params); 1375 type, err ? NULL : &flags, &params);
1294 1376
1295 unlock:
1296 cfg80211_unlock_rdev(rdev);
1297 unlock_rtnl:
1298 rtnl_unlock();
1299 return err; 1377 return err;
1300} 1378}
1301 1379
1302static int nl80211_del_interface(struct sk_buff *skb, struct genl_info *info) 1380static int nl80211_del_interface(struct sk_buff *skb, struct genl_info *info)
1303{ 1381{
1304 struct cfg80211_registered_device *rdev; 1382 struct cfg80211_registered_device *rdev = info->user_ptr[0];
1305 int err; 1383 struct net_device *dev = info->user_ptr[1];
1306 struct net_device *dev;
1307 1384
1308 rtnl_lock(); 1385 if (!rdev->ops->del_virtual_intf)
1309 1386 return -EOPNOTSUPP;
1310 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
1311 if (err)
1312 goto unlock_rtnl;
1313
1314 if (!rdev->ops->del_virtual_intf) {
1315 err = -EOPNOTSUPP;
1316 goto out;
1317 }
1318
1319 err = rdev->ops->del_virtual_intf(&rdev->wiphy, dev);
1320 1387
1321 out: 1388 return rdev->ops->del_virtual_intf(&rdev->wiphy, dev);
1322 cfg80211_unlock_rdev(rdev);
1323 dev_put(dev);
1324 unlock_rtnl:
1325 rtnl_unlock();
1326 return err;
1327} 1389}
1328 1390
1329struct get_key_cookie { 1391struct get_key_cookie {
@@ -1376,11 +1438,12 @@ static void get_key_callback(void *c, struct key_params *params)
1376 1438
1377static int nl80211_get_key(struct sk_buff *skb, struct genl_info *info) 1439static int nl80211_get_key(struct sk_buff *skb, struct genl_info *info)
1378{ 1440{
1379 struct cfg80211_registered_device *rdev; 1441 struct cfg80211_registered_device *rdev = info->user_ptr[0];
1380 int err; 1442 int err;
1381 struct net_device *dev; 1443 struct net_device *dev = info->user_ptr[1];
1382 u8 key_idx = 0; 1444 u8 key_idx = 0;
1383 u8 *mac_addr = NULL; 1445 const u8 *mac_addr = NULL;
1446 bool pairwise;
1384 struct get_key_cookie cookie = { 1447 struct get_key_cookie cookie = {
1385 .error = 0, 1448 .error = 0,
1386 }; 1449 };
@@ -1396,30 +1459,28 @@ static int nl80211_get_key(struct sk_buff *skb, struct genl_info *info)
1396 if (info->attrs[NL80211_ATTR_MAC]) 1459 if (info->attrs[NL80211_ATTR_MAC])
1397 mac_addr = nla_data(info->attrs[NL80211_ATTR_MAC]); 1460 mac_addr = nla_data(info->attrs[NL80211_ATTR_MAC]);
1398 1461
1399 rtnl_lock(); 1462 pairwise = !!mac_addr;
1400 1463 if (info->attrs[NL80211_ATTR_KEY_TYPE]) {
1401 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev); 1464 u32 kt = nla_get_u32(info->attrs[NL80211_ATTR_KEY_TYPE]);
1402 if (err) 1465 if (kt >= NUM_NL80211_KEYTYPES)
1403 goto unlock_rtnl; 1466 return -EINVAL;
1404 1467 if (kt != NL80211_KEYTYPE_GROUP &&
1405 if (!rdev->ops->get_key) { 1468 kt != NL80211_KEYTYPE_PAIRWISE)
1406 err = -EOPNOTSUPP; 1469 return -EINVAL;
1407 goto out; 1470 pairwise = kt == NL80211_KEYTYPE_PAIRWISE;
1408 } 1471 }
1409 1472
1473 if (!rdev->ops->get_key)
1474 return -EOPNOTSUPP;
1475
1410 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL); 1476 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
1411 if (!msg) { 1477 if (!msg)
1412 err = -ENOMEM; 1478 return -ENOMEM;
1413 goto out;
1414 }
1415 1479
1416 hdr = nl80211hdr_put(msg, info->snd_pid, info->snd_seq, 0, 1480 hdr = nl80211hdr_put(msg, info->snd_pid, info->snd_seq, 0,
1417 NL80211_CMD_NEW_KEY); 1481 NL80211_CMD_NEW_KEY);
1418 1482 if (IS_ERR(hdr))
1419 if (IS_ERR(hdr)) { 1483 return PTR_ERR(hdr);
1420 err = PTR_ERR(hdr);
1421 goto free_msg;
1422 }
1423 1484
1424 cookie.msg = msg; 1485 cookie.msg = msg;
1425 cookie.idx = key_idx; 1486 cookie.idx = key_idx;
@@ -1429,8 +1490,12 @@ static int nl80211_get_key(struct sk_buff *skb, struct genl_info *info)
1429 if (mac_addr) 1490 if (mac_addr)
1430 NLA_PUT(msg, NL80211_ATTR_MAC, ETH_ALEN, mac_addr); 1491 NLA_PUT(msg, NL80211_ATTR_MAC, ETH_ALEN, mac_addr);
1431 1492
1432 err = rdev->ops->get_key(&rdev->wiphy, dev, key_idx, mac_addr, 1493 if (pairwise && mac_addr &&
1433 &cookie, get_key_callback); 1494 !(rdev->wiphy.flags & WIPHY_FLAG_IBSS_RSN))
1495 return -ENOENT;
1496
1497 err = rdev->ops->get_key(&rdev->wiphy, dev, key_idx, pairwise,
1498 mac_addr, &cookie, get_key_callback);
1434 1499
1435 if (err) 1500 if (err)
1436 goto free_msg; 1501 goto free_msg;
@@ -1439,28 +1504,21 @@ static int nl80211_get_key(struct sk_buff *skb, struct genl_info *info)
1439 goto nla_put_failure; 1504 goto nla_put_failure;
1440 1505
1441 genlmsg_end(msg, hdr); 1506 genlmsg_end(msg, hdr);
1442 err = genlmsg_reply(msg, info); 1507 return genlmsg_reply(msg, info);
1443 goto out;
1444 1508
1445 nla_put_failure: 1509 nla_put_failure:
1446 err = -ENOBUFS; 1510 err = -ENOBUFS;
1447 free_msg: 1511 free_msg:
1448 nlmsg_free(msg); 1512 nlmsg_free(msg);
1449 out:
1450 cfg80211_unlock_rdev(rdev);
1451 dev_put(dev);
1452 unlock_rtnl:
1453 rtnl_unlock();
1454
1455 return err; 1513 return err;
1456} 1514}
1457 1515
1458static int nl80211_set_key(struct sk_buff *skb, struct genl_info *info) 1516static int nl80211_set_key(struct sk_buff *skb, struct genl_info *info)
1459{ 1517{
1460 struct cfg80211_registered_device *rdev; 1518 struct cfg80211_registered_device *rdev = info->user_ptr[0];
1461 struct key_parse key; 1519 struct key_parse key;
1462 int err; 1520 int err;
1463 struct net_device *dev; 1521 struct net_device *dev = info->user_ptr[1];
1464 int (*func)(struct wiphy *wiphy, struct net_device *netdev, 1522 int (*func)(struct wiphy *wiphy, struct net_device *netdev,
1465 u8 key_index); 1523 u8 key_index);
1466 1524
@@ -1475,21 +1533,13 @@ static int nl80211_set_key(struct sk_buff *skb, struct genl_info *info)
1475 if (!key.def && !key.defmgmt) 1533 if (!key.def && !key.defmgmt)
1476 return -EINVAL; 1534 return -EINVAL;
1477 1535
1478 rtnl_lock();
1479
1480 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
1481 if (err)
1482 goto unlock_rtnl;
1483
1484 if (key.def) 1536 if (key.def)
1485 func = rdev->ops->set_default_key; 1537 func = rdev->ops->set_default_key;
1486 else 1538 else
1487 func = rdev->ops->set_default_mgmt_key; 1539 func = rdev->ops->set_default_mgmt_key;
1488 1540
1489 if (!func) { 1541 if (!func)
1490 err = -EOPNOTSUPP; 1542 return -EOPNOTSUPP;
1491 goto out;
1492 }
1493 1543
1494 wdev_lock(dev->ieee80211_ptr); 1544 wdev_lock(dev->ieee80211_ptr);
1495 err = nl80211_key_allowed(dev->ieee80211_ptr); 1545 err = nl80211_key_allowed(dev->ieee80211_ptr);
@@ -1506,23 +1556,16 @@ static int nl80211_set_key(struct sk_buff *skb, struct genl_info *info)
1506#endif 1556#endif
1507 wdev_unlock(dev->ieee80211_ptr); 1557 wdev_unlock(dev->ieee80211_ptr);
1508 1558
1509 out:
1510 cfg80211_unlock_rdev(rdev);
1511 dev_put(dev);
1512
1513 unlock_rtnl:
1514 rtnl_unlock();
1515
1516 return err; 1559 return err;
1517} 1560}
1518 1561
1519static int nl80211_new_key(struct sk_buff *skb, struct genl_info *info) 1562static int nl80211_new_key(struct sk_buff *skb, struct genl_info *info)
1520{ 1563{
1521 struct cfg80211_registered_device *rdev; 1564 struct cfg80211_registered_device *rdev = info->user_ptr[0];
1522 int err; 1565 int err;
1523 struct net_device *dev; 1566 struct net_device *dev = info->user_ptr[1];
1524 struct key_parse key; 1567 struct key_parse key;
1525 u8 *mac_addr = NULL; 1568 const u8 *mac_addr = NULL;
1526 1569
1527 err = nl80211_parse_key(info, &key); 1570 err = nl80211_parse_key(info, &key);
1528 if (err) 1571 if (err)
@@ -1534,43 +1577,42 @@ static int nl80211_new_key(struct sk_buff *skb, struct genl_info *info)
1534 if (info->attrs[NL80211_ATTR_MAC]) 1577 if (info->attrs[NL80211_ATTR_MAC])
1535 mac_addr = nla_data(info->attrs[NL80211_ATTR_MAC]); 1578 mac_addr = nla_data(info->attrs[NL80211_ATTR_MAC]);
1536 1579
1537 rtnl_lock(); 1580 if (key.type == -1) {
1581 if (mac_addr)
1582 key.type = NL80211_KEYTYPE_PAIRWISE;
1583 else
1584 key.type = NL80211_KEYTYPE_GROUP;
1585 }
1538 1586
1539 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev); 1587 /* for now */
1540 if (err) 1588 if (key.type != NL80211_KEYTYPE_PAIRWISE &&
1541 goto unlock_rtnl; 1589 key.type != NL80211_KEYTYPE_GROUP)
1590 return -EINVAL;
1542 1591
1543 if (!rdev->ops->add_key) { 1592 if (!rdev->ops->add_key)
1544 err = -EOPNOTSUPP; 1593 return -EOPNOTSUPP;
1545 goto out;
1546 }
1547 1594
1548 if (cfg80211_validate_key_settings(rdev, &key.p, key.idx, mac_addr)) { 1595 if (cfg80211_validate_key_settings(rdev, &key.p, key.idx,
1549 err = -EINVAL; 1596 key.type == NL80211_KEYTYPE_PAIRWISE,
1550 goto out; 1597 mac_addr))
1551 } 1598 return -EINVAL;
1552 1599
1553 wdev_lock(dev->ieee80211_ptr); 1600 wdev_lock(dev->ieee80211_ptr);
1554 err = nl80211_key_allowed(dev->ieee80211_ptr); 1601 err = nl80211_key_allowed(dev->ieee80211_ptr);
1555 if (!err) 1602 if (!err)
1556 err = rdev->ops->add_key(&rdev->wiphy, dev, key.idx, 1603 err = rdev->ops->add_key(&rdev->wiphy, dev, key.idx,
1604 key.type == NL80211_KEYTYPE_PAIRWISE,
1557 mac_addr, &key.p); 1605 mac_addr, &key.p);
1558 wdev_unlock(dev->ieee80211_ptr); 1606 wdev_unlock(dev->ieee80211_ptr);
1559 1607
1560 out:
1561 cfg80211_unlock_rdev(rdev);
1562 dev_put(dev);
1563 unlock_rtnl:
1564 rtnl_unlock();
1565
1566 return err; 1608 return err;
1567} 1609}
1568 1610
1569static int nl80211_del_key(struct sk_buff *skb, struct genl_info *info) 1611static int nl80211_del_key(struct sk_buff *skb, struct genl_info *info)
1570{ 1612{
1571 struct cfg80211_registered_device *rdev; 1613 struct cfg80211_registered_device *rdev = info->user_ptr[0];
1572 int err; 1614 int err;
1573 struct net_device *dev; 1615 struct net_device *dev = info->user_ptr[1];
1574 u8 *mac_addr = NULL; 1616 u8 *mac_addr = NULL;
1575 struct key_parse key; 1617 struct key_parse key;
1576 1618
@@ -1581,21 +1623,32 @@ static int nl80211_del_key(struct sk_buff *skb, struct genl_info *info)
1581 if (info->attrs[NL80211_ATTR_MAC]) 1623 if (info->attrs[NL80211_ATTR_MAC])
1582 mac_addr = nla_data(info->attrs[NL80211_ATTR_MAC]); 1624 mac_addr = nla_data(info->attrs[NL80211_ATTR_MAC]);
1583 1625
1584 rtnl_lock(); 1626 if (key.type == -1) {
1627 if (mac_addr)
1628 key.type = NL80211_KEYTYPE_PAIRWISE;
1629 else
1630 key.type = NL80211_KEYTYPE_GROUP;
1631 }
1585 1632
1586 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev); 1633 /* for now */
1587 if (err) 1634 if (key.type != NL80211_KEYTYPE_PAIRWISE &&
1588 goto unlock_rtnl; 1635 key.type != NL80211_KEYTYPE_GROUP)
1636 return -EINVAL;
1589 1637
1590 if (!rdev->ops->del_key) { 1638 if (!rdev->ops->del_key)
1591 err = -EOPNOTSUPP; 1639 return -EOPNOTSUPP;
1592 goto out;
1593 }
1594 1640
1595 wdev_lock(dev->ieee80211_ptr); 1641 wdev_lock(dev->ieee80211_ptr);
1596 err = nl80211_key_allowed(dev->ieee80211_ptr); 1642 err = nl80211_key_allowed(dev->ieee80211_ptr);
1643
1644 if (key.type == NL80211_KEYTYPE_PAIRWISE && mac_addr &&
1645 !(rdev->wiphy.flags & WIPHY_FLAG_IBSS_RSN))
1646 err = -ENOENT;
1647
1597 if (!err) 1648 if (!err)
1598 err = rdev->ops->del_key(&rdev->wiphy, dev, key.idx, mac_addr); 1649 err = rdev->ops->del_key(&rdev->wiphy, dev, key.idx,
1650 key.type == NL80211_KEYTYPE_PAIRWISE,
1651 mac_addr);
1599 1652
1600#ifdef CONFIG_CFG80211_WEXT 1653#ifdef CONFIG_CFG80211_WEXT
1601 if (!err) { 1654 if (!err) {
@@ -1607,13 +1660,6 @@ static int nl80211_del_key(struct sk_buff *skb, struct genl_info *info)
1607#endif 1660#endif
1608 wdev_unlock(dev->ieee80211_ptr); 1661 wdev_unlock(dev->ieee80211_ptr);
1609 1662
1610 out:
1611 cfg80211_unlock_rdev(rdev);
1612 dev_put(dev);
1613
1614 unlock_rtnl:
1615 rtnl_unlock();
1616
1617 return err; 1663 return err;
1618} 1664}
1619 1665
@@ -1621,35 +1667,25 @@ static int nl80211_addset_beacon(struct sk_buff *skb, struct genl_info *info)
1621{ 1667{
1622 int (*call)(struct wiphy *wiphy, struct net_device *dev, 1668 int (*call)(struct wiphy *wiphy, struct net_device *dev,
1623 struct beacon_parameters *info); 1669 struct beacon_parameters *info);
1624 struct cfg80211_registered_device *rdev; 1670 struct cfg80211_registered_device *rdev = info->user_ptr[0];
1625 int err; 1671 struct net_device *dev = info->user_ptr[1];
1626 struct net_device *dev;
1627 struct beacon_parameters params; 1672 struct beacon_parameters params;
1628 int haveinfo = 0; 1673 int haveinfo = 0;
1629 1674
1630 if (!is_valid_ie_attr(info->attrs[NL80211_ATTR_BEACON_TAIL])) 1675 if (!is_valid_ie_attr(info->attrs[NL80211_ATTR_BEACON_TAIL]))
1631 return -EINVAL; 1676 return -EINVAL;
1632 1677
1633 rtnl_lock(); 1678 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_AP &&
1634 1679 dev->ieee80211_ptr->iftype != NL80211_IFTYPE_P2P_GO)
1635 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev); 1680 return -EOPNOTSUPP;
1636 if (err)
1637 goto unlock_rtnl;
1638
1639 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_AP) {
1640 err = -EOPNOTSUPP;
1641 goto out;
1642 }
1643 1681
1644 switch (info->genlhdr->cmd) { 1682 switch (info->genlhdr->cmd) {
1645 case NL80211_CMD_NEW_BEACON: 1683 case NL80211_CMD_NEW_BEACON:
1646 /* these are required for NEW_BEACON */ 1684 /* these are required for NEW_BEACON */
1647 if (!info->attrs[NL80211_ATTR_BEACON_INTERVAL] || 1685 if (!info->attrs[NL80211_ATTR_BEACON_INTERVAL] ||
1648 !info->attrs[NL80211_ATTR_DTIM_PERIOD] || 1686 !info->attrs[NL80211_ATTR_DTIM_PERIOD] ||
1649 !info->attrs[NL80211_ATTR_BEACON_HEAD]) { 1687 !info->attrs[NL80211_ATTR_BEACON_HEAD])
1650 err = -EINVAL; 1688 return -EINVAL;
1651 goto out;
1652 }
1653 1689
1654 call = rdev->ops->add_beacon; 1690 call = rdev->ops->add_beacon;
1655 break; 1691 break;
@@ -1658,14 +1694,11 @@ static int nl80211_addset_beacon(struct sk_buff *skb, struct genl_info *info)
1658 break; 1694 break;
1659 default: 1695 default:
1660 WARN_ON(1); 1696 WARN_ON(1);
1661 err = -EOPNOTSUPP; 1697 return -EOPNOTSUPP;
1662 goto out;
1663 } 1698 }
1664 1699
1665 if (!call) { 1700 if (!call)
1666 err = -EOPNOTSUPP; 1701 return -EOPNOTSUPP;
1667 goto out;
1668 }
1669 1702
1670 memset(&params, 0, sizeof(params)); 1703 memset(&params, 0, sizeof(params));
1671 1704
@@ -1695,52 +1728,25 @@ static int nl80211_addset_beacon(struct sk_buff *skb, struct genl_info *info)
1695 haveinfo = 1; 1728 haveinfo = 1;
1696 } 1729 }
1697 1730
1698 if (!haveinfo) { 1731 if (!haveinfo)
1699 err = -EINVAL; 1732 return -EINVAL;
1700 goto out;
1701 }
1702
1703 err = call(&rdev->wiphy, dev, &params);
1704
1705 out:
1706 cfg80211_unlock_rdev(rdev);
1707 dev_put(dev);
1708 unlock_rtnl:
1709 rtnl_unlock();
1710 1733
1711 return err; 1734 return call(&rdev->wiphy, dev, &params);
1712} 1735}
1713 1736
1714static int nl80211_del_beacon(struct sk_buff *skb, struct genl_info *info) 1737static int nl80211_del_beacon(struct sk_buff *skb, struct genl_info *info)
1715{ 1738{
1716 struct cfg80211_registered_device *rdev; 1739 struct cfg80211_registered_device *rdev = info->user_ptr[0];
1717 int err; 1740 struct net_device *dev = info->user_ptr[1];
1718 struct net_device *dev;
1719 1741
1720 rtnl_lock(); 1742 if (!rdev->ops->del_beacon)
1721 1743 return -EOPNOTSUPP;
1722 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
1723 if (err)
1724 goto unlock_rtnl;
1725
1726 if (!rdev->ops->del_beacon) {
1727 err = -EOPNOTSUPP;
1728 goto out;
1729 }
1730
1731 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_AP) {
1732 err = -EOPNOTSUPP;
1733 goto out;
1734 }
1735 err = rdev->ops->del_beacon(&rdev->wiphy, dev);
1736 1744
1737 out: 1745 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_AP &&
1738 cfg80211_unlock_rdev(rdev); 1746 dev->ieee80211_ptr->iftype != NL80211_IFTYPE_P2P_GO)
1739 dev_put(dev); 1747 return -EOPNOTSUPP;
1740 unlock_rtnl:
1741 rtnl_unlock();
1742 1748
1743 return err; 1749 return rdev->ops->del_beacon(&rdev->wiphy, dev);
1744} 1750}
1745 1751
1746static const struct nla_policy sta_flags_policy[NL80211_STA_FLAG_MAX + 1] = { 1752static const struct nla_policy sta_flags_policy[NL80211_STA_FLAG_MAX + 1] = {
@@ -1861,6 +1867,12 @@ static int nl80211_send_station(struct sk_buff *msg, u32 pid, u32 seq,
1861 if (sinfo->filled & STATION_INFO_TX_PACKETS) 1867 if (sinfo->filled & STATION_INFO_TX_PACKETS)
1862 NLA_PUT_U32(msg, NL80211_STA_INFO_TX_PACKETS, 1868 NLA_PUT_U32(msg, NL80211_STA_INFO_TX_PACKETS,
1863 sinfo->tx_packets); 1869 sinfo->tx_packets);
1870 if (sinfo->filled & STATION_INFO_TX_RETRIES)
1871 NLA_PUT_U32(msg, NL80211_STA_INFO_TX_RETRIES,
1872 sinfo->tx_retries);
1873 if (sinfo->filled & STATION_INFO_TX_FAILED)
1874 NLA_PUT_U32(msg, NL80211_STA_INFO_TX_FAILED,
1875 sinfo->tx_failed);
1864 nla_nest_end(msg, sinfoattr); 1876 nla_nest_end(msg, sinfoattr);
1865 1877
1866 return genlmsg_end(msg, hdr); 1878 return genlmsg_end(msg, hdr);
@@ -1877,28 +1889,12 @@ static int nl80211_dump_station(struct sk_buff *skb,
1877 struct cfg80211_registered_device *dev; 1889 struct cfg80211_registered_device *dev;
1878 struct net_device *netdev; 1890 struct net_device *netdev;
1879 u8 mac_addr[ETH_ALEN]; 1891 u8 mac_addr[ETH_ALEN];
1880 int ifidx = cb->args[0];
1881 int sta_idx = cb->args[1]; 1892 int sta_idx = cb->args[1];
1882 int err; 1893 int err;
1883 1894
1884 if (!ifidx) 1895 err = nl80211_prepare_netdev_dump(skb, cb, &dev, &netdev);
1885 ifidx = nl80211_get_ifidx(cb); 1896 if (err)
1886 if (ifidx < 0) 1897 return err;
1887 return ifidx;
1888
1889 rtnl_lock();
1890
1891 netdev = __dev_get_by_index(sock_net(skb->sk), ifidx);
1892 if (!netdev) {
1893 err = -ENODEV;
1894 goto out_rtnl;
1895 }
1896
1897 dev = cfg80211_get_dev_from_ifindex(sock_net(skb->sk), ifidx);
1898 if (IS_ERR(dev)) {
1899 err = PTR_ERR(dev);
1900 goto out_rtnl;
1901 }
1902 1898
1903 if (!dev->ops->dump_station) { 1899 if (!dev->ops->dump_station) {
1904 err = -EOPNOTSUPP; 1900 err = -EOPNOTSUPP;
@@ -1928,21 +1924,19 @@ static int nl80211_dump_station(struct sk_buff *skb,
1928 cb->args[1] = sta_idx; 1924 cb->args[1] = sta_idx;
1929 err = skb->len; 1925 err = skb->len;
1930 out_err: 1926 out_err:
1931 cfg80211_unlock_rdev(dev); 1927 nl80211_finish_netdev_dump(dev);
1932 out_rtnl:
1933 rtnl_unlock();
1934 1928
1935 return err; 1929 return err;
1936} 1930}
1937 1931
1938static int nl80211_get_station(struct sk_buff *skb, struct genl_info *info) 1932static int nl80211_get_station(struct sk_buff *skb, struct genl_info *info)
1939{ 1933{
1940 struct cfg80211_registered_device *rdev; 1934 struct cfg80211_registered_device *rdev = info->user_ptr[0];
1941 int err; 1935 struct net_device *dev = info->user_ptr[1];
1942 struct net_device *dev;
1943 struct station_info sinfo; 1936 struct station_info sinfo;
1944 struct sk_buff *msg; 1937 struct sk_buff *msg;
1945 u8 *mac_addr = NULL; 1938 u8 *mac_addr = NULL;
1939 int err;
1946 1940
1947 memset(&sinfo, 0, sizeof(sinfo)); 1941 memset(&sinfo, 0, sizeof(sinfo));
1948 1942
@@ -1951,41 +1945,24 @@ static int nl80211_get_station(struct sk_buff *skb, struct genl_info *info)
1951 1945
1952 mac_addr = nla_data(info->attrs[NL80211_ATTR_MAC]); 1946 mac_addr = nla_data(info->attrs[NL80211_ATTR_MAC]);
1953 1947
1954 rtnl_lock(); 1948 if (!rdev->ops->get_station)
1955 1949 return -EOPNOTSUPP;
1956 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
1957 if (err)
1958 goto out_rtnl;
1959
1960 if (!rdev->ops->get_station) {
1961 err = -EOPNOTSUPP;
1962 goto out;
1963 }
1964 1950
1965 err = rdev->ops->get_station(&rdev->wiphy, dev, mac_addr, &sinfo); 1951 err = rdev->ops->get_station(&rdev->wiphy, dev, mac_addr, &sinfo);
1966 if (err) 1952 if (err)
1967 goto out; 1953 return err;
1968 1954
1969 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL); 1955 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
1970 if (!msg) 1956 if (!msg)
1971 goto out; 1957 return -ENOMEM;
1972 1958
1973 if (nl80211_send_station(msg, info->snd_pid, info->snd_seq, 0, 1959 if (nl80211_send_station(msg, info->snd_pid, info->snd_seq, 0,
1974 dev, mac_addr, &sinfo) < 0) 1960 dev, mac_addr, &sinfo) < 0) {
1975 goto out_free; 1961 nlmsg_free(msg);
1976 1962 return -ENOBUFS;
1977 err = genlmsg_reply(msg, info); 1963 }
1978 goto out;
1979
1980 out_free:
1981 nlmsg_free(msg);
1982 out:
1983 cfg80211_unlock_rdev(rdev);
1984 dev_put(dev);
1985 out_rtnl:
1986 rtnl_unlock();
1987 1964
1988 return err; 1965 return genlmsg_reply(msg, info);
1989} 1966}
1990 1967
1991/* 1968/*
@@ -2015,9 +1992,9 @@ static int get_vlan(struct genl_info *info,
2015 1992
2016static int nl80211_set_station(struct sk_buff *skb, struct genl_info *info) 1993static int nl80211_set_station(struct sk_buff *skb, struct genl_info *info)
2017{ 1994{
2018 struct cfg80211_registered_device *rdev; 1995 struct cfg80211_registered_device *rdev = info->user_ptr[0];
2019 int err; 1996 int err;
2020 struct net_device *dev; 1997 struct net_device *dev = info->user_ptr[1];
2021 struct station_parameters params; 1998 struct station_parameters params;
2022 u8 *mac_addr = NULL; 1999 u8 *mac_addr = NULL;
2023 2000
@@ -2055,12 +2032,6 @@ static int nl80211_set_station(struct sk_buff *skb, struct genl_info *info)
2055 params.plink_action = 2032 params.plink_action =
2056 nla_get_u8(info->attrs[NL80211_ATTR_STA_PLINK_ACTION]); 2033 nla_get_u8(info->attrs[NL80211_ATTR_STA_PLINK_ACTION]);
2057 2034
2058 rtnl_lock();
2059
2060 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
2061 if (err)
2062 goto out_rtnl;
2063
2064 err = get_vlan(info, rdev, &params.vlan); 2035 err = get_vlan(info, rdev, &params.vlan);
2065 if (err) 2036 if (err)
2066 goto out; 2037 goto out;
@@ -2071,10 +2042,12 @@ static int nl80211_set_station(struct sk_buff *skb, struct genl_info *info)
2071 switch (dev->ieee80211_ptr->iftype) { 2042 switch (dev->ieee80211_ptr->iftype) {
2072 case NL80211_IFTYPE_AP: 2043 case NL80211_IFTYPE_AP:
2073 case NL80211_IFTYPE_AP_VLAN: 2044 case NL80211_IFTYPE_AP_VLAN:
2045 case NL80211_IFTYPE_P2P_GO:
2074 /* disallow mesh-specific things */ 2046 /* disallow mesh-specific things */
2075 if (params.plink_action) 2047 if (params.plink_action)
2076 err = -EINVAL; 2048 err = -EINVAL;
2077 break; 2049 break;
2050 case NL80211_IFTYPE_P2P_CLIENT:
2078 case NL80211_IFTYPE_STATION: 2051 case NL80211_IFTYPE_STATION:
2079 /* disallow everything but AUTHORIZED flag */ 2052 /* disallow everything but AUTHORIZED flag */
2080 if (params.plink_action) 2053 if (params.plink_action)
@@ -2120,19 +2093,15 @@ static int nl80211_set_station(struct sk_buff *skb, struct genl_info *info)
2120 out: 2093 out:
2121 if (params.vlan) 2094 if (params.vlan)
2122 dev_put(params.vlan); 2095 dev_put(params.vlan);
2123 cfg80211_unlock_rdev(rdev);
2124 dev_put(dev);
2125 out_rtnl:
2126 rtnl_unlock();
2127 2096
2128 return err; 2097 return err;
2129} 2098}
2130 2099
2131static int nl80211_new_station(struct sk_buff *skb, struct genl_info *info) 2100static int nl80211_new_station(struct sk_buff *skb, struct genl_info *info)
2132{ 2101{
2133 struct cfg80211_registered_device *rdev; 2102 struct cfg80211_registered_device *rdev = info->user_ptr[0];
2134 int err; 2103 int err;
2135 struct net_device *dev; 2104 struct net_device *dev = info->user_ptr[1];
2136 struct station_parameters params; 2105 struct station_parameters params;
2137 u8 *mac_addr = NULL; 2106 u8 *mac_addr = NULL;
2138 2107
@@ -2169,17 +2138,10 @@ static int nl80211_new_station(struct sk_buff *skb, struct genl_info *info)
2169 if (parse_station_flags(info, &params)) 2138 if (parse_station_flags(info, &params))
2170 return -EINVAL; 2139 return -EINVAL;
2171 2140
2172 rtnl_lock();
2173
2174 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
2175 if (err)
2176 goto out_rtnl;
2177
2178 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_AP && 2141 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_AP &&
2179 dev->ieee80211_ptr->iftype != NL80211_IFTYPE_AP_VLAN) { 2142 dev->ieee80211_ptr->iftype != NL80211_IFTYPE_AP_VLAN &&
2180 err = -EINVAL; 2143 dev->ieee80211_ptr->iftype != NL80211_IFTYPE_P2P_GO)
2181 goto out; 2144 return -EINVAL;
2182 }
2183 2145
2184 err = get_vlan(info, rdev, &params.vlan); 2146 err = get_vlan(info, rdev, &params.vlan);
2185 if (err) 2147 if (err)
@@ -2193,61 +2155,33 @@ static int nl80211_new_station(struct sk_buff *skb, struct genl_info *info)
2193 goto out; 2155 goto out;
2194 } 2156 }
2195 2157
2196 if (!netif_running(dev)) {
2197 err = -ENETDOWN;
2198 goto out;
2199 }
2200
2201 err = rdev->ops->add_station(&rdev->wiphy, dev, mac_addr, &params); 2158 err = rdev->ops->add_station(&rdev->wiphy, dev, mac_addr, &params);
2202 2159
2203 out: 2160 out:
2204 if (params.vlan) 2161 if (params.vlan)
2205 dev_put(params.vlan); 2162 dev_put(params.vlan);
2206 cfg80211_unlock_rdev(rdev);
2207 dev_put(dev);
2208 out_rtnl:
2209 rtnl_unlock();
2210
2211 return err; 2163 return err;
2212} 2164}
2213 2165
2214static int nl80211_del_station(struct sk_buff *skb, struct genl_info *info) 2166static int nl80211_del_station(struct sk_buff *skb, struct genl_info *info)
2215{ 2167{
2216 struct cfg80211_registered_device *rdev; 2168 struct cfg80211_registered_device *rdev = info->user_ptr[0];
2217 int err; 2169 struct net_device *dev = info->user_ptr[1];
2218 struct net_device *dev;
2219 u8 *mac_addr = NULL; 2170 u8 *mac_addr = NULL;
2220 2171
2221 if (info->attrs[NL80211_ATTR_MAC]) 2172 if (info->attrs[NL80211_ATTR_MAC])
2222 mac_addr = nla_data(info->attrs[NL80211_ATTR_MAC]); 2173 mac_addr = nla_data(info->attrs[NL80211_ATTR_MAC]);
2223 2174
2224 rtnl_lock();
2225
2226 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
2227 if (err)
2228 goto out_rtnl;
2229
2230 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_AP && 2175 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_AP &&
2231 dev->ieee80211_ptr->iftype != NL80211_IFTYPE_AP_VLAN && 2176 dev->ieee80211_ptr->iftype != NL80211_IFTYPE_AP_VLAN &&
2232 dev->ieee80211_ptr->iftype != NL80211_IFTYPE_MESH_POINT) { 2177 dev->ieee80211_ptr->iftype != NL80211_IFTYPE_MESH_POINT &&
2233 err = -EINVAL; 2178 dev->ieee80211_ptr->iftype != NL80211_IFTYPE_P2P_GO)
2234 goto out; 2179 return -EINVAL;
2235 }
2236
2237 if (!rdev->ops->del_station) {
2238 err = -EOPNOTSUPP;
2239 goto out;
2240 }
2241
2242 err = rdev->ops->del_station(&rdev->wiphy, dev, mac_addr);
2243 2180
2244 out: 2181 if (!rdev->ops->del_station)
2245 cfg80211_unlock_rdev(rdev); 2182 return -EOPNOTSUPP;
2246 dev_put(dev);
2247 out_rtnl:
2248 rtnl_unlock();
2249 2183
2250 return err; 2184 return rdev->ops->del_station(&rdev->wiphy, dev, mac_addr);
2251} 2185}
2252 2186
2253static int nl80211_send_mpath(struct sk_buff *msg, u32 pid, u32 seq, 2187static int nl80211_send_mpath(struct sk_buff *msg, u32 pid, u32 seq,
@@ -2310,28 +2244,12 @@ static int nl80211_dump_mpath(struct sk_buff *skb,
2310 struct net_device *netdev; 2244 struct net_device *netdev;
2311 u8 dst[ETH_ALEN]; 2245 u8 dst[ETH_ALEN];
2312 u8 next_hop[ETH_ALEN]; 2246 u8 next_hop[ETH_ALEN];
2313 int ifidx = cb->args[0];
2314 int path_idx = cb->args[1]; 2247 int path_idx = cb->args[1];
2315 int err; 2248 int err;
2316 2249
2317 if (!ifidx) 2250 err = nl80211_prepare_netdev_dump(skb, cb, &dev, &netdev);
2318 ifidx = nl80211_get_ifidx(cb); 2251 if (err)
2319 if (ifidx < 0) 2252 return err;
2320 return ifidx;
2321
2322 rtnl_lock();
2323
2324 netdev = __dev_get_by_index(sock_net(skb->sk), ifidx);
2325 if (!netdev) {
2326 err = -ENODEV;
2327 goto out_rtnl;
2328 }
2329
2330 dev = cfg80211_get_dev_from_ifindex(sock_net(skb->sk), ifidx);
2331 if (IS_ERR(dev)) {
2332 err = PTR_ERR(dev);
2333 goto out_rtnl;
2334 }
2335 2253
2336 if (!dev->ops->dump_mpath) { 2254 if (!dev->ops->dump_mpath) {
2337 err = -EOPNOTSUPP; 2255 err = -EOPNOTSUPP;
@@ -2365,18 +2283,15 @@ static int nl80211_dump_mpath(struct sk_buff *skb,
2365 cb->args[1] = path_idx; 2283 cb->args[1] = path_idx;
2366 err = skb->len; 2284 err = skb->len;
2367 out_err: 2285 out_err:
2368 cfg80211_unlock_rdev(dev); 2286 nl80211_finish_netdev_dump(dev);
2369 out_rtnl:
2370 rtnl_unlock();
2371
2372 return err; 2287 return err;
2373} 2288}
2374 2289
2375static int nl80211_get_mpath(struct sk_buff *skb, struct genl_info *info) 2290static int nl80211_get_mpath(struct sk_buff *skb, struct genl_info *info)
2376{ 2291{
2377 struct cfg80211_registered_device *rdev; 2292 struct cfg80211_registered_device *rdev = info->user_ptr[0];
2378 int err; 2293 int err;
2379 struct net_device *dev; 2294 struct net_device *dev = info->user_ptr[1];
2380 struct mpath_info pinfo; 2295 struct mpath_info pinfo;
2381 struct sk_buff *msg; 2296 struct sk_buff *msg;
2382 u8 *dst = NULL; 2297 u8 *dst = NULL;
@@ -2389,53 +2304,33 @@ static int nl80211_get_mpath(struct sk_buff *skb, struct genl_info *info)
2389 2304
2390 dst = nla_data(info->attrs[NL80211_ATTR_MAC]); 2305 dst = nla_data(info->attrs[NL80211_ATTR_MAC]);
2391 2306
2392 rtnl_lock(); 2307 if (!rdev->ops->get_mpath)
2393 2308 return -EOPNOTSUPP;
2394 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
2395 if (err)
2396 goto out_rtnl;
2397
2398 if (!rdev->ops->get_mpath) {
2399 err = -EOPNOTSUPP;
2400 goto out;
2401 }
2402 2309
2403 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_MESH_POINT) { 2310 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_MESH_POINT)
2404 err = -EOPNOTSUPP; 2311 return -EOPNOTSUPP;
2405 goto out;
2406 }
2407 2312
2408 err = rdev->ops->get_mpath(&rdev->wiphy, dev, dst, next_hop, &pinfo); 2313 err = rdev->ops->get_mpath(&rdev->wiphy, dev, dst, next_hop, &pinfo);
2409 if (err) 2314 if (err)
2410 goto out; 2315 return err;
2411 2316
2412 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL); 2317 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
2413 if (!msg) 2318 if (!msg)
2414 goto out; 2319 return -ENOMEM;
2415 2320
2416 if (nl80211_send_mpath(msg, info->snd_pid, info->snd_seq, 0, 2321 if (nl80211_send_mpath(msg, info->snd_pid, info->snd_seq, 0,
2417 dev, dst, next_hop, &pinfo) < 0) 2322 dev, dst, next_hop, &pinfo) < 0) {
2418 goto out_free; 2323 nlmsg_free(msg);
2419 2324 return -ENOBUFS;
2420 err = genlmsg_reply(msg, info); 2325 }
2421 goto out;
2422
2423 out_free:
2424 nlmsg_free(msg);
2425 out:
2426 cfg80211_unlock_rdev(rdev);
2427 dev_put(dev);
2428 out_rtnl:
2429 rtnl_unlock();
2430 2326
2431 return err; 2327 return genlmsg_reply(msg, info);
2432} 2328}
2433 2329
2434static int nl80211_set_mpath(struct sk_buff *skb, struct genl_info *info) 2330static int nl80211_set_mpath(struct sk_buff *skb, struct genl_info *info)
2435{ 2331{
2436 struct cfg80211_registered_device *rdev; 2332 struct cfg80211_registered_device *rdev = info->user_ptr[0];
2437 int err; 2333 struct net_device *dev = info->user_ptr[1];
2438 struct net_device *dev;
2439 u8 *dst = NULL; 2334 u8 *dst = NULL;
2440 u8 *next_hop = NULL; 2335 u8 *next_hop = NULL;
2441 2336
@@ -2448,42 +2343,19 @@ static int nl80211_set_mpath(struct sk_buff *skb, struct genl_info *info)
2448 dst = nla_data(info->attrs[NL80211_ATTR_MAC]); 2343 dst = nla_data(info->attrs[NL80211_ATTR_MAC]);
2449 next_hop = nla_data(info->attrs[NL80211_ATTR_MPATH_NEXT_HOP]); 2344 next_hop = nla_data(info->attrs[NL80211_ATTR_MPATH_NEXT_HOP]);
2450 2345
2451 rtnl_lock(); 2346 if (!rdev->ops->change_mpath)
2452 2347 return -EOPNOTSUPP;
2453 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
2454 if (err)
2455 goto out_rtnl;
2456
2457 if (!rdev->ops->change_mpath) {
2458 err = -EOPNOTSUPP;
2459 goto out;
2460 }
2461
2462 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_MESH_POINT) {
2463 err = -EOPNOTSUPP;
2464 goto out;
2465 }
2466
2467 if (!netif_running(dev)) {
2468 err = -ENETDOWN;
2469 goto out;
2470 }
2471
2472 err = rdev->ops->change_mpath(&rdev->wiphy, dev, dst, next_hop);
2473 2348
2474 out: 2349 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_MESH_POINT)
2475 cfg80211_unlock_rdev(rdev); 2350 return -EOPNOTSUPP;
2476 dev_put(dev);
2477 out_rtnl:
2478 rtnl_unlock();
2479 2351
2480 return err; 2352 return rdev->ops->change_mpath(&rdev->wiphy, dev, dst, next_hop);
2481} 2353}
2354
2482static int nl80211_new_mpath(struct sk_buff *skb, struct genl_info *info) 2355static int nl80211_new_mpath(struct sk_buff *skb, struct genl_info *info)
2483{ 2356{
2484 struct cfg80211_registered_device *rdev; 2357 struct cfg80211_registered_device *rdev = info->user_ptr[0];
2485 int err; 2358 struct net_device *dev = info->user_ptr[1];
2486 struct net_device *dev;
2487 u8 *dst = NULL; 2359 u8 *dst = NULL;
2488 u8 *next_hop = NULL; 2360 u8 *next_hop = NULL;
2489 2361
@@ -2496,75 +2368,34 @@ static int nl80211_new_mpath(struct sk_buff *skb, struct genl_info *info)
2496 dst = nla_data(info->attrs[NL80211_ATTR_MAC]); 2368 dst = nla_data(info->attrs[NL80211_ATTR_MAC]);
2497 next_hop = nla_data(info->attrs[NL80211_ATTR_MPATH_NEXT_HOP]); 2369 next_hop = nla_data(info->attrs[NL80211_ATTR_MPATH_NEXT_HOP]);
2498 2370
2499 rtnl_lock(); 2371 if (!rdev->ops->add_mpath)
2500 2372 return -EOPNOTSUPP;
2501 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
2502 if (err)
2503 goto out_rtnl;
2504
2505 if (!rdev->ops->add_mpath) {
2506 err = -EOPNOTSUPP;
2507 goto out;
2508 }
2509
2510 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_MESH_POINT) {
2511 err = -EOPNOTSUPP;
2512 goto out;
2513 }
2514
2515 if (!netif_running(dev)) {
2516 err = -ENETDOWN;
2517 goto out;
2518 }
2519
2520 err = rdev->ops->add_mpath(&rdev->wiphy, dev, dst, next_hop);
2521 2373
2522 out: 2374 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_MESH_POINT)
2523 cfg80211_unlock_rdev(rdev); 2375 return -EOPNOTSUPP;
2524 dev_put(dev);
2525 out_rtnl:
2526 rtnl_unlock();
2527 2376
2528 return err; 2377 return rdev->ops->add_mpath(&rdev->wiphy, dev, dst, next_hop);
2529} 2378}
2530 2379
2531static int nl80211_del_mpath(struct sk_buff *skb, struct genl_info *info) 2380static int nl80211_del_mpath(struct sk_buff *skb, struct genl_info *info)
2532{ 2381{
2533 struct cfg80211_registered_device *rdev; 2382 struct cfg80211_registered_device *rdev = info->user_ptr[0];
2534 int err; 2383 struct net_device *dev = info->user_ptr[1];
2535 struct net_device *dev;
2536 u8 *dst = NULL; 2384 u8 *dst = NULL;
2537 2385
2538 if (info->attrs[NL80211_ATTR_MAC]) 2386 if (info->attrs[NL80211_ATTR_MAC])
2539 dst = nla_data(info->attrs[NL80211_ATTR_MAC]); 2387 dst = nla_data(info->attrs[NL80211_ATTR_MAC]);
2540 2388
2541 rtnl_lock(); 2389 if (!rdev->ops->del_mpath)
2542 2390 return -EOPNOTSUPP;
2543 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
2544 if (err)
2545 goto out_rtnl;
2546
2547 if (!rdev->ops->del_mpath) {
2548 err = -EOPNOTSUPP;
2549 goto out;
2550 }
2551
2552 err = rdev->ops->del_mpath(&rdev->wiphy, dev, dst);
2553
2554 out:
2555 cfg80211_unlock_rdev(rdev);
2556 dev_put(dev);
2557 out_rtnl:
2558 rtnl_unlock();
2559 2391
2560 return err; 2392 return rdev->ops->del_mpath(&rdev->wiphy, dev, dst);
2561} 2393}
2562 2394
2563static int nl80211_set_bss(struct sk_buff *skb, struct genl_info *info) 2395static int nl80211_set_bss(struct sk_buff *skb, struct genl_info *info)
2564{ 2396{
2565 struct cfg80211_registered_device *rdev; 2397 struct cfg80211_registered_device *rdev = info->user_ptr[0];
2566 int err; 2398 struct net_device *dev = info->user_ptr[1];
2567 struct net_device *dev;
2568 struct bss_parameters params; 2399 struct bss_parameters params;
2569 2400
2570 memset(&params, 0, sizeof(params)); 2401 memset(&params, 0, sizeof(params));
@@ -2592,31 +2423,14 @@ static int nl80211_set_bss(struct sk_buff *skb, struct genl_info *info)
2592 if (info->attrs[NL80211_ATTR_AP_ISOLATE]) 2423 if (info->attrs[NL80211_ATTR_AP_ISOLATE])
2593 params.ap_isolate = !!nla_get_u8(info->attrs[NL80211_ATTR_AP_ISOLATE]); 2424 params.ap_isolate = !!nla_get_u8(info->attrs[NL80211_ATTR_AP_ISOLATE]);
2594 2425
2595 rtnl_lock(); 2426 if (!rdev->ops->change_bss)
2596 2427 return -EOPNOTSUPP;
2597 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
2598 if (err)
2599 goto out_rtnl;
2600
2601 if (!rdev->ops->change_bss) {
2602 err = -EOPNOTSUPP;
2603 goto out;
2604 }
2605
2606 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_AP) {
2607 err = -EOPNOTSUPP;
2608 goto out;
2609 }
2610
2611 err = rdev->ops->change_bss(&rdev->wiphy, dev, &params);
2612 2428
2613 out: 2429 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_AP &&
2614 cfg80211_unlock_rdev(rdev); 2430 dev->ieee80211_ptr->iftype != NL80211_IFTYPE_P2P_GO)
2615 dev_put(dev); 2431 return -EOPNOTSUPP;
2616 out_rtnl:
2617 rtnl_unlock();
2618 2432
2619 return err; 2433 return rdev->ops->change_bss(&rdev->wiphy, dev, &params);
2620} 2434}
2621 2435
2622static const struct nla_policy reg_rule_policy[NL80211_REG_RULE_ATTR_MAX + 1] = { 2436static const struct nla_policy reg_rule_policy[NL80211_REG_RULE_ATTR_MAX + 1] = {
@@ -2695,37 +2509,26 @@ static int nl80211_req_set_reg(struct sk_buff *skb, struct genl_info *info)
2695static int nl80211_get_mesh_params(struct sk_buff *skb, 2509static int nl80211_get_mesh_params(struct sk_buff *skb,
2696 struct genl_info *info) 2510 struct genl_info *info)
2697{ 2511{
2698 struct cfg80211_registered_device *rdev; 2512 struct cfg80211_registered_device *rdev = info->user_ptr[0];
2699 struct mesh_config cur_params; 2513 struct mesh_config cur_params;
2700 int err; 2514 int err;
2701 struct net_device *dev; 2515 struct net_device *dev = info->user_ptr[1];
2702 void *hdr; 2516 void *hdr;
2703 struct nlattr *pinfoattr; 2517 struct nlattr *pinfoattr;
2704 struct sk_buff *msg; 2518 struct sk_buff *msg;
2705 2519
2706 rtnl_lock(); 2520 if (!rdev->ops->get_mesh_params)
2707 2521 return -EOPNOTSUPP;
2708 /* Look up our device */
2709 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
2710 if (err)
2711 goto out_rtnl;
2712
2713 if (!rdev->ops->get_mesh_params) {
2714 err = -EOPNOTSUPP;
2715 goto out;
2716 }
2717 2522
2718 /* Get the mesh params */ 2523 /* Get the mesh params */
2719 err = rdev->ops->get_mesh_params(&rdev->wiphy, dev, &cur_params); 2524 err = rdev->ops->get_mesh_params(&rdev->wiphy, dev, &cur_params);
2720 if (err) 2525 if (err)
2721 goto out; 2526 return err;
2722 2527
2723 /* Draw up a netlink message to send back */ 2528 /* Draw up a netlink message to send back */
2724 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL); 2529 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
2725 if (!msg) { 2530 if (!msg)
2726 err = -ENOBUFS; 2531 return -ENOMEM;
2727 goto out;
2728 }
2729 hdr = nl80211hdr_put(msg, info->snd_pid, info->snd_seq, 0, 2532 hdr = nl80211hdr_put(msg, info->snd_pid, info->snd_seq, 0,
2730 NL80211_CMD_GET_MESH_PARAMS); 2533 NL80211_CMD_GET_MESH_PARAMS);
2731 if (!hdr) 2534 if (!hdr)
@@ -2764,21 +2567,12 @@ static int nl80211_get_mesh_params(struct sk_buff *skb,
2764 cur_params.dot11MeshHWMPRootMode); 2567 cur_params.dot11MeshHWMPRootMode);
2765 nla_nest_end(msg, pinfoattr); 2568 nla_nest_end(msg, pinfoattr);
2766 genlmsg_end(msg, hdr); 2569 genlmsg_end(msg, hdr);
2767 err = genlmsg_reply(msg, info); 2570 return genlmsg_reply(msg, info);
2768 goto out;
2769 2571
2770 nla_put_failure: 2572 nla_put_failure:
2771 genlmsg_cancel(msg, hdr); 2573 genlmsg_cancel(msg, hdr);
2772 nlmsg_free(msg); 2574 nlmsg_free(msg);
2773 err = -EMSGSIZE; 2575 return -ENOBUFS;
2774 out:
2775 /* Cleanup */
2776 cfg80211_unlock_rdev(rdev);
2777 dev_put(dev);
2778 out_rtnl:
2779 rtnl_unlock();
2780
2781 return err;
2782} 2576}
2783 2577
2784#define FILL_IN_MESH_PARAM_IF_SET(table, cfg, param, mask, attr_num, nla_fn) \ 2578#define FILL_IN_MESH_PARAM_IF_SET(table, cfg, param, mask, attr_num, nla_fn) \
@@ -2808,10 +2602,9 @@ static const struct nla_policy nl80211_meshconf_params_policy[NL80211_MESHCONF_A
2808 2602
2809static int nl80211_set_mesh_params(struct sk_buff *skb, struct genl_info *info) 2603static int nl80211_set_mesh_params(struct sk_buff *skb, struct genl_info *info)
2810{ 2604{
2811 int err;
2812 u32 mask; 2605 u32 mask;
2813 struct cfg80211_registered_device *rdev; 2606 struct cfg80211_registered_device *rdev = info->user_ptr[0];
2814 struct net_device *dev; 2607 struct net_device *dev = info->user_ptr[1];
2815 struct mesh_config cfg; 2608 struct mesh_config cfg;
2816 struct nlattr *tb[NL80211_MESHCONF_ATTR_MAX + 1]; 2609 struct nlattr *tb[NL80211_MESHCONF_ATTR_MAX + 1];
2817 struct nlattr *parent_attr; 2610 struct nlattr *parent_attr;
@@ -2823,16 +2616,8 @@ static int nl80211_set_mesh_params(struct sk_buff *skb, struct genl_info *info)
2823 parent_attr, nl80211_meshconf_params_policy)) 2616 parent_attr, nl80211_meshconf_params_policy))
2824 return -EINVAL; 2617 return -EINVAL;
2825 2618
2826 rtnl_lock(); 2619 if (!rdev->ops->set_mesh_params)
2827 2620 return -EOPNOTSUPP;
2828 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
2829 if (err)
2830 goto out_rtnl;
2831
2832 if (!rdev->ops->set_mesh_params) {
2833 err = -EOPNOTSUPP;
2834 goto out;
2835 }
2836 2621
2837 /* This makes sure that there aren't more than 32 mesh config 2622 /* This makes sure that there aren't more than 32 mesh config
2838 * parameters (otherwise our bitfield scheme would not work.) */ 2623 * parameters (otherwise our bitfield scheme would not work.) */
@@ -2878,16 +2663,7 @@ static int nl80211_set_mesh_params(struct sk_buff *skb, struct genl_info *info)
2878 nla_get_u8); 2663 nla_get_u8);
2879 2664
2880 /* Apply changes */ 2665 /* Apply changes */
2881 err = rdev->ops->set_mesh_params(&rdev->wiphy, dev, &cfg, mask); 2666 return rdev->ops->set_mesh_params(&rdev->wiphy, dev, &cfg, mask);
2882
2883 out:
2884 /* cleanup */
2885 cfg80211_unlock_rdev(rdev);
2886 dev_put(dev);
2887 out_rtnl:
2888 rtnl_unlock();
2889
2890 return err;
2891} 2667}
2892 2668
2893#undef FILL_IN_MESH_PARAM_IF_SET 2669#undef FILL_IN_MESH_PARAM_IF_SET
@@ -3070,8 +2846,8 @@ static int validate_scan_freqs(struct nlattr *freqs)
3070 2846
3071static int nl80211_trigger_scan(struct sk_buff *skb, struct genl_info *info) 2847static int nl80211_trigger_scan(struct sk_buff *skb, struct genl_info *info)
3072{ 2848{
3073 struct cfg80211_registered_device *rdev; 2849 struct cfg80211_registered_device *rdev = info->user_ptr[0];
3074 struct net_device *dev; 2850 struct net_device *dev = info->user_ptr[1];
3075 struct cfg80211_scan_request *request; 2851 struct cfg80211_scan_request *request;
3076 struct cfg80211_ssid *ssid; 2852 struct cfg80211_ssid *ssid;
3077 struct ieee80211_channel *channel; 2853 struct ieee80211_channel *channel;
@@ -3084,36 +2860,19 @@ static int nl80211_trigger_scan(struct sk_buff *skb, struct genl_info *info)
3084 if (!is_valid_ie_attr(info->attrs[NL80211_ATTR_IE])) 2860 if (!is_valid_ie_attr(info->attrs[NL80211_ATTR_IE]))
3085 return -EINVAL; 2861 return -EINVAL;
3086 2862
3087 rtnl_lock();
3088
3089 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
3090 if (err)
3091 goto out_rtnl;
3092
3093 wiphy = &rdev->wiphy; 2863 wiphy = &rdev->wiphy;
3094 2864
3095 if (!rdev->ops->scan) { 2865 if (!rdev->ops->scan)
3096 err = -EOPNOTSUPP; 2866 return -EOPNOTSUPP;
3097 goto out;
3098 }
3099
3100 if (!netif_running(dev)) {
3101 err = -ENETDOWN;
3102 goto out;
3103 }
3104 2867
3105 if (rdev->scan_req) { 2868 if (rdev->scan_req)
3106 err = -EBUSY; 2869 return -EBUSY;
3107 goto out;
3108 }
3109 2870
3110 if (info->attrs[NL80211_ATTR_SCAN_FREQUENCIES]) { 2871 if (info->attrs[NL80211_ATTR_SCAN_FREQUENCIES]) {
3111 n_channels = validate_scan_freqs( 2872 n_channels = validate_scan_freqs(
3112 info->attrs[NL80211_ATTR_SCAN_FREQUENCIES]); 2873 info->attrs[NL80211_ATTR_SCAN_FREQUENCIES]);
3113 if (!n_channels) { 2874 if (!n_channels)
3114 err = -EINVAL; 2875 return -EINVAL;
3115 goto out;
3116 }
3117 } else { 2876 } else {
3118 n_channels = 0; 2877 n_channels = 0;
3119 2878
@@ -3126,29 +2885,23 @@ static int nl80211_trigger_scan(struct sk_buff *skb, struct genl_info *info)
3126 nla_for_each_nested(attr, info->attrs[NL80211_ATTR_SCAN_SSIDS], tmp) 2885 nla_for_each_nested(attr, info->attrs[NL80211_ATTR_SCAN_SSIDS], tmp)
3127 n_ssids++; 2886 n_ssids++;
3128 2887
3129 if (n_ssids > wiphy->max_scan_ssids) { 2888 if (n_ssids > wiphy->max_scan_ssids)
3130 err = -EINVAL; 2889 return -EINVAL;
3131 goto out;
3132 }
3133 2890
3134 if (info->attrs[NL80211_ATTR_IE]) 2891 if (info->attrs[NL80211_ATTR_IE])
3135 ie_len = nla_len(info->attrs[NL80211_ATTR_IE]); 2892 ie_len = nla_len(info->attrs[NL80211_ATTR_IE]);
3136 else 2893 else
3137 ie_len = 0; 2894 ie_len = 0;
3138 2895
3139 if (ie_len > wiphy->max_scan_ie_len) { 2896 if (ie_len > wiphy->max_scan_ie_len)
3140 err = -EINVAL; 2897 return -EINVAL;
3141 goto out;
3142 }
3143 2898
3144 request = kzalloc(sizeof(*request) 2899 request = kzalloc(sizeof(*request)
3145 + sizeof(*ssid) * n_ssids 2900 + sizeof(*ssid) * n_ssids
3146 + sizeof(channel) * n_channels 2901 + sizeof(channel) * n_channels
3147 + ie_len, GFP_KERNEL); 2902 + ie_len, GFP_KERNEL);
3148 if (!request) { 2903 if (!request)
3149 err = -ENOMEM; 2904 return -ENOMEM;
3150 goto out;
3151 }
3152 2905
3153 if (n_ssids) 2906 if (n_ssids)
3154 request->ssids = (void *)&request->channels[n_channels]; 2907 request->ssids = (void *)&request->channels[n_channels];
@@ -3236,18 +2989,11 @@ static int nl80211_trigger_scan(struct sk_buff *skb, struct genl_info *info)
3236 if (!err) { 2989 if (!err) {
3237 nl80211_send_scan_start(rdev, dev); 2990 nl80211_send_scan_start(rdev, dev);
3238 dev_hold(dev); 2991 dev_hold(dev);
3239 } 2992 } else {
3240
3241 out_free: 2993 out_free:
3242 if (err) {
3243 rdev->scan_req = NULL; 2994 rdev->scan_req = NULL;
3244 kfree(request); 2995 kfree(request);
3245 } 2996 }
3246 out:
3247 cfg80211_unlock_rdev(rdev);
3248 dev_put(dev);
3249 out_rtnl:
3250 rtnl_unlock();
3251 2997
3252 return err; 2998 return err;
3253} 2999}
@@ -3306,6 +3052,7 @@ static int nl80211_send_bss(struct sk_buff *msg, u32 pid, u32 seq, int flags,
3306 } 3052 }
3307 3053
3308 switch (wdev->iftype) { 3054 switch (wdev->iftype) {
3055 case NL80211_IFTYPE_P2P_CLIENT:
3309 case NL80211_IFTYPE_STATION: 3056 case NL80211_IFTYPE_STATION:
3310 if (intbss == wdev->current_bss) 3057 if (intbss == wdev->current_bss)
3311 NLA_PUT_U32(msg, NL80211_BSS_STATUS, 3058 NLA_PUT_U32(msg, NL80211_BSS_STATUS,
@@ -3343,25 +3090,12 @@ static int nl80211_dump_scan(struct sk_buff *skb,
3343 struct net_device *dev; 3090 struct net_device *dev;
3344 struct cfg80211_internal_bss *scan; 3091 struct cfg80211_internal_bss *scan;
3345 struct wireless_dev *wdev; 3092 struct wireless_dev *wdev;
3346 int ifidx = cb->args[0];
3347 int start = cb->args[1], idx = 0; 3093 int start = cb->args[1], idx = 0;
3348 int err; 3094 int err;
3349 3095
3350 if (!ifidx) 3096 err = nl80211_prepare_netdev_dump(skb, cb, &rdev, &dev);
3351 ifidx = nl80211_get_ifidx(cb); 3097 if (err)
3352 if (ifidx < 0) 3098 return err;
3353 return ifidx;
3354 cb->args[0] = ifidx;
3355
3356 dev = dev_get_by_index(sock_net(skb->sk), ifidx);
3357 if (!dev)
3358 return -ENODEV;
3359
3360 rdev = cfg80211_get_dev_from_ifindex(sock_net(skb->sk), ifidx);
3361 if (IS_ERR(rdev)) {
3362 err = PTR_ERR(rdev);
3363 goto out_put_netdev;
3364 }
3365 3099
3366 wdev = dev->ieee80211_ptr; 3100 wdev = dev->ieee80211_ptr;
3367 3101
@@ -3377,21 +3111,17 @@ static int nl80211_dump_scan(struct sk_buff *skb,
3377 cb->nlh->nlmsg_seq, NLM_F_MULTI, 3111 cb->nlh->nlmsg_seq, NLM_F_MULTI,
3378 rdev, wdev, scan) < 0) { 3112 rdev, wdev, scan) < 0) {
3379 idx--; 3113 idx--;
3380 goto out; 3114 break;
3381 } 3115 }
3382 } 3116 }
3383 3117
3384 out:
3385 spin_unlock_bh(&rdev->bss_lock); 3118 spin_unlock_bh(&rdev->bss_lock);
3386 wdev_unlock(wdev); 3119 wdev_unlock(wdev);
3387 3120
3388 cb->args[1] = idx; 3121 cb->args[1] = idx;
3389 err = skb->len; 3122 nl80211_finish_netdev_dump(rdev);
3390 cfg80211_unlock_rdev(rdev);
3391 out_put_netdev:
3392 dev_put(dev);
3393 3123
3394 return err; 3124 return skb->len;
3395} 3125}
3396 3126
3397static int nl80211_send_survey(struct sk_buff *msg, u32 pid, u32 seq, 3127static int nl80211_send_survey(struct sk_buff *msg, u32 pid, u32 seq,
@@ -3421,6 +3151,23 @@ static int nl80211_send_survey(struct sk_buff *msg, u32 pid, u32 seq,
3421 if (survey->filled & SURVEY_INFO_NOISE_DBM) 3151 if (survey->filled & SURVEY_INFO_NOISE_DBM)
3422 NLA_PUT_U8(msg, NL80211_SURVEY_INFO_NOISE, 3152 NLA_PUT_U8(msg, NL80211_SURVEY_INFO_NOISE,
3423 survey->noise); 3153 survey->noise);
3154 if (survey->filled & SURVEY_INFO_IN_USE)
3155 NLA_PUT_FLAG(msg, NL80211_SURVEY_INFO_IN_USE);
3156 if (survey->filled & SURVEY_INFO_CHANNEL_TIME)
3157 NLA_PUT_U64(msg, NL80211_SURVEY_INFO_CHANNEL_TIME,
3158 survey->channel_time);
3159 if (survey->filled & SURVEY_INFO_CHANNEL_TIME_BUSY)
3160 NLA_PUT_U64(msg, NL80211_SURVEY_INFO_CHANNEL_TIME_BUSY,
3161 survey->channel_time_busy);
3162 if (survey->filled & SURVEY_INFO_CHANNEL_TIME_EXT_BUSY)
3163 NLA_PUT_U64(msg, NL80211_SURVEY_INFO_CHANNEL_TIME_EXT_BUSY,
3164 survey->channel_time_ext_busy);
3165 if (survey->filled & SURVEY_INFO_CHANNEL_TIME_RX)
3166 NLA_PUT_U64(msg, NL80211_SURVEY_INFO_CHANNEL_TIME_RX,
3167 survey->channel_time_rx);
3168 if (survey->filled & SURVEY_INFO_CHANNEL_TIME_TX)
3169 NLA_PUT_U64(msg, NL80211_SURVEY_INFO_CHANNEL_TIME_TX,
3170 survey->channel_time_tx);
3424 3171
3425 nla_nest_end(msg, infoattr); 3172 nla_nest_end(msg, infoattr);
3426 3173
@@ -3437,29 +3184,12 @@ static int nl80211_dump_survey(struct sk_buff *skb,
3437 struct survey_info survey; 3184 struct survey_info survey;
3438 struct cfg80211_registered_device *dev; 3185 struct cfg80211_registered_device *dev;
3439 struct net_device *netdev; 3186 struct net_device *netdev;
3440 int ifidx = cb->args[0];
3441 int survey_idx = cb->args[1]; 3187 int survey_idx = cb->args[1];
3442 int res; 3188 int res;
3443 3189
3444 if (!ifidx) 3190 res = nl80211_prepare_netdev_dump(skb, cb, &dev, &netdev);
3445 ifidx = nl80211_get_ifidx(cb); 3191 if (res)
3446 if (ifidx < 0) 3192 return res;
3447 return ifidx;
3448 cb->args[0] = ifidx;
3449
3450 rtnl_lock();
3451
3452 netdev = __dev_get_by_index(sock_net(skb->sk), ifidx);
3453 if (!netdev) {
3454 res = -ENODEV;
3455 goto out_rtnl;
3456 }
3457
3458 dev = cfg80211_get_dev_from_ifindex(sock_net(skb->sk), ifidx);
3459 if (IS_ERR(dev)) {
3460 res = PTR_ERR(dev);
3461 goto out_rtnl;
3462 }
3463 3193
3464 if (!dev->ops->dump_survey) { 3194 if (!dev->ops->dump_survey) {
3465 res = -EOPNOTSUPP; 3195 res = -EOPNOTSUPP;
@@ -3487,10 +3217,7 @@ static int nl80211_dump_survey(struct sk_buff *skb,
3487 cb->args[1] = survey_idx; 3217 cb->args[1] = survey_idx;
3488 res = skb->len; 3218 res = skb->len;
3489 out_err: 3219 out_err:
3490 cfg80211_unlock_rdev(dev); 3220 nl80211_finish_netdev_dump(dev);
3491 out_rtnl:
3492 rtnl_unlock();
3493
3494 return res; 3221 return res;
3495} 3222}
3496 3223
@@ -3523,8 +3250,8 @@ static bool nl80211_valid_cipher_suite(u32 cipher)
3523 3250
3524static int nl80211_authenticate(struct sk_buff *skb, struct genl_info *info) 3251static int nl80211_authenticate(struct sk_buff *skb, struct genl_info *info)
3525{ 3252{
3526 struct cfg80211_registered_device *rdev; 3253 struct cfg80211_registered_device *rdev = info->user_ptr[0];
3527 struct net_device *dev; 3254 struct net_device *dev = info->user_ptr[1];
3528 struct ieee80211_channel *chan; 3255 struct ieee80211_channel *chan;
3529 const u8 *bssid, *ssid, *ie = NULL; 3256 const u8 *bssid, *ssid, *ie = NULL;
3530 int err, ssid_len, ie_len = 0; 3257 int err, ssid_len, ie_len = 0;
@@ -3552,6 +3279,8 @@ static int nl80211_authenticate(struct sk_buff *skb, struct genl_info *info)
3552 return err; 3279 return err;
3553 3280
3554 if (key.idx >= 0) { 3281 if (key.idx >= 0) {
3282 if (key.type != -1 && key.type != NL80211_KEYTYPE_GROUP)
3283 return -EINVAL;
3555 if (!key.p.key || !key.p.key_len) 3284 if (!key.p.key || !key.p.key_len)
3556 return -EINVAL; 3285 return -EINVAL;
3557 if ((key.p.cipher != WLAN_CIPHER_SUITE_WEP40 || 3286 if ((key.p.cipher != WLAN_CIPHER_SUITE_WEP40 ||
@@ -3566,34 +3295,31 @@ static int nl80211_authenticate(struct sk_buff *skb, struct genl_info *info)
3566 key.p.key = NULL; 3295 key.p.key = NULL;
3567 } 3296 }
3568 3297
3569 rtnl_lock(); 3298 if (key.idx >= 0) {
3570 3299 int i;
3571 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev); 3300 bool ok = false;
3572 if (err) 3301 for (i = 0; i < rdev->wiphy.n_cipher_suites; i++) {
3573 goto unlock_rtnl; 3302 if (key.p.cipher == rdev->wiphy.cipher_suites[i]) {
3574 3303 ok = true;
3575 if (!rdev->ops->auth) { 3304 break;
3576 err = -EOPNOTSUPP; 3305 }
3577 goto out; 3306 }
3307 if (!ok)
3308 return -EINVAL;
3578 } 3309 }
3579 3310
3580 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_STATION) { 3311 if (!rdev->ops->auth)
3581 err = -EOPNOTSUPP; 3312 return -EOPNOTSUPP;
3582 goto out;
3583 }
3584 3313
3585 if (!netif_running(dev)) { 3314 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_STATION &&
3586 err = -ENETDOWN; 3315 dev->ieee80211_ptr->iftype != NL80211_IFTYPE_P2P_CLIENT)
3587 goto out; 3316 return -EOPNOTSUPP;
3588 }
3589 3317
3590 bssid = nla_data(info->attrs[NL80211_ATTR_MAC]); 3318 bssid = nla_data(info->attrs[NL80211_ATTR_MAC]);
3591 chan = ieee80211_get_channel(&rdev->wiphy, 3319 chan = ieee80211_get_channel(&rdev->wiphy,
3592 nla_get_u32(info->attrs[NL80211_ATTR_WIPHY_FREQ])); 3320 nla_get_u32(info->attrs[NL80211_ATTR_WIPHY_FREQ]));
3593 if (!chan || (chan->flags & IEEE80211_CHAN_DISABLED)) { 3321 if (!chan || (chan->flags & IEEE80211_CHAN_DISABLED))
3594 err = -EINVAL; 3322 return -EINVAL;
3595 goto out;
3596 }
3597 3323
3598 ssid = nla_data(info->attrs[NL80211_ATTR_SSID]); 3324 ssid = nla_data(info->attrs[NL80211_ATTR_SSID]);
3599 ssid_len = nla_len(info->attrs[NL80211_ATTR_SSID]); 3325 ssid_len = nla_len(info->attrs[NL80211_ATTR_SSID]);
@@ -3604,27 +3330,19 @@ static int nl80211_authenticate(struct sk_buff *skb, struct genl_info *info)
3604 } 3330 }
3605 3331
3606 auth_type = nla_get_u32(info->attrs[NL80211_ATTR_AUTH_TYPE]); 3332 auth_type = nla_get_u32(info->attrs[NL80211_ATTR_AUTH_TYPE]);
3607 if (!nl80211_valid_auth_type(auth_type)) { 3333 if (!nl80211_valid_auth_type(auth_type))
3608 err = -EINVAL; 3334 return -EINVAL;
3609 goto out;
3610 }
3611 3335
3612 local_state_change = !!info->attrs[NL80211_ATTR_LOCAL_STATE_CHANGE]; 3336 local_state_change = !!info->attrs[NL80211_ATTR_LOCAL_STATE_CHANGE];
3613 3337
3614 err = cfg80211_mlme_auth(rdev, dev, chan, auth_type, bssid, 3338 return cfg80211_mlme_auth(rdev, dev, chan, auth_type, bssid,
3615 ssid, ssid_len, ie, ie_len, 3339 ssid, ssid_len, ie, ie_len,
3616 key.p.key, key.p.key_len, key.idx, 3340 key.p.key, key.p.key_len, key.idx,
3617 local_state_change); 3341 local_state_change);
3618
3619out:
3620 cfg80211_unlock_rdev(rdev);
3621 dev_put(dev);
3622unlock_rtnl:
3623 rtnl_unlock();
3624 return err;
3625} 3342}
3626 3343
3627static int nl80211_crypto_settings(struct genl_info *info, 3344static int nl80211_crypto_settings(struct cfg80211_registered_device *rdev,
3345 struct genl_info *info,
3628 struct cfg80211_crypto_settings *settings, 3346 struct cfg80211_crypto_settings *settings,
3629 int cipher_limit) 3347 int cipher_limit)
3630{ 3348{
@@ -3632,6 +3350,19 @@ static int nl80211_crypto_settings(struct genl_info *info,
3632 3350
3633 settings->control_port = info->attrs[NL80211_ATTR_CONTROL_PORT]; 3351 settings->control_port = info->attrs[NL80211_ATTR_CONTROL_PORT];
3634 3352
3353 if (info->attrs[NL80211_ATTR_CONTROL_PORT_ETHERTYPE]) {
3354 u16 proto;
3355 proto = nla_get_u16(
3356 info->attrs[NL80211_ATTR_CONTROL_PORT_ETHERTYPE]);
3357 settings->control_port_ethertype = cpu_to_be16(proto);
3358 if (!(rdev->wiphy.flags & WIPHY_FLAG_CONTROL_PORT_PROTOCOL) &&
3359 proto != ETH_P_PAE)
3360 return -EINVAL;
3361 if (info->attrs[NL80211_ATTR_CONTROL_PORT_NO_ENCRYPT])
3362 settings->control_port_no_encrypt = true;
3363 } else
3364 settings->control_port_ethertype = cpu_to_be16(ETH_P_PAE);
3365
3635 if (info->attrs[NL80211_ATTR_CIPHER_SUITES_PAIRWISE]) { 3366 if (info->attrs[NL80211_ATTR_CIPHER_SUITES_PAIRWISE]) {
3636 void *data; 3367 void *data;
3637 int len, i; 3368 int len, i;
@@ -3691,8 +3422,8 @@ static int nl80211_crypto_settings(struct genl_info *info,
3691 3422
3692static int nl80211_associate(struct sk_buff *skb, struct genl_info *info) 3423static int nl80211_associate(struct sk_buff *skb, struct genl_info *info)
3693{ 3424{
3694 struct cfg80211_registered_device *rdev; 3425 struct cfg80211_registered_device *rdev = info->user_ptr[0];
3695 struct net_device *dev; 3426 struct net_device *dev = info->user_ptr[1];
3696 struct cfg80211_crypto_settings crypto; 3427 struct cfg80211_crypto_settings crypto;
3697 struct ieee80211_channel *chan; 3428 struct ieee80211_channel *chan;
3698 const u8 *bssid, *ssid, *ie = NULL, *prev_bssid = NULL; 3429 const u8 *bssid, *ssid, *ie = NULL, *prev_bssid = NULL;
@@ -3707,35 +3438,19 @@ static int nl80211_associate(struct sk_buff *skb, struct genl_info *info)
3707 !info->attrs[NL80211_ATTR_WIPHY_FREQ]) 3438 !info->attrs[NL80211_ATTR_WIPHY_FREQ])
3708 return -EINVAL; 3439 return -EINVAL;
3709 3440
3710 rtnl_lock(); 3441 if (!rdev->ops->assoc)
3711 3442 return -EOPNOTSUPP;
3712 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
3713 if (err)
3714 goto unlock_rtnl;
3715
3716 if (!rdev->ops->assoc) {
3717 err = -EOPNOTSUPP;
3718 goto out;
3719 }
3720
3721 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_STATION) {
3722 err = -EOPNOTSUPP;
3723 goto out;
3724 }
3725 3443
3726 if (!netif_running(dev)) { 3444 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_STATION &&
3727 err = -ENETDOWN; 3445 dev->ieee80211_ptr->iftype != NL80211_IFTYPE_P2P_CLIENT)
3728 goto out; 3446 return -EOPNOTSUPP;
3729 }
3730 3447
3731 bssid = nla_data(info->attrs[NL80211_ATTR_MAC]); 3448 bssid = nla_data(info->attrs[NL80211_ATTR_MAC]);
3732 3449
3733 chan = ieee80211_get_channel(&rdev->wiphy, 3450 chan = ieee80211_get_channel(&rdev->wiphy,
3734 nla_get_u32(info->attrs[NL80211_ATTR_WIPHY_FREQ])); 3451 nla_get_u32(info->attrs[NL80211_ATTR_WIPHY_FREQ]));
3735 if (!chan || (chan->flags & IEEE80211_CHAN_DISABLED)) { 3452 if (!chan || (chan->flags & IEEE80211_CHAN_DISABLED))
3736 err = -EINVAL; 3453 return -EINVAL;
3737 goto out;
3738 }
3739 3454
3740 ssid = nla_data(info->attrs[NL80211_ATTR_SSID]); 3455 ssid = nla_data(info->attrs[NL80211_ATTR_SSID]);
3741 ssid_len = nla_len(info->attrs[NL80211_ATTR_SSID]); 3456 ssid_len = nla_len(info->attrs[NL80211_ATTR_SSID]);
@@ -3750,35 +3465,28 @@ static int nl80211_associate(struct sk_buff *skb, struct genl_info *info)
3750 nla_get_u32(info->attrs[NL80211_ATTR_USE_MFP]); 3465 nla_get_u32(info->attrs[NL80211_ATTR_USE_MFP]);
3751 if (mfp == NL80211_MFP_REQUIRED) 3466 if (mfp == NL80211_MFP_REQUIRED)
3752 use_mfp = true; 3467 use_mfp = true;
3753 else if (mfp != NL80211_MFP_NO) { 3468 else if (mfp != NL80211_MFP_NO)
3754 err = -EINVAL; 3469 return -EINVAL;
3755 goto out;
3756 }
3757 } 3470 }
3758 3471
3759 if (info->attrs[NL80211_ATTR_PREV_BSSID]) 3472 if (info->attrs[NL80211_ATTR_PREV_BSSID])
3760 prev_bssid = nla_data(info->attrs[NL80211_ATTR_PREV_BSSID]); 3473 prev_bssid = nla_data(info->attrs[NL80211_ATTR_PREV_BSSID]);
3761 3474
3762 err = nl80211_crypto_settings(info, &crypto, 1); 3475 err = nl80211_crypto_settings(rdev, info, &crypto, 1);
3763 if (!err) 3476 if (!err)
3764 err = cfg80211_mlme_assoc(rdev, dev, chan, bssid, prev_bssid, 3477 err = cfg80211_mlme_assoc(rdev, dev, chan, bssid, prev_bssid,
3765 ssid, ssid_len, ie, ie_len, use_mfp, 3478 ssid, ssid_len, ie, ie_len, use_mfp,
3766 &crypto); 3479 &crypto);
3767 3480
3768out:
3769 cfg80211_unlock_rdev(rdev);
3770 dev_put(dev);
3771unlock_rtnl:
3772 rtnl_unlock();
3773 return err; 3481 return err;
3774} 3482}
3775 3483
3776static int nl80211_deauthenticate(struct sk_buff *skb, struct genl_info *info) 3484static int nl80211_deauthenticate(struct sk_buff *skb, struct genl_info *info)
3777{ 3485{
3778 struct cfg80211_registered_device *rdev; 3486 struct cfg80211_registered_device *rdev = info->user_ptr[0];
3779 struct net_device *dev; 3487 struct net_device *dev = info->user_ptr[1];
3780 const u8 *ie = NULL, *bssid; 3488 const u8 *ie = NULL, *bssid;
3781 int err, ie_len = 0; 3489 int ie_len = 0;
3782 u16 reason_code; 3490 u16 reason_code;
3783 bool local_state_change; 3491 bool local_state_change;
3784 3492
@@ -3791,34 +3499,19 @@ static int nl80211_deauthenticate(struct sk_buff *skb, struct genl_info *info)
3791 if (!info->attrs[NL80211_ATTR_REASON_CODE]) 3499 if (!info->attrs[NL80211_ATTR_REASON_CODE])
3792 return -EINVAL; 3500 return -EINVAL;
3793 3501
3794 rtnl_lock(); 3502 if (!rdev->ops->deauth)
3795 3503 return -EOPNOTSUPP;
3796 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
3797 if (err)
3798 goto unlock_rtnl;
3799
3800 if (!rdev->ops->deauth) {
3801 err = -EOPNOTSUPP;
3802 goto out;
3803 }
3804
3805 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_STATION) {
3806 err = -EOPNOTSUPP;
3807 goto out;
3808 }
3809 3504
3810 if (!netif_running(dev)) { 3505 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_STATION &&
3811 err = -ENETDOWN; 3506 dev->ieee80211_ptr->iftype != NL80211_IFTYPE_P2P_CLIENT)
3812 goto out; 3507 return -EOPNOTSUPP;
3813 }
3814 3508
3815 bssid = nla_data(info->attrs[NL80211_ATTR_MAC]); 3509 bssid = nla_data(info->attrs[NL80211_ATTR_MAC]);
3816 3510
3817 reason_code = nla_get_u16(info->attrs[NL80211_ATTR_REASON_CODE]); 3511 reason_code = nla_get_u16(info->attrs[NL80211_ATTR_REASON_CODE]);
3818 if (reason_code == 0) { 3512 if (reason_code == 0) {
3819 /* Reason Code 0 is reserved */ 3513 /* Reason Code 0 is reserved */
3820 err = -EINVAL; 3514 return -EINVAL;
3821 goto out;
3822 } 3515 }
3823 3516
3824 if (info->attrs[NL80211_ATTR_IE]) { 3517 if (info->attrs[NL80211_ATTR_IE]) {
@@ -3828,23 +3521,16 @@ static int nl80211_deauthenticate(struct sk_buff *skb, struct genl_info *info)
3828 3521
3829 local_state_change = !!info->attrs[NL80211_ATTR_LOCAL_STATE_CHANGE]; 3522 local_state_change = !!info->attrs[NL80211_ATTR_LOCAL_STATE_CHANGE];
3830 3523
3831 err = cfg80211_mlme_deauth(rdev, dev, bssid, ie, ie_len, reason_code, 3524 return cfg80211_mlme_deauth(rdev, dev, bssid, ie, ie_len, reason_code,
3832 local_state_change); 3525 local_state_change);
3833
3834out:
3835 cfg80211_unlock_rdev(rdev);
3836 dev_put(dev);
3837unlock_rtnl:
3838 rtnl_unlock();
3839 return err;
3840} 3526}
3841 3527
3842static int nl80211_disassociate(struct sk_buff *skb, struct genl_info *info) 3528static int nl80211_disassociate(struct sk_buff *skb, struct genl_info *info)
3843{ 3529{
3844 struct cfg80211_registered_device *rdev; 3530 struct cfg80211_registered_device *rdev = info->user_ptr[0];
3845 struct net_device *dev; 3531 struct net_device *dev = info->user_ptr[1];
3846 const u8 *ie = NULL, *bssid; 3532 const u8 *ie = NULL, *bssid;
3847 int err, ie_len = 0; 3533 int ie_len = 0;
3848 u16 reason_code; 3534 u16 reason_code;
3849 bool local_state_change; 3535 bool local_state_change;
3850 3536
@@ -3857,34 +3543,19 @@ static int nl80211_disassociate(struct sk_buff *skb, struct genl_info *info)
3857 if (!info->attrs[NL80211_ATTR_REASON_CODE]) 3543 if (!info->attrs[NL80211_ATTR_REASON_CODE])
3858 return -EINVAL; 3544 return -EINVAL;
3859 3545
3860 rtnl_lock(); 3546 if (!rdev->ops->disassoc)
3861 3547 return -EOPNOTSUPP;
3862 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
3863 if (err)
3864 goto unlock_rtnl;
3865
3866 if (!rdev->ops->disassoc) {
3867 err = -EOPNOTSUPP;
3868 goto out;
3869 }
3870
3871 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_STATION) {
3872 err = -EOPNOTSUPP;
3873 goto out;
3874 }
3875 3548
3876 if (!netif_running(dev)) { 3549 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_STATION &&
3877 err = -ENETDOWN; 3550 dev->ieee80211_ptr->iftype != NL80211_IFTYPE_P2P_CLIENT)
3878 goto out; 3551 return -EOPNOTSUPP;
3879 }
3880 3552
3881 bssid = nla_data(info->attrs[NL80211_ATTR_MAC]); 3553 bssid = nla_data(info->attrs[NL80211_ATTR_MAC]);
3882 3554
3883 reason_code = nla_get_u16(info->attrs[NL80211_ATTR_REASON_CODE]); 3555 reason_code = nla_get_u16(info->attrs[NL80211_ATTR_REASON_CODE]);
3884 if (reason_code == 0) { 3556 if (reason_code == 0) {
3885 /* Reason Code 0 is reserved */ 3557 /* Reason Code 0 is reserved */
3886 err = -EINVAL; 3558 return -EINVAL;
3887 goto out;
3888 } 3559 }
3889 3560
3890 if (info->attrs[NL80211_ATTR_IE]) { 3561 if (info->attrs[NL80211_ATTR_IE]) {
@@ -3894,21 +3565,14 @@ static int nl80211_disassociate(struct sk_buff *skb, struct genl_info *info)
3894 3565
3895 local_state_change = !!info->attrs[NL80211_ATTR_LOCAL_STATE_CHANGE]; 3566 local_state_change = !!info->attrs[NL80211_ATTR_LOCAL_STATE_CHANGE];
3896 3567
3897 err = cfg80211_mlme_disassoc(rdev, dev, bssid, ie, ie_len, reason_code, 3568 return cfg80211_mlme_disassoc(rdev, dev, bssid, ie, ie_len, reason_code,
3898 local_state_change); 3569 local_state_change);
3899
3900out:
3901 cfg80211_unlock_rdev(rdev);
3902 dev_put(dev);
3903unlock_rtnl:
3904 rtnl_unlock();
3905 return err;
3906} 3570}
3907 3571
3908static int nl80211_join_ibss(struct sk_buff *skb, struct genl_info *info) 3572static int nl80211_join_ibss(struct sk_buff *skb, struct genl_info *info)
3909{ 3573{
3910 struct cfg80211_registered_device *rdev; 3574 struct cfg80211_registered_device *rdev = info->user_ptr[0];
3911 struct net_device *dev; 3575 struct net_device *dev = info->user_ptr[1];
3912 struct cfg80211_ibss_params ibss; 3576 struct cfg80211_ibss_params ibss;
3913 struct wiphy *wiphy; 3577 struct wiphy *wiphy;
3914 struct cfg80211_cached_keys *connkeys = NULL; 3578 struct cfg80211_cached_keys *connkeys = NULL;
@@ -3933,26 +3597,11 @@ static int nl80211_join_ibss(struct sk_buff *skb, struct genl_info *info)
3933 return -EINVAL; 3597 return -EINVAL;
3934 } 3598 }
3935 3599
3936 rtnl_lock(); 3600 if (!rdev->ops->join_ibss)
3937 3601 return -EOPNOTSUPP;
3938 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
3939 if (err)
3940 goto unlock_rtnl;
3941
3942 if (!rdev->ops->join_ibss) {
3943 err = -EOPNOTSUPP;
3944 goto out;
3945 }
3946
3947 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_ADHOC) {
3948 err = -EOPNOTSUPP;
3949 goto out;
3950 }
3951 3602
3952 if (!netif_running(dev)) { 3603 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_ADHOC)
3953 err = -ENETDOWN; 3604 return -EOPNOTSUPP;
3954 goto out;
3955 }
3956 3605
3957 wiphy = &rdev->wiphy; 3606 wiphy = &rdev->wiphy;
3958 3607
@@ -3970,24 +3619,12 @@ static int nl80211_join_ibss(struct sk_buff *skb, struct genl_info *info)
3970 nla_get_u32(info->attrs[NL80211_ATTR_WIPHY_FREQ])); 3619 nla_get_u32(info->attrs[NL80211_ATTR_WIPHY_FREQ]));
3971 if (!ibss.channel || 3620 if (!ibss.channel ||
3972 ibss.channel->flags & IEEE80211_CHAN_NO_IBSS || 3621 ibss.channel->flags & IEEE80211_CHAN_NO_IBSS ||
3973 ibss.channel->flags & IEEE80211_CHAN_DISABLED) { 3622 ibss.channel->flags & IEEE80211_CHAN_DISABLED)
3974 err = -EINVAL; 3623 return -EINVAL;
3975 goto out;
3976 }
3977 3624
3978 ibss.channel_fixed = !!info->attrs[NL80211_ATTR_FREQ_FIXED]; 3625 ibss.channel_fixed = !!info->attrs[NL80211_ATTR_FREQ_FIXED];
3979 ibss.privacy = !!info->attrs[NL80211_ATTR_PRIVACY]; 3626 ibss.privacy = !!info->attrs[NL80211_ATTR_PRIVACY];
3980 3627
3981 if (ibss.privacy && info->attrs[NL80211_ATTR_KEYS]) {
3982 connkeys = nl80211_parse_connkeys(rdev,
3983 info->attrs[NL80211_ATTR_KEYS]);
3984 if (IS_ERR(connkeys)) {
3985 err = PTR_ERR(connkeys);
3986 connkeys = NULL;
3987 goto out;
3988 }
3989 }
3990
3991 if (info->attrs[NL80211_ATTR_BSS_BASIC_RATES]) { 3628 if (info->attrs[NL80211_ATTR_BSS_BASIC_RATES]) {
3992 u8 *rates = 3629 u8 *rates =
3993 nla_data(info->attrs[NL80211_ATTR_BSS_BASIC_RATES]); 3630 nla_data(info->attrs[NL80211_ATTR_BSS_BASIC_RATES]);
@@ -3997,10 +3634,8 @@ static int nl80211_join_ibss(struct sk_buff *skb, struct genl_info *info)
3997 wiphy->bands[ibss.channel->band]; 3634 wiphy->bands[ibss.channel->band];
3998 int i, j; 3635 int i, j;
3999 3636
4000 if (n_rates == 0) { 3637 if (n_rates == 0)
4001 err = -EINVAL; 3638 return -EINVAL;
4002 goto out;
4003 }
4004 3639
4005 for (i = 0; i < n_rates; i++) { 3640 for (i = 0; i < n_rates; i++) {
4006 int rate = (rates[i] & 0x7f) * 5; 3641 int rate = (rates[i] & 0x7f) * 5;
@@ -4013,77 +3648,36 @@ static int nl80211_join_ibss(struct sk_buff *skb, struct genl_info *info)
4013 break; 3648 break;
4014 } 3649 }
4015 } 3650 }
4016 if (!found) { 3651 if (!found)
4017 err = -EINVAL; 3652 return -EINVAL;
4018 goto out;
4019 }
4020 }
4021 } else {
4022 /*
4023 * If no rates were explicitly configured,
4024 * use the mandatory rate set for 11b or
4025 * 11a for maximum compatibility.
4026 */
4027 struct ieee80211_supported_band *sband =
4028 wiphy->bands[ibss.channel->band];
4029 int j;
4030 u32 flag = ibss.channel->band == IEEE80211_BAND_5GHZ ?
4031 IEEE80211_RATE_MANDATORY_A :
4032 IEEE80211_RATE_MANDATORY_B;
4033
4034 for (j = 0; j < sband->n_bitrates; j++) {
4035 if (sband->bitrates[j].flags & flag)
4036 ibss.basic_rates |= BIT(j);
4037 } 3653 }
4038 } 3654 }
4039 3655
4040 err = cfg80211_join_ibss(rdev, dev, &ibss, connkeys); 3656 if (ibss.privacy && info->attrs[NL80211_ATTR_KEYS]) {
3657 connkeys = nl80211_parse_connkeys(rdev,
3658 info->attrs[NL80211_ATTR_KEYS]);
3659 if (IS_ERR(connkeys))
3660 return PTR_ERR(connkeys);
3661 }
4041 3662
4042out: 3663 err = cfg80211_join_ibss(rdev, dev, &ibss, connkeys);
4043 cfg80211_unlock_rdev(rdev);
4044 dev_put(dev);
4045unlock_rtnl:
4046 if (err) 3664 if (err)
4047 kfree(connkeys); 3665 kfree(connkeys);
4048 rtnl_unlock();
4049 return err; 3666 return err;
4050} 3667}
4051 3668
4052static int nl80211_leave_ibss(struct sk_buff *skb, struct genl_info *info) 3669static int nl80211_leave_ibss(struct sk_buff *skb, struct genl_info *info)
4053{ 3670{
4054 struct cfg80211_registered_device *rdev; 3671 struct cfg80211_registered_device *rdev = info->user_ptr[0];
4055 struct net_device *dev; 3672 struct net_device *dev = info->user_ptr[1];
4056 int err;
4057
4058 rtnl_lock();
4059
4060 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
4061 if (err)
4062 goto unlock_rtnl;
4063
4064 if (!rdev->ops->leave_ibss) {
4065 err = -EOPNOTSUPP;
4066 goto out;
4067 }
4068 3673
4069 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_ADHOC) { 3674 if (!rdev->ops->leave_ibss)
4070 err = -EOPNOTSUPP; 3675 return -EOPNOTSUPP;
4071 goto out;
4072 }
4073
4074 if (!netif_running(dev)) {
4075 err = -ENETDOWN;
4076 goto out;
4077 }
4078 3676
4079 err = cfg80211_leave_ibss(rdev, dev, false); 3677 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_ADHOC)
3678 return -EOPNOTSUPP;
4080 3679
4081out: 3680 return cfg80211_leave_ibss(rdev, dev, false);
4082 cfg80211_unlock_rdev(rdev);
4083 dev_put(dev);
4084unlock_rtnl:
4085 rtnl_unlock();
4086 return err;
4087} 3681}
4088 3682
4089#ifdef CONFIG_NL80211_TESTMODE 3683#ifdef CONFIG_NL80211_TESTMODE
@@ -4093,20 +3687,12 @@ static struct genl_multicast_group nl80211_testmode_mcgrp = {
4093 3687
4094static int nl80211_testmode_do(struct sk_buff *skb, struct genl_info *info) 3688static int nl80211_testmode_do(struct sk_buff *skb, struct genl_info *info)
4095{ 3689{
4096 struct cfg80211_registered_device *rdev; 3690 struct cfg80211_registered_device *rdev = info->user_ptr[0];
4097 int err; 3691 int err;
4098 3692
4099 if (!info->attrs[NL80211_ATTR_TESTDATA]) 3693 if (!info->attrs[NL80211_ATTR_TESTDATA])
4100 return -EINVAL; 3694 return -EINVAL;
4101 3695
4102 rtnl_lock();
4103
4104 rdev = cfg80211_get_dev_from_info(info);
4105 if (IS_ERR(rdev)) {
4106 err = PTR_ERR(rdev);
4107 goto unlock_rtnl;
4108 }
4109
4110 err = -EOPNOTSUPP; 3696 err = -EOPNOTSUPP;
4111 if (rdev->ops->testmode_cmd) { 3697 if (rdev->ops->testmode_cmd) {
4112 rdev->testmode_info = info; 3698 rdev->testmode_info = info;
@@ -4116,10 +3702,6 @@ static int nl80211_testmode_do(struct sk_buff *skb, struct genl_info *info)
4116 rdev->testmode_info = NULL; 3702 rdev->testmode_info = NULL;
4117 } 3703 }
4118 3704
4119 cfg80211_unlock_rdev(rdev);
4120
4121 unlock_rtnl:
4122 rtnl_unlock();
4123 return err; 3705 return err;
4124} 3706}
4125 3707
@@ -4210,8 +3792,8 @@ EXPORT_SYMBOL(cfg80211_testmode_event);
4210 3792
4211static int nl80211_connect(struct sk_buff *skb, struct genl_info *info) 3793static int nl80211_connect(struct sk_buff *skb, struct genl_info *info)
4212{ 3794{
4213 struct cfg80211_registered_device *rdev; 3795 struct cfg80211_registered_device *rdev = info->user_ptr[0];
4214 struct net_device *dev; 3796 struct net_device *dev = info->user_ptr[1];
4215 struct cfg80211_connect_params connect; 3797 struct cfg80211_connect_params connect;
4216 struct wiphy *wiphy; 3798 struct wiphy *wiphy;
4217 struct cfg80211_cached_keys *connkeys = NULL; 3799 struct cfg80211_cached_keys *connkeys = NULL;
@@ -4236,25 +3818,14 @@ static int nl80211_connect(struct sk_buff *skb, struct genl_info *info)
4236 3818
4237 connect.privacy = info->attrs[NL80211_ATTR_PRIVACY]; 3819 connect.privacy = info->attrs[NL80211_ATTR_PRIVACY];
4238 3820
4239 err = nl80211_crypto_settings(info, &connect.crypto, 3821 err = nl80211_crypto_settings(rdev, info, &connect.crypto,
4240 NL80211_MAX_NR_CIPHER_SUITES); 3822 NL80211_MAX_NR_CIPHER_SUITES);
4241 if (err) 3823 if (err)
4242 return err; 3824 return err;
4243 rtnl_lock();
4244 3825
4245 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev); 3826 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_STATION &&
4246 if (err) 3827 dev->ieee80211_ptr->iftype != NL80211_IFTYPE_P2P_CLIENT)
4247 goto unlock_rtnl; 3828 return -EOPNOTSUPP;
4248
4249 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_STATION) {
4250 err = -EOPNOTSUPP;
4251 goto out;
4252 }
4253
4254 if (!netif_running(dev)) {
4255 err = -ENETDOWN;
4256 goto out;
4257 }
4258 3829
4259 wiphy = &rdev->wiphy; 3830 wiphy = &rdev->wiphy;
4260 3831
@@ -4273,39 +3844,27 @@ static int nl80211_connect(struct sk_buff *skb, struct genl_info *info)
4273 ieee80211_get_channel(wiphy, 3844 ieee80211_get_channel(wiphy,
4274 nla_get_u32(info->attrs[NL80211_ATTR_WIPHY_FREQ])); 3845 nla_get_u32(info->attrs[NL80211_ATTR_WIPHY_FREQ]));
4275 if (!connect.channel || 3846 if (!connect.channel ||
4276 connect.channel->flags & IEEE80211_CHAN_DISABLED) { 3847 connect.channel->flags & IEEE80211_CHAN_DISABLED)
4277 err = -EINVAL; 3848 return -EINVAL;
4278 goto out;
4279 }
4280 } 3849 }
4281 3850
4282 if (connect.privacy && info->attrs[NL80211_ATTR_KEYS]) { 3851 if (connect.privacy && info->attrs[NL80211_ATTR_KEYS]) {
4283 connkeys = nl80211_parse_connkeys(rdev, 3852 connkeys = nl80211_parse_connkeys(rdev,
4284 info->attrs[NL80211_ATTR_KEYS]); 3853 info->attrs[NL80211_ATTR_KEYS]);
4285 if (IS_ERR(connkeys)) { 3854 if (IS_ERR(connkeys))
4286 err = PTR_ERR(connkeys); 3855 return PTR_ERR(connkeys);
4287 connkeys = NULL;
4288 goto out;
4289 }
4290 } 3856 }
4291 3857
4292 err = cfg80211_connect(rdev, dev, &connect, connkeys); 3858 err = cfg80211_connect(rdev, dev, &connect, connkeys);
4293
4294out:
4295 cfg80211_unlock_rdev(rdev);
4296 dev_put(dev);
4297unlock_rtnl:
4298 if (err) 3859 if (err)
4299 kfree(connkeys); 3860 kfree(connkeys);
4300 rtnl_unlock();
4301 return err; 3861 return err;
4302} 3862}
4303 3863
4304static int nl80211_disconnect(struct sk_buff *skb, struct genl_info *info) 3864static int nl80211_disconnect(struct sk_buff *skb, struct genl_info *info)
4305{ 3865{
4306 struct cfg80211_registered_device *rdev; 3866 struct cfg80211_registered_device *rdev = info->user_ptr[0];
4307 struct net_device *dev; 3867 struct net_device *dev = info->user_ptr[1];
4308 int err;
4309 u16 reason; 3868 u16 reason;
4310 3869
4311 if (!info->attrs[NL80211_ATTR_REASON_CODE]) 3870 if (!info->attrs[NL80211_ATTR_REASON_CODE])
@@ -4316,35 +3875,16 @@ static int nl80211_disconnect(struct sk_buff *skb, struct genl_info *info)
4316 if (reason == 0) 3875 if (reason == 0)
4317 return -EINVAL; 3876 return -EINVAL;
4318 3877
4319 rtnl_lock(); 3878 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_STATION &&
4320 3879 dev->ieee80211_ptr->iftype != NL80211_IFTYPE_P2P_CLIENT)
4321 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev); 3880 return -EOPNOTSUPP;
4322 if (err)
4323 goto unlock_rtnl;
4324
4325 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_STATION) {
4326 err = -EOPNOTSUPP;
4327 goto out;
4328 }
4329
4330 if (!netif_running(dev)) {
4331 err = -ENETDOWN;
4332 goto out;
4333 }
4334
4335 err = cfg80211_disconnect(rdev, dev, reason, true);
4336 3881
4337out: 3882 return cfg80211_disconnect(rdev, dev, reason, true);
4338 cfg80211_unlock_rdev(rdev);
4339 dev_put(dev);
4340unlock_rtnl:
4341 rtnl_unlock();
4342 return err;
4343} 3883}
4344 3884
4345static int nl80211_wiphy_netns(struct sk_buff *skb, struct genl_info *info) 3885static int nl80211_wiphy_netns(struct sk_buff *skb, struct genl_info *info)
4346{ 3886{
4347 struct cfg80211_registered_device *rdev; 3887 struct cfg80211_registered_device *rdev = info->user_ptr[0];
4348 struct net *net; 3888 struct net *net;
4349 int err; 3889 int err;
4350 u32 pid; 3890 u32 pid;
@@ -4354,43 +3894,26 @@ static int nl80211_wiphy_netns(struct sk_buff *skb, struct genl_info *info)
4354 3894
4355 pid = nla_get_u32(info->attrs[NL80211_ATTR_PID]); 3895 pid = nla_get_u32(info->attrs[NL80211_ATTR_PID]);
4356 3896
4357 rtnl_lock();
4358
4359 rdev = cfg80211_get_dev_from_info(info);
4360 if (IS_ERR(rdev)) {
4361 err = PTR_ERR(rdev);
4362 goto out_rtnl;
4363 }
4364
4365 net = get_net_ns_by_pid(pid); 3897 net = get_net_ns_by_pid(pid);
4366 if (IS_ERR(net)) { 3898 if (IS_ERR(net))
4367 err = PTR_ERR(net); 3899 return PTR_ERR(net);
4368 goto out;
4369 }
4370 3900
4371 err = 0; 3901 err = 0;
4372 3902
4373 /* check if anything to do */ 3903 /* check if anything to do */
4374 if (net_eq(wiphy_net(&rdev->wiphy), net)) 3904 if (!net_eq(wiphy_net(&rdev->wiphy), net))
4375 goto out_put_net; 3905 err = cfg80211_switch_netns(rdev, net);
4376 3906
4377 err = cfg80211_switch_netns(rdev, net);
4378 out_put_net:
4379 put_net(net); 3907 put_net(net);
4380 out:
4381 cfg80211_unlock_rdev(rdev);
4382 out_rtnl:
4383 rtnl_unlock();
4384 return err; 3908 return err;
4385} 3909}
4386 3910
4387static int nl80211_setdel_pmksa(struct sk_buff *skb, struct genl_info *info) 3911static int nl80211_setdel_pmksa(struct sk_buff *skb, struct genl_info *info)
4388{ 3912{
4389 struct cfg80211_registered_device *rdev; 3913 struct cfg80211_registered_device *rdev = info->user_ptr[0];
4390 int (*rdev_ops)(struct wiphy *wiphy, struct net_device *dev, 3914 int (*rdev_ops)(struct wiphy *wiphy, struct net_device *dev,
4391 struct cfg80211_pmksa *pmksa) = NULL; 3915 struct cfg80211_pmksa *pmksa) = NULL;
4392 int err; 3916 struct net_device *dev = info->user_ptr[1];
4393 struct net_device *dev;
4394 struct cfg80211_pmksa pmksa; 3917 struct cfg80211_pmksa pmksa;
4395 3918
4396 memset(&pmksa, 0, sizeof(struct cfg80211_pmksa)); 3919 memset(&pmksa, 0, sizeof(struct cfg80211_pmksa));
@@ -4401,19 +3924,12 @@ static int nl80211_setdel_pmksa(struct sk_buff *skb, struct genl_info *info)
4401 if (!info->attrs[NL80211_ATTR_PMKID]) 3924 if (!info->attrs[NL80211_ATTR_PMKID])
4402 return -EINVAL; 3925 return -EINVAL;
4403 3926
4404 rtnl_lock();
4405
4406 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
4407 if (err)
4408 goto out_rtnl;
4409
4410 pmksa.pmkid = nla_data(info->attrs[NL80211_ATTR_PMKID]); 3927 pmksa.pmkid = nla_data(info->attrs[NL80211_ATTR_PMKID]);
4411 pmksa.bssid = nla_data(info->attrs[NL80211_ATTR_MAC]); 3928 pmksa.bssid = nla_data(info->attrs[NL80211_ATTR_MAC]);
4412 3929
4413 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_STATION) { 3930 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_STATION &&
4414 err = -EOPNOTSUPP; 3931 dev->ieee80211_ptr->iftype != NL80211_IFTYPE_P2P_CLIENT)
4415 goto out; 3932 return -EOPNOTSUPP;
4416 }
4417 3933
4418 switch (info->genlhdr->cmd) { 3934 switch (info->genlhdr->cmd) {
4419 case NL80211_CMD_SET_PMKSA: 3935 case NL80211_CMD_SET_PMKSA:
@@ -4427,61 +3943,32 @@ static int nl80211_setdel_pmksa(struct sk_buff *skb, struct genl_info *info)
4427 break; 3943 break;
4428 } 3944 }
4429 3945
4430 if (!rdev_ops) { 3946 if (!rdev_ops)
4431 err = -EOPNOTSUPP; 3947 return -EOPNOTSUPP;
4432 goto out;
4433 }
4434
4435 err = rdev_ops(&rdev->wiphy, dev, &pmksa);
4436
4437 out:
4438 cfg80211_unlock_rdev(rdev);
4439 dev_put(dev);
4440 out_rtnl:
4441 rtnl_unlock();
4442 3948
4443 return err; 3949 return rdev_ops(&rdev->wiphy, dev, &pmksa);
4444} 3950}
4445 3951
4446static int nl80211_flush_pmksa(struct sk_buff *skb, struct genl_info *info) 3952static int nl80211_flush_pmksa(struct sk_buff *skb, struct genl_info *info)
4447{ 3953{
4448 struct cfg80211_registered_device *rdev; 3954 struct cfg80211_registered_device *rdev = info->user_ptr[0];
4449 int err; 3955 struct net_device *dev = info->user_ptr[1];
4450 struct net_device *dev;
4451
4452 rtnl_lock();
4453
4454 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
4455 if (err)
4456 goto out_rtnl;
4457
4458 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_STATION) {
4459 err = -EOPNOTSUPP;
4460 goto out;
4461 }
4462
4463 if (!rdev->ops->flush_pmksa) {
4464 err = -EOPNOTSUPP;
4465 goto out;
4466 }
4467
4468 err = rdev->ops->flush_pmksa(&rdev->wiphy, dev);
4469 3956
4470 out: 3957 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_STATION &&
4471 cfg80211_unlock_rdev(rdev); 3958 dev->ieee80211_ptr->iftype != NL80211_IFTYPE_P2P_CLIENT)
4472 dev_put(dev); 3959 return -EOPNOTSUPP;
4473 out_rtnl:
4474 rtnl_unlock();
4475 3960
4476 return err; 3961 if (!rdev->ops->flush_pmksa)
3962 return -EOPNOTSUPP;
4477 3963
3964 return rdev->ops->flush_pmksa(&rdev->wiphy, dev);
4478} 3965}
4479 3966
4480static int nl80211_remain_on_channel(struct sk_buff *skb, 3967static int nl80211_remain_on_channel(struct sk_buff *skb,
4481 struct genl_info *info) 3968 struct genl_info *info)
4482{ 3969{
4483 struct cfg80211_registered_device *rdev; 3970 struct cfg80211_registered_device *rdev = info->user_ptr[0];
4484 struct net_device *dev; 3971 struct net_device *dev = info->user_ptr[1];
4485 struct ieee80211_channel *chan; 3972 struct ieee80211_channel *chan;
4486 struct sk_buff *msg; 3973 struct sk_buff *msg;
4487 void *hdr; 3974 void *hdr;
@@ -4503,21 +3990,8 @@ static int nl80211_remain_on_channel(struct sk_buff *skb,
4503 if (!duration || !msecs_to_jiffies(duration) || duration > 5000) 3990 if (!duration || !msecs_to_jiffies(duration) || duration > 5000)
4504 return -EINVAL; 3991 return -EINVAL;
4505 3992
4506 rtnl_lock(); 3993 if (!rdev->ops->remain_on_channel)
4507 3994 return -EOPNOTSUPP;
4508 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
4509 if (err)
4510 goto unlock_rtnl;
4511
4512 if (!rdev->ops->remain_on_channel) {
4513 err = -EOPNOTSUPP;
4514 goto out;
4515 }
4516
4517 if (!netif_running(dev)) {
4518 err = -ENETDOWN;
4519 goto out;
4520 }
4521 3995
4522 if (info->attrs[NL80211_ATTR_WIPHY_CHANNEL_TYPE]) { 3996 if (info->attrs[NL80211_ATTR_WIPHY_CHANNEL_TYPE]) {
4523 channel_type = nla_get_u32( 3997 channel_type = nla_get_u32(
@@ -4525,24 +3999,18 @@ static int nl80211_remain_on_channel(struct sk_buff *skb,
4525 if (channel_type != NL80211_CHAN_NO_HT && 3999 if (channel_type != NL80211_CHAN_NO_HT &&
4526 channel_type != NL80211_CHAN_HT20 && 4000 channel_type != NL80211_CHAN_HT20 &&
4527 channel_type != NL80211_CHAN_HT40PLUS && 4001 channel_type != NL80211_CHAN_HT40PLUS &&
4528 channel_type != NL80211_CHAN_HT40MINUS) { 4002 channel_type != NL80211_CHAN_HT40MINUS)
4529 err = -EINVAL; 4003 return -EINVAL;
4530 goto out;
4531 }
4532 } 4004 }
4533 4005
4534 freq = nla_get_u32(info->attrs[NL80211_ATTR_WIPHY_FREQ]); 4006 freq = nla_get_u32(info->attrs[NL80211_ATTR_WIPHY_FREQ]);
4535 chan = rdev_freq_to_chan(rdev, freq, channel_type); 4007 chan = rdev_freq_to_chan(rdev, freq, channel_type);
4536 if (chan == NULL) { 4008 if (chan == NULL)
4537 err = -EINVAL; 4009 return -EINVAL;
4538 goto out;
4539 }
4540 4010
4541 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL); 4011 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
4542 if (!msg) { 4012 if (!msg)
4543 err = -ENOMEM; 4013 return -ENOMEM;
4544 goto out;
4545 }
4546 4014
4547 hdr = nl80211hdr_put(msg, info->snd_pid, info->snd_seq, 0, 4015 hdr = nl80211hdr_put(msg, info->snd_pid, info->snd_seq, 0,
4548 NL80211_CMD_REMAIN_ON_CHANNEL); 4016 NL80211_CMD_REMAIN_ON_CHANNEL);
@@ -4561,58 +4029,32 @@ static int nl80211_remain_on_channel(struct sk_buff *skb,
4561 NLA_PUT_U64(msg, NL80211_ATTR_COOKIE, cookie); 4029 NLA_PUT_U64(msg, NL80211_ATTR_COOKIE, cookie);
4562 4030
4563 genlmsg_end(msg, hdr); 4031 genlmsg_end(msg, hdr);
4564 err = genlmsg_reply(msg, info); 4032
4565 goto out; 4033 return genlmsg_reply(msg, info);
4566 4034
4567 nla_put_failure: 4035 nla_put_failure:
4568 err = -ENOBUFS; 4036 err = -ENOBUFS;
4569 free_msg: 4037 free_msg:
4570 nlmsg_free(msg); 4038 nlmsg_free(msg);
4571 out:
4572 cfg80211_unlock_rdev(rdev);
4573 dev_put(dev);
4574 unlock_rtnl:
4575 rtnl_unlock();
4576 return err; 4039 return err;
4577} 4040}
4578 4041
4579static int nl80211_cancel_remain_on_channel(struct sk_buff *skb, 4042static int nl80211_cancel_remain_on_channel(struct sk_buff *skb,
4580 struct genl_info *info) 4043 struct genl_info *info)
4581{ 4044{
4582 struct cfg80211_registered_device *rdev; 4045 struct cfg80211_registered_device *rdev = info->user_ptr[0];
4583 struct net_device *dev; 4046 struct net_device *dev = info->user_ptr[1];
4584 u64 cookie; 4047 u64 cookie;
4585 int err;
4586 4048
4587 if (!info->attrs[NL80211_ATTR_COOKIE]) 4049 if (!info->attrs[NL80211_ATTR_COOKIE])
4588 return -EINVAL; 4050 return -EINVAL;
4589 4051
4590 rtnl_lock(); 4052 if (!rdev->ops->cancel_remain_on_channel)
4591 4053 return -EOPNOTSUPP;
4592 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
4593 if (err)
4594 goto unlock_rtnl;
4595
4596 if (!rdev->ops->cancel_remain_on_channel) {
4597 err = -EOPNOTSUPP;
4598 goto out;
4599 }
4600
4601 if (!netif_running(dev)) {
4602 err = -ENETDOWN;
4603 goto out;
4604 }
4605 4054
4606 cookie = nla_get_u64(info->attrs[NL80211_ATTR_COOKIE]); 4055 cookie = nla_get_u64(info->attrs[NL80211_ATTR_COOKIE]);
4607 4056
4608 err = rdev->ops->cancel_remain_on_channel(&rdev->wiphy, dev, cookie); 4057 return rdev->ops->cancel_remain_on_channel(&rdev->wiphy, dev, cookie);
4609
4610 out:
4611 cfg80211_unlock_rdev(rdev);
4612 dev_put(dev);
4613 unlock_rtnl:
4614 rtnl_unlock();
4615 return err;
4616} 4058}
4617 4059
4618static u32 rateset_to_mask(struct ieee80211_supported_band *sband, 4060static u32 rateset_to_mask(struct ieee80211_supported_band *sband,
@@ -4648,26 +4090,18 @@ static int nl80211_set_tx_bitrate_mask(struct sk_buff *skb,
4648 struct genl_info *info) 4090 struct genl_info *info)
4649{ 4091{
4650 struct nlattr *tb[NL80211_TXRATE_MAX + 1]; 4092 struct nlattr *tb[NL80211_TXRATE_MAX + 1];
4651 struct cfg80211_registered_device *rdev; 4093 struct cfg80211_registered_device *rdev = info->user_ptr[0];
4652 struct cfg80211_bitrate_mask mask; 4094 struct cfg80211_bitrate_mask mask;
4653 int err, rem, i; 4095 int rem, i;
4654 struct net_device *dev; 4096 struct net_device *dev = info->user_ptr[1];
4655 struct nlattr *tx_rates; 4097 struct nlattr *tx_rates;
4656 struct ieee80211_supported_band *sband; 4098 struct ieee80211_supported_band *sband;
4657 4099
4658 if (info->attrs[NL80211_ATTR_TX_RATES] == NULL) 4100 if (info->attrs[NL80211_ATTR_TX_RATES] == NULL)
4659 return -EINVAL; 4101 return -EINVAL;
4660 4102
4661 rtnl_lock(); 4103 if (!rdev->ops->set_bitrate_mask)
4662 4104 return -EOPNOTSUPP;
4663 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
4664 if (err)
4665 goto unlock_rtnl;
4666
4667 if (!rdev->ops->set_bitrate_mask) {
4668 err = -EOPNOTSUPP;
4669 goto unlock;
4670 }
4671 4105
4672 memset(&mask, 0, sizeof(mask)); 4106 memset(&mask, 0, sizeof(mask));
4673 /* Default to all rates enabled */ 4107 /* Default to all rates enabled */
@@ -4684,15 +4118,11 @@ static int nl80211_set_tx_bitrate_mask(struct sk_buff *skb,
4684 nla_for_each_nested(tx_rates, info->attrs[NL80211_ATTR_TX_RATES], rem) 4118 nla_for_each_nested(tx_rates, info->attrs[NL80211_ATTR_TX_RATES], rem)
4685 { 4119 {
4686 enum ieee80211_band band = nla_type(tx_rates); 4120 enum ieee80211_band band = nla_type(tx_rates);
4687 if (band < 0 || band >= IEEE80211_NUM_BANDS) { 4121 if (band < 0 || band >= IEEE80211_NUM_BANDS)
4688 err = -EINVAL; 4122 return -EINVAL;
4689 goto unlock;
4690 }
4691 sband = rdev->wiphy.bands[band]; 4123 sband = rdev->wiphy.bands[band];
4692 if (sband == NULL) { 4124 if (sband == NULL)
4693 err = -EINVAL; 4125 return -EINVAL;
4694 goto unlock;
4695 }
4696 nla_parse(tb, NL80211_TXRATE_MAX, nla_data(tx_rates), 4126 nla_parse(tb, NL80211_TXRATE_MAX, nla_data(tx_rates),
4697 nla_len(tx_rates), nl80211_txattr_policy); 4127 nla_len(tx_rates), nl80211_txattr_policy);
4698 if (tb[NL80211_TXRATE_LEGACY]) { 4128 if (tb[NL80211_TXRATE_LEGACY]) {
@@ -4700,68 +4130,48 @@ static int nl80211_set_tx_bitrate_mask(struct sk_buff *skb,
4700 sband, 4130 sband,
4701 nla_data(tb[NL80211_TXRATE_LEGACY]), 4131 nla_data(tb[NL80211_TXRATE_LEGACY]),
4702 nla_len(tb[NL80211_TXRATE_LEGACY])); 4132 nla_len(tb[NL80211_TXRATE_LEGACY]));
4703 if (mask.control[band].legacy == 0) { 4133 if (mask.control[band].legacy == 0)
4704 err = -EINVAL; 4134 return -EINVAL;
4705 goto unlock;
4706 }
4707 } 4135 }
4708 } 4136 }
4709 4137
4710 err = rdev->ops->set_bitrate_mask(&rdev->wiphy, dev, NULL, &mask); 4138 return rdev->ops->set_bitrate_mask(&rdev->wiphy, dev, NULL, &mask);
4711
4712 unlock:
4713 dev_put(dev);
4714 cfg80211_unlock_rdev(rdev);
4715 unlock_rtnl:
4716 rtnl_unlock();
4717 return err;
4718} 4139}
4719 4140
4720static int nl80211_register_action(struct sk_buff *skb, struct genl_info *info) 4141static int nl80211_register_mgmt(struct sk_buff *skb, struct genl_info *info)
4721{ 4142{
4722 struct cfg80211_registered_device *rdev; 4143 struct cfg80211_registered_device *rdev = info->user_ptr[0];
4723 struct net_device *dev; 4144 struct net_device *dev = info->user_ptr[1];
4724 int err; 4145 u16 frame_type = IEEE80211_FTYPE_MGMT | IEEE80211_STYPE_ACTION;
4725 4146
4726 if (!info->attrs[NL80211_ATTR_FRAME_MATCH]) 4147 if (!info->attrs[NL80211_ATTR_FRAME_MATCH])
4727 return -EINVAL; 4148 return -EINVAL;
4728 4149
4729 if (nla_len(info->attrs[NL80211_ATTR_FRAME_MATCH]) < 1) 4150 if (info->attrs[NL80211_ATTR_FRAME_TYPE])
4730 return -EINVAL; 4151 frame_type = nla_get_u16(info->attrs[NL80211_ATTR_FRAME_TYPE]);
4731
4732 rtnl_lock();
4733
4734 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
4735 if (err)
4736 goto unlock_rtnl;
4737 4152
4738 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_STATION && 4153 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_STATION &&
4739 dev->ieee80211_ptr->iftype != NL80211_IFTYPE_ADHOC) { 4154 dev->ieee80211_ptr->iftype != NL80211_IFTYPE_ADHOC &&
4740 err = -EOPNOTSUPP; 4155 dev->ieee80211_ptr->iftype != NL80211_IFTYPE_P2P_CLIENT &&
4741 goto out; 4156 dev->ieee80211_ptr->iftype != NL80211_IFTYPE_AP &&
4742 } 4157 dev->ieee80211_ptr->iftype != NL80211_IFTYPE_AP_VLAN &&
4158 dev->ieee80211_ptr->iftype != NL80211_IFTYPE_P2P_GO)
4159 return -EOPNOTSUPP;
4743 4160
4744 /* not much point in registering if we can't reply */ 4161 /* not much point in registering if we can't reply */
4745 if (!rdev->ops->action) { 4162 if (!rdev->ops->mgmt_tx)
4746 err = -EOPNOTSUPP; 4163 return -EOPNOTSUPP;
4747 goto out;
4748 }
4749 4164
4750 err = cfg80211_mlme_register_action(dev->ieee80211_ptr, info->snd_pid, 4165 return cfg80211_mlme_register_mgmt(dev->ieee80211_ptr, info->snd_pid,
4166 frame_type,
4751 nla_data(info->attrs[NL80211_ATTR_FRAME_MATCH]), 4167 nla_data(info->attrs[NL80211_ATTR_FRAME_MATCH]),
4752 nla_len(info->attrs[NL80211_ATTR_FRAME_MATCH])); 4168 nla_len(info->attrs[NL80211_ATTR_FRAME_MATCH]));
4753 out:
4754 cfg80211_unlock_rdev(rdev);
4755 dev_put(dev);
4756 unlock_rtnl:
4757 rtnl_unlock();
4758 return err;
4759} 4169}
4760 4170
4761static int nl80211_action(struct sk_buff *skb, struct genl_info *info) 4171static int nl80211_tx_mgmt(struct sk_buff *skb, struct genl_info *info)
4762{ 4172{
4763 struct cfg80211_registered_device *rdev; 4173 struct cfg80211_registered_device *rdev = info->user_ptr[0];
4764 struct net_device *dev; 4174 struct net_device *dev = info->user_ptr[1];
4765 struct ieee80211_channel *chan; 4175 struct ieee80211_channel *chan;
4766 enum nl80211_channel_type channel_type = NL80211_CHAN_NO_HT; 4176 enum nl80211_channel_type channel_type = NL80211_CHAN_NO_HT;
4767 bool channel_type_valid = false; 4177 bool channel_type_valid = false;
@@ -4775,27 +4185,16 @@ static int nl80211_action(struct sk_buff *skb, struct genl_info *info)
4775 !info->attrs[NL80211_ATTR_WIPHY_FREQ]) 4185 !info->attrs[NL80211_ATTR_WIPHY_FREQ])
4776 return -EINVAL; 4186 return -EINVAL;
4777 4187
4778 rtnl_lock(); 4188 if (!rdev->ops->mgmt_tx)
4779 4189 return -EOPNOTSUPP;
4780 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
4781 if (err)
4782 goto unlock_rtnl;
4783
4784 if (!rdev->ops->action) {
4785 err = -EOPNOTSUPP;
4786 goto out;
4787 }
4788 4190
4789 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_STATION && 4191 if (dev->ieee80211_ptr->iftype != NL80211_IFTYPE_STATION &&
4790 dev->ieee80211_ptr->iftype != NL80211_IFTYPE_ADHOC) { 4192 dev->ieee80211_ptr->iftype != NL80211_IFTYPE_ADHOC &&
4791 err = -EOPNOTSUPP; 4193 dev->ieee80211_ptr->iftype != NL80211_IFTYPE_P2P_CLIENT &&
4792 goto out; 4194 dev->ieee80211_ptr->iftype != NL80211_IFTYPE_AP &&
4793 } 4195 dev->ieee80211_ptr->iftype != NL80211_IFTYPE_AP_VLAN &&
4794 4196 dev->ieee80211_ptr->iftype != NL80211_IFTYPE_P2P_GO)
4795 if (!netif_running(dev)) { 4197 return -EOPNOTSUPP;
4796 err = -ENETDOWN;
4797 goto out;
4798 }
4799 4198
4800 if (info->attrs[NL80211_ATTR_WIPHY_CHANNEL_TYPE]) { 4199 if (info->attrs[NL80211_ATTR_WIPHY_CHANNEL_TYPE]) {
4801 channel_type = nla_get_u32( 4200 channel_type = nla_get_u32(
@@ -4803,147 +4202,104 @@ static int nl80211_action(struct sk_buff *skb, struct genl_info *info)
4803 if (channel_type != NL80211_CHAN_NO_HT && 4202 if (channel_type != NL80211_CHAN_NO_HT &&
4804 channel_type != NL80211_CHAN_HT20 && 4203 channel_type != NL80211_CHAN_HT20 &&
4805 channel_type != NL80211_CHAN_HT40PLUS && 4204 channel_type != NL80211_CHAN_HT40PLUS &&
4806 channel_type != NL80211_CHAN_HT40MINUS) { 4205 channel_type != NL80211_CHAN_HT40MINUS)
4807 err = -EINVAL; 4206 return -EINVAL;
4808 goto out;
4809 }
4810 channel_type_valid = true; 4207 channel_type_valid = true;
4811 } 4208 }
4812 4209
4813 freq = nla_get_u32(info->attrs[NL80211_ATTR_WIPHY_FREQ]); 4210 freq = nla_get_u32(info->attrs[NL80211_ATTR_WIPHY_FREQ]);
4814 chan = rdev_freq_to_chan(rdev, freq, channel_type); 4211 chan = rdev_freq_to_chan(rdev, freq, channel_type);
4815 if (chan == NULL) { 4212 if (chan == NULL)
4816 err = -EINVAL; 4213 return -EINVAL;
4817 goto out;
4818 }
4819 4214
4820 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL); 4215 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
4821 if (!msg) { 4216 if (!msg)
4822 err = -ENOMEM; 4217 return -ENOMEM;
4823 goto out;
4824 }
4825 4218
4826 hdr = nl80211hdr_put(msg, info->snd_pid, info->snd_seq, 0, 4219 hdr = nl80211hdr_put(msg, info->snd_pid, info->snd_seq, 0,
4827 NL80211_CMD_ACTION); 4220 NL80211_CMD_FRAME);
4828 4221
4829 if (IS_ERR(hdr)) { 4222 if (IS_ERR(hdr)) {
4830 err = PTR_ERR(hdr); 4223 err = PTR_ERR(hdr);
4831 goto free_msg; 4224 goto free_msg;
4832 } 4225 }
4833 err = cfg80211_mlme_action(rdev, dev, chan, channel_type, 4226 err = cfg80211_mlme_mgmt_tx(rdev, dev, chan, channel_type,
4834 channel_type_valid, 4227 channel_type_valid,
4835 nla_data(info->attrs[NL80211_ATTR_FRAME]), 4228 nla_data(info->attrs[NL80211_ATTR_FRAME]),
4836 nla_len(info->attrs[NL80211_ATTR_FRAME]), 4229 nla_len(info->attrs[NL80211_ATTR_FRAME]),
4837 &cookie); 4230 &cookie);
4838 if (err) 4231 if (err)
4839 goto free_msg; 4232 goto free_msg;
4840 4233
4841 NLA_PUT_U64(msg, NL80211_ATTR_COOKIE, cookie); 4234 NLA_PUT_U64(msg, NL80211_ATTR_COOKIE, cookie);
4842 4235
4843 genlmsg_end(msg, hdr); 4236 genlmsg_end(msg, hdr);
4844 err = genlmsg_reply(msg, info); 4237 return genlmsg_reply(msg, info);
4845 goto out;
4846 4238
4847 nla_put_failure: 4239 nla_put_failure:
4848 err = -ENOBUFS; 4240 err = -ENOBUFS;
4849 free_msg: 4241 free_msg:
4850 nlmsg_free(msg); 4242 nlmsg_free(msg);
4851 out:
4852 cfg80211_unlock_rdev(rdev);
4853 dev_put(dev);
4854unlock_rtnl:
4855 rtnl_unlock();
4856 return err; 4243 return err;
4857} 4244}
4858 4245
4859static int nl80211_set_power_save(struct sk_buff *skb, struct genl_info *info) 4246static int nl80211_set_power_save(struct sk_buff *skb, struct genl_info *info)
4860{ 4247{
4861 struct cfg80211_registered_device *rdev; 4248 struct cfg80211_registered_device *rdev = info->user_ptr[0];
4862 struct wireless_dev *wdev; 4249 struct wireless_dev *wdev;
4863 struct net_device *dev; 4250 struct net_device *dev = info->user_ptr[1];
4864 u8 ps_state; 4251 u8 ps_state;
4865 bool state; 4252 bool state;
4866 int err; 4253 int err;
4867 4254
4868 if (!info->attrs[NL80211_ATTR_PS_STATE]) { 4255 if (!info->attrs[NL80211_ATTR_PS_STATE])
4869 err = -EINVAL; 4256 return -EINVAL;
4870 goto out;
4871 }
4872 4257
4873 ps_state = nla_get_u32(info->attrs[NL80211_ATTR_PS_STATE]); 4258 ps_state = nla_get_u32(info->attrs[NL80211_ATTR_PS_STATE]);
4874 4259
4875 if (ps_state != NL80211_PS_DISABLED && ps_state != NL80211_PS_ENABLED) { 4260 if (ps_state != NL80211_PS_DISABLED && ps_state != NL80211_PS_ENABLED)
4876 err = -EINVAL; 4261 return -EINVAL;
4877 goto out;
4878 }
4879
4880 rtnl_lock();
4881
4882 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
4883 if (err)
4884 goto unlock_rdev;
4885 4262
4886 wdev = dev->ieee80211_ptr; 4263 wdev = dev->ieee80211_ptr;
4887 4264
4888 if (!rdev->ops->set_power_mgmt) { 4265 if (!rdev->ops->set_power_mgmt)
4889 err = -EOPNOTSUPP; 4266 return -EOPNOTSUPP;
4890 goto unlock_rdev;
4891 }
4892 4267
4893 state = (ps_state == NL80211_PS_ENABLED) ? true : false; 4268 state = (ps_state == NL80211_PS_ENABLED) ? true : false;
4894 4269
4895 if (state == wdev->ps) 4270 if (state == wdev->ps)
4896 goto unlock_rdev; 4271 return 0;
4897
4898 wdev->ps = state;
4899
4900 if (rdev->ops->set_power_mgmt(wdev->wiphy, dev, wdev->ps,
4901 wdev->ps_timeout))
4902 /* assume this means it's off */
4903 wdev->ps = false;
4904
4905unlock_rdev:
4906 cfg80211_unlock_rdev(rdev);
4907 dev_put(dev);
4908 rtnl_unlock();
4909 4272
4910out: 4273 err = rdev->ops->set_power_mgmt(wdev->wiphy, dev, state,
4274 wdev->ps_timeout);
4275 if (!err)
4276 wdev->ps = state;
4911 return err; 4277 return err;
4912} 4278}
4913 4279
4914static int nl80211_get_power_save(struct sk_buff *skb, struct genl_info *info) 4280static int nl80211_get_power_save(struct sk_buff *skb, struct genl_info *info)
4915{ 4281{
4916 struct cfg80211_registered_device *rdev; 4282 struct cfg80211_registered_device *rdev = info->user_ptr[0];
4917 enum nl80211_ps_state ps_state; 4283 enum nl80211_ps_state ps_state;
4918 struct wireless_dev *wdev; 4284 struct wireless_dev *wdev;
4919 struct net_device *dev; 4285 struct net_device *dev = info->user_ptr[1];
4920 struct sk_buff *msg; 4286 struct sk_buff *msg;
4921 void *hdr; 4287 void *hdr;
4922 int err; 4288 int err;
4923 4289
4924 rtnl_lock();
4925
4926 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
4927 if (err)
4928 goto unlock_rtnl;
4929
4930 wdev = dev->ieee80211_ptr; 4290 wdev = dev->ieee80211_ptr;
4931 4291
4932 if (!rdev->ops->set_power_mgmt) { 4292 if (!rdev->ops->set_power_mgmt)
4933 err = -EOPNOTSUPP; 4293 return -EOPNOTSUPP;
4934 goto out;
4935 }
4936 4294
4937 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL); 4295 msg = nlmsg_new(NLMSG_DEFAULT_SIZE, GFP_KERNEL);
4938 if (!msg) { 4296 if (!msg)
4939 err = -ENOMEM; 4297 return -ENOMEM;
4940 goto out;
4941 }
4942 4298
4943 hdr = nl80211hdr_put(msg, info->snd_pid, info->snd_seq, 0, 4299 hdr = nl80211hdr_put(msg, info->snd_pid, info->snd_seq, 0,
4944 NL80211_CMD_GET_POWER_SAVE); 4300 NL80211_CMD_GET_POWER_SAVE);
4945 if (!hdr) { 4301 if (!hdr) {
4946 err = -ENOMEM; 4302 err = -ENOBUFS;
4947 goto free_msg; 4303 goto free_msg;
4948 } 4304 }
4949 4305
@@ -4955,22 +4311,12 @@ static int nl80211_get_power_save(struct sk_buff *skb, struct genl_info *info)
4955 NLA_PUT_U32(msg, NL80211_ATTR_PS_STATE, ps_state); 4311 NLA_PUT_U32(msg, NL80211_ATTR_PS_STATE, ps_state);
4956 4312
4957 genlmsg_end(msg, hdr); 4313 genlmsg_end(msg, hdr);
4958 err = genlmsg_reply(msg, info); 4314 return genlmsg_reply(msg, info);
4959 goto out;
4960 4315
4961nla_put_failure: 4316 nla_put_failure:
4962 err = -ENOBUFS; 4317 err = -ENOBUFS;
4963 4318 free_msg:
4964free_msg:
4965 nlmsg_free(msg); 4319 nlmsg_free(msg);
4966
4967out:
4968 cfg80211_unlock_rdev(rdev);
4969 dev_put(dev);
4970
4971unlock_rtnl:
4972 rtnl_unlock();
4973
4974 return err; 4320 return err;
4975} 4321}
4976 4322
@@ -4984,41 +4330,24 @@ nl80211_attr_cqm_policy[NL80211_ATTR_CQM_MAX + 1] __read_mostly = {
4984static int nl80211_set_cqm_rssi(struct genl_info *info, 4330static int nl80211_set_cqm_rssi(struct genl_info *info,
4985 s32 threshold, u32 hysteresis) 4331 s32 threshold, u32 hysteresis)
4986{ 4332{
4987 struct cfg80211_registered_device *rdev; 4333 struct cfg80211_registered_device *rdev = info->user_ptr[0];
4988 struct wireless_dev *wdev; 4334 struct wireless_dev *wdev;
4989 struct net_device *dev; 4335 struct net_device *dev = info->user_ptr[1];
4990 int err;
4991 4336
4992 if (threshold > 0) 4337 if (threshold > 0)
4993 return -EINVAL; 4338 return -EINVAL;
4994 4339
4995 rtnl_lock();
4996
4997 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
4998 if (err)
4999 goto unlock_rdev;
5000
5001 wdev = dev->ieee80211_ptr; 4340 wdev = dev->ieee80211_ptr;
5002 4341
5003 if (!rdev->ops->set_cqm_rssi_config) { 4342 if (!rdev->ops->set_cqm_rssi_config)
5004 err = -EOPNOTSUPP; 4343 return -EOPNOTSUPP;
5005 goto unlock_rdev;
5006 }
5007
5008 if (wdev->iftype != NL80211_IFTYPE_STATION) {
5009 err = -EOPNOTSUPP;
5010 goto unlock_rdev;
5011 }
5012
5013 err = rdev->ops->set_cqm_rssi_config(wdev->wiphy, dev,
5014 threshold, hysteresis);
5015 4344
5016unlock_rdev: 4345 if (wdev->iftype != NL80211_IFTYPE_STATION &&
5017 cfg80211_unlock_rdev(rdev); 4346 wdev->iftype != NL80211_IFTYPE_P2P_CLIENT)
5018 dev_put(dev); 4347 return -EOPNOTSUPP;
5019 rtnl_unlock();
5020 4348
5021 return err; 4349 return rdev->ops->set_cqm_rssi_config(wdev->wiphy, dev,
4350 threshold, hysteresis);
5022} 4351}
5023 4352
5024static int nl80211_set_cqm(struct sk_buff *skb, struct genl_info *info) 4353static int nl80211_set_cqm(struct sk_buff *skb, struct genl_info *info)
@@ -5052,6 +4381,65 @@ out:
5052 return err; 4381 return err;
5053} 4382}
5054 4383
4384#define NL80211_FLAG_NEED_WIPHY 0x01
4385#define NL80211_FLAG_NEED_NETDEV 0x02
4386#define NL80211_FLAG_NEED_RTNL 0x04
4387#define NL80211_FLAG_CHECK_NETDEV_UP 0x08
4388#define NL80211_FLAG_NEED_NETDEV_UP (NL80211_FLAG_NEED_NETDEV |\
4389 NL80211_FLAG_CHECK_NETDEV_UP)
4390
4391static int nl80211_pre_doit(struct genl_ops *ops, struct sk_buff *skb,
4392 struct genl_info *info)
4393{
4394 struct cfg80211_registered_device *rdev;
4395 struct net_device *dev;
4396 int err;
4397 bool rtnl = ops->internal_flags & NL80211_FLAG_NEED_RTNL;
4398
4399 if (rtnl)
4400 rtnl_lock();
4401
4402 if (ops->internal_flags & NL80211_FLAG_NEED_WIPHY) {
4403 rdev = cfg80211_get_dev_from_info(info);
4404 if (IS_ERR(rdev)) {
4405 if (rtnl)
4406 rtnl_unlock();
4407 return PTR_ERR(rdev);
4408 }
4409 info->user_ptr[0] = rdev;
4410 } else if (ops->internal_flags & NL80211_FLAG_NEED_NETDEV) {
4411 err = get_rdev_dev_by_info_ifindex(info, &rdev, &dev);
4412 if (err) {
4413 if (rtnl)
4414 rtnl_unlock();
4415 return err;
4416 }
4417 if (ops->internal_flags & NL80211_FLAG_CHECK_NETDEV_UP &&
4418 !netif_running(dev)) {
4419 cfg80211_unlock_rdev(rdev);
4420 dev_put(dev);
4421 if (rtnl)
4422 rtnl_unlock();
4423 return -ENETDOWN;
4424 }
4425 info->user_ptr[0] = rdev;
4426 info->user_ptr[1] = dev;
4427 }
4428
4429 return 0;
4430}
4431
4432static void nl80211_post_doit(struct genl_ops *ops, struct sk_buff *skb,
4433 struct genl_info *info)
4434{
4435 if (info->user_ptr[0])
4436 cfg80211_unlock_rdev(info->user_ptr[0]);
4437 if (info->user_ptr[1])
4438 dev_put(info->user_ptr[1]);
4439 if (ops->internal_flags & NL80211_FLAG_NEED_RTNL)
4440 rtnl_unlock();
4441}
4442
5055static struct genl_ops nl80211_ops[] = { 4443static struct genl_ops nl80211_ops[] = {
5056 { 4444 {
5057 .cmd = NL80211_CMD_GET_WIPHY, 4445 .cmd = NL80211_CMD_GET_WIPHY,
@@ -5059,12 +4447,14 @@ static struct genl_ops nl80211_ops[] = {
5059 .dumpit = nl80211_dump_wiphy, 4447 .dumpit = nl80211_dump_wiphy,
5060 .policy = nl80211_policy, 4448 .policy = nl80211_policy,
5061 /* can be retrieved by unprivileged users */ 4449 /* can be retrieved by unprivileged users */
4450 .internal_flags = NL80211_FLAG_NEED_WIPHY,
5062 }, 4451 },
5063 { 4452 {
5064 .cmd = NL80211_CMD_SET_WIPHY, 4453 .cmd = NL80211_CMD_SET_WIPHY,
5065 .doit = nl80211_set_wiphy, 4454 .doit = nl80211_set_wiphy,
5066 .policy = nl80211_policy, 4455 .policy = nl80211_policy,
5067 .flags = GENL_ADMIN_PERM, 4456 .flags = GENL_ADMIN_PERM,
4457 .internal_flags = NL80211_FLAG_NEED_RTNL,
5068 }, 4458 },
5069 { 4459 {
5070 .cmd = NL80211_CMD_GET_INTERFACE, 4460 .cmd = NL80211_CMD_GET_INTERFACE,
@@ -5072,90 +4462,119 @@ static struct genl_ops nl80211_ops[] = {
5072 .dumpit = nl80211_dump_interface, 4462 .dumpit = nl80211_dump_interface,
5073 .policy = nl80211_policy, 4463 .policy = nl80211_policy,
5074 /* can be retrieved by unprivileged users */ 4464 /* can be retrieved by unprivileged users */
4465 .internal_flags = NL80211_FLAG_NEED_NETDEV,
5075 }, 4466 },
5076 { 4467 {
5077 .cmd = NL80211_CMD_SET_INTERFACE, 4468 .cmd = NL80211_CMD_SET_INTERFACE,
5078 .doit = nl80211_set_interface, 4469 .doit = nl80211_set_interface,
5079 .policy = nl80211_policy, 4470 .policy = nl80211_policy,
5080 .flags = GENL_ADMIN_PERM, 4471 .flags = GENL_ADMIN_PERM,
4472 .internal_flags = NL80211_FLAG_NEED_NETDEV |
4473 NL80211_FLAG_NEED_RTNL,
5081 }, 4474 },
5082 { 4475 {
5083 .cmd = NL80211_CMD_NEW_INTERFACE, 4476 .cmd = NL80211_CMD_NEW_INTERFACE,
5084 .doit = nl80211_new_interface, 4477 .doit = nl80211_new_interface,
5085 .policy = nl80211_policy, 4478 .policy = nl80211_policy,
5086 .flags = GENL_ADMIN_PERM, 4479 .flags = GENL_ADMIN_PERM,
4480 .internal_flags = NL80211_FLAG_NEED_WIPHY |
4481 NL80211_FLAG_NEED_RTNL,
5087 }, 4482 },
5088 { 4483 {
5089 .cmd = NL80211_CMD_DEL_INTERFACE, 4484 .cmd = NL80211_CMD_DEL_INTERFACE,
5090 .doit = nl80211_del_interface, 4485 .doit = nl80211_del_interface,
5091 .policy = nl80211_policy, 4486 .policy = nl80211_policy,
5092 .flags = GENL_ADMIN_PERM, 4487 .flags = GENL_ADMIN_PERM,
4488 .internal_flags = NL80211_FLAG_NEED_NETDEV |
4489 NL80211_FLAG_NEED_RTNL,
5093 }, 4490 },
5094 { 4491 {
5095 .cmd = NL80211_CMD_GET_KEY, 4492 .cmd = NL80211_CMD_GET_KEY,
5096 .doit = nl80211_get_key, 4493 .doit = nl80211_get_key,
5097 .policy = nl80211_policy, 4494 .policy = nl80211_policy,
5098 .flags = GENL_ADMIN_PERM, 4495 .flags = GENL_ADMIN_PERM,
4496 .internal_flags = NL80211_FLAG_NEED_NETDEV |
4497 NL80211_FLAG_NEED_RTNL,
5099 }, 4498 },
5100 { 4499 {
5101 .cmd = NL80211_CMD_SET_KEY, 4500 .cmd = NL80211_CMD_SET_KEY,
5102 .doit = nl80211_set_key, 4501 .doit = nl80211_set_key,
5103 .policy = nl80211_policy, 4502 .policy = nl80211_policy,
5104 .flags = GENL_ADMIN_PERM, 4503 .flags = GENL_ADMIN_PERM,
4504 .internal_flags = NL80211_FLAG_NEED_NETDEV_UP |
4505 NL80211_FLAG_NEED_RTNL,
5105 }, 4506 },
5106 { 4507 {
5107 .cmd = NL80211_CMD_NEW_KEY, 4508 .cmd = NL80211_CMD_NEW_KEY,
5108 .doit = nl80211_new_key, 4509 .doit = nl80211_new_key,
5109 .policy = nl80211_policy, 4510 .policy = nl80211_policy,
5110 .flags = GENL_ADMIN_PERM, 4511 .flags = GENL_ADMIN_PERM,
4512 .internal_flags = NL80211_FLAG_NEED_NETDEV_UP |
4513 NL80211_FLAG_NEED_RTNL,
5111 }, 4514 },
5112 { 4515 {
5113 .cmd = NL80211_CMD_DEL_KEY, 4516 .cmd = NL80211_CMD_DEL_KEY,
5114 .doit = nl80211_del_key, 4517 .doit = nl80211_del_key,
5115 .policy = nl80211_policy, 4518 .policy = nl80211_policy,
5116 .flags = GENL_ADMIN_PERM, 4519 .flags = GENL_ADMIN_PERM,
4520 .internal_flags = NL80211_FLAG_NEED_NETDEV_UP |
4521 NL80211_FLAG_NEED_RTNL,
5117 }, 4522 },
5118 { 4523 {
5119 .cmd = NL80211_CMD_SET_BEACON, 4524 .cmd = NL80211_CMD_SET_BEACON,
5120 .policy = nl80211_policy, 4525 .policy = nl80211_policy,
5121 .flags = GENL_ADMIN_PERM, 4526 .flags = GENL_ADMIN_PERM,
5122 .doit = nl80211_addset_beacon, 4527 .doit = nl80211_addset_beacon,
4528 .internal_flags = NL80211_FLAG_NEED_NETDEV |
4529 NL80211_FLAG_NEED_RTNL,
5123 }, 4530 },
5124 { 4531 {
5125 .cmd = NL80211_CMD_NEW_BEACON, 4532 .cmd = NL80211_CMD_NEW_BEACON,
5126 .policy = nl80211_policy, 4533 .policy = nl80211_policy,
5127 .flags = GENL_ADMIN_PERM, 4534 .flags = GENL_ADMIN_PERM,
5128 .doit = nl80211_addset_beacon, 4535 .doit = nl80211_addset_beacon,
4536 .internal_flags = NL80211_FLAG_NEED_NETDEV |
4537 NL80211_FLAG_NEED_RTNL,
5129 }, 4538 },
5130 { 4539 {
5131 .cmd = NL80211_CMD_DEL_BEACON, 4540 .cmd = NL80211_CMD_DEL_BEACON,
5132 .policy = nl80211_policy, 4541 .policy = nl80211_policy,
5133 .flags = GENL_ADMIN_PERM, 4542 .flags = GENL_ADMIN_PERM,
5134 .doit = nl80211_del_beacon, 4543 .doit = nl80211_del_beacon,
4544 .internal_flags = NL80211_FLAG_NEED_NETDEV |
4545 NL80211_FLAG_NEED_RTNL,
5135 }, 4546 },
5136 { 4547 {
5137 .cmd = NL80211_CMD_GET_STATION, 4548 .cmd = NL80211_CMD_GET_STATION,
5138 .doit = nl80211_get_station, 4549 .doit = nl80211_get_station,
5139 .dumpit = nl80211_dump_station, 4550 .dumpit = nl80211_dump_station,
5140 .policy = nl80211_policy, 4551 .policy = nl80211_policy,
4552 .internal_flags = NL80211_FLAG_NEED_NETDEV |
4553 NL80211_FLAG_NEED_RTNL,
5141 }, 4554 },
5142 { 4555 {
5143 .cmd = NL80211_CMD_SET_STATION, 4556 .cmd = NL80211_CMD_SET_STATION,
5144 .doit = nl80211_set_station, 4557 .doit = nl80211_set_station,
5145 .policy = nl80211_policy, 4558 .policy = nl80211_policy,
5146 .flags = GENL_ADMIN_PERM, 4559 .flags = GENL_ADMIN_PERM,
4560 .internal_flags = NL80211_FLAG_NEED_NETDEV |
4561 NL80211_FLAG_NEED_RTNL,
5147 }, 4562 },
5148 { 4563 {
5149 .cmd = NL80211_CMD_NEW_STATION, 4564 .cmd = NL80211_CMD_NEW_STATION,
5150 .doit = nl80211_new_station, 4565 .doit = nl80211_new_station,
5151 .policy = nl80211_policy, 4566 .policy = nl80211_policy,
5152 .flags = GENL_ADMIN_PERM, 4567 .flags = GENL_ADMIN_PERM,
4568 .internal_flags = NL80211_FLAG_NEED_NETDEV_UP |
4569 NL80211_FLAG_NEED_RTNL,
5153 }, 4570 },
5154 { 4571 {
5155 .cmd = NL80211_CMD_DEL_STATION, 4572 .cmd = NL80211_CMD_DEL_STATION,
5156 .doit = nl80211_del_station, 4573 .doit = nl80211_del_station,
5157 .policy = nl80211_policy, 4574 .policy = nl80211_policy,
5158 .flags = GENL_ADMIN_PERM, 4575 .flags = GENL_ADMIN_PERM,
4576 .internal_flags = NL80211_FLAG_NEED_NETDEV |
4577 NL80211_FLAG_NEED_RTNL,
5159 }, 4578 },
5160 { 4579 {
5161 .cmd = NL80211_CMD_GET_MPATH, 4580 .cmd = NL80211_CMD_GET_MPATH,
@@ -5163,30 +4582,40 @@ static struct genl_ops nl80211_ops[] = {
5163 .dumpit = nl80211_dump_mpath, 4582 .dumpit = nl80211_dump_mpath,
5164 .policy = nl80211_policy, 4583 .policy = nl80211_policy,
5165 .flags = GENL_ADMIN_PERM, 4584 .flags = GENL_ADMIN_PERM,
4585 .internal_flags = NL80211_FLAG_NEED_NETDEV_UP |
4586 NL80211_FLAG_NEED_RTNL,
5166 }, 4587 },
5167 { 4588 {
5168 .cmd = NL80211_CMD_SET_MPATH, 4589 .cmd = NL80211_CMD_SET_MPATH,
5169 .doit = nl80211_set_mpath, 4590 .doit = nl80211_set_mpath,
5170 .policy = nl80211_policy, 4591 .policy = nl80211_policy,
5171 .flags = GENL_ADMIN_PERM, 4592 .flags = GENL_ADMIN_PERM,
4593 .internal_flags = NL80211_FLAG_NEED_NETDEV_UP |
4594 NL80211_FLAG_NEED_RTNL,
5172 }, 4595 },
5173 { 4596 {
5174 .cmd = NL80211_CMD_NEW_MPATH, 4597 .cmd = NL80211_CMD_NEW_MPATH,
5175 .doit = nl80211_new_mpath, 4598 .doit = nl80211_new_mpath,
5176 .policy = nl80211_policy, 4599 .policy = nl80211_policy,
5177 .flags = GENL_ADMIN_PERM, 4600 .flags = GENL_ADMIN_PERM,
4601 .internal_flags = NL80211_FLAG_NEED_NETDEV_UP |
4602 NL80211_FLAG_NEED_RTNL,
5178 }, 4603 },
5179 { 4604 {
5180 .cmd = NL80211_CMD_DEL_MPATH, 4605 .cmd = NL80211_CMD_DEL_MPATH,
5181 .doit = nl80211_del_mpath, 4606 .doit = nl80211_del_mpath,
5182 .policy = nl80211_policy, 4607 .policy = nl80211_policy,
5183 .flags = GENL_ADMIN_PERM, 4608 .flags = GENL_ADMIN_PERM,
4609 .internal_flags = NL80211_FLAG_NEED_NETDEV |
4610 NL80211_FLAG_NEED_RTNL,
5184 }, 4611 },
5185 { 4612 {
5186 .cmd = NL80211_CMD_SET_BSS, 4613 .cmd = NL80211_CMD_SET_BSS,
5187 .doit = nl80211_set_bss, 4614 .doit = nl80211_set_bss,
5188 .policy = nl80211_policy, 4615 .policy = nl80211_policy,
5189 .flags = GENL_ADMIN_PERM, 4616 .flags = GENL_ADMIN_PERM,
4617 .internal_flags = NL80211_FLAG_NEED_NETDEV |
4618 NL80211_FLAG_NEED_RTNL,
5190 }, 4619 },
5191 { 4620 {
5192 .cmd = NL80211_CMD_GET_REG, 4621 .cmd = NL80211_CMD_GET_REG,
@@ -5211,18 +4640,24 @@ static struct genl_ops nl80211_ops[] = {
5211 .doit = nl80211_get_mesh_params, 4640 .doit = nl80211_get_mesh_params,
5212 .policy = nl80211_policy, 4641 .policy = nl80211_policy,
5213 /* can be retrieved by unprivileged users */ 4642 /* can be retrieved by unprivileged users */
4643 .internal_flags = NL80211_FLAG_NEED_NETDEV |
4644 NL80211_FLAG_NEED_RTNL,
5214 }, 4645 },
5215 { 4646 {
5216 .cmd = NL80211_CMD_SET_MESH_PARAMS, 4647 .cmd = NL80211_CMD_SET_MESH_PARAMS,
5217 .doit = nl80211_set_mesh_params, 4648 .doit = nl80211_set_mesh_params,
5218 .policy = nl80211_policy, 4649 .policy = nl80211_policy,
5219 .flags = GENL_ADMIN_PERM, 4650 .flags = GENL_ADMIN_PERM,
4651 .internal_flags = NL80211_FLAG_NEED_NETDEV |
4652 NL80211_FLAG_NEED_RTNL,
5220 }, 4653 },
5221 { 4654 {
5222 .cmd = NL80211_CMD_TRIGGER_SCAN, 4655 .cmd = NL80211_CMD_TRIGGER_SCAN,
5223 .doit = nl80211_trigger_scan, 4656 .doit = nl80211_trigger_scan,
5224 .policy = nl80211_policy, 4657 .policy = nl80211_policy,
5225 .flags = GENL_ADMIN_PERM, 4658 .flags = GENL_ADMIN_PERM,
4659 .internal_flags = NL80211_FLAG_NEED_NETDEV_UP |
4660 NL80211_FLAG_NEED_RTNL,
5226 }, 4661 },
5227 { 4662 {
5228 .cmd = NL80211_CMD_GET_SCAN, 4663 .cmd = NL80211_CMD_GET_SCAN,
@@ -5234,36 +4669,48 @@ static struct genl_ops nl80211_ops[] = {
5234 .doit = nl80211_authenticate, 4669 .doit = nl80211_authenticate,
5235 .policy = nl80211_policy, 4670 .policy = nl80211_policy,
5236 .flags = GENL_ADMIN_PERM, 4671 .flags = GENL_ADMIN_PERM,
4672 .internal_flags = NL80211_FLAG_NEED_NETDEV_UP |
4673 NL80211_FLAG_NEED_RTNL,
5237 }, 4674 },
5238 { 4675 {
5239 .cmd = NL80211_CMD_ASSOCIATE, 4676 .cmd = NL80211_CMD_ASSOCIATE,
5240 .doit = nl80211_associate, 4677 .doit = nl80211_associate,
5241 .policy = nl80211_policy, 4678 .policy = nl80211_policy,
5242 .flags = GENL_ADMIN_PERM, 4679 .flags = GENL_ADMIN_PERM,
4680 .internal_flags = NL80211_FLAG_NEED_NETDEV_UP |
4681 NL80211_FLAG_NEED_RTNL,
5243 }, 4682 },
5244 { 4683 {
5245 .cmd = NL80211_CMD_DEAUTHENTICATE, 4684 .cmd = NL80211_CMD_DEAUTHENTICATE,
5246 .doit = nl80211_deauthenticate, 4685 .doit = nl80211_deauthenticate,
5247 .policy = nl80211_policy, 4686 .policy = nl80211_policy,
5248 .flags = GENL_ADMIN_PERM, 4687 .flags = GENL_ADMIN_PERM,
4688 .internal_flags = NL80211_FLAG_NEED_NETDEV_UP |
4689 NL80211_FLAG_NEED_RTNL,
5249 }, 4690 },
5250 { 4691 {
5251 .cmd = NL80211_CMD_DISASSOCIATE, 4692 .cmd = NL80211_CMD_DISASSOCIATE,
5252 .doit = nl80211_disassociate, 4693 .doit = nl80211_disassociate,
5253 .policy = nl80211_policy, 4694 .policy = nl80211_policy,
5254 .flags = GENL_ADMIN_PERM, 4695 .flags = GENL_ADMIN_PERM,
4696 .internal_flags = NL80211_FLAG_NEED_NETDEV_UP |
4697 NL80211_FLAG_NEED_RTNL,
5255 }, 4698 },
5256 { 4699 {
5257 .cmd = NL80211_CMD_JOIN_IBSS, 4700 .cmd = NL80211_CMD_JOIN_IBSS,
5258 .doit = nl80211_join_ibss, 4701 .doit = nl80211_join_ibss,
5259 .policy = nl80211_policy, 4702 .policy = nl80211_policy,
5260 .flags = GENL_ADMIN_PERM, 4703 .flags = GENL_ADMIN_PERM,
4704 .internal_flags = NL80211_FLAG_NEED_NETDEV_UP |
4705 NL80211_FLAG_NEED_RTNL,
5261 }, 4706 },
5262 { 4707 {
5263 .cmd = NL80211_CMD_LEAVE_IBSS, 4708 .cmd = NL80211_CMD_LEAVE_IBSS,
5264 .doit = nl80211_leave_ibss, 4709 .doit = nl80211_leave_ibss,
5265 .policy = nl80211_policy, 4710 .policy = nl80211_policy,
5266 .flags = GENL_ADMIN_PERM, 4711 .flags = GENL_ADMIN_PERM,
4712 .internal_flags = NL80211_FLAG_NEED_NETDEV_UP |
4713 NL80211_FLAG_NEED_RTNL,
5267 }, 4714 },
5268#ifdef CONFIG_NL80211_TESTMODE 4715#ifdef CONFIG_NL80211_TESTMODE
5269 { 4716 {
@@ -5271,6 +4718,8 @@ static struct genl_ops nl80211_ops[] = {
5271 .doit = nl80211_testmode_do, 4718 .doit = nl80211_testmode_do,
5272 .policy = nl80211_policy, 4719 .policy = nl80211_policy,
5273 .flags = GENL_ADMIN_PERM, 4720 .flags = GENL_ADMIN_PERM,
4721 .internal_flags = NL80211_FLAG_NEED_WIPHY |
4722 NL80211_FLAG_NEED_RTNL,
5274 }, 4723 },
5275#endif 4724#endif
5276 { 4725 {
@@ -5278,18 +4727,24 @@ static struct genl_ops nl80211_ops[] = {
5278 .doit = nl80211_connect, 4727 .doit = nl80211_connect,
5279 .policy = nl80211_policy, 4728 .policy = nl80211_policy,
5280 .flags = GENL_ADMIN_PERM, 4729 .flags = GENL_ADMIN_PERM,
4730 .internal_flags = NL80211_FLAG_NEED_NETDEV_UP |
4731 NL80211_FLAG_NEED_RTNL,
5281 }, 4732 },
5282 { 4733 {
5283 .cmd = NL80211_CMD_DISCONNECT, 4734 .cmd = NL80211_CMD_DISCONNECT,
5284 .doit = nl80211_disconnect, 4735 .doit = nl80211_disconnect,
5285 .policy = nl80211_policy, 4736 .policy = nl80211_policy,
5286 .flags = GENL_ADMIN_PERM, 4737 .flags = GENL_ADMIN_PERM,
4738 .internal_flags = NL80211_FLAG_NEED_NETDEV_UP |
4739 NL80211_FLAG_NEED_RTNL,
5287 }, 4740 },
5288 { 4741 {
5289 .cmd = NL80211_CMD_SET_WIPHY_NETNS, 4742 .cmd = NL80211_CMD_SET_WIPHY_NETNS,
5290 .doit = nl80211_wiphy_netns, 4743 .doit = nl80211_wiphy_netns,
5291 .policy = nl80211_policy, 4744 .policy = nl80211_policy,
5292 .flags = GENL_ADMIN_PERM, 4745 .flags = GENL_ADMIN_PERM,
4746 .internal_flags = NL80211_FLAG_NEED_WIPHY |
4747 NL80211_FLAG_NEED_RTNL,
5293 }, 4748 },
5294 { 4749 {
5295 .cmd = NL80211_CMD_GET_SURVEY, 4750 .cmd = NL80211_CMD_GET_SURVEY,
@@ -5301,72 +4756,104 @@ static struct genl_ops nl80211_ops[] = {
5301 .doit = nl80211_setdel_pmksa, 4756 .doit = nl80211_setdel_pmksa,
5302 .policy = nl80211_policy, 4757 .policy = nl80211_policy,
5303 .flags = GENL_ADMIN_PERM, 4758 .flags = GENL_ADMIN_PERM,
4759 .internal_flags = NL80211_FLAG_NEED_NETDEV |
4760 NL80211_FLAG_NEED_RTNL,
5304 }, 4761 },
5305 { 4762 {
5306 .cmd = NL80211_CMD_DEL_PMKSA, 4763 .cmd = NL80211_CMD_DEL_PMKSA,
5307 .doit = nl80211_setdel_pmksa, 4764 .doit = nl80211_setdel_pmksa,
5308 .policy = nl80211_policy, 4765 .policy = nl80211_policy,
5309 .flags = GENL_ADMIN_PERM, 4766 .flags = GENL_ADMIN_PERM,
4767 .internal_flags = NL80211_FLAG_NEED_NETDEV |
4768 NL80211_FLAG_NEED_RTNL,
5310 }, 4769 },
5311 { 4770 {
5312 .cmd = NL80211_CMD_FLUSH_PMKSA, 4771 .cmd = NL80211_CMD_FLUSH_PMKSA,
5313 .doit = nl80211_flush_pmksa, 4772 .doit = nl80211_flush_pmksa,
5314 .policy = nl80211_policy, 4773 .policy = nl80211_policy,
5315 .flags = GENL_ADMIN_PERM, 4774 .flags = GENL_ADMIN_PERM,
4775 .internal_flags = NL80211_FLAG_NEED_NETDEV |
4776 NL80211_FLAG_NEED_RTNL,
5316 }, 4777 },
5317 { 4778 {
5318 .cmd = NL80211_CMD_REMAIN_ON_CHANNEL, 4779 .cmd = NL80211_CMD_REMAIN_ON_CHANNEL,
5319 .doit = nl80211_remain_on_channel, 4780 .doit = nl80211_remain_on_channel,
5320 .policy = nl80211_policy, 4781 .policy = nl80211_policy,
5321 .flags = GENL_ADMIN_PERM, 4782 .flags = GENL_ADMIN_PERM,
4783 .internal_flags = NL80211_FLAG_NEED_NETDEV_UP |
4784 NL80211_FLAG_NEED_RTNL,
5322 }, 4785 },
5323 { 4786 {
5324 .cmd = NL80211_CMD_CANCEL_REMAIN_ON_CHANNEL, 4787 .cmd = NL80211_CMD_CANCEL_REMAIN_ON_CHANNEL,
5325 .doit = nl80211_cancel_remain_on_channel, 4788 .doit = nl80211_cancel_remain_on_channel,
5326 .policy = nl80211_policy, 4789 .policy = nl80211_policy,
5327 .flags = GENL_ADMIN_PERM, 4790 .flags = GENL_ADMIN_PERM,
4791 .internal_flags = NL80211_FLAG_NEED_NETDEV_UP |
4792 NL80211_FLAG_NEED_RTNL,
5328 }, 4793 },
5329 { 4794 {
5330 .cmd = NL80211_CMD_SET_TX_BITRATE_MASK, 4795 .cmd = NL80211_CMD_SET_TX_BITRATE_MASK,
5331 .doit = nl80211_set_tx_bitrate_mask, 4796 .doit = nl80211_set_tx_bitrate_mask,
5332 .policy = nl80211_policy, 4797 .policy = nl80211_policy,
5333 .flags = GENL_ADMIN_PERM, 4798 .flags = GENL_ADMIN_PERM,
4799 .internal_flags = NL80211_FLAG_NEED_NETDEV |
4800 NL80211_FLAG_NEED_RTNL,
5334 }, 4801 },
5335 { 4802 {
5336 .cmd = NL80211_CMD_REGISTER_ACTION, 4803 .cmd = NL80211_CMD_REGISTER_FRAME,
5337 .doit = nl80211_register_action, 4804 .doit = nl80211_register_mgmt,
5338 .policy = nl80211_policy, 4805 .policy = nl80211_policy,
5339 .flags = GENL_ADMIN_PERM, 4806 .flags = GENL_ADMIN_PERM,
4807 .internal_flags = NL80211_FLAG_NEED_NETDEV |
4808 NL80211_FLAG_NEED_RTNL,
5340 }, 4809 },
5341 { 4810 {
5342 .cmd = NL80211_CMD_ACTION, 4811 .cmd = NL80211_CMD_FRAME,
5343 .doit = nl80211_action, 4812 .doit = nl80211_tx_mgmt,
5344 .policy = nl80211_policy, 4813 .policy = nl80211_policy,
5345 .flags = GENL_ADMIN_PERM, 4814 .flags = GENL_ADMIN_PERM,
4815 .internal_flags = NL80211_FLAG_NEED_NETDEV_UP |
4816 NL80211_FLAG_NEED_RTNL,
5346 }, 4817 },
5347 { 4818 {
5348 .cmd = NL80211_CMD_SET_POWER_SAVE, 4819 .cmd = NL80211_CMD_SET_POWER_SAVE,
5349 .doit = nl80211_set_power_save, 4820 .doit = nl80211_set_power_save,
5350 .policy = nl80211_policy, 4821 .policy = nl80211_policy,
5351 .flags = GENL_ADMIN_PERM, 4822 .flags = GENL_ADMIN_PERM,
4823 .internal_flags = NL80211_FLAG_NEED_NETDEV |
4824 NL80211_FLAG_NEED_RTNL,
5352 }, 4825 },
5353 { 4826 {
5354 .cmd = NL80211_CMD_GET_POWER_SAVE, 4827 .cmd = NL80211_CMD_GET_POWER_SAVE,
5355 .doit = nl80211_get_power_save, 4828 .doit = nl80211_get_power_save,
5356 .policy = nl80211_policy, 4829 .policy = nl80211_policy,
5357 /* can be retrieved by unprivileged users */ 4830 /* can be retrieved by unprivileged users */
4831 .internal_flags = NL80211_FLAG_NEED_NETDEV |
4832 NL80211_FLAG_NEED_RTNL,
5358 }, 4833 },
5359 { 4834 {
5360 .cmd = NL80211_CMD_SET_CQM, 4835 .cmd = NL80211_CMD_SET_CQM,
5361 .doit = nl80211_set_cqm, 4836 .doit = nl80211_set_cqm,
5362 .policy = nl80211_policy, 4837 .policy = nl80211_policy,
5363 .flags = GENL_ADMIN_PERM, 4838 .flags = GENL_ADMIN_PERM,
4839 .internal_flags = NL80211_FLAG_NEED_NETDEV |
4840 NL80211_FLAG_NEED_RTNL,
5364 }, 4841 },
5365 { 4842 {
5366 .cmd = NL80211_CMD_SET_CHANNEL, 4843 .cmd = NL80211_CMD_SET_CHANNEL,
5367 .doit = nl80211_set_channel, 4844 .doit = nl80211_set_channel,
5368 .policy = nl80211_policy, 4845 .policy = nl80211_policy,
5369 .flags = GENL_ADMIN_PERM, 4846 .flags = GENL_ADMIN_PERM,
4847 .internal_flags = NL80211_FLAG_NEED_NETDEV |
4848 NL80211_FLAG_NEED_RTNL,
4849 },
4850 {
4851 .cmd = NL80211_CMD_SET_WDS_PEER,
4852 .doit = nl80211_set_wds_peer,
4853 .policy = nl80211_policy,
4854 .flags = GENL_ADMIN_PERM,
4855 .internal_flags = NL80211_FLAG_NEED_NETDEV |
4856 NL80211_FLAG_NEED_RTNL,
5370 }, 4857 },
5371}; 4858};
5372 4859
@@ -6040,9 +5527,9 @@ void nl80211_send_sta_event(struct cfg80211_registered_device *rdev,
6040 nl80211_mlme_mcgrp.id, gfp); 5527 nl80211_mlme_mcgrp.id, gfp);
6041} 5528}
6042 5529
6043int nl80211_send_action(struct cfg80211_registered_device *rdev, 5530int nl80211_send_mgmt(struct cfg80211_registered_device *rdev,
6044 struct net_device *netdev, u32 nlpid, 5531 struct net_device *netdev, u32 nlpid,
6045 int freq, const u8 *buf, size_t len, gfp_t gfp) 5532 int freq, const u8 *buf, size_t len, gfp_t gfp)
6046{ 5533{
6047 struct sk_buff *msg; 5534 struct sk_buff *msg;
6048 void *hdr; 5535 void *hdr;
@@ -6052,7 +5539,7 @@ int nl80211_send_action(struct cfg80211_registered_device *rdev,
6052 if (!msg) 5539 if (!msg)
6053 return -ENOMEM; 5540 return -ENOMEM;
6054 5541
6055 hdr = nl80211hdr_put(msg, 0, 0, 0, NL80211_CMD_ACTION); 5542 hdr = nl80211hdr_put(msg, 0, 0, 0, NL80211_CMD_FRAME);
6056 if (!hdr) { 5543 if (!hdr) {
6057 nlmsg_free(msg); 5544 nlmsg_free(msg);
6058 return -ENOMEM; 5545 return -ENOMEM;
@@ -6080,10 +5567,10 @@ int nl80211_send_action(struct cfg80211_registered_device *rdev,
6080 return -ENOBUFS; 5567 return -ENOBUFS;
6081} 5568}
6082 5569
6083void nl80211_send_action_tx_status(struct cfg80211_registered_device *rdev, 5570void nl80211_send_mgmt_tx_status(struct cfg80211_registered_device *rdev,
6084 struct net_device *netdev, u64 cookie, 5571 struct net_device *netdev, u64 cookie,
6085 const u8 *buf, size_t len, bool ack, 5572 const u8 *buf, size_t len, bool ack,
6086 gfp_t gfp) 5573 gfp_t gfp)
6087{ 5574{
6088 struct sk_buff *msg; 5575 struct sk_buff *msg;
6089 void *hdr; 5576 void *hdr;
@@ -6092,7 +5579,7 @@ void nl80211_send_action_tx_status(struct cfg80211_registered_device *rdev,
6092 if (!msg) 5579 if (!msg)
6093 return; 5580 return;
6094 5581
6095 hdr = nl80211hdr_put(msg, 0, 0, 0, NL80211_CMD_ACTION_TX_STATUS); 5582 hdr = nl80211hdr_put(msg, 0, 0, 0, NL80211_CMD_FRAME_TX_STATUS);
6096 if (!hdr) { 5583 if (!hdr) {
6097 nlmsg_free(msg); 5584 nlmsg_free(msg);
6098 return; 5585 return;
@@ -6179,7 +5666,7 @@ static int nl80211_netlink_notify(struct notifier_block * nb,
6179 5666
6180 list_for_each_entry_rcu(rdev, &cfg80211_rdev_list, list) 5667 list_for_each_entry_rcu(rdev, &cfg80211_rdev_list, list)
6181 list_for_each_entry_rcu(wdev, &rdev->netdev_list, list) 5668 list_for_each_entry_rcu(wdev, &rdev->netdev_list, list)
6182 cfg80211_mlme_unregister_actions(wdev, notify->pid); 5669 cfg80211_mlme_unregister_socket(wdev, notify->pid);
6183 5670
6184 rcu_read_unlock(); 5671 rcu_read_unlock();
6185 5672
diff --git a/net/wireless/nl80211.h b/net/wireless/nl80211.h
index 2ad7fbc7d9f1..30d2f939150d 100644
--- a/net/wireless/nl80211.h
+++ b/net/wireless/nl80211.h
@@ -74,13 +74,13 @@ void nl80211_send_sta_event(struct cfg80211_registered_device *rdev,
74 struct net_device *dev, const u8 *mac_addr, 74 struct net_device *dev, const u8 *mac_addr,
75 struct station_info *sinfo, gfp_t gfp); 75 struct station_info *sinfo, gfp_t gfp);
76 76
77int nl80211_send_action(struct cfg80211_registered_device *rdev, 77int nl80211_send_mgmt(struct cfg80211_registered_device *rdev,
78 struct net_device *netdev, u32 nlpid, int freq, 78 struct net_device *netdev, u32 nlpid, int freq,
79 const u8 *buf, size_t len, gfp_t gfp); 79 const u8 *buf, size_t len, gfp_t gfp);
80void nl80211_send_action_tx_status(struct cfg80211_registered_device *rdev, 80void nl80211_send_mgmt_tx_status(struct cfg80211_registered_device *rdev,
81 struct net_device *netdev, u64 cookie, 81 struct net_device *netdev, u64 cookie,
82 const u8 *buf, size_t len, bool ack, 82 const u8 *buf, size_t len, bool ack,
83 gfp_t gfp); 83 gfp_t gfp);
84 84
85void 85void
86nl80211_send_cqm_rssi_notify(struct cfg80211_registered_device *rdev, 86nl80211_send_cqm_rssi_notify(struct cfg80211_registered_device *rdev,
diff --git a/net/wireless/radiotap.c b/net/wireless/radiotap.c
index 1332c445d1c7..dbe35e138e94 100644
--- a/net/wireless/radiotap.c
+++ b/net/wireless/radiotap.c
@@ -14,6 +14,7 @@
14 * See COPYING for more details. 14 * See COPYING for more details.
15 */ 15 */
16 16
17#include <linux/kernel.h>
17#include <net/cfg80211.h> 18#include <net/cfg80211.h>
18#include <net/ieee80211_radiotap.h> 19#include <net/ieee80211_radiotap.h>
19#include <asm/unaligned.h> 20#include <asm/unaligned.h>
@@ -45,7 +46,7 @@ static const struct radiotap_align_size rtap_namespace_sizes[] = {
45}; 46};
46 47
47static const struct ieee80211_radiotap_namespace radiotap_ns = { 48static const struct ieee80211_radiotap_namespace radiotap_ns = {
48 .n_bits = sizeof(rtap_namespace_sizes) / sizeof(rtap_namespace_sizes[0]), 49 .n_bits = ARRAY_SIZE(rtap_namespace_sizes),
49 .align_size = rtap_namespace_sizes, 50 .align_size = rtap_namespace_sizes,
50}; 51};
51 52
@@ -200,7 +201,7 @@ int ieee80211_radiotap_iterator_next(
200{ 201{
201 while (1) { 202 while (1) {
202 int hit = 0; 203 int hit = 0;
203 int pad, align, size, subns, vnslen; 204 int pad, align, size, subns;
204 uint32_t oui; 205 uint32_t oui;
205 206
206 /* if no more EXT bits, that's it */ 207 /* if no more EXT bits, that's it */
@@ -260,6 +261,27 @@ int ieee80211_radiotap_iterator_next(
260 if (pad) 261 if (pad)
261 iterator->_arg += align - pad; 262 iterator->_arg += align - pad;
262 263
264 if (iterator->_arg_index % 32 == IEEE80211_RADIOTAP_VENDOR_NAMESPACE) {
265 int vnslen;
266
267 if ((unsigned long)iterator->_arg + size -
268 (unsigned long)iterator->_rtheader >
269 (unsigned long)iterator->_max_length)
270 return -EINVAL;
271
272 oui = (*iterator->_arg << 16) |
273 (*(iterator->_arg + 1) << 8) |
274 *(iterator->_arg + 2);
275 subns = *(iterator->_arg + 3);
276
277 find_ns(iterator, oui, subns);
278
279 vnslen = get_unaligned_le16(iterator->_arg + 4);
280 iterator->_next_ns_data = iterator->_arg + size + vnslen;
281 if (!iterator->current_namespace)
282 size += vnslen;
283 }
284
263 /* 285 /*
264 * this is what we will return to user, but we need to 286 * this is what we will return to user, but we need to
265 * move on first so next call has something fresh to test 287 * move on first so next call has something fresh to test
@@ -286,40 +308,25 @@ int ieee80211_radiotap_iterator_next(
286 /* these special ones are valid in each bitmap word */ 308 /* these special ones are valid in each bitmap word */
287 switch (iterator->_arg_index % 32) { 309 switch (iterator->_arg_index % 32) {
288 case IEEE80211_RADIOTAP_VENDOR_NAMESPACE: 310 case IEEE80211_RADIOTAP_VENDOR_NAMESPACE:
289 iterator->_bitmap_shifter >>= 1;
290 iterator->_arg_index++;
291
292 iterator->_reset_on_ext = 1; 311 iterator->_reset_on_ext = 1;
293 312
294 vnslen = get_unaligned_le16(iterator->this_arg + 4);
295 iterator->_next_ns_data = iterator->_arg + vnslen;
296 oui = (*iterator->this_arg << 16) |
297 (*(iterator->this_arg + 1) << 8) |
298 *(iterator->this_arg + 2);
299 subns = *(iterator->this_arg + 3);
300
301 find_ns(iterator, oui, subns);
302
303 iterator->is_radiotap_ns = 0; 313 iterator->is_radiotap_ns = 0;
304 /* allow parsers to show this information */ 314 /*
315 * If parser didn't register this vendor
316 * namespace with us, allow it to show it
317 * as 'raw. Do do that, set argument index
318 * to vendor namespace.
319 */
305 iterator->this_arg_index = 320 iterator->this_arg_index =
306 IEEE80211_RADIOTAP_VENDOR_NAMESPACE; 321 IEEE80211_RADIOTAP_VENDOR_NAMESPACE;
307 iterator->this_arg_size += vnslen; 322 if (!iterator->current_namespace)
308 if ((unsigned long)iterator->this_arg + 323 hit = 1;
309 iterator->this_arg_size - 324 goto next_entry;
310 (unsigned long)iterator->_rtheader >
311 (unsigned long)(unsigned long)iterator->_max_length)
312 return -EINVAL;
313 hit = 1;
314 break;
315 case IEEE80211_RADIOTAP_RADIOTAP_NAMESPACE: 325 case IEEE80211_RADIOTAP_RADIOTAP_NAMESPACE:
316 iterator->_bitmap_shifter >>= 1;
317 iterator->_arg_index++;
318
319 iterator->_reset_on_ext = 1; 326 iterator->_reset_on_ext = 1;
320 iterator->current_namespace = &radiotap_ns; 327 iterator->current_namespace = &radiotap_ns;
321 iterator->is_radiotap_ns = 1; 328 iterator->is_radiotap_ns = 1;
322 break; 329 goto next_entry;
323 case IEEE80211_RADIOTAP_EXT: 330 case IEEE80211_RADIOTAP_EXT:
324 /* 331 /*
325 * bit 31 was set, there is more 332 * bit 31 was set, there is more
diff --git a/net/wireless/reg.c b/net/wireless/reg.c
index f180db0de66c..d14bbf960c18 100644
--- a/net/wireless/reg.c
+++ b/net/wireless/reg.c
@@ -36,6 +36,7 @@
36#include <linux/slab.h> 36#include <linux/slab.h>
37#include <linux/list.h> 37#include <linux/list.h>
38#include <linux/random.h> 38#include <linux/random.h>
39#include <linux/ctype.h>
39#include <linux/nl80211.h> 40#include <linux/nl80211.h>
40#include <linux/platform_device.h> 41#include <linux/platform_device.h>
41#include <net/cfg80211.h> 42#include <net/cfg80211.h>
@@ -73,7 +74,11 @@ const struct ieee80211_regdomain *cfg80211_regdomain;
73 * - last_request 74 * - last_request
74 */ 75 */
75static DEFINE_MUTEX(reg_mutex); 76static DEFINE_MUTEX(reg_mutex);
76#define assert_reg_lock() WARN_ON(!mutex_is_locked(&reg_mutex)) 77
78static inline void assert_reg_lock(void)
79{
80 lockdep_assert_held(&reg_mutex);
81}
77 82
78/* Used to queue up regulatory hints */ 83/* Used to queue up regulatory hints */
79static LIST_HEAD(reg_requests_list); 84static LIST_HEAD(reg_requests_list);
@@ -181,14 +186,6 @@ static bool is_alpha2_set(const char *alpha2)
181 return false; 186 return false;
182} 187}
183 188
184static bool is_alpha_upper(char letter)
185{
186 /* ASCII A - Z */
187 if (letter >= 65 && letter <= 90)
188 return true;
189 return false;
190}
191
192static bool is_unknown_alpha2(const char *alpha2) 189static bool is_unknown_alpha2(const char *alpha2)
193{ 190{
194 if (!alpha2) 191 if (!alpha2)
@@ -220,7 +217,7 @@ static bool is_an_alpha2(const char *alpha2)
220{ 217{
221 if (!alpha2) 218 if (!alpha2)
222 return false; 219 return false;
223 if (is_alpha_upper(alpha2[0]) && is_alpha_upper(alpha2[1])) 220 if (isalpha(alpha2[0]) && isalpha(alpha2[1]))
224 return true; 221 return true;
225 return false; 222 return false;
226} 223}
@@ -1399,6 +1396,11 @@ static DECLARE_WORK(reg_work, reg_todo);
1399 1396
1400static void queue_regulatory_request(struct regulatory_request *request) 1397static void queue_regulatory_request(struct regulatory_request *request)
1401{ 1398{
1399 if (isalpha(request->alpha2[0]))
1400 request->alpha2[0] = toupper(request->alpha2[0]);
1401 if (isalpha(request->alpha2[1]))
1402 request->alpha2[1] = toupper(request->alpha2[1]);
1403
1402 spin_lock(&reg_requests_lock); 1404 spin_lock(&reg_requests_lock);
1403 list_add_tail(&request->list, &reg_requests_list); 1405 list_add_tail(&request->list, &reg_requests_list);
1404 spin_unlock(&reg_requests_lock); 1406 spin_unlock(&reg_requests_lock);
diff --git a/net/wireless/scan.c b/net/wireless/scan.c
index 5ca8c7180141..503ebb86ba18 100644
--- a/net/wireless/scan.c
+++ b/net/wireless/scan.c
@@ -650,14 +650,14 @@ void cfg80211_unlink_bss(struct wiphy *wiphy, struct cfg80211_bss *pub)
650 bss = container_of(pub, struct cfg80211_internal_bss, pub); 650 bss = container_of(pub, struct cfg80211_internal_bss, pub);
651 651
652 spin_lock_bh(&dev->bss_lock); 652 spin_lock_bh(&dev->bss_lock);
653 if (!list_empty(&bss->list)) {
654 list_del_init(&bss->list);
655 dev->bss_generation++;
656 rb_erase(&bss->rbn, &dev->bss_tree);
653 657
654 list_del(&bss->list); 658 kref_put(&bss->ref, bss_release);
655 dev->bss_generation++; 659 }
656 rb_erase(&bss->rbn, &dev->bss_tree);
657
658 spin_unlock_bh(&dev->bss_lock); 660 spin_unlock_bh(&dev->bss_lock);
659
660 kref_put(&bss->ref, bss_release);
661} 661}
662EXPORT_SYMBOL(cfg80211_unlink_bss); 662EXPORT_SYMBOL(cfg80211_unlink_bss);
663 663
diff --git a/net/wireless/sme.c b/net/wireless/sme.c
index a8c2d6b877ae..e17b0bee6bdc 100644
--- a/net/wireless/sme.c
+++ b/net/wireless/sme.c
@@ -411,7 +411,8 @@ void __cfg80211_connect_result(struct net_device *dev, const u8 *bssid,
411 411
412 ASSERT_WDEV_LOCK(wdev); 412 ASSERT_WDEV_LOCK(wdev);
413 413
414 if (WARN_ON(wdev->iftype != NL80211_IFTYPE_STATION)) 414 if (WARN_ON(wdev->iftype != NL80211_IFTYPE_STATION &&
415 wdev->iftype != NL80211_IFTYPE_P2P_CLIENT))
415 return; 416 return;
416 417
417 if (wdev->sme_state != CFG80211_SME_CONNECTING) 418 if (wdev->sme_state != CFG80211_SME_CONNECTING)
@@ -548,7 +549,8 @@ void __cfg80211_roamed(struct wireless_dev *wdev, const u8 *bssid,
548 549
549 ASSERT_WDEV_LOCK(wdev); 550 ASSERT_WDEV_LOCK(wdev);
550 551
551 if (WARN_ON(wdev->iftype != NL80211_IFTYPE_STATION)) 552 if (WARN_ON(wdev->iftype != NL80211_IFTYPE_STATION &&
553 wdev->iftype != NL80211_IFTYPE_P2P_CLIENT))
552 return; 554 return;
553 555
554 if (wdev->sme_state != CFG80211_SME_CONNECTED) 556 if (wdev->sme_state != CFG80211_SME_CONNECTED)
@@ -644,7 +646,8 @@ void __cfg80211_disconnected(struct net_device *dev, const u8 *ie,
644 646
645 ASSERT_WDEV_LOCK(wdev); 647 ASSERT_WDEV_LOCK(wdev);
646 648
647 if (WARN_ON(wdev->iftype != NL80211_IFTYPE_STATION)) 649 if (WARN_ON(wdev->iftype != NL80211_IFTYPE_STATION &&
650 wdev->iftype != NL80211_IFTYPE_P2P_CLIENT))
648 return; 651 return;
649 652
650 if (wdev->sme_state != CFG80211_SME_CONNECTED) 653 if (wdev->sme_state != CFG80211_SME_CONNECTED)
@@ -695,7 +698,7 @@ void __cfg80211_disconnected(struct net_device *dev, const u8 *ie,
695 */ 698 */
696 if (rdev->ops->del_key) 699 if (rdev->ops->del_key)
697 for (i = 0; i < 6; i++) 700 for (i = 0; i < 6; i++)
698 rdev->ops->del_key(wdev->wiphy, dev, i, NULL); 701 rdev->ops->del_key(wdev->wiphy, dev, i, false, NULL);
699 702
700#ifdef CONFIG_CFG80211_WEXT 703#ifdef CONFIG_CFG80211_WEXT
701 memset(&wrqu, 0, sizeof(wrqu)); 704 memset(&wrqu, 0, sizeof(wrqu));
diff --git a/net/wireless/sysfs.c b/net/wireless/sysfs.c
index 9f2cef3e0ca0..4294fa22bb2d 100644
--- a/net/wireless/sysfs.c
+++ b/net/wireless/sysfs.c
@@ -35,6 +35,14 @@ SHOW_FMT(index, "%d", wiphy_idx);
35SHOW_FMT(macaddress, "%pM", wiphy.perm_addr); 35SHOW_FMT(macaddress, "%pM", wiphy.perm_addr);
36SHOW_FMT(address_mask, "%pM", wiphy.addr_mask); 36SHOW_FMT(address_mask, "%pM", wiphy.addr_mask);
37 37
38static ssize_t name_show(struct device *dev,
39 struct device_attribute *attr,
40 char *buf) {
41 struct wiphy *wiphy = &dev_to_rdev(dev)->wiphy;
42 return sprintf(buf, "%s\n", dev_name(&wiphy->dev));
43}
44
45
38static ssize_t addresses_show(struct device *dev, 46static ssize_t addresses_show(struct device *dev,
39 struct device_attribute *attr, 47 struct device_attribute *attr,
40 char *buf) 48 char *buf)
@@ -57,6 +65,7 @@ static struct device_attribute ieee80211_dev_attrs[] = {
57 __ATTR_RO(macaddress), 65 __ATTR_RO(macaddress),
58 __ATTR_RO(address_mask), 66 __ATTR_RO(address_mask),
59 __ATTR_RO(addresses), 67 __ATTR_RO(addresses),
68 __ATTR_RO(name),
60 {} 69 {}
61}; 70};
62 71
@@ -110,6 +119,13 @@ static int wiphy_resume(struct device *dev)
110 return ret; 119 return ret;
111} 120}
112 121
122static const void *wiphy_namespace(struct device *d)
123{
124 struct wiphy *wiphy = container_of(d, struct wiphy, dev);
125
126 return wiphy_net(wiphy);
127}
128
113struct class ieee80211_class = { 129struct class ieee80211_class = {
114 .name = "ieee80211", 130 .name = "ieee80211",
115 .owner = THIS_MODULE, 131 .owner = THIS_MODULE,
@@ -120,6 +136,8 @@ struct class ieee80211_class = {
120#endif 136#endif
121 .suspend = wiphy_suspend, 137 .suspend = wiphy_suspend,
122 .resume = wiphy_resume, 138 .resume = wiphy_resume,
139 .ns_type = &net_ns_type_operations,
140 .namespace = wiphy_namespace,
123}; 141};
124 142
125int wiphy_sysfs_init(void) 143int wiphy_sysfs_init(void)
diff --git a/net/wireless/util.c b/net/wireless/util.c
index 0c8a1e8b7690..76120aeda57d 100644
--- a/net/wireless/util.c
+++ b/net/wireless/util.c
@@ -144,19 +144,25 @@ void ieee80211_set_bitrate_flags(struct wiphy *wiphy)
144 144
145int cfg80211_validate_key_settings(struct cfg80211_registered_device *rdev, 145int cfg80211_validate_key_settings(struct cfg80211_registered_device *rdev,
146 struct key_params *params, int key_idx, 146 struct key_params *params, int key_idx,
147 const u8 *mac_addr) 147 bool pairwise, const u8 *mac_addr)
148{ 148{
149 int i; 149 int i;
150 150
151 if (key_idx > 5) 151 if (key_idx > 5)
152 return -EINVAL; 152 return -EINVAL;
153 153
154 if (!pairwise && mac_addr && !(rdev->wiphy.flags & WIPHY_FLAG_IBSS_RSN))
155 return -EINVAL;
156
157 if (pairwise && !mac_addr)
158 return -EINVAL;
159
154 /* 160 /*
155 * Disallow pairwise keys with non-zero index unless it's WEP 161 * Disallow pairwise keys with non-zero index unless it's WEP
156 * (because current deployments use pairwise WEP keys with 162 * (because current deployments use pairwise WEP keys with
157 * non-zero indizes but 802.11i clearly specifies to use zero) 163 * non-zero indizes but 802.11i clearly specifies to use zero)
158 */ 164 */
159 if (mac_addr && key_idx && 165 if (pairwise && key_idx &&
160 params->cipher != WLAN_CIPHER_SUITE_WEP40 && 166 params->cipher != WLAN_CIPHER_SUITE_WEP40 &&
161 params->cipher != WLAN_CIPHER_SUITE_WEP104) 167 params->cipher != WLAN_CIPHER_SUITE_WEP104)
162 return -EINVAL; 168 return -EINVAL;
@@ -183,7 +189,14 @@ int cfg80211_validate_key_settings(struct cfg80211_registered_device *rdev,
183 return -EINVAL; 189 return -EINVAL;
184 break; 190 break;
185 default: 191 default:
186 return -EINVAL; 192 /*
193 * We don't know anything about this algorithm,
194 * allow using it -- but the driver must check
195 * all parameters! We still check below whether
196 * or not the driver supports this algorithm,
197 * of course.
198 */
199 break;
187 } 200 }
188 201
189 if (params->seq) { 202 if (params->seq) {
@@ -221,7 +234,7 @@ const unsigned char bridge_tunnel_header[] __aligned(2) =
221 { 0xaa, 0xaa, 0x03, 0x00, 0x00, 0xf8 }; 234 { 0xaa, 0xaa, 0x03, 0x00, 0x00, 0xf8 };
222EXPORT_SYMBOL(bridge_tunnel_header); 235EXPORT_SYMBOL(bridge_tunnel_header);
223 236
224unsigned int ieee80211_hdrlen(__le16 fc) 237unsigned int __attribute_const__ ieee80211_hdrlen(__le16 fc)
225{ 238{
226 unsigned int hdrlen = 24; 239 unsigned int hdrlen = 24;
227 240
@@ -319,7 +332,8 @@ int ieee80211_data_to_8023(struct sk_buff *skb, const u8 *addr,
319 cpu_to_le16(IEEE80211_FCTL_TODS | IEEE80211_FCTL_FROMDS)) { 332 cpu_to_le16(IEEE80211_FCTL_TODS | IEEE80211_FCTL_FROMDS)) {
320 case cpu_to_le16(IEEE80211_FCTL_TODS): 333 case cpu_to_le16(IEEE80211_FCTL_TODS):
321 if (unlikely(iftype != NL80211_IFTYPE_AP && 334 if (unlikely(iftype != NL80211_IFTYPE_AP &&
322 iftype != NL80211_IFTYPE_AP_VLAN)) 335 iftype != NL80211_IFTYPE_AP_VLAN &&
336 iftype != NL80211_IFTYPE_P2P_GO))
323 return -1; 337 return -1;
324 break; 338 break;
325 case cpu_to_le16(IEEE80211_FCTL_TODS | IEEE80211_FCTL_FROMDS): 339 case cpu_to_le16(IEEE80211_FCTL_TODS | IEEE80211_FCTL_FROMDS):
@@ -347,7 +361,8 @@ int ieee80211_data_to_8023(struct sk_buff *skb, const u8 *addr,
347 break; 361 break;
348 case cpu_to_le16(IEEE80211_FCTL_FROMDS): 362 case cpu_to_le16(IEEE80211_FCTL_FROMDS):
349 if ((iftype != NL80211_IFTYPE_STATION && 363 if ((iftype != NL80211_IFTYPE_STATION &&
350 iftype != NL80211_IFTYPE_MESH_POINT) || 364 iftype != NL80211_IFTYPE_P2P_CLIENT &&
365 iftype != NL80211_IFTYPE_MESH_POINT) ||
351 (is_multicast_ether_addr(dst) && 366 (is_multicast_ether_addr(dst) &&
352 !compare_ether_addr(src, addr))) 367 !compare_ether_addr(src, addr)))
353 return -1; 368 return -1;
@@ -424,6 +439,7 @@ int ieee80211_data_from_8023(struct sk_buff *skb, const u8 *addr,
424 switch (iftype) { 439 switch (iftype) {
425 case NL80211_IFTYPE_AP: 440 case NL80211_IFTYPE_AP:
426 case NL80211_IFTYPE_AP_VLAN: 441 case NL80211_IFTYPE_AP_VLAN:
442 case NL80211_IFTYPE_P2P_GO:
427 fc |= cpu_to_le16(IEEE80211_FCTL_FROMDS); 443 fc |= cpu_to_le16(IEEE80211_FCTL_FROMDS);
428 /* DA BSSID SA */ 444 /* DA BSSID SA */
429 memcpy(hdr.addr1, skb->data, ETH_ALEN); 445 memcpy(hdr.addr1, skb->data, ETH_ALEN);
@@ -432,6 +448,7 @@ int ieee80211_data_from_8023(struct sk_buff *skb, const u8 *addr,
432 hdrlen = 24; 448 hdrlen = 24;
433 break; 449 break;
434 case NL80211_IFTYPE_STATION: 450 case NL80211_IFTYPE_STATION:
451 case NL80211_IFTYPE_P2P_CLIENT:
435 fc |= cpu_to_le16(IEEE80211_FCTL_TODS); 452 fc |= cpu_to_le16(IEEE80211_FCTL_TODS);
436 /* BSSID SA DA */ 453 /* BSSID SA DA */
437 memcpy(hdr.addr1, bssid, ETH_ALEN); 454 memcpy(hdr.addr1, bssid, ETH_ALEN);
@@ -666,7 +683,7 @@ void cfg80211_upload_connect_keys(struct wireless_dev *wdev)
666 for (i = 0; i < 6; i++) { 683 for (i = 0; i < 6; i++) {
667 if (!wdev->connect_keys->params[i].cipher) 684 if (!wdev->connect_keys->params[i].cipher)
668 continue; 685 continue;
669 if (rdev->ops->add_key(wdev->wiphy, dev, i, NULL, 686 if (rdev->ops->add_key(wdev->wiphy, dev, i, false, NULL,
670 &wdev->connect_keys->params[i])) { 687 &wdev->connect_keys->params[i])) {
671 printk(KERN_ERR "%s: failed to set key %d\n", 688 printk(KERN_ERR "%s: failed to set key %d\n",
672 dev->name, i); 689 dev->name, i);
@@ -771,7 +788,9 @@ int cfg80211_change_iface(struct cfg80211_registered_device *rdev,
771 788
772 /* if it's part of a bridge, reject changing type to station/ibss */ 789 /* if it's part of a bridge, reject changing type to station/ibss */
773 if ((dev->priv_flags & IFF_BRIDGE_PORT) && 790 if ((dev->priv_flags & IFF_BRIDGE_PORT) &&
774 (ntype == NL80211_IFTYPE_ADHOC || ntype == NL80211_IFTYPE_STATION)) 791 (ntype == NL80211_IFTYPE_ADHOC ||
792 ntype == NL80211_IFTYPE_STATION ||
793 ntype == NL80211_IFTYPE_P2P_CLIENT))
775 return -EBUSY; 794 return -EBUSY;
776 795
777 if (ntype != otype) { 796 if (ntype != otype) {
@@ -782,6 +801,7 @@ int cfg80211_change_iface(struct cfg80211_registered_device *rdev,
782 cfg80211_leave_ibss(rdev, dev, false); 801 cfg80211_leave_ibss(rdev, dev, false);
783 break; 802 break;
784 case NL80211_IFTYPE_STATION: 803 case NL80211_IFTYPE_STATION:
804 case NL80211_IFTYPE_P2P_CLIENT:
785 cfg80211_disconnect(rdev, dev, 805 cfg80211_disconnect(rdev, dev,
786 WLAN_REASON_DEAUTH_LEAVING, true); 806 WLAN_REASON_DEAUTH_LEAVING, true);
787 break; 807 break;
@@ -810,9 +830,11 @@ int cfg80211_change_iface(struct cfg80211_registered_device *rdev,
810 if (dev->ieee80211_ptr->use_4addr) 830 if (dev->ieee80211_ptr->use_4addr)
811 break; 831 break;
812 /* fall through */ 832 /* fall through */
833 case NL80211_IFTYPE_P2P_CLIENT:
813 case NL80211_IFTYPE_ADHOC: 834 case NL80211_IFTYPE_ADHOC:
814 dev->priv_flags |= IFF_DONT_BRIDGE; 835 dev->priv_flags |= IFF_DONT_BRIDGE;
815 break; 836 break;
837 case NL80211_IFTYPE_P2P_GO:
816 case NL80211_IFTYPE_AP: 838 case NL80211_IFTYPE_AP:
817 case NL80211_IFTYPE_AP_VLAN: 839 case NL80211_IFTYPE_AP_VLAN:
818 case NL80211_IFTYPE_WDS: 840 case NL80211_IFTYPE_WDS:
@@ -823,7 +845,7 @@ int cfg80211_change_iface(struct cfg80211_registered_device *rdev,
823 /* monitor can't bridge anyway */ 845 /* monitor can't bridge anyway */
824 break; 846 break;
825 case NL80211_IFTYPE_UNSPECIFIED: 847 case NL80211_IFTYPE_UNSPECIFIED:
826 case __NL80211_IFTYPE_AFTER_LAST: 848 case NUM_NL80211_IFTYPES:
827 /* not happening */ 849 /* not happening */
828 break; 850 break;
829 } 851 }
diff --git a/net/wireless/wext-compat.c b/net/wireless/wext-compat.c
index 7e5c3a45f811..12222ee6ebf2 100644
--- a/net/wireless/wext-compat.c
+++ b/net/wireless/wext-compat.c
@@ -432,14 +432,17 @@ int cfg80211_wext_giwretry(struct net_device *dev,
432EXPORT_SYMBOL_GPL(cfg80211_wext_giwretry); 432EXPORT_SYMBOL_GPL(cfg80211_wext_giwretry);
433 433
434static int __cfg80211_set_encryption(struct cfg80211_registered_device *rdev, 434static int __cfg80211_set_encryption(struct cfg80211_registered_device *rdev,
435 struct net_device *dev, const u8 *addr, 435 struct net_device *dev, bool pairwise,
436 bool remove, bool tx_key, int idx, 436 const u8 *addr, bool remove, bool tx_key,
437 struct key_params *params) 437 int idx, struct key_params *params)
438{ 438{
439 struct wireless_dev *wdev = dev->ieee80211_ptr; 439 struct wireless_dev *wdev = dev->ieee80211_ptr;
440 int err, i; 440 int err, i;
441 bool rejoin = false; 441 bool rejoin = false;
442 442
443 if (pairwise && !addr)
444 return -EINVAL;
445
443 if (!wdev->wext.keys) { 446 if (!wdev->wext.keys) {
444 wdev->wext.keys = kzalloc(sizeof(*wdev->wext.keys), 447 wdev->wext.keys = kzalloc(sizeof(*wdev->wext.keys),
445 GFP_KERNEL); 448 GFP_KERNEL);
@@ -478,7 +481,13 @@ static int __cfg80211_set_encryption(struct cfg80211_registered_device *rdev,
478 __cfg80211_leave_ibss(rdev, wdev->netdev, true); 481 __cfg80211_leave_ibss(rdev, wdev->netdev, true);
479 rejoin = true; 482 rejoin = true;
480 } 483 }
481 err = rdev->ops->del_key(&rdev->wiphy, dev, idx, addr); 484
485 if (!pairwise && addr &&
486 !(rdev->wiphy.flags & WIPHY_FLAG_IBSS_RSN))
487 err = -ENOENT;
488 else
489 err = rdev->ops->del_key(&rdev->wiphy, dev, idx,
490 pairwise, addr);
482 } 491 }
483 wdev->wext.connect.privacy = false; 492 wdev->wext.connect.privacy = false;
484 /* 493 /*
@@ -507,12 +516,13 @@ static int __cfg80211_set_encryption(struct cfg80211_registered_device *rdev,
507 if (addr) 516 if (addr)
508 tx_key = false; 517 tx_key = false;
509 518
510 if (cfg80211_validate_key_settings(rdev, params, idx, addr)) 519 if (cfg80211_validate_key_settings(rdev, params, idx, pairwise, addr))
511 return -EINVAL; 520 return -EINVAL;
512 521
513 err = 0; 522 err = 0;
514 if (wdev->current_bss) 523 if (wdev->current_bss)
515 err = rdev->ops->add_key(&rdev->wiphy, dev, idx, addr, params); 524 err = rdev->ops->add_key(&rdev->wiphy, dev, idx,
525 pairwise, addr, params);
516 if (err) 526 if (err)
517 return err; 527 return err;
518 528
@@ -563,17 +573,17 @@ static int __cfg80211_set_encryption(struct cfg80211_registered_device *rdev,
563} 573}
564 574
565static int cfg80211_set_encryption(struct cfg80211_registered_device *rdev, 575static int cfg80211_set_encryption(struct cfg80211_registered_device *rdev,
566 struct net_device *dev, const u8 *addr, 576 struct net_device *dev, bool pairwise,
567 bool remove, bool tx_key, int idx, 577 const u8 *addr, bool remove, bool tx_key,
568 struct key_params *params) 578 int idx, struct key_params *params)
569{ 579{
570 int err; 580 int err;
571 581
572 /* devlist mutex needed for possible IBSS re-join */ 582 /* devlist mutex needed for possible IBSS re-join */
573 mutex_lock(&rdev->devlist_mtx); 583 mutex_lock(&rdev->devlist_mtx);
574 wdev_lock(dev->ieee80211_ptr); 584 wdev_lock(dev->ieee80211_ptr);
575 err = __cfg80211_set_encryption(rdev, dev, addr, remove, 585 err = __cfg80211_set_encryption(rdev, dev, pairwise, addr,
576 tx_key, idx, params); 586 remove, tx_key, idx, params);
577 wdev_unlock(dev->ieee80211_ptr); 587 wdev_unlock(dev->ieee80211_ptr);
578 mutex_unlock(&rdev->devlist_mtx); 588 mutex_unlock(&rdev->devlist_mtx);
579 589
@@ -635,7 +645,7 @@ int cfg80211_wext_siwencode(struct net_device *dev,
635 else if (!remove) 645 else if (!remove)
636 return -EINVAL; 646 return -EINVAL;
637 647
638 return cfg80211_set_encryption(rdev, dev, NULL, remove, 648 return cfg80211_set_encryption(rdev, dev, false, NULL, remove,
639 wdev->wext.default_key == -1, 649 wdev->wext.default_key == -1,
640 idx, &params); 650 idx, &params);
641} 651}
@@ -725,7 +735,9 @@ int cfg80211_wext_siwencodeext(struct net_device *dev,
725 } 735 }
726 736
727 return cfg80211_set_encryption( 737 return cfg80211_set_encryption(
728 rdev, dev, addr, remove, 738 rdev, dev,
739 !(ext->ext_flags & IW_ENCODE_EXT_GROUP_KEY),
740 addr, remove,
729 ext->ext_flags & IW_ENCODE_EXT_SET_TX_KEY, 741 ext->ext_flags & IW_ENCODE_EXT_SET_TX_KEY,
730 idx, &params); 742 idx, &params);
731} 743}
@@ -1354,6 +1366,10 @@ struct iw_statistics *cfg80211_wireless_stats(struct net_device *dev)
1354 } 1366 }
1355 1367
1356 wstats.qual.updated |= IW_QUAL_NOISE_INVALID; 1368 wstats.qual.updated |= IW_QUAL_NOISE_INVALID;
1369 if (sinfo.filled & STATION_INFO_RX_DROP_MISC)
1370 wstats.discard.misc = sinfo.rx_dropped_misc;
1371 if (sinfo.filled & STATION_INFO_TX_FAILED)
1372 wstats.discard.retries = sinfo.tx_failed;
1357 1373
1358 return &wstats; 1374 return &wstats;
1359} 1375}
diff --git a/net/wireless/wext-core.c b/net/wireless/wext-core.c
index 8f5116f5af19..dc675a3daa3d 100644
--- a/net/wireless/wext-core.c
+++ b/net/wireless/wext-core.c
@@ -611,7 +611,7 @@ struct iw_statistics *get_wireless_stats(struct net_device *dev)
611#endif 611#endif
612 612
613#ifdef CONFIG_CFG80211_WEXT 613#ifdef CONFIG_CFG80211_WEXT
614 if (dev->ieee80211_ptr && dev->ieee80211_ptr && 614 if (dev->ieee80211_ptr &&
615 dev->ieee80211_ptr->wiphy && 615 dev->ieee80211_ptr->wiphy &&
616 dev->ieee80211_ptr->wiphy->wext && 616 dev->ieee80211_ptr->wiphy->wext &&
617 dev->ieee80211_ptr->wiphy->wext->get_wireless_stats) 617 dev->ieee80211_ptr->wiphy->wext->get_wireless_stats)
diff --git a/net/wireless/wext-sme.c b/net/wireless/wext-sme.c
index 9818198add8a..6fffe62d7c25 100644
--- a/net/wireless/wext-sme.c
+++ b/net/wireless/wext-sme.c
@@ -197,6 +197,8 @@ int cfg80211_mgd_wext_siwessid(struct net_device *dev,
197 wdev->wext.connect.ssid_len = len; 197 wdev->wext.connect.ssid_len = len;
198 198
199 wdev->wext.connect.crypto.control_port = false; 199 wdev->wext.connect.crypto.control_port = false;
200 wdev->wext.connect.crypto.control_port_ethertype =
201 cpu_to_be16(ETH_P_PAE);
200 202
201 err = cfg80211_mgd_wext_connect(rdev, wdev); 203 err = cfg80211_mgd_wext_connect(rdev, wdev);
202 out: 204 out: