2
* Intel Wireless Multicomm 3200 WiFi driver
4
* Copyright (C) 2009 Intel Corporation <ilw@linux.intel.com>
5
* Samuel Ortiz <samuel.ortiz@intel.com>
6
* Zhu Yi <yi.zhu@intel.com>
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.
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.
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
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 <linux/slab.h>
31
#include <net/cfg80211.h>
38
#define RATETAB_ENT(_rate, _rateid, _flags) \
41
.hw_value = (_rateid), \
45
#define CHAN2G(_channel, _freq, _flags) { \
46
.band = IEEE80211_BAND_2GHZ, \
47
.center_freq = (_freq), \
48
.hw_value = (_channel), \
50
.max_antenna_gain = 0, \
54
#define CHAN5G(_channel, _flags) { \
55
.band = IEEE80211_BAND_5GHZ, \
56
.center_freq = 5000 + (5 * (_channel)), \
57
.hw_value = (_channel), \
59
.max_antenna_gain = 0, \
63
static struct ieee80211_rate iwm_rates[] = {
64
RATETAB_ENT(10, 0x1, 0),
65
RATETAB_ENT(20, 0x2, 0),
66
RATETAB_ENT(55, 0x4, 0),
67
RATETAB_ENT(110, 0x8, 0),
68
RATETAB_ENT(60, 0x10, 0),
69
RATETAB_ENT(90, 0x20, 0),
70
RATETAB_ENT(120, 0x40, 0),
71
RATETAB_ENT(180, 0x80, 0),
72
RATETAB_ENT(240, 0x100, 0),
73
RATETAB_ENT(360, 0x200, 0),
74
RATETAB_ENT(480, 0x400, 0),
75
RATETAB_ENT(540, 0x800, 0),
78
#define iwm_a_rates (iwm_rates + 4)
79
#define iwm_a_rates_size 8
80
#define iwm_g_rates (iwm_rates + 0)
81
#define iwm_g_rates_size 12
83
static struct ieee80211_channel iwm_2ghz_channels[] = {
100
static struct ieee80211_channel iwm_5ghz_a_channels[] = {
101
CHAN5G(34, 0), CHAN5G(36, 0),
102
CHAN5G(38, 0), CHAN5G(40, 0),
103
CHAN5G(42, 0), CHAN5G(44, 0),
104
CHAN5G(46, 0), CHAN5G(48, 0),
105
CHAN5G(52, 0), CHAN5G(56, 0),
106
CHAN5G(60, 0), CHAN5G(64, 0),
107
CHAN5G(100, 0), CHAN5G(104, 0),
108
CHAN5G(108, 0), CHAN5G(112, 0),
109
CHAN5G(116, 0), CHAN5G(120, 0),
110
CHAN5G(124, 0), CHAN5G(128, 0),
111
CHAN5G(132, 0), CHAN5G(136, 0),
112
CHAN5G(140, 0), CHAN5G(149, 0),
113
CHAN5G(153, 0), CHAN5G(157, 0),
114
CHAN5G(161, 0), CHAN5G(165, 0),
115
CHAN5G(184, 0), CHAN5G(188, 0),
116
CHAN5G(192, 0), CHAN5G(196, 0),
117
CHAN5G(200, 0), CHAN5G(204, 0),
118
CHAN5G(208, 0), CHAN5G(212, 0),
122
static struct ieee80211_supported_band iwm_band_2ghz = {
123
.channels = iwm_2ghz_channels,
124
.n_channels = ARRAY_SIZE(iwm_2ghz_channels),
125
.bitrates = iwm_g_rates,
126
.n_bitrates = iwm_g_rates_size,
129
static struct ieee80211_supported_band iwm_band_5ghz = {
130
.channels = iwm_5ghz_a_channels,
131
.n_channels = ARRAY_SIZE(iwm_5ghz_a_channels),
132
.bitrates = iwm_a_rates,
133
.n_bitrates = iwm_a_rates_size,
136
static int iwm_key_init(struct iwm_key *key, u8 key_index,
137
const u8 *mac_addr, struct key_params *params)
139
key->hdr.key_idx = key_index;
140
if (!mac_addr || is_broadcast_ether_addr(mac_addr)) {
141
key->hdr.multicast = 1;
142
memset(key->hdr.mac, 0xff, ETH_ALEN);
144
key->hdr.multicast = 0;
145
memcpy(key->hdr.mac, mac_addr, ETH_ALEN);
149
if (params->key_len > WLAN_MAX_KEY_LEN ||
150
params->seq_len > IW_ENCODE_SEQ_MAX_SIZE)
153
key->cipher = params->cipher;
154
key->key_len = params->key_len;
155
key->seq_len = params->seq_len;
156
memcpy(key->key, params->key, key->key_len);
157
memcpy(key->seq, params->seq, key->seq_len);
163
static int iwm_cfg80211_add_key(struct wiphy *wiphy, struct net_device *ndev,
164
u8 key_index, const u8 *mac_addr,
165
struct key_params *params)
167
struct iwm_priv *iwm = ndev_to_iwm(ndev);
168
struct iwm_key *key = &iwm->keys[key_index];
171
IWM_DBG_WEXT(iwm, DBG, "Adding key for %pM\n", mac_addr);
173
memset(key, 0, sizeof(struct iwm_key));
174
ret = iwm_key_init(key, key_index, mac_addr, params);
176
IWM_ERR(iwm, "Invalid key_params\n");
180
return iwm_set_key(iwm, 0, key);
183
static int iwm_cfg80211_get_key(struct wiphy *wiphy, struct net_device *ndev,
184
u8 key_index, const u8 *mac_addr, void *cookie,
185
void (*callback)(void *cookie,
188
struct iwm_priv *iwm = ndev_to_iwm(ndev);
189
struct iwm_key *key = &iwm->keys[key_index];
190
struct key_params params;
192
IWM_DBG_WEXT(iwm, DBG, "Getting key %d\n", key_index);
194
memset(¶ms, 0, sizeof(params));
196
params.cipher = key->cipher;
197
params.key_len = key->key_len;
198
params.seq_len = key->seq_len;
199
params.seq = key->seq;
200
params.key = key->key;
202
callback(cookie, ¶ms);
204
return key->key_len ? 0 : -ENOENT;
208
static int iwm_cfg80211_del_key(struct wiphy *wiphy, struct net_device *ndev,
209
u8 key_index, const u8 *mac_addr)
211
struct iwm_priv *iwm = ndev_to_iwm(ndev);
212
struct iwm_key *key = &iwm->keys[key_index];
214
if (!iwm->keys[key_index].key_len) {
215
IWM_DBG_WEXT(iwm, DBG, "Key %d not used\n", key_index);
219
if (key_index == iwm->default_key)
220
iwm->default_key = -1;
222
return iwm_set_key(iwm, 1, key);
225
static int iwm_cfg80211_set_default_key(struct wiphy *wiphy,
226
struct net_device *ndev,
229
struct iwm_priv *iwm = ndev_to_iwm(ndev);
231
IWM_DBG_WEXT(iwm, DBG, "Default key index is: %d\n", key_index);
233
if (!iwm->keys[key_index].key_len) {
234
IWM_ERR(iwm, "Key %d not used\n", key_index);
238
iwm->default_key = key_index;
240
return iwm_set_tx_key(iwm, key_index);
243
static int iwm_cfg80211_get_station(struct wiphy *wiphy,
244
struct net_device *ndev,
245
u8 *mac, struct station_info *sinfo)
247
struct iwm_priv *iwm = ndev_to_iwm(ndev);
249
if (memcmp(mac, iwm->bssid, ETH_ALEN))
252
sinfo->filled |= STATION_INFO_TX_BITRATE;
253
sinfo->txrate.legacy = iwm->rate * 10;
255
if (test_bit(IWM_STATUS_ASSOCIATED, &iwm->status)) {
256
sinfo->filled |= STATION_INFO_SIGNAL;
257
sinfo->signal = iwm->wstats.qual.level;
264
int iwm_cfg80211_inform_bss(struct iwm_priv *iwm)
266
struct wiphy *wiphy = iwm_to_wiphy(iwm);
267
struct iwm_bss_info *bss;
268
struct iwm_umac_notif_bss_info *umac_bss;
269
struct ieee80211_mgmt *mgmt;
270
struct ieee80211_channel *channel;
271
struct ieee80211_supported_band *band;
275
list_for_each_entry(bss, &iwm->bss_list, node) {
277
mgmt = (struct ieee80211_mgmt *)(umac_bss->frame_buf);
279
if (umac_bss->band == UMAC_BAND_2GHZ)
280
band = wiphy->bands[IEEE80211_BAND_2GHZ];
281
else if (umac_bss->band == UMAC_BAND_5GHZ)
282
band = wiphy->bands[IEEE80211_BAND_5GHZ];
284
IWM_ERR(iwm, "Invalid band: %d\n", umac_bss->band);
288
freq = ieee80211_channel_to_frequency(umac_bss->channel);
289
channel = ieee80211_get_channel(wiphy, freq);
290
signal = umac_bss->rssi * 100;
292
if (!cfg80211_inform_bss_frame(wiphy, channel, mgmt,
293
le16_to_cpu(umac_bss->frame_len),
301
static int iwm_cfg80211_change_iface(struct wiphy *wiphy,
302
struct net_device *ndev,
303
enum nl80211_iftype type, u32 *flags,
304
struct vif_params *params)
306
struct wireless_dev *wdev;
307
struct iwm_priv *iwm;
310
wdev = ndev->ieee80211_ptr;
311
iwm = ndev_to_iwm(ndev);
312
old_mode = iwm->conf.mode;
315
case NL80211_IFTYPE_STATION:
316
iwm->conf.mode = UMAC_MODE_BSS;
318
case NL80211_IFTYPE_ADHOC:
319
iwm->conf.mode = UMAC_MODE_IBSS;
327
if ((old_mode == iwm->conf.mode) || !iwm->umac_profile)
330
iwm->umac_profile->mode = cpu_to_le32(iwm->conf.mode);
332
if (iwm->umac_profile_active)
333
iwm_invalidate_mlme_profile(iwm);
338
static int iwm_cfg80211_scan(struct wiphy *wiphy, struct net_device *ndev,
339
struct cfg80211_scan_request *request)
341
struct iwm_priv *iwm = ndev_to_iwm(ndev);
344
if (!test_bit(IWM_STATUS_READY, &iwm->status)) {
345
IWM_ERR(iwm, "Scan while device is not ready\n");
349
if (test_bit(IWM_STATUS_SCANNING, &iwm->status)) {
350
IWM_ERR(iwm, "Scanning already\n");
354
if (test_bit(IWM_STATUS_SCAN_ABORTING, &iwm->status)) {
355
IWM_ERR(iwm, "Scanning being aborted\n");
359
set_bit(IWM_STATUS_SCANNING, &iwm->status);
361
ret = iwm_scan_ssids(iwm, request->ssids, request->n_ssids);
363
clear_bit(IWM_STATUS_SCANNING, &iwm->status);
367
iwm->scan_request = request;
371
static int iwm_cfg80211_set_wiphy_params(struct wiphy *wiphy, u32 changed)
373
struct iwm_priv *iwm = wiphy_to_iwm(wiphy);
375
if (changed & WIPHY_PARAM_RTS_THRESHOLD &&
376
(iwm->conf.rts_threshold != wiphy->rts_threshold)) {
379
iwm->conf.rts_threshold = wiphy->rts_threshold;
381
ret = iwm_umac_set_config_fix(iwm, UMAC_PARAM_TBL_CFG_FIX,
383
iwm->conf.rts_threshold);
388
if (changed & WIPHY_PARAM_FRAG_THRESHOLD &&
389
(iwm->conf.frag_threshold != wiphy->frag_threshold)) {
392
iwm->conf.frag_threshold = wiphy->frag_threshold;
394
ret = iwm_umac_set_config_fix(iwm, UMAC_PARAM_TBL_FA_CFG_FIX,
396
iwm->conf.frag_threshold);
404
static int iwm_cfg80211_join_ibss(struct wiphy *wiphy, struct net_device *dev,
405
struct cfg80211_ibss_params *params)
407
struct iwm_priv *iwm = wiphy_to_iwm(wiphy);
408
struct ieee80211_channel *chan = params->channel;
410
if (!test_bit(IWM_STATUS_READY, &iwm->status))
413
/* UMAC doesn't support creating or joining an IBSS network
414
* with specified bssid. */
418
iwm->channel = ieee80211_frequency_to_channel(chan->center_freq);
419
iwm->umac_profile->ibss.band = chan->band;
420
iwm->umac_profile->ibss.channel = iwm->channel;
421
iwm->umac_profile->ssid.ssid_len = params->ssid_len;
422
memcpy(iwm->umac_profile->ssid.ssid, params->ssid, params->ssid_len);
424
return iwm_send_mlme_profile(iwm);
427
static int iwm_cfg80211_leave_ibss(struct wiphy *wiphy, struct net_device *dev)
429
struct iwm_priv *iwm = wiphy_to_iwm(wiphy);
431
if (iwm->umac_profile_active)
432
return iwm_invalidate_mlme_profile(iwm);
437
static int iwm_set_auth_type(struct iwm_priv *iwm,
438
enum nl80211_auth_type sme_auth_type)
440
u8 *auth_type = &iwm->umac_profile->sec.auth_type;
442
switch (sme_auth_type) {
443
case NL80211_AUTHTYPE_AUTOMATIC:
444
case NL80211_AUTHTYPE_OPEN_SYSTEM:
445
IWM_DBG_WEXT(iwm, DBG, "OPEN auth\n");
446
*auth_type = UMAC_AUTH_TYPE_OPEN;
448
case NL80211_AUTHTYPE_SHARED_KEY:
449
if (iwm->umac_profile->sec.flags &
450
(UMAC_SEC_FLG_WPA_ON_MSK | UMAC_SEC_FLG_RSNA_ON_MSK)) {
451
IWM_DBG_WEXT(iwm, DBG, "WPA auth alg\n");
452
*auth_type = UMAC_AUTH_TYPE_RSNA_PSK;
454
IWM_DBG_WEXT(iwm, DBG, "WEP shared key auth alg\n");
455
*auth_type = UMAC_AUTH_TYPE_LEGACY_PSK;
460
IWM_ERR(iwm, "Unsupported auth alg: 0x%x\n", sme_auth_type);
467
static int iwm_set_wpa_version(struct iwm_priv *iwm, u32 wpa_version)
469
IWM_DBG_WEXT(iwm, DBG, "wpa_version: %d\n", wpa_version);
472
iwm->umac_profile->sec.flags = UMAC_SEC_FLG_LEGACY_PROFILE;
476
if (wpa_version & NL80211_WPA_VERSION_1)
477
iwm->umac_profile->sec.flags = UMAC_SEC_FLG_WPA_ON_MSK;
479
if (wpa_version & NL80211_WPA_VERSION_2)
480
iwm->umac_profile->sec.flags = UMAC_SEC_FLG_RSNA_ON_MSK;
485
static int iwm_set_cipher(struct iwm_priv *iwm, u32 cipher, bool ucast)
487
u8 *profile_cipher = ucast ? &iwm->umac_profile->sec.ucast_cipher :
488
&iwm->umac_profile->sec.mcast_cipher;
491
*profile_cipher = UMAC_CIPHER_TYPE_NONE;
495
IWM_DBG_WEXT(iwm, DBG, "%ccast cipher is 0x%x\n", ucast ? 'u' : 'm',
499
case IW_AUTH_CIPHER_NONE:
500
*profile_cipher = UMAC_CIPHER_TYPE_NONE;
502
case WLAN_CIPHER_SUITE_WEP40:
503
*profile_cipher = UMAC_CIPHER_TYPE_WEP_40;
505
case WLAN_CIPHER_SUITE_WEP104:
506
*profile_cipher = UMAC_CIPHER_TYPE_WEP_104;
508
case WLAN_CIPHER_SUITE_TKIP:
509
*profile_cipher = UMAC_CIPHER_TYPE_TKIP;
511
case WLAN_CIPHER_SUITE_CCMP:
512
*profile_cipher = UMAC_CIPHER_TYPE_CCMP;
515
IWM_ERR(iwm, "Unsupported cipher: 0x%x\n", cipher);
522
static int iwm_set_key_mgt(struct iwm_priv *iwm, u32 key_mgt)
524
u8 *auth_type = &iwm->umac_profile->sec.auth_type;
526
IWM_DBG_WEXT(iwm, DBG, "key_mgt: 0x%x\n", key_mgt);
528
if (key_mgt == WLAN_AKM_SUITE_8021X)
529
*auth_type = UMAC_AUTH_TYPE_8021X;
530
else if (key_mgt == WLAN_AKM_SUITE_PSK) {
531
if (iwm->umac_profile->sec.flags &
532
(UMAC_SEC_FLG_WPA_ON_MSK | UMAC_SEC_FLG_RSNA_ON_MSK))
533
*auth_type = UMAC_AUTH_TYPE_RSNA_PSK;
535
*auth_type = UMAC_AUTH_TYPE_LEGACY_PSK;
537
IWM_ERR(iwm, "Invalid key mgt: 0x%x\n", key_mgt);
545
static int iwm_cfg80211_connect(struct wiphy *wiphy, struct net_device *dev,
546
struct cfg80211_connect_params *sme)
548
struct iwm_priv *iwm = wiphy_to_iwm(wiphy);
549
struct ieee80211_channel *chan = sme->channel;
550
struct key_params key_param;
553
if (!test_bit(IWM_STATUS_READY, &iwm->status))
559
if (iwm->umac_profile_active) {
560
ret = iwm_invalidate_mlme_profile(iwm);
562
IWM_ERR(iwm, "Couldn't invalidate profile\n");
569
ieee80211_frequency_to_channel(chan->center_freq);
571
iwm->umac_profile->ssid.ssid_len = sme->ssid_len;
572
memcpy(iwm->umac_profile->ssid.ssid, sme->ssid, sme->ssid_len);
575
IWM_DBG_WEXT(iwm, DBG, "BSSID: %pM\n", sme->bssid);
576
memcpy(&iwm->umac_profile->bssid[0], sme->bssid, ETH_ALEN);
577
iwm->umac_profile->bss_num = 1;
579
memset(&iwm->umac_profile->bssid[0], 0, ETH_ALEN);
580
iwm->umac_profile->bss_num = 0;
583
ret = iwm_set_wpa_version(iwm, sme->crypto.wpa_versions);
587
ret = iwm_set_auth_type(iwm, sme->auth_type);
591
if (sme->crypto.n_ciphers_pairwise) {
592
ret = iwm_set_cipher(iwm, sme->crypto.ciphers_pairwise[0],
598
ret = iwm_set_cipher(iwm, sme->crypto.cipher_group, false);
602
if (sme->crypto.n_akm_suites) {
603
ret = iwm_set_key_mgt(iwm, sme->crypto.akm_suites[0]);
609
* We save the WEP key in case we want to do shared authentication.
610
* We have to do it so because UMAC will assert whenever it gets a
611
* key before a profile.
614
key_param.key = kmemdup(sme->key, sme->key_len, GFP_KERNEL);
615
if (key_param.key == NULL)
617
key_param.key_len = sme->key_len;
618
key_param.seq_len = 0;
619
key_param.cipher = sme->crypto.ciphers_pairwise[0];
621
ret = iwm_key_init(&iwm->keys[sme->key_idx], sme->key_idx,
623
kfree(key_param.key);
625
IWM_ERR(iwm, "Invalid key_params\n");
629
iwm->default_key = sme->key_idx;
632
/* WPA and open AUTH type from wpa_s means WPS (a.k.a. WSC) */
633
if ((iwm->umac_profile->sec.flags &
634
(UMAC_SEC_FLG_WPA_ON_MSK | UMAC_SEC_FLG_RSNA_ON_MSK)) &&
635
iwm->umac_profile->sec.auth_type == UMAC_AUTH_TYPE_OPEN) {
636
iwm->umac_profile->sec.flags = UMAC_SEC_FLG_WSC_ON_MSK;
639
ret = iwm_send_mlme_profile(iwm);
641
if (iwm->umac_profile->sec.auth_type != UMAC_AUTH_TYPE_LEGACY_PSK ||
646
* We want to do shared auth.
647
* We need to actually set the key we previously cached,
648
* and then tell the UMAC it's the default one.
649
* That will trigger the auth+assoc UMAC machinery, and again,
650
* this must be done after setting the profile.
652
ret = iwm_set_key(iwm, 0, &iwm->keys[sme->key_idx]);
656
return iwm_set_tx_key(iwm, iwm->default_key);
659
static int iwm_cfg80211_disconnect(struct wiphy *wiphy, struct net_device *dev,
662
struct iwm_priv *iwm = wiphy_to_iwm(wiphy);
664
IWM_DBG_WEXT(iwm, DBG, "Active: %d\n", iwm->umac_profile_active);
666
if (iwm->umac_profile_active)
667
iwm_invalidate_mlme_profile(iwm);
672
static int iwm_cfg80211_set_txpower(struct wiphy *wiphy,
673
enum nl80211_tx_power_setting type, int mbm)
675
struct iwm_priv *iwm = wiphy_to_iwm(wiphy);
679
case NL80211_TX_POWER_AUTOMATIC:
681
case NL80211_TX_POWER_FIXED:
682
if (mbm < 0 || (mbm % 100))
685
if (!test_bit(IWM_STATUS_READY, &iwm->status))
688
ret = iwm_umac_set_config_fix(iwm, UMAC_PARAM_TBL_CFG_FIX,
689
CFG_TX_PWR_LIMIT_USR,
690
MBM_TO_DBM(mbm) * 2);
694
return iwm_tx_power_trigger(iwm);
696
IWM_ERR(iwm, "Unsupported power type: %d\n", type);
703
static int iwm_cfg80211_get_txpower(struct wiphy *wiphy, int *dbm)
705
struct iwm_priv *iwm = wiphy_to_iwm(wiphy);
707
*dbm = iwm->txpower >> 1;
712
static int iwm_cfg80211_set_power_mgmt(struct wiphy *wiphy,
713
struct net_device *dev,
714
bool enabled, int timeout)
716
struct iwm_priv *iwm = wiphy_to_iwm(wiphy);
720
power_index = IWM_POWER_INDEX_DEFAULT;
722
power_index = IWM_POWER_INDEX_MIN;
724
if (power_index == iwm->conf.power_index)
727
iwm->conf.power_index = power_index;
729
return iwm_umac_set_config_fix(iwm, UMAC_PARAM_TBL_CFG_FIX,
730
CFG_POWER_INDEX, iwm->conf.power_index);
733
static int iwm_cfg80211_set_pmksa(struct wiphy *wiphy,
734
struct net_device *netdev,
735
struct cfg80211_pmksa *pmksa)
737
struct iwm_priv *iwm = wiphy_to_iwm(wiphy);
739
return iwm_send_pmkid_update(iwm, pmksa, IWM_CMD_PMKID_ADD);
742
static int iwm_cfg80211_del_pmksa(struct wiphy *wiphy,
743
struct net_device *netdev,
744
struct cfg80211_pmksa *pmksa)
746
struct iwm_priv *iwm = wiphy_to_iwm(wiphy);
748
return iwm_send_pmkid_update(iwm, pmksa, IWM_CMD_PMKID_DEL);
751
static int iwm_cfg80211_flush_pmksa(struct wiphy *wiphy,
752
struct net_device *netdev)
754
struct iwm_priv *iwm = wiphy_to_iwm(wiphy);
755
struct cfg80211_pmksa pmksa;
757
memset(&pmksa, 0, sizeof(struct cfg80211_pmksa));
759
return iwm_send_pmkid_update(iwm, &pmksa, IWM_CMD_PMKID_FLUSH);
763
static struct cfg80211_ops iwm_cfg80211_ops = {
764
.change_virtual_intf = iwm_cfg80211_change_iface,
765
.add_key = iwm_cfg80211_add_key,
766
.get_key = iwm_cfg80211_get_key,
767
.del_key = iwm_cfg80211_del_key,
768
.set_default_key = iwm_cfg80211_set_default_key,
769
.get_station = iwm_cfg80211_get_station,
770
.scan = iwm_cfg80211_scan,
771
.set_wiphy_params = iwm_cfg80211_set_wiphy_params,
772
.connect = iwm_cfg80211_connect,
773
.disconnect = iwm_cfg80211_disconnect,
774
.join_ibss = iwm_cfg80211_join_ibss,
775
.leave_ibss = iwm_cfg80211_leave_ibss,
776
.set_tx_power = iwm_cfg80211_set_txpower,
777
.get_tx_power = iwm_cfg80211_get_txpower,
778
.set_power_mgmt = iwm_cfg80211_set_power_mgmt,
779
.set_pmksa = iwm_cfg80211_set_pmksa,
780
.del_pmksa = iwm_cfg80211_del_pmksa,
781
.flush_pmksa = iwm_cfg80211_flush_pmksa,
784
static const u32 cipher_suites[] = {
785
WLAN_CIPHER_SUITE_WEP40,
786
WLAN_CIPHER_SUITE_WEP104,
787
WLAN_CIPHER_SUITE_TKIP,
788
WLAN_CIPHER_SUITE_CCMP,
791
struct wireless_dev *iwm_wdev_alloc(int sizeof_bus, struct device *dev)
794
struct wireless_dev *wdev;
797
* We're trying to have the following memory
800
* +-------------------------+
802
* +-------------------------+
803
* | struct iwm_priv |
804
* +-------------------------+
805
* | bus private data |
806
* | (e.g. iwm_priv_sdio) |
807
* +-------------------------+
811
wdev = kzalloc(sizeof(struct wireless_dev), GFP_KERNEL);
813
dev_err(dev, "Couldn't allocate wireless device\n");
814
return ERR_PTR(-ENOMEM);
817
wdev->wiphy = wiphy_new(&iwm_cfg80211_ops,
818
sizeof(struct iwm_priv) + sizeof_bus);
820
dev_err(dev, "Couldn't allocate wiphy device\n");
825
set_wiphy_dev(wdev->wiphy, dev);
826
wdev->wiphy->max_scan_ssids = UMAC_WIFI_IF_PROBE_OPTION_MAX;
827
wdev->wiphy->max_num_pmkids = UMAC_MAX_NUM_PMKIDS;
828
wdev->wiphy->interface_modes = BIT(NL80211_IFTYPE_STATION) |
829
BIT(NL80211_IFTYPE_ADHOC);
830
wdev->wiphy->bands[IEEE80211_BAND_2GHZ] = &iwm_band_2ghz;
831
wdev->wiphy->bands[IEEE80211_BAND_5GHZ] = &iwm_band_5ghz;
832
wdev->wiphy->signal_type = CFG80211_SIGNAL_TYPE_MBM;
834
wdev->wiphy->cipher_suites = cipher_suites;
835
wdev->wiphy->n_cipher_suites = ARRAY_SIZE(cipher_suites);
837
ret = wiphy_register(wdev->wiphy);
839
dev_err(dev, "Couldn't register wiphy device\n");
840
goto out_err_register;
846
wiphy_free(wdev->wiphy);
854
void iwm_wdev_free(struct iwm_priv *iwm)
856
struct wireless_dev *wdev = iwm_to_wdev(iwm);
861
wiphy_unregister(wdev->wiphy);
862
wiphy_free(wdev->wiphy);