Merge branch 'ipmi' into release
[GitHub/mt8127/android_kernel_alcatel_ttab.git] / drivers / net / wireless / iwmc3200wifi / cfg80211.c
1 /*
2 * Intel Wireless Multicomm 3200 WiFi driver
3 *
4 * Copyright (C) 2009 Intel Corporation <ilw@linux.intel.com>
5 * Samuel Ortiz <samuel.ortiz@intel.com>
6 * Zhu Yi <yi.zhu@intel.com>
7 *
8 * This program is free software; you can redistribute it and/or
9 * modify it under the terms of the GNU General Public License version
10 * 2 as published by the Free Software Foundation.
11 *
12 * This program is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 * GNU General Public License for more details.
16 *
17 * You should have received a copy of the GNU General Public License
18 * along with this program; if not, write to the Free Software
19 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
20 * 02110-1301, USA.
21 *
22 */
23
24 #include <linux/kernel.h>
25 #include <linux/netdevice.h>
26 #include <linux/sched.h>
27 #include <linux/etherdevice.h>
28 #include <linux/wireless.h>
29 #include <linux/ieee80211.h>
30 #include <net/cfg80211.h>
31
32 #include "iwm.h"
33 #include "commands.h"
34 #include "cfg80211.h"
35 #include "debug.h"
36
37 #define RATETAB_ENT(_rate, _rateid, _flags) \
38 { \
39 .bitrate = (_rate), \
40 .hw_value = (_rateid), \
41 .flags = (_flags), \
42 }
43
44 #define CHAN2G(_channel, _freq, _flags) { \
45 .band = IEEE80211_BAND_2GHZ, \
46 .center_freq = (_freq), \
47 .hw_value = (_channel), \
48 .flags = (_flags), \
49 .max_antenna_gain = 0, \
50 .max_power = 30, \
51 }
52
53 #define CHAN5G(_channel, _flags) { \
54 .band = IEEE80211_BAND_5GHZ, \
55 .center_freq = 5000 + (5 * (_channel)), \
56 .hw_value = (_channel), \
57 .flags = (_flags), \
58 .max_antenna_gain = 0, \
59 .max_power = 30, \
60 }
61
62 static struct ieee80211_rate iwm_rates[] = {
63 RATETAB_ENT(10, 0x1, 0),
64 RATETAB_ENT(20, 0x2, 0),
65 RATETAB_ENT(55, 0x4, 0),
66 RATETAB_ENT(110, 0x8, 0),
67 RATETAB_ENT(60, 0x10, 0),
68 RATETAB_ENT(90, 0x20, 0),
69 RATETAB_ENT(120, 0x40, 0),
70 RATETAB_ENT(180, 0x80, 0),
71 RATETAB_ENT(240, 0x100, 0),
72 RATETAB_ENT(360, 0x200, 0),
73 RATETAB_ENT(480, 0x400, 0),
74 RATETAB_ENT(540, 0x800, 0),
75 };
76
77 #define iwm_a_rates (iwm_rates + 4)
78 #define iwm_a_rates_size 8
79 #define iwm_g_rates (iwm_rates + 0)
80 #define iwm_g_rates_size 12
81
82 static struct ieee80211_channel iwm_2ghz_channels[] = {
83 CHAN2G(1, 2412, 0),
84 CHAN2G(2, 2417, 0),
85 CHAN2G(3, 2422, 0),
86 CHAN2G(4, 2427, 0),
87 CHAN2G(5, 2432, 0),
88 CHAN2G(6, 2437, 0),
89 CHAN2G(7, 2442, 0),
90 CHAN2G(8, 2447, 0),
91 CHAN2G(9, 2452, 0),
92 CHAN2G(10, 2457, 0),
93 CHAN2G(11, 2462, 0),
94 CHAN2G(12, 2467, 0),
95 CHAN2G(13, 2472, 0),
96 CHAN2G(14, 2484, 0),
97 };
98
99 static struct ieee80211_channel iwm_5ghz_a_channels[] = {
100 CHAN5G(34, 0), CHAN5G(36, 0),
101 CHAN5G(38, 0), CHAN5G(40, 0),
102 CHAN5G(42, 0), CHAN5G(44, 0),
103 CHAN5G(46, 0), CHAN5G(48, 0),
104 CHAN5G(52, 0), CHAN5G(56, 0),
105 CHAN5G(60, 0), CHAN5G(64, 0),
106 CHAN5G(100, 0), CHAN5G(104, 0),
107 CHAN5G(108, 0), CHAN5G(112, 0),
108 CHAN5G(116, 0), CHAN5G(120, 0),
109 CHAN5G(124, 0), CHAN5G(128, 0),
110 CHAN5G(132, 0), CHAN5G(136, 0),
111 CHAN5G(140, 0), CHAN5G(149, 0),
112 CHAN5G(153, 0), CHAN5G(157, 0),
113 CHAN5G(161, 0), CHAN5G(165, 0),
114 CHAN5G(184, 0), CHAN5G(188, 0),
115 CHAN5G(192, 0), CHAN5G(196, 0),
116 CHAN5G(200, 0), CHAN5G(204, 0),
117 CHAN5G(208, 0), CHAN5G(212, 0),
118 CHAN5G(216, 0),
119 };
120
121 static struct ieee80211_supported_band iwm_band_2ghz = {
122 .channels = iwm_2ghz_channels,
123 .n_channels = ARRAY_SIZE(iwm_2ghz_channels),
124 .bitrates = iwm_g_rates,
125 .n_bitrates = iwm_g_rates_size,
126 };
127
128 static struct ieee80211_supported_band iwm_band_5ghz = {
129 .channels = iwm_5ghz_a_channels,
130 .n_channels = ARRAY_SIZE(iwm_5ghz_a_channels),
131 .bitrates = iwm_a_rates,
132 .n_bitrates = iwm_a_rates_size,
133 };
134
135 static int iwm_key_init(struct iwm_key *key, u8 key_index,
136 const u8 *mac_addr, struct key_params *params)
137 {
138 key->hdr.key_idx = key_index;
139 if (!mac_addr || is_broadcast_ether_addr(mac_addr)) {
140 key->hdr.multicast = 1;
141 memset(key->hdr.mac, 0xff, ETH_ALEN);
142 } else {
143 key->hdr.multicast = 0;
144 memcpy(key->hdr.mac, mac_addr, ETH_ALEN);
145 }
146
147 if (params) {
148 if (params->key_len > WLAN_MAX_KEY_LEN ||
149 params->seq_len > IW_ENCODE_SEQ_MAX_SIZE)
150 return -EINVAL;
151
152 key->cipher = params->cipher;
153 key->key_len = params->key_len;
154 key->seq_len = params->seq_len;
155 memcpy(key->key, params->key, key->key_len);
156 memcpy(key->seq, params->seq, key->seq_len);
157 }
158
159 return 0;
160 }
161
162 static int iwm_cfg80211_add_key(struct wiphy *wiphy, struct net_device *ndev,
163 u8 key_index, const u8 *mac_addr,
164 struct key_params *params)
165 {
166 struct iwm_priv *iwm = ndev_to_iwm(ndev);
167 struct iwm_key *key = &iwm->keys[key_index];
168 int ret;
169
170 IWM_DBG_WEXT(iwm, DBG, "Adding key for %pM\n", mac_addr);
171
172 memset(key, 0, sizeof(struct iwm_key));
173 ret = iwm_key_init(key, key_index, mac_addr, params);
174 if (ret < 0) {
175 IWM_ERR(iwm, "Invalid key_params\n");
176 return ret;
177 }
178
179 return iwm_set_key(iwm, 0, key);
180 }
181
182 static int iwm_cfg80211_get_key(struct wiphy *wiphy, struct net_device *ndev,
183 u8 key_index, const u8 *mac_addr, void *cookie,
184 void (*callback)(void *cookie,
185 struct key_params*))
186 {
187 struct iwm_priv *iwm = ndev_to_iwm(ndev);
188 struct iwm_key *key = &iwm->keys[key_index];
189 struct key_params params;
190
191 IWM_DBG_WEXT(iwm, DBG, "Getting key %d\n", key_index);
192
193 memset(&params, 0, sizeof(params));
194
195 params.cipher = key->cipher;
196 params.key_len = key->key_len;
197 params.seq_len = key->seq_len;
198 params.seq = key->seq;
199 params.key = key->key;
200
201 callback(cookie, &params);
202
203 return key->key_len ? 0 : -ENOENT;
204 }
205
206
207 static int iwm_cfg80211_del_key(struct wiphy *wiphy, struct net_device *ndev,
208 u8 key_index, const u8 *mac_addr)
209 {
210 struct iwm_priv *iwm = ndev_to_iwm(ndev);
211 struct iwm_key *key = &iwm->keys[key_index];
212
213 if (!iwm->keys[key_index].key_len) {
214 IWM_DBG_WEXT(iwm, DBG, "Key %d not used\n", key_index);
215 return 0;
216 }
217
218 if (key_index == iwm->default_key)
219 iwm->default_key = -1;
220
221 return iwm_set_key(iwm, 1, key);
222 }
223
224 static int iwm_cfg80211_set_default_key(struct wiphy *wiphy,
225 struct net_device *ndev,
226 u8 key_index)
227 {
228 struct iwm_priv *iwm = ndev_to_iwm(ndev);
229
230 IWM_DBG_WEXT(iwm, DBG, "Default key index is: %d\n", key_index);
231
232 if (!iwm->keys[key_index].key_len) {
233 IWM_ERR(iwm, "Key %d not used\n", key_index);
234 return -EINVAL;
235 }
236
237 iwm->default_key = key_index;
238
239 return iwm_set_tx_key(iwm, key_index);
240 }
241
242 static int iwm_cfg80211_get_station(struct wiphy *wiphy,
243 struct net_device *ndev,
244 u8 *mac, struct station_info *sinfo)
245 {
246 struct iwm_priv *iwm = ndev_to_iwm(ndev);
247
248 if (memcmp(mac, iwm->bssid, ETH_ALEN))
249 return -ENOENT;
250
251 sinfo->filled |= STATION_INFO_TX_BITRATE;
252 sinfo->txrate.legacy = iwm->rate * 10;
253
254 if (test_bit(IWM_STATUS_ASSOCIATED, &iwm->status)) {
255 sinfo->filled |= STATION_INFO_SIGNAL;
256 sinfo->signal = iwm->wstats.qual.level;
257 }
258
259 return 0;
260 }
261
262
263 int iwm_cfg80211_inform_bss(struct iwm_priv *iwm)
264 {
265 struct wiphy *wiphy = iwm_to_wiphy(iwm);
266 struct iwm_bss_info *bss, *next;
267 struct iwm_umac_notif_bss_info *umac_bss;
268 struct ieee80211_mgmt *mgmt;
269 struct ieee80211_channel *channel;
270 struct ieee80211_supported_band *band;
271 s32 signal;
272 int freq;
273
274 list_for_each_entry_safe(bss, next, &iwm->bss_list, node) {
275 umac_bss = bss->bss;
276 mgmt = (struct ieee80211_mgmt *)(umac_bss->frame_buf);
277
278 if (umac_bss->band == UMAC_BAND_2GHZ)
279 band = wiphy->bands[IEEE80211_BAND_2GHZ];
280 else if (umac_bss->band == UMAC_BAND_5GHZ)
281 band = wiphy->bands[IEEE80211_BAND_5GHZ];
282 else {
283 IWM_ERR(iwm, "Invalid band: %d\n", umac_bss->band);
284 return -EINVAL;
285 }
286
287 freq = ieee80211_channel_to_frequency(umac_bss->channel);
288 channel = ieee80211_get_channel(wiphy, freq);
289 signal = umac_bss->rssi * 100;
290
291 if (!cfg80211_inform_bss_frame(wiphy, channel, mgmt,
292 le16_to_cpu(umac_bss->frame_len),
293 signal, GFP_KERNEL))
294 return -EINVAL;
295 }
296
297 return 0;
298 }
299
300 static int iwm_cfg80211_change_iface(struct wiphy *wiphy,
301 struct net_device *ndev,
302 enum nl80211_iftype type, u32 *flags,
303 struct vif_params *params)
304 {
305 struct wireless_dev *wdev;
306 struct iwm_priv *iwm;
307 u32 old_mode;
308
309 wdev = ndev->ieee80211_ptr;
310 iwm = ndev_to_iwm(ndev);
311 old_mode = iwm->conf.mode;
312
313 switch (type) {
314 case NL80211_IFTYPE_STATION:
315 iwm->conf.mode = UMAC_MODE_BSS;
316 break;
317 case NL80211_IFTYPE_ADHOC:
318 iwm->conf.mode = UMAC_MODE_IBSS;
319 break;
320 default:
321 return -EOPNOTSUPP;
322 }
323
324 wdev->iftype = type;
325
326 if ((old_mode == iwm->conf.mode) || !iwm->umac_profile)
327 return 0;
328
329 iwm->umac_profile->mode = cpu_to_le32(iwm->conf.mode);
330
331 if (iwm->umac_profile_active)
332 iwm_invalidate_mlme_profile(iwm);
333
334 return 0;
335 }
336
337 static int iwm_cfg80211_scan(struct wiphy *wiphy, struct net_device *ndev,
338 struct cfg80211_scan_request *request)
339 {
340 struct iwm_priv *iwm = ndev_to_iwm(ndev);
341 int ret;
342
343 if (!test_bit(IWM_STATUS_READY, &iwm->status)) {
344 IWM_ERR(iwm, "Scan while device is not ready\n");
345 return -EIO;
346 }
347
348 if (test_bit(IWM_STATUS_SCANNING, &iwm->status)) {
349 IWM_ERR(iwm, "Scanning already\n");
350 return -EAGAIN;
351 }
352
353 if (test_bit(IWM_STATUS_SCAN_ABORTING, &iwm->status)) {
354 IWM_ERR(iwm, "Scanning being aborted\n");
355 return -EAGAIN;
356 }
357
358 set_bit(IWM_STATUS_SCANNING, &iwm->status);
359
360 ret = iwm_scan_ssids(iwm, request->ssids, request->n_ssids);
361 if (ret) {
362 clear_bit(IWM_STATUS_SCANNING, &iwm->status);
363 return ret;
364 }
365
366 iwm->scan_request = request;
367 return 0;
368 }
369
370 static int iwm_cfg80211_set_wiphy_params(struct wiphy *wiphy, u32 changed)
371 {
372 struct iwm_priv *iwm = wiphy_to_iwm(wiphy);
373
374 if (changed & WIPHY_PARAM_RTS_THRESHOLD &&
375 (iwm->conf.rts_threshold != wiphy->rts_threshold)) {
376 int ret;
377
378 iwm->conf.rts_threshold = wiphy->rts_threshold;
379
380 ret = iwm_umac_set_config_fix(iwm, UMAC_PARAM_TBL_CFG_FIX,
381 CFG_RTS_THRESHOLD,
382 iwm->conf.rts_threshold);
383 if (ret < 0)
384 return ret;
385 }
386
387 if (changed & WIPHY_PARAM_FRAG_THRESHOLD &&
388 (iwm->conf.frag_threshold != wiphy->frag_threshold)) {
389 int ret;
390
391 iwm->conf.frag_threshold = wiphy->frag_threshold;
392
393 ret = iwm_umac_set_config_fix(iwm, UMAC_PARAM_TBL_FA_CFG_FIX,
394 CFG_FRAG_THRESHOLD,
395 iwm->conf.frag_threshold);
396 if (ret < 0)
397 return ret;
398 }
399
400 return 0;
401 }
402
403 static int iwm_cfg80211_join_ibss(struct wiphy *wiphy, struct net_device *dev,
404 struct cfg80211_ibss_params *params)
405 {
406 struct iwm_priv *iwm = wiphy_to_iwm(wiphy);
407 struct ieee80211_channel *chan = params->channel;
408
409 if (!test_bit(IWM_STATUS_READY, &iwm->status))
410 return -EIO;
411
412 /* UMAC doesn't support creating or joining an IBSS network
413 * with specified bssid. */
414 if (params->bssid)
415 return -EOPNOTSUPP;
416
417 iwm->channel = ieee80211_frequency_to_channel(chan->center_freq);
418 iwm->umac_profile->ibss.band = chan->band;
419 iwm->umac_profile->ibss.channel = iwm->channel;
420 iwm->umac_profile->ssid.ssid_len = params->ssid_len;
421 memcpy(iwm->umac_profile->ssid.ssid, params->ssid, params->ssid_len);
422
423 return iwm_send_mlme_profile(iwm);
424 }
425
426 static int iwm_cfg80211_leave_ibss(struct wiphy *wiphy, struct net_device *dev)
427 {
428 struct iwm_priv *iwm = wiphy_to_iwm(wiphy);
429
430 if (iwm->umac_profile_active)
431 return iwm_invalidate_mlme_profile(iwm);
432
433 return 0;
434 }
435
436 static int iwm_set_auth_type(struct iwm_priv *iwm,
437 enum nl80211_auth_type sme_auth_type)
438 {
439 u8 *auth_type = &iwm->umac_profile->sec.auth_type;
440
441 switch (sme_auth_type) {
442 case NL80211_AUTHTYPE_AUTOMATIC:
443 case NL80211_AUTHTYPE_OPEN_SYSTEM:
444 IWM_DBG_WEXT(iwm, DBG, "OPEN auth\n");
445 *auth_type = UMAC_AUTH_TYPE_OPEN;
446 break;
447 case NL80211_AUTHTYPE_SHARED_KEY:
448 if (iwm->umac_profile->sec.flags &
449 (UMAC_SEC_FLG_WPA_ON_MSK | UMAC_SEC_FLG_RSNA_ON_MSK)) {
450 IWM_DBG_WEXT(iwm, DBG, "WPA auth alg\n");
451 *auth_type = UMAC_AUTH_TYPE_RSNA_PSK;
452 } else {
453 IWM_DBG_WEXT(iwm, DBG, "WEP shared key auth alg\n");
454 *auth_type = UMAC_AUTH_TYPE_LEGACY_PSK;
455 }
456
457 break;
458 default:
459 IWM_ERR(iwm, "Unsupported auth alg: 0x%x\n", sme_auth_type);
460 return -ENOTSUPP;
461 }
462
463 return 0;
464 }
465
466 static int iwm_set_wpa_version(struct iwm_priv *iwm, u32 wpa_version)
467 {
468 IWM_DBG_WEXT(iwm, DBG, "wpa_version: %d\n", wpa_version);
469
470 if (!wpa_version) {
471 iwm->umac_profile->sec.flags = UMAC_SEC_FLG_LEGACY_PROFILE;
472 return 0;
473 }
474
475 if (wpa_version & NL80211_WPA_VERSION_1)
476 iwm->umac_profile->sec.flags = UMAC_SEC_FLG_WPA_ON_MSK;
477
478 if (wpa_version & NL80211_WPA_VERSION_2)
479 iwm->umac_profile->sec.flags = UMAC_SEC_FLG_RSNA_ON_MSK;
480
481 return 0;
482 }
483
484 static int iwm_set_cipher(struct iwm_priv *iwm, u32 cipher, bool ucast)
485 {
486 u8 *profile_cipher = ucast ? &iwm->umac_profile->sec.ucast_cipher :
487 &iwm->umac_profile->sec.mcast_cipher;
488
489 if (!cipher) {
490 *profile_cipher = UMAC_CIPHER_TYPE_NONE;
491 return 0;
492 }
493
494 IWM_DBG_WEXT(iwm, DBG, "%ccast cipher is 0x%x\n", ucast ? 'u' : 'm',
495 cipher);
496
497 switch (cipher) {
498 case IW_AUTH_CIPHER_NONE:
499 *profile_cipher = UMAC_CIPHER_TYPE_NONE;
500 break;
501 case WLAN_CIPHER_SUITE_WEP40:
502 *profile_cipher = UMAC_CIPHER_TYPE_WEP_40;
503 break;
504 case WLAN_CIPHER_SUITE_WEP104:
505 *profile_cipher = UMAC_CIPHER_TYPE_WEP_104;
506 break;
507 case WLAN_CIPHER_SUITE_TKIP:
508 *profile_cipher = UMAC_CIPHER_TYPE_TKIP;
509 break;
510 case WLAN_CIPHER_SUITE_CCMP:
511 *profile_cipher = UMAC_CIPHER_TYPE_CCMP;
512 break;
513 default:
514 IWM_ERR(iwm, "Unsupported cipher: 0x%x\n", cipher);
515 return -ENOTSUPP;
516 }
517
518 return 0;
519 }
520
521 static int iwm_set_key_mgt(struct iwm_priv *iwm, u32 key_mgt)
522 {
523 u8 *auth_type = &iwm->umac_profile->sec.auth_type;
524
525 IWM_DBG_WEXT(iwm, DBG, "key_mgt: 0x%x\n", key_mgt);
526
527 if (key_mgt == WLAN_AKM_SUITE_8021X)
528 *auth_type = UMAC_AUTH_TYPE_8021X;
529 else if (key_mgt == WLAN_AKM_SUITE_PSK) {
530 if (iwm->umac_profile->sec.flags &
531 (UMAC_SEC_FLG_WPA_ON_MSK | UMAC_SEC_FLG_RSNA_ON_MSK))
532 *auth_type = UMAC_AUTH_TYPE_RSNA_PSK;
533 else
534 *auth_type = UMAC_AUTH_TYPE_LEGACY_PSK;
535 } else {
536 IWM_ERR(iwm, "Invalid key mgt: 0x%x\n", key_mgt);
537 return -EINVAL;
538 }
539
540 return 0;
541 }
542
543
544 static int iwm_cfg80211_connect(struct wiphy *wiphy, struct net_device *dev,
545 struct cfg80211_connect_params *sme)
546 {
547 struct iwm_priv *iwm = wiphy_to_iwm(wiphy);
548 struct ieee80211_channel *chan = sme->channel;
549 struct key_params key_param;
550 int ret;
551
552 if (!test_bit(IWM_STATUS_READY, &iwm->status))
553 return -EIO;
554
555 if (!sme->ssid)
556 return -EINVAL;
557
558 if (iwm->umac_profile_active) {
559 ret = iwm_invalidate_mlme_profile(iwm);
560 if (ret) {
561 IWM_ERR(iwm, "Couldn't invalidate profile\n");
562 return ret;
563 }
564 }
565
566 if (chan)
567 iwm->channel =
568 ieee80211_frequency_to_channel(chan->center_freq);
569
570 iwm->umac_profile->ssid.ssid_len = sme->ssid_len;
571 memcpy(iwm->umac_profile->ssid.ssid, sme->ssid, sme->ssid_len);
572
573 if (sme->bssid) {
574 IWM_DBG_WEXT(iwm, DBG, "BSSID: %pM\n", sme->bssid);
575 memcpy(&iwm->umac_profile->bssid[0], sme->bssid, ETH_ALEN);
576 iwm->umac_profile->bss_num = 1;
577 } else {
578 memset(&iwm->umac_profile->bssid[0], 0, ETH_ALEN);
579 iwm->umac_profile->bss_num = 0;
580 }
581
582 ret = iwm_set_wpa_version(iwm, sme->crypto.wpa_versions);
583 if (ret < 0)
584 return ret;
585
586 ret = iwm_set_auth_type(iwm, sme->auth_type);
587 if (ret < 0)
588 return ret;
589
590 if (sme->crypto.n_ciphers_pairwise) {
591 ret = iwm_set_cipher(iwm, sme->crypto.ciphers_pairwise[0],
592 true);
593 if (ret < 0)
594 return ret;
595 }
596
597 ret = iwm_set_cipher(iwm, sme->crypto.cipher_group, false);
598 if (ret < 0)
599 return ret;
600
601 if (sme->crypto.n_akm_suites) {
602 ret = iwm_set_key_mgt(iwm, sme->crypto.akm_suites[0]);
603 if (ret < 0)
604 return ret;
605 }
606
607 /*
608 * We save the WEP key in case we want to do shared authentication.
609 * We have to do it so because UMAC will assert whenever it gets a
610 * key before a profile.
611 */
612 if (sme->key) {
613 key_param.key = kmemdup(sme->key, sme->key_len, GFP_KERNEL);
614 if (key_param.key == NULL)
615 return -ENOMEM;
616 key_param.key_len = sme->key_len;
617 key_param.seq_len = 0;
618 key_param.cipher = sme->crypto.ciphers_pairwise[0];
619
620 ret = iwm_key_init(&iwm->keys[sme->key_idx], sme->key_idx,
621 NULL, &key_param);
622 kfree(key_param.key);
623 if (ret < 0) {
624 IWM_ERR(iwm, "Invalid key_params\n");
625 return ret;
626 }
627
628 iwm->default_key = sme->key_idx;
629 }
630
631 /* WPA and open AUTH type from wpa_s means WPS (a.k.a. WSC) */
632 if ((iwm->umac_profile->sec.flags &
633 (UMAC_SEC_FLG_WPA_ON_MSK | UMAC_SEC_FLG_RSNA_ON_MSK)) &&
634 iwm->umac_profile->sec.auth_type == UMAC_AUTH_TYPE_OPEN) {
635 iwm->umac_profile->sec.flags = UMAC_SEC_FLG_WSC_ON_MSK;
636 }
637
638 ret = iwm_send_mlme_profile(iwm);
639
640 if (iwm->umac_profile->sec.auth_type != UMAC_AUTH_TYPE_LEGACY_PSK ||
641 sme->key == NULL)
642 return ret;
643
644 /*
645 * We want to do shared auth.
646 * We need to actually set the key we previously cached,
647 * and then tell the UMAC it's the default one.
648 * That will trigger the auth+assoc UMAC machinery, and again,
649 * this must be done after setting the profile.
650 */
651 ret = iwm_set_key(iwm, 0, &iwm->keys[sme->key_idx]);
652 if (ret < 0)
653 return ret;
654
655 return iwm_set_tx_key(iwm, iwm->default_key);
656 }
657
658 static int iwm_cfg80211_disconnect(struct wiphy *wiphy, struct net_device *dev,
659 u16 reason_code)
660 {
661 struct iwm_priv *iwm = wiphy_to_iwm(wiphy);
662
663 IWM_DBG_WEXT(iwm, DBG, "Active: %d\n", iwm->umac_profile_active);
664
665 if (iwm->umac_profile_active)
666 iwm_invalidate_mlme_profile(iwm);
667
668 return 0;
669 }
670
671 static int iwm_cfg80211_set_txpower(struct wiphy *wiphy,
672 enum tx_power_setting type, int dbm)
673 {
674 struct iwm_priv *iwm = wiphy_to_iwm(wiphy);
675 int ret;
676
677 switch (type) {
678 case TX_POWER_AUTOMATIC:
679 return 0;
680 case TX_POWER_FIXED:
681 if (!test_bit(IWM_STATUS_READY, &iwm->status))
682 return 0;
683
684 ret = iwm_umac_set_config_fix(iwm, UMAC_PARAM_TBL_CFG_FIX,
685 CFG_TX_PWR_LIMIT_USR, dbm * 2);
686 if (ret < 0)
687 return ret;
688
689 return iwm_tx_power_trigger(iwm);
690 default:
691 IWM_ERR(iwm, "Unsupported power type: %d\n", type);
692 return -EOPNOTSUPP;
693 }
694
695 return 0;
696 }
697
698 static int iwm_cfg80211_get_txpower(struct wiphy *wiphy, int *dbm)
699 {
700 struct iwm_priv *iwm = wiphy_to_iwm(wiphy);
701
702 *dbm = iwm->txpower >> 1;
703
704 return 0;
705 }
706
707 static int iwm_cfg80211_set_power_mgmt(struct wiphy *wiphy,
708 struct net_device *dev,
709 bool enabled, int timeout)
710 {
711 struct iwm_priv *iwm = wiphy_to_iwm(wiphy);
712 u32 power_index;
713
714 if (enabled)
715 power_index = IWM_POWER_INDEX_DEFAULT;
716 else
717 power_index = IWM_POWER_INDEX_MIN;
718
719 if (power_index == iwm->conf.power_index)
720 return 0;
721
722 iwm->conf.power_index = power_index;
723
724 return iwm_umac_set_config_fix(iwm, UMAC_PARAM_TBL_CFG_FIX,
725 CFG_POWER_INDEX, iwm->conf.power_index);
726 }
727
728 int iwm_cfg80211_set_pmksa(struct wiphy *wiphy, struct net_device *netdev,
729 struct cfg80211_pmksa *pmksa)
730 {
731 struct iwm_priv *iwm = wiphy_to_iwm(wiphy);
732
733 return iwm_send_pmkid_update(iwm, pmksa, IWM_CMD_PMKID_ADD);
734 }
735
736 int iwm_cfg80211_del_pmksa(struct wiphy *wiphy, struct net_device *netdev,
737 struct cfg80211_pmksa *pmksa)
738 {
739 struct iwm_priv *iwm = wiphy_to_iwm(wiphy);
740
741 return iwm_send_pmkid_update(iwm, pmksa, IWM_CMD_PMKID_DEL);
742 }
743
744 int iwm_cfg80211_flush_pmksa(struct wiphy *wiphy, struct net_device *netdev)
745 {
746 struct iwm_priv *iwm = wiphy_to_iwm(wiphy);
747 struct cfg80211_pmksa pmksa;
748
749 memset(&pmksa, 0, sizeof(struct cfg80211_pmksa));
750
751 return iwm_send_pmkid_update(iwm, &pmksa, IWM_CMD_PMKID_FLUSH);
752 }
753
754
755 static struct cfg80211_ops iwm_cfg80211_ops = {
756 .change_virtual_intf = iwm_cfg80211_change_iface,
757 .add_key = iwm_cfg80211_add_key,
758 .get_key = iwm_cfg80211_get_key,
759 .del_key = iwm_cfg80211_del_key,
760 .set_default_key = iwm_cfg80211_set_default_key,
761 .get_station = iwm_cfg80211_get_station,
762 .scan = iwm_cfg80211_scan,
763 .set_wiphy_params = iwm_cfg80211_set_wiphy_params,
764 .connect = iwm_cfg80211_connect,
765 .disconnect = iwm_cfg80211_disconnect,
766 .join_ibss = iwm_cfg80211_join_ibss,
767 .leave_ibss = iwm_cfg80211_leave_ibss,
768 .set_tx_power = iwm_cfg80211_set_txpower,
769 .get_tx_power = iwm_cfg80211_get_txpower,
770 .set_power_mgmt = iwm_cfg80211_set_power_mgmt,
771 .set_pmksa = iwm_cfg80211_set_pmksa,
772 .del_pmksa = iwm_cfg80211_del_pmksa,
773 .flush_pmksa = iwm_cfg80211_flush_pmksa,
774 };
775
776 static const u32 cipher_suites[] = {
777 WLAN_CIPHER_SUITE_WEP40,
778 WLAN_CIPHER_SUITE_WEP104,
779 WLAN_CIPHER_SUITE_TKIP,
780 WLAN_CIPHER_SUITE_CCMP,
781 };
782
783 struct wireless_dev *iwm_wdev_alloc(int sizeof_bus, struct device *dev)
784 {
785 int ret = 0;
786 struct wireless_dev *wdev;
787
788 /*
789 * We're trying to have the following memory
790 * layout:
791 *
792 * +-------------------------+
793 * | struct wiphy |
794 * +-------------------------+
795 * | struct iwm_priv |
796 * +-------------------------+
797 * | bus private data |
798 * | (e.g. iwm_priv_sdio) |
799 * +-------------------------+
800 *
801 */
802
803 wdev = kzalloc(sizeof(struct wireless_dev), GFP_KERNEL);
804 if (!wdev) {
805 dev_err(dev, "Couldn't allocate wireless device\n");
806 return ERR_PTR(-ENOMEM);
807 }
808
809 wdev->wiphy = wiphy_new(&iwm_cfg80211_ops,
810 sizeof(struct iwm_priv) + sizeof_bus);
811 if (!wdev->wiphy) {
812 dev_err(dev, "Couldn't allocate wiphy device\n");
813 ret = -ENOMEM;
814 goto out_err_new;
815 }
816
817 set_wiphy_dev(wdev->wiphy, dev);
818 wdev->wiphy->max_scan_ssids = UMAC_WIFI_IF_PROBE_OPTION_MAX;
819 wdev->wiphy->max_num_pmkids = UMAC_MAX_NUM_PMKIDS;
820 wdev->wiphy->interface_modes = BIT(NL80211_IFTYPE_STATION) |
821 BIT(NL80211_IFTYPE_ADHOC);
822 wdev->wiphy->bands[IEEE80211_BAND_2GHZ] = &iwm_band_2ghz;
823 wdev->wiphy->bands[IEEE80211_BAND_5GHZ] = &iwm_band_5ghz;
824 wdev->wiphy->signal_type = CFG80211_SIGNAL_TYPE_MBM;
825
826 wdev->wiphy->cipher_suites = cipher_suites;
827 wdev->wiphy->n_cipher_suites = ARRAY_SIZE(cipher_suites);
828
829 ret = wiphy_register(wdev->wiphy);
830 if (ret < 0) {
831 dev_err(dev, "Couldn't register wiphy device\n");
832 goto out_err_register;
833 }
834
835 return wdev;
836
837 out_err_register:
838 wiphy_free(wdev->wiphy);
839
840 out_err_new:
841 kfree(wdev);
842
843 return ERR_PTR(ret);
844 }
845
846 void iwm_wdev_free(struct iwm_priv *iwm)
847 {
848 struct wireless_dev *wdev = iwm_to_wdev(iwm);
849
850 if (!wdev)
851 return;
852
853 wiphy_unregister(wdev->wiphy);
854 wiphy_free(wdev->wiphy);
855 kfree(wdev);
856 }