0001
0002
0003
0004
0005
0006
0007 #include "cfg80211.h"
0008
0009 #define GO_NEG_REQ 0x00
0010 #define GO_NEG_RSP 0x01
0011 #define GO_NEG_CONF 0x02
0012 #define P2P_INV_REQ 0x03
0013 #define P2P_INV_RSP 0x04
0014
0015 #define WILC_INVALID_CHANNEL 0
0016
0017
0018 #define WILC_WLAN_OPERATING_CLASS_2_4GHZ 0x51
0019
0020 static const struct ieee80211_txrx_stypes
0021 wilc_wfi_cfg80211_mgmt_types[NUM_NL80211_IFTYPES] = {
0022 [NL80211_IFTYPE_STATION] = {
0023 .tx = BIT(IEEE80211_STYPE_ACTION >> 4) |
0024 BIT(IEEE80211_STYPE_AUTH >> 4),
0025 .rx = BIT(IEEE80211_STYPE_ACTION >> 4) |
0026 BIT(IEEE80211_STYPE_PROBE_REQ >> 4) |
0027 BIT(IEEE80211_STYPE_AUTH >> 4)
0028 },
0029 [NL80211_IFTYPE_AP] = {
0030 .tx = 0xffff,
0031 .rx = BIT(IEEE80211_STYPE_ASSOC_REQ >> 4) |
0032 BIT(IEEE80211_STYPE_REASSOC_REQ >> 4) |
0033 BIT(IEEE80211_STYPE_PROBE_REQ >> 4) |
0034 BIT(IEEE80211_STYPE_DISASSOC >> 4) |
0035 BIT(IEEE80211_STYPE_AUTH >> 4) |
0036 BIT(IEEE80211_STYPE_DEAUTH >> 4) |
0037 BIT(IEEE80211_STYPE_ACTION >> 4)
0038 },
0039 [NL80211_IFTYPE_P2P_CLIENT] = {
0040 .tx = 0xffff,
0041 .rx = BIT(IEEE80211_STYPE_ACTION >> 4) |
0042 BIT(IEEE80211_STYPE_PROBE_REQ >> 4) |
0043 BIT(IEEE80211_STYPE_ASSOC_REQ >> 4) |
0044 BIT(IEEE80211_STYPE_REASSOC_REQ >> 4) |
0045 BIT(IEEE80211_STYPE_DISASSOC >> 4) |
0046 BIT(IEEE80211_STYPE_AUTH >> 4) |
0047 BIT(IEEE80211_STYPE_DEAUTH >> 4)
0048 }
0049 };
0050
0051 #ifdef CONFIG_PM
0052 static const struct wiphy_wowlan_support wowlan_support = {
0053 .flags = WIPHY_WOWLAN_ANY
0054 };
0055 #endif
0056
0057 struct wilc_p2p_mgmt_data {
0058 int size;
0059 u8 *buff;
0060 };
0061
0062 struct wilc_p2p_pub_act_frame {
0063 u8 category;
0064 u8 action;
0065 u8 oui[3];
0066 u8 oui_type;
0067 u8 oui_subtype;
0068 u8 dialog_token;
0069 u8 elem[];
0070 } __packed;
0071
0072 struct wilc_vendor_specific_ie {
0073 u8 tag_number;
0074 u8 tag_len;
0075 u8 oui[3];
0076 u8 oui_type;
0077 u8 attr[];
0078 } __packed;
0079
0080 struct wilc_attr_entry {
0081 u8 attr_type;
0082 __le16 attr_len;
0083 u8 val[];
0084 } __packed;
0085
0086 struct wilc_attr_oper_ch {
0087 u8 attr_type;
0088 __le16 attr_len;
0089 u8 country_code[IEEE80211_COUNTRY_STRING_LEN];
0090 u8 op_class;
0091 u8 op_channel;
0092 } __packed;
0093
0094 struct wilc_attr_ch_list {
0095 u8 attr_type;
0096 __le16 attr_len;
0097 u8 country_code[IEEE80211_COUNTRY_STRING_LEN];
0098 u8 elem[];
0099 } __packed;
0100
0101 struct wilc_ch_list_elem {
0102 u8 op_class;
0103 u8 no_of_channels;
0104 u8 ch_list[];
0105 } __packed;
0106
0107 static void cfg_scan_result(enum scan_event scan_event,
0108 struct wilc_rcvd_net_info *info, void *user_void)
0109 {
0110 struct wilc_priv *priv = user_void;
0111
0112 if (!priv->cfg_scanning)
0113 return;
0114
0115 if (scan_event == SCAN_EVENT_NETWORK_FOUND) {
0116 s32 freq;
0117 struct ieee80211_channel *channel;
0118 struct cfg80211_bss *bss;
0119 struct wiphy *wiphy = priv->dev->ieee80211_ptr->wiphy;
0120
0121 if (!wiphy || !info)
0122 return;
0123
0124 freq = ieee80211_channel_to_frequency((s32)info->ch,
0125 NL80211_BAND_2GHZ);
0126 channel = ieee80211_get_channel(wiphy, freq);
0127 if (!channel)
0128 return;
0129
0130 bss = cfg80211_inform_bss_frame(wiphy, channel, info->mgmt,
0131 info->frame_len,
0132 (s32)info->rssi * 100,
0133 GFP_KERNEL);
0134 cfg80211_put_bss(wiphy, bss);
0135 } else if (scan_event == SCAN_EVENT_DONE) {
0136 mutex_lock(&priv->scan_req_lock);
0137
0138 if (priv->scan_req) {
0139 struct cfg80211_scan_info info = {
0140 .aborted = false,
0141 };
0142
0143 cfg80211_scan_done(priv->scan_req, &info);
0144 priv->cfg_scanning = false;
0145 priv->scan_req = NULL;
0146 }
0147 mutex_unlock(&priv->scan_req_lock);
0148 } else if (scan_event == SCAN_EVENT_ABORTED) {
0149 mutex_lock(&priv->scan_req_lock);
0150
0151 if (priv->scan_req) {
0152 struct cfg80211_scan_info info = {
0153 .aborted = false,
0154 };
0155
0156 cfg80211_scan_done(priv->scan_req, &info);
0157 priv->cfg_scanning = false;
0158 priv->scan_req = NULL;
0159 }
0160 mutex_unlock(&priv->scan_req_lock);
0161 }
0162 }
0163
0164 static void cfg_connect_result(enum conn_event conn_disconn_evt, u8 mac_status,
0165 void *priv_data)
0166 {
0167 struct wilc_priv *priv = priv_data;
0168 struct net_device *dev = priv->dev;
0169 struct wilc_vif *vif = netdev_priv(dev);
0170 struct wilc *wl = vif->wilc;
0171 struct host_if_drv *wfi_drv = priv->hif_drv;
0172 struct wilc_conn_info *conn_info = &wfi_drv->conn_info;
0173 struct wiphy *wiphy = dev->ieee80211_ptr->wiphy;
0174
0175 vif->connecting = false;
0176
0177 if (conn_disconn_evt == CONN_DISCONN_EVENT_CONN_RESP) {
0178 u16 connect_status = conn_info->status;
0179
0180 if (mac_status == WILC_MAC_STATUS_DISCONNECTED &&
0181 connect_status == WLAN_STATUS_SUCCESS) {
0182 connect_status = WLAN_STATUS_UNSPECIFIED_FAILURE;
0183 wilc_wlan_set_bssid(priv->dev, NULL, WILC_STATION_MODE);
0184
0185 if (vif->iftype != WILC_CLIENT_MODE)
0186 wl->sta_ch = WILC_INVALID_CHANNEL;
0187
0188 netdev_err(dev, "Unspecified failure\n");
0189 }
0190
0191 if (connect_status == WLAN_STATUS_SUCCESS)
0192 memcpy(priv->associated_bss, conn_info->bssid,
0193 ETH_ALEN);
0194
0195 cfg80211_ref_bss(wiphy, vif->bss);
0196 cfg80211_connect_bss(dev, conn_info->bssid, vif->bss,
0197 conn_info->req_ies,
0198 conn_info->req_ies_len,
0199 conn_info->resp_ies,
0200 conn_info->resp_ies_len,
0201 connect_status, GFP_KERNEL,
0202 NL80211_TIMEOUT_UNSPECIFIED);
0203
0204 vif->bss = NULL;
0205 } else if (conn_disconn_evt == CONN_DISCONN_EVENT_DISCONN_NOTIF) {
0206 u16 reason = 0;
0207
0208 eth_zero_addr(priv->associated_bss);
0209 wilc_wlan_set_bssid(priv->dev, NULL, WILC_STATION_MODE);
0210
0211 if (vif->iftype != WILC_CLIENT_MODE) {
0212 wl->sta_ch = WILC_INVALID_CHANNEL;
0213 } else {
0214 if (wfi_drv->ifc_up)
0215 reason = 3;
0216 else
0217 reason = 1;
0218 }
0219
0220 cfg80211_disconnected(dev, reason, NULL, 0, false, GFP_KERNEL);
0221 }
0222 }
0223
0224 struct wilc_vif *wilc_get_wl_to_vif(struct wilc *wl)
0225 {
0226 struct wilc_vif *vif;
0227
0228 vif = list_first_or_null_rcu(&wl->vif_list, typeof(*vif), list);
0229 if (!vif)
0230 return ERR_PTR(-EINVAL);
0231
0232 return vif;
0233 }
0234
0235 static int set_channel(struct wiphy *wiphy,
0236 struct cfg80211_chan_def *chandef)
0237 {
0238 struct wilc *wl = wiphy_priv(wiphy);
0239 struct wilc_vif *vif;
0240 u32 channelnum;
0241 int result;
0242 int srcu_idx;
0243
0244 srcu_idx = srcu_read_lock(&wl->srcu);
0245 vif = wilc_get_wl_to_vif(wl);
0246 if (IS_ERR(vif)) {
0247 srcu_read_unlock(&wl->srcu, srcu_idx);
0248 return PTR_ERR(vif);
0249 }
0250
0251 channelnum = ieee80211_frequency_to_channel(chandef->chan->center_freq);
0252
0253 wl->op_ch = channelnum;
0254 result = wilc_set_mac_chnl_num(vif, channelnum);
0255 if (result)
0256 netdev_err(vif->ndev, "Error in setting channel\n");
0257
0258 srcu_read_unlock(&wl->srcu, srcu_idx);
0259 return result;
0260 }
0261
0262 static int scan(struct wiphy *wiphy, struct cfg80211_scan_request *request)
0263 {
0264 struct wilc_vif *vif = netdev_priv(request->wdev->netdev);
0265 struct wilc_priv *priv = &vif->priv;
0266 u32 i;
0267 int ret = 0;
0268 u8 scan_ch_list[WILC_MAX_NUM_SCANNED_CH];
0269 u8 scan_type;
0270
0271 if (request->n_channels > WILC_MAX_NUM_SCANNED_CH) {
0272 netdev_err(vif->ndev, "Requested scanned channels over\n");
0273 return -EINVAL;
0274 }
0275
0276 priv->scan_req = request;
0277 priv->cfg_scanning = true;
0278 for (i = 0; i < request->n_channels; i++) {
0279 u16 freq = request->channels[i]->center_freq;
0280
0281 scan_ch_list[i] = ieee80211_frequency_to_channel(freq);
0282 }
0283
0284 if (request->n_ssids)
0285 scan_type = WILC_FW_ACTIVE_SCAN;
0286 else
0287 scan_type = WILC_FW_PASSIVE_SCAN;
0288
0289 ret = wilc_scan(vif, WILC_FW_USER_SCAN, scan_type, scan_ch_list,
0290 request->n_channels, cfg_scan_result, (void *)priv,
0291 request);
0292
0293 if (ret) {
0294 priv->scan_req = NULL;
0295 priv->cfg_scanning = false;
0296 }
0297
0298 return ret;
0299 }
0300
0301 static int connect(struct wiphy *wiphy, struct net_device *dev,
0302 struct cfg80211_connect_params *sme)
0303 {
0304 struct wilc_vif *vif = netdev_priv(dev);
0305 struct wilc_priv *priv = &vif->priv;
0306 struct host_if_drv *wfi_drv = priv->hif_drv;
0307 int ret;
0308 u32 i;
0309 u8 security = WILC_FW_SEC_NO;
0310 enum mfptype mfp_type = WILC_FW_MFP_NONE;
0311 enum authtype auth_type = WILC_FW_AUTH_ANY;
0312 u32 cipher_group;
0313 struct cfg80211_bss *bss;
0314 void *join_params;
0315 u8 ch;
0316
0317 vif->connecting = true;
0318
0319 cipher_group = sme->crypto.cipher_group;
0320 if (cipher_group != 0) {
0321 if (sme->crypto.wpa_versions & NL80211_WPA_VERSION_2) {
0322 if (cipher_group == WLAN_CIPHER_SUITE_TKIP)
0323 security = WILC_FW_SEC_WPA2_TKIP;
0324 else
0325 security = WILC_FW_SEC_WPA2_AES;
0326 } else if (sme->crypto.wpa_versions & NL80211_WPA_VERSION_1) {
0327 if (cipher_group == WLAN_CIPHER_SUITE_TKIP)
0328 security = WILC_FW_SEC_WPA_TKIP;
0329 else
0330 security = WILC_FW_SEC_WPA_AES;
0331 } else {
0332 ret = -ENOTSUPP;
0333 netdev_err(dev, "%s: Unsupported cipher\n",
0334 __func__);
0335 goto out_error;
0336 }
0337 }
0338
0339 if ((sme->crypto.wpa_versions & NL80211_WPA_VERSION_1) ||
0340 (sme->crypto.wpa_versions & NL80211_WPA_VERSION_2)) {
0341 for (i = 0; i < sme->crypto.n_ciphers_pairwise; i++) {
0342 u32 ciphers_pairwise = sme->crypto.ciphers_pairwise[i];
0343
0344 if (ciphers_pairwise == WLAN_CIPHER_SUITE_TKIP)
0345 security |= WILC_FW_TKIP;
0346 else
0347 security |= WILC_FW_AES;
0348 }
0349 }
0350
0351 switch (sme->auth_type) {
0352 case NL80211_AUTHTYPE_OPEN_SYSTEM:
0353 auth_type = WILC_FW_AUTH_OPEN_SYSTEM;
0354 break;
0355
0356 case NL80211_AUTHTYPE_SAE:
0357 auth_type = WILC_FW_AUTH_SAE;
0358 if (sme->ssid_len) {
0359 memcpy(vif->auth.ssid.ssid, sme->ssid, sme->ssid_len);
0360 vif->auth.ssid.ssid_len = sme->ssid_len;
0361 }
0362 vif->auth.key_mgmt_suite = cpu_to_be32(sme->crypto.akm_suites[0]);
0363 ether_addr_copy(vif->auth.bssid, sme->bssid);
0364 break;
0365
0366 default:
0367 break;
0368 }
0369
0370 if (sme->crypto.n_akm_suites) {
0371 if (sme->crypto.akm_suites[0] == WLAN_AKM_SUITE_8021X)
0372 auth_type = WILC_FW_AUTH_IEEE8021;
0373 else if (sme->crypto.akm_suites[0] == WLAN_AKM_SUITE_PSK_SHA256)
0374 auth_type = WILC_FW_AUTH_OPEN_SYSTEM_SHA256;
0375 else if (sme->crypto.akm_suites[0] == WLAN_AKM_SUITE_8021X_SHA256)
0376 auth_type = WILC_FW_AUTH_IEE8021X_SHA256;
0377 }
0378
0379 if (wfi_drv->usr_scan_req.scan_result) {
0380 netdev_err(vif->ndev, "%s: Scan in progress\n", __func__);
0381 ret = -EBUSY;
0382 goto out_error;
0383 }
0384
0385 bss = cfg80211_get_bss(wiphy, sme->channel, sme->bssid, sme->ssid,
0386 sme->ssid_len, IEEE80211_BSS_TYPE_ANY,
0387 IEEE80211_PRIVACY(sme->privacy));
0388 if (!bss) {
0389 ret = -EINVAL;
0390 goto out_error;
0391 }
0392
0393 if (ether_addr_equal_unaligned(vif->bssid, bss->bssid)) {
0394 ret = -EALREADY;
0395 goto out_put_bss;
0396 }
0397
0398 join_params = wilc_parse_join_bss_param(bss, &sme->crypto);
0399 if (!join_params) {
0400 netdev_err(dev, "%s: failed to construct join param\n",
0401 __func__);
0402 ret = -EINVAL;
0403 goto out_put_bss;
0404 }
0405
0406 ch = ieee80211_frequency_to_channel(bss->channel->center_freq);
0407 vif->wilc->op_ch = ch;
0408 if (vif->iftype != WILC_CLIENT_MODE)
0409 vif->wilc->sta_ch = ch;
0410
0411 wilc_wlan_set_bssid(dev, bss->bssid, WILC_STATION_MODE);
0412
0413 wfi_drv->conn_info.security = security;
0414 wfi_drv->conn_info.auth_type = auth_type;
0415 wfi_drv->conn_info.ch = ch;
0416 wfi_drv->conn_info.conn_result = cfg_connect_result;
0417 wfi_drv->conn_info.arg = priv;
0418 wfi_drv->conn_info.param = join_params;
0419
0420 if (sme->mfp == NL80211_MFP_OPTIONAL)
0421 mfp_type = WILC_FW_MFP_OPTIONAL;
0422 else if (sme->mfp == NL80211_MFP_REQUIRED)
0423 mfp_type = WILC_FW_MFP_REQUIRED;
0424
0425 wfi_drv->conn_info.mfp_type = mfp_type;
0426
0427 ret = wilc_set_join_req(vif, bss->bssid, sme->ie, sme->ie_len);
0428 if (ret) {
0429 netdev_err(dev, "wilc_set_join_req(): Error\n");
0430 ret = -ENOENT;
0431 if (vif->iftype != WILC_CLIENT_MODE)
0432 vif->wilc->sta_ch = WILC_INVALID_CHANNEL;
0433 wilc_wlan_set_bssid(dev, NULL, WILC_STATION_MODE);
0434 wfi_drv->conn_info.conn_result = NULL;
0435 kfree(join_params);
0436 goto out_put_bss;
0437 }
0438 kfree(join_params);
0439 vif->bss = bss;
0440 cfg80211_put_bss(wiphy, bss);
0441 return 0;
0442
0443 out_put_bss:
0444 cfg80211_put_bss(wiphy, bss);
0445
0446 out_error:
0447 vif->connecting = false;
0448 return ret;
0449 }
0450
0451 static int disconnect(struct wiphy *wiphy, struct net_device *dev,
0452 u16 reason_code)
0453 {
0454 struct wilc_vif *vif = netdev_priv(dev);
0455 struct wilc_priv *priv = &vif->priv;
0456 struct wilc *wilc = vif->wilc;
0457 int ret;
0458
0459 vif->connecting = false;
0460
0461 if (!wilc)
0462 return -EIO;
0463
0464 if (wilc->close) {
0465
0466 cfg80211_disconnected(dev, 0, NULL, 0, true, GFP_KERNEL);
0467 return 0;
0468 }
0469
0470 if (vif->iftype != WILC_CLIENT_MODE)
0471 wilc->sta_ch = WILC_INVALID_CHANNEL;
0472 wilc_wlan_set_bssid(priv->dev, NULL, WILC_STATION_MODE);
0473
0474 priv->hif_drv->p2p_timeout = 0;
0475
0476 ret = wilc_disconnect(vif);
0477 if (ret != 0) {
0478 netdev_err(priv->dev, "Error in disconnecting\n");
0479 ret = -EINVAL;
0480 }
0481
0482 vif->bss = NULL;
0483
0484 return ret;
0485 }
0486
0487 static int wilc_wfi_cfg_allocate_wpa_entry(struct wilc_priv *priv, u8 idx)
0488 {
0489 if (!priv->wilc_gtk[idx]) {
0490 priv->wilc_gtk[idx] = kzalloc(sizeof(*priv->wilc_gtk[idx]),
0491 GFP_KERNEL);
0492 if (!priv->wilc_gtk[idx])
0493 return -ENOMEM;
0494 }
0495
0496 if (!priv->wilc_ptk[idx]) {
0497 priv->wilc_ptk[idx] = kzalloc(sizeof(*priv->wilc_ptk[idx]),
0498 GFP_KERNEL);
0499 if (!priv->wilc_ptk[idx])
0500 return -ENOMEM;
0501 }
0502
0503 return 0;
0504 }
0505
0506 static int wilc_wfi_cfg_allocate_wpa_igtk_entry(struct wilc_priv *priv, u8 idx)
0507 {
0508 idx -= 4;
0509 if (!priv->wilc_igtk[idx]) {
0510 priv->wilc_igtk[idx] = kzalloc(sizeof(*priv->wilc_igtk[idx]),
0511 GFP_KERNEL);
0512 if (!priv->wilc_igtk[idx])
0513 return -ENOMEM;
0514 }
0515 return 0;
0516 }
0517
0518 static int wilc_wfi_cfg_copy_wpa_info(struct wilc_wfi_key *key_info,
0519 struct key_params *params)
0520 {
0521 kfree(key_info->key);
0522
0523 key_info->key = kmemdup(params->key, params->key_len, GFP_KERNEL);
0524 if (!key_info->key)
0525 return -ENOMEM;
0526
0527 kfree(key_info->seq);
0528
0529 if (params->seq_len > 0) {
0530 key_info->seq = kmemdup(params->seq, params->seq_len,
0531 GFP_KERNEL);
0532 if (!key_info->seq)
0533 return -ENOMEM;
0534 }
0535
0536 key_info->cipher = params->cipher;
0537 key_info->key_len = params->key_len;
0538 key_info->seq_len = params->seq_len;
0539
0540 return 0;
0541 }
0542
0543 static int add_key(struct wiphy *wiphy, struct net_device *netdev, u8 key_index,
0544 bool pairwise, const u8 *mac_addr, struct key_params *params)
0545
0546 {
0547 int ret = 0, keylen = params->key_len;
0548 const u8 *rx_mic = NULL;
0549 const u8 *tx_mic = NULL;
0550 u8 mode = WILC_FW_SEC_NO;
0551 u8 op_mode;
0552 struct wilc_vif *vif = netdev_priv(netdev);
0553 struct wilc_priv *priv = &vif->priv;
0554 struct wilc_wfi_key *key;
0555
0556 switch (params->cipher) {
0557 case WLAN_CIPHER_SUITE_TKIP:
0558 case WLAN_CIPHER_SUITE_CCMP:
0559 if (priv->wdev.iftype == NL80211_IFTYPE_AP ||
0560 priv->wdev.iftype == NL80211_IFTYPE_P2P_GO) {
0561 struct wilc_wfi_key *key;
0562
0563 ret = wilc_wfi_cfg_allocate_wpa_entry(priv, key_index);
0564 if (ret)
0565 return -ENOMEM;
0566
0567 if (params->key_len > 16 &&
0568 params->cipher == WLAN_CIPHER_SUITE_TKIP) {
0569 tx_mic = params->key + 24;
0570 rx_mic = params->key + 16;
0571 keylen = params->key_len - 16;
0572 }
0573
0574 if (!pairwise) {
0575 if (params->cipher == WLAN_CIPHER_SUITE_TKIP)
0576 mode = WILC_FW_SEC_WPA_TKIP;
0577 else
0578 mode = WILC_FW_SEC_WPA2_AES;
0579
0580 priv->wilc_groupkey = mode;
0581
0582 key = priv->wilc_gtk[key_index];
0583 } else {
0584 if (params->cipher == WLAN_CIPHER_SUITE_TKIP)
0585 mode = WILC_FW_SEC_WPA_TKIP;
0586 else
0587 mode = priv->wilc_groupkey | WILC_FW_AES;
0588
0589 key = priv->wilc_ptk[key_index];
0590 }
0591 ret = wilc_wfi_cfg_copy_wpa_info(key, params);
0592 if (ret)
0593 return -ENOMEM;
0594
0595 op_mode = WILC_AP_MODE;
0596 } else {
0597 if (params->key_len > 16 &&
0598 params->cipher == WLAN_CIPHER_SUITE_TKIP) {
0599 rx_mic = params->key + 24;
0600 tx_mic = params->key + 16;
0601 keylen = params->key_len - 16;
0602 }
0603
0604 op_mode = WILC_STATION_MODE;
0605 }
0606
0607 if (!pairwise)
0608 ret = wilc_add_rx_gtk(vif, params->key, keylen,
0609 key_index, params->seq_len,
0610 params->seq, rx_mic, tx_mic,
0611 op_mode, mode);
0612 else
0613 ret = wilc_add_ptk(vif, params->key, keylen, mac_addr,
0614 rx_mic, tx_mic, op_mode, mode,
0615 key_index);
0616
0617 break;
0618 case WLAN_CIPHER_SUITE_AES_CMAC:
0619 ret = wilc_wfi_cfg_allocate_wpa_igtk_entry(priv, key_index);
0620 if (ret)
0621 return -ENOMEM;
0622
0623 key = priv->wilc_igtk[key_index - 4];
0624 ret = wilc_wfi_cfg_copy_wpa_info(key, params);
0625 if (ret)
0626 return -ENOMEM;
0627
0628 if (priv->wdev.iftype == NL80211_IFTYPE_AP ||
0629 priv->wdev.iftype == NL80211_IFTYPE_P2P_GO)
0630 op_mode = WILC_AP_MODE;
0631 else
0632 op_mode = WILC_STATION_MODE;
0633
0634 ret = wilc_add_igtk(vif, params->key, keylen, params->seq,
0635 params->seq_len, mac_addr, op_mode,
0636 key_index);
0637 break;
0638
0639 default:
0640 netdev_err(netdev, "%s: Unsupported cipher\n", __func__);
0641 ret = -ENOTSUPP;
0642 }
0643
0644 return ret;
0645 }
0646
0647 static int del_key(struct wiphy *wiphy, struct net_device *netdev,
0648 u8 key_index,
0649 bool pairwise,
0650 const u8 *mac_addr)
0651 {
0652 struct wilc_vif *vif = netdev_priv(netdev);
0653 struct wilc_priv *priv = &vif->priv;
0654
0655 if (!pairwise && (key_index == 4 || key_index == 5)) {
0656 key_index -= 4;
0657 if (priv->wilc_igtk[key_index]) {
0658 kfree(priv->wilc_igtk[key_index]->key);
0659 priv->wilc_igtk[key_index]->key = NULL;
0660 kfree(priv->wilc_igtk[key_index]->seq);
0661 priv->wilc_igtk[key_index]->seq = NULL;
0662 kfree(priv->wilc_igtk[key_index]);
0663 priv->wilc_igtk[key_index] = NULL;
0664 }
0665 } else {
0666 if (priv->wilc_gtk[key_index]) {
0667 kfree(priv->wilc_gtk[key_index]->key);
0668 priv->wilc_gtk[key_index]->key = NULL;
0669 kfree(priv->wilc_gtk[key_index]->seq);
0670 priv->wilc_gtk[key_index]->seq = NULL;
0671
0672 kfree(priv->wilc_gtk[key_index]);
0673 priv->wilc_gtk[key_index] = NULL;
0674 }
0675 if (priv->wilc_ptk[key_index]) {
0676 kfree(priv->wilc_ptk[key_index]->key);
0677 priv->wilc_ptk[key_index]->key = NULL;
0678 kfree(priv->wilc_ptk[key_index]->seq);
0679 priv->wilc_ptk[key_index]->seq = NULL;
0680 kfree(priv->wilc_ptk[key_index]);
0681 priv->wilc_ptk[key_index] = NULL;
0682 }
0683 }
0684
0685 return 0;
0686 }
0687
0688 static int get_key(struct wiphy *wiphy, struct net_device *netdev, u8 key_index,
0689 bool pairwise, const u8 *mac_addr, void *cookie,
0690 void (*callback)(void *cookie, struct key_params *))
0691 {
0692 struct wilc_vif *vif = netdev_priv(netdev);
0693 struct wilc_priv *priv = &vif->priv;
0694 struct key_params key_params;
0695
0696 if (!pairwise) {
0697 if (key_index == 4 || key_index == 5) {
0698 key_index -= 4;
0699 key_params.key = priv->wilc_igtk[key_index]->key;
0700 key_params.cipher = priv->wilc_igtk[key_index]->cipher;
0701 key_params.key_len = priv->wilc_igtk[key_index]->key_len;
0702 key_params.seq = priv->wilc_igtk[key_index]->seq;
0703 key_params.seq_len = priv->wilc_igtk[key_index]->seq_len;
0704 } else {
0705 key_params.key = priv->wilc_gtk[key_index]->key;
0706 key_params.cipher = priv->wilc_gtk[key_index]->cipher;
0707 key_params.key_len = priv->wilc_gtk[key_index]->key_len;
0708 key_params.seq = priv->wilc_gtk[key_index]->seq;
0709 key_params.seq_len = priv->wilc_gtk[key_index]->seq_len;
0710 }
0711 } else {
0712 key_params.key = priv->wilc_ptk[key_index]->key;
0713 key_params.cipher = priv->wilc_ptk[key_index]->cipher;
0714 key_params.key_len = priv->wilc_ptk[key_index]->key_len;
0715 key_params.seq = priv->wilc_ptk[key_index]->seq;
0716 key_params.seq_len = priv->wilc_ptk[key_index]->seq_len;
0717 }
0718
0719 callback(cookie, &key_params);
0720
0721 return 0;
0722 }
0723
0724
0725 static int set_default_key(struct wiphy *wiphy, struct net_device *netdev,
0726 u8 key_index, bool unicast, bool multicast)
0727 {
0728 return 0;
0729 }
0730
0731 static int set_default_mgmt_key(struct wiphy *wiphy, struct net_device *netdev,
0732 u8 key_index)
0733 {
0734 struct wilc_vif *vif = netdev_priv(netdev);
0735
0736 return wilc_set_default_mgmt_key_index(vif, key_index);
0737 }
0738
0739 static int get_station(struct wiphy *wiphy, struct net_device *dev,
0740 const u8 *mac, struct station_info *sinfo)
0741 {
0742 struct wilc_vif *vif = netdev_priv(dev);
0743 struct wilc_priv *priv = &vif->priv;
0744 struct wilc *wilc = vif->wilc;
0745 u32 i = 0;
0746 u32 associatedsta = ~0;
0747 u32 inactive_time = 0;
0748
0749 if (vif->iftype == WILC_AP_MODE || vif->iftype == WILC_GO_MODE) {
0750 for (i = 0; i < NUM_STA_ASSOCIATED; i++) {
0751 if (!(memcmp(mac,
0752 priv->assoc_stainfo.sta_associated_bss[i],
0753 ETH_ALEN))) {
0754 associatedsta = i;
0755 break;
0756 }
0757 }
0758
0759 if (associatedsta == ~0) {
0760 netdev_err(dev, "sta required is not associated\n");
0761 return -ENOENT;
0762 }
0763
0764 sinfo->filled |= BIT_ULL(NL80211_STA_INFO_INACTIVE_TIME);
0765
0766 wilc_get_inactive_time(vif, mac, &inactive_time);
0767 sinfo->inactive_time = 1000 * inactive_time;
0768 } else if (vif->iftype == WILC_STATION_MODE) {
0769 struct rf_info stats;
0770
0771 if (!wilc->initialized)
0772 return -EBUSY;
0773
0774 wilc_get_statistics(vif, &stats);
0775
0776 sinfo->filled |= BIT_ULL(NL80211_STA_INFO_SIGNAL) |
0777 BIT_ULL(NL80211_STA_INFO_RX_PACKETS) |
0778 BIT_ULL(NL80211_STA_INFO_TX_PACKETS) |
0779 BIT_ULL(NL80211_STA_INFO_TX_FAILED) |
0780 BIT_ULL(NL80211_STA_INFO_TX_BITRATE);
0781
0782 sinfo->signal = stats.rssi;
0783 sinfo->rx_packets = stats.rx_cnt;
0784 sinfo->tx_packets = stats.tx_cnt + stats.tx_fail_cnt;
0785 sinfo->tx_failed = stats.tx_fail_cnt;
0786 sinfo->txrate.legacy = stats.link_speed * 10;
0787
0788 if (stats.link_speed > TCP_ACK_FILTER_LINK_SPEED_THRESH &&
0789 stats.link_speed != DEFAULT_LINK_SPEED)
0790 wilc_enable_tcp_ack_filter(vif, true);
0791 else if (stats.link_speed != DEFAULT_LINK_SPEED)
0792 wilc_enable_tcp_ack_filter(vif, false);
0793 }
0794 return 0;
0795 }
0796
0797 static int change_bss(struct wiphy *wiphy, struct net_device *dev,
0798 struct bss_parameters *params)
0799 {
0800 return 0;
0801 }
0802
0803 static int set_wiphy_params(struct wiphy *wiphy, u32 changed)
0804 {
0805 int ret = -EINVAL;
0806 struct cfg_param_attr cfg_param_val;
0807 struct wilc *wl = wiphy_priv(wiphy);
0808 struct wilc_vif *vif;
0809 struct wilc_priv *priv;
0810 int srcu_idx;
0811
0812 srcu_idx = srcu_read_lock(&wl->srcu);
0813 vif = wilc_get_wl_to_vif(wl);
0814 if (IS_ERR(vif))
0815 goto out;
0816
0817 priv = &vif->priv;
0818 cfg_param_val.flag = 0;
0819
0820 if (changed & WIPHY_PARAM_RETRY_SHORT) {
0821 netdev_dbg(vif->ndev,
0822 "Setting WIPHY_PARAM_RETRY_SHORT %d\n",
0823 wiphy->retry_short);
0824 cfg_param_val.flag |= WILC_CFG_PARAM_RETRY_SHORT;
0825 cfg_param_val.short_retry_limit = wiphy->retry_short;
0826 }
0827 if (changed & WIPHY_PARAM_RETRY_LONG) {
0828 netdev_dbg(vif->ndev,
0829 "Setting WIPHY_PARAM_RETRY_LONG %d\n",
0830 wiphy->retry_long);
0831 cfg_param_val.flag |= WILC_CFG_PARAM_RETRY_LONG;
0832 cfg_param_val.long_retry_limit = wiphy->retry_long;
0833 }
0834 if (changed & WIPHY_PARAM_FRAG_THRESHOLD) {
0835 if (wiphy->frag_threshold > 255 &&
0836 wiphy->frag_threshold < 7937) {
0837 netdev_dbg(vif->ndev,
0838 "Setting WIPHY_PARAM_FRAG_THRESHOLD %d\n",
0839 wiphy->frag_threshold);
0840 cfg_param_val.flag |= WILC_CFG_PARAM_FRAG_THRESHOLD;
0841 cfg_param_val.frag_threshold = wiphy->frag_threshold;
0842 } else {
0843 netdev_err(vif->ndev,
0844 "Fragmentation threshold out of range\n");
0845 goto out;
0846 }
0847 }
0848
0849 if (changed & WIPHY_PARAM_RTS_THRESHOLD) {
0850 if (wiphy->rts_threshold > 255) {
0851 netdev_dbg(vif->ndev,
0852 "Setting WIPHY_PARAM_RTS_THRESHOLD %d\n",
0853 wiphy->rts_threshold);
0854 cfg_param_val.flag |= WILC_CFG_PARAM_RTS_THRESHOLD;
0855 cfg_param_val.rts_threshold = wiphy->rts_threshold;
0856 } else {
0857 netdev_err(vif->ndev, "RTS threshold out of range\n");
0858 goto out;
0859 }
0860 }
0861
0862 ret = wilc_hif_set_cfg(vif, &cfg_param_val);
0863 if (ret)
0864 netdev_err(priv->dev, "Error in setting WIPHY PARAMS\n");
0865
0866 out:
0867 srcu_read_unlock(&wl->srcu, srcu_idx);
0868 return ret;
0869 }
0870
0871 static int set_pmksa(struct wiphy *wiphy, struct net_device *netdev,
0872 struct cfg80211_pmksa *pmksa)
0873 {
0874 struct wilc_vif *vif = netdev_priv(netdev);
0875 struct wilc_priv *priv = &vif->priv;
0876 u32 i;
0877 int ret = 0;
0878 u8 flag = 0;
0879
0880 for (i = 0; i < priv->pmkid_list.numpmkid; i++) {
0881 if (!memcmp(pmksa->bssid, priv->pmkid_list.pmkidlist[i].bssid,
0882 ETH_ALEN)) {
0883 flag = PMKID_FOUND;
0884 break;
0885 }
0886 }
0887 if (i < WILC_MAX_NUM_PMKIDS) {
0888 memcpy(priv->pmkid_list.pmkidlist[i].bssid, pmksa->bssid,
0889 ETH_ALEN);
0890 memcpy(priv->pmkid_list.pmkidlist[i].pmkid, pmksa->pmkid,
0891 WLAN_PMKID_LEN);
0892 if (!(flag == PMKID_FOUND))
0893 priv->pmkid_list.numpmkid++;
0894 } else {
0895 netdev_err(netdev, "Invalid PMKID index\n");
0896 ret = -EINVAL;
0897 }
0898
0899 if (!ret)
0900 ret = wilc_set_pmkid_info(vif, &priv->pmkid_list);
0901
0902 return ret;
0903 }
0904
0905 static int del_pmksa(struct wiphy *wiphy, struct net_device *netdev,
0906 struct cfg80211_pmksa *pmksa)
0907 {
0908 u32 i;
0909 struct wilc_vif *vif = netdev_priv(netdev);
0910 struct wilc_priv *priv = &vif->priv;
0911
0912 for (i = 0; i < priv->pmkid_list.numpmkid; i++) {
0913 if (!memcmp(pmksa->bssid, priv->pmkid_list.pmkidlist[i].bssid,
0914 ETH_ALEN)) {
0915 memset(&priv->pmkid_list.pmkidlist[i], 0,
0916 sizeof(struct wilc_pmkid));
0917 break;
0918 }
0919 }
0920
0921 if (i == priv->pmkid_list.numpmkid)
0922 return -EINVAL;
0923
0924 for (; i < (priv->pmkid_list.numpmkid - 1); i++) {
0925 memcpy(priv->pmkid_list.pmkidlist[i].bssid,
0926 priv->pmkid_list.pmkidlist[i + 1].bssid,
0927 ETH_ALEN);
0928 memcpy(priv->pmkid_list.pmkidlist[i].pmkid,
0929 priv->pmkid_list.pmkidlist[i + 1].pmkid,
0930 WLAN_PMKID_LEN);
0931 }
0932 priv->pmkid_list.numpmkid--;
0933
0934 return 0;
0935 }
0936
0937 static int flush_pmksa(struct wiphy *wiphy, struct net_device *netdev)
0938 {
0939 struct wilc_vif *vif = netdev_priv(netdev);
0940
0941 memset(&vif->priv.pmkid_list, 0, sizeof(struct wilc_pmkid_attr));
0942
0943 return 0;
0944 }
0945
0946 static inline void wilc_wfi_cfg_parse_ch_attr(u8 *buf, u32 len, u8 sta_ch)
0947 {
0948 struct wilc_attr_entry *e;
0949 struct wilc_attr_ch_list *ch_list;
0950 struct wilc_attr_oper_ch *op_ch;
0951 u32 index = 0;
0952 u8 ch_list_idx = 0;
0953 u8 op_ch_idx = 0;
0954
0955 if (sta_ch == WILC_INVALID_CHANNEL)
0956 return;
0957
0958 while (index + sizeof(*e) <= len) {
0959 e = (struct wilc_attr_entry *)&buf[index];
0960 if (e->attr_type == IEEE80211_P2P_ATTR_CHANNEL_LIST)
0961 ch_list_idx = index;
0962 else if (e->attr_type == IEEE80211_P2P_ATTR_OPER_CHANNEL)
0963 op_ch_idx = index;
0964 if (ch_list_idx && op_ch_idx)
0965 break;
0966 index += le16_to_cpu(e->attr_len) + sizeof(*e);
0967 }
0968
0969 if (ch_list_idx) {
0970 u16 attr_size;
0971 struct wilc_ch_list_elem *e;
0972 int i;
0973
0974 ch_list = (struct wilc_attr_ch_list *)&buf[ch_list_idx];
0975 attr_size = le16_to_cpu(ch_list->attr_len);
0976 for (i = 0; i < attr_size;) {
0977 e = (struct wilc_ch_list_elem *)(ch_list->elem + i);
0978 if (e->op_class == WILC_WLAN_OPERATING_CLASS_2_4GHZ) {
0979 memset(e->ch_list, sta_ch, e->no_of_channels);
0980 break;
0981 }
0982 i += e->no_of_channels;
0983 }
0984 }
0985
0986 if (op_ch_idx) {
0987 op_ch = (struct wilc_attr_oper_ch *)&buf[op_ch_idx];
0988 op_ch->op_class = WILC_WLAN_OPERATING_CLASS_2_4GHZ;
0989 op_ch->op_channel = sta_ch;
0990 }
0991 }
0992
0993 bool wilc_wfi_mgmt_frame_rx(struct wilc_vif *vif, u8 *buff, u32 size)
0994 {
0995 struct wilc *wl = vif->wilc;
0996 struct wilc_priv *priv = &vif->priv;
0997 int freq, ret;
0998
0999 freq = ieee80211_channel_to_frequency(wl->op_ch, NL80211_BAND_2GHZ);
1000 ret = cfg80211_rx_mgmt(&priv->wdev, freq, 0, buff, size, 0);
1001
1002 return ret;
1003 }
1004
1005 void wilc_wfi_p2p_rx(struct wilc_vif *vif, u8 *buff, u32 size)
1006 {
1007 struct wilc *wl = vif->wilc;
1008 struct wilc_priv *priv = &vif->priv;
1009 struct host_if_drv *wfi_drv = priv->hif_drv;
1010 struct ieee80211_mgmt *mgmt;
1011 struct wilc_vendor_specific_ie *p;
1012 struct wilc_p2p_pub_act_frame *d;
1013 int ie_offset = offsetof(struct ieee80211_mgmt, u) + sizeof(*d);
1014 const u8 *vendor_ie;
1015 u32 header, pkt_offset;
1016 s32 freq;
1017
1018 header = get_unaligned_le32(buff - HOST_HDR_OFFSET);
1019 pkt_offset = FIELD_GET(WILC_PKT_HDR_OFFSET_FIELD, header);
1020
1021 if (pkt_offset & IS_MANAGMEMENT_CALLBACK) {
1022 bool ack = false;
1023 struct ieee80211_hdr *hdr = (struct ieee80211_hdr *)buff;
1024
1025 if (ieee80211_is_probe_resp(hdr->frame_control) ||
1026 pkt_offset & IS_MGMT_STATUS_SUCCES)
1027 ack = true;
1028
1029 cfg80211_mgmt_tx_status(&priv->wdev, priv->tx_cookie, buff,
1030 size, ack, GFP_KERNEL);
1031 return;
1032 }
1033
1034 freq = ieee80211_channel_to_frequency(wl->op_ch, NL80211_BAND_2GHZ);
1035
1036 mgmt = (struct ieee80211_mgmt *)buff;
1037 if (!ieee80211_is_action(mgmt->frame_control))
1038 goto out_rx_mgmt;
1039
1040 if (priv->cfg_scanning &&
1041 time_after_eq(jiffies, (unsigned long)wfi_drv->p2p_timeout)) {
1042 netdev_dbg(vif->ndev, "Receiving action wrong ch\n");
1043 return;
1044 }
1045
1046 if (!ieee80211_is_public_action((struct ieee80211_hdr *)buff, size))
1047 goto out_rx_mgmt;
1048
1049 d = (struct wilc_p2p_pub_act_frame *)(&mgmt->u.action);
1050 if (d->oui_subtype != GO_NEG_REQ && d->oui_subtype != GO_NEG_RSP &&
1051 d->oui_subtype != P2P_INV_REQ && d->oui_subtype != P2P_INV_RSP)
1052 goto out_rx_mgmt;
1053
1054 vendor_ie = cfg80211_find_vendor_ie(WLAN_OUI_WFA, WLAN_OUI_TYPE_WFA_P2P,
1055 buff + ie_offset, size - ie_offset);
1056 if (!vendor_ie)
1057 goto out_rx_mgmt;
1058
1059 p = (struct wilc_vendor_specific_ie *)vendor_ie;
1060 wilc_wfi_cfg_parse_ch_attr(p->attr, p->tag_len - 4, vif->wilc->sta_ch);
1061
1062 out_rx_mgmt:
1063 cfg80211_rx_mgmt(&priv->wdev, freq, 0, buff, size, 0);
1064 }
1065
1066 static void wilc_wfi_mgmt_tx_complete(void *priv, int status)
1067 {
1068 struct wilc_p2p_mgmt_data *pv_data = priv;
1069
1070 kfree(pv_data->buff);
1071 kfree(pv_data);
1072 }
1073
1074 static void wilc_wfi_remain_on_channel_expired(void *data, u64 cookie)
1075 {
1076 struct wilc_vif *vif = data;
1077 struct wilc_priv *priv = &vif->priv;
1078 struct wilc_wfi_p2p_listen_params *params = &priv->remain_on_ch_params;
1079
1080 if (cookie != params->listen_cookie)
1081 return;
1082
1083 priv->p2p_listen_state = false;
1084
1085 cfg80211_remain_on_channel_expired(&priv->wdev, params->listen_cookie,
1086 params->listen_ch, GFP_KERNEL);
1087 }
1088
1089 static int remain_on_channel(struct wiphy *wiphy,
1090 struct wireless_dev *wdev,
1091 struct ieee80211_channel *chan,
1092 unsigned int duration, u64 *cookie)
1093 {
1094 int ret = 0;
1095 struct wilc_vif *vif = netdev_priv(wdev->netdev);
1096 struct wilc_priv *priv = &vif->priv;
1097 u64 id;
1098
1099 if (wdev->iftype == NL80211_IFTYPE_AP) {
1100 netdev_dbg(vif->ndev, "Required while in AP mode\n");
1101 return ret;
1102 }
1103
1104 id = ++priv->inc_roc_cookie;
1105 if (id == 0)
1106 id = ++priv->inc_roc_cookie;
1107
1108 ret = wilc_remain_on_channel(vif, id, duration, chan->hw_value,
1109 wilc_wfi_remain_on_channel_expired,
1110 (void *)vif);
1111 if (ret)
1112 return ret;
1113
1114 vif->wilc->op_ch = chan->hw_value;
1115
1116 priv->remain_on_ch_params.listen_ch = chan;
1117 priv->remain_on_ch_params.listen_cookie = id;
1118 *cookie = id;
1119 priv->p2p_listen_state = true;
1120 priv->remain_on_ch_params.listen_duration = duration;
1121
1122 cfg80211_ready_on_channel(wdev, *cookie, chan, duration, GFP_KERNEL);
1123 mod_timer(&vif->hif_drv->remain_on_ch_timer,
1124 jiffies + msecs_to_jiffies(duration + 1000));
1125
1126 return ret;
1127 }
1128
1129 static int cancel_remain_on_channel(struct wiphy *wiphy,
1130 struct wireless_dev *wdev,
1131 u64 cookie)
1132 {
1133 struct wilc_vif *vif = netdev_priv(wdev->netdev);
1134 struct wilc_priv *priv = &vif->priv;
1135
1136 if (cookie != priv->remain_on_ch_params.listen_cookie)
1137 return -ENOENT;
1138
1139 return wilc_listen_state_expired(vif, cookie);
1140 }
1141
1142 static int mgmt_tx(struct wiphy *wiphy,
1143 struct wireless_dev *wdev,
1144 struct cfg80211_mgmt_tx_params *params,
1145 u64 *cookie)
1146 {
1147 struct ieee80211_channel *chan = params->chan;
1148 unsigned int wait = params->wait;
1149 const u8 *buf = params->buf;
1150 size_t len = params->len;
1151 const struct ieee80211_mgmt *mgmt;
1152 struct wilc_p2p_mgmt_data *mgmt_tx;
1153 struct wilc_vif *vif = netdev_priv(wdev->netdev);
1154 struct wilc_priv *priv = &vif->priv;
1155 struct host_if_drv *wfi_drv = priv->hif_drv;
1156 struct wilc_vendor_specific_ie *p;
1157 struct wilc_p2p_pub_act_frame *d;
1158 int ie_offset = offsetof(struct ieee80211_mgmt, u) + sizeof(*d);
1159 const u8 *vendor_ie;
1160 int ret = 0;
1161
1162 *cookie = prandom_u32();
1163 priv->tx_cookie = *cookie;
1164 mgmt = (const struct ieee80211_mgmt *)buf;
1165
1166 if (!ieee80211_is_mgmt(mgmt->frame_control))
1167 goto out;
1168
1169 mgmt_tx = kmalloc(sizeof(*mgmt_tx), GFP_KERNEL);
1170 if (!mgmt_tx) {
1171 ret = -ENOMEM;
1172 goto out;
1173 }
1174
1175 mgmt_tx->buff = kmemdup(buf, len, GFP_KERNEL);
1176 if (!mgmt_tx->buff) {
1177 ret = -ENOMEM;
1178 kfree(mgmt_tx);
1179 goto out;
1180 }
1181
1182 mgmt_tx->size = len;
1183
1184 if (ieee80211_is_probe_resp(mgmt->frame_control)) {
1185 wilc_set_mac_chnl_num(vif, chan->hw_value);
1186 vif->wilc->op_ch = chan->hw_value;
1187 goto out_txq_add_pkt;
1188 }
1189
1190 if (!ieee80211_is_public_action((struct ieee80211_hdr *)buf, len)) {
1191 if (chan)
1192 wilc_set_mac_chnl_num(vif, chan->hw_value);
1193 else
1194 wilc_set_mac_chnl_num(vif, vif->wilc->op_ch);
1195
1196 goto out_set_timeout;
1197 }
1198
1199 d = (struct wilc_p2p_pub_act_frame *)(&mgmt->u.action);
1200 if (d->oui_type != WLAN_OUI_TYPE_WFA_P2P ||
1201 d->oui_subtype != GO_NEG_CONF) {
1202 wilc_set_mac_chnl_num(vif, chan->hw_value);
1203 vif->wilc->op_ch = chan->hw_value;
1204 }
1205
1206 if (d->oui_subtype != P2P_INV_REQ && d->oui_subtype != P2P_INV_RSP)
1207 goto out_set_timeout;
1208
1209 vendor_ie = cfg80211_find_vendor_ie(WLAN_OUI_WFA, WLAN_OUI_TYPE_WFA_P2P,
1210 mgmt_tx->buff + ie_offset,
1211 len - ie_offset);
1212 if (!vendor_ie)
1213 goto out_set_timeout;
1214
1215 p = (struct wilc_vendor_specific_ie *)vendor_ie;
1216 wilc_wfi_cfg_parse_ch_attr(p->attr, p->tag_len - 4, vif->wilc->sta_ch);
1217
1218 out_set_timeout:
1219 wfi_drv->p2p_timeout = (jiffies + msecs_to_jiffies(wait));
1220
1221 out_txq_add_pkt:
1222
1223 wilc_wlan_txq_add_mgmt_pkt(wdev->netdev, mgmt_tx,
1224 mgmt_tx->buff, mgmt_tx->size,
1225 wilc_wfi_mgmt_tx_complete);
1226
1227 out:
1228
1229 return ret;
1230 }
1231
1232 static int mgmt_tx_cancel_wait(struct wiphy *wiphy,
1233 struct wireless_dev *wdev,
1234 u64 cookie)
1235 {
1236 struct wilc_vif *vif = netdev_priv(wdev->netdev);
1237 struct wilc_priv *priv = &vif->priv;
1238 struct host_if_drv *wfi_drv = priv->hif_drv;
1239
1240 wfi_drv->p2p_timeout = jiffies;
1241
1242 if (!priv->p2p_listen_state) {
1243 struct wilc_wfi_p2p_listen_params *params;
1244
1245 params = &priv->remain_on_ch_params;
1246
1247 cfg80211_remain_on_channel_expired(wdev,
1248 params->listen_cookie,
1249 params->listen_ch,
1250 GFP_KERNEL);
1251 }
1252
1253 return 0;
1254 }
1255
1256 void wilc_update_mgmt_frame_registrations(struct wiphy *wiphy,
1257 struct wireless_dev *wdev,
1258 struct mgmt_frame_regs *upd)
1259 {
1260 struct wilc *wl = wiphy_priv(wiphy);
1261 struct wilc_vif *vif = netdev_priv(wdev->netdev);
1262 u32 presp_bit = BIT(IEEE80211_STYPE_PROBE_REQ >> 4);
1263 u32 action_bit = BIT(IEEE80211_STYPE_ACTION >> 4);
1264 u32 pauth_bit = BIT(IEEE80211_STYPE_AUTH >> 4);
1265
1266 if (wl->initialized) {
1267 bool prev = vif->mgmt_reg_stypes & presp_bit;
1268 bool now = upd->interface_stypes & presp_bit;
1269
1270 if (now != prev)
1271 wilc_frame_register(vif, IEEE80211_STYPE_PROBE_REQ, now);
1272
1273 prev = vif->mgmt_reg_stypes & action_bit;
1274 now = upd->interface_stypes & action_bit;
1275
1276 if (now != prev)
1277 wilc_frame_register(vif, IEEE80211_STYPE_ACTION, now);
1278
1279 prev = vif->mgmt_reg_stypes & pauth_bit;
1280 now = upd->interface_stypes & pauth_bit;
1281 if (now != prev)
1282 wilc_frame_register(vif, IEEE80211_STYPE_AUTH, now);
1283 }
1284
1285 vif->mgmt_reg_stypes =
1286 upd->interface_stypes & (presp_bit | action_bit | pauth_bit);
1287 }
1288
1289 static int external_auth(struct wiphy *wiphy, struct net_device *dev,
1290 struct cfg80211_external_auth_params *auth)
1291 {
1292 struct wilc_vif *vif = netdev_priv(dev);
1293
1294 if (auth->status == WLAN_STATUS_SUCCESS)
1295 wilc_set_external_auth_param(vif, auth);
1296
1297 return 0;
1298 }
1299
1300 static int set_cqm_rssi_config(struct wiphy *wiphy, struct net_device *dev,
1301 s32 rssi_thold, u32 rssi_hyst)
1302 {
1303 return 0;
1304 }
1305
1306 static int dump_station(struct wiphy *wiphy, struct net_device *dev,
1307 int idx, u8 *mac, struct station_info *sinfo)
1308 {
1309 struct wilc_vif *vif = netdev_priv(dev);
1310 int ret;
1311
1312 if (idx != 0)
1313 return -ENOENT;
1314
1315 ret = wilc_get_rssi(vif, &sinfo->signal);
1316 if (ret)
1317 return ret;
1318
1319 sinfo->filled |= BIT_ULL(NL80211_STA_INFO_SIGNAL);
1320 memcpy(mac, vif->priv.associated_bss, ETH_ALEN);
1321 return 0;
1322 }
1323
1324 static int set_power_mgmt(struct wiphy *wiphy, struct net_device *dev,
1325 bool enabled, int timeout)
1326 {
1327 struct wilc_vif *vif = netdev_priv(dev);
1328 struct wilc_priv *priv = &vif->priv;
1329
1330 if (!priv->hif_drv)
1331 return -EIO;
1332
1333 wilc_set_power_mgmt(vif, enabled, timeout);
1334
1335 return 0;
1336 }
1337
1338 static int change_virtual_intf(struct wiphy *wiphy, struct net_device *dev,
1339 enum nl80211_iftype type,
1340 struct vif_params *params)
1341 {
1342 struct wilc *wl = wiphy_priv(wiphy);
1343 struct wilc_vif *vif = netdev_priv(dev);
1344 struct wilc_priv *priv = &vif->priv;
1345
1346 switch (type) {
1347 case NL80211_IFTYPE_STATION:
1348 vif->connecting = false;
1349 dev->ieee80211_ptr->iftype = type;
1350 priv->wdev.iftype = type;
1351 vif->monitor_flag = 0;
1352 if (vif->iftype == WILC_AP_MODE || vif->iftype == WILC_GO_MODE)
1353 wilc_wfi_deinit_mon_interface(wl, true);
1354 vif->iftype = WILC_STATION_MODE;
1355
1356 if (wl->initialized)
1357 wilc_set_operation_mode(vif, wilc_get_vif_idx(vif),
1358 WILC_STATION_MODE, vif->idx);
1359
1360 memset(priv->assoc_stainfo.sta_associated_bss, 0,
1361 WILC_MAX_NUM_STA * ETH_ALEN);
1362 break;
1363
1364 case NL80211_IFTYPE_P2P_CLIENT:
1365 vif->connecting = false;
1366 dev->ieee80211_ptr->iftype = type;
1367 priv->wdev.iftype = type;
1368 vif->monitor_flag = 0;
1369 vif->iftype = WILC_CLIENT_MODE;
1370
1371 if (wl->initialized)
1372 wilc_set_operation_mode(vif, wilc_get_vif_idx(vif),
1373 WILC_STATION_MODE, vif->idx);
1374 break;
1375
1376 case NL80211_IFTYPE_AP:
1377 dev->ieee80211_ptr->iftype = type;
1378 priv->wdev.iftype = type;
1379 vif->iftype = WILC_AP_MODE;
1380
1381 if (wl->initialized)
1382 wilc_set_operation_mode(vif, wilc_get_vif_idx(vif),
1383 WILC_AP_MODE, vif->idx);
1384 break;
1385
1386 case NL80211_IFTYPE_P2P_GO:
1387 dev->ieee80211_ptr->iftype = type;
1388 priv->wdev.iftype = type;
1389 vif->iftype = WILC_GO_MODE;
1390
1391 if (wl->initialized)
1392 wilc_set_operation_mode(vif, wilc_get_vif_idx(vif),
1393 WILC_AP_MODE, vif->idx);
1394 break;
1395
1396 default:
1397 netdev_err(dev, "Unknown interface type= %d\n", type);
1398 return -EINVAL;
1399 }
1400
1401 return 0;
1402 }
1403
1404 static int start_ap(struct wiphy *wiphy, struct net_device *dev,
1405 struct cfg80211_ap_settings *settings)
1406 {
1407 struct wilc_vif *vif = netdev_priv(dev);
1408 int ret;
1409
1410 ret = set_channel(wiphy, &settings->chandef);
1411 if (ret != 0)
1412 netdev_err(dev, "Error in setting channel\n");
1413
1414 wilc_wlan_set_bssid(dev, dev->dev_addr, WILC_AP_MODE);
1415
1416 return wilc_add_beacon(vif, settings->beacon_interval,
1417 settings->dtim_period, &settings->beacon);
1418 }
1419
1420 static int change_beacon(struct wiphy *wiphy, struct net_device *dev,
1421 struct cfg80211_beacon_data *beacon)
1422 {
1423 struct wilc_vif *vif = netdev_priv(dev);
1424
1425 return wilc_add_beacon(vif, 0, 0, beacon);
1426 }
1427
1428 static int stop_ap(struct wiphy *wiphy, struct net_device *dev,
1429 unsigned int link_id)
1430 {
1431 int ret;
1432 struct wilc_vif *vif = netdev_priv(dev);
1433
1434 wilc_wlan_set_bssid(dev, NULL, WILC_AP_MODE);
1435
1436 ret = wilc_del_beacon(vif);
1437
1438 if (ret)
1439 netdev_err(dev, "Host delete beacon fail\n");
1440
1441 return ret;
1442 }
1443
1444 static int add_station(struct wiphy *wiphy, struct net_device *dev,
1445 const u8 *mac, struct station_parameters *params)
1446 {
1447 int ret = 0;
1448 struct wilc_vif *vif = netdev_priv(dev);
1449 struct wilc_priv *priv = &vif->priv;
1450
1451 if (vif->iftype == WILC_AP_MODE || vif->iftype == WILC_GO_MODE) {
1452 memcpy(priv->assoc_stainfo.sta_associated_bss[params->aid], mac,
1453 ETH_ALEN);
1454
1455 ret = wilc_add_station(vif, mac, params);
1456 if (ret)
1457 netdev_err(dev, "Host add station fail\n");
1458 }
1459
1460 return ret;
1461 }
1462
1463 static int del_station(struct wiphy *wiphy, struct net_device *dev,
1464 struct station_del_parameters *params)
1465 {
1466 const u8 *mac = params->mac;
1467 int ret = 0;
1468 struct wilc_vif *vif = netdev_priv(dev);
1469 struct wilc_priv *priv = &vif->priv;
1470 struct sta_info *info;
1471
1472 if (!(vif->iftype == WILC_AP_MODE || vif->iftype == WILC_GO_MODE))
1473 return ret;
1474
1475 info = &priv->assoc_stainfo;
1476
1477 if (!mac)
1478 ret = wilc_del_allstation(vif, info->sta_associated_bss);
1479
1480 ret = wilc_del_station(vif, mac);
1481 if (ret)
1482 netdev_err(dev, "Host delete station fail\n");
1483 return ret;
1484 }
1485
1486 static int change_station(struct wiphy *wiphy, struct net_device *dev,
1487 const u8 *mac, struct station_parameters *params)
1488 {
1489 int ret = 0;
1490 struct wilc_vif *vif = netdev_priv(dev);
1491
1492 if (vif->iftype == WILC_AP_MODE || vif->iftype == WILC_GO_MODE) {
1493 ret = wilc_edit_station(vif, mac, params);
1494 if (ret)
1495 netdev_err(dev, "Host edit station fail\n");
1496 }
1497 return ret;
1498 }
1499
1500 static struct wilc_vif *wilc_get_vif_from_type(struct wilc *wl, int type)
1501 {
1502 struct wilc_vif *vif;
1503
1504 list_for_each_entry_rcu(vif, &wl->vif_list, list) {
1505 if (vif->iftype == type)
1506 return vif;
1507 }
1508
1509 return NULL;
1510 }
1511
1512 static struct wireless_dev *add_virtual_intf(struct wiphy *wiphy,
1513 const char *name,
1514 unsigned char name_assign_type,
1515 enum nl80211_iftype type,
1516 struct vif_params *params)
1517 {
1518 struct wilc *wl = wiphy_priv(wiphy);
1519 struct wilc_vif *vif;
1520 struct wireless_dev *wdev;
1521 int iftype;
1522
1523 if (type == NL80211_IFTYPE_MONITOR) {
1524 struct net_device *ndev;
1525 int srcu_idx;
1526
1527 srcu_idx = srcu_read_lock(&wl->srcu);
1528 vif = wilc_get_vif_from_type(wl, WILC_AP_MODE);
1529 if (!vif) {
1530 vif = wilc_get_vif_from_type(wl, WILC_GO_MODE);
1531 if (!vif) {
1532 srcu_read_unlock(&wl->srcu, srcu_idx);
1533 goto validate_interface;
1534 }
1535 }
1536
1537 if (vif->monitor_flag) {
1538 srcu_read_unlock(&wl->srcu, srcu_idx);
1539 goto validate_interface;
1540 }
1541
1542 ndev = wilc_wfi_init_mon_interface(wl, name, vif->ndev);
1543 if (ndev) {
1544 vif->monitor_flag = 1;
1545 } else {
1546 srcu_read_unlock(&wl->srcu, srcu_idx);
1547 return ERR_PTR(-EINVAL);
1548 }
1549
1550 wdev = &vif->priv.wdev;
1551 srcu_read_unlock(&wl->srcu, srcu_idx);
1552 return wdev;
1553 }
1554
1555 validate_interface:
1556 mutex_lock(&wl->vif_mutex);
1557 if (wl->vif_num == WILC_NUM_CONCURRENT_IFC) {
1558 pr_err("Reached maximum number of interface\n");
1559 mutex_unlock(&wl->vif_mutex);
1560 return ERR_PTR(-EINVAL);
1561 }
1562 mutex_unlock(&wl->vif_mutex);
1563
1564 switch (type) {
1565 case NL80211_IFTYPE_STATION:
1566 iftype = WILC_STATION_MODE;
1567 break;
1568 case NL80211_IFTYPE_AP:
1569 iftype = WILC_AP_MODE;
1570 break;
1571 default:
1572 return ERR_PTR(-EOPNOTSUPP);
1573 }
1574
1575 vif = wilc_netdev_ifc_init(wl, name, iftype, type, true);
1576 if (IS_ERR(vif))
1577 return ERR_CAST(vif);
1578
1579 return &vif->priv.wdev;
1580 }
1581
1582 static int del_virtual_intf(struct wiphy *wiphy, struct wireless_dev *wdev)
1583 {
1584 struct wilc *wl = wiphy_priv(wiphy);
1585 struct wilc_vif *vif;
1586
1587 if (wdev->iftype == NL80211_IFTYPE_AP ||
1588 wdev->iftype == NL80211_IFTYPE_P2P_GO)
1589 wilc_wfi_deinit_mon_interface(wl, true);
1590 vif = netdev_priv(wdev->netdev);
1591 cfg80211_stop_iface(wiphy, wdev, GFP_KERNEL);
1592 cfg80211_unregister_netdevice(vif->ndev);
1593 vif->monitor_flag = 0;
1594
1595 wilc_set_operation_mode(vif, 0, 0, 0);
1596 mutex_lock(&wl->vif_mutex);
1597 list_del_rcu(&vif->list);
1598 wl->vif_num--;
1599 mutex_unlock(&wl->vif_mutex);
1600 synchronize_srcu(&wl->srcu);
1601 return 0;
1602 }
1603
1604 static int wilc_suspend(struct wiphy *wiphy, struct cfg80211_wowlan *wow)
1605 {
1606 struct wilc *wl = wiphy_priv(wiphy);
1607
1608 if (!wow && wilc_wlan_get_num_conn_ifcs(wl))
1609 wl->suspend_event = true;
1610 else
1611 wl->suspend_event = false;
1612
1613 return 0;
1614 }
1615
1616 static int wilc_resume(struct wiphy *wiphy)
1617 {
1618 return 0;
1619 }
1620
1621 static void wilc_set_wakeup(struct wiphy *wiphy, bool enabled)
1622 {
1623 struct wilc *wl = wiphy_priv(wiphy);
1624 struct wilc_vif *vif;
1625 int srcu_idx;
1626
1627 srcu_idx = srcu_read_lock(&wl->srcu);
1628 vif = wilc_get_wl_to_vif(wl);
1629 if (IS_ERR(vif)) {
1630 srcu_read_unlock(&wl->srcu, srcu_idx);
1631 return;
1632 }
1633
1634 netdev_info(vif->ndev, "cfg set wake up = %d\n", enabled);
1635 wilc_set_wowlan_trigger(vif, enabled);
1636 srcu_read_unlock(&wl->srcu, srcu_idx);
1637 }
1638
1639 static int set_tx_power(struct wiphy *wiphy, struct wireless_dev *wdev,
1640 enum nl80211_tx_power_setting type, int mbm)
1641 {
1642 int ret;
1643 int srcu_idx;
1644 s32 tx_power = MBM_TO_DBM(mbm);
1645 struct wilc *wl = wiphy_priv(wiphy);
1646 struct wilc_vif *vif;
1647
1648 if (!wl->initialized)
1649 return -EIO;
1650
1651 srcu_idx = srcu_read_lock(&wl->srcu);
1652 vif = wilc_get_wl_to_vif(wl);
1653 if (IS_ERR(vif)) {
1654 srcu_read_unlock(&wl->srcu, srcu_idx);
1655 return -EINVAL;
1656 }
1657
1658 netdev_info(vif->ndev, "Setting tx power %d\n", tx_power);
1659 if (tx_power < 0)
1660 tx_power = 0;
1661 else if (tx_power > 18)
1662 tx_power = 18;
1663 ret = wilc_set_tx_power(vif, tx_power);
1664 if (ret)
1665 netdev_err(vif->ndev, "Failed to set tx power\n");
1666 srcu_read_unlock(&wl->srcu, srcu_idx);
1667
1668 return ret;
1669 }
1670
1671 static int get_tx_power(struct wiphy *wiphy, struct wireless_dev *wdev,
1672 int *dbm)
1673 {
1674 int ret;
1675 struct wilc_vif *vif = netdev_priv(wdev->netdev);
1676 struct wilc *wl = vif->wilc;
1677
1678
1679 if (!wl->initialized)
1680 return -EIO;
1681
1682 ret = wilc_get_tx_power(vif, (u8 *)dbm);
1683 if (ret)
1684 netdev_err(vif->ndev, "Failed to get tx power\n");
1685
1686 return ret;
1687 }
1688
1689 static const struct cfg80211_ops wilc_cfg80211_ops = {
1690 .set_monitor_channel = set_channel,
1691 .scan = scan,
1692 .connect = connect,
1693 .disconnect = disconnect,
1694 .add_key = add_key,
1695 .del_key = del_key,
1696 .get_key = get_key,
1697 .set_default_key = set_default_key,
1698 .set_default_mgmt_key = set_default_mgmt_key,
1699 .add_virtual_intf = add_virtual_intf,
1700 .del_virtual_intf = del_virtual_intf,
1701 .change_virtual_intf = change_virtual_intf,
1702
1703 .start_ap = start_ap,
1704 .change_beacon = change_beacon,
1705 .stop_ap = stop_ap,
1706 .add_station = add_station,
1707 .del_station = del_station,
1708 .change_station = change_station,
1709 .get_station = get_station,
1710 .dump_station = dump_station,
1711 .change_bss = change_bss,
1712 .set_wiphy_params = set_wiphy_params,
1713
1714 .external_auth = external_auth,
1715 .set_pmksa = set_pmksa,
1716 .del_pmksa = del_pmksa,
1717 .flush_pmksa = flush_pmksa,
1718 .remain_on_channel = remain_on_channel,
1719 .cancel_remain_on_channel = cancel_remain_on_channel,
1720 .mgmt_tx_cancel_wait = mgmt_tx_cancel_wait,
1721 .mgmt_tx = mgmt_tx,
1722 .update_mgmt_frame_registrations = wilc_update_mgmt_frame_registrations,
1723 .set_power_mgmt = set_power_mgmt,
1724 .set_cqm_rssi_config = set_cqm_rssi_config,
1725
1726 .suspend = wilc_suspend,
1727 .resume = wilc_resume,
1728 .set_wakeup = wilc_set_wakeup,
1729 .set_tx_power = set_tx_power,
1730 .get_tx_power = get_tx_power,
1731
1732 };
1733
1734 static void wlan_init_locks(struct wilc *wl)
1735 {
1736 mutex_init(&wl->hif_cs);
1737 mutex_init(&wl->rxq_cs);
1738 mutex_init(&wl->cfg_cmd_lock);
1739 mutex_init(&wl->vif_mutex);
1740 mutex_init(&wl->deinit_lock);
1741
1742 spin_lock_init(&wl->txq_spinlock);
1743 mutex_init(&wl->txq_add_to_head_cs);
1744
1745 init_completion(&wl->txq_event);
1746 init_completion(&wl->cfg_event);
1747 init_completion(&wl->sync_event);
1748 init_completion(&wl->txq_thread_started);
1749 init_srcu_struct(&wl->srcu);
1750 }
1751
1752 void wlan_deinit_locks(struct wilc *wilc)
1753 {
1754 mutex_destroy(&wilc->hif_cs);
1755 mutex_destroy(&wilc->rxq_cs);
1756 mutex_destroy(&wilc->cfg_cmd_lock);
1757 mutex_destroy(&wilc->txq_add_to_head_cs);
1758 mutex_destroy(&wilc->vif_mutex);
1759 mutex_destroy(&wilc->deinit_lock);
1760 cleanup_srcu_struct(&wilc->srcu);
1761 }
1762
1763 int wilc_cfg80211_init(struct wilc **wilc, struct device *dev, int io_type,
1764 const struct wilc_hif_func *ops)
1765 {
1766 struct wilc *wl;
1767 struct wilc_vif *vif;
1768 int ret, i;
1769
1770 wl = wilc_create_wiphy(dev);
1771 if (!wl)
1772 return -EINVAL;
1773
1774 wlan_init_locks(wl);
1775
1776 ret = wilc_wlan_cfg_init(wl);
1777 if (ret)
1778 goto free_wl;
1779
1780 *wilc = wl;
1781 wl->io_type = io_type;
1782 wl->hif_func = ops;
1783
1784 for (i = 0; i < NQUEUES; i++)
1785 INIT_LIST_HEAD(&wl->txq[i].txq_head.list);
1786
1787 INIT_LIST_HEAD(&wl->rxq_head.list);
1788 INIT_LIST_HEAD(&wl->vif_list);
1789
1790 vif = wilc_netdev_ifc_init(wl, "wlan%d", WILC_STATION_MODE,
1791 NL80211_IFTYPE_STATION, false);
1792 if (IS_ERR(vif)) {
1793 ret = PTR_ERR(vif);
1794 goto free_cfg;
1795 }
1796
1797 return 0;
1798
1799 free_cfg:
1800 wilc_wlan_cfg_deinit(wl);
1801
1802 free_wl:
1803 wlan_deinit_locks(wl);
1804 wiphy_unregister(wl->wiphy);
1805 wiphy_free(wl->wiphy);
1806 return ret;
1807 }
1808 EXPORT_SYMBOL_GPL(wilc_cfg80211_init);
1809
1810 struct wilc *wilc_create_wiphy(struct device *dev)
1811 {
1812 struct wiphy *wiphy;
1813 struct wilc *wl;
1814 int ret;
1815
1816 wiphy = wiphy_new(&wilc_cfg80211_ops, sizeof(*wl));
1817 if (!wiphy)
1818 return NULL;
1819
1820 wl = wiphy_priv(wiphy);
1821
1822 memcpy(wl->bitrates, wilc_bitrates, sizeof(wilc_bitrates));
1823 memcpy(wl->channels, wilc_2ghz_channels, sizeof(wilc_2ghz_channels));
1824 wl->band.bitrates = wl->bitrates;
1825 wl->band.n_bitrates = ARRAY_SIZE(wl->bitrates);
1826 wl->band.channels = wl->channels;
1827 wl->band.n_channels = ARRAY_SIZE(wilc_2ghz_channels);
1828
1829 wl->band.ht_cap.ht_supported = 1;
1830 wl->band.ht_cap.cap |= (1 << IEEE80211_HT_CAP_RX_STBC_SHIFT);
1831 wl->band.ht_cap.mcs.rx_mask[0] = 0xff;
1832 wl->band.ht_cap.ampdu_factor = IEEE80211_HT_MAX_AMPDU_8K;
1833 wl->band.ht_cap.ampdu_density = IEEE80211_HT_MPDU_DENSITY_NONE;
1834
1835 wiphy->bands[NL80211_BAND_2GHZ] = &wl->band;
1836
1837 wiphy->max_scan_ssids = WILC_MAX_NUM_PROBED_SSID;
1838 #ifdef CONFIG_PM
1839 wiphy->wowlan = &wowlan_support;
1840 #endif
1841 wiphy->max_num_pmkids = WILC_MAX_NUM_PMKIDS;
1842 wiphy->max_scan_ie_len = 1000;
1843 wiphy->signal_type = CFG80211_SIGNAL_TYPE_MBM;
1844 memcpy(wl->cipher_suites, wilc_cipher_suites,
1845 sizeof(wilc_cipher_suites));
1846 wiphy->cipher_suites = wl->cipher_suites;
1847 wiphy->n_cipher_suites = ARRAY_SIZE(wilc_cipher_suites);
1848 wiphy->mgmt_stypes = wilc_wfi_cfg80211_mgmt_types;
1849
1850 wiphy->max_remain_on_channel_duration = 500;
1851 wiphy->interface_modes = BIT(NL80211_IFTYPE_STATION) |
1852 BIT(NL80211_IFTYPE_AP) |
1853 BIT(NL80211_IFTYPE_MONITOR) |
1854 BIT(NL80211_IFTYPE_P2P_GO) |
1855 BIT(NL80211_IFTYPE_P2P_CLIENT);
1856 wiphy->flags |= WIPHY_FLAG_HAS_REMAIN_ON_CHANNEL;
1857 wiphy->features |= NL80211_FEATURE_SAE;
1858 set_wiphy_dev(wiphy, dev);
1859 wl->wiphy = wiphy;
1860 ret = wiphy_register(wiphy);
1861 if (ret) {
1862 wiphy_free(wiphy);
1863 return NULL;
1864 }
1865 return wl;
1866 }
1867
1868 int wilc_init_host_int(struct net_device *net)
1869 {
1870 int ret;
1871 struct wilc_vif *vif = netdev_priv(net);
1872 struct wilc_priv *priv = &vif->priv;
1873
1874 priv->p2p_listen_state = false;
1875
1876 mutex_init(&priv->scan_req_lock);
1877 ret = wilc_init(net, &priv->hif_drv);
1878 if (ret)
1879 netdev_err(net, "Error while initializing hostinterface\n");
1880
1881 return ret;
1882 }
1883
1884 void wilc_deinit_host_int(struct net_device *net)
1885 {
1886 int ret;
1887 struct wilc_vif *vif = netdev_priv(net);
1888 struct wilc_priv *priv = &vif->priv;
1889
1890 priv->p2p_listen_state = false;
1891
1892 flush_workqueue(vif->wilc->hif_workqueue);
1893 mutex_destroy(&priv->scan_req_lock);
1894 ret = wilc_deinit(vif);
1895
1896 if (ret)
1897 netdev_err(net, "Error while deinitializing host interface\n");
1898 }
1899