aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/net/wireless/mwifiex/cfg80211.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/net/wireless/mwifiex/cfg80211.c')
-rw-r--r--drivers/net/wireless/mwifiex/cfg80211.c403
1 files changed, 303 insertions, 100 deletions
diff --git a/drivers/net/wireless/mwifiex/cfg80211.c b/drivers/net/wireless/mwifiex/cfg80211.c
index 8bfc07cd330e..21ee27ab7b74 100644
--- a/drivers/net/wireless/mwifiex/cfg80211.c
+++ b/drivers/net/wireless/mwifiex/cfg80211.c
@@ -252,9 +252,9 @@ mwifiex_cfg80211_mgmt_frame_register(struct wiphy *wiphy,
252 252
253 if (mask != priv->mgmt_frame_mask) { 253 if (mask != priv->mgmt_frame_mask) {
254 priv->mgmt_frame_mask = mask; 254 priv->mgmt_frame_mask = mask;
255 mwifiex_send_cmd_async(priv, HostCmd_CMD_MGMT_FRAME_REG, 255 mwifiex_send_cmd(priv, HostCmd_CMD_MGMT_FRAME_REG,
256 HostCmd_ACT_GEN_SET, 0, 256 HostCmd_ACT_GEN_SET, 0,
257 &priv->mgmt_frame_mask); 257 &priv->mgmt_frame_mask, false);
258 wiphy_dbg(wiphy, "info: mgmt frame registered\n"); 258 wiphy_dbg(wiphy, "info: mgmt frame registered\n");
259 } 259 }
260} 260}
@@ -515,8 +515,8 @@ static int mwifiex_send_domain_info_cmd_fw(struct wiphy *wiphy)
515 515
516 priv = mwifiex_get_priv(adapter, MWIFIEX_BSS_ROLE_ANY); 516 priv = mwifiex_get_priv(adapter, MWIFIEX_BSS_ROLE_ANY);
517 517
518 if (mwifiex_send_cmd_async(priv, HostCmd_CMD_802_11D_DOMAIN_INFO, 518 if (mwifiex_send_cmd(priv, HostCmd_CMD_802_11D_DOMAIN_INFO,
519 HostCmd_ACT_GEN_SET, 0, NULL)) { 519 HostCmd_ACT_GEN_SET, 0, NULL, false)) {
520 wiphy_err(wiphy, "11D: setting domain info in FW\n"); 520 wiphy_err(wiphy, "11D: setting domain info in FW\n");
521 return -1; 521 return -1;
522 } 522 }
@@ -580,9 +580,9 @@ mwifiex_set_frag(struct mwifiex_private *priv, u32 frag_thr)
580 frag_thr > MWIFIEX_FRAG_MAX_VALUE) 580 frag_thr > MWIFIEX_FRAG_MAX_VALUE)
581 frag_thr = MWIFIEX_FRAG_MAX_VALUE; 581 frag_thr = MWIFIEX_FRAG_MAX_VALUE;
582 582
583 return mwifiex_send_cmd_sync(priv, HostCmd_CMD_802_11_SNMP_MIB, 583 return mwifiex_send_cmd(priv, HostCmd_CMD_802_11_SNMP_MIB,
584 HostCmd_ACT_GEN_SET, FRAG_THRESH_I, 584 HostCmd_ACT_GEN_SET, FRAG_THRESH_I,
585 &frag_thr); 585 &frag_thr, true);
586} 586}
587 587
588/* 588/*
@@ -597,9 +597,9 @@ mwifiex_set_rts(struct mwifiex_private *priv, u32 rts_thr)
597 if (rts_thr < MWIFIEX_RTS_MIN_VALUE || rts_thr > MWIFIEX_RTS_MAX_VALUE) 597 if (rts_thr < MWIFIEX_RTS_MIN_VALUE || rts_thr > MWIFIEX_RTS_MAX_VALUE)
598 rts_thr = MWIFIEX_RTS_MAX_VALUE; 598 rts_thr = MWIFIEX_RTS_MAX_VALUE;
599 599
600 return mwifiex_send_cmd_sync(priv, HostCmd_CMD_802_11_SNMP_MIB, 600 return mwifiex_send_cmd(priv, HostCmd_CMD_802_11_SNMP_MIB,
601 HostCmd_ACT_GEN_SET, RTS_THRESH_I, 601 HostCmd_ACT_GEN_SET, RTS_THRESH_I,
602 &rts_thr); 602 &rts_thr, true);
603} 603}
604 604
605/* 605/*
@@ -637,20 +637,19 @@ mwifiex_cfg80211_set_wiphy_params(struct wiphy *wiphy, u32 changed)
637 637
638 bss_started = priv->bss_started; 638 bss_started = priv->bss_started;
639 639
640 ret = mwifiex_send_cmd_sync(priv, 640 ret = mwifiex_send_cmd(priv, HostCmd_CMD_UAP_BSS_STOP,
641 HostCmd_CMD_UAP_BSS_STOP, 641 HostCmd_ACT_GEN_SET, 0,
642 HostCmd_ACT_GEN_SET, 0, 642 NULL, true);
643 NULL);
644 if (ret) { 643 if (ret) {
645 wiphy_err(wiphy, "Failed to stop the BSS\n"); 644 wiphy_err(wiphy, "Failed to stop the BSS\n");
646 kfree(bss_cfg); 645 kfree(bss_cfg);
647 return ret; 646 return ret;
648 } 647 }
649 648
650 ret = mwifiex_send_cmd_async(priv, 649 ret = mwifiex_send_cmd(priv, HostCmd_CMD_UAP_SYS_CONFIG,
651 HostCmd_CMD_UAP_SYS_CONFIG, 650 HostCmd_ACT_GEN_SET,
652 HostCmd_ACT_GEN_SET, 651 UAP_BSS_PARAMS_I, bss_cfg,
653 UAP_BSS_PARAMS_I, bss_cfg); 652 false);
654 653
655 kfree(bss_cfg); 654 kfree(bss_cfg);
656 655
@@ -662,10 +661,9 @@ mwifiex_cfg80211_set_wiphy_params(struct wiphy *wiphy, u32 changed)
662 if (!bss_started) 661 if (!bss_started)
663 break; 662 break;
664 663
665 ret = mwifiex_send_cmd_async(priv, 664 ret = mwifiex_send_cmd(priv, HostCmd_CMD_UAP_BSS_START,
666 HostCmd_CMD_UAP_BSS_START, 665 HostCmd_ACT_GEN_SET, 0,
667 HostCmd_ACT_GEN_SET, 0, 666 NULL, false);
668 NULL);
669 if (ret) { 667 if (ret) {
670 wiphy_err(wiphy, "Failed to start BSS\n"); 668 wiphy_err(wiphy, "Failed to start BSS\n");
671 return ret; 669 return ret;
@@ -700,8 +698,8 @@ mwifiex_cfg80211_deinit_p2p(struct mwifiex_private *priv)
700 if (GET_BSS_ROLE(priv) != MWIFIEX_BSS_ROLE_STA) 698 if (GET_BSS_ROLE(priv) != MWIFIEX_BSS_ROLE_STA)
701 mwifiex_set_bss_role(priv, MWIFIEX_BSS_ROLE_STA); 699 mwifiex_set_bss_role(priv, MWIFIEX_BSS_ROLE_STA);
702 700
703 if (mwifiex_send_cmd_sync(priv, HostCmd_CMD_P2P_MODE_CFG, 701 if (mwifiex_send_cmd(priv, HostCmd_CMD_P2P_MODE_CFG,
704 HostCmd_ACT_GEN_SET, 0, &mode)) 702 HostCmd_ACT_GEN_SET, 0, &mode, true))
705 return -1; 703 return -1;
706 704
707 return 0; 705 return 0;
@@ -721,13 +719,13 @@ mwifiex_cfg80211_init_p2p_client(struct mwifiex_private *priv)
721 return -1; 719 return -1;
722 720
723 mode = P2P_MODE_DEVICE; 721 mode = P2P_MODE_DEVICE;
724 if (mwifiex_send_cmd_sync(priv, HostCmd_CMD_P2P_MODE_CFG, 722 if (mwifiex_send_cmd(priv, HostCmd_CMD_P2P_MODE_CFG,
725 HostCmd_ACT_GEN_SET, 0, &mode)) 723 HostCmd_ACT_GEN_SET, 0, &mode, true))
726 return -1; 724 return -1;
727 725
728 mode = P2P_MODE_CLIENT; 726 mode = P2P_MODE_CLIENT;
729 if (mwifiex_send_cmd_sync(priv, HostCmd_CMD_P2P_MODE_CFG, 727 if (mwifiex_send_cmd(priv, HostCmd_CMD_P2P_MODE_CFG,
730 HostCmd_ACT_GEN_SET, 0, &mode)) 728 HostCmd_ACT_GEN_SET, 0, &mode, true))
731 return -1; 729 return -1;
732 730
733 return 0; 731 return 0;
@@ -747,13 +745,13 @@ mwifiex_cfg80211_init_p2p_go(struct mwifiex_private *priv)
747 return -1; 745 return -1;
748 746
749 mode = P2P_MODE_DEVICE; 747 mode = P2P_MODE_DEVICE;
750 if (mwifiex_send_cmd_sync(priv, HostCmd_CMD_P2P_MODE_CFG, 748 if (mwifiex_send_cmd(priv, HostCmd_CMD_P2P_MODE_CFG,
751 HostCmd_ACT_GEN_SET, 0, &mode)) 749 HostCmd_ACT_GEN_SET, 0, &mode, true))
752 return -1; 750 return -1;
753 751
754 mode = P2P_MODE_GO; 752 mode = P2P_MODE_GO;
755 if (mwifiex_send_cmd_sync(priv, HostCmd_CMD_P2P_MODE_CFG, 753 if (mwifiex_send_cmd(priv, HostCmd_CMD_P2P_MODE_CFG,
756 HostCmd_ACT_GEN_SET, 0, &mode)) 754 HostCmd_ACT_GEN_SET, 0, &mode, true))
757 return -1; 755 return -1;
758 756
759 if (GET_BSS_ROLE(priv) != MWIFIEX_BSS_ROLE_UAP) 757 if (GET_BSS_ROLE(priv) != MWIFIEX_BSS_ROLE_UAP)
@@ -853,8 +851,8 @@ mwifiex_cfg80211_change_virtual_intf(struct wiphy *wiphy,
853 851
854 priv->sec_info.authentication_mode = NL80211_AUTHTYPE_OPEN_SYSTEM; 852 priv->sec_info.authentication_mode = NL80211_AUTHTYPE_OPEN_SYSTEM;
855 853
856 ret = mwifiex_send_cmd_sync(priv, HostCmd_CMD_SET_BSS_MODE, 854 ret = mwifiex_send_cmd(priv, HostCmd_CMD_SET_BSS_MODE,
857 HostCmd_ACT_GEN_SET, 0, NULL); 855 HostCmd_ACT_GEN_SET, 0, NULL, true);
858 856
859 return ret; 857 return ret;
860} 858}
@@ -942,8 +940,8 @@ mwifiex_dump_station_info(struct mwifiex_private *priv,
942 STATION_INFO_SIGNAL | STATION_INFO_SIGNAL_AVG; 940 STATION_INFO_SIGNAL | STATION_INFO_SIGNAL_AVG;
943 941
944 /* Get signal information from the firmware */ 942 /* Get signal information from the firmware */
945 if (mwifiex_send_cmd_sync(priv, HostCmd_CMD_RSSI_INFO, 943 if (mwifiex_send_cmd(priv, HostCmd_CMD_RSSI_INFO,
946 HostCmd_ACT_GEN_GET, 0, NULL)) { 944 HostCmd_ACT_GEN_GET, 0, NULL, true)) {
947 dev_err(priv->adapter->dev, "failed to get signal information\n"); 945 dev_err(priv->adapter->dev, "failed to get signal information\n");
948 return -EFAULT; 946 return -EFAULT;
949 } 947 }
@@ -954,9 +952,9 @@ mwifiex_dump_station_info(struct mwifiex_private *priv,
954 } 952 }
955 953
956 /* Get DTIM period information from firmware */ 954 /* Get DTIM period information from firmware */
957 mwifiex_send_cmd_sync(priv, HostCmd_CMD_802_11_SNMP_MIB, 955 mwifiex_send_cmd(priv, HostCmd_CMD_802_11_SNMP_MIB,
958 HostCmd_ACT_GEN_GET, DTIM_PERIOD_I, 956 HostCmd_ACT_GEN_GET, DTIM_PERIOD_I,
959 &priv->dtim_period); 957 &priv->dtim_period, true);
960 958
961 mwifiex_parse_htinfo(priv, priv->tx_htinfo, &sinfo->txrate); 959 mwifiex_parse_htinfo(priv, priv->tx_htinfo, &sinfo->txrate);
962 960
@@ -1160,9 +1158,10 @@ static int mwifiex_cfg80211_set_bitrate_mask(struct wiphy *wiphy,
1160 struct mwifiex_private *priv = mwifiex_netdev_get_priv(dev); 1158 struct mwifiex_private *priv = mwifiex_netdev_get_priv(dev);
1161 u16 bitmap_rates[MAX_BITMAP_RATES_SIZE]; 1159 u16 bitmap_rates[MAX_BITMAP_RATES_SIZE];
1162 enum ieee80211_band band; 1160 enum ieee80211_band band;
1161 struct mwifiex_adapter *adapter = priv->adapter;
1163 1162
1164 if (!priv->media_connected) { 1163 if (!priv->media_connected) {
1165 dev_err(priv->adapter->dev, 1164 dev_err(adapter->dev,
1166 "Can not set Tx data rate in disconnected state\n"); 1165 "Can not set Tx data rate in disconnected state\n");
1167 return -EINVAL; 1166 return -EINVAL;
1168 } 1167 }
@@ -1183,11 +1182,18 @@ static int mwifiex_cfg80211_set_bitrate_mask(struct wiphy *wiphy,
1183 1182
1184 /* Fill HT MCS rates */ 1183 /* Fill HT MCS rates */
1185 bitmap_rates[2] = mask->control[band].ht_mcs[0]; 1184 bitmap_rates[2] = mask->control[band].ht_mcs[0];
1186 if (priv->adapter->hw_dev_mcs_support == HT_STREAM_2X2) 1185 if (adapter->hw_dev_mcs_support == HT_STREAM_2X2)
1187 bitmap_rates[2] |= mask->control[band].ht_mcs[1] << 8; 1186 bitmap_rates[2] |= mask->control[band].ht_mcs[1] << 8;
1188 1187
1189 return mwifiex_send_cmd_sync(priv, HostCmd_CMD_TX_RATE_CFG, 1188 /* Fill VHT MCS rates */
1190 HostCmd_ACT_GEN_SET, 0, bitmap_rates); 1189 if (adapter->fw_api_ver == MWIFIEX_FW_V15) {
1190 bitmap_rates[10] = mask->control[band].vht_mcs[0];
1191 if (adapter->hw_dev_mcs_support == HT_STREAM_2X2)
1192 bitmap_rates[11] = mask->control[band].vht_mcs[1];
1193 }
1194
1195 return mwifiex_send_cmd(priv, HostCmd_CMD_TX_RATE_CFG,
1196 HostCmd_ACT_GEN_SET, 0, bitmap_rates, true);
1191} 1197}
1192 1198
1193/* 1199/*
@@ -1216,14 +1222,14 @@ static int mwifiex_cfg80211_set_cqm_rssi_config(struct wiphy *wiphy,
1216 subsc_evt.bcn_h_rssi_cfg.abs_value = abs(rssi_thold); 1222 subsc_evt.bcn_h_rssi_cfg.abs_value = abs(rssi_thold);
1217 subsc_evt.bcn_l_rssi_cfg.evt_freq = 1; 1223 subsc_evt.bcn_l_rssi_cfg.evt_freq = 1;
1218 subsc_evt.bcn_h_rssi_cfg.evt_freq = 1; 1224 subsc_evt.bcn_h_rssi_cfg.evt_freq = 1;
1219 return mwifiex_send_cmd_sync(priv, 1225 return mwifiex_send_cmd(priv,
1220 HostCmd_CMD_802_11_SUBSCRIBE_EVENT, 1226 HostCmd_CMD_802_11_SUBSCRIBE_EVENT,
1221 0, 0, &subsc_evt); 1227 0, 0, &subsc_evt, true);
1222 } else { 1228 } else {
1223 subsc_evt.action = HostCmd_ACT_BITWISE_CLR; 1229 subsc_evt.action = HostCmd_ACT_BITWISE_CLR;
1224 return mwifiex_send_cmd_sync(priv, 1230 return mwifiex_send_cmd(priv,
1225 HostCmd_CMD_802_11_SUBSCRIBE_EVENT, 1231 HostCmd_CMD_802_11_SUBSCRIBE_EVENT,
1226 0, 0, &subsc_evt); 1232 0, 0, &subsc_evt, true);
1227 } 1233 }
1228 1234
1229 return 0; 1235 return 0;
@@ -1276,10 +1282,9 @@ mwifiex_cfg80211_del_station(struct wiphy *wiphy, struct net_device *dev,
1276 if (!mac || is_broadcast_ether_addr(mac)) { 1282 if (!mac || is_broadcast_ether_addr(mac)) {
1277 wiphy_dbg(wiphy, "%s: NULL/broadcast mac address\n", __func__); 1283 wiphy_dbg(wiphy, "%s: NULL/broadcast mac address\n", __func__);
1278 list_for_each_entry(sta_node, &priv->sta_list, list) { 1284 list_for_each_entry(sta_node, &priv->sta_list, list) {
1279 if (mwifiex_send_cmd_sync(priv, 1285 if (mwifiex_send_cmd(priv, HostCmd_CMD_UAP_STA_DEAUTH,
1280 HostCmd_CMD_UAP_STA_DEAUTH, 1286 HostCmd_ACT_GEN_SET, 0,
1281 HostCmd_ACT_GEN_SET, 0, 1287 sta_node->mac_addr, true))
1282 sta_node->mac_addr))
1283 return -1; 1288 return -1;
1284 mwifiex_uap_del_sta_data(priv, sta_node); 1289 mwifiex_uap_del_sta_data(priv, sta_node);
1285 } 1290 }
@@ -1289,10 +1294,9 @@ mwifiex_cfg80211_del_station(struct wiphy *wiphy, struct net_device *dev,
1289 sta_node = mwifiex_get_sta_entry(priv, mac); 1294 sta_node = mwifiex_get_sta_entry(priv, mac);
1290 spin_unlock_irqrestore(&priv->sta_list_spinlock, flags); 1295 spin_unlock_irqrestore(&priv->sta_list_spinlock, flags);
1291 if (sta_node) { 1296 if (sta_node) {
1292 if (mwifiex_send_cmd_sync(priv, 1297 if (mwifiex_send_cmd(priv, HostCmd_CMD_UAP_STA_DEAUTH,
1293 HostCmd_CMD_UAP_STA_DEAUTH, 1298 HostCmd_ACT_GEN_SET, 0,
1294 HostCmd_ACT_GEN_SET, 0, 1299 sta_node->mac_addr, true))
1295 sta_node->mac_addr))
1296 return -1; 1300 return -1;
1297 mwifiex_uap_del_sta_data(priv, sta_node); 1301 mwifiex_uap_del_sta_data(priv, sta_node);
1298 } 1302 }
@@ -1328,13 +1332,40 @@ mwifiex_cfg80211_set_antenna(struct wiphy *wiphy, u32 tx_ant, u32 rx_ant)
1328 tx_ant = RF_ANTENNA_AUTO; 1332 tx_ant = RF_ANTENNA_AUTO;
1329 rx_ant = RF_ANTENNA_AUTO; 1333 rx_ant = RF_ANTENNA_AUTO;
1330 } 1334 }
1335 } else {
1336 struct ieee80211_sta_ht_cap *ht_info;
1337 int rx_mcs_supp;
1338 enum ieee80211_band band;
1339
1340 if ((tx_ant == 0x1 && rx_ant == 0x1)) {
1341 adapter->user_dev_mcs_support = HT_STREAM_1X1;
1342 if (adapter->is_hw_11ac_capable)
1343 adapter->usr_dot_11ac_mcs_support =
1344 MWIFIEX_11AC_MCS_MAP_1X1;
1345 } else {
1346 adapter->user_dev_mcs_support = HT_STREAM_2X2;
1347 if (adapter->is_hw_11ac_capable)
1348 adapter->usr_dot_11ac_mcs_support =
1349 MWIFIEX_11AC_MCS_MAP_2X2;
1350 }
1351
1352 for (band = 0; band < IEEE80211_NUM_BANDS; band++) {
1353 if (!adapter->wiphy->bands[band])
1354 continue;
1355
1356 ht_info = &adapter->wiphy->bands[band]->ht_cap;
1357 rx_mcs_supp =
1358 GET_RXMCSSUPP(adapter->user_dev_mcs_support);
1359 memset(&ht_info->mcs, 0, adapter->number_of_antenna);
1360 memset(&ht_info->mcs, 0xff, rx_mcs_supp);
1361 }
1331 } 1362 }
1332 1363
1333 ant_cfg.tx_ant = tx_ant; 1364 ant_cfg.tx_ant = tx_ant;
1334 ant_cfg.rx_ant = rx_ant; 1365 ant_cfg.rx_ant = rx_ant;
1335 1366
1336 return mwifiex_send_cmd_sync(priv, HostCmd_CMD_RF_ANTENNA, 1367 return mwifiex_send_cmd(priv, HostCmd_CMD_RF_ANTENNA,
1337 HostCmd_ACT_GEN_SET, 0, &ant_cfg); 1368 HostCmd_ACT_GEN_SET, 0, &ant_cfg, true);
1338} 1369}
1339 1370
1340/* cfg80211 operation handler for stop ap. 1371/* cfg80211 operation handler for stop ap.
@@ -1349,8 +1380,8 @@ static int mwifiex_cfg80211_stop_ap(struct wiphy *wiphy, struct net_device *dev)
1349 1380
1350 priv->ap_11n_enabled = 0; 1381 priv->ap_11n_enabled = 0;
1351 1382
1352 if (mwifiex_send_cmd_sync(priv, HostCmd_CMD_UAP_BSS_STOP, 1383 if (mwifiex_send_cmd(priv, HostCmd_CMD_UAP_BSS_STOP,
1353 HostCmd_ACT_GEN_SET, 0, NULL)) { 1384 HostCmd_ACT_GEN_SET, 0, NULL, true)) {
1354 wiphy_err(wiphy, "Failed to stop the BSS\n"); 1385 wiphy_err(wiphy, "Failed to stop the BSS\n");
1355 return -1; 1386 return -1;
1356 } 1387 }
@@ -1416,9 +1447,6 @@ static int mwifiex_cfg80211_start_ap(struct wiphy *wiphy,
1416 1447
1417 if (params->chandef.width > NL80211_CHAN_WIDTH_20_NOHT) 1448 if (params->chandef.width > NL80211_CHAN_WIDTH_20_NOHT)
1418 config_bands |= BAND_GN; 1449 config_bands |= BAND_GN;
1419
1420 if (params->chandef.width > NL80211_CHAN_WIDTH_40)
1421 config_bands |= BAND_GAC;
1422 } else { 1450 } else {
1423 bss_cfg->band_cfg = BAND_CONFIG_A; 1451 bss_cfg->band_cfg = BAND_CONFIG_A;
1424 config_bands = BAND_A; 1452 config_bands = BAND_A;
@@ -1464,16 +1492,16 @@ static int mwifiex_cfg80211_start_ap(struct wiphy *wiphy,
1464 bss_cfg->ps_sta_ao_timer = 10 * params->inactivity_timeout; 1492 bss_cfg->ps_sta_ao_timer = 10 * params->inactivity_timeout;
1465 } 1493 }
1466 1494
1467 if (mwifiex_send_cmd_sync(priv, HostCmd_CMD_UAP_BSS_STOP, 1495 if (mwifiex_send_cmd(priv, HostCmd_CMD_UAP_BSS_STOP,
1468 HostCmd_ACT_GEN_SET, 0, NULL)) { 1496 HostCmd_ACT_GEN_SET, 0, NULL, true)) {
1469 wiphy_err(wiphy, "Failed to stop the BSS\n"); 1497 wiphy_err(wiphy, "Failed to stop the BSS\n");
1470 kfree(bss_cfg); 1498 kfree(bss_cfg);
1471 return -1; 1499 return -1;
1472 } 1500 }
1473 1501
1474 if (mwifiex_send_cmd_async(priv, HostCmd_CMD_UAP_SYS_CONFIG, 1502 if (mwifiex_send_cmd(priv, HostCmd_CMD_UAP_SYS_CONFIG,
1475 HostCmd_ACT_GEN_SET, 1503 HostCmd_ACT_GEN_SET,
1476 UAP_BSS_PARAMS_I, bss_cfg)) { 1504 UAP_BSS_PARAMS_I, bss_cfg, false)) {
1477 wiphy_err(wiphy, "Failed to set the SSID\n"); 1505 wiphy_err(wiphy, "Failed to set the SSID\n");
1478 kfree(bss_cfg); 1506 kfree(bss_cfg);
1479 return -1; 1507 return -1;
@@ -1481,8 +1509,8 @@ static int mwifiex_cfg80211_start_ap(struct wiphy *wiphy,
1481 1509
1482 kfree(bss_cfg); 1510 kfree(bss_cfg);
1483 1511
1484 if (mwifiex_send_cmd_async(priv, HostCmd_CMD_UAP_BSS_START, 1512 if (mwifiex_send_cmd(priv, HostCmd_CMD_UAP_BSS_START,
1485 HostCmd_ACT_GEN_SET, 0, NULL)) { 1513 HostCmd_ACT_GEN_SET, 0, NULL, false)) {
1486 wiphy_err(wiphy, "Failed to start the BSS\n"); 1514 wiphy_err(wiphy, "Failed to start the BSS\n");
1487 return -1; 1515 return -1;
1488 } 1516 }
@@ -1492,9 +1520,9 @@ static int mwifiex_cfg80211_start_ap(struct wiphy *wiphy,
1492 else 1520 else
1493 priv->curr_pkt_filter &= ~HostCmd_ACT_MAC_WEP_ENABLE; 1521 priv->curr_pkt_filter &= ~HostCmd_ACT_MAC_WEP_ENABLE;
1494 1522
1495 if (mwifiex_send_cmd_sync(priv, HostCmd_CMD_MAC_CONTROL, 1523 if (mwifiex_send_cmd(priv, HostCmd_CMD_MAC_CONTROL,
1496 HostCmd_ACT_GEN_SET, 0, 1524 HostCmd_ACT_GEN_SET, 0,
1497 &priv->curr_pkt_filter)) 1525 &priv->curr_pkt_filter, true))
1498 return -1; 1526 return -1;
1499 1527
1500 return 0; 1528 return 0;
@@ -1583,8 +1611,9 @@ static int mwifiex_cfg80211_inform_ibss_bss(struct mwifiex_private *priv)
1583 * the function notifies the CFG802.11 subsystem of the new BSS connection. 1611 * the function notifies the CFG802.11 subsystem of the new BSS connection.
1584 */ 1612 */
1585static int 1613static int
1586mwifiex_cfg80211_assoc(struct mwifiex_private *priv, size_t ssid_len, u8 *ssid, 1614mwifiex_cfg80211_assoc(struct mwifiex_private *priv, size_t ssid_len,
1587 u8 *bssid, int mode, struct ieee80211_channel *channel, 1615 const u8 *ssid, const u8 *bssid, int mode,
1616 struct ieee80211_channel *channel,
1588 struct cfg80211_connect_params *sme, bool privacy) 1617 struct cfg80211_connect_params *sme, bool privacy)
1589{ 1618{
1590 struct cfg80211_ssid req_ssid; 1619 struct cfg80211_ssid req_ssid;
@@ -1881,7 +1910,8 @@ mwifiex_cfg80211_join_ibss(struct wiphy *wiphy, struct net_device *dev,
1881 params->privacy); 1910 params->privacy);
1882done: 1911done:
1883 if (!ret) { 1912 if (!ret) {
1884 cfg80211_ibss_joined(priv->netdev, priv->cfg_bssid, GFP_KERNEL); 1913 cfg80211_ibss_joined(priv->netdev, priv->cfg_bssid,
1914 params->chandef.chan, GFP_KERNEL);
1885 dev_dbg(priv->adapter->dev, 1915 dev_dbg(priv->adapter->dev,
1886 "info: joined/created adhoc network with bssid" 1916 "info: joined/created adhoc network with bssid"
1887 " %pM successfully\n", priv->cfg_bssid); 1917 " %pM successfully\n", priv->cfg_bssid);
@@ -2070,10 +2100,10 @@ mwifiex_setup_ht_caps(struct ieee80211_sta_ht_cap *ht_info,
2070 else 2100 else
2071 ht_info->cap &= ~IEEE80211_HT_CAP_SGI_40; 2101 ht_info->cap &= ~IEEE80211_HT_CAP_SGI_40;
2072 2102
2073 if (ISSUPP_RXSTBC(adapter->hw_dot_11n_dev_cap)) 2103 if (adapter->user_dev_mcs_support == HT_STREAM_2X2)
2074 ht_info->cap |= 1 << IEEE80211_HT_CAP_RX_STBC_SHIFT; 2104 ht_info->cap |= 3 << IEEE80211_HT_CAP_RX_STBC_SHIFT;
2075 else 2105 else
2076 ht_info->cap &= ~(3 << IEEE80211_HT_CAP_RX_STBC_SHIFT); 2106 ht_info->cap |= 1 << IEEE80211_HT_CAP_RX_STBC_SHIFT;
2077 2107
2078 if (ISSUPP_TXSTBC(adapter->hw_dot_11n_dev_cap)) 2108 if (ISSUPP_TXSTBC(adapter->hw_dot_11n_dev_cap))
2079 ht_info->cap |= IEEE80211_HT_CAP_TX_STBC; 2109 ht_info->cap |= IEEE80211_HT_CAP_TX_STBC;
@@ -2098,8 +2128,8 @@ mwifiex_setup_ht_caps(struct ieee80211_sta_ht_cap *ht_info,
2098 ht_info->cap &= ~IEEE80211_HT_CAP_MAX_AMSDU; 2128 ht_info->cap &= ~IEEE80211_HT_CAP_MAX_AMSDU;
2099 ht_info->cap |= IEEE80211_HT_CAP_SM_PS; 2129 ht_info->cap |= IEEE80211_HT_CAP_SM_PS;
2100 2130
2101 rx_mcs_supp = GET_RXMCSSUPP(adapter->hw_dev_mcs_support); 2131 rx_mcs_supp = GET_RXMCSSUPP(adapter->user_dev_mcs_support);
2102 /* Set MCS for 1x1 */ 2132 /* Set MCS for 1x1/2x2 */
2103 memset(mcs, 0xff, rx_mcs_supp); 2133 memset(mcs, 0xff, rx_mcs_supp);
2104 /* Clear all the other values */ 2134 /* Clear all the other values */
2105 memset(&mcs[rx_mcs_supp], 0, 2135 memset(&mcs[rx_mcs_supp], 0,
@@ -2460,9 +2490,8 @@ static int mwifiex_cfg80211_suspend(struct wiphy *wiphy,
2460 MWIFIEX_CRITERIA_UNICAST | 2490 MWIFIEX_CRITERIA_UNICAST |
2461 MWIFIEX_CRITERIA_MULTICAST; 2491 MWIFIEX_CRITERIA_MULTICAST;
2462 2492
2463 ret = mwifiex_send_cmd_sync(priv, HostCmd_CMD_MEF_CFG, 2493 ret = mwifiex_send_cmd(priv, HostCmd_CMD_MEF_CFG,
2464 HostCmd_ACT_GEN_SET, 0, 2494 HostCmd_ACT_GEN_SET, 0, &mef_cfg, true);
2465 &mef_cfg);
2466 2495
2467 kfree(mef_entry); 2496 kfree(mef_entry);
2468 return ret; 2497 return ret;
@@ -2574,9 +2603,9 @@ static int mwifiex_cfg80211_set_coalesce(struct wiphy *wiphy,
2574 if (!coalesce) { 2603 if (!coalesce) {
2575 dev_dbg(adapter->dev, 2604 dev_dbg(adapter->dev,
2576 "Disable coalesce and reset all previous rules\n"); 2605 "Disable coalesce and reset all previous rules\n");
2577 return mwifiex_send_cmd_sync(priv, HostCmd_CMD_COALESCE_CFG, 2606 return mwifiex_send_cmd(priv, HostCmd_CMD_COALESCE_CFG,
2578 HostCmd_ACT_GEN_SET, 0, 2607 HostCmd_ACT_GEN_SET, 0,
2579 &coalesce_cfg); 2608 &coalesce_cfg, true);
2580 } 2609 }
2581 2610
2582 coalesce_cfg.num_of_rules = coalesce->n_rules; 2611 coalesce_cfg.num_of_rules = coalesce->n_rules;
@@ -2591,8 +2620,172 @@ static int mwifiex_cfg80211_set_coalesce(struct wiphy *wiphy,
2591 } 2620 }
2592 } 2621 }
2593 2622
2594 return mwifiex_send_cmd_sync(priv, HostCmd_CMD_COALESCE_CFG, 2623 return mwifiex_send_cmd(priv, HostCmd_CMD_COALESCE_CFG,
2595 HostCmd_ACT_GEN_SET, 0, &coalesce_cfg); 2624 HostCmd_ACT_GEN_SET, 0, &coalesce_cfg, true);
2625}
2626
2627/* cfg80211 ops handler for tdls_mgmt.
2628 * Function prepares TDLS action frame packets and forwards them to FW
2629 */
2630static int
2631mwifiex_cfg80211_tdls_mgmt(struct wiphy *wiphy, struct net_device *dev,
2632 u8 *peer, u8 action_code, u8 dialog_token,
2633 u16 status_code, u32 peer_capability,
2634 const u8 *extra_ies, size_t extra_ies_len)
2635{
2636 struct mwifiex_private *priv = mwifiex_netdev_get_priv(dev);
2637 int ret;
2638
2639 if (!(wiphy->flags & WIPHY_FLAG_SUPPORTS_TDLS))
2640 return -ENOTSUPP;
2641
2642 /* make sure we are in station mode and connected */
2643 if (!(priv->bss_type == MWIFIEX_BSS_TYPE_STA && priv->media_connected))
2644 return -ENOTSUPP;
2645
2646 switch (action_code) {
2647 case WLAN_TDLS_SETUP_REQUEST:
2648 dev_dbg(priv->adapter->dev,
2649 "Send TDLS Setup Request to %pM status_code=%d\n", peer,
2650 status_code);
2651 ret = mwifiex_send_tdls_data_frame(priv, peer, action_code,
2652 dialog_token, status_code,
2653 extra_ies, extra_ies_len);
2654 break;
2655 case WLAN_TDLS_SETUP_RESPONSE:
2656 dev_dbg(priv->adapter->dev,
2657 "Send TDLS Setup Response to %pM status_code=%d\n",
2658 peer, status_code);
2659 ret = mwifiex_send_tdls_data_frame(priv, peer, action_code,
2660 dialog_token, status_code,
2661 extra_ies, extra_ies_len);
2662 break;
2663 case WLAN_TDLS_SETUP_CONFIRM:
2664 dev_dbg(priv->adapter->dev,
2665 "Send TDLS Confirm to %pM status_code=%d\n", peer,
2666 status_code);
2667 ret = mwifiex_send_tdls_data_frame(priv, peer, action_code,
2668 dialog_token, status_code,
2669 extra_ies, extra_ies_len);
2670 break;
2671 case WLAN_TDLS_TEARDOWN:
2672 dev_dbg(priv->adapter->dev, "Send TDLS Tear down to %pM\n",
2673 peer);
2674 ret = mwifiex_send_tdls_data_frame(priv, peer, action_code,
2675 dialog_token, status_code,
2676 extra_ies, extra_ies_len);
2677 break;
2678 case WLAN_TDLS_DISCOVERY_REQUEST:
2679 dev_dbg(priv->adapter->dev,
2680 "Send TDLS Discovery Request to %pM\n", peer);
2681 ret = mwifiex_send_tdls_data_frame(priv, peer, action_code,
2682 dialog_token, status_code,
2683 extra_ies, extra_ies_len);
2684 break;
2685 case WLAN_PUB_ACTION_TDLS_DISCOVER_RES:
2686 dev_dbg(priv->adapter->dev,
2687 "Send TDLS Discovery Response to %pM\n", peer);
2688 ret = mwifiex_send_tdls_action_frame(priv, peer, action_code,
2689 dialog_token, status_code,
2690 extra_ies, extra_ies_len);
2691 break;
2692 default:
2693 dev_warn(priv->adapter->dev,
2694 "Unknown TDLS mgmt/action frame %pM\n", peer);
2695 ret = -EINVAL;
2696 break;
2697 }
2698
2699 return ret;
2700}
2701
2702static int
2703mwifiex_cfg80211_tdls_oper(struct wiphy *wiphy, struct net_device *dev,
2704 u8 *peer, enum nl80211_tdls_operation action)
2705{
2706 struct mwifiex_private *priv = mwifiex_netdev_get_priv(dev);
2707
2708 if (!(wiphy->flags & WIPHY_FLAG_SUPPORTS_TDLS) ||
2709 !(wiphy->flags & WIPHY_FLAG_TDLS_EXTERNAL_SETUP))
2710 return -ENOTSUPP;
2711
2712 /* make sure we are in station mode and connected */
2713 if (!(priv->bss_type == MWIFIEX_BSS_TYPE_STA && priv->media_connected))
2714 return -ENOTSUPP;
2715
2716 dev_dbg(priv->adapter->dev,
2717 "TDLS peer=%pM, oper=%d\n", peer, action);
2718
2719 switch (action) {
2720 case NL80211_TDLS_ENABLE_LINK:
2721 action = MWIFIEX_TDLS_ENABLE_LINK;
2722 break;
2723 case NL80211_TDLS_DISABLE_LINK:
2724 action = MWIFIEX_TDLS_DISABLE_LINK;
2725 break;
2726 case NL80211_TDLS_TEARDOWN:
2727 /* shouldn't happen!*/
2728 dev_warn(priv->adapter->dev,
2729 "tdls_oper: teardown from driver not supported\n");
2730 return -EINVAL;
2731 case NL80211_TDLS_SETUP:
2732 /* shouldn't happen!*/
2733 dev_warn(priv->adapter->dev,
2734 "tdls_oper: setup from driver not supported\n");
2735 return -EINVAL;
2736 case NL80211_TDLS_DISCOVERY_REQ:
2737 /* shouldn't happen!*/
2738 dev_warn(priv->adapter->dev,
2739 "tdls_oper: discovery from driver not supported\n");
2740 return -EINVAL;
2741 default:
2742 dev_err(priv->adapter->dev,
2743 "tdls_oper: operation not supported\n");
2744 return -ENOTSUPP;
2745 }
2746
2747 return mwifiex_tdls_oper(priv, peer, action);
2748}
2749
2750static int
2751mwifiex_cfg80211_add_station(struct wiphy *wiphy,
2752 struct net_device *dev,
2753 u8 *mac, struct station_parameters *params)
2754{
2755 struct mwifiex_private *priv = mwifiex_netdev_get_priv(dev);
2756
2757 if (!(params->sta_flags_set & BIT(NL80211_STA_FLAG_TDLS_PEER)))
2758 return -ENOTSUPP;
2759
2760 /* make sure we are in station mode and connected */
2761 if ((priv->bss_type != MWIFIEX_BSS_TYPE_STA) || !priv->media_connected)
2762 return -ENOTSUPP;
2763
2764 return mwifiex_tdls_oper(priv, mac, MWIFIEX_TDLS_CREATE_LINK);
2765}
2766
2767static int
2768mwifiex_cfg80211_change_station(struct wiphy *wiphy,
2769 struct net_device *dev,
2770 u8 *mac, struct station_parameters *params)
2771{
2772 int ret;
2773 struct mwifiex_private *priv = mwifiex_netdev_get_priv(dev);
2774
2775 /* we support change_station handler only for TDLS peers*/
2776 if (!(params->sta_flags_set & BIT(NL80211_STA_FLAG_TDLS_PEER)))
2777 return -ENOTSUPP;
2778
2779 /* make sure we are in station mode and connected */
2780 if ((priv->bss_type != MWIFIEX_BSS_TYPE_STA) || !priv->media_connected)
2781 return -ENOTSUPP;
2782
2783 priv->sta_params = params;
2784
2785 ret = mwifiex_tdls_oper(priv, mac, MWIFIEX_TDLS_CONFIG_LINK);
2786 priv->sta_params = NULL;
2787
2788 return ret;
2596} 2789}
2597 2790
2598/* station cfg80211 operations */ 2791/* station cfg80211 operations */
@@ -2630,6 +2823,10 @@ static struct cfg80211_ops mwifiex_cfg80211_ops = {
2630 .set_wakeup = mwifiex_cfg80211_set_wakeup, 2823 .set_wakeup = mwifiex_cfg80211_set_wakeup,
2631#endif 2824#endif
2632 .set_coalesce = mwifiex_cfg80211_set_coalesce, 2825 .set_coalesce = mwifiex_cfg80211_set_coalesce,
2826 .tdls_mgmt = mwifiex_cfg80211_tdls_mgmt,
2827 .tdls_oper = mwifiex_cfg80211_tdls_oper,
2828 .add_station = mwifiex_cfg80211_add_station,
2829 .change_station = mwifiex_cfg80211_change_station,
2633}; 2830};
2634 2831
2635#ifdef CONFIG_PM 2832#ifdef CONFIG_PM
@@ -2715,6 +2912,11 @@ int mwifiex_register_cfg80211(struct mwifiex_adapter *adapter)
2715 WIPHY_FLAG_AP_PROBE_RESP_OFFLOAD | 2912 WIPHY_FLAG_AP_PROBE_RESP_OFFLOAD |
2716 WIPHY_FLAG_AP_UAPSD | 2913 WIPHY_FLAG_AP_UAPSD |
2717 WIPHY_FLAG_HAS_REMAIN_ON_CHANNEL; 2914 WIPHY_FLAG_HAS_REMAIN_ON_CHANNEL;
2915
2916 if (ISSUPP_TDLS_ENABLED(adapter->fw_cap_info))
2917 wiphy->flags |= WIPHY_FLAG_SUPPORTS_TDLS |
2918 WIPHY_FLAG_TDLS_EXTERNAL_SETUP;
2919
2718 wiphy->regulatory_flags |= 2920 wiphy->regulatory_flags |=
2719 REGULATORY_CUSTOM_REG | 2921 REGULATORY_CUSTOM_REG |
2720 REGULATORY_STRICT_REG; 2922 REGULATORY_STRICT_REG;
@@ -2736,7 +2938,8 @@ int mwifiex_register_cfg80211(struct mwifiex_adapter *adapter)
2736 2938
2737 wiphy->features |= NL80211_FEATURE_HT_IBSS | 2939 wiphy->features |= NL80211_FEATURE_HT_IBSS |
2738 NL80211_FEATURE_INACTIVITY_TIMER | 2940 NL80211_FEATURE_INACTIVITY_TIMER |
2739 NL80211_FEATURE_LOW_PRIORITY_SCAN; 2941 NL80211_FEATURE_LOW_PRIORITY_SCAN |
2942 NL80211_FEATURE_NEED_OBSS_SCAN;
2740 2943
2741 /* Reserve space for mwifiex specific private data for BSS */ 2944 /* Reserve space for mwifiex specific private data for BSS */
2742 wiphy->bss_priv_size = sizeof(struct mwifiex_bss_priv); 2945 wiphy->bss_priv_size = sizeof(struct mwifiex_bss_priv);
@@ -2767,17 +2970,17 @@ int mwifiex_register_cfg80211(struct mwifiex_adapter *adapter)
2767 country_code); 2970 country_code);
2768 } 2971 }
2769 2972
2770 mwifiex_send_cmd_sync(priv, HostCmd_CMD_802_11_SNMP_MIB, 2973 mwifiex_send_cmd(priv, HostCmd_CMD_802_11_SNMP_MIB,
2771 HostCmd_ACT_GEN_GET, FRAG_THRESH_I, &thr); 2974 HostCmd_ACT_GEN_GET, FRAG_THRESH_I, &thr, true);
2772 wiphy->frag_threshold = thr; 2975 wiphy->frag_threshold = thr;
2773 mwifiex_send_cmd_sync(priv, HostCmd_CMD_802_11_SNMP_MIB, 2976 mwifiex_send_cmd(priv, HostCmd_CMD_802_11_SNMP_MIB,
2774 HostCmd_ACT_GEN_GET, RTS_THRESH_I, &thr); 2977 HostCmd_ACT_GEN_GET, RTS_THRESH_I, &thr, true);
2775 wiphy->rts_threshold = thr; 2978 wiphy->rts_threshold = thr;
2776 mwifiex_send_cmd_sync(priv, HostCmd_CMD_802_11_SNMP_MIB, 2979 mwifiex_send_cmd(priv, HostCmd_CMD_802_11_SNMP_MIB,
2777 HostCmd_ACT_GEN_GET, SHORT_RETRY_LIM_I, &retry); 2980 HostCmd_ACT_GEN_GET, SHORT_RETRY_LIM_I, &retry, true);
2778 wiphy->retry_short = (u8) retry; 2981 wiphy->retry_short = (u8) retry;
2779 mwifiex_send_cmd_sync(priv, HostCmd_CMD_802_11_SNMP_MIB, 2982 mwifiex_send_cmd(priv, HostCmd_CMD_802_11_SNMP_MIB,
2780 HostCmd_ACT_GEN_GET, LONG_RETRY_LIM_I, &retry); 2983 HostCmd_ACT_GEN_GET, LONG_RETRY_LIM_I, &retry, true);
2781 wiphy->retry_long = (u8) retry; 2984 wiphy->retry_long = (u8) retry;
2782 2985
2783 adapter->wiphy = wiphy; 2986 adapter->wiphy = wiphy;