blob: 72b8f177445de989486f465d775e32d3347073e3 [file] [log] [blame]
Kalle Valo5e3dd152013-06-12 20:52:10 +03001/*
2 * Copyright (c) 2005-2011 Atheros Communications Inc.
3 * Copyright (c) 2011-2013 Qualcomm Atheros, Inc.
4 *
5 * Permission to use, copy, modify, and/or distribute this software for any
6 * purpose with or without fee is hereby granted, provided that the above
7 * copyright notice and this permission notice appear in all copies.
8 *
9 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
10 * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
11 * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
12 * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
13 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
14 * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
15 * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
16 */
17
18#include "mac.h"
19
20#include <net/mac80211.h>
21#include <linux/etherdevice.h>
22
Michal Kazior8cd13ca2013-07-16 09:38:54 +020023#include "hif.h"
Kalle Valo5e3dd152013-06-12 20:52:10 +030024#include "core.h"
25#include "debug.h"
26#include "wmi.h"
27#include "htt.h"
28#include "txrx.h"
Kalle Valo43d2a302014-09-10 18:23:30 +030029#include "testmode.h"
Michal Kaziord7579d12014-12-03 10:10:54 +020030#include "wmi.h"
Michal Kaziorb4aa5392015-03-31 10:26:24 +000031#include "wmi-tlv.h"
Michal Kaziord7579d12014-12-03 10:10:54 +020032#include "wmi-ops.h"
Janusz Dziedzic5fd3ac32015-03-23 17:32:53 +020033#include "wow.h"
Kalle Valo5e3dd152013-06-12 20:52:10 +030034
Michal Kaziordcc33092015-03-30 09:51:54 +030035/*********/
36/* Rates */
37/*********/
38
Michal Kaziordcc33092015-03-30 09:51:54 +030039static struct ieee80211_rate ath10k_rates[] = {
Michal Kazior5528e032015-03-30 09:51:56 +030040 { .bitrate = 10,
41 .hw_value = ATH10K_HW_RATE_CCK_LP_1M },
42 { .bitrate = 20,
43 .hw_value = ATH10K_HW_RATE_CCK_LP_2M,
44 .hw_value_short = ATH10K_HW_RATE_CCK_SP_2M,
45 .flags = IEEE80211_RATE_SHORT_PREAMBLE },
46 { .bitrate = 55,
47 .hw_value = ATH10K_HW_RATE_CCK_LP_5_5M,
48 .hw_value_short = ATH10K_HW_RATE_CCK_SP_5_5M,
49 .flags = IEEE80211_RATE_SHORT_PREAMBLE },
50 { .bitrate = 110,
51 .hw_value = ATH10K_HW_RATE_CCK_LP_11M,
52 .hw_value_short = ATH10K_HW_RATE_CCK_SP_11M,
53 .flags = IEEE80211_RATE_SHORT_PREAMBLE },
Michal Kazior5653b392015-03-30 09:51:54 +030054
Michal Kazioraf001482015-03-30 09:51:56 +030055 { .bitrate = 60, .hw_value = ATH10K_HW_RATE_OFDM_6M },
56 { .bitrate = 90, .hw_value = ATH10K_HW_RATE_OFDM_9M },
57 { .bitrate = 120, .hw_value = ATH10K_HW_RATE_OFDM_12M },
58 { .bitrate = 180, .hw_value = ATH10K_HW_RATE_OFDM_18M },
59 { .bitrate = 240, .hw_value = ATH10K_HW_RATE_OFDM_24M },
60 { .bitrate = 360, .hw_value = ATH10K_HW_RATE_OFDM_36M },
61 { .bitrate = 480, .hw_value = ATH10K_HW_RATE_OFDM_48M },
62 { .bitrate = 540, .hw_value = ATH10K_HW_RATE_OFDM_54M },
Michal Kaziordcc33092015-03-30 09:51:54 +030063};
64
Michal Kazior8d7aa6b2015-03-30 09:51:57 +030065#define ATH10K_MAC_FIRST_OFDM_RATE_IDX 4
66
67#define ath10k_a_rates (ath10k_rates + ATH10K_MAC_FIRST_OFDM_RATE_IDX)
68#define ath10k_a_rates_size (ARRAY_SIZE(ath10k_rates) - \
69 ATH10K_MAC_FIRST_OFDM_RATE_IDX)
Michal Kaziordcc33092015-03-30 09:51:54 +030070#define ath10k_g_rates (ath10k_rates + 0)
71#define ath10k_g_rates_size (ARRAY_SIZE(ath10k_rates))
72
Michal Kazior486017c2015-03-30 09:51:54 +030073static bool ath10k_mac_bitrate_is_cck(int bitrate)
74{
75 switch (bitrate) {
76 case 10:
77 case 20:
78 case 55:
79 case 110:
80 return true;
81 }
82
83 return false;
84}
85
86static u8 ath10k_mac_bitrate_to_rate(int bitrate)
87{
88 return DIV_ROUND_UP(bitrate, 5) |
89 (ath10k_mac_bitrate_is_cck(bitrate) ? BIT(7) : 0);
90}
91
Michal Kazior5528e032015-03-30 09:51:56 +030092u8 ath10k_mac_hw_rate_to_idx(const struct ieee80211_supported_band *sband,
Yanbo Li4b7f3532015-11-12 10:36:10 -080093 u8 hw_rate, bool cck)
Michal Kazior5528e032015-03-30 09:51:56 +030094{
95 const struct ieee80211_rate *rate;
96 int i;
97
98 for (i = 0; i < sband->n_bitrates; i++) {
99 rate = &sband->bitrates[i];
100
Yanbo Li4b7f3532015-11-12 10:36:10 -0800101 if (ath10k_mac_bitrate_is_cck(rate->bitrate) != cck)
102 continue;
103
Michal Kazior5528e032015-03-30 09:51:56 +0300104 if (rate->hw_value == hw_rate)
105 return i;
106 else if (rate->flags & IEEE80211_RATE_SHORT_PREAMBLE &&
107 rate->hw_value_short == hw_rate)
108 return i;
109 }
110
111 return 0;
112}
113
Michal Kazior01cebe12015-03-30 09:51:56 +0300114u8 ath10k_mac_bitrate_to_idx(const struct ieee80211_supported_band *sband,
115 u32 bitrate)
116{
117 int i;
118
119 for (i = 0; i < sband->n_bitrates; i++)
120 if (sband->bitrates[i].bitrate == bitrate)
121 return i;
122
123 return 0;
124}
125
Michal Kazior3ae54222015-03-31 10:49:20 +0000126static int ath10k_mac_get_max_vht_mcs_map(u16 mcs_map, int nss)
127{
128 switch ((mcs_map >> (2 * nss)) & 0x3) {
129 case IEEE80211_VHT_MCS_SUPPORT_0_7: return BIT(8) - 1;
130 case IEEE80211_VHT_MCS_SUPPORT_0_8: return BIT(9) - 1;
131 case IEEE80211_VHT_MCS_SUPPORT_0_9: return BIT(10) - 1;
132 }
133 return 0;
134}
135
Michal Kazior45c9abc2015-04-21 20:42:58 +0300136static u32
137ath10k_mac_max_ht_nss(const u8 ht_mcs_mask[IEEE80211_HT_MCS_MASK_LEN])
138{
139 int nss;
140
141 for (nss = IEEE80211_HT_MCS_MASK_LEN - 1; nss >= 0; nss--)
142 if (ht_mcs_mask[nss])
143 return nss + 1;
144
145 return 1;
146}
147
148static u32
149ath10k_mac_max_vht_nss(const u16 vht_mcs_mask[NL80211_VHT_NSS_MAX])
150{
151 int nss;
152
153 for (nss = NL80211_VHT_NSS_MAX - 1; nss >= 0; nss--)
154 if (vht_mcs_mask[nss])
155 return nss + 1;
156
157 return 1;
158}
Kalle Valo5e3dd152013-06-12 20:52:10 +0300159
160/**********/
161/* Crypto */
162/**********/
163
164static int ath10k_send_key(struct ath10k_vif *arvif,
165 struct ieee80211_key_conf *key,
166 enum set_key_cmd cmd,
Michal Kazior370e5672015-02-18 14:02:26 +0100167 const u8 *macaddr, u32 flags)
Kalle Valo5e3dd152013-06-12 20:52:10 +0300168{
Michal Kazior7aa7a722014-08-25 12:09:38 +0200169 struct ath10k *ar = arvif->ar;
Kalle Valo5e3dd152013-06-12 20:52:10 +0300170 struct wmi_vdev_install_key_arg arg = {
171 .vdev_id = arvif->vdev_id,
172 .key_idx = key->keyidx,
173 .key_len = key->keylen,
174 .key_data = key->key,
Michal Kazior370e5672015-02-18 14:02:26 +0100175 .key_flags = flags,
Kalle Valo5e3dd152013-06-12 20:52:10 +0300176 .macaddr = macaddr,
177 };
178
Michal Kazior548db542013-07-05 16:15:15 +0300179 lockdep_assert_held(&arvif->ar->conf_mutex);
180
Kalle Valo5e3dd152013-06-12 20:52:10 +0300181 switch (key->cipher) {
182 case WLAN_CIPHER_SUITE_CCMP:
183 arg.key_cipher = WMI_CIPHER_AES_CCM;
Marek Kwaczynskie4e82e92015-01-24 12:14:53 +0200184 key->flags |= IEEE80211_KEY_FLAG_GENERATE_IV_MGMT;
Kalle Valo5e3dd152013-06-12 20:52:10 +0300185 break;
186 case WLAN_CIPHER_SUITE_TKIP:
Kalle Valo5e3dd152013-06-12 20:52:10 +0300187 arg.key_cipher = WMI_CIPHER_TKIP;
188 arg.key_txmic_len = 8;
189 arg.key_rxmic_len = 8;
190 break;
191 case WLAN_CIPHER_SUITE_WEP40:
192 case WLAN_CIPHER_SUITE_WEP104:
193 arg.key_cipher = WMI_CIPHER_WEP;
Kalle Valo5e3dd152013-06-12 20:52:10 +0300194 break;
Johannes Berg3cb10942015-01-22 21:38:45 +0100195 case WLAN_CIPHER_SUITE_AES_CMAC:
Bartosz Markowskid7131c02015-03-10 14:32:19 +0100196 WARN_ON(1);
197 return -EINVAL;
Kalle Valo5e3dd152013-06-12 20:52:10 +0300198 default:
Michal Kazior7aa7a722014-08-25 12:09:38 +0200199 ath10k_warn(ar, "cipher %d is not supported\n", key->cipher);
Kalle Valo5e3dd152013-06-12 20:52:10 +0300200 return -EOPNOTSUPP;
201 }
202
Kalle Valob9e284e2015-10-05 17:56:35 +0300203 if (test_bit(ATH10K_FLAG_RAW_MODE, &ar->dev_flags))
David Liuccec9032015-07-24 20:25:32 +0300204 key->flags |= IEEE80211_KEY_FLAG_GENERATE_IV;
David Liuccec9032015-07-24 20:25:32 +0300205
Kalle Valo5e3dd152013-06-12 20:52:10 +0300206 if (cmd == DISABLE_KEY) {
207 arg.key_cipher = WMI_CIPHER_NONE;
208 arg.key_data = NULL;
209 }
210
211 return ath10k_wmi_vdev_install_key(arvif->ar, &arg);
212}
213
214static int ath10k_install_key(struct ath10k_vif *arvif,
215 struct ieee80211_key_conf *key,
216 enum set_key_cmd cmd,
Michal Kazior370e5672015-02-18 14:02:26 +0100217 const u8 *macaddr, u32 flags)
Kalle Valo5e3dd152013-06-12 20:52:10 +0300218{
219 struct ath10k *ar = arvif->ar;
220 int ret;
Nicholas Mc Guire8e9904f52015-03-30 15:39:19 +0300221 unsigned long time_left;
Kalle Valo5e3dd152013-06-12 20:52:10 +0300222
Michal Kazior548db542013-07-05 16:15:15 +0300223 lockdep_assert_held(&ar->conf_mutex);
224
Wolfram Sang16735d02013-11-14 14:32:02 -0800225 reinit_completion(&ar->install_key_done);
Kalle Valo5e3dd152013-06-12 20:52:10 +0300226
David Liuccec9032015-07-24 20:25:32 +0300227 if (arvif->nohwcrypt)
228 return 1;
229
Michal Kazior370e5672015-02-18 14:02:26 +0100230 ret = ath10k_send_key(arvif, key, cmd, macaddr, flags);
Kalle Valo5e3dd152013-06-12 20:52:10 +0300231 if (ret)
232 return ret;
233
Nicholas Mc Guire8e9904f52015-03-30 15:39:19 +0300234 time_left = wait_for_completion_timeout(&ar->install_key_done, 3 * HZ);
235 if (time_left == 0)
Kalle Valo5e3dd152013-06-12 20:52:10 +0300236 return -ETIMEDOUT;
237
238 return 0;
239}
240
241static int ath10k_install_peer_wep_keys(struct ath10k_vif *arvif,
242 const u8 *addr)
243{
244 struct ath10k *ar = arvif->ar;
245 struct ath10k_peer *peer;
246 int ret;
247 int i;
Michal Kazior370e5672015-02-18 14:02:26 +0100248 u32 flags;
Kalle Valo5e3dd152013-06-12 20:52:10 +0300249
250 lockdep_assert_held(&ar->conf_mutex);
251
Michal Kazior8674d902015-08-13 14:10:46 +0200252 if (WARN_ON(arvif->vif->type != NL80211_IFTYPE_AP &&
Peter Oh7c97b722015-12-03 09:50:55 -0800253 arvif->vif->type != NL80211_IFTYPE_ADHOC &&
254 arvif->vif->type != NL80211_IFTYPE_MESH_POINT))
Michal Kazior8674d902015-08-13 14:10:46 +0200255 return -EINVAL;
256
Kalle Valo5e3dd152013-06-12 20:52:10 +0300257 spin_lock_bh(&ar->data_lock);
258 peer = ath10k_peer_find(ar, arvif->vdev_id, addr);
259 spin_unlock_bh(&ar->data_lock);
260
261 if (!peer)
262 return -ENOENT;
263
264 for (i = 0; i < ARRAY_SIZE(arvif->wep_keys); i++) {
265 if (arvif->wep_keys[i] == NULL)
266 continue;
Michal Kazior370e5672015-02-18 14:02:26 +0100267
Michal Kazior8674d902015-08-13 14:10:46 +0200268 switch (arvif->vif->type) {
269 case NL80211_IFTYPE_AP:
270 flags = WMI_KEY_PAIRWISE;
Kalle Valo5e3dd152013-06-12 20:52:10 +0300271
Michal Kazior8674d902015-08-13 14:10:46 +0200272 if (arvif->def_wep_key_idx == i)
273 flags |= WMI_KEY_TX_USAGE;
Michal Kaziorce90b272015-04-10 13:23:21 +0000274
Michal Kazior8674d902015-08-13 14:10:46 +0200275 ret = ath10k_install_key(arvif, arvif->wep_keys[i],
276 SET_KEY, addr, flags);
277 if (ret < 0)
278 return ret;
279 break;
280 case NL80211_IFTYPE_ADHOC:
281 ret = ath10k_install_key(arvif, arvif->wep_keys[i],
282 SET_KEY, addr,
283 WMI_KEY_PAIRWISE);
284 if (ret < 0)
285 return ret;
Kalle Valo5e3dd152013-06-12 20:52:10 +0300286
Michal Kazior8674d902015-08-13 14:10:46 +0200287 ret = ath10k_install_key(arvif, arvif->wep_keys[i],
288 SET_KEY, addr, WMI_KEY_GROUP);
289 if (ret < 0)
290 return ret;
291 break;
292 default:
293 WARN_ON(1);
294 return -EINVAL;
295 }
Kalle Valo5e3dd152013-06-12 20:52:10 +0300296
Sujith Manoharanae167132014-11-25 11:46:59 +0530297 spin_lock_bh(&ar->data_lock);
Kalle Valo5e3dd152013-06-12 20:52:10 +0300298 peer->keys[i] = arvif->wep_keys[i];
Sujith Manoharanae167132014-11-25 11:46:59 +0530299 spin_unlock_bh(&ar->data_lock);
Kalle Valo5e3dd152013-06-12 20:52:10 +0300300 }
301
Michal Kaziorce90b272015-04-10 13:23:21 +0000302 /* In some cases (notably with static WEP IBSS with multiple keys)
303 * multicast Tx becomes broken. Both pairwise and groupwise keys are
304 * installed already. Using WMI_KEY_TX_USAGE in different combinations
305 * didn't seem help. Using def_keyid vdev parameter seems to be
306 * effective so use that.
307 *
308 * FIXME: Revisit. Perhaps this can be done in a less hacky way.
309 */
Michal Kazior8674d902015-08-13 14:10:46 +0200310 if (arvif->vif->type != NL80211_IFTYPE_ADHOC)
311 return 0;
312
Michal Kaziorce90b272015-04-10 13:23:21 +0000313 if (arvif->def_wep_key_idx == -1)
314 return 0;
315
316 ret = ath10k_wmi_vdev_set_param(arvif->ar,
317 arvif->vdev_id,
318 arvif->ar->wmi.vdev_param->def_keyid,
319 arvif->def_wep_key_idx);
320 if (ret) {
321 ath10k_warn(ar, "failed to re-set def wpa key idxon vdev %i: %d\n",
322 arvif->vdev_id, ret);
323 return ret;
324 }
325
Kalle Valo5e3dd152013-06-12 20:52:10 +0300326 return 0;
327}
328
329static int ath10k_clear_peer_keys(struct ath10k_vif *arvif,
330 const u8 *addr)
331{
332 struct ath10k *ar = arvif->ar;
333 struct ath10k_peer *peer;
334 int first_errno = 0;
335 int ret;
336 int i;
Michal Kazior370e5672015-02-18 14:02:26 +0100337 u32 flags = 0;
Kalle Valo5e3dd152013-06-12 20:52:10 +0300338
339 lockdep_assert_held(&ar->conf_mutex);
340
341 spin_lock_bh(&ar->data_lock);
342 peer = ath10k_peer_find(ar, arvif->vdev_id, addr);
343 spin_unlock_bh(&ar->data_lock);
344
345 if (!peer)
346 return -ENOENT;
347
348 for (i = 0; i < ARRAY_SIZE(peer->keys); i++) {
349 if (peer->keys[i] == NULL)
350 continue;
351
SenthilKumar Jegadeesan627613f2015-01-29 13:50:38 +0200352 /* key flags are not required to delete the key */
Kalle Valo5e3dd152013-06-12 20:52:10 +0300353 ret = ath10k_install_key(arvif, peer->keys[i],
Michal Kazior370e5672015-02-18 14:02:26 +0100354 DISABLE_KEY, addr, flags);
David Liuccec9032015-07-24 20:25:32 +0300355 if (ret < 0 && first_errno == 0)
Kalle Valo5e3dd152013-06-12 20:52:10 +0300356 first_errno = ret;
357
David Liuccec9032015-07-24 20:25:32 +0300358 if (ret < 0)
Michal Kazior7aa7a722014-08-25 12:09:38 +0200359 ath10k_warn(ar, "failed to remove peer wep key %d: %d\n",
Kalle Valo5e3dd152013-06-12 20:52:10 +0300360 i, ret);
361
Sujith Manoharanae167132014-11-25 11:46:59 +0530362 spin_lock_bh(&ar->data_lock);
Kalle Valo5e3dd152013-06-12 20:52:10 +0300363 peer->keys[i] = NULL;
Sujith Manoharanae167132014-11-25 11:46:59 +0530364 spin_unlock_bh(&ar->data_lock);
Kalle Valo5e3dd152013-06-12 20:52:10 +0300365 }
366
367 return first_errno;
368}
369
Sujith Manoharan504f6cd2014-11-25 11:46:58 +0530370bool ath10k_mac_is_peer_wep_key_set(struct ath10k *ar, const u8 *addr,
371 u8 keyidx)
372{
373 struct ath10k_peer *peer;
374 int i;
375
376 lockdep_assert_held(&ar->data_lock);
377
378 /* We don't know which vdev this peer belongs to,
379 * since WMI doesn't give us that information.
380 *
381 * FIXME: multi-bss needs to be handled.
382 */
383 peer = ath10k_peer_find(ar, 0, addr);
384 if (!peer)
385 return false;
386
387 for (i = 0; i < ARRAY_SIZE(peer->keys); i++) {
388 if (peer->keys[i] && peer->keys[i]->keyidx == keyidx)
389 return true;
390 }
391
392 return false;
393}
394
Kalle Valo5e3dd152013-06-12 20:52:10 +0300395static int ath10k_clear_vdev_key(struct ath10k_vif *arvif,
396 struct ieee80211_key_conf *key)
397{
398 struct ath10k *ar = arvif->ar;
399 struct ath10k_peer *peer;
400 u8 addr[ETH_ALEN];
401 int first_errno = 0;
402 int ret;
403 int i;
Michal Kazior370e5672015-02-18 14:02:26 +0100404 u32 flags = 0;
Kalle Valo5e3dd152013-06-12 20:52:10 +0300405
406 lockdep_assert_held(&ar->conf_mutex);
407
408 for (;;) {
409 /* since ath10k_install_key we can't hold data_lock all the
410 * time, so we try to remove the keys incrementally */
411 spin_lock_bh(&ar->data_lock);
412 i = 0;
413 list_for_each_entry(peer, &ar->peers, list) {
414 for (i = 0; i < ARRAY_SIZE(peer->keys); i++) {
415 if (peer->keys[i] == key) {
Kalle Valob25f32c2014-09-14 12:50:49 +0300416 ether_addr_copy(addr, peer->addr);
Kalle Valo5e3dd152013-06-12 20:52:10 +0300417 peer->keys[i] = NULL;
418 break;
419 }
420 }
421
422 if (i < ARRAY_SIZE(peer->keys))
423 break;
424 }
425 spin_unlock_bh(&ar->data_lock);
426
427 if (i == ARRAY_SIZE(peer->keys))
428 break;
SenthilKumar Jegadeesan627613f2015-01-29 13:50:38 +0200429 /* key flags are not required to delete the key */
Michal Kazior370e5672015-02-18 14:02:26 +0100430 ret = ath10k_install_key(arvif, key, DISABLE_KEY, addr, flags);
David Liuccec9032015-07-24 20:25:32 +0300431 if (ret < 0 && first_errno == 0)
Kalle Valo5e3dd152013-06-12 20:52:10 +0300432 first_errno = ret;
433
434 if (ret)
Michal Kazior7aa7a722014-08-25 12:09:38 +0200435 ath10k_warn(ar, "failed to remove key for %pM: %d\n",
Kalle Valobe6546f2014-03-25 14:18:51 +0200436 addr, ret);
Kalle Valo5e3dd152013-06-12 20:52:10 +0300437 }
438
439 return first_errno;
440}
441
Michal Kaziorad325cb2015-02-18 14:02:27 +0100442static int ath10k_mac_vif_update_wep_key(struct ath10k_vif *arvif,
443 struct ieee80211_key_conf *key)
444{
445 struct ath10k *ar = arvif->ar;
446 struct ath10k_peer *peer;
447 int ret;
448
449 lockdep_assert_held(&ar->conf_mutex);
450
451 list_for_each_entry(peer, &ar->peers, list) {
452 if (!memcmp(peer->addr, arvif->vif->addr, ETH_ALEN))
453 continue;
454
455 if (!memcmp(peer->addr, arvif->bssid, ETH_ALEN))
456 continue;
457
458 if (peer->keys[key->keyidx] == key)
459 continue;
460
461 ath10k_dbg(ar, ATH10K_DBG_MAC, "mac vif vdev %i update key %i needs update\n",
462 arvif->vdev_id, key->keyidx);
463
464 ret = ath10k_install_peer_wep_keys(arvif, peer->addr);
465 if (ret) {
466 ath10k_warn(ar, "failed to update wep keys on vdev %i for peer %pM: %d\n",
467 arvif->vdev_id, peer->addr, ret);
468 return ret;
469 }
470 }
471
472 return 0;
473}
474
Kalle Valo5e3dd152013-06-12 20:52:10 +0300475/*********************/
476/* General utilities */
477/*********************/
478
479static inline enum wmi_phy_mode
480chan_to_phymode(const struct cfg80211_chan_def *chandef)
481{
482 enum wmi_phy_mode phymode = MODE_UNKNOWN;
483
484 switch (chandef->chan->band) {
485 case IEEE80211_BAND_2GHZ:
486 switch (chandef->width) {
487 case NL80211_CHAN_WIDTH_20_NOHT:
Peter Oh6faab122014-12-18 10:13:00 -0800488 if (chandef->chan->flags & IEEE80211_CHAN_NO_OFDM)
489 phymode = MODE_11B;
490 else
491 phymode = MODE_11G;
Kalle Valo5e3dd152013-06-12 20:52:10 +0300492 break;
493 case NL80211_CHAN_WIDTH_20:
494 phymode = MODE_11NG_HT20;
495 break;
496 case NL80211_CHAN_WIDTH_40:
497 phymode = MODE_11NG_HT40;
498 break;
John W. Linville0f817ed2013-06-27 13:50:09 -0400499 case NL80211_CHAN_WIDTH_5:
500 case NL80211_CHAN_WIDTH_10:
Kalle Valo5e3dd152013-06-12 20:52:10 +0300501 case NL80211_CHAN_WIDTH_80:
502 case NL80211_CHAN_WIDTH_80P80:
503 case NL80211_CHAN_WIDTH_160:
504 phymode = MODE_UNKNOWN;
505 break;
506 }
507 break;
508 case IEEE80211_BAND_5GHZ:
509 switch (chandef->width) {
510 case NL80211_CHAN_WIDTH_20_NOHT:
511 phymode = MODE_11A;
512 break;
513 case NL80211_CHAN_WIDTH_20:
514 phymode = MODE_11NA_HT20;
515 break;
516 case NL80211_CHAN_WIDTH_40:
517 phymode = MODE_11NA_HT40;
518 break;
519 case NL80211_CHAN_WIDTH_80:
520 phymode = MODE_11AC_VHT80;
521 break;
John W. Linville0f817ed2013-06-27 13:50:09 -0400522 case NL80211_CHAN_WIDTH_5:
523 case NL80211_CHAN_WIDTH_10:
Kalle Valo5e3dd152013-06-12 20:52:10 +0300524 case NL80211_CHAN_WIDTH_80P80:
525 case NL80211_CHAN_WIDTH_160:
526 phymode = MODE_UNKNOWN;
527 break;
528 }
529 break;
530 default:
531 break;
532 }
533
534 WARN_ON(phymode == MODE_UNKNOWN);
535 return phymode;
536}
537
538static u8 ath10k_parse_mpdudensity(u8 mpdudensity)
539{
540/*
541 * 802.11n D2.0 defined values for "Minimum MPDU Start Spacing":
542 * 0 for no restriction
543 * 1 for 1/4 us
544 * 2 for 1/2 us
545 * 3 for 1 us
546 * 4 for 2 us
547 * 5 for 4 us
548 * 6 for 8 us
549 * 7 for 16 us
550 */
551 switch (mpdudensity) {
552 case 0:
553 return 0;
554 case 1:
555 case 2:
556 case 3:
557 /* Our lower layer calculations limit our precision to
558 1 microsecond */
559 return 1;
560 case 4:
561 return 2;
562 case 5:
563 return 4;
564 case 6:
565 return 8;
566 case 7:
567 return 16;
568 default:
569 return 0;
570 }
571}
572
Michal Kazior500ff9f2015-03-31 10:26:21 +0000573int ath10k_mac_vif_chan(struct ieee80211_vif *vif,
574 struct cfg80211_chan_def *def)
575{
576 struct ieee80211_chanctx_conf *conf;
577
578 rcu_read_lock();
579 conf = rcu_dereference(vif->chanctx_conf);
580 if (!conf) {
581 rcu_read_unlock();
582 return -ENOENT;
583 }
584
585 *def = conf->def;
586 rcu_read_unlock();
587
588 return 0;
589}
590
591static void ath10k_mac_num_chanctxs_iter(struct ieee80211_hw *hw,
592 struct ieee80211_chanctx_conf *conf,
593 void *data)
594{
595 int *num = data;
596
597 (*num)++;
598}
599
600static int ath10k_mac_num_chanctxs(struct ath10k *ar)
601{
602 int num = 0;
603
604 ieee80211_iter_chan_contexts_atomic(ar->hw,
605 ath10k_mac_num_chanctxs_iter,
606 &num);
607
608 return num;
609}
610
611static void
612ath10k_mac_get_any_chandef_iter(struct ieee80211_hw *hw,
613 struct ieee80211_chanctx_conf *conf,
614 void *data)
615{
616 struct cfg80211_chan_def **def = data;
617
618 *def = &conf->def;
619}
620
Marek Puzyniak7390ed32015-03-30 09:51:52 +0300621static int ath10k_peer_create(struct ath10k *ar, u32 vdev_id, const u8 *addr,
622 enum wmi_peer_type peer_type)
Kalle Valo5e3dd152013-06-12 20:52:10 +0300623{
Michal Kaziore04cafb2015-08-05 12:15:24 +0200624 struct ath10k_vif *arvif;
625 int num_peers = 0;
Kalle Valo5e3dd152013-06-12 20:52:10 +0300626 int ret;
627
628 lockdep_assert_held(&ar->conf_mutex);
629
Michal Kaziore04cafb2015-08-05 12:15:24 +0200630 num_peers = ar->num_peers;
631
632 /* Each vdev consumes a peer entry as well */
633 list_for_each_entry(arvif, &ar->arvifs, list)
634 num_peers++;
635
636 if (num_peers >= ar->max_num_peers)
Michal Kaziorcfd10612014-11-25 15:16:05 +0100637 return -ENOBUFS;
638
Marek Puzyniak7390ed32015-03-30 09:51:52 +0300639 ret = ath10k_wmi_peer_create(ar, vdev_id, addr, peer_type);
Ben Greear479398b2013-11-04 09:19:34 -0800640 if (ret) {
Michal Kazior7aa7a722014-08-25 12:09:38 +0200641 ath10k_warn(ar, "failed to create wmi peer %pM on vdev %i: %i\n",
Ben Greear69244e52014-02-27 18:50:00 +0200642 addr, vdev_id, ret);
Kalle Valo5e3dd152013-06-12 20:52:10 +0300643 return ret;
Ben Greear479398b2013-11-04 09:19:34 -0800644 }
Kalle Valo5e3dd152013-06-12 20:52:10 +0300645
646 ret = ath10k_wait_for_peer_created(ar, vdev_id, addr);
Ben Greear479398b2013-11-04 09:19:34 -0800647 if (ret) {
Michal Kazior7aa7a722014-08-25 12:09:38 +0200648 ath10k_warn(ar, "failed to wait for created wmi peer %pM on vdev %i: %i\n",
Ben Greear69244e52014-02-27 18:50:00 +0200649 addr, vdev_id, ret);
Kalle Valo5e3dd152013-06-12 20:52:10 +0300650 return ret;
Ben Greear479398b2013-11-04 09:19:34 -0800651 }
Michal Kazior292a7532014-11-25 15:16:04 +0100652
Bartosz Markowski0e759f32014-01-02 14:38:33 +0100653 ar->num_peers++;
Kalle Valo5e3dd152013-06-12 20:52:10 +0300654
655 return 0;
656}
657
Kalle Valo5a13e762014-01-20 11:01:46 +0200658static int ath10k_mac_set_kickout(struct ath10k_vif *arvif)
659{
660 struct ath10k *ar = arvif->ar;
661 u32 param;
662 int ret;
663
664 param = ar->wmi.pdev_param->sta_kickout_th;
665 ret = ath10k_wmi_pdev_set_param(ar, param,
666 ATH10K_KICKOUT_THRESHOLD);
667 if (ret) {
Michal Kazior7aa7a722014-08-25 12:09:38 +0200668 ath10k_warn(ar, "failed to set kickout threshold on vdev %i: %d\n",
Ben Greear69244e52014-02-27 18:50:00 +0200669 arvif->vdev_id, ret);
Kalle Valo5a13e762014-01-20 11:01:46 +0200670 return ret;
671 }
672
673 param = ar->wmi.vdev_param->ap_keepalive_min_idle_inactive_time_secs;
674 ret = ath10k_wmi_vdev_set_param(ar, arvif->vdev_id, param,
675 ATH10K_KEEPALIVE_MIN_IDLE);
676 if (ret) {
Michal Kazior7aa7a722014-08-25 12:09:38 +0200677 ath10k_warn(ar, "failed to set keepalive minimum idle time on vdev %i: %d\n",
Ben Greear69244e52014-02-27 18:50:00 +0200678 arvif->vdev_id, ret);
Kalle Valo5a13e762014-01-20 11:01:46 +0200679 return ret;
680 }
681
682 param = ar->wmi.vdev_param->ap_keepalive_max_idle_inactive_time_secs;
683 ret = ath10k_wmi_vdev_set_param(ar, arvif->vdev_id, param,
684 ATH10K_KEEPALIVE_MAX_IDLE);
685 if (ret) {
Michal Kazior7aa7a722014-08-25 12:09:38 +0200686 ath10k_warn(ar, "failed to set keepalive maximum idle time on vdev %i: %d\n",
Ben Greear69244e52014-02-27 18:50:00 +0200687 arvif->vdev_id, ret);
Kalle Valo5a13e762014-01-20 11:01:46 +0200688 return ret;
689 }
690
691 param = ar->wmi.vdev_param->ap_keepalive_max_unresponsive_time_secs;
692 ret = ath10k_wmi_vdev_set_param(ar, arvif->vdev_id, param,
693 ATH10K_KEEPALIVE_MAX_UNRESPONSIVE);
694 if (ret) {
Michal Kazior7aa7a722014-08-25 12:09:38 +0200695 ath10k_warn(ar, "failed to set keepalive maximum unresponsive time on vdev %i: %d\n",
Ben Greear69244e52014-02-27 18:50:00 +0200696 arvif->vdev_id, ret);
Kalle Valo5a13e762014-01-20 11:01:46 +0200697 return ret;
698 }
699
700 return 0;
701}
702
Vivek Natarajanacab6402014-11-26 09:06:12 +0200703static int ath10k_mac_set_rts(struct ath10k_vif *arvif, u32 value)
Michal Kazior424121c2013-07-22 14:13:31 +0200704{
Bartosz Markowski6d1506e2013-09-26 17:47:15 +0200705 struct ath10k *ar = arvif->ar;
706 u32 vdev_param;
707
Bartosz Markowski6d1506e2013-09-26 17:47:15 +0200708 vdev_param = ar->wmi.vdev_param->rts_threshold;
709 return ath10k_wmi_vdev_set_param(ar, arvif->vdev_id, vdev_param, value);
Michal Kazior424121c2013-07-22 14:13:31 +0200710}
711
Kalle Valo5e3dd152013-06-12 20:52:10 +0300712static int ath10k_peer_delete(struct ath10k *ar, u32 vdev_id, const u8 *addr)
713{
714 int ret;
715
716 lockdep_assert_held(&ar->conf_mutex);
717
718 ret = ath10k_wmi_peer_delete(ar, vdev_id, addr);
719 if (ret)
720 return ret;
721
722 ret = ath10k_wait_for_peer_deleted(ar, vdev_id, addr);
723 if (ret)
724 return ret;
725
Bartosz Markowski0e759f32014-01-02 14:38:33 +0100726 ar->num_peers--;
Bartosz Markowski0e759f32014-01-02 14:38:33 +0100727
Kalle Valo5e3dd152013-06-12 20:52:10 +0300728 return 0;
729}
730
731static void ath10k_peer_cleanup(struct ath10k *ar, u32 vdev_id)
732{
733 struct ath10k_peer *peer, *tmp;
734
735 lockdep_assert_held(&ar->conf_mutex);
736
737 spin_lock_bh(&ar->data_lock);
738 list_for_each_entry_safe(peer, tmp, &ar->peers, list) {
739 if (peer->vdev_id != vdev_id)
740 continue;
741
Michal Kazior7aa7a722014-08-25 12:09:38 +0200742 ath10k_warn(ar, "removing stale peer %pM from vdev_id %d\n",
Kalle Valo5e3dd152013-06-12 20:52:10 +0300743 peer->addr, vdev_id);
744
745 list_del(&peer->list);
746 kfree(peer);
Bartosz Markowski0e759f32014-01-02 14:38:33 +0100747 ar->num_peers--;
Kalle Valo5e3dd152013-06-12 20:52:10 +0300748 }
749 spin_unlock_bh(&ar->data_lock);
750}
751
Michal Kaziora96d7742013-07-16 09:38:56 +0200752static void ath10k_peer_cleanup_all(struct ath10k *ar)
753{
754 struct ath10k_peer *peer, *tmp;
755
756 lockdep_assert_held(&ar->conf_mutex);
757
758 spin_lock_bh(&ar->data_lock);
759 list_for_each_entry_safe(peer, tmp, &ar->peers, list) {
760 list_del(&peer->list);
761 kfree(peer);
762 }
763 spin_unlock_bh(&ar->data_lock);
Michal Kazior292a7532014-11-25 15:16:04 +0100764
765 ar->num_peers = 0;
Michal Kaziorcfd10612014-11-25 15:16:05 +0100766 ar->num_stations = 0;
Michal Kaziora96d7742013-07-16 09:38:56 +0200767}
768
Marek Puzyniak75d85fd2015-03-30 09:51:53 +0300769static int ath10k_mac_tdls_peer_update(struct ath10k *ar, u32 vdev_id,
770 struct ieee80211_sta *sta,
771 enum wmi_tdls_peer_state state)
772{
773 int ret;
774 struct wmi_tdls_peer_update_cmd_arg arg = {};
775 struct wmi_tdls_peer_capab_arg cap = {};
776 struct wmi_channel_arg chan_arg = {};
777
778 lockdep_assert_held(&ar->conf_mutex);
779
780 arg.vdev_id = vdev_id;
781 arg.peer_state = state;
782 ether_addr_copy(arg.addr, sta->addr);
783
784 cap.peer_max_sp = sta->max_sp;
785 cap.peer_uapsd_queues = sta->uapsd_queues;
786
787 if (state == WMI_TDLS_PEER_STATE_CONNECTED &&
788 !sta->tdls_initiator)
789 cap.is_peer_responder = 1;
790
791 ret = ath10k_wmi_tdls_peer_update(ar, &arg, &cap, &chan_arg);
792 if (ret) {
793 ath10k_warn(ar, "failed to update tdls peer %pM on vdev %i: %i\n",
794 arg.addr, vdev_id, ret);
795 return ret;
796 }
797
798 return 0;
799}
800
Kalle Valo5e3dd152013-06-12 20:52:10 +0300801/************************/
802/* Interface management */
803/************************/
804
Michal Kazior64badcb2014-09-18 11:18:02 +0300805void ath10k_mac_vif_beacon_free(struct ath10k_vif *arvif)
806{
807 struct ath10k *ar = arvif->ar;
808
809 lockdep_assert_held(&ar->data_lock);
810
811 if (!arvif->beacon)
812 return;
813
814 if (!arvif->beacon_buf)
815 dma_unmap_single(ar->dev, ATH10K_SKB_CB(arvif->beacon)->paddr,
816 arvif->beacon->len, DMA_TO_DEVICE);
817
Michal Kazioraf213192015-01-29 14:29:52 +0200818 if (WARN_ON(arvif->beacon_state != ATH10K_BEACON_SCHEDULED &&
819 arvif->beacon_state != ATH10K_BEACON_SENT))
820 return;
821
Michal Kazior64badcb2014-09-18 11:18:02 +0300822 dev_kfree_skb_any(arvif->beacon);
823
824 arvif->beacon = NULL;
Michal Kazioraf213192015-01-29 14:29:52 +0200825 arvif->beacon_state = ATH10K_BEACON_SCHEDULED;
Michal Kazior64badcb2014-09-18 11:18:02 +0300826}
827
828static void ath10k_mac_vif_beacon_cleanup(struct ath10k_vif *arvif)
829{
830 struct ath10k *ar = arvif->ar;
831
832 lockdep_assert_held(&ar->data_lock);
833
834 ath10k_mac_vif_beacon_free(arvif);
835
836 if (arvif->beacon_buf) {
837 dma_free_coherent(ar->dev, IEEE80211_MAX_FRAME_LEN,
838 arvif->beacon_buf, arvif->beacon_paddr);
839 arvif->beacon_buf = NULL;
840 }
841}
842
Kalle Valo5e3dd152013-06-12 20:52:10 +0300843static inline int ath10k_vdev_setup_sync(struct ath10k *ar)
844{
Nicholas Mc Guire8e9904f52015-03-30 15:39:19 +0300845 unsigned long time_left;
Kalle Valo5e3dd152013-06-12 20:52:10 +0300846
Michal Kazior548db542013-07-05 16:15:15 +0300847 lockdep_assert_held(&ar->conf_mutex);
848
Michal Kazior7962b0d2014-10-28 10:34:38 +0100849 if (test_bit(ATH10K_FLAG_CRASH_FLUSH, &ar->dev_flags))
850 return -ESHUTDOWN;
851
Nicholas Mc Guire8e9904f52015-03-30 15:39:19 +0300852 time_left = wait_for_completion_timeout(&ar->vdev_setup_done,
853 ATH10K_VDEV_SETUP_TIMEOUT_HZ);
854 if (time_left == 0)
Kalle Valo5e3dd152013-06-12 20:52:10 +0300855 return -ETIMEDOUT;
856
857 return 0;
858}
859
Michal Kazior1bbc0972014-04-08 09:45:47 +0300860static int ath10k_monitor_vdev_start(struct ath10k *ar, int vdev_id)
Kalle Valo5e3dd152013-06-12 20:52:10 +0300861{
Michal Kazior500ff9f2015-03-31 10:26:21 +0000862 struct cfg80211_chan_def *chandef = NULL;
Maninder Singh19be9e92015-07-16 09:25:33 +0530863 struct ieee80211_channel *channel = NULL;
Kalle Valo5e3dd152013-06-12 20:52:10 +0300864 struct wmi_vdev_start_request_arg arg = {};
Kalle Valo5e3dd152013-06-12 20:52:10 +0300865 int ret = 0;
866
867 lockdep_assert_held(&ar->conf_mutex);
868
Michal Kazior500ff9f2015-03-31 10:26:21 +0000869 ieee80211_iter_chan_contexts_atomic(ar->hw,
870 ath10k_mac_get_any_chandef_iter,
871 &chandef);
872 if (WARN_ON_ONCE(!chandef))
873 return -ENOENT;
874
875 channel = chandef->chan;
876
Kalle Valo5e3dd152013-06-12 20:52:10 +0300877 arg.vdev_id = vdev_id;
878 arg.channel.freq = channel->center_freq;
Michal Kaziorc930f742014-01-23 11:38:25 +0100879 arg.channel.band_center_freq1 = chandef->center_freq1;
Kalle Valo5e3dd152013-06-12 20:52:10 +0300880
881 /* TODO setup this dynamically, what in case we
882 don't have any vifs? */
Michal Kaziorc930f742014-01-23 11:38:25 +0100883 arg.channel.mode = chan_to_phymode(chandef);
Marek Puzyniake8a50f82013-11-20 09:59:47 +0200884 arg.channel.chan_radar =
885 !!(channel->flags & IEEE80211_CHAN_RADAR);
Kalle Valo5e3dd152013-06-12 20:52:10 +0300886
Michal Kazior89c5c842013-10-23 04:02:13 -0700887 arg.channel.min_power = 0;
Michal Kazior02256932013-10-23 04:02:14 -0700888 arg.channel.max_power = channel->max_power * 2;
889 arg.channel.max_reg_power = channel->max_reg_power * 2;
890 arg.channel.max_antenna_gain = channel->max_antenna_gain * 2;
Kalle Valo5e3dd152013-06-12 20:52:10 +0300891
Michal Kazior7962b0d2014-10-28 10:34:38 +0100892 reinit_completion(&ar->vdev_setup_done);
893
Kalle Valo5e3dd152013-06-12 20:52:10 +0300894 ret = ath10k_wmi_vdev_start(ar, &arg);
895 if (ret) {
Michal Kazior7aa7a722014-08-25 12:09:38 +0200896 ath10k_warn(ar, "failed to request monitor vdev %i start: %d\n",
Ben Greear69244e52014-02-27 18:50:00 +0200897 vdev_id, ret);
Kalle Valo5e3dd152013-06-12 20:52:10 +0300898 return ret;
899 }
900
901 ret = ath10k_vdev_setup_sync(ar);
902 if (ret) {
Ben Greear60028a82015-02-15 16:50:39 +0200903 ath10k_warn(ar, "failed to synchronize setup for monitor vdev %i start: %d\n",
Ben Greear69244e52014-02-27 18:50:00 +0200904 vdev_id, ret);
Kalle Valo5e3dd152013-06-12 20:52:10 +0300905 return ret;
906 }
907
908 ret = ath10k_wmi_vdev_up(ar, vdev_id, 0, ar->mac_addr);
909 if (ret) {
Michal Kazior7aa7a722014-08-25 12:09:38 +0200910 ath10k_warn(ar, "failed to put up monitor vdev %i: %d\n",
Ben Greear69244e52014-02-27 18:50:00 +0200911 vdev_id, ret);
Kalle Valo5e3dd152013-06-12 20:52:10 +0300912 goto vdev_stop;
913 }
914
915 ar->monitor_vdev_id = vdev_id;
Kalle Valo5e3dd152013-06-12 20:52:10 +0300916
Michal Kazior7aa7a722014-08-25 12:09:38 +0200917 ath10k_dbg(ar, ATH10K_DBG_MAC, "mac monitor vdev %i started\n",
Michal Kazior1bbc0972014-04-08 09:45:47 +0300918 ar->monitor_vdev_id);
Kalle Valo5e3dd152013-06-12 20:52:10 +0300919 return 0;
920
921vdev_stop:
922 ret = ath10k_wmi_vdev_stop(ar, ar->monitor_vdev_id);
923 if (ret)
Michal Kazior7aa7a722014-08-25 12:09:38 +0200924 ath10k_warn(ar, "failed to stop monitor vdev %i after start failure: %d\n",
Ben Greear69244e52014-02-27 18:50:00 +0200925 ar->monitor_vdev_id, ret);
Kalle Valo5e3dd152013-06-12 20:52:10 +0300926
927 return ret;
928}
929
Michal Kazior1bbc0972014-04-08 09:45:47 +0300930static int ath10k_monitor_vdev_stop(struct ath10k *ar)
Kalle Valo5e3dd152013-06-12 20:52:10 +0300931{
932 int ret = 0;
933
934 lockdep_assert_held(&ar->conf_mutex);
935
Marek Puzyniak52fa0192013-09-24 14:06:24 +0200936 ret = ath10k_wmi_vdev_down(ar, ar->monitor_vdev_id);
937 if (ret)
Michal Kazior7aa7a722014-08-25 12:09:38 +0200938 ath10k_warn(ar, "failed to put down monitor vdev %i: %d\n",
Ben Greear69244e52014-02-27 18:50:00 +0200939 ar->monitor_vdev_id, ret);
Kalle Valo5e3dd152013-06-12 20:52:10 +0300940
Michal Kazior7962b0d2014-10-28 10:34:38 +0100941 reinit_completion(&ar->vdev_setup_done);
942
Kalle Valo5e3dd152013-06-12 20:52:10 +0300943 ret = ath10k_wmi_vdev_stop(ar, ar->monitor_vdev_id);
944 if (ret)
Michal Kazior7aa7a722014-08-25 12:09:38 +0200945 ath10k_warn(ar, "failed to to request monitor vdev %i stop: %d\n",
Ben Greear69244e52014-02-27 18:50:00 +0200946 ar->monitor_vdev_id, ret);
Kalle Valo5e3dd152013-06-12 20:52:10 +0300947
948 ret = ath10k_vdev_setup_sync(ar);
949 if (ret)
Ben Greear60028a82015-02-15 16:50:39 +0200950 ath10k_warn(ar, "failed to synchronize monitor vdev %i stop: %d\n",
Ben Greear69244e52014-02-27 18:50:00 +0200951 ar->monitor_vdev_id, ret);
Kalle Valo5e3dd152013-06-12 20:52:10 +0300952
Michal Kazior7aa7a722014-08-25 12:09:38 +0200953 ath10k_dbg(ar, ATH10K_DBG_MAC, "mac monitor vdev %i stopped\n",
Michal Kazior1bbc0972014-04-08 09:45:47 +0300954 ar->monitor_vdev_id);
Kalle Valo5e3dd152013-06-12 20:52:10 +0300955 return ret;
956}
957
Michal Kazior1bbc0972014-04-08 09:45:47 +0300958static int ath10k_monitor_vdev_create(struct ath10k *ar)
Kalle Valo5e3dd152013-06-12 20:52:10 +0300959{
960 int bit, ret = 0;
961
962 lockdep_assert_held(&ar->conf_mutex);
963
Ben Greeara9aefb32014-08-12 11:02:19 +0300964 if (ar->free_vdev_map == 0) {
Michal Kazior7aa7a722014-08-25 12:09:38 +0200965 ath10k_warn(ar, "failed to find free vdev id for monitor vdev\n");
Kalle Valo5e3dd152013-06-12 20:52:10 +0300966 return -ENOMEM;
967 }
968
Ben Greear16c11172014-09-23 14:17:16 -0700969 bit = __ffs64(ar->free_vdev_map);
Ben Greeara9aefb32014-08-12 11:02:19 +0300970
Ben Greear16c11172014-09-23 14:17:16 -0700971 ar->monitor_vdev_id = bit;
Kalle Valo5e3dd152013-06-12 20:52:10 +0300972
973 ret = ath10k_wmi_vdev_create(ar, ar->monitor_vdev_id,
974 WMI_VDEV_TYPE_MONITOR,
975 0, ar->mac_addr);
976 if (ret) {
Michal Kazior7aa7a722014-08-25 12:09:38 +0200977 ath10k_warn(ar, "failed to request monitor vdev %i creation: %d\n",
Ben Greear69244e52014-02-27 18:50:00 +0200978 ar->monitor_vdev_id, ret);
Ben Greeara9aefb32014-08-12 11:02:19 +0300979 return ret;
Kalle Valo5e3dd152013-06-12 20:52:10 +0300980 }
981
Ben Greear16c11172014-09-23 14:17:16 -0700982 ar->free_vdev_map &= ~(1LL << ar->monitor_vdev_id);
Michal Kazior7aa7a722014-08-25 12:09:38 +0200983 ath10k_dbg(ar, ATH10K_DBG_MAC, "mac monitor vdev %d created\n",
Kalle Valo5e3dd152013-06-12 20:52:10 +0300984 ar->monitor_vdev_id);
985
Kalle Valo5e3dd152013-06-12 20:52:10 +0300986 return 0;
Kalle Valo5e3dd152013-06-12 20:52:10 +0300987}
988
Michal Kazior1bbc0972014-04-08 09:45:47 +0300989static int ath10k_monitor_vdev_delete(struct ath10k *ar)
Kalle Valo5e3dd152013-06-12 20:52:10 +0300990{
991 int ret = 0;
992
993 lockdep_assert_held(&ar->conf_mutex);
994
Kalle Valo5e3dd152013-06-12 20:52:10 +0300995 ret = ath10k_wmi_vdev_delete(ar, ar->monitor_vdev_id);
996 if (ret) {
Michal Kazior7aa7a722014-08-25 12:09:38 +0200997 ath10k_warn(ar, "failed to request wmi monitor vdev %i removal: %d\n",
Ben Greear69244e52014-02-27 18:50:00 +0200998 ar->monitor_vdev_id, ret);
Kalle Valo5e3dd152013-06-12 20:52:10 +0300999 return ret;
1000 }
1001
Ben Greear16c11172014-09-23 14:17:16 -07001002 ar->free_vdev_map |= 1LL << ar->monitor_vdev_id;
Kalle Valo5e3dd152013-06-12 20:52:10 +03001003
Michal Kazior7aa7a722014-08-25 12:09:38 +02001004 ath10k_dbg(ar, ATH10K_DBG_MAC, "mac monitor vdev %d deleted\n",
Kalle Valo5e3dd152013-06-12 20:52:10 +03001005 ar->monitor_vdev_id);
1006 return ret;
1007}
1008
Michal Kazior1bbc0972014-04-08 09:45:47 +03001009static int ath10k_monitor_start(struct ath10k *ar)
1010{
1011 int ret;
1012
1013 lockdep_assert_held(&ar->conf_mutex);
1014
Michal Kazior1bbc0972014-04-08 09:45:47 +03001015 ret = ath10k_monitor_vdev_create(ar);
1016 if (ret) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02001017 ath10k_warn(ar, "failed to create monitor vdev: %d\n", ret);
Michal Kazior1bbc0972014-04-08 09:45:47 +03001018 return ret;
1019 }
1020
1021 ret = ath10k_monitor_vdev_start(ar, ar->monitor_vdev_id);
1022 if (ret) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02001023 ath10k_warn(ar, "failed to start monitor vdev: %d\n", ret);
Michal Kazior1bbc0972014-04-08 09:45:47 +03001024 ath10k_monitor_vdev_delete(ar);
1025 return ret;
1026 }
1027
1028 ar->monitor_started = true;
Michal Kazior7aa7a722014-08-25 12:09:38 +02001029 ath10k_dbg(ar, ATH10K_DBG_MAC, "mac monitor started\n");
Michal Kazior1bbc0972014-04-08 09:45:47 +03001030
1031 return 0;
1032}
1033
Michal Kazior19337472014-08-28 12:58:16 +02001034static int ath10k_monitor_stop(struct ath10k *ar)
Michal Kazior1bbc0972014-04-08 09:45:47 +03001035{
1036 int ret;
1037
1038 lockdep_assert_held(&ar->conf_mutex);
1039
Michal Kazior1bbc0972014-04-08 09:45:47 +03001040 ret = ath10k_monitor_vdev_stop(ar);
Michal Kazior19337472014-08-28 12:58:16 +02001041 if (ret) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02001042 ath10k_warn(ar, "failed to stop monitor vdev: %d\n", ret);
Michal Kazior19337472014-08-28 12:58:16 +02001043 return ret;
1044 }
Michal Kazior1bbc0972014-04-08 09:45:47 +03001045
1046 ret = ath10k_monitor_vdev_delete(ar);
Michal Kazior19337472014-08-28 12:58:16 +02001047 if (ret) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02001048 ath10k_warn(ar, "failed to delete monitor vdev: %d\n", ret);
Michal Kazior19337472014-08-28 12:58:16 +02001049 return ret;
1050 }
Michal Kazior1bbc0972014-04-08 09:45:47 +03001051
1052 ar->monitor_started = false;
Michal Kazior7aa7a722014-08-25 12:09:38 +02001053 ath10k_dbg(ar, ATH10K_DBG_MAC, "mac monitor stopped\n");
Michal Kazior19337472014-08-28 12:58:16 +02001054
1055 return 0;
1056}
1057
Michal Kazior500ff9f2015-03-31 10:26:21 +00001058static bool ath10k_mac_monitor_vdev_is_needed(struct ath10k *ar)
1059{
1060 int num_ctx;
1061
1062 /* At least one chanctx is required to derive a channel to start
1063 * monitor vdev on.
1064 */
1065 num_ctx = ath10k_mac_num_chanctxs(ar);
1066 if (num_ctx == 0)
1067 return false;
1068
1069 /* If there's already an existing special monitor interface then don't
1070 * bother creating another monitor vdev.
1071 */
1072 if (ar->monitor_arvif)
1073 return false;
1074
1075 return ar->monitor ||
Bob Copeland0d031c82015-09-09 12:47:34 -04001076 ar->filter_flags & FIF_OTHER_BSS ||
Michal Kazior500ff9f2015-03-31 10:26:21 +00001077 test_bit(ATH10K_CAC_RUNNING, &ar->dev_flags);
1078}
1079
1080static bool ath10k_mac_monitor_vdev_is_allowed(struct ath10k *ar)
1081{
1082 int num_ctx;
1083
1084 num_ctx = ath10k_mac_num_chanctxs(ar);
1085
1086 /* FIXME: Current interface combinations and cfg80211/mac80211 code
1087 * shouldn't allow this but make sure to prevent handling the following
1088 * case anyway since multi-channel DFS hasn't been tested at all.
1089 */
1090 if (test_bit(ATH10K_CAC_RUNNING, &ar->dev_flags) && num_ctx > 1)
1091 return false;
1092
1093 return true;
1094}
1095
Michal Kazior19337472014-08-28 12:58:16 +02001096static int ath10k_monitor_recalc(struct ath10k *ar)
1097{
Michal Kazior500ff9f2015-03-31 10:26:21 +00001098 bool needed;
1099 bool allowed;
1100 int ret;
Michal Kazior19337472014-08-28 12:58:16 +02001101
1102 lockdep_assert_held(&ar->conf_mutex);
1103
Michal Kazior500ff9f2015-03-31 10:26:21 +00001104 needed = ath10k_mac_monitor_vdev_is_needed(ar);
1105 allowed = ath10k_mac_monitor_vdev_is_allowed(ar);
Michal Kazior19337472014-08-28 12:58:16 +02001106
1107 ath10k_dbg(ar, ATH10K_DBG_MAC,
Michal Kazior500ff9f2015-03-31 10:26:21 +00001108 "mac monitor recalc started? %d needed? %d allowed? %d\n",
1109 ar->monitor_started, needed, allowed);
Michal Kazior19337472014-08-28 12:58:16 +02001110
Michal Kazior500ff9f2015-03-31 10:26:21 +00001111 if (WARN_ON(needed && !allowed)) {
1112 if (ar->monitor_started) {
1113 ath10k_dbg(ar, ATH10K_DBG_MAC, "mac monitor stopping disallowed monitor\n");
1114
1115 ret = ath10k_monitor_stop(ar);
1116 if (ret)
Kalle Valo2a995082015-10-05 17:56:37 +03001117 ath10k_warn(ar, "failed to stop disallowed monitor: %d\n",
1118 ret);
Michal Kazior500ff9f2015-03-31 10:26:21 +00001119 /* not serious */
1120 }
1121
1122 return -EPERM;
1123 }
1124
1125 if (needed == ar->monitor_started)
Michal Kazior19337472014-08-28 12:58:16 +02001126 return 0;
1127
Michal Kazior500ff9f2015-03-31 10:26:21 +00001128 if (needed)
Michal Kazior19337472014-08-28 12:58:16 +02001129 return ath10k_monitor_start(ar);
Michal Kazior500ff9f2015-03-31 10:26:21 +00001130 else
1131 return ath10k_monitor_stop(ar);
Michal Kazior1bbc0972014-04-08 09:45:47 +03001132}
1133
Marek Kwaczynskie81bd102014-03-11 12:58:00 +02001134static int ath10k_recalc_rtscts_prot(struct ath10k_vif *arvif)
1135{
1136 struct ath10k *ar = arvif->ar;
1137 u32 vdev_param, rts_cts = 0;
1138
1139 lockdep_assert_held(&ar->conf_mutex);
1140
1141 vdev_param = ar->wmi.vdev_param->enable_rtscts;
1142
Rajkumar Manoharan9a5ab0f2015-03-19 16:03:29 +02001143 rts_cts |= SM(WMI_RTSCTS_ENABLED, WMI_RTSCTS_SET);
Marek Kwaczynskie81bd102014-03-11 12:58:00 +02001144
1145 if (arvif->num_legacy_stations > 0)
1146 rts_cts |= SM(WMI_RTSCTS_ACROSS_SW_RETRIES,
1147 WMI_RTSCTS_PROFILE);
Rajkumar Manoharan9a5ab0f2015-03-19 16:03:29 +02001148 else
1149 rts_cts |= SM(WMI_RTSCTS_FOR_SECOND_RATESERIES,
1150 WMI_RTSCTS_PROFILE);
Marek Kwaczynskie81bd102014-03-11 12:58:00 +02001151
1152 return ath10k_wmi_vdev_set_param(ar, arvif->vdev_id, vdev_param,
1153 rts_cts);
1154}
1155
Marek Puzyniake8a50f82013-11-20 09:59:47 +02001156static int ath10k_start_cac(struct ath10k *ar)
1157{
1158 int ret;
1159
1160 lockdep_assert_held(&ar->conf_mutex);
1161
1162 set_bit(ATH10K_CAC_RUNNING, &ar->dev_flags);
1163
Michal Kazior19337472014-08-28 12:58:16 +02001164 ret = ath10k_monitor_recalc(ar);
Marek Puzyniake8a50f82013-11-20 09:59:47 +02001165 if (ret) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02001166 ath10k_warn(ar, "failed to start monitor (cac): %d\n", ret);
Marek Puzyniake8a50f82013-11-20 09:59:47 +02001167 clear_bit(ATH10K_CAC_RUNNING, &ar->dev_flags);
1168 return ret;
1169 }
1170
Michal Kazior7aa7a722014-08-25 12:09:38 +02001171 ath10k_dbg(ar, ATH10K_DBG_MAC, "mac cac start monitor vdev %d\n",
Marek Puzyniake8a50f82013-11-20 09:59:47 +02001172 ar->monitor_vdev_id);
1173
1174 return 0;
1175}
1176
1177static int ath10k_stop_cac(struct ath10k *ar)
1178{
1179 lockdep_assert_held(&ar->conf_mutex);
1180
1181 /* CAC is not running - do nothing */
1182 if (!test_bit(ATH10K_CAC_RUNNING, &ar->dev_flags))
1183 return 0;
1184
Marek Puzyniake8a50f82013-11-20 09:59:47 +02001185 clear_bit(ATH10K_CAC_RUNNING, &ar->dev_flags);
Michal Kazior1bbc0972014-04-08 09:45:47 +03001186 ath10k_monitor_stop(ar);
Marek Puzyniake8a50f82013-11-20 09:59:47 +02001187
Michal Kazior7aa7a722014-08-25 12:09:38 +02001188 ath10k_dbg(ar, ATH10K_DBG_MAC, "mac cac finished\n");
Marek Puzyniake8a50f82013-11-20 09:59:47 +02001189
1190 return 0;
1191}
1192
Michal Kazior500ff9f2015-03-31 10:26:21 +00001193static void ath10k_mac_has_radar_iter(struct ieee80211_hw *hw,
1194 struct ieee80211_chanctx_conf *conf,
1195 void *data)
1196{
1197 bool *ret = data;
1198
1199 if (!*ret && conf->radar_enabled)
1200 *ret = true;
1201}
1202
1203static bool ath10k_mac_has_radar_enabled(struct ath10k *ar)
1204{
1205 bool has_radar = false;
1206
1207 ieee80211_iter_chan_contexts_atomic(ar->hw,
1208 ath10k_mac_has_radar_iter,
1209 &has_radar);
1210
1211 return has_radar;
1212}
1213
Michal Kaziord6500972014-04-08 09:56:09 +03001214static void ath10k_recalc_radar_detection(struct ath10k *ar)
Marek Puzyniake8a50f82013-11-20 09:59:47 +02001215{
Marek Puzyniake8a50f82013-11-20 09:59:47 +02001216 int ret;
1217
1218 lockdep_assert_held(&ar->conf_mutex);
1219
Marek Puzyniake8a50f82013-11-20 09:59:47 +02001220 ath10k_stop_cac(ar);
1221
Michal Kazior500ff9f2015-03-31 10:26:21 +00001222 if (!ath10k_mac_has_radar_enabled(ar))
Marek Puzyniake8a50f82013-11-20 09:59:47 +02001223 return;
1224
Michal Kaziord6500972014-04-08 09:56:09 +03001225 if (ar->num_started_vdevs > 0)
Marek Puzyniake8a50f82013-11-20 09:59:47 +02001226 return;
1227
1228 ret = ath10k_start_cac(ar);
1229 if (ret) {
1230 /*
1231 * Not possible to start CAC on current channel so starting
1232 * radiation is not allowed, make this channel DFS_UNAVAILABLE
1233 * by indicating that radar was detected.
1234 */
Michal Kazior7aa7a722014-08-25 12:09:38 +02001235 ath10k_warn(ar, "failed to start CAC: %d\n", ret);
Marek Puzyniake8a50f82013-11-20 09:59:47 +02001236 ieee80211_radar_detected(ar->hw);
1237 }
1238}
1239
Vasanthakumar Thiagarajan822b7e02015-03-02 17:45:27 +05301240static int ath10k_vdev_stop(struct ath10k_vif *arvif)
Michal Kazior72654fa2014-04-08 09:56:09 +03001241{
1242 struct ath10k *ar = arvif->ar;
Vasanthakumar Thiagarajan822b7e02015-03-02 17:45:27 +05301243 int ret;
1244
1245 lockdep_assert_held(&ar->conf_mutex);
1246
1247 reinit_completion(&ar->vdev_setup_done);
1248
1249 ret = ath10k_wmi_vdev_stop(ar, arvif->vdev_id);
1250 if (ret) {
1251 ath10k_warn(ar, "failed to stop WMI vdev %i: %d\n",
1252 arvif->vdev_id, ret);
1253 return ret;
1254 }
1255
1256 ret = ath10k_vdev_setup_sync(ar);
1257 if (ret) {
1258 ath10k_warn(ar, "failed to syncronise setup for vdev %i: %d\n",
1259 arvif->vdev_id, ret);
1260 return ret;
1261 }
1262
1263 WARN_ON(ar->num_started_vdevs == 0);
1264
1265 if (ar->num_started_vdevs != 0) {
1266 ar->num_started_vdevs--;
1267 ath10k_recalc_radar_detection(ar);
1268 }
1269
1270 return ret;
1271}
1272
Michal Kazior500ff9f2015-03-31 10:26:21 +00001273static int ath10k_vdev_start_restart(struct ath10k_vif *arvif,
1274 const struct cfg80211_chan_def *chandef,
1275 bool restart)
Michal Kazior72654fa2014-04-08 09:56:09 +03001276{
1277 struct ath10k *ar = arvif->ar;
Michal Kazior72654fa2014-04-08 09:56:09 +03001278 struct wmi_vdev_start_request_arg arg = {};
1279 int ret = 0;
1280
1281 lockdep_assert_held(&ar->conf_mutex);
1282
1283 reinit_completion(&ar->vdev_setup_done);
1284
1285 arg.vdev_id = arvif->vdev_id;
1286 arg.dtim_period = arvif->dtim_period;
1287 arg.bcn_intval = arvif->beacon_interval;
1288
1289 arg.channel.freq = chandef->chan->center_freq;
1290 arg.channel.band_center_freq1 = chandef->center_freq1;
1291 arg.channel.mode = chan_to_phymode(chandef);
1292
1293 arg.channel.min_power = 0;
1294 arg.channel.max_power = chandef->chan->max_power * 2;
1295 arg.channel.max_reg_power = chandef->chan->max_reg_power * 2;
1296 arg.channel.max_antenna_gain = chandef->chan->max_antenna_gain * 2;
1297
1298 if (arvif->vdev_type == WMI_VDEV_TYPE_AP) {
1299 arg.ssid = arvif->u.ap.ssid;
1300 arg.ssid_len = arvif->u.ap.ssid_len;
1301 arg.hidden_ssid = arvif->u.ap.hidden_ssid;
1302
1303 /* For now allow DFS for AP mode */
1304 arg.channel.chan_radar =
1305 !!(chandef->chan->flags & IEEE80211_CHAN_RADAR);
1306 } else if (arvif->vdev_type == WMI_VDEV_TYPE_IBSS) {
1307 arg.ssid = arvif->vif->bss_conf.ssid;
1308 arg.ssid_len = arvif->vif->bss_conf.ssid_len;
1309 }
1310
Michal Kazior7aa7a722014-08-25 12:09:38 +02001311 ath10k_dbg(ar, ATH10K_DBG_MAC,
Michal Kazior72654fa2014-04-08 09:56:09 +03001312 "mac vdev %d start center_freq %d phymode %s\n",
1313 arg.vdev_id, arg.channel.freq,
1314 ath10k_wmi_phymode_str(arg.channel.mode));
1315
Michal Kaziordc55e302014-07-29 12:53:36 +03001316 if (restart)
1317 ret = ath10k_wmi_vdev_restart(ar, &arg);
1318 else
1319 ret = ath10k_wmi_vdev_start(ar, &arg);
1320
Michal Kazior72654fa2014-04-08 09:56:09 +03001321 if (ret) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02001322 ath10k_warn(ar, "failed to start WMI vdev %i: %d\n",
Michal Kazior72654fa2014-04-08 09:56:09 +03001323 arg.vdev_id, ret);
1324 return ret;
1325 }
1326
1327 ret = ath10k_vdev_setup_sync(ar);
1328 if (ret) {
Ben Greear60028a82015-02-15 16:50:39 +02001329 ath10k_warn(ar,
1330 "failed to synchronize setup for vdev %i restart %d: %d\n",
1331 arg.vdev_id, restart, ret);
Michal Kazior72654fa2014-04-08 09:56:09 +03001332 return ret;
1333 }
1334
Michal Kaziord6500972014-04-08 09:56:09 +03001335 ar->num_started_vdevs++;
1336 ath10k_recalc_radar_detection(ar);
1337
Michal Kazior72654fa2014-04-08 09:56:09 +03001338 return ret;
1339}
1340
Michal Kazior500ff9f2015-03-31 10:26:21 +00001341static int ath10k_vdev_start(struct ath10k_vif *arvif,
1342 const struct cfg80211_chan_def *def)
Michal Kaziordc55e302014-07-29 12:53:36 +03001343{
Michal Kazior500ff9f2015-03-31 10:26:21 +00001344 return ath10k_vdev_start_restart(arvif, def, false);
Michal Kaziordc55e302014-07-29 12:53:36 +03001345}
1346
Michal Kazior500ff9f2015-03-31 10:26:21 +00001347static int ath10k_vdev_restart(struct ath10k_vif *arvif,
1348 const struct cfg80211_chan_def *def)
Michal Kaziordc55e302014-07-29 12:53:36 +03001349{
Michal Kazior500ff9f2015-03-31 10:26:21 +00001350 return ath10k_vdev_start_restart(arvif, def, true);
Michal Kazior72654fa2014-04-08 09:56:09 +03001351}
1352
Michal Kaziorfbb8f1b2015-01-13 16:30:12 +02001353static int ath10k_mac_setup_bcn_p2p_ie(struct ath10k_vif *arvif,
1354 struct sk_buff *bcn)
1355{
1356 struct ath10k *ar = arvif->ar;
1357 struct ieee80211_mgmt *mgmt;
1358 const u8 *p2p_ie;
1359 int ret;
1360
Peter Oh08c27be2016-01-28 13:54:09 -08001361 if (arvif->vif->type != NL80211_IFTYPE_AP || !arvif->vif->p2p)
Michal Kaziorfbb8f1b2015-01-13 16:30:12 +02001362 return 0;
1363
1364 mgmt = (void *)bcn->data;
1365 p2p_ie = cfg80211_find_vendor_ie(WLAN_OUI_WFA, WLAN_OUI_TYPE_WFA_P2P,
1366 mgmt->u.beacon.variable,
1367 bcn->len - (mgmt->u.beacon.variable -
1368 bcn->data));
1369 if (!p2p_ie)
1370 return -ENOENT;
1371
1372 ret = ath10k_wmi_p2p_go_bcn_ie(ar, arvif->vdev_id, p2p_ie);
1373 if (ret) {
1374 ath10k_warn(ar, "failed to submit p2p go bcn ie for vdev %i: %d\n",
1375 arvif->vdev_id, ret);
1376 return ret;
1377 }
1378
1379 return 0;
1380}
1381
1382static int ath10k_mac_remove_vendor_ie(struct sk_buff *skb, unsigned int oui,
1383 u8 oui_type, size_t ie_offset)
1384{
1385 size_t len;
1386 const u8 *next;
1387 const u8 *end;
1388 u8 *ie;
1389
1390 if (WARN_ON(skb->len < ie_offset))
1391 return -EINVAL;
1392
1393 ie = (u8 *)cfg80211_find_vendor_ie(oui, oui_type,
1394 skb->data + ie_offset,
1395 skb->len - ie_offset);
1396 if (!ie)
1397 return -ENOENT;
1398
1399 len = ie[1] + 2;
1400 end = skb->data + skb->len;
1401 next = ie + len;
1402
1403 if (WARN_ON(next > end))
1404 return -EINVAL;
1405
1406 memmove(ie, next, end - next);
1407 skb_trim(skb, skb->len - len);
1408
1409 return 0;
1410}
1411
1412static int ath10k_mac_setup_bcn_tmpl(struct ath10k_vif *arvif)
1413{
1414 struct ath10k *ar = arvif->ar;
1415 struct ieee80211_hw *hw = ar->hw;
1416 struct ieee80211_vif *vif = arvif->vif;
1417 struct ieee80211_mutable_offsets offs = {};
1418 struct sk_buff *bcn;
1419 int ret;
1420
1421 if (!test_bit(WMI_SERVICE_BEACON_OFFLOAD, ar->wmi.svc_map))
1422 return 0;
1423
Michal Kazior81a9a172015-03-05 16:02:17 +02001424 if (arvif->vdev_type != WMI_VDEV_TYPE_AP &&
1425 arvif->vdev_type != WMI_VDEV_TYPE_IBSS)
1426 return 0;
1427
Michal Kaziorfbb8f1b2015-01-13 16:30:12 +02001428 bcn = ieee80211_beacon_get_template(hw, vif, &offs);
1429 if (!bcn) {
1430 ath10k_warn(ar, "failed to get beacon template from mac80211\n");
1431 return -EPERM;
1432 }
1433
1434 ret = ath10k_mac_setup_bcn_p2p_ie(arvif, bcn);
1435 if (ret) {
1436 ath10k_warn(ar, "failed to setup p2p go bcn ie: %d\n", ret);
1437 kfree_skb(bcn);
1438 return ret;
1439 }
1440
1441 /* P2P IE is inserted by firmware automatically (as configured above)
1442 * so remove it from the base beacon template to avoid duplicate P2P
1443 * IEs in beacon frames.
1444 */
1445 ath10k_mac_remove_vendor_ie(bcn, WLAN_OUI_WFA, WLAN_OUI_TYPE_WFA_P2P,
1446 offsetof(struct ieee80211_mgmt,
1447 u.beacon.variable));
1448
1449 ret = ath10k_wmi_bcn_tmpl(ar, arvif->vdev_id, offs.tim_offset, bcn, 0,
1450 0, NULL, 0);
1451 kfree_skb(bcn);
1452
1453 if (ret) {
1454 ath10k_warn(ar, "failed to submit beacon template command: %d\n",
1455 ret);
1456 return ret;
1457 }
1458
1459 return 0;
1460}
1461
1462static int ath10k_mac_setup_prb_tmpl(struct ath10k_vif *arvif)
1463{
1464 struct ath10k *ar = arvif->ar;
1465 struct ieee80211_hw *hw = ar->hw;
1466 struct ieee80211_vif *vif = arvif->vif;
1467 struct sk_buff *prb;
1468 int ret;
1469
1470 if (!test_bit(WMI_SERVICE_BEACON_OFFLOAD, ar->wmi.svc_map))
1471 return 0;
1472
Michal Kazior81a9a172015-03-05 16:02:17 +02001473 if (arvif->vdev_type != WMI_VDEV_TYPE_AP)
1474 return 0;
1475
Michal Kaziorfbb8f1b2015-01-13 16:30:12 +02001476 prb = ieee80211_proberesp_get(hw, vif);
1477 if (!prb) {
1478 ath10k_warn(ar, "failed to get probe resp template from mac80211\n");
1479 return -EPERM;
1480 }
1481
1482 ret = ath10k_wmi_prb_tmpl(ar, arvif->vdev_id, prb);
1483 kfree_skb(prb);
1484
1485 if (ret) {
1486 ath10k_warn(ar, "failed to submit probe resp template command: %d\n",
1487 ret);
1488 return ret;
1489 }
1490
1491 return 0;
1492}
1493
Michal Kazior500ff9f2015-03-31 10:26:21 +00001494static int ath10k_mac_vif_fix_hidden_ssid(struct ath10k_vif *arvif)
1495{
1496 struct ath10k *ar = arvif->ar;
1497 struct cfg80211_chan_def def;
1498 int ret;
1499
1500 /* When originally vdev is started during assign_vif_chanctx() some
1501 * information is missing, notably SSID. Firmware revisions with beacon
1502 * offloading require the SSID to be provided during vdev (re)start to
1503 * handle hidden SSID properly.
1504 *
1505 * Vdev restart must be done after vdev has been both started and
1506 * upped. Otherwise some firmware revisions (at least 10.2) fail to
1507 * deliver vdev restart response event causing timeouts during vdev
1508 * syncing in ath10k.
1509 *
1510 * Note: The vdev down/up and template reinstallation could be skipped
1511 * since only wmi-tlv firmware are known to have beacon offload and
1512 * wmi-tlv doesn't seem to misbehave like 10.2 wrt vdev restart
1513 * response delivery. It's probably more robust to keep it as is.
1514 */
1515 if (!test_bit(WMI_SERVICE_BEACON_OFFLOAD, ar->wmi.svc_map))
1516 return 0;
1517
1518 if (WARN_ON(!arvif->is_started))
1519 return -EINVAL;
1520
1521 if (WARN_ON(!arvif->is_up))
1522 return -EINVAL;
1523
1524 if (WARN_ON(ath10k_mac_vif_chan(arvif->vif, &def)))
1525 return -EINVAL;
1526
1527 ret = ath10k_wmi_vdev_down(ar, arvif->vdev_id);
1528 if (ret) {
1529 ath10k_warn(ar, "failed to bring down ap vdev %i: %d\n",
1530 arvif->vdev_id, ret);
1531 return ret;
1532 }
1533
1534 /* Vdev down reset beacon & presp templates. Reinstall them. Otherwise
1535 * firmware will crash upon vdev up.
1536 */
1537
1538 ret = ath10k_mac_setup_bcn_tmpl(arvif);
1539 if (ret) {
1540 ath10k_warn(ar, "failed to update beacon template: %d\n", ret);
1541 return ret;
1542 }
1543
1544 ret = ath10k_mac_setup_prb_tmpl(arvif);
1545 if (ret) {
1546 ath10k_warn(ar, "failed to update presp template: %d\n", ret);
1547 return ret;
1548 }
1549
1550 ret = ath10k_vdev_restart(arvif, &def);
1551 if (ret) {
1552 ath10k_warn(ar, "failed to restart ap vdev %i: %d\n",
1553 arvif->vdev_id, ret);
1554 return ret;
1555 }
1556
1557 ret = ath10k_wmi_vdev_up(arvif->ar, arvif->vdev_id, arvif->aid,
1558 arvif->bssid);
1559 if (ret) {
1560 ath10k_warn(ar, "failed to bring up ap vdev %i: %d\n",
1561 arvif->vdev_id, ret);
1562 return ret;
1563 }
1564
1565 return 0;
1566}
1567
Kalle Valo5e3dd152013-06-12 20:52:10 +03001568static void ath10k_control_beaconing(struct ath10k_vif *arvif,
Kalle Valo5b07e072014-09-14 12:50:06 +03001569 struct ieee80211_bss_conf *info)
Kalle Valo5e3dd152013-06-12 20:52:10 +03001570{
Michal Kazior7aa7a722014-08-25 12:09:38 +02001571 struct ath10k *ar = arvif->ar;
Kalle Valo5e3dd152013-06-12 20:52:10 +03001572 int ret = 0;
1573
Michal Kazior548db542013-07-05 16:15:15 +03001574 lockdep_assert_held(&arvif->ar->conf_mutex);
1575
Kalle Valo5e3dd152013-06-12 20:52:10 +03001576 if (!info->enable_beacon) {
Michal Kazior500ff9f2015-03-31 10:26:21 +00001577 ret = ath10k_wmi_vdev_down(ar, arvif->vdev_id);
1578 if (ret)
1579 ath10k_warn(ar, "failed to down vdev_id %i: %d\n",
1580 arvif->vdev_id, ret);
Michal Kaziorc930f742014-01-23 11:38:25 +01001581
Michal Kaziorc930f742014-01-23 11:38:25 +01001582 arvif->is_up = false;
1583
Michal Kazior748afc42014-01-23 12:48:21 +01001584 spin_lock_bh(&arvif->ar->data_lock);
Michal Kazior64badcb2014-09-18 11:18:02 +03001585 ath10k_mac_vif_beacon_free(arvif);
Michal Kazior748afc42014-01-23 12:48:21 +01001586 spin_unlock_bh(&arvif->ar->data_lock);
1587
Kalle Valo5e3dd152013-06-12 20:52:10 +03001588 return;
1589 }
1590
1591 arvif->tx_seq_no = 0x1000;
1592
Michal Kaziorc930f742014-01-23 11:38:25 +01001593 arvif->aid = 0;
Kalle Valob25f32c2014-09-14 12:50:49 +03001594 ether_addr_copy(arvif->bssid, info->bssid);
Michal Kaziorc930f742014-01-23 11:38:25 +01001595
1596 ret = ath10k_wmi_vdev_up(arvif->ar, arvif->vdev_id, arvif->aid,
1597 arvif->bssid);
Kalle Valo5e3dd152013-06-12 20:52:10 +03001598 if (ret) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02001599 ath10k_warn(ar, "failed to bring up vdev %d: %i\n",
Ben Greear69244e52014-02-27 18:50:00 +02001600 arvif->vdev_id, ret);
Kalle Valo5e3dd152013-06-12 20:52:10 +03001601 return;
1602 }
Michal Kaziorc930f742014-01-23 11:38:25 +01001603
Michal Kaziorc930f742014-01-23 11:38:25 +01001604 arvif->is_up = true;
1605
Michal Kazior500ff9f2015-03-31 10:26:21 +00001606 ret = ath10k_mac_vif_fix_hidden_ssid(arvif);
1607 if (ret) {
1608 ath10k_warn(ar, "failed to fix hidden ssid for vdev %i, expect trouble: %d\n",
1609 arvif->vdev_id, ret);
1610 return;
1611 }
1612
Michal Kazior7aa7a722014-08-25 12:09:38 +02001613 ath10k_dbg(ar, ATH10K_DBG_MAC, "mac vdev %d up\n", arvif->vdev_id);
Kalle Valo5e3dd152013-06-12 20:52:10 +03001614}
1615
1616static void ath10k_control_ibss(struct ath10k_vif *arvif,
1617 struct ieee80211_bss_conf *info,
1618 const u8 self_peer[ETH_ALEN])
1619{
Michal Kazior7aa7a722014-08-25 12:09:38 +02001620 struct ath10k *ar = arvif->ar;
Bartosz Markowski6d1506e2013-09-26 17:47:15 +02001621 u32 vdev_param;
Kalle Valo5e3dd152013-06-12 20:52:10 +03001622 int ret = 0;
1623
Michal Kazior548db542013-07-05 16:15:15 +03001624 lockdep_assert_held(&arvif->ar->conf_mutex);
1625
Kalle Valo5e3dd152013-06-12 20:52:10 +03001626 if (!info->ibss_joined) {
Michal Kaziorc930f742014-01-23 11:38:25 +01001627 if (is_zero_ether_addr(arvif->bssid))
Kalle Valo5e3dd152013-06-12 20:52:10 +03001628 return;
1629
Joe Perches93803b32015-03-02 19:54:49 -08001630 eth_zero_addr(arvif->bssid);
Kalle Valo5e3dd152013-06-12 20:52:10 +03001631
1632 return;
1633 }
1634
Bartosz Markowski6d1506e2013-09-26 17:47:15 +02001635 vdev_param = arvif->ar->wmi.vdev_param->atim_window;
1636 ret = ath10k_wmi_vdev_set_param(arvif->ar, arvif->vdev_id, vdev_param,
Kalle Valo5e3dd152013-06-12 20:52:10 +03001637 ATH10K_DEFAULT_ATIM);
1638 if (ret)
Michal Kazior7aa7a722014-08-25 12:09:38 +02001639 ath10k_warn(ar, "failed to set IBSS ATIM for vdev %d: %d\n",
Kalle Valo5e3dd152013-06-12 20:52:10 +03001640 arvif->vdev_id, ret);
1641}
1642
Michal Kazior9f9b5742014-12-12 12:41:36 +01001643static int ath10k_mac_vif_recalc_ps_wake_threshold(struct ath10k_vif *arvif)
1644{
1645 struct ath10k *ar = arvif->ar;
1646 u32 param;
1647 u32 value;
1648 int ret;
1649
1650 lockdep_assert_held(&arvif->ar->conf_mutex);
1651
1652 if (arvif->u.sta.uapsd)
1653 value = WMI_STA_PS_TX_WAKE_THRESHOLD_NEVER;
1654 else
1655 value = WMI_STA_PS_TX_WAKE_THRESHOLD_ALWAYS;
1656
1657 param = WMI_STA_PS_PARAM_TX_WAKE_THRESHOLD;
1658 ret = ath10k_wmi_set_sta_ps_param(ar, arvif->vdev_id, param, value);
1659 if (ret) {
1660 ath10k_warn(ar, "failed to submit ps wake threshold %u on vdev %i: %d\n",
1661 value, arvif->vdev_id, ret);
1662 return ret;
1663 }
1664
1665 return 0;
1666}
1667
1668static int ath10k_mac_vif_recalc_ps_poll_count(struct ath10k_vif *arvif)
1669{
1670 struct ath10k *ar = arvif->ar;
1671 u32 param;
1672 u32 value;
1673 int ret;
1674
1675 lockdep_assert_held(&arvif->ar->conf_mutex);
1676
1677 if (arvif->u.sta.uapsd)
1678 value = WMI_STA_PS_PSPOLL_COUNT_UAPSD;
1679 else
1680 value = WMI_STA_PS_PSPOLL_COUNT_NO_MAX;
1681
1682 param = WMI_STA_PS_PARAM_PSPOLL_COUNT;
1683 ret = ath10k_wmi_set_sta_ps_param(ar, arvif->vdev_id,
1684 param, value);
1685 if (ret) {
1686 ath10k_warn(ar, "failed to submit ps poll count %u on vdev %i: %d\n",
1687 value, arvif->vdev_id, ret);
1688 return ret;
1689 }
1690
1691 return 0;
1692}
1693
Michal Kazior424f2632015-07-09 13:08:35 +02001694static int ath10k_mac_num_vifs_started(struct ath10k *ar)
Michal Kaziorcffb41f2015-02-13 13:30:16 +01001695{
1696 struct ath10k_vif *arvif;
1697 int num = 0;
1698
1699 lockdep_assert_held(&ar->conf_mutex);
1700
1701 list_for_each_entry(arvif, &ar->arvifs, list)
Michal Kazior424f2632015-07-09 13:08:35 +02001702 if (arvif->is_started)
Michal Kaziorcffb41f2015-02-13 13:30:16 +01001703 num++;
1704
1705 return num;
1706}
1707
Michal Kaziorad088bf2013-10-16 15:44:46 +03001708static int ath10k_mac_vif_setup_ps(struct ath10k_vif *arvif)
Kalle Valo5e3dd152013-06-12 20:52:10 +03001709{
Michal Kaziorad088bf2013-10-16 15:44:46 +03001710 struct ath10k *ar = arvif->ar;
Michal Kazior526549a2014-12-12 12:41:37 +01001711 struct ieee80211_vif *vif = arvif->vif;
Michal Kaziorad088bf2013-10-16 15:44:46 +03001712 struct ieee80211_conf *conf = &ar->hw->conf;
Kalle Valo5e3dd152013-06-12 20:52:10 +03001713 enum wmi_sta_powersave_param param;
1714 enum wmi_sta_ps_mode psmode;
1715 int ret;
Michal Kazior526549a2014-12-12 12:41:37 +01001716 int ps_timeout;
Michal Kaziorcffb41f2015-02-13 13:30:16 +01001717 bool enable_ps;
Kalle Valo5e3dd152013-06-12 20:52:10 +03001718
Michal Kazior548db542013-07-05 16:15:15 +03001719 lockdep_assert_held(&arvif->ar->conf_mutex);
1720
Michal Kaziorad088bf2013-10-16 15:44:46 +03001721 if (arvif->vif->type != NL80211_IFTYPE_STATION)
1722 return 0;
Kalle Valo5e3dd152013-06-12 20:52:10 +03001723
Michal Kaziorcffb41f2015-02-13 13:30:16 +01001724 enable_ps = arvif->ps;
1725
Michal Kazior424f2632015-07-09 13:08:35 +02001726 if (enable_ps && ath10k_mac_num_vifs_started(ar) > 1 &&
Michal Kaziorcffb41f2015-02-13 13:30:16 +01001727 !test_bit(ATH10K_FW_FEATURE_MULTI_VIF_PS_SUPPORT,
1728 ar->fw_features)) {
1729 ath10k_warn(ar, "refusing to enable ps on vdev %i: not supported by fw\n",
1730 arvif->vdev_id);
1731 enable_ps = false;
1732 }
1733
Janusz Dziedzic917826b2015-05-18 09:38:17 +00001734 if (!arvif->is_started) {
1735 /* mac80211 can update vif powersave state while disconnected.
1736 * Firmware doesn't behave nicely and consumes more power than
1737 * necessary if PS is disabled on a non-started vdev. Hence
1738 * force-enable PS for non-running vdevs.
1739 */
1740 psmode = WMI_STA_PS_MODE_ENABLED;
1741 } else if (enable_ps) {
Kalle Valo5e3dd152013-06-12 20:52:10 +03001742 psmode = WMI_STA_PS_MODE_ENABLED;
1743 param = WMI_STA_PS_PARAM_INACTIVITY_TIME;
1744
Michal Kazior526549a2014-12-12 12:41:37 +01001745 ps_timeout = conf->dynamic_ps_timeout;
1746 if (ps_timeout == 0) {
1747 /* Firmware doesn't like 0 */
1748 ps_timeout = ieee80211_tu_to_usec(
1749 vif->bss_conf.beacon_int) / 1000;
1750 }
1751
Michal Kaziorad088bf2013-10-16 15:44:46 +03001752 ret = ath10k_wmi_set_sta_ps_param(ar, arvif->vdev_id, param,
Michal Kazior526549a2014-12-12 12:41:37 +01001753 ps_timeout);
Kalle Valo5e3dd152013-06-12 20:52:10 +03001754 if (ret) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02001755 ath10k_warn(ar, "failed to set inactivity time for vdev %d: %i\n",
Ben Greear69244e52014-02-27 18:50:00 +02001756 arvif->vdev_id, ret);
Michal Kaziorad088bf2013-10-16 15:44:46 +03001757 return ret;
Kalle Valo5e3dd152013-06-12 20:52:10 +03001758 }
Kalle Valo5e3dd152013-06-12 20:52:10 +03001759 } else {
1760 psmode = WMI_STA_PS_MODE_DISABLED;
1761 }
1762
Michal Kazior7aa7a722014-08-25 12:09:38 +02001763 ath10k_dbg(ar, ATH10K_DBG_MAC, "mac vdev %d psmode %s\n",
Kalle Valo60c3daa2013-09-08 17:56:07 +03001764 arvif->vdev_id, psmode ? "enable" : "disable");
1765
Michal Kaziorad088bf2013-10-16 15:44:46 +03001766 ret = ath10k_wmi_set_psmode(ar, arvif->vdev_id, psmode);
1767 if (ret) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02001768 ath10k_warn(ar, "failed to set PS Mode %d for vdev %d: %d\n",
Kalle Valobe6546f2014-03-25 14:18:51 +02001769 psmode, arvif->vdev_id, ret);
Michal Kaziorad088bf2013-10-16 15:44:46 +03001770 return ret;
1771 }
1772
1773 return 0;
Kalle Valo5e3dd152013-06-12 20:52:10 +03001774}
1775
Michal Kazior46725b152015-01-28 09:57:49 +02001776static int ath10k_mac_vif_disable_keepalive(struct ath10k_vif *arvif)
1777{
1778 struct ath10k *ar = arvif->ar;
1779 struct wmi_sta_keepalive_arg arg = {};
1780 int ret;
1781
1782 lockdep_assert_held(&arvif->ar->conf_mutex);
1783
1784 if (arvif->vdev_type != WMI_VDEV_TYPE_STA)
1785 return 0;
1786
1787 if (!test_bit(WMI_SERVICE_STA_KEEP_ALIVE, ar->wmi.svc_map))
1788 return 0;
1789
1790 /* Some firmware revisions have a bug and ignore the `enabled` field.
1791 * Instead use the interval to disable the keepalive.
1792 */
1793 arg.vdev_id = arvif->vdev_id;
1794 arg.enabled = 1;
1795 arg.method = WMI_STA_KEEPALIVE_METHOD_NULL_FRAME;
1796 arg.interval = WMI_STA_KEEPALIVE_INTERVAL_DISABLE;
1797
1798 ret = ath10k_wmi_sta_keepalive(ar, &arg);
1799 if (ret) {
1800 ath10k_warn(ar, "failed to submit keepalive on vdev %i: %d\n",
1801 arvif->vdev_id, ret);
1802 return ret;
1803 }
1804
1805 return 0;
1806}
1807
Michal Kazior81a9a172015-03-05 16:02:17 +02001808static void ath10k_mac_vif_ap_csa_count_down(struct ath10k_vif *arvif)
1809{
1810 struct ath10k *ar = arvif->ar;
1811 struct ieee80211_vif *vif = arvif->vif;
1812 int ret;
1813
Michal Kazior8513d952015-03-09 14:19:24 +01001814 lockdep_assert_held(&arvif->ar->conf_mutex);
1815
1816 if (WARN_ON(!test_bit(WMI_SERVICE_BEACON_OFFLOAD, ar->wmi.svc_map)))
1817 return;
1818
Michal Kazior81a9a172015-03-05 16:02:17 +02001819 if (arvif->vdev_type != WMI_VDEV_TYPE_AP)
1820 return;
1821
1822 if (!vif->csa_active)
1823 return;
1824
1825 if (!arvif->is_up)
1826 return;
1827
1828 if (!ieee80211_csa_is_complete(vif)) {
1829 ieee80211_csa_update_counter(vif);
1830
1831 ret = ath10k_mac_setup_bcn_tmpl(arvif);
1832 if (ret)
1833 ath10k_warn(ar, "failed to update bcn tmpl during csa: %d\n",
1834 ret);
1835
1836 ret = ath10k_mac_setup_prb_tmpl(arvif);
1837 if (ret)
1838 ath10k_warn(ar, "failed to update prb tmpl during csa: %d\n",
1839 ret);
1840 } else {
1841 ieee80211_csa_finish(vif);
1842 }
1843}
1844
1845static void ath10k_mac_vif_ap_csa_work(struct work_struct *work)
1846{
1847 struct ath10k_vif *arvif = container_of(work, struct ath10k_vif,
1848 ap_csa_work);
1849 struct ath10k *ar = arvif->ar;
1850
1851 mutex_lock(&ar->conf_mutex);
1852 ath10k_mac_vif_ap_csa_count_down(arvif);
1853 mutex_unlock(&ar->conf_mutex);
1854}
1855
Michal Kaziorcc9904e2015-03-10 16:22:01 +02001856static void ath10k_mac_handle_beacon_iter(void *data, u8 *mac,
1857 struct ieee80211_vif *vif)
1858{
1859 struct sk_buff *skb = data;
1860 struct ieee80211_mgmt *mgmt = (void *)skb->data;
1861 struct ath10k_vif *arvif = ath10k_vif_to_arvif(vif);
1862
1863 if (vif->type != NL80211_IFTYPE_STATION)
1864 return;
1865
1866 if (!ether_addr_equal(mgmt->bssid, vif->bss_conf.bssid))
1867 return;
1868
1869 cancel_delayed_work(&arvif->connection_loss_work);
1870}
1871
1872void ath10k_mac_handle_beacon(struct ath10k *ar, struct sk_buff *skb)
1873{
1874 ieee80211_iterate_active_interfaces_atomic(ar->hw,
1875 IEEE80211_IFACE_ITER_NORMAL,
1876 ath10k_mac_handle_beacon_iter,
1877 skb);
1878}
1879
1880static void ath10k_mac_handle_beacon_miss_iter(void *data, u8 *mac,
1881 struct ieee80211_vif *vif)
1882{
1883 u32 *vdev_id = data;
1884 struct ath10k_vif *arvif = ath10k_vif_to_arvif(vif);
1885 struct ath10k *ar = arvif->ar;
1886 struct ieee80211_hw *hw = ar->hw;
1887
1888 if (arvif->vdev_id != *vdev_id)
1889 return;
1890
1891 if (!arvif->is_up)
1892 return;
1893
1894 ieee80211_beacon_loss(vif);
1895
1896 /* Firmware doesn't report beacon loss events repeatedly. If AP probe
1897 * (done by mac80211) succeeds but beacons do not resume then it
1898 * doesn't make sense to continue operation. Queue connection loss work
1899 * which can be cancelled when beacon is received.
1900 */
1901 ieee80211_queue_delayed_work(hw, &arvif->connection_loss_work,
1902 ATH10K_CONNECTION_LOSS_HZ);
1903}
1904
1905void ath10k_mac_handle_beacon_miss(struct ath10k *ar, u32 vdev_id)
1906{
1907 ieee80211_iterate_active_interfaces_atomic(ar->hw,
1908 IEEE80211_IFACE_ITER_NORMAL,
1909 ath10k_mac_handle_beacon_miss_iter,
1910 &vdev_id);
1911}
1912
1913static void ath10k_mac_vif_sta_connection_loss_work(struct work_struct *work)
1914{
1915 struct ath10k_vif *arvif = container_of(work, struct ath10k_vif,
1916 connection_loss_work.work);
1917 struct ieee80211_vif *vif = arvif->vif;
1918
1919 if (!arvif->is_up)
1920 return;
1921
1922 ieee80211_connection_loss(vif);
1923}
1924
Kalle Valo5e3dd152013-06-12 20:52:10 +03001925/**********************/
1926/* Station management */
1927/**********************/
1928
Michal Kazior590922a2014-10-21 10:10:29 +03001929static u32 ath10k_peer_assoc_h_listen_intval(struct ath10k *ar,
1930 struct ieee80211_vif *vif)
1931{
1932 /* Some firmware revisions have unstable STA powersave when listen
1933 * interval is set too high (e.g. 5). The symptoms are firmware doesn't
1934 * generate NullFunc frames properly even if buffered frames have been
1935 * indicated in Beacon TIM. Firmware would seldom wake up to pull
1936 * buffered frames. Often pinging the device from AP would simply fail.
1937 *
1938 * As a workaround set it to 1.
1939 */
1940 if (vif->type == NL80211_IFTYPE_STATION)
1941 return 1;
1942
1943 return ar->hw->conf.listen_interval;
1944}
1945
Kalle Valo5e3dd152013-06-12 20:52:10 +03001946static void ath10k_peer_assoc_h_basic(struct ath10k *ar,
Michal Kazior590922a2014-10-21 10:10:29 +03001947 struct ieee80211_vif *vif,
Kalle Valo5e3dd152013-06-12 20:52:10 +03001948 struct ieee80211_sta *sta,
Kalle Valo5e3dd152013-06-12 20:52:10 +03001949 struct wmi_peer_assoc_complete_arg *arg)
1950{
Michal Kazior590922a2014-10-21 10:10:29 +03001951 struct ath10k_vif *arvif = ath10k_vif_to_arvif(vif);
Michal Kaziorc51880e2015-03-30 09:51:57 +03001952 u32 aid;
Michal Kazior590922a2014-10-21 10:10:29 +03001953
Michal Kazior548db542013-07-05 16:15:15 +03001954 lockdep_assert_held(&ar->conf_mutex);
1955
Michal Kaziorc51880e2015-03-30 09:51:57 +03001956 if (vif->type == NL80211_IFTYPE_STATION)
1957 aid = vif->bss_conf.aid;
1958 else
1959 aid = sta->aid;
1960
Kalle Valob25f32c2014-09-14 12:50:49 +03001961 ether_addr_copy(arg->addr, sta->addr);
Kalle Valo5e3dd152013-06-12 20:52:10 +03001962 arg->vdev_id = arvif->vdev_id;
Michal Kaziorc51880e2015-03-30 09:51:57 +03001963 arg->peer_aid = aid;
Tamizh chelvam3fab30f2015-10-29 14:27:37 +02001964 arg->peer_flags |= arvif->ar->wmi.peer_flags->auth;
Michal Kazior590922a2014-10-21 10:10:29 +03001965 arg->peer_listen_intval = ath10k_peer_assoc_h_listen_intval(ar, vif);
Kalle Valo5e3dd152013-06-12 20:52:10 +03001966 arg->peer_num_spatial_streams = 1;
Michal Kazior590922a2014-10-21 10:10:29 +03001967 arg->peer_caps = vif->bss_conf.assoc_capability;
Kalle Valo5e3dd152013-06-12 20:52:10 +03001968}
1969
1970static void ath10k_peer_assoc_h_crypto(struct ath10k *ar,
Michal Kazior590922a2014-10-21 10:10:29 +03001971 struct ieee80211_vif *vif,
Tamizh chelvam90eceb32015-10-29 14:27:42 +02001972 struct ieee80211_sta *sta,
Kalle Valo5e3dd152013-06-12 20:52:10 +03001973 struct wmi_peer_assoc_complete_arg *arg)
1974{
Kalle Valo5e3dd152013-06-12 20:52:10 +03001975 struct ieee80211_bss_conf *info = &vif->bss_conf;
Michal Kazior500ff9f2015-03-31 10:26:21 +00001976 struct cfg80211_chan_def def;
Kalle Valo5e3dd152013-06-12 20:52:10 +03001977 struct cfg80211_bss *bss;
1978 const u8 *rsnie = NULL;
1979 const u8 *wpaie = NULL;
1980
Michal Kazior548db542013-07-05 16:15:15 +03001981 lockdep_assert_held(&ar->conf_mutex);
1982
Michal Kazior500ff9f2015-03-31 10:26:21 +00001983 if (WARN_ON(ath10k_mac_vif_chan(vif, &def)))
1984 return;
1985
1986 bss = cfg80211_get_bss(ar->hw->wiphy, def.chan, info->bssid, NULL, 0,
1987 IEEE80211_BSS_TYPE_ANY, IEEE80211_PRIVACY_ANY);
Kalle Valo5e3dd152013-06-12 20:52:10 +03001988 if (bss) {
1989 const struct cfg80211_bss_ies *ies;
1990
1991 rcu_read_lock();
1992 rsnie = ieee80211_bss_get_ie(bss, WLAN_EID_RSN);
1993
1994 ies = rcu_dereference(bss->ies);
1995
1996 wpaie = cfg80211_find_vendor_ie(WLAN_OUI_MICROSOFT,
Kalle Valo5b07e072014-09-14 12:50:06 +03001997 WLAN_OUI_TYPE_MICROSOFT_WPA,
1998 ies->data,
1999 ies->len);
Kalle Valo5e3dd152013-06-12 20:52:10 +03002000 rcu_read_unlock();
2001 cfg80211_put_bss(ar->hw->wiphy, bss);
2002 }
2003
2004 /* FIXME: base on RSN IE/WPA IE is a correct idea? */
2005 if (rsnie || wpaie) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02002006 ath10k_dbg(ar, ATH10K_DBG_WMI, "%s: rsn ie found\n", __func__);
Tamizh chelvam3fab30f2015-10-29 14:27:37 +02002007 arg->peer_flags |= ar->wmi.peer_flags->need_ptk_4_way;
Kalle Valo5e3dd152013-06-12 20:52:10 +03002008 }
2009
2010 if (wpaie) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02002011 ath10k_dbg(ar, ATH10K_DBG_WMI, "%s: wpa ie found\n", __func__);
Tamizh chelvam3fab30f2015-10-29 14:27:37 +02002012 arg->peer_flags |= ar->wmi.peer_flags->need_gtk_2_way;
Kalle Valo5e3dd152013-06-12 20:52:10 +03002013 }
Tamizh chelvam90eceb32015-10-29 14:27:42 +02002014
2015 if (sta->mfp &&
2016 test_bit(ATH10K_FW_FEATURE_MFP_SUPPORT, ar->fw_features)) {
2017 arg->peer_flags |= ar->wmi.peer_flags->pmf;
Kalle Valo5e3dd152013-06-12 20:52:10 +03002018 }
2019}
2020
2021static void ath10k_peer_assoc_h_rates(struct ath10k *ar,
Michal Kazior500ff9f2015-03-31 10:26:21 +00002022 struct ieee80211_vif *vif,
Kalle Valo5e3dd152013-06-12 20:52:10 +03002023 struct ieee80211_sta *sta,
2024 struct wmi_peer_assoc_complete_arg *arg)
2025{
Michal Kazior45c9abc2015-04-21 20:42:58 +03002026 struct ath10k_vif *arvif = ath10k_vif_to_arvif(vif);
Kalle Valo5e3dd152013-06-12 20:52:10 +03002027 struct wmi_rate_set_arg *rateset = &arg->peer_legacy_rates;
Michal Kazior500ff9f2015-03-31 10:26:21 +00002028 struct cfg80211_chan_def def;
Kalle Valo5e3dd152013-06-12 20:52:10 +03002029 const struct ieee80211_supported_band *sband;
2030 const struct ieee80211_rate *rates;
Michal Kazior45c9abc2015-04-21 20:42:58 +03002031 enum ieee80211_band band;
Kalle Valo5e3dd152013-06-12 20:52:10 +03002032 u32 ratemask;
Michal Kazior486017c2015-03-30 09:51:54 +03002033 u8 rate;
Kalle Valo5e3dd152013-06-12 20:52:10 +03002034 int i;
2035
Michal Kazior548db542013-07-05 16:15:15 +03002036 lockdep_assert_held(&ar->conf_mutex);
2037
Michal Kazior500ff9f2015-03-31 10:26:21 +00002038 if (WARN_ON(ath10k_mac_vif_chan(vif, &def)))
2039 return;
2040
Michal Kazior45c9abc2015-04-21 20:42:58 +03002041 band = def.chan->band;
2042 sband = ar->hw->wiphy->bands[band];
2043 ratemask = sta->supp_rates[band];
2044 ratemask &= arvif->bitrate_mask.control[band].legacy;
Kalle Valo5e3dd152013-06-12 20:52:10 +03002045 rates = sband->bitrates;
2046
2047 rateset->num_rates = 0;
2048
2049 for (i = 0; i < 32; i++, ratemask >>= 1, rates++) {
2050 if (!(ratemask & 1))
2051 continue;
2052
Michal Kazior486017c2015-03-30 09:51:54 +03002053 rate = ath10k_mac_bitrate_to_rate(rates->bitrate);
2054 rateset->rates[rateset->num_rates] = rate;
Kalle Valo5e3dd152013-06-12 20:52:10 +03002055 rateset->num_rates++;
2056 }
2057}
2058
Michal Kazior45c9abc2015-04-21 20:42:58 +03002059static bool
2060ath10k_peer_assoc_h_ht_masked(const u8 ht_mcs_mask[IEEE80211_HT_MCS_MASK_LEN])
2061{
2062 int nss;
2063
2064 for (nss = 0; nss < IEEE80211_HT_MCS_MASK_LEN; nss++)
2065 if (ht_mcs_mask[nss])
2066 return false;
2067
2068 return true;
2069}
2070
2071static bool
2072ath10k_peer_assoc_h_vht_masked(const u16 vht_mcs_mask[NL80211_VHT_NSS_MAX])
2073{
2074 int nss;
2075
2076 for (nss = 0; nss < NL80211_VHT_NSS_MAX; nss++)
2077 if (vht_mcs_mask[nss])
2078 return false;
2079
2080 return true;
2081}
2082
Kalle Valo5e3dd152013-06-12 20:52:10 +03002083static void ath10k_peer_assoc_h_ht(struct ath10k *ar,
Michal Kazior45c9abc2015-04-21 20:42:58 +03002084 struct ieee80211_vif *vif,
Kalle Valo5e3dd152013-06-12 20:52:10 +03002085 struct ieee80211_sta *sta,
2086 struct wmi_peer_assoc_complete_arg *arg)
2087{
2088 const struct ieee80211_sta_ht_cap *ht_cap = &sta->ht_cap;
Michal Kazior45c9abc2015-04-21 20:42:58 +03002089 struct ath10k_vif *arvif = ath10k_vif_to_arvif(vif);
2090 struct cfg80211_chan_def def;
2091 enum ieee80211_band band;
2092 const u8 *ht_mcs_mask;
2093 const u16 *vht_mcs_mask;
Vivek Natarajan72f8cef2015-10-06 15:19:34 +03002094 int i, n;
2095 u8 max_nss;
Kalle Valoaf762c02014-09-14 12:50:17 +03002096 u32 stbc;
Kalle Valo5e3dd152013-06-12 20:52:10 +03002097
Michal Kazior548db542013-07-05 16:15:15 +03002098 lockdep_assert_held(&ar->conf_mutex);
2099
Michal Kazior45c9abc2015-04-21 20:42:58 +03002100 if (WARN_ON(ath10k_mac_vif_chan(vif, &def)))
2101 return;
2102
Kalle Valo5e3dd152013-06-12 20:52:10 +03002103 if (!ht_cap->ht_supported)
2104 return;
2105
Michal Kazior45c9abc2015-04-21 20:42:58 +03002106 band = def.chan->band;
2107 ht_mcs_mask = arvif->bitrate_mask.control[band].ht_mcs;
2108 vht_mcs_mask = arvif->bitrate_mask.control[band].vht_mcs;
2109
2110 if (ath10k_peer_assoc_h_ht_masked(ht_mcs_mask) &&
2111 ath10k_peer_assoc_h_vht_masked(vht_mcs_mask))
2112 return;
2113
Tamizh chelvam3fab30f2015-10-29 14:27:37 +02002114 arg->peer_flags |= ar->wmi.peer_flags->ht;
Kalle Valo5e3dd152013-06-12 20:52:10 +03002115 arg->peer_max_mpdu = (1 << (IEEE80211_HT_MAX_AMPDU_FACTOR +
2116 ht_cap->ampdu_factor)) - 1;
2117
2118 arg->peer_mpdu_density =
2119 ath10k_parse_mpdudensity(ht_cap->ampdu_density);
2120
2121 arg->peer_ht_caps = ht_cap->cap;
2122 arg->peer_rate_caps |= WMI_RC_HT_FLAG;
2123
2124 if (ht_cap->cap & IEEE80211_HT_CAP_LDPC_CODING)
Tamizh chelvam3fab30f2015-10-29 14:27:37 +02002125 arg->peer_flags |= ar->wmi.peer_flags->ldbc;
Kalle Valo5e3dd152013-06-12 20:52:10 +03002126
2127 if (sta->bandwidth >= IEEE80211_STA_RX_BW_40) {
Tamizh chelvam3fab30f2015-10-29 14:27:37 +02002128 arg->peer_flags |= ar->wmi.peer_flags->bw40;
Kalle Valo5e3dd152013-06-12 20:52:10 +03002129 arg->peer_rate_caps |= WMI_RC_CW40_FLAG;
2130 }
2131
Michal Kazior45c9abc2015-04-21 20:42:58 +03002132 if (arvif->bitrate_mask.control[band].gi != NL80211_TXRATE_FORCE_LGI) {
2133 if (ht_cap->cap & IEEE80211_HT_CAP_SGI_20)
2134 arg->peer_rate_caps |= WMI_RC_SGI_FLAG;
Kalle Valo5e3dd152013-06-12 20:52:10 +03002135
Michal Kazior45c9abc2015-04-21 20:42:58 +03002136 if (ht_cap->cap & IEEE80211_HT_CAP_SGI_40)
2137 arg->peer_rate_caps |= WMI_RC_SGI_FLAG;
2138 }
Kalle Valo5e3dd152013-06-12 20:52:10 +03002139
2140 if (ht_cap->cap & IEEE80211_HT_CAP_TX_STBC) {
2141 arg->peer_rate_caps |= WMI_RC_TX_STBC_FLAG;
Tamizh chelvam3fab30f2015-10-29 14:27:37 +02002142 arg->peer_flags |= ar->wmi.peer_flags->stbc;
Kalle Valo5e3dd152013-06-12 20:52:10 +03002143 }
2144
2145 if (ht_cap->cap & IEEE80211_HT_CAP_RX_STBC) {
Kalle Valo5e3dd152013-06-12 20:52:10 +03002146 stbc = ht_cap->cap & IEEE80211_HT_CAP_RX_STBC;
2147 stbc = stbc >> IEEE80211_HT_CAP_RX_STBC_SHIFT;
2148 stbc = stbc << WMI_RC_RX_STBC_FLAG_S;
2149 arg->peer_rate_caps |= stbc;
Tamizh chelvam3fab30f2015-10-29 14:27:37 +02002150 arg->peer_flags |= ar->wmi.peer_flags->stbc;
Kalle Valo5e3dd152013-06-12 20:52:10 +03002151 }
2152
Kalle Valo5e3dd152013-06-12 20:52:10 +03002153 if (ht_cap->mcs.rx_mask[1] && ht_cap->mcs.rx_mask[2])
2154 arg->peer_rate_caps |= WMI_RC_TS_FLAG;
2155 else if (ht_cap->mcs.rx_mask[1])
2156 arg->peer_rate_caps |= WMI_RC_DS_FLAG;
2157
Michal Kazior45c9abc2015-04-21 20:42:58 +03002158 for (i = 0, n = 0, max_nss = 0; i < IEEE80211_HT_MCS_MASK_LEN * 8; i++)
2159 if ((ht_cap->mcs.rx_mask[i / 8] & BIT(i % 8)) &&
2160 (ht_mcs_mask[i / 8] & BIT(i % 8))) {
2161 max_nss = (i / 8) + 1;
Kalle Valo5e3dd152013-06-12 20:52:10 +03002162 arg->peer_ht_rates.rates[n++] = i;
Michal Kazior45c9abc2015-04-21 20:42:58 +03002163 }
Kalle Valo5e3dd152013-06-12 20:52:10 +03002164
Bartosz Markowskifd71f802014-02-10 13:12:55 +01002165 /*
2166 * This is a workaround for HT-enabled STAs which break the spec
2167 * and have no HT capabilities RX mask (no HT RX MCS map).
2168 *
2169 * As per spec, in section 20.3.5 Modulation and coding scheme (MCS),
2170 * MCS 0 through 7 are mandatory in 20MHz with 800 ns GI at all STAs.
2171 *
2172 * Firmware asserts if such situation occurs.
2173 */
2174 if (n == 0) {
2175 arg->peer_ht_rates.num_rates = 8;
2176 for (i = 0; i < arg->peer_ht_rates.num_rates; i++)
2177 arg->peer_ht_rates.rates[i] = i;
2178 } else {
2179 arg->peer_ht_rates.num_rates = n;
Vivek Natarajan72f8cef2015-10-06 15:19:34 +03002180 arg->peer_num_spatial_streams = min(sta->rx_nss, max_nss);
Bartosz Markowskifd71f802014-02-10 13:12:55 +01002181 }
Kalle Valo5e3dd152013-06-12 20:52:10 +03002182
Michal Kazior7aa7a722014-08-25 12:09:38 +02002183 ath10k_dbg(ar, ATH10K_DBG_MAC, "mac ht peer %pM mcs cnt %d nss %d\n",
Kalle Valo60c3daa2013-09-08 17:56:07 +03002184 arg->addr,
Kalle Valo5e3dd152013-06-12 20:52:10 +03002185 arg->peer_ht_rates.num_rates,
2186 arg->peer_num_spatial_streams);
2187}
2188
Janusz Dziedzicd3d3ff42014-01-21 07:06:53 +01002189static int ath10k_peer_assoc_qos_ap(struct ath10k *ar,
2190 struct ath10k_vif *arvif,
2191 struct ieee80211_sta *sta)
Kalle Valo5e3dd152013-06-12 20:52:10 +03002192{
2193 u32 uapsd = 0;
2194 u32 max_sp = 0;
Janusz Dziedzicd3d3ff42014-01-21 07:06:53 +01002195 int ret = 0;
Kalle Valo5e3dd152013-06-12 20:52:10 +03002196
Michal Kazior548db542013-07-05 16:15:15 +03002197 lockdep_assert_held(&ar->conf_mutex);
2198
Kalle Valo5e3dd152013-06-12 20:52:10 +03002199 if (sta->wme && sta->uapsd_queues) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02002200 ath10k_dbg(ar, ATH10K_DBG_MAC, "mac uapsd_queues 0x%x max_sp %d\n",
Kalle Valo5e3dd152013-06-12 20:52:10 +03002201 sta->uapsd_queues, sta->max_sp);
2202
Kalle Valo5e3dd152013-06-12 20:52:10 +03002203 if (sta->uapsd_queues & IEEE80211_WMM_IE_STA_QOSINFO_AC_VO)
2204 uapsd |= WMI_AP_PS_UAPSD_AC3_DELIVERY_EN |
2205 WMI_AP_PS_UAPSD_AC3_TRIGGER_EN;
2206 if (sta->uapsd_queues & IEEE80211_WMM_IE_STA_QOSINFO_AC_VI)
2207 uapsd |= WMI_AP_PS_UAPSD_AC2_DELIVERY_EN |
2208 WMI_AP_PS_UAPSD_AC2_TRIGGER_EN;
2209 if (sta->uapsd_queues & IEEE80211_WMM_IE_STA_QOSINFO_AC_BK)
2210 uapsd |= WMI_AP_PS_UAPSD_AC1_DELIVERY_EN |
2211 WMI_AP_PS_UAPSD_AC1_TRIGGER_EN;
2212 if (sta->uapsd_queues & IEEE80211_WMM_IE_STA_QOSINFO_AC_BE)
2213 uapsd |= WMI_AP_PS_UAPSD_AC0_DELIVERY_EN |
2214 WMI_AP_PS_UAPSD_AC0_TRIGGER_EN;
2215
Kalle Valo5e3dd152013-06-12 20:52:10 +03002216 if (sta->max_sp < MAX_WMI_AP_PS_PEER_PARAM_MAX_SP)
2217 max_sp = sta->max_sp;
2218
Janusz Dziedzicd3d3ff42014-01-21 07:06:53 +01002219 ret = ath10k_wmi_set_ap_ps_param(ar, arvif->vdev_id,
2220 sta->addr,
2221 WMI_AP_PS_PEER_PARAM_UAPSD,
2222 uapsd);
2223 if (ret) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02002224 ath10k_warn(ar, "failed to set ap ps peer param uapsd for vdev %i: %d\n",
Ben Greear69244e52014-02-27 18:50:00 +02002225 arvif->vdev_id, ret);
Janusz Dziedzicd3d3ff42014-01-21 07:06:53 +01002226 return ret;
2227 }
Kalle Valo5e3dd152013-06-12 20:52:10 +03002228
Janusz Dziedzicd3d3ff42014-01-21 07:06:53 +01002229 ret = ath10k_wmi_set_ap_ps_param(ar, arvif->vdev_id,
2230 sta->addr,
2231 WMI_AP_PS_PEER_PARAM_MAX_SP,
2232 max_sp);
2233 if (ret) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02002234 ath10k_warn(ar, "failed to set ap ps peer param max sp for vdev %i: %d\n",
Ben Greear69244e52014-02-27 18:50:00 +02002235 arvif->vdev_id, ret);
Janusz Dziedzicd3d3ff42014-01-21 07:06:53 +01002236 return ret;
2237 }
Kalle Valo5e3dd152013-06-12 20:52:10 +03002238
2239 /* TODO setup this based on STA listen interval and
2240 beacon interval. Currently we don't know
2241 sta->listen_interval - mac80211 patch required.
2242 Currently use 10 seconds */
Janusz Dziedzicd3d3ff42014-01-21 07:06:53 +01002243 ret = ath10k_wmi_set_ap_ps_param(ar, arvif->vdev_id, sta->addr,
Kalle Valo5b07e072014-09-14 12:50:06 +03002244 WMI_AP_PS_PEER_PARAM_AGEOUT_TIME,
2245 10);
Janusz Dziedzicd3d3ff42014-01-21 07:06:53 +01002246 if (ret) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02002247 ath10k_warn(ar, "failed to set ap ps peer param ageout time for vdev %i: %d\n",
Ben Greear69244e52014-02-27 18:50:00 +02002248 arvif->vdev_id, ret);
Janusz Dziedzicd3d3ff42014-01-21 07:06:53 +01002249 return ret;
2250 }
Kalle Valo5e3dd152013-06-12 20:52:10 +03002251 }
Kalle Valo5e3dd152013-06-12 20:52:10 +03002252
Janusz Dziedzicd3d3ff42014-01-21 07:06:53 +01002253 return 0;
Kalle Valo5e3dd152013-06-12 20:52:10 +03002254}
2255
Michal Kazior45c9abc2015-04-21 20:42:58 +03002256static u16
2257ath10k_peer_assoc_h_vht_limit(u16 tx_mcs_set,
2258 const u16 vht_mcs_limit[NL80211_VHT_NSS_MAX])
2259{
2260 int idx_limit;
2261 int nss;
2262 u16 mcs_map;
2263 u16 mcs;
2264
2265 for (nss = 0; nss < NL80211_VHT_NSS_MAX; nss++) {
2266 mcs_map = ath10k_mac_get_max_vht_mcs_map(tx_mcs_set, nss) &
2267 vht_mcs_limit[nss];
2268
2269 if (mcs_map)
2270 idx_limit = fls(mcs_map) - 1;
2271 else
2272 idx_limit = -1;
2273
2274 switch (idx_limit) {
2275 case 0: /* fall through */
2276 case 1: /* fall through */
2277 case 2: /* fall through */
2278 case 3: /* fall through */
2279 case 4: /* fall through */
2280 case 5: /* fall through */
2281 case 6: /* fall through */
2282 default:
2283 /* see ath10k_mac_can_set_bitrate_mask() */
2284 WARN_ON(1);
2285 /* fall through */
2286 case -1:
2287 mcs = IEEE80211_VHT_MCS_NOT_SUPPORTED;
2288 break;
2289 case 7:
2290 mcs = IEEE80211_VHT_MCS_SUPPORT_0_7;
2291 break;
2292 case 8:
2293 mcs = IEEE80211_VHT_MCS_SUPPORT_0_8;
2294 break;
2295 case 9:
2296 mcs = IEEE80211_VHT_MCS_SUPPORT_0_9;
2297 break;
2298 }
2299
2300 tx_mcs_set &= ~(0x3 << (nss * 2));
2301 tx_mcs_set |= mcs << (nss * 2);
2302 }
2303
2304 return tx_mcs_set;
2305}
2306
Kalle Valo5e3dd152013-06-12 20:52:10 +03002307static void ath10k_peer_assoc_h_vht(struct ath10k *ar,
Michal Kazior500ff9f2015-03-31 10:26:21 +00002308 struct ieee80211_vif *vif,
Kalle Valo5e3dd152013-06-12 20:52:10 +03002309 struct ieee80211_sta *sta,
2310 struct wmi_peer_assoc_complete_arg *arg)
2311{
2312 const struct ieee80211_sta_vht_cap *vht_cap = &sta->vht_cap;
Michal Kazior45c9abc2015-04-21 20:42:58 +03002313 struct ath10k_vif *arvif = ath10k_vif_to_arvif(vif);
Michal Kazior500ff9f2015-03-31 10:26:21 +00002314 struct cfg80211_chan_def def;
Michal Kazior45c9abc2015-04-21 20:42:58 +03002315 enum ieee80211_band band;
2316 const u16 *vht_mcs_mask;
Sujith Manoharana24b88b2013-10-07 19:51:57 -07002317 u8 ampdu_factor;
Kalle Valo5e3dd152013-06-12 20:52:10 +03002318
Michal Kazior500ff9f2015-03-31 10:26:21 +00002319 if (WARN_ON(ath10k_mac_vif_chan(vif, &def)))
2320 return;
2321
Kalle Valo5e3dd152013-06-12 20:52:10 +03002322 if (!vht_cap->vht_supported)
2323 return;
2324
Michal Kazior45c9abc2015-04-21 20:42:58 +03002325 band = def.chan->band;
2326 vht_mcs_mask = arvif->bitrate_mask.control[band].vht_mcs;
2327
2328 if (ath10k_peer_assoc_h_vht_masked(vht_mcs_mask))
2329 return;
2330
Tamizh chelvam3fab30f2015-10-29 14:27:37 +02002331 arg->peer_flags |= ar->wmi.peer_flags->vht;
Yanbo Lid68bb122015-01-23 08:18:20 +08002332
Michal Kazior500ff9f2015-03-31 10:26:21 +00002333 if (def.chan->band == IEEE80211_BAND_2GHZ)
Tamizh chelvam3fab30f2015-10-29 14:27:37 +02002334 arg->peer_flags |= ar->wmi.peer_flags->vht_2g;
Yanbo Lid68bb122015-01-23 08:18:20 +08002335
Kalle Valo5e3dd152013-06-12 20:52:10 +03002336 arg->peer_vht_caps = vht_cap->cap;
2337
Sujith Manoharana24b88b2013-10-07 19:51:57 -07002338 ampdu_factor = (vht_cap->cap &
2339 IEEE80211_VHT_CAP_MAX_A_MPDU_LENGTH_EXPONENT_MASK) >>
2340 IEEE80211_VHT_CAP_MAX_A_MPDU_LENGTH_EXPONENT_SHIFT;
2341
2342 /* Workaround: Some Netgear/Linksys 11ac APs set Rx A-MPDU factor to
2343 * zero in VHT IE. Using it would result in degraded throughput.
2344 * arg->peer_max_mpdu at this point contains HT max_mpdu so keep
2345 * it if VHT max_mpdu is smaller. */
2346 arg->peer_max_mpdu = max(arg->peer_max_mpdu,
2347 (1U << (IEEE80211_HT_MAX_AMPDU_FACTOR +
2348 ampdu_factor)) - 1);
2349
Kalle Valo5e3dd152013-06-12 20:52:10 +03002350 if (sta->bandwidth == IEEE80211_STA_RX_BW_80)
Tamizh chelvam3fab30f2015-10-29 14:27:37 +02002351 arg->peer_flags |= ar->wmi.peer_flags->bw80;
Kalle Valo5e3dd152013-06-12 20:52:10 +03002352
2353 arg->peer_vht_rates.rx_max_rate =
2354 __le16_to_cpu(vht_cap->vht_mcs.rx_highest);
2355 arg->peer_vht_rates.rx_mcs_set =
2356 __le16_to_cpu(vht_cap->vht_mcs.rx_mcs_map);
2357 arg->peer_vht_rates.tx_max_rate =
2358 __le16_to_cpu(vht_cap->vht_mcs.tx_highest);
Michal Kazior45c9abc2015-04-21 20:42:58 +03002359 arg->peer_vht_rates.tx_mcs_set = ath10k_peer_assoc_h_vht_limit(
2360 __le16_to_cpu(vht_cap->vht_mcs.tx_mcs_map), vht_mcs_mask);
Kalle Valo5e3dd152013-06-12 20:52:10 +03002361
Michal Kazior7aa7a722014-08-25 12:09:38 +02002362 ath10k_dbg(ar, ATH10K_DBG_MAC, "mac vht peer %pM max_mpdu %d flags 0x%x\n",
Kalle Valo60c3daa2013-09-08 17:56:07 +03002363 sta->addr, arg->peer_max_mpdu, arg->peer_flags);
Kalle Valo5e3dd152013-06-12 20:52:10 +03002364}
2365
2366static void ath10k_peer_assoc_h_qos(struct ath10k *ar,
Michal Kazior590922a2014-10-21 10:10:29 +03002367 struct ieee80211_vif *vif,
Kalle Valo5e3dd152013-06-12 20:52:10 +03002368 struct ieee80211_sta *sta,
Kalle Valo5e3dd152013-06-12 20:52:10 +03002369 struct wmi_peer_assoc_complete_arg *arg)
2370{
Michal Kazior590922a2014-10-21 10:10:29 +03002371 struct ath10k_vif *arvif = ath10k_vif_to_arvif(vif);
2372
Kalle Valo5e3dd152013-06-12 20:52:10 +03002373 switch (arvif->vdev_type) {
2374 case WMI_VDEV_TYPE_AP:
Janusz Dziedzicd3d3ff42014-01-21 07:06:53 +01002375 if (sta->wme)
Tamizh chelvam3fab30f2015-10-29 14:27:37 +02002376 arg->peer_flags |= arvif->ar->wmi.peer_flags->qos;
Janusz Dziedzicd3d3ff42014-01-21 07:06:53 +01002377
2378 if (sta->wme && sta->uapsd_queues) {
Tamizh chelvam3fab30f2015-10-29 14:27:37 +02002379 arg->peer_flags |= arvif->ar->wmi.peer_flags->apsd;
Janusz Dziedzicd3d3ff42014-01-21 07:06:53 +01002380 arg->peer_rate_caps |= WMI_RC_UAPSD_FLAG;
2381 }
Kalle Valo5e3dd152013-06-12 20:52:10 +03002382 break;
2383 case WMI_VDEV_TYPE_STA:
Michal Kazior590922a2014-10-21 10:10:29 +03002384 if (vif->bss_conf.qos)
Tamizh chelvam3fab30f2015-10-29 14:27:37 +02002385 arg->peer_flags |= arvif->ar->wmi.peer_flags->qos;
Kalle Valo5e3dd152013-06-12 20:52:10 +03002386 break;
Janusz Dziedzic627d9842014-12-17 12:29:54 +02002387 case WMI_VDEV_TYPE_IBSS:
2388 if (sta->wme)
Tamizh chelvam3fab30f2015-10-29 14:27:37 +02002389 arg->peer_flags |= arvif->ar->wmi.peer_flags->qos;
Janusz Dziedzic627d9842014-12-17 12:29:54 +02002390 break;
Kalle Valo5e3dd152013-06-12 20:52:10 +03002391 default:
2392 break;
2393 }
Janusz Dziedzic627d9842014-12-17 12:29:54 +02002394
2395 ath10k_dbg(ar, ATH10K_DBG_MAC, "mac peer %pM qos %d\n",
Tamizh chelvam3fab30f2015-10-29 14:27:37 +02002396 sta->addr, !!(arg->peer_flags &
2397 arvif->ar->wmi.peer_flags->qos));
Kalle Valo5e3dd152013-06-12 20:52:10 +03002398}
2399
Michal Kazior8d7aa6b2015-03-30 09:51:57 +03002400static bool ath10k_mac_sta_has_ofdm_only(struct ieee80211_sta *sta)
Michal Kazior91b12082014-12-12 12:41:35 +01002401{
Michal Kazior8d7aa6b2015-03-30 09:51:57 +03002402 return sta->supp_rates[IEEE80211_BAND_2GHZ] >>
2403 ATH10K_MAC_FIRST_OFDM_RATE_IDX;
Michal Kazior91b12082014-12-12 12:41:35 +01002404}
2405
Kalle Valo5e3dd152013-06-12 20:52:10 +03002406static void ath10k_peer_assoc_h_phymode(struct ath10k *ar,
Michal Kazior590922a2014-10-21 10:10:29 +03002407 struct ieee80211_vif *vif,
Kalle Valo5e3dd152013-06-12 20:52:10 +03002408 struct ieee80211_sta *sta,
2409 struct wmi_peer_assoc_complete_arg *arg)
2410{
Michal Kazior45c9abc2015-04-21 20:42:58 +03002411 struct ath10k_vif *arvif = ath10k_vif_to_arvif(vif);
Michal Kazior500ff9f2015-03-31 10:26:21 +00002412 struct cfg80211_chan_def def;
Michal Kazior45c9abc2015-04-21 20:42:58 +03002413 enum ieee80211_band band;
2414 const u8 *ht_mcs_mask;
2415 const u16 *vht_mcs_mask;
Kalle Valo5e3dd152013-06-12 20:52:10 +03002416 enum wmi_phy_mode phymode = MODE_UNKNOWN;
2417
Michal Kazior500ff9f2015-03-31 10:26:21 +00002418 if (WARN_ON(ath10k_mac_vif_chan(vif, &def)))
2419 return;
2420
Michal Kazior45c9abc2015-04-21 20:42:58 +03002421 band = def.chan->band;
2422 ht_mcs_mask = arvif->bitrate_mask.control[band].ht_mcs;
2423 vht_mcs_mask = arvif->bitrate_mask.control[band].vht_mcs;
2424
2425 switch (band) {
Kalle Valo5e3dd152013-06-12 20:52:10 +03002426 case IEEE80211_BAND_2GHZ:
Michal Kazior45c9abc2015-04-21 20:42:58 +03002427 if (sta->vht_cap.vht_supported &&
2428 !ath10k_peer_assoc_h_vht_masked(vht_mcs_mask)) {
Yanbo Lid68bb122015-01-23 08:18:20 +08002429 if (sta->bandwidth == IEEE80211_STA_RX_BW_40)
2430 phymode = MODE_11AC_VHT40;
2431 else
2432 phymode = MODE_11AC_VHT20;
Michal Kazior45c9abc2015-04-21 20:42:58 +03002433 } else if (sta->ht_cap.ht_supported &&
2434 !ath10k_peer_assoc_h_ht_masked(ht_mcs_mask)) {
Kalle Valo5e3dd152013-06-12 20:52:10 +03002435 if (sta->bandwidth == IEEE80211_STA_RX_BW_40)
2436 phymode = MODE_11NG_HT40;
2437 else
2438 phymode = MODE_11NG_HT20;
Michal Kazior8d7aa6b2015-03-30 09:51:57 +03002439 } else if (ath10k_mac_sta_has_ofdm_only(sta)) {
Kalle Valo5e3dd152013-06-12 20:52:10 +03002440 phymode = MODE_11G;
Michal Kazior91b12082014-12-12 12:41:35 +01002441 } else {
2442 phymode = MODE_11B;
Kalle Valo5e3dd152013-06-12 20:52:10 +03002443 }
2444
2445 break;
2446 case IEEE80211_BAND_5GHZ:
Sujith Manoharan7cc45e92013-09-08 18:19:55 +03002447 /*
2448 * Check VHT first.
2449 */
Michal Kazior45c9abc2015-04-21 20:42:58 +03002450 if (sta->vht_cap.vht_supported &&
2451 !ath10k_peer_assoc_h_vht_masked(vht_mcs_mask)) {
Sujith Manoharan7cc45e92013-09-08 18:19:55 +03002452 if (sta->bandwidth == IEEE80211_STA_RX_BW_80)
2453 phymode = MODE_11AC_VHT80;
2454 else if (sta->bandwidth == IEEE80211_STA_RX_BW_40)
2455 phymode = MODE_11AC_VHT40;
2456 else if (sta->bandwidth == IEEE80211_STA_RX_BW_20)
2457 phymode = MODE_11AC_VHT20;
Michal Kazior45c9abc2015-04-21 20:42:58 +03002458 } else if (sta->ht_cap.ht_supported &&
2459 !ath10k_peer_assoc_h_ht_masked(ht_mcs_mask)) {
2460 if (sta->bandwidth >= IEEE80211_STA_RX_BW_40)
Kalle Valo5e3dd152013-06-12 20:52:10 +03002461 phymode = MODE_11NA_HT40;
2462 else
2463 phymode = MODE_11NA_HT20;
2464 } else {
2465 phymode = MODE_11A;
2466 }
2467
2468 break;
2469 default:
2470 break;
2471 }
2472
Michal Kazior7aa7a722014-08-25 12:09:38 +02002473 ath10k_dbg(ar, ATH10K_DBG_MAC, "mac peer %pM phymode %s\n",
Kalle Valo38a1d472013-09-08 17:56:14 +03002474 sta->addr, ath10k_wmi_phymode_str(phymode));
Kalle Valo60c3daa2013-09-08 17:56:07 +03002475
Kalle Valo5e3dd152013-06-12 20:52:10 +03002476 arg->peer_phymode = phymode;
2477 WARN_ON(phymode == MODE_UNKNOWN);
2478}
2479
Kalle Valob9ada652013-10-16 15:44:46 +03002480static int ath10k_peer_assoc_prepare(struct ath10k *ar,
Michal Kazior590922a2014-10-21 10:10:29 +03002481 struct ieee80211_vif *vif,
Kalle Valob9ada652013-10-16 15:44:46 +03002482 struct ieee80211_sta *sta,
Kalle Valob9ada652013-10-16 15:44:46 +03002483 struct wmi_peer_assoc_complete_arg *arg)
Kalle Valo5e3dd152013-06-12 20:52:10 +03002484{
Michal Kazior548db542013-07-05 16:15:15 +03002485 lockdep_assert_held(&ar->conf_mutex);
2486
Kalle Valob9ada652013-10-16 15:44:46 +03002487 memset(arg, 0, sizeof(*arg));
Kalle Valo5e3dd152013-06-12 20:52:10 +03002488
Michal Kazior590922a2014-10-21 10:10:29 +03002489 ath10k_peer_assoc_h_basic(ar, vif, sta, arg);
Tamizh chelvam90eceb32015-10-29 14:27:42 +02002490 ath10k_peer_assoc_h_crypto(ar, vif, sta, arg);
Michal Kazior500ff9f2015-03-31 10:26:21 +00002491 ath10k_peer_assoc_h_rates(ar, vif, sta, arg);
Michal Kazior45c9abc2015-04-21 20:42:58 +03002492 ath10k_peer_assoc_h_ht(ar, vif, sta, arg);
Michal Kazior500ff9f2015-03-31 10:26:21 +00002493 ath10k_peer_assoc_h_vht(ar, vif, sta, arg);
Michal Kazior590922a2014-10-21 10:10:29 +03002494 ath10k_peer_assoc_h_qos(ar, vif, sta, arg);
2495 ath10k_peer_assoc_h_phymode(ar, vif, sta, arg);
Kalle Valo5e3dd152013-06-12 20:52:10 +03002496
Kalle Valob9ada652013-10-16 15:44:46 +03002497 return 0;
Kalle Valo5e3dd152013-06-12 20:52:10 +03002498}
2499
Michal Kazior90046f52014-02-14 14:45:51 +01002500static const u32 ath10k_smps_map[] = {
2501 [WLAN_HT_CAP_SM_PS_STATIC] = WMI_PEER_SMPS_STATIC,
2502 [WLAN_HT_CAP_SM_PS_DYNAMIC] = WMI_PEER_SMPS_DYNAMIC,
2503 [WLAN_HT_CAP_SM_PS_INVALID] = WMI_PEER_SMPS_PS_NONE,
2504 [WLAN_HT_CAP_SM_PS_DISABLED] = WMI_PEER_SMPS_PS_NONE,
2505};
2506
2507static int ath10k_setup_peer_smps(struct ath10k *ar, struct ath10k_vif *arvif,
2508 const u8 *addr,
2509 const struct ieee80211_sta_ht_cap *ht_cap)
2510{
2511 int smps;
2512
2513 if (!ht_cap->ht_supported)
2514 return 0;
2515
2516 smps = ht_cap->cap & IEEE80211_HT_CAP_SM_PS;
2517 smps >>= IEEE80211_HT_CAP_SM_PS_SHIFT;
2518
2519 if (smps >= ARRAY_SIZE(ath10k_smps_map))
2520 return -EINVAL;
2521
2522 return ath10k_wmi_peer_set_param(ar, arvif->vdev_id, addr,
2523 WMI_PEER_SMPS_STATE,
2524 ath10k_smps_map[smps]);
2525}
2526
Michal Kazior139e1702015-02-15 16:50:42 +02002527static int ath10k_mac_vif_recalc_txbf(struct ath10k *ar,
2528 struct ieee80211_vif *vif,
2529 struct ieee80211_sta_vht_cap vht_cap)
2530{
2531 struct ath10k_vif *arvif = ath10k_vif_to_arvif(vif);
2532 int ret;
2533 u32 param;
2534 u32 value;
2535
Vivek Natarajan08e75ea2015-08-04 10:45:11 +05302536 if (ath10k_wmi_get_txbf_conf_scheme(ar) != WMI_TXBF_CONF_AFTER_ASSOC)
2537 return 0;
2538
Michal Kazior139e1702015-02-15 16:50:42 +02002539 if (!(ar->vht_cap_info &
2540 (IEEE80211_VHT_CAP_SU_BEAMFORMEE_CAPABLE |
2541 IEEE80211_VHT_CAP_MU_BEAMFORMEE_CAPABLE |
2542 IEEE80211_VHT_CAP_SU_BEAMFORMER_CAPABLE |
2543 IEEE80211_VHT_CAP_MU_BEAMFORMER_CAPABLE)))
2544 return 0;
2545
2546 param = ar->wmi.vdev_param->txbf;
2547 value = 0;
2548
2549 if (WARN_ON(param == WMI_VDEV_PARAM_UNSUPPORTED))
2550 return 0;
2551
2552 /* The following logic is correct. If a remote STA advertises support
2553 * for being a beamformer then we should enable us being a beamformee.
2554 */
2555
2556 if (ar->vht_cap_info &
2557 (IEEE80211_VHT_CAP_SU_BEAMFORMEE_CAPABLE |
2558 IEEE80211_VHT_CAP_MU_BEAMFORMEE_CAPABLE)) {
2559 if (vht_cap.cap & IEEE80211_VHT_CAP_SU_BEAMFORMER_CAPABLE)
2560 value |= WMI_VDEV_PARAM_TXBF_SU_TX_BFEE;
2561
2562 if (vht_cap.cap & IEEE80211_VHT_CAP_MU_BEAMFORMER_CAPABLE)
2563 value |= WMI_VDEV_PARAM_TXBF_MU_TX_BFEE;
2564 }
2565
2566 if (ar->vht_cap_info &
2567 (IEEE80211_VHT_CAP_SU_BEAMFORMER_CAPABLE |
2568 IEEE80211_VHT_CAP_MU_BEAMFORMER_CAPABLE)) {
2569 if (vht_cap.cap & IEEE80211_VHT_CAP_SU_BEAMFORMEE_CAPABLE)
2570 value |= WMI_VDEV_PARAM_TXBF_SU_TX_BFER;
2571
2572 if (vht_cap.cap & IEEE80211_VHT_CAP_MU_BEAMFORMEE_CAPABLE)
2573 value |= WMI_VDEV_PARAM_TXBF_MU_TX_BFER;
2574 }
2575
2576 if (value & WMI_VDEV_PARAM_TXBF_MU_TX_BFEE)
2577 value |= WMI_VDEV_PARAM_TXBF_SU_TX_BFEE;
2578
2579 if (value & WMI_VDEV_PARAM_TXBF_MU_TX_BFER)
2580 value |= WMI_VDEV_PARAM_TXBF_SU_TX_BFER;
2581
2582 ret = ath10k_wmi_vdev_set_param(ar, arvif->vdev_id, param, value);
2583 if (ret) {
2584 ath10k_warn(ar, "failed to submit vdev param txbf 0x%x: %d\n",
2585 value, ret);
2586 return ret;
2587 }
2588
2589 return 0;
2590}
2591
Kalle Valo5e3dd152013-06-12 20:52:10 +03002592/* can be called only in mac80211 callbacks due to `key_count` usage */
2593static void ath10k_bss_assoc(struct ieee80211_hw *hw,
2594 struct ieee80211_vif *vif,
2595 struct ieee80211_bss_conf *bss_conf)
2596{
2597 struct ath10k *ar = hw->priv;
2598 struct ath10k_vif *arvif = ath10k_vif_to_arvif(vif);
Michal Kazior90046f52014-02-14 14:45:51 +01002599 struct ieee80211_sta_ht_cap ht_cap;
Michal Kazior139e1702015-02-15 16:50:42 +02002600 struct ieee80211_sta_vht_cap vht_cap;
Kalle Valob9ada652013-10-16 15:44:46 +03002601 struct wmi_peer_assoc_complete_arg peer_arg;
Kalle Valo5e3dd152013-06-12 20:52:10 +03002602 struct ieee80211_sta *ap_sta;
2603 int ret;
2604
Michal Kazior548db542013-07-05 16:15:15 +03002605 lockdep_assert_held(&ar->conf_mutex);
2606
Michal Kazior077efc82014-10-21 10:10:29 +03002607 ath10k_dbg(ar, ATH10K_DBG_MAC, "mac vdev %i assoc bssid %pM aid %d\n",
2608 arvif->vdev_id, arvif->bssid, arvif->aid);
2609
Kalle Valo5e3dd152013-06-12 20:52:10 +03002610 rcu_read_lock();
2611
2612 ap_sta = ieee80211_find_sta(vif, bss_conf->bssid);
2613 if (!ap_sta) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02002614 ath10k_warn(ar, "failed to find station entry for bss %pM vdev %i\n",
Ben Greear69244e52014-02-27 18:50:00 +02002615 bss_conf->bssid, arvif->vdev_id);
Kalle Valo5e3dd152013-06-12 20:52:10 +03002616 rcu_read_unlock();
2617 return;
2618 }
2619
Michal Kazior90046f52014-02-14 14:45:51 +01002620 /* ap_sta must be accessed only within rcu section which must be left
2621 * before calling ath10k_setup_peer_smps() which might sleep. */
2622 ht_cap = ap_sta->ht_cap;
Michal Kazior139e1702015-02-15 16:50:42 +02002623 vht_cap = ap_sta->vht_cap;
Michal Kazior90046f52014-02-14 14:45:51 +01002624
Michal Kazior590922a2014-10-21 10:10:29 +03002625 ret = ath10k_peer_assoc_prepare(ar, vif, ap_sta, &peer_arg);
Kalle Valo5e3dd152013-06-12 20:52:10 +03002626 if (ret) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02002627 ath10k_warn(ar, "failed to prepare peer assoc for %pM vdev %i: %d\n",
Ben Greear69244e52014-02-27 18:50:00 +02002628 bss_conf->bssid, arvif->vdev_id, ret);
Kalle Valo5e3dd152013-06-12 20:52:10 +03002629 rcu_read_unlock();
2630 return;
2631 }
2632
2633 rcu_read_unlock();
2634
Kalle Valob9ada652013-10-16 15:44:46 +03002635 ret = ath10k_wmi_peer_assoc(ar, &peer_arg);
2636 if (ret) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02002637 ath10k_warn(ar, "failed to run peer assoc for %pM vdev %i: %d\n",
Ben Greear69244e52014-02-27 18:50:00 +02002638 bss_conf->bssid, arvif->vdev_id, ret);
Kalle Valob9ada652013-10-16 15:44:46 +03002639 return;
2640 }
2641
Michal Kazior90046f52014-02-14 14:45:51 +01002642 ret = ath10k_setup_peer_smps(ar, arvif, bss_conf->bssid, &ht_cap);
2643 if (ret) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02002644 ath10k_warn(ar, "failed to setup peer SMPS for vdev %i: %d\n",
Ben Greear69244e52014-02-27 18:50:00 +02002645 arvif->vdev_id, ret);
Michal Kazior90046f52014-02-14 14:45:51 +01002646 return;
2647 }
2648
Michal Kazior139e1702015-02-15 16:50:42 +02002649 ret = ath10k_mac_vif_recalc_txbf(ar, vif, vht_cap);
2650 if (ret) {
2651 ath10k_warn(ar, "failed to recalc txbf for vdev %i on bss %pM: %d\n",
2652 arvif->vdev_id, bss_conf->bssid, ret);
2653 return;
2654 }
2655
Michal Kazior7aa7a722014-08-25 12:09:38 +02002656 ath10k_dbg(ar, ATH10K_DBG_MAC,
Kalle Valo60c3daa2013-09-08 17:56:07 +03002657 "mac vdev %d up (associated) bssid %pM aid %d\n",
2658 arvif->vdev_id, bss_conf->bssid, bss_conf->aid);
2659
Michal Kazior077efc82014-10-21 10:10:29 +03002660 WARN_ON(arvif->is_up);
2661
Michal Kaziorc930f742014-01-23 11:38:25 +01002662 arvif->aid = bss_conf->aid;
Kalle Valob25f32c2014-09-14 12:50:49 +03002663 ether_addr_copy(arvif->bssid, bss_conf->bssid);
Michal Kaziorc930f742014-01-23 11:38:25 +01002664
2665 ret = ath10k_wmi_vdev_up(ar, arvif->vdev_id, arvif->aid, arvif->bssid);
2666 if (ret) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02002667 ath10k_warn(ar, "failed to set vdev %d up: %d\n",
Kalle Valo5e3dd152013-06-12 20:52:10 +03002668 arvif->vdev_id, ret);
Michal Kaziorc930f742014-01-23 11:38:25 +01002669 return;
2670 }
2671
2672 arvif->is_up = true;
Michal Kazior0a987fb2015-02-13 13:30:15 +01002673
2674 /* Workaround: Some firmware revisions (tested with qca6174
2675 * WLAN.RM.2.0-00073) have buggy powersave state machine and must be
2676 * poked with peer param command.
2677 */
2678 ret = ath10k_wmi_peer_set_param(ar, arvif->vdev_id, arvif->bssid,
2679 WMI_PEER_DUMMY_VAR, 1);
2680 if (ret) {
2681 ath10k_warn(ar, "failed to poke peer %pM param for ps workaround on vdev %i: %d\n",
2682 arvif->bssid, arvif->vdev_id, ret);
2683 return;
2684 }
Kalle Valo5e3dd152013-06-12 20:52:10 +03002685}
2686
Kalle Valo5e3dd152013-06-12 20:52:10 +03002687static void ath10k_bss_disassoc(struct ieee80211_hw *hw,
2688 struct ieee80211_vif *vif)
2689{
2690 struct ath10k *ar = hw->priv;
2691 struct ath10k_vif *arvif = ath10k_vif_to_arvif(vif);
Michal Kazior139e1702015-02-15 16:50:42 +02002692 struct ieee80211_sta_vht_cap vht_cap = {};
Kalle Valo5e3dd152013-06-12 20:52:10 +03002693 int ret;
2694
Michal Kazior548db542013-07-05 16:15:15 +03002695 lockdep_assert_held(&ar->conf_mutex);
2696
Michal Kazior077efc82014-10-21 10:10:29 +03002697 ath10k_dbg(ar, ATH10K_DBG_MAC, "mac vdev %i disassoc bssid %pM\n",
2698 arvif->vdev_id, arvif->bssid);
Kalle Valo60c3daa2013-09-08 17:56:07 +03002699
Kalle Valo5e3dd152013-06-12 20:52:10 +03002700 ret = ath10k_wmi_vdev_down(ar, arvif->vdev_id);
Michal Kazior077efc82014-10-21 10:10:29 +03002701 if (ret)
2702 ath10k_warn(ar, "faield to down vdev %i: %d\n",
2703 arvif->vdev_id, ret);
Kalle Valo5e3dd152013-06-12 20:52:10 +03002704
SenthilKumar Jegadeesan627613f2015-01-29 13:50:38 +02002705 arvif->def_wep_key_idx = -1;
2706
Michal Kazior139e1702015-02-15 16:50:42 +02002707 ret = ath10k_mac_vif_recalc_txbf(ar, vif, vht_cap);
2708 if (ret) {
2709 ath10k_warn(ar, "failed to recalc txbf for vdev %i: %d\n",
2710 arvif->vdev_id, ret);
2711 return;
2712 }
2713
Michal Kaziorc930f742014-01-23 11:38:25 +01002714 arvif->is_up = false;
Michal Kaziorcc9904e2015-03-10 16:22:01 +02002715
2716 cancel_delayed_work_sync(&arvif->connection_loss_work);
Kalle Valo5e3dd152013-06-12 20:52:10 +03002717}
2718
Michal Kazior590922a2014-10-21 10:10:29 +03002719static int ath10k_station_assoc(struct ath10k *ar,
2720 struct ieee80211_vif *vif,
2721 struct ieee80211_sta *sta,
2722 bool reassoc)
Kalle Valo5e3dd152013-06-12 20:52:10 +03002723{
Michal Kazior590922a2014-10-21 10:10:29 +03002724 struct ath10k_vif *arvif = ath10k_vif_to_arvif(vif);
Kalle Valob9ada652013-10-16 15:44:46 +03002725 struct wmi_peer_assoc_complete_arg peer_arg;
Kalle Valo5e3dd152013-06-12 20:52:10 +03002726 int ret = 0;
2727
Michal Kazior548db542013-07-05 16:15:15 +03002728 lockdep_assert_held(&ar->conf_mutex);
2729
Michal Kazior590922a2014-10-21 10:10:29 +03002730 ret = ath10k_peer_assoc_prepare(ar, vif, sta, &peer_arg);
Kalle Valo5e3dd152013-06-12 20:52:10 +03002731 if (ret) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02002732 ath10k_warn(ar, "failed to prepare WMI peer assoc for %pM vdev %i: %i\n",
Ben Greear69244e52014-02-27 18:50:00 +02002733 sta->addr, arvif->vdev_id, ret);
Kalle Valob9ada652013-10-16 15:44:46 +03002734 return ret;
2735 }
2736
2737 ret = ath10k_wmi_peer_assoc(ar, &peer_arg);
2738 if (ret) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02002739 ath10k_warn(ar, "failed to run peer assoc for STA %pM vdev %i: %d\n",
Ben Greear69244e52014-02-27 18:50:00 +02002740 sta->addr, arvif->vdev_id, ret);
Kalle Valo5e3dd152013-06-12 20:52:10 +03002741 return ret;
2742 }
2743
Michal Kaziorb1ecde32014-10-21 10:10:29 +03002744 /* Re-assoc is run only to update supported rates for given station. It
2745 * doesn't make much sense to reconfigure the peer completely.
2746 */
2747 if (!reassoc) {
2748 ret = ath10k_setup_peer_smps(ar, arvif, sta->addr,
2749 &sta->ht_cap);
Marek Kwaczynskie81bd102014-03-11 12:58:00 +02002750 if (ret) {
Michal Kaziorb1ecde32014-10-21 10:10:29 +03002751 ath10k_warn(ar, "failed to setup peer SMPS for vdev %d: %d\n",
Marek Kwaczynskie81bd102014-03-11 12:58:00 +02002752 arvif->vdev_id, ret);
2753 return ret;
2754 }
Marek Kwaczynskie81bd102014-03-11 12:58:00 +02002755
Michal Kaziorb1ecde32014-10-21 10:10:29 +03002756 ret = ath10k_peer_assoc_qos_ap(ar, arvif, sta);
2757 if (ret) {
2758 ath10k_warn(ar, "failed to set qos params for STA %pM for vdev %i: %d\n",
2759 sta->addr, arvif->vdev_id, ret);
2760 return ret;
2761 }
Kalle Valo5e3dd152013-06-12 20:52:10 +03002762
Michal Kaziorb1ecde32014-10-21 10:10:29 +03002763 if (!sta->wme) {
2764 arvif->num_legacy_stations++;
2765 ret = ath10k_recalc_rtscts_prot(arvif);
2766 if (ret) {
2767 ath10k_warn(ar, "failed to recalculate rts/cts prot for vdev %d: %d\n",
2768 arvif->vdev_id, ret);
2769 return ret;
2770 }
2771 }
2772
SenthilKumar Jegadeesan627613f2015-01-29 13:50:38 +02002773 /* Plumb cached keys only for static WEP */
2774 if (arvif->def_wep_key_idx != -1) {
2775 ret = ath10k_install_peer_wep_keys(arvif, sta->addr);
2776 if (ret) {
2777 ath10k_warn(ar, "failed to install peer wep keys for vdev %i: %d\n",
2778 arvif->vdev_id, ret);
2779 return ret;
2780 }
Kalle Valo5e3dd152013-06-12 20:52:10 +03002781 }
2782 }
2783
Kalle Valo5e3dd152013-06-12 20:52:10 +03002784 return ret;
2785}
2786
Michal Kazior590922a2014-10-21 10:10:29 +03002787static int ath10k_station_disassoc(struct ath10k *ar,
2788 struct ieee80211_vif *vif,
Kalle Valo5e3dd152013-06-12 20:52:10 +03002789 struct ieee80211_sta *sta)
2790{
Michal Kazior590922a2014-10-21 10:10:29 +03002791 struct ath10k_vif *arvif = ath10k_vif_to_arvif(vif);
Kalle Valo5e3dd152013-06-12 20:52:10 +03002792 int ret = 0;
2793
2794 lockdep_assert_held(&ar->conf_mutex);
2795
Marek Kwaczynskie81bd102014-03-11 12:58:00 +02002796 if (!sta->wme) {
2797 arvif->num_legacy_stations--;
2798 ret = ath10k_recalc_rtscts_prot(arvif);
2799 if (ret) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02002800 ath10k_warn(ar, "failed to recalculate rts/cts prot for vdev %d: %d\n",
Marek Kwaczynskie81bd102014-03-11 12:58:00 +02002801 arvif->vdev_id, ret);
2802 return ret;
2803 }
2804 }
2805
Kalle Valo5e3dd152013-06-12 20:52:10 +03002806 ret = ath10k_clear_peer_keys(arvif, sta->addr);
2807 if (ret) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02002808 ath10k_warn(ar, "failed to clear all peer wep keys for vdev %i: %d\n",
Ben Greear69244e52014-02-27 18:50:00 +02002809 arvif->vdev_id, ret);
Kalle Valo5e3dd152013-06-12 20:52:10 +03002810 return ret;
2811 }
2812
2813 return ret;
2814}
2815
2816/**************/
2817/* Regulatory */
2818/**************/
2819
2820static int ath10k_update_channel_list(struct ath10k *ar)
2821{
2822 struct ieee80211_hw *hw = ar->hw;
2823 struct ieee80211_supported_band **bands;
2824 enum ieee80211_band band;
2825 struct ieee80211_channel *channel;
2826 struct wmi_scan_chan_list_arg arg = {0};
2827 struct wmi_channel_arg *ch;
2828 bool passive;
2829 int len;
2830 int ret;
2831 int i;
2832
Michal Kazior548db542013-07-05 16:15:15 +03002833 lockdep_assert_held(&ar->conf_mutex);
2834
Kalle Valo5e3dd152013-06-12 20:52:10 +03002835 bands = hw->wiphy->bands;
2836 for (band = 0; band < IEEE80211_NUM_BANDS; band++) {
2837 if (!bands[band])
2838 continue;
2839
2840 for (i = 0; i < bands[band]->n_channels; i++) {
2841 if (bands[band]->channels[i].flags &
2842 IEEE80211_CHAN_DISABLED)
2843 continue;
2844
2845 arg.n_channels++;
2846 }
2847 }
2848
2849 len = sizeof(struct wmi_channel_arg) * arg.n_channels;
2850 arg.channels = kzalloc(len, GFP_KERNEL);
2851 if (!arg.channels)
2852 return -ENOMEM;
2853
2854 ch = arg.channels;
2855 for (band = 0; band < IEEE80211_NUM_BANDS; band++) {
2856 if (!bands[band])
2857 continue;
2858
2859 for (i = 0; i < bands[band]->n_channels; i++) {
2860 channel = &bands[band]->channels[i];
2861
2862 if (channel->flags & IEEE80211_CHAN_DISABLED)
2863 continue;
2864
2865 ch->allow_ht = true;
2866
2867 /* FIXME: when should we really allow VHT? */
2868 ch->allow_vht = true;
2869
2870 ch->allow_ibss =
Luis R. Rodriguez8fe02e12013-10-21 19:22:25 +02002871 !(channel->flags & IEEE80211_CHAN_NO_IR);
Kalle Valo5e3dd152013-06-12 20:52:10 +03002872
2873 ch->ht40plus =
2874 !(channel->flags & IEEE80211_CHAN_NO_HT40PLUS);
2875
Marek Puzyniake8a50f82013-11-20 09:59:47 +02002876 ch->chan_radar =
2877 !!(channel->flags & IEEE80211_CHAN_RADAR);
2878
Luis R. Rodriguez8fe02e12013-10-21 19:22:25 +02002879 passive = channel->flags & IEEE80211_CHAN_NO_IR;
Kalle Valo5e3dd152013-06-12 20:52:10 +03002880 ch->passive = passive;
2881
2882 ch->freq = channel->center_freq;
Michal Kazior2d667212014-09-18 15:21:21 +02002883 ch->band_center_freq1 = channel->center_freq;
Michal Kazior89c5c842013-10-23 04:02:13 -07002884 ch->min_power = 0;
Michal Kazior02256932013-10-23 04:02:14 -07002885 ch->max_power = channel->max_power * 2;
2886 ch->max_reg_power = channel->max_reg_power * 2;
2887 ch->max_antenna_gain = channel->max_antenna_gain * 2;
Kalle Valo5e3dd152013-06-12 20:52:10 +03002888 ch->reg_class_id = 0; /* FIXME */
2889
2890 /* FIXME: why use only legacy modes, why not any
2891 * HT/VHT modes? Would that even make any
2892 * difference? */
2893 if (channel->band == IEEE80211_BAND_2GHZ)
2894 ch->mode = MODE_11G;
2895 else
2896 ch->mode = MODE_11A;
2897
2898 if (WARN_ON_ONCE(ch->mode == MODE_UNKNOWN))
2899 continue;
2900
Michal Kazior7aa7a722014-08-25 12:09:38 +02002901 ath10k_dbg(ar, ATH10K_DBG_WMI,
Kalle Valo60c3daa2013-09-08 17:56:07 +03002902 "mac channel [%zd/%d] freq %d maxpower %d regpower %d antenna %d mode %d\n",
2903 ch - arg.channels, arg.n_channels,
Kalle Valo5e3dd152013-06-12 20:52:10 +03002904 ch->freq, ch->max_power, ch->max_reg_power,
2905 ch->max_antenna_gain, ch->mode);
2906
2907 ch++;
2908 }
2909 }
2910
2911 ret = ath10k_wmi_scan_chan_list(ar, &arg);
2912 kfree(arg.channels);
2913
2914 return ret;
2915}
2916
Marek Puzyniak821af6a2014-03-21 17:46:57 +02002917static enum wmi_dfs_region
2918ath10k_mac_get_dfs_region(enum nl80211_dfs_regions dfs_region)
2919{
2920 switch (dfs_region) {
2921 case NL80211_DFS_UNSET:
2922 return WMI_UNINIT_DFS_DOMAIN;
2923 case NL80211_DFS_FCC:
2924 return WMI_FCC_DFS_DOMAIN;
2925 case NL80211_DFS_ETSI:
2926 return WMI_ETSI_DFS_DOMAIN;
2927 case NL80211_DFS_JP:
2928 return WMI_MKK4_DFS_DOMAIN;
2929 }
2930 return WMI_UNINIT_DFS_DOMAIN;
2931}
2932
Michal Kaziorf7843d72013-07-16 09:38:52 +02002933static void ath10k_regd_update(struct ath10k *ar)
Kalle Valo5e3dd152013-06-12 20:52:10 +03002934{
Kalle Valo5e3dd152013-06-12 20:52:10 +03002935 struct reg_dmn_pair_mapping *regpair;
Kalle Valo5e3dd152013-06-12 20:52:10 +03002936 int ret;
Marek Puzyniak821af6a2014-03-21 17:46:57 +02002937 enum wmi_dfs_region wmi_dfs_reg;
2938 enum nl80211_dfs_regions nl_dfs_reg;
Kalle Valo5e3dd152013-06-12 20:52:10 +03002939
Michal Kaziorf7843d72013-07-16 09:38:52 +02002940 lockdep_assert_held(&ar->conf_mutex);
Kalle Valo5e3dd152013-06-12 20:52:10 +03002941
2942 ret = ath10k_update_channel_list(ar);
2943 if (ret)
Michal Kazior7aa7a722014-08-25 12:09:38 +02002944 ath10k_warn(ar, "failed to update channel list: %d\n", ret);
Kalle Valo5e3dd152013-06-12 20:52:10 +03002945
2946 regpair = ar->ath_common.regulatory.regpair;
Michal Kaziorf7843d72013-07-16 09:38:52 +02002947
Marek Puzyniak821af6a2014-03-21 17:46:57 +02002948 if (config_enabled(CONFIG_ATH10K_DFS_CERTIFIED) && ar->dfs_detector) {
2949 nl_dfs_reg = ar->dfs_detector->region;
2950 wmi_dfs_reg = ath10k_mac_get_dfs_region(nl_dfs_reg);
2951 } else {
2952 wmi_dfs_reg = WMI_UNINIT_DFS_DOMAIN;
2953 }
2954
Kalle Valo5e3dd152013-06-12 20:52:10 +03002955 /* Target allows setting up per-band regdomain but ath_common provides
2956 * a combined one only */
2957 ret = ath10k_wmi_pdev_set_regdomain(ar,
Kalle Valoef8c0012014-02-13 18:13:12 +02002958 regpair->reg_domain,
2959 regpair->reg_domain, /* 2ghz */
2960 regpair->reg_domain, /* 5ghz */
Kalle Valo5e3dd152013-06-12 20:52:10 +03002961 regpair->reg_2ghz_ctl,
Marek Puzyniak821af6a2014-03-21 17:46:57 +02002962 regpair->reg_5ghz_ctl,
2963 wmi_dfs_reg);
Kalle Valo5e3dd152013-06-12 20:52:10 +03002964 if (ret)
Michal Kazior7aa7a722014-08-25 12:09:38 +02002965 ath10k_warn(ar, "failed to set pdev regdomain: %d\n", ret);
Michal Kaziorf7843d72013-07-16 09:38:52 +02002966}
Michal Kazior548db542013-07-05 16:15:15 +03002967
Michal Kaziorf7843d72013-07-16 09:38:52 +02002968static void ath10k_reg_notifier(struct wiphy *wiphy,
2969 struct regulatory_request *request)
2970{
2971 struct ieee80211_hw *hw = wiphy_to_ieee80211_hw(wiphy);
2972 struct ath10k *ar = hw->priv;
Janusz Dziedzic9702c682013-11-20 09:59:41 +02002973 bool result;
Michal Kaziorf7843d72013-07-16 09:38:52 +02002974
2975 ath_reg_notifier_apply(wiphy, request, &ar->ath_common.regulatory);
2976
Janusz Dziedzic9702c682013-11-20 09:59:41 +02002977 if (config_enabled(CONFIG_ATH10K_DFS_CERTIFIED) && ar->dfs_detector) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02002978 ath10k_dbg(ar, ATH10K_DBG_REGULATORY, "dfs region 0x%x\n",
Janusz Dziedzic9702c682013-11-20 09:59:41 +02002979 request->dfs_region);
2980 result = ar->dfs_detector->set_dfs_domain(ar->dfs_detector,
2981 request->dfs_region);
2982 if (!result)
Michal Kazior7aa7a722014-08-25 12:09:38 +02002983 ath10k_warn(ar, "DFS region 0x%X not supported, will trigger radar for every pulse\n",
Janusz Dziedzic9702c682013-11-20 09:59:41 +02002984 request->dfs_region);
2985 }
2986
Michal Kaziorf7843d72013-07-16 09:38:52 +02002987 mutex_lock(&ar->conf_mutex);
2988 if (ar->state == ATH10K_STATE_ON)
2989 ath10k_regd_update(ar);
Michal Kazior548db542013-07-05 16:15:15 +03002990 mutex_unlock(&ar->conf_mutex);
Kalle Valo5e3dd152013-06-12 20:52:10 +03002991}
2992
2993/***************/
2994/* TX handlers */
2995/***************/
2996
Michal Kaziora30c7d02016-03-06 16:14:23 +02002997enum ath10k_mac_tx_path {
2998 ATH10K_MAC_TX_HTT,
2999 ATH10K_MAC_TX_HTT_MGMT,
3000 ATH10K_MAC_TX_WMI_MGMT,
3001 ATH10K_MAC_TX_UNKNOWN,
3002};
3003
Michal Kazior96d828d2015-03-31 10:26:23 +00003004void ath10k_mac_tx_lock(struct ath10k *ar, int reason)
3005{
3006 lockdep_assert_held(&ar->htt.tx_lock);
3007
3008 WARN_ON(reason >= ATH10K_TX_PAUSE_MAX);
3009 ar->tx_paused |= BIT(reason);
3010 ieee80211_stop_queues(ar->hw);
3011}
3012
3013static void ath10k_mac_tx_unlock_iter(void *data, u8 *mac,
3014 struct ieee80211_vif *vif)
3015{
3016 struct ath10k *ar = data;
3017 struct ath10k_vif *arvif = ath10k_vif_to_arvif(vif);
3018
3019 if (arvif->tx_paused)
3020 return;
3021
3022 ieee80211_wake_queue(ar->hw, arvif->vdev_id);
3023}
3024
3025void ath10k_mac_tx_unlock(struct ath10k *ar, int reason)
3026{
3027 lockdep_assert_held(&ar->htt.tx_lock);
3028
3029 WARN_ON(reason >= ATH10K_TX_PAUSE_MAX);
3030 ar->tx_paused &= ~BIT(reason);
3031
3032 if (ar->tx_paused)
3033 return;
3034
3035 ieee80211_iterate_active_interfaces_atomic(ar->hw,
3036 IEEE80211_IFACE_ITER_RESUME_ALL,
3037 ath10k_mac_tx_unlock_iter,
3038 ar);
Michal Kazior3a73d1a2015-08-06 14:46:54 +02003039
3040 ieee80211_wake_queue(ar->hw, ar->hw->offchannel_tx_hw_queue);
Michal Kazior96d828d2015-03-31 10:26:23 +00003041}
3042
3043void ath10k_mac_vif_tx_lock(struct ath10k_vif *arvif, int reason)
3044{
3045 struct ath10k *ar = arvif->ar;
3046
3047 lockdep_assert_held(&ar->htt.tx_lock);
3048
3049 WARN_ON(reason >= BITS_PER_LONG);
3050 arvif->tx_paused |= BIT(reason);
3051 ieee80211_stop_queue(ar->hw, arvif->vdev_id);
3052}
3053
3054void ath10k_mac_vif_tx_unlock(struct ath10k_vif *arvif, int reason)
3055{
3056 struct ath10k *ar = arvif->ar;
3057
3058 lockdep_assert_held(&ar->htt.tx_lock);
3059
3060 WARN_ON(reason >= BITS_PER_LONG);
3061 arvif->tx_paused &= ~BIT(reason);
3062
3063 if (ar->tx_paused)
3064 return;
3065
3066 if (arvif->tx_paused)
3067 return;
3068
3069 ieee80211_wake_queue(ar->hw, arvif->vdev_id);
3070}
3071
Michal Kaziorb4aa5392015-03-31 10:26:24 +00003072static void ath10k_mac_vif_handle_tx_pause(struct ath10k_vif *arvif,
3073 enum wmi_tlv_tx_pause_id pause_id,
3074 enum wmi_tlv_tx_pause_action action)
3075{
3076 struct ath10k *ar = arvif->ar;
3077
3078 lockdep_assert_held(&ar->htt.tx_lock);
3079
Michal Kazioracd0b272015-07-09 13:08:38 +02003080 switch (action) {
3081 case WMI_TLV_TX_PAUSE_ACTION_STOP:
3082 ath10k_mac_vif_tx_lock(arvif, pause_id);
Michal Kaziorb4aa5392015-03-31 10:26:24 +00003083 break;
Michal Kazioracd0b272015-07-09 13:08:38 +02003084 case WMI_TLV_TX_PAUSE_ACTION_WAKE:
3085 ath10k_mac_vif_tx_unlock(arvif, pause_id);
3086 break;
Michal Kaziorb4aa5392015-03-31 10:26:24 +00003087 default:
Michal Kazioracd0b272015-07-09 13:08:38 +02003088 ath10k_warn(ar, "received unknown tx pause action %d on vdev %i, ignoring\n",
3089 action, arvif->vdev_id);
Michal Kaziorb4aa5392015-03-31 10:26:24 +00003090 break;
3091 }
3092}
3093
3094struct ath10k_mac_tx_pause {
3095 u32 vdev_id;
3096 enum wmi_tlv_tx_pause_id pause_id;
3097 enum wmi_tlv_tx_pause_action action;
3098};
3099
3100static void ath10k_mac_handle_tx_pause_iter(void *data, u8 *mac,
3101 struct ieee80211_vif *vif)
3102{
3103 struct ath10k_vif *arvif = ath10k_vif_to_arvif(vif);
3104 struct ath10k_mac_tx_pause *arg = data;
3105
Michal Kazioracd0b272015-07-09 13:08:38 +02003106 if (arvif->vdev_id != arg->vdev_id)
3107 return;
3108
Michal Kaziorb4aa5392015-03-31 10:26:24 +00003109 ath10k_mac_vif_handle_tx_pause(arvif, arg->pause_id, arg->action);
3110}
3111
Michal Kazioracd0b272015-07-09 13:08:38 +02003112void ath10k_mac_handle_tx_pause_vdev(struct ath10k *ar, u32 vdev_id,
3113 enum wmi_tlv_tx_pause_id pause_id,
3114 enum wmi_tlv_tx_pause_action action)
Michal Kaziorb4aa5392015-03-31 10:26:24 +00003115{
3116 struct ath10k_mac_tx_pause arg = {
3117 .vdev_id = vdev_id,
3118 .pause_id = pause_id,
3119 .action = action,
3120 };
3121
3122 spin_lock_bh(&ar->htt.tx_lock);
3123 ieee80211_iterate_active_interfaces_atomic(ar->hw,
3124 IEEE80211_IFACE_ITER_RESUME_ALL,
3125 ath10k_mac_handle_tx_pause_iter,
3126 &arg);
3127 spin_unlock_bh(&ar->htt.tx_lock);
3128}
3129
Michal Kaziord740d8f2015-03-30 09:51:51 +03003130static enum ath10k_hw_txrx_mode
Michal Kazior6a2636d2015-11-18 06:59:16 +01003131ath10k_mac_tx_h_get_txmode(struct ath10k *ar,
3132 struct ieee80211_vif *vif,
3133 struct ieee80211_sta *sta,
3134 struct sk_buff *skb)
Michal Kaziord740d8f2015-03-30 09:51:51 +03003135{
3136 const struct ieee80211_hdr *hdr = (void *)skb->data;
3137 __le16 fc = hdr->frame_control;
3138
3139 if (!vif || vif->type == NL80211_IFTYPE_MONITOR)
3140 return ATH10K_HW_TXRX_RAW;
3141
3142 if (ieee80211_is_mgmt(fc))
3143 return ATH10K_HW_TXRX_MGMT;
3144
3145 /* Workaround:
3146 *
3147 * NullFunc frames are mostly used to ping if a client or AP are still
3148 * reachable and responsive. This implies tx status reports must be
3149 * accurate - otherwise either mac80211 or userspace (e.g. hostapd) can
3150 * come to a conclusion that the other end disappeared and tear down
3151 * BSS connection or it can never disconnect from BSS/client (which is
3152 * the case).
3153 *
3154 * Firmware with HTT older than 3.0 delivers incorrect tx status for
3155 * NullFunc frames to driver. However there's a HTT Mgmt Tx command
3156 * which seems to deliver correct tx reports for NullFunc frames. The
3157 * downside of using it is it ignores client powersave state so it can
3158 * end up disconnecting sleeping clients in AP mode. It should fix STA
3159 * mode though because AP don't sleep.
3160 */
3161 if (ar->htt.target_version_major < 3 &&
3162 (ieee80211_is_nullfunc(fc) || ieee80211_is_qos_nullfunc(fc)) &&
3163 !test_bit(ATH10K_FW_FEATURE_HAS_WMI_MGMT_TX, ar->fw_features))
3164 return ATH10K_HW_TXRX_MGMT;
3165
Marek Puzyniak75d85fd2015-03-30 09:51:53 +03003166 /* Workaround:
3167 *
3168 * Some wmi-tlv firmwares for qca6174 have broken Tx key selection for
3169 * NativeWifi txmode - it selects AP key instead of peer key. It seems
3170 * to work with Ethernet txmode so use it.
David Liuccec9032015-07-24 20:25:32 +03003171 *
3172 * FIXME: Check if raw mode works with TDLS.
Marek Puzyniak75d85fd2015-03-30 09:51:53 +03003173 */
3174 if (ieee80211_is_data_present(fc) && sta && sta->tdls)
3175 return ATH10K_HW_TXRX_ETHERNET;
3176
David Liuccec9032015-07-24 20:25:32 +03003177 if (test_bit(ATH10K_FLAG_RAW_MODE, &ar->dev_flags))
3178 return ATH10K_HW_TXRX_RAW;
3179
Michal Kaziord740d8f2015-03-30 09:51:51 +03003180 return ATH10K_HW_TXRX_NATIVE_WIFI;
3181}
3182
David Liuccec9032015-07-24 20:25:32 +03003183static bool ath10k_tx_h_use_hwcrypto(struct ieee80211_vif *vif,
Michal Kaziorfd12cb32015-11-18 06:59:15 +01003184 struct sk_buff *skb)
3185{
3186 const struct ieee80211_tx_info *info = IEEE80211_SKB_CB(skb);
3187 const struct ieee80211_hdr *hdr = (void *)skb->data;
David Liuccec9032015-07-24 20:25:32 +03003188 const u32 mask = IEEE80211_TX_INTFL_DONT_ENCRYPT |
3189 IEEE80211_TX_CTL_INJECTED;
Michal Kaziorfd12cb32015-11-18 06:59:15 +01003190
3191 if (!ieee80211_has_protected(hdr->frame_control))
3192 return false;
3193
David Liuccec9032015-07-24 20:25:32 +03003194 if ((info->flags & mask) == mask)
3195 return false;
Michal Kaziorfd12cb32015-11-18 06:59:15 +01003196
David Liuccec9032015-07-24 20:25:32 +03003197 if (vif)
3198 return !ath10k_vif_to_arvif(vif)->nohwcrypt;
Michal Kaziorfd12cb32015-11-18 06:59:15 +01003199
David Liuccec9032015-07-24 20:25:32 +03003200 return true;
3201}
3202
Michal Kazior4b604552014-07-21 21:03:09 +03003203/* HTT Tx uses Native Wifi tx mode which expects 802.11 frames without QoS
3204 * Control in the header.
Kalle Valo5e3dd152013-06-12 20:52:10 +03003205 */
Michal Kazior4b604552014-07-21 21:03:09 +03003206static void ath10k_tx_h_nwifi(struct ieee80211_hw *hw, struct sk_buff *skb)
Kalle Valo5e3dd152013-06-12 20:52:10 +03003207{
3208 struct ieee80211_hdr *hdr = (void *)skb->data;
Michal Kaziorc21c64d2014-07-21 21:03:10 +03003209 struct ath10k_skb_cb *cb = ATH10K_SKB_CB(skb);
Kalle Valo5e3dd152013-06-12 20:52:10 +03003210 u8 *qos_ctl;
3211
3212 if (!ieee80211_is_data_qos(hdr->frame_control))
3213 return;
3214
3215 qos_ctl = ieee80211_get_qos_ctl(hdr);
Michal Kaziorba0ccd72013-07-22 14:25:28 +02003216 memmove(skb->data + IEEE80211_QOS_CTL_LEN,
3217 skb->data, (void *)qos_ctl - (void *)skb->data);
3218 skb_pull(skb, IEEE80211_QOS_CTL_LEN);
Michal Kaziorc21c64d2014-07-21 21:03:10 +03003219
Michal Kazior8bad8dc2015-03-11 14:25:26 +01003220 /* Some firmware revisions don't handle sending QoS NullFunc well.
3221 * These frames are mainly used for CQM purposes so it doesn't really
3222 * matter whether QoS NullFunc or NullFunc are sent.
Michal Kaziorc21c64d2014-07-21 21:03:10 +03003223 */
Michal Kaziorbf0a26d2015-01-24 12:14:51 +02003224 hdr = (void *)skb->data;
Michal Kazior8bad8dc2015-03-11 14:25:26 +01003225 if (ieee80211_is_qos_nullfunc(hdr->frame_control))
Michal Kazior609db222015-11-18 06:59:22 +01003226 cb->flags &= ~ATH10K_SKB_F_QOS;
Michal Kazior8bad8dc2015-03-11 14:25:26 +01003227
3228 hdr->frame_control &= ~__cpu_to_le16(IEEE80211_STYPE_QOS_DATA);
Kalle Valo5e3dd152013-06-12 20:52:10 +03003229}
3230
Michal Kaziord740d8f2015-03-30 09:51:51 +03003231static void ath10k_tx_h_8023(struct sk_buff *skb)
3232{
3233 struct ieee80211_hdr *hdr;
3234 struct rfc1042_hdr *rfc1042;
3235 struct ethhdr *eth;
3236 size_t hdrlen;
3237 u8 da[ETH_ALEN];
3238 u8 sa[ETH_ALEN];
3239 __be16 type;
3240
3241 hdr = (void *)skb->data;
3242 hdrlen = ieee80211_hdrlen(hdr->frame_control);
3243 rfc1042 = (void *)skb->data + hdrlen;
3244
3245 ether_addr_copy(da, ieee80211_get_DA(hdr));
3246 ether_addr_copy(sa, ieee80211_get_SA(hdr));
3247 type = rfc1042->snap_type;
3248
3249 skb_pull(skb, hdrlen + sizeof(*rfc1042));
3250 skb_push(skb, sizeof(*eth));
3251
3252 eth = (void *)skb->data;
3253 ether_addr_copy(eth->h_dest, da);
3254 ether_addr_copy(eth->h_source, sa);
3255 eth->h_proto = type;
Kalle Valo5e3dd152013-06-12 20:52:10 +03003256}
3257
Michal Kazior4b604552014-07-21 21:03:09 +03003258static void ath10k_tx_h_add_p2p_noa_ie(struct ath10k *ar,
3259 struct ieee80211_vif *vif,
3260 struct sk_buff *skb)
Kalle Valo5e3dd152013-06-12 20:52:10 +03003261{
3262 struct ieee80211_hdr *hdr = (struct ieee80211_hdr *)skb->data;
Kalle Valo5e3dd152013-06-12 20:52:10 +03003263 struct ath10k_vif *arvif = ath10k_vif_to_arvif(vif);
3264
3265 /* This is case only for P2P_GO */
Peter Oh08c27be2016-01-28 13:54:09 -08003266 if (vif->type != NL80211_IFTYPE_AP || !vif->p2p)
Kalle Valo5e3dd152013-06-12 20:52:10 +03003267 return;
3268
3269 if (unlikely(ieee80211_is_probe_resp(hdr->frame_control))) {
3270 spin_lock_bh(&ar->data_lock);
3271 if (arvif->u.ap.noa_data)
3272 if (!pskb_expand_head(skb, 0, arvif->u.ap.noa_len,
3273 GFP_ATOMIC))
3274 memcpy(skb_put(skb, arvif->u.ap.noa_len),
3275 arvif->u.ap.noa_data,
3276 arvif->u.ap.noa_len);
3277 spin_unlock_bh(&ar->data_lock);
3278 }
3279}
3280
Michal Kaziorf2f6eca2016-03-01 11:32:46 +01003281static void ath10k_mac_tx_h_fill_cb(struct ath10k *ar,
3282 struct ieee80211_vif *vif,
3283 struct sk_buff *skb)
3284{
3285 struct ieee80211_hdr *hdr = (void *)skb->data;
3286 struct ath10k_skb_cb *cb = ATH10K_SKB_CB(skb);
3287
3288 cb->flags = 0;
3289 if (!ath10k_tx_h_use_hwcrypto(vif, skb))
3290 cb->flags |= ATH10K_SKB_F_NO_HWCRYPT;
3291
3292 if (ieee80211_is_mgmt(hdr->frame_control))
3293 cb->flags |= ATH10K_SKB_F_MGMT;
3294
3295 if (ieee80211_is_data_qos(hdr->frame_control))
3296 cb->flags |= ATH10K_SKB_F_QOS;
3297
3298 cb->vif = vif;
3299}
3300
Vasanthakumar Thiagarajand39de992015-11-05 11:34:00 +05303301bool ath10k_mac_tx_frm_has_freq(struct ath10k *ar)
Michal Kazior8d6d3622014-11-24 14:58:31 +01003302{
3303 /* FIXME: Not really sure since when the behaviour changed. At some
3304 * point new firmware stopped requiring creation of peer entries for
3305 * offchannel tx (and actually creating them causes issues with wmi-htc
3306 * tx credit replenishment and reliability). Assuming it's at least 3.4
3307 * because that's when the `freq` was introduced to TX_FRM HTT command.
3308 */
Vasanthakumar Thiagarajan8921f5f2015-11-05 11:33:59 +05303309 return (ar->htt.target_version_major >= 3 &&
Vasanthakumar Thiagarajand39de992015-11-05 11:34:00 +05303310 ar->htt.target_version_minor >= 4 &&
3311 ar->htt.op_version == ATH10K_FW_HTT_OP_VERSION_TLV);
Michal Kazior8d6d3622014-11-24 14:58:31 +01003312}
3313
Michal Kaziord740d8f2015-03-30 09:51:51 +03003314static int ath10k_mac_tx_wmi_mgmt(struct ath10k *ar, struct sk_buff *skb)
Kalle Valo5e3dd152013-06-12 20:52:10 +03003315{
Michal Kaziord740d8f2015-03-30 09:51:51 +03003316 struct sk_buff_head *q = &ar->wmi_mgmt_tx_queue;
Bartosz Markowski5e00d312013-09-26 17:47:12 +02003317 int ret = 0;
Kalle Valo5e3dd152013-06-12 20:52:10 +03003318
Michal Kaziord740d8f2015-03-30 09:51:51 +03003319 spin_lock_bh(&ar->data_lock);
3320
3321 if (skb_queue_len(q) == ATH10K_MAX_NUM_MGMT_PENDING) {
3322 ath10k_warn(ar, "wmi mgmt tx queue is full\n");
3323 ret = -ENOSPC;
3324 goto unlock;
Michal Kazior961d4c32013-08-09 10:13:34 +02003325 }
3326
Michal Kaziord740d8f2015-03-30 09:51:51 +03003327 __skb_queue_tail(q, skb);
3328 ieee80211_queue_work(ar->hw, &ar->wmi_mgmt_tx_work);
3329
3330unlock:
3331 spin_unlock_bh(&ar->data_lock);
3332
3333 return ret;
3334}
3335
Michal Kaziora30c7d02016-03-06 16:14:23 +02003336static enum ath10k_mac_tx_path
3337ath10k_mac_tx_h_get_txpath(struct ath10k *ar,
3338 struct sk_buff *skb,
3339 enum ath10k_hw_txrx_mode txmode)
3340{
3341 switch (txmode) {
3342 case ATH10K_HW_TXRX_RAW:
3343 case ATH10K_HW_TXRX_NATIVE_WIFI:
3344 case ATH10K_HW_TXRX_ETHERNET:
3345 return ATH10K_MAC_TX_HTT;
3346 case ATH10K_HW_TXRX_MGMT:
3347 if (test_bit(ATH10K_FW_FEATURE_HAS_WMI_MGMT_TX,
3348 ar->fw_features))
3349 return ATH10K_MAC_TX_WMI_MGMT;
3350 else if (ar->htt.target_version_major >= 3)
3351 return ATH10K_MAC_TX_HTT;
3352 else
3353 return ATH10K_MAC_TX_HTT_MGMT;
3354 }
3355
3356 return ATH10K_MAC_TX_UNKNOWN;
3357}
3358
Michal Kaziorf2f6eca2016-03-01 11:32:46 +01003359static int ath10k_mac_tx_submit(struct ath10k *ar,
3360 enum ath10k_hw_txrx_mode txmode,
Michal Kazior6421969f2016-03-06 16:14:25 +02003361 enum ath10k_mac_tx_path txpath,
Michal Kaziorf2f6eca2016-03-01 11:32:46 +01003362 struct sk_buff *skb)
Michal Kaziord740d8f2015-03-30 09:51:51 +03003363{
Michal Kaziord740d8f2015-03-30 09:51:51 +03003364 struct ath10k_htt *htt = &ar->htt;
Michal Kazior6421969f2016-03-06 16:14:25 +02003365 int ret = -EINVAL;
Michal Kaziora30c7d02016-03-06 16:14:23 +02003366
3367 switch (txpath) {
3368 case ATH10K_MAC_TX_HTT:
Michal Kazior8a933962015-11-18 06:59:17 +01003369 ret = ath10k_htt_tx(htt, txmode, skb);
Michal Kaziord740d8f2015-03-30 09:51:51 +03003370 break;
Michal Kaziora30c7d02016-03-06 16:14:23 +02003371 case ATH10K_MAC_TX_HTT_MGMT:
3372 ret = ath10k_htt_mgmt_tx(htt, skb);
3373 break;
3374 case ATH10K_MAC_TX_WMI_MGMT:
3375 ret = ath10k_mac_tx_wmi_mgmt(ar, skb);
3376 break;
3377 case ATH10K_MAC_TX_UNKNOWN:
3378 WARN_ON_ONCE(1);
3379 ret = -EINVAL;
Michal Kaziord740d8f2015-03-30 09:51:51 +03003380 break;
Bartosz Markowski5e00d312013-09-26 17:47:12 +02003381 }
Kalle Valo5e3dd152013-06-12 20:52:10 +03003382
3383 if (ret) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02003384 ath10k_warn(ar, "failed to transmit packet, dropping: %d\n",
3385 ret);
Kalle Valo5e3dd152013-06-12 20:52:10 +03003386 ieee80211_free_txskb(ar->hw, skb);
3387 }
Michal Kaziorf2f6eca2016-03-01 11:32:46 +01003388
3389 return ret;
3390}
3391
3392/* This function consumes the sk_buff regardless of return value as far as
3393 * caller is concerned so no freeing is necessary afterwards.
3394 */
3395static int ath10k_mac_tx(struct ath10k *ar,
3396 struct ieee80211_vif *vif,
3397 struct ieee80211_sta *sta,
3398 enum ath10k_hw_txrx_mode txmode,
Michal Kazior6421969f2016-03-06 16:14:25 +02003399 enum ath10k_mac_tx_path txpath,
Michal Kaziorf2f6eca2016-03-01 11:32:46 +01003400 struct sk_buff *skb)
3401{
3402 struct ieee80211_hw *hw = ar->hw;
3403 struct ieee80211_tx_info *info = IEEE80211_SKB_CB(skb);
3404 int ret;
3405
3406 /* We should disable CCK RATE due to P2P */
3407 if (info->flags & IEEE80211_TX_CTL_NO_CCK_RATE)
3408 ath10k_dbg(ar, ATH10K_DBG_MAC, "IEEE80211_TX_CTL_NO_CCK_RATE\n");
3409
3410 switch (txmode) {
3411 case ATH10K_HW_TXRX_MGMT:
3412 case ATH10K_HW_TXRX_NATIVE_WIFI:
3413 ath10k_tx_h_nwifi(hw, skb);
3414 ath10k_tx_h_add_p2p_noa_ie(ar, vif, skb);
3415 ath10k_tx_h_seq_no(vif, skb);
3416 break;
3417 case ATH10K_HW_TXRX_ETHERNET:
3418 ath10k_tx_h_8023(skb);
3419 break;
3420 case ATH10K_HW_TXRX_RAW:
3421 if (!test_bit(ATH10K_FLAG_RAW_MODE, &ar->dev_flags)) {
3422 WARN_ON_ONCE(1);
3423 ieee80211_free_txskb(hw, skb);
3424 return -ENOTSUPP;
3425 }
3426 }
3427
3428 if (info->flags & IEEE80211_TX_CTL_TX_OFFCHAN) {
3429 if (!ath10k_mac_tx_frm_has_freq(ar)) {
3430 ath10k_dbg(ar, ATH10K_DBG_MAC, "queued offchannel skb %p\n",
3431 skb);
3432
3433 skb_queue_tail(&ar->offchan_tx_queue, skb);
3434 ieee80211_queue_work(hw, &ar->offchan_tx_work);
3435 return 0;
3436 }
3437 }
3438
Michal Kazior6421969f2016-03-06 16:14:25 +02003439 ret = ath10k_mac_tx_submit(ar, txmode, txpath, skb);
Michal Kaziorf2f6eca2016-03-01 11:32:46 +01003440 if (ret) {
3441 ath10k_warn(ar, "failed to submit frame: %d\n", ret);
3442 return ret;
3443 }
3444
3445 return 0;
Kalle Valo5e3dd152013-06-12 20:52:10 +03003446}
3447
3448void ath10k_offchan_tx_purge(struct ath10k *ar)
3449{
3450 struct sk_buff *skb;
3451
3452 for (;;) {
3453 skb = skb_dequeue(&ar->offchan_tx_queue);
3454 if (!skb)
3455 break;
3456
3457 ieee80211_free_txskb(ar->hw, skb);
3458 }
3459}
3460
3461void ath10k_offchan_tx_work(struct work_struct *work)
3462{
3463 struct ath10k *ar = container_of(work, struct ath10k, offchan_tx_work);
3464 struct ath10k_peer *peer;
Michal Kazior8a933962015-11-18 06:59:17 +01003465 struct ath10k_vif *arvif;
Michal Kaziorf2f6eca2016-03-01 11:32:46 +01003466 enum ath10k_hw_txrx_mode txmode;
Michal Kazior6421969f2016-03-06 16:14:25 +02003467 enum ath10k_mac_tx_path txpath;
Kalle Valo5e3dd152013-06-12 20:52:10 +03003468 struct ieee80211_hdr *hdr;
Michal Kazior8a933962015-11-18 06:59:17 +01003469 struct ieee80211_vif *vif;
3470 struct ieee80211_sta *sta;
Kalle Valo5e3dd152013-06-12 20:52:10 +03003471 struct sk_buff *skb;
3472 const u8 *peer_addr;
3473 int vdev_id;
3474 int ret;
Nicholas Mc Guire8e9904f52015-03-30 15:39:19 +03003475 unsigned long time_left;
Michal Kazioradaeed72015-08-05 12:15:23 +02003476 bool tmp_peer_created = false;
Kalle Valo5e3dd152013-06-12 20:52:10 +03003477
3478 /* FW requirement: We must create a peer before FW will send out
3479 * an offchannel frame. Otherwise the frame will be stuck and
3480 * never transmitted. We delete the peer upon tx completion.
3481 * It is unlikely that a peer for offchannel tx will already be
3482 * present. However it may be in some rare cases so account for that.
3483 * Otherwise we might remove a legitimate peer and break stuff. */
3484
3485 for (;;) {
3486 skb = skb_dequeue(&ar->offchan_tx_queue);
3487 if (!skb)
3488 break;
3489
3490 mutex_lock(&ar->conf_mutex);
3491
Michal Kazior7aa7a722014-08-25 12:09:38 +02003492 ath10k_dbg(ar, ATH10K_DBG_MAC, "mac offchannel skb %p\n",
Kalle Valo5e3dd152013-06-12 20:52:10 +03003493 skb);
3494
3495 hdr = (struct ieee80211_hdr *)skb->data;
3496 peer_addr = ieee80211_get_DA(hdr);
Kalle Valo5e3dd152013-06-12 20:52:10 +03003497
3498 spin_lock_bh(&ar->data_lock);
Michal Kazior609db222015-11-18 06:59:22 +01003499 vdev_id = ar->scan.vdev_id;
Kalle Valo5e3dd152013-06-12 20:52:10 +03003500 peer = ath10k_peer_find(ar, vdev_id, peer_addr);
3501 spin_unlock_bh(&ar->data_lock);
3502
3503 if (peer)
Kalle Valo60c3daa2013-09-08 17:56:07 +03003504 /* FIXME: should this use ath10k_warn()? */
Michal Kazior7aa7a722014-08-25 12:09:38 +02003505 ath10k_dbg(ar, ATH10K_DBG_MAC, "peer %pM on vdev %d already present\n",
Kalle Valo5e3dd152013-06-12 20:52:10 +03003506 peer_addr, vdev_id);
3507
3508 if (!peer) {
Marek Puzyniak7390ed32015-03-30 09:51:52 +03003509 ret = ath10k_peer_create(ar, vdev_id, peer_addr,
3510 WMI_PEER_TYPE_DEFAULT);
Kalle Valo5e3dd152013-06-12 20:52:10 +03003511 if (ret)
Michal Kazior7aa7a722014-08-25 12:09:38 +02003512 ath10k_warn(ar, "failed to create peer %pM on vdev %d: %d\n",
Kalle Valo5e3dd152013-06-12 20:52:10 +03003513 peer_addr, vdev_id, ret);
Michal Kazioradaeed72015-08-05 12:15:23 +02003514 tmp_peer_created = (ret == 0);
Kalle Valo5e3dd152013-06-12 20:52:10 +03003515 }
3516
3517 spin_lock_bh(&ar->data_lock);
Wolfram Sang16735d02013-11-14 14:32:02 -08003518 reinit_completion(&ar->offchan_tx_completed);
Kalle Valo5e3dd152013-06-12 20:52:10 +03003519 ar->offchan_tx_skb = skb;
3520 spin_unlock_bh(&ar->data_lock);
3521
Michal Kazior8a933962015-11-18 06:59:17 +01003522 /* It's safe to access vif and sta - conf_mutex guarantees that
3523 * sta_state() and remove_interface() are locked exclusively
3524 * out wrt to this offchannel worker.
3525 */
3526 arvif = ath10k_get_arvif(ar, vdev_id);
3527 if (arvif) {
3528 vif = arvif->vif;
3529 sta = ieee80211_find_sta(vif, peer_addr);
3530 } else {
3531 vif = NULL;
3532 sta = NULL;
3533 }
3534
3535 txmode = ath10k_mac_tx_h_get_txmode(ar, vif, sta, skb);
Michal Kazior6421969f2016-03-06 16:14:25 +02003536 txpath = ath10k_mac_tx_h_get_txpath(ar, skb, txmode);
Michal Kazior8a933962015-11-18 06:59:17 +01003537
Michal Kazior6421969f2016-03-06 16:14:25 +02003538 ret = ath10k_mac_tx(ar, vif, sta, txmode, txpath, skb);
Michal Kaziorf2f6eca2016-03-01 11:32:46 +01003539 if (ret) {
3540 ath10k_warn(ar, "failed to transmit offchannel frame: %d\n",
3541 ret);
3542 /* not serious */
3543 }
Kalle Valo5e3dd152013-06-12 20:52:10 +03003544
Nicholas Mc Guire8e9904f52015-03-30 15:39:19 +03003545 time_left =
3546 wait_for_completion_timeout(&ar->offchan_tx_completed, 3 * HZ);
3547 if (time_left == 0)
Michal Kazior7aa7a722014-08-25 12:09:38 +02003548 ath10k_warn(ar, "timed out waiting for offchannel skb %p\n",
Kalle Valo5e3dd152013-06-12 20:52:10 +03003549 skb);
3550
Michal Kazioradaeed72015-08-05 12:15:23 +02003551 if (!peer && tmp_peer_created) {
Kalle Valo5e3dd152013-06-12 20:52:10 +03003552 ret = ath10k_peer_delete(ar, vdev_id, peer_addr);
3553 if (ret)
Michal Kazior7aa7a722014-08-25 12:09:38 +02003554 ath10k_warn(ar, "failed to delete peer %pM on vdev %d: %d\n",
Kalle Valo5e3dd152013-06-12 20:52:10 +03003555 peer_addr, vdev_id, ret);
3556 }
3557
3558 mutex_unlock(&ar->conf_mutex);
3559 }
3560}
3561
Bartosz Markowski5e00d312013-09-26 17:47:12 +02003562void ath10k_mgmt_over_wmi_tx_purge(struct ath10k *ar)
3563{
3564 struct sk_buff *skb;
3565
3566 for (;;) {
3567 skb = skb_dequeue(&ar->wmi_mgmt_tx_queue);
3568 if (!skb)
3569 break;
3570
3571 ieee80211_free_txskb(ar->hw, skb);
3572 }
3573}
3574
3575void ath10k_mgmt_over_wmi_tx_work(struct work_struct *work)
3576{
3577 struct ath10k *ar = container_of(work, struct ath10k, wmi_mgmt_tx_work);
3578 struct sk_buff *skb;
3579 int ret;
3580
3581 for (;;) {
3582 skb = skb_dequeue(&ar->wmi_mgmt_tx_queue);
3583 if (!skb)
3584 break;
3585
3586 ret = ath10k_wmi_mgmt_tx(ar, skb);
Michal Kazior5fb5e412013-10-28 07:18:13 +01003587 if (ret) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02003588 ath10k_warn(ar, "failed to transmit management frame via WMI: %d\n",
Kalle Valobe6546f2014-03-25 14:18:51 +02003589 ret);
Michal Kazior5fb5e412013-10-28 07:18:13 +01003590 ieee80211_free_txskb(ar->hw, skb);
3591 }
Bartosz Markowski5e00d312013-09-26 17:47:12 +02003592 }
3593}
3594
Kalle Valo5e3dd152013-06-12 20:52:10 +03003595/************/
3596/* Scanning */
3597/************/
3598
Michal Kazior5c81c7f2014-08-05 14:54:44 +02003599void __ath10k_scan_finish(struct ath10k *ar)
Kalle Valo5e3dd152013-06-12 20:52:10 +03003600{
Michal Kazior5c81c7f2014-08-05 14:54:44 +02003601 lockdep_assert_held(&ar->data_lock);
Kalle Valo5e3dd152013-06-12 20:52:10 +03003602
Michal Kazior5c81c7f2014-08-05 14:54:44 +02003603 switch (ar->scan.state) {
3604 case ATH10K_SCAN_IDLE:
3605 break;
3606 case ATH10K_SCAN_RUNNING:
Michal Kazior7305d3e2014-11-24 14:58:33 +01003607 case ATH10K_SCAN_ABORTING:
3608 if (!ar->scan.is_roc)
Michal Kazior5c81c7f2014-08-05 14:54:44 +02003609 ieee80211_scan_completed(ar->hw,
3610 (ar->scan.state ==
3611 ATH10K_SCAN_ABORTING));
Michal Kaziord710e752015-07-09 13:08:36 +02003612 else if (ar->scan.roc_notify)
3613 ieee80211_remain_on_channel_expired(ar->hw);
Michal Kazior5c81c7f2014-08-05 14:54:44 +02003614 /* fall through */
3615 case ATH10K_SCAN_STARTING:
3616 ar->scan.state = ATH10K_SCAN_IDLE;
3617 ar->scan_channel = NULL;
Michal Kaziorbd877442015-11-18 06:59:19 +01003618 ar->scan.roc_freq = 0;
Michal Kazior5c81c7f2014-08-05 14:54:44 +02003619 ath10k_offchan_tx_purge(ar);
3620 cancel_delayed_work(&ar->scan.timeout);
3621 complete_all(&ar->scan.completed);
3622 break;
Kalle Valo5e3dd152013-06-12 20:52:10 +03003623 }
Michal Kazior5c81c7f2014-08-05 14:54:44 +02003624}
Kalle Valo5e3dd152013-06-12 20:52:10 +03003625
Michal Kazior5c81c7f2014-08-05 14:54:44 +02003626void ath10k_scan_finish(struct ath10k *ar)
3627{
3628 spin_lock_bh(&ar->data_lock);
3629 __ath10k_scan_finish(ar);
Kalle Valo5e3dd152013-06-12 20:52:10 +03003630 spin_unlock_bh(&ar->data_lock);
3631}
3632
Michal Kazior5c81c7f2014-08-05 14:54:44 +02003633static int ath10k_scan_stop(struct ath10k *ar)
Kalle Valo5e3dd152013-06-12 20:52:10 +03003634{
3635 struct wmi_stop_scan_arg arg = {
3636 .req_id = 1, /* FIXME */
3637 .req_type = WMI_SCAN_STOP_ONE,
3638 .u.scan_id = ATH10K_SCAN_ID,
3639 };
3640 int ret;
3641
3642 lockdep_assert_held(&ar->conf_mutex);
3643
Kalle Valo5e3dd152013-06-12 20:52:10 +03003644 ret = ath10k_wmi_stop_scan(ar, &arg);
3645 if (ret) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02003646 ath10k_warn(ar, "failed to stop wmi scan: %d\n", ret);
Michal Kazior5c81c7f2014-08-05 14:54:44 +02003647 goto out;
Kalle Valo5e3dd152013-06-12 20:52:10 +03003648 }
3649
Kalle Valo5e3dd152013-06-12 20:52:10 +03003650 ret = wait_for_completion_timeout(&ar->scan.completed, 3*HZ);
Michal Kazior5c81c7f2014-08-05 14:54:44 +02003651 if (ret == 0) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02003652 ath10k_warn(ar, "failed to receive scan abortion completion: timed out\n");
Kalle Valo5e3dd152013-06-12 20:52:10 +03003653 ret = -ETIMEDOUT;
Michal Kazior5c81c7f2014-08-05 14:54:44 +02003654 } else if (ret > 0) {
3655 ret = 0;
Kalle Valo5e3dd152013-06-12 20:52:10 +03003656 }
Michal Kazior5c81c7f2014-08-05 14:54:44 +02003657
3658out:
3659 /* Scan state should be updated upon scan completion but in case
3660 * firmware fails to deliver the event (for whatever reason) it is
3661 * desired to clean up scan state anyway. Firmware may have just
3662 * dropped the scan completion event delivery due to transport pipe
3663 * being overflown with data and/or it can recover on its own before
3664 * next scan request is submitted.
3665 */
3666 spin_lock_bh(&ar->data_lock);
3667 if (ar->scan.state != ATH10K_SCAN_IDLE)
3668 __ath10k_scan_finish(ar);
Kalle Valo5e3dd152013-06-12 20:52:10 +03003669 spin_unlock_bh(&ar->data_lock);
3670
3671 return ret;
3672}
3673
Michal Kazior5c81c7f2014-08-05 14:54:44 +02003674static void ath10k_scan_abort(struct ath10k *ar)
3675{
3676 int ret;
3677
3678 lockdep_assert_held(&ar->conf_mutex);
3679
3680 spin_lock_bh(&ar->data_lock);
3681
3682 switch (ar->scan.state) {
3683 case ATH10K_SCAN_IDLE:
3684 /* This can happen if timeout worker kicked in and called
3685 * abortion while scan completion was being processed.
3686 */
3687 break;
3688 case ATH10K_SCAN_STARTING:
3689 case ATH10K_SCAN_ABORTING:
Michal Kazior7aa7a722014-08-25 12:09:38 +02003690 ath10k_warn(ar, "refusing scan abortion due to invalid scan state: %s (%d)\n",
Michal Kazior5c81c7f2014-08-05 14:54:44 +02003691 ath10k_scan_state_str(ar->scan.state),
3692 ar->scan.state);
3693 break;
3694 case ATH10K_SCAN_RUNNING:
3695 ar->scan.state = ATH10K_SCAN_ABORTING;
3696 spin_unlock_bh(&ar->data_lock);
3697
3698 ret = ath10k_scan_stop(ar);
3699 if (ret)
Michal Kazior7aa7a722014-08-25 12:09:38 +02003700 ath10k_warn(ar, "failed to abort scan: %d\n", ret);
Michal Kazior5c81c7f2014-08-05 14:54:44 +02003701
3702 spin_lock_bh(&ar->data_lock);
3703 break;
3704 }
3705
3706 spin_unlock_bh(&ar->data_lock);
3707}
3708
3709void ath10k_scan_timeout_work(struct work_struct *work)
3710{
3711 struct ath10k *ar = container_of(work, struct ath10k,
3712 scan.timeout.work);
3713
3714 mutex_lock(&ar->conf_mutex);
3715 ath10k_scan_abort(ar);
3716 mutex_unlock(&ar->conf_mutex);
3717}
3718
Kalle Valo5e3dd152013-06-12 20:52:10 +03003719static int ath10k_start_scan(struct ath10k *ar,
3720 const struct wmi_start_scan_arg *arg)
3721{
3722 int ret;
3723
3724 lockdep_assert_held(&ar->conf_mutex);
3725
3726 ret = ath10k_wmi_start_scan(ar, arg);
3727 if (ret)
3728 return ret;
3729
Kalle Valo5e3dd152013-06-12 20:52:10 +03003730 ret = wait_for_completion_timeout(&ar->scan.started, 1*HZ);
3731 if (ret == 0) {
Michal Kazior5c81c7f2014-08-05 14:54:44 +02003732 ret = ath10k_scan_stop(ar);
3733 if (ret)
Michal Kazior7aa7a722014-08-25 12:09:38 +02003734 ath10k_warn(ar, "failed to stop scan: %d\n", ret);
Michal Kazior5c81c7f2014-08-05 14:54:44 +02003735
3736 return -ETIMEDOUT;
Kalle Valo5e3dd152013-06-12 20:52:10 +03003737 }
3738
Ben Greear2f9eec02015-02-15 16:50:38 +02003739 /* If we failed to start the scan, return error code at
3740 * this point. This is probably due to some issue in the
3741 * firmware, but no need to wedge the driver due to that...
3742 */
3743 spin_lock_bh(&ar->data_lock);
3744 if (ar->scan.state == ATH10K_SCAN_IDLE) {
3745 spin_unlock_bh(&ar->data_lock);
3746 return -EINVAL;
3747 }
3748 spin_unlock_bh(&ar->data_lock);
3749
Kalle Valo5e3dd152013-06-12 20:52:10 +03003750 return 0;
3751}
3752
3753/**********************/
3754/* mac80211 callbacks */
3755/**********************/
3756
Michal Kaziorf2f6eca2016-03-01 11:32:46 +01003757static void ath10k_mac_op_tx(struct ieee80211_hw *hw,
3758 struct ieee80211_tx_control *control,
3759 struct sk_buff *skb)
Kalle Valo5e3dd152013-06-12 20:52:10 +03003760{
Kalle Valo5e3dd152013-06-12 20:52:10 +03003761 struct ath10k *ar = hw->priv;
Michal Kazior6421969f2016-03-06 16:14:25 +02003762 struct ath10k_htt *htt = &ar->htt;
Michal Kazior4b604552014-07-21 21:03:09 +03003763 struct ieee80211_tx_info *info = IEEE80211_SKB_CB(skb);
3764 struct ieee80211_vif *vif = info->control.vif;
Marek Puzyniak75d85fd2015-03-30 09:51:53 +03003765 struct ieee80211_sta *sta = control->sta;
Michal Kazior6421969f2016-03-06 16:14:25 +02003766 struct ieee80211_hdr *hdr = (void *)skb->data;
Michal Kazior8a933962015-11-18 06:59:17 +01003767 enum ath10k_hw_txrx_mode txmode;
Michal Kazior6421969f2016-03-06 16:14:25 +02003768 enum ath10k_mac_tx_path txpath;
3769 bool is_htt;
3770 bool is_mgmt;
3771 bool is_presp;
Michal Kaziorf2f6eca2016-03-01 11:32:46 +01003772 int ret;
Kalle Valo5e3dd152013-06-12 20:52:10 +03003773
Michal Kaziorf2f6eca2016-03-01 11:32:46 +01003774 ath10k_mac_tx_h_fill_cb(ar, vif, skb);
Kalle Valo5e3dd152013-06-12 20:52:10 +03003775
Michal Kazior8a933962015-11-18 06:59:17 +01003776 txmode = ath10k_mac_tx_h_get_txmode(ar, vif, sta, skb);
Michal Kazior6421969f2016-03-06 16:14:25 +02003777 txpath = ath10k_mac_tx_h_get_txpath(ar, skb, txmode);
3778 is_htt = (txpath == ATH10K_MAC_TX_HTT ||
3779 txpath == ATH10K_MAC_TX_HTT_MGMT);
Kalle Valo5e3dd152013-06-12 20:52:10 +03003780
Michal Kazior6421969f2016-03-06 16:14:25 +02003781 if (is_htt) {
3782 spin_lock_bh(&ar->htt.tx_lock);
3783
3784 is_mgmt = ieee80211_is_mgmt(hdr->frame_control);
3785 is_presp = ieee80211_is_probe_resp(hdr->frame_control);
3786
3787 ret = ath10k_htt_tx_inc_pending(htt, is_mgmt, is_presp);
3788 if (ret) {
3789 ath10k_warn(ar, "failed to increase tx pending count: %d, dropping\n",
3790 ret);
3791 spin_unlock_bh(&ar->htt.tx_lock);
3792 ieee80211_free_txskb(ar->hw, skb);
3793 return;
3794 }
3795
3796 spin_unlock_bh(&ar->htt.tx_lock);
3797 }
3798
3799 ret = ath10k_mac_tx(ar, vif, sta, txmode, txpath, skb);
3800 if (ret) {
Michal Kaziorf2f6eca2016-03-01 11:32:46 +01003801 ath10k_warn(ar, "failed to transmit frame: %d\n", ret);
Michal Kazior6421969f2016-03-06 16:14:25 +02003802 if (is_htt) {
3803 spin_lock_bh(&ar->htt.tx_lock);
3804 ath10k_htt_tx_dec_pending(htt, is_mgmt);
3805 spin_unlock_bh(&ar->htt.tx_lock);
3806 }
3807 return;
3808 }
Kalle Valo5e3dd152013-06-12 20:52:10 +03003809}
3810
Michal Kaziorbca7baf2014-05-26 12:46:03 +03003811/* Must not be called with conf_mutex held as workers can use that also. */
Michal Kazior7962b0d2014-10-28 10:34:38 +01003812void ath10k_drain_tx(struct ath10k *ar)
Michal Kaziorbca7baf2014-05-26 12:46:03 +03003813{
3814 /* make sure rcu-protected mac80211 tx path itself is drained */
3815 synchronize_net();
3816
3817 ath10k_offchan_tx_purge(ar);
3818 ath10k_mgmt_over_wmi_tx_purge(ar);
3819
3820 cancel_work_sync(&ar->offchan_tx_work);
3821 cancel_work_sync(&ar->wmi_mgmt_tx_work);
3822}
3823
Michal Kazioraffd3212013-07-16 09:54:35 +02003824void ath10k_halt(struct ath10k *ar)
Michal Kazior818bdd12013-07-16 09:38:57 +02003825{
Michal Kaziord9bc4b92014-04-23 19:30:06 +03003826 struct ath10k_vif *arvif;
3827
Michal Kazior818bdd12013-07-16 09:38:57 +02003828 lockdep_assert_held(&ar->conf_mutex);
3829
Michal Kazior19337472014-08-28 12:58:16 +02003830 clear_bit(ATH10K_CAC_RUNNING, &ar->dev_flags);
3831 ar->filter_flags = 0;
3832 ar->monitor = false;
Michal Kazior500ff9f2015-03-31 10:26:21 +00003833 ar->monitor_arvif = NULL;
Michal Kazior19337472014-08-28 12:58:16 +02003834
3835 if (ar->monitor_started)
Michal Kazior1bbc0972014-04-08 09:45:47 +03003836 ath10k_monitor_stop(ar);
Michal Kazior19337472014-08-28 12:58:16 +02003837
3838 ar->monitor_started = false;
Michal Kazior96d828d2015-03-31 10:26:23 +00003839 ar->tx_paused = 0;
Michal Kazior1bbc0972014-04-08 09:45:47 +03003840
Michal Kazior5c81c7f2014-08-05 14:54:44 +02003841 ath10k_scan_finish(ar);
Michal Kazior818bdd12013-07-16 09:38:57 +02003842 ath10k_peer_cleanup_all(ar);
3843 ath10k_core_stop(ar);
3844 ath10k_hif_power_down(ar);
3845
3846 spin_lock_bh(&ar->data_lock);
Michal Kazior64badcb2014-09-18 11:18:02 +03003847 list_for_each_entry(arvif, &ar->arvifs, list)
3848 ath10k_mac_vif_beacon_cleanup(arvif);
Michal Kazior818bdd12013-07-16 09:38:57 +02003849 spin_unlock_bh(&ar->data_lock);
3850}
3851
Ben Greear46acf7bb2014-05-16 17:15:38 +03003852static int ath10k_get_antenna(struct ieee80211_hw *hw, u32 *tx_ant, u32 *rx_ant)
3853{
3854 struct ath10k *ar = hw->priv;
3855
3856 mutex_lock(&ar->conf_mutex);
3857
Rajkumar Manoharan166de3f2015-10-27 17:51:11 +05303858 *tx_ant = ar->cfg_tx_chainmask;
3859 *rx_ant = ar->cfg_rx_chainmask;
Ben Greear46acf7bb2014-05-16 17:15:38 +03003860
3861 mutex_unlock(&ar->conf_mutex);
3862
3863 return 0;
3864}
3865
Ben Greear5572a952014-11-24 16:22:10 +02003866static void ath10k_check_chain_mask(struct ath10k *ar, u32 cm, const char *dbg)
3867{
3868 /* It is not clear that allowing gaps in chainmask
3869 * is helpful. Probably it will not do what user
3870 * is hoping for, so warn in that case.
3871 */
3872 if (cm == 15 || cm == 7 || cm == 3 || cm == 1 || cm == 0)
3873 return;
3874
3875 ath10k_warn(ar, "mac %s antenna chainmask may be invalid: 0x%x. Suggested values: 15, 7, 3, 1 or 0.\n",
3876 dbg, cm);
3877}
3878
Rajkumar Manoharanf58512f2015-10-27 17:51:13 +05303879static int ath10k_mac_get_vht_cap_bf_sts(struct ath10k *ar)
3880{
3881 int nsts = ar->vht_cap_info;
3882
3883 nsts &= IEEE80211_VHT_CAP_BEAMFORMEE_STS_MASK;
3884 nsts >>= IEEE80211_VHT_CAP_BEAMFORMEE_STS_SHIFT;
3885
3886 /* If firmware does not deliver to host number of space-time
3887 * streams supported, assume it support up to 4 BF STS and return
3888 * the value for VHT CAP: nsts-1)
3889 */
3890 if (nsts == 0)
3891 return 3;
3892
3893 return nsts;
3894}
3895
3896static int ath10k_mac_get_vht_cap_bf_sound_dim(struct ath10k *ar)
3897{
3898 int sound_dim = ar->vht_cap_info;
3899
3900 sound_dim &= IEEE80211_VHT_CAP_SOUNDING_DIMENSIONS_MASK;
3901 sound_dim >>= IEEE80211_VHT_CAP_SOUNDING_DIMENSIONS_SHIFT;
3902
3903 /* If the sounding dimension is not advertised by the firmware,
3904 * let's use a default value of 1
3905 */
3906 if (sound_dim == 0)
3907 return 1;
3908
3909 return sound_dim;
3910}
3911
3912static struct ieee80211_sta_vht_cap ath10k_create_vht_cap(struct ath10k *ar)
3913{
3914 struct ieee80211_sta_vht_cap vht_cap = {0};
3915 u16 mcs_map;
3916 u32 val;
3917 int i;
3918
3919 vht_cap.vht_supported = 1;
3920 vht_cap.cap = ar->vht_cap_info;
3921
3922 if (ar->vht_cap_info & (IEEE80211_VHT_CAP_SU_BEAMFORMEE_CAPABLE |
3923 IEEE80211_VHT_CAP_MU_BEAMFORMEE_CAPABLE)) {
3924 val = ath10k_mac_get_vht_cap_bf_sts(ar);
3925 val <<= IEEE80211_VHT_CAP_BEAMFORMEE_STS_SHIFT;
3926 val &= IEEE80211_VHT_CAP_BEAMFORMEE_STS_MASK;
3927
3928 vht_cap.cap |= val;
3929 }
3930
3931 if (ar->vht_cap_info & (IEEE80211_VHT_CAP_SU_BEAMFORMER_CAPABLE |
3932 IEEE80211_VHT_CAP_MU_BEAMFORMER_CAPABLE)) {
3933 val = ath10k_mac_get_vht_cap_bf_sound_dim(ar);
3934 val <<= IEEE80211_VHT_CAP_SOUNDING_DIMENSIONS_SHIFT;
3935 val &= IEEE80211_VHT_CAP_SOUNDING_DIMENSIONS_MASK;
3936
3937 vht_cap.cap |= val;
3938 }
3939
3940 mcs_map = 0;
3941 for (i = 0; i < 8; i++) {
3942 if ((i < ar->num_rf_chains) && (ar->cfg_tx_chainmask & BIT(i)))
3943 mcs_map |= IEEE80211_VHT_MCS_SUPPORT_0_9 << (i * 2);
3944 else
3945 mcs_map |= IEEE80211_VHT_MCS_NOT_SUPPORTED << (i * 2);
3946 }
3947
3948 vht_cap.vht_mcs.rx_mcs_map = cpu_to_le16(mcs_map);
3949 vht_cap.vht_mcs.tx_mcs_map = cpu_to_le16(mcs_map);
3950
3951 return vht_cap;
3952}
3953
3954static struct ieee80211_sta_ht_cap ath10k_get_ht_cap(struct ath10k *ar)
3955{
3956 int i;
3957 struct ieee80211_sta_ht_cap ht_cap = {0};
3958
3959 if (!(ar->ht_cap_info & WMI_HT_CAP_ENABLED))
3960 return ht_cap;
3961
3962 ht_cap.ht_supported = 1;
3963 ht_cap.ampdu_factor = IEEE80211_HT_MAX_AMPDU_64K;
3964 ht_cap.ampdu_density = IEEE80211_HT_MPDU_DENSITY_8;
3965 ht_cap.cap |= IEEE80211_HT_CAP_SUP_WIDTH_20_40;
3966 ht_cap.cap |= IEEE80211_HT_CAP_DSSSCCK40;
Peter Ohe33a99e2015-12-31 15:26:20 +02003967 ht_cap.cap |=
3968 WLAN_HT_CAP_SM_PS_DISABLED << IEEE80211_HT_CAP_SM_PS_SHIFT;
Rajkumar Manoharanf58512f2015-10-27 17:51:13 +05303969
3970 if (ar->ht_cap_info & WMI_HT_CAP_HT20_SGI)
3971 ht_cap.cap |= IEEE80211_HT_CAP_SGI_20;
3972
3973 if (ar->ht_cap_info & WMI_HT_CAP_HT40_SGI)
3974 ht_cap.cap |= IEEE80211_HT_CAP_SGI_40;
3975
3976 if (ar->ht_cap_info & WMI_HT_CAP_DYNAMIC_SMPS) {
3977 u32 smps;
3978
3979 smps = WLAN_HT_CAP_SM_PS_DYNAMIC;
3980 smps <<= IEEE80211_HT_CAP_SM_PS_SHIFT;
3981
3982 ht_cap.cap |= smps;
3983 }
3984
3985 if (ar->ht_cap_info & WMI_HT_CAP_TX_STBC)
3986 ht_cap.cap |= IEEE80211_HT_CAP_TX_STBC;
3987
3988 if (ar->ht_cap_info & WMI_HT_CAP_RX_STBC) {
3989 u32 stbc;
3990
3991 stbc = ar->ht_cap_info;
3992 stbc &= WMI_HT_CAP_RX_STBC;
3993 stbc >>= WMI_HT_CAP_RX_STBC_MASK_SHIFT;
3994 stbc <<= IEEE80211_HT_CAP_RX_STBC_SHIFT;
3995 stbc &= IEEE80211_HT_CAP_RX_STBC;
3996
3997 ht_cap.cap |= stbc;
3998 }
3999
4000 if (ar->ht_cap_info & WMI_HT_CAP_LDPC)
4001 ht_cap.cap |= IEEE80211_HT_CAP_LDPC_CODING;
4002
4003 if (ar->ht_cap_info & WMI_HT_CAP_L_SIG_TXOP_PROT)
4004 ht_cap.cap |= IEEE80211_HT_CAP_LSIG_TXOP_PROT;
4005
4006 /* max AMSDU is implicitly taken from vht_cap_info */
4007 if (ar->vht_cap_info & WMI_VHT_CAP_MAX_MPDU_LEN_MASK)
4008 ht_cap.cap |= IEEE80211_HT_CAP_MAX_AMSDU;
4009
4010 for (i = 0; i < ar->num_rf_chains; i++) {
4011 if (ar->cfg_rx_chainmask & BIT(i))
4012 ht_cap.mcs.rx_mask[i] = 0xFF;
4013 }
4014
4015 ht_cap.mcs.tx_params |= IEEE80211_HT_MCS_TX_DEFINED;
4016
4017 return ht_cap;
4018}
4019
Rajkumar Manoharan5036fe02015-10-27 17:51:14 +05304020static void ath10k_mac_setup_ht_vht_cap(struct ath10k *ar)
4021{
4022 struct ieee80211_supported_band *band;
4023 struct ieee80211_sta_vht_cap vht_cap;
4024 struct ieee80211_sta_ht_cap ht_cap;
4025
4026 ht_cap = ath10k_get_ht_cap(ar);
4027 vht_cap = ath10k_create_vht_cap(ar);
4028
4029 if (ar->phy_capability & WHAL_WLAN_11G_CAPABILITY) {
4030 band = &ar->mac.sbands[IEEE80211_BAND_2GHZ];
4031 band->ht_cap = ht_cap;
4032
4033 /* Enable the VHT support at 2.4 GHz */
4034 band->vht_cap = vht_cap;
4035 }
4036 if (ar->phy_capability & WHAL_WLAN_11A_CAPABILITY) {
4037 band = &ar->mac.sbands[IEEE80211_BAND_5GHZ];
4038 band->ht_cap = ht_cap;
4039 band->vht_cap = vht_cap;
4040 }
4041}
4042
Ben Greear46acf7bb2014-05-16 17:15:38 +03004043static int __ath10k_set_antenna(struct ath10k *ar, u32 tx_ant, u32 rx_ant)
4044{
4045 int ret;
4046
4047 lockdep_assert_held(&ar->conf_mutex);
4048
Ben Greear5572a952014-11-24 16:22:10 +02004049 ath10k_check_chain_mask(ar, tx_ant, "tx");
4050 ath10k_check_chain_mask(ar, rx_ant, "rx");
4051
Ben Greear46acf7bb2014-05-16 17:15:38 +03004052 ar->cfg_tx_chainmask = tx_ant;
4053 ar->cfg_rx_chainmask = rx_ant;
4054
4055 if ((ar->state != ATH10K_STATE_ON) &&
4056 (ar->state != ATH10K_STATE_RESTARTED))
4057 return 0;
4058
4059 ret = ath10k_wmi_pdev_set_param(ar, ar->wmi.pdev_param->tx_chain_mask,
4060 tx_ant);
4061 if (ret) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02004062 ath10k_warn(ar, "failed to set tx-chainmask: %d, req 0x%x\n",
Ben Greear46acf7bb2014-05-16 17:15:38 +03004063 ret, tx_ant);
4064 return ret;
4065 }
4066
4067 ret = ath10k_wmi_pdev_set_param(ar, ar->wmi.pdev_param->rx_chain_mask,
4068 rx_ant);
4069 if (ret) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02004070 ath10k_warn(ar, "failed to set rx-chainmask: %d, req 0x%x\n",
Ben Greear46acf7bb2014-05-16 17:15:38 +03004071 ret, rx_ant);
4072 return ret;
4073 }
4074
Rajkumar Manoharan5036fe02015-10-27 17:51:14 +05304075 /* Reload HT/VHT capability */
4076 ath10k_mac_setup_ht_vht_cap(ar);
4077
Ben Greear46acf7bb2014-05-16 17:15:38 +03004078 return 0;
4079}
4080
4081static int ath10k_set_antenna(struct ieee80211_hw *hw, u32 tx_ant, u32 rx_ant)
4082{
4083 struct ath10k *ar = hw->priv;
4084 int ret;
4085
4086 mutex_lock(&ar->conf_mutex);
4087 ret = __ath10k_set_antenna(ar, tx_ant, rx_ant);
4088 mutex_unlock(&ar->conf_mutex);
4089 return ret;
4090}
4091
Kalle Valo5e3dd152013-06-12 20:52:10 +03004092static int ath10k_start(struct ieee80211_hw *hw)
4093{
4094 struct ath10k *ar = hw->priv;
Mohammed Shafi Shajakhan1fe374f2016-01-13 21:16:30 +05304095 u32 param;
Michal Kazior818bdd12013-07-16 09:38:57 +02004096 int ret = 0;
Kalle Valo5e3dd152013-06-12 20:52:10 +03004097
Michal Kaziorbca7baf2014-05-26 12:46:03 +03004098 /*
4099 * This makes sense only when restarting hw. It is harmless to call
4100 * uncoditionally. This is necessary to make sure no HTT/WMI tx
4101 * commands will be submitted while restarting.
4102 */
4103 ath10k_drain_tx(ar);
4104
Michal Kazior548db542013-07-05 16:15:15 +03004105 mutex_lock(&ar->conf_mutex);
4106
Michal Kaziorc5058f52014-05-26 12:46:03 +03004107 switch (ar->state) {
4108 case ATH10K_STATE_OFF:
4109 ar->state = ATH10K_STATE_ON;
4110 break;
4111 case ATH10K_STATE_RESTARTING:
4112 ath10k_halt(ar);
4113 ar->state = ATH10K_STATE_RESTARTED;
4114 break;
4115 case ATH10K_STATE_ON:
4116 case ATH10K_STATE_RESTARTED:
4117 case ATH10K_STATE_WEDGED:
4118 WARN_ON(1);
Michal Kazior818bdd12013-07-16 09:38:57 +02004119 ret = -EINVAL;
Michal Kaziorae254432014-05-26 12:46:02 +03004120 goto err;
Kalle Valo43d2a302014-09-10 18:23:30 +03004121 case ATH10K_STATE_UTF:
4122 ret = -EBUSY;
4123 goto err;
Michal Kazior818bdd12013-07-16 09:38:57 +02004124 }
4125
4126 ret = ath10k_hif_power_up(ar);
4127 if (ret) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02004128 ath10k_err(ar, "Could not init hif: %d\n", ret);
Michal Kaziorae254432014-05-26 12:46:02 +03004129 goto err_off;
Michal Kazior818bdd12013-07-16 09:38:57 +02004130 }
4131
Kalle Valo43d2a302014-09-10 18:23:30 +03004132 ret = ath10k_core_start(ar, ATH10K_FIRMWARE_MODE_NORMAL);
Michal Kazior818bdd12013-07-16 09:38:57 +02004133 if (ret) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02004134 ath10k_err(ar, "Could not init core: %d\n", ret);
Michal Kaziorae254432014-05-26 12:46:02 +03004135 goto err_power_down;
Michal Kazior818bdd12013-07-16 09:38:57 +02004136 }
4137
Mohammed Shafi Shajakhan1fe374f2016-01-13 21:16:30 +05304138 param = ar->wmi.pdev_param->pmf_qos;
4139 ret = ath10k_wmi_pdev_set_param(ar, param, 1);
Michal Kaziorae254432014-05-26 12:46:02 +03004140 if (ret) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02004141 ath10k_warn(ar, "failed to enable PMF QOS: %d\n", ret);
Michal Kaziorae254432014-05-26 12:46:02 +03004142 goto err_core_stop;
4143 }
Kalle Valo5e3dd152013-06-12 20:52:10 +03004144
Mohammed Shafi Shajakhan1fe374f2016-01-13 21:16:30 +05304145 param = ar->wmi.pdev_param->dynamic_bw;
4146 ret = ath10k_wmi_pdev_set_param(ar, param, 1);
Michal Kaziorae254432014-05-26 12:46:02 +03004147 if (ret) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02004148 ath10k_warn(ar, "failed to enable dynamic BW: %d\n", ret);
Michal Kaziorae254432014-05-26 12:46:02 +03004149 goto err_core_stop;
4150 }
Kalle Valo5e3dd152013-06-12 20:52:10 +03004151
Michal Kaziorcf327842015-03-31 10:26:25 +00004152 if (test_bit(WMI_SERVICE_ADAPTIVE_OCS, ar->wmi.svc_map)) {
4153 ret = ath10k_wmi_adaptive_qcs(ar, true);
4154 if (ret) {
4155 ath10k_warn(ar, "failed to enable adaptive qcs: %d\n",
4156 ret);
4157 goto err_core_stop;
4158 }
4159 }
4160
Janusz Dziedzic24ab13e2015-04-01 22:53:18 +03004161 if (test_bit(WMI_SERVICE_BURST, ar->wmi.svc_map)) {
Mohammed Shafi Shajakhan1fe374f2016-01-13 21:16:30 +05304162 param = ar->wmi.pdev_param->burst_enable;
4163 ret = ath10k_wmi_pdev_set_param(ar, param, 0);
Janusz Dziedzic24ab13e2015-04-01 22:53:18 +03004164 if (ret) {
4165 ath10k_warn(ar, "failed to disable burst: %d\n", ret);
4166 goto err_core_stop;
4167 }
4168 }
4169
Rajkumar Manoharan166de3f2015-10-27 17:51:11 +05304170 __ath10k_set_antenna(ar, ar->cfg_tx_chainmask, ar->cfg_rx_chainmask);
Ben Greear46acf7bb2014-05-16 17:15:38 +03004171
Marek Puzyniakab6258e2014-01-29 15:03:31 +02004172 /*
4173 * By default FW set ARP frames ac to voice (6). In that case ARP
4174 * exchange is not working properly for UAPSD enabled AP. ARP requests
4175 * which arrives with access category 0 are processed by network stack
4176 * and send back with access category 0, but FW changes access category
4177 * to 6. Set ARP frames access category to best effort (0) solves
4178 * this problem.
4179 */
4180
Mohammed Shafi Shajakhan1fe374f2016-01-13 21:16:30 +05304181 param = ar->wmi.pdev_param->arp_ac_override;
4182 ret = ath10k_wmi_pdev_set_param(ar, param, 0);
Marek Puzyniakab6258e2014-01-29 15:03:31 +02004183 if (ret) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02004184 ath10k_warn(ar, "failed to set arp ac override parameter: %d\n",
Marek Puzyniakab6258e2014-01-29 15:03:31 +02004185 ret);
Michal Kaziorae254432014-05-26 12:46:02 +03004186 goto err_core_stop;
Marek Puzyniakab6258e2014-01-29 15:03:31 +02004187 }
4188
Maharaja62f77f02015-10-21 11:49:18 +03004189 if (test_bit(ATH10K_FW_FEATURE_SUPPORTS_ADAPTIVE_CCA,
4190 ar->fw_features)) {
4191 ret = ath10k_wmi_pdev_enable_adaptive_cca(ar, 1,
4192 WMI_CCA_DETECT_LEVEL_AUTO,
4193 WMI_CCA_DETECT_MARGIN_AUTO);
4194 if (ret) {
4195 ath10k_warn(ar, "failed to enable adaptive cca: %d\n",
4196 ret);
4197 goto err_core_stop;
4198 }
4199 }
4200
Mohammed Shafi Shajakhan1fe374f2016-01-13 21:16:30 +05304201 param = ar->wmi.pdev_param->ani_enable;
4202 ret = ath10k_wmi_pdev_set_param(ar, param, 1);
Ashok Raj Nagarajan575f1c32015-03-19 16:37:59 +05304203 if (ret) {
4204 ath10k_warn(ar, "failed to enable ani by default: %d\n",
4205 ret);
4206 goto err_core_stop;
4207 }
4208
Ashok Raj Nagarajanb3e71d72015-03-19 16:38:00 +05304209 ar->ani_enabled = true;
4210
Mohammed Shafi Shajakhan8351c052016-01-13 21:16:33 +05304211 if (test_bit(WMI_SERVICE_PEER_STATS, ar->wmi.svc_map)) {
4212 param = ar->wmi.pdev_param->peer_stats_update_period;
4213 ret = ath10k_wmi_pdev_set_param(ar, param,
4214 PEER_DEFAULT_STATS_UPDATE_PERIOD);
4215 if (ret) {
4216 ath10k_warn(ar,
4217 "failed to set peer stats period : %d\n",
4218 ret);
4219 goto err_core_stop;
4220 }
4221 }
4222
Michal Kaziord6500972014-04-08 09:56:09 +03004223 ar->num_started_vdevs = 0;
Michal Kaziorf7843d72013-07-16 09:38:52 +02004224 ath10k_regd_update(ar);
4225
Simon Wunderlich855aed12014-08-02 09:12:54 +03004226 ath10k_spectral_start(ar);
Rajkumar Manoharan8515b5c2015-03-15 20:36:22 +05304227 ath10k_thermal_set_throttling(ar);
Simon Wunderlich855aed12014-08-02 09:12:54 +03004228
Michal Kaziorae254432014-05-26 12:46:02 +03004229 mutex_unlock(&ar->conf_mutex);
4230 return 0;
4231
4232err_core_stop:
4233 ath10k_core_stop(ar);
4234
4235err_power_down:
4236 ath10k_hif_power_down(ar);
4237
4238err_off:
4239 ar->state = ATH10K_STATE_OFF;
4240
4241err:
Michal Kazior548db542013-07-05 16:15:15 +03004242 mutex_unlock(&ar->conf_mutex);
Michal Kaziorc60bdd82014-01-29 07:26:31 +01004243 return ret;
Kalle Valo5e3dd152013-06-12 20:52:10 +03004244}
4245
4246static void ath10k_stop(struct ieee80211_hw *hw)
4247{
4248 struct ath10k *ar = hw->priv;
4249
Michal Kaziorbca7baf2014-05-26 12:46:03 +03004250 ath10k_drain_tx(ar);
4251
Michal Kazior548db542013-07-05 16:15:15 +03004252 mutex_lock(&ar->conf_mutex);
Michal Kaziorc5058f52014-05-26 12:46:03 +03004253 if (ar->state != ATH10K_STATE_OFF) {
Michal Kazior818bdd12013-07-16 09:38:57 +02004254 ath10k_halt(ar);
Michal Kaziorc5058f52014-05-26 12:46:03 +03004255 ar->state = ATH10K_STATE_OFF;
4256 }
Michal Kazior548db542013-07-05 16:15:15 +03004257 mutex_unlock(&ar->conf_mutex);
4258
Michal Kazior5c81c7f2014-08-05 14:54:44 +02004259 cancel_delayed_work_sync(&ar->scan.timeout);
Michal Kazioraffd3212013-07-16 09:54:35 +02004260 cancel_work_sync(&ar->restart_work);
4261}
4262
Michal Kaziorad088bf2013-10-16 15:44:46 +03004263static int ath10k_config_ps(struct ath10k *ar)
Michal Kazioraffd3212013-07-16 09:54:35 +02004264{
Michal Kaziorad088bf2013-10-16 15:44:46 +03004265 struct ath10k_vif *arvif;
4266 int ret = 0;
Michal Kazioraffd3212013-07-16 09:54:35 +02004267
4268 lockdep_assert_held(&ar->conf_mutex);
4269
Michal Kaziorad088bf2013-10-16 15:44:46 +03004270 list_for_each_entry(arvif, &ar->arvifs, list) {
4271 ret = ath10k_mac_vif_setup_ps(arvif);
4272 if (ret) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02004273 ath10k_warn(ar, "failed to setup powersave: %d\n", ret);
Michal Kaziorad088bf2013-10-16 15:44:46 +03004274 break;
4275 }
4276 }
Michal Kazioraffd3212013-07-16 09:54:35 +02004277
Michal Kaziorad088bf2013-10-16 15:44:46 +03004278 return ret;
Kalle Valo5e3dd152013-06-12 20:52:10 +03004279}
4280
Michal Kazior7d9d5582014-10-21 10:40:15 +03004281static int ath10k_mac_txpower_setup(struct ath10k *ar, int txpower)
4282{
4283 int ret;
4284 u32 param;
4285
4286 lockdep_assert_held(&ar->conf_mutex);
4287
4288 ath10k_dbg(ar, ATH10K_DBG_MAC, "mac txpower %d\n", txpower);
4289
4290 param = ar->wmi.pdev_param->txpower_limit2g;
4291 ret = ath10k_wmi_pdev_set_param(ar, param, txpower * 2);
4292 if (ret) {
4293 ath10k_warn(ar, "failed to set 2g txpower %d: %d\n",
4294 txpower, ret);
4295 return ret;
4296 }
4297
4298 param = ar->wmi.pdev_param->txpower_limit5g;
4299 ret = ath10k_wmi_pdev_set_param(ar, param, txpower * 2);
4300 if (ret) {
4301 ath10k_warn(ar, "failed to set 5g txpower %d: %d\n",
4302 txpower, ret);
4303 return ret;
4304 }
4305
4306 return 0;
4307}
4308
4309static int ath10k_mac_txpower_recalc(struct ath10k *ar)
4310{
4311 struct ath10k_vif *arvif;
4312 int ret, txpower = -1;
4313
4314 lockdep_assert_held(&ar->conf_mutex);
4315
4316 list_for_each_entry(arvif, &ar->arvifs, list) {
4317 WARN_ON(arvif->txpower < 0);
4318
4319 if (txpower == -1)
4320 txpower = arvif->txpower;
4321 else
4322 txpower = min(txpower, arvif->txpower);
4323 }
4324
4325 if (WARN_ON(txpower == -1))
4326 return -EINVAL;
4327
4328 ret = ath10k_mac_txpower_setup(ar, txpower);
4329 if (ret) {
4330 ath10k_warn(ar, "failed to setup tx power %d: %d\n",
4331 txpower, ret);
4332 return ret;
4333 }
4334
4335 return 0;
4336}
4337
Kalle Valo5e3dd152013-06-12 20:52:10 +03004338static int ath10k_config(struct ieee80211_hw *hw, u32 changed)
4339{
Kalle Valo5e3dd152013-06-12 20:52:10 +03004340 struct ath10k *ar = hw->priv;
4341 struct ieee80211_conf *conf = &hw->conf;
4342 int ret = 0;
Kalle Valo5e3dd152013-06-12 20:52:10 +03004343
4344 mutex_lock(&ar->conf_mutex);
4345
Michal Kazioraffd3212013-07-16 09:54:35 +02004346 if (changed & IEEE80211_CONF_CHANGE_PS)
4347 ath10k_config_ps(ar);
Kalle Valo5e3dd152013-06-12 20:52:10 +03004348
4349 if (changed & IEEE80211_CONF_CHANGE_MONITOR) {
Michal Kazior19337472014-08-28 12:58:16 +02004350 ar->monitor = conf->flags & IEEE80211_CONF_MONITOR;
4351 ret = ath10k_monitor_recalc(ar);
4352 if (ret)
4353 ath10k_warn(ar, "failed to recalc monitor: %d\n", ret);
Kalle Valo5e3dd152013-06-12 20:52:10 +03004354 }
4355
4356 mutex_unlock(&ar->conf_mutex);
4357 return ret;
4358}
4359
Ben Greear5572a952014-11-24 16:22:10 +02004360static u32 get_nss_from_chainmask(u16 chain_mask)
4361{
Rajkumar Manoharanf680f702015-11-03 11:51:33 +05304362 if ((chain_mask & 0xf) == 0xf)
Ben Greear5572a952014-11-24 16:22:10 +02004363 return 4;
4364 else if ((chain_mask & 0x7) == 0x7)
4365 return 3;
4366 else if ((chain_mask & 0x3) == 0x3)
4367 return 2;
4368 return 1;
4369}
4370
Vivek Natarajana48e2cc2015-08-04 10:45:12 +05304371static int ath10k_mac_set_txbf_conf(struct ath10k_vif *arvif)
4372{
4373 u32 value = 0;
4374 struct ath10k *ar = arvif->ar;
Bartosz Markowski707a0c82015-09-02 13:20:19 +02004375 int nsts;
Bartosz Markowski0c6d6f22015-09-02 13:20:20 +02004376 int sound_dim;
Vivek Natarajana48e2cc2015-08-04 10:45:12 +05304377
4378 if (ath10k_wmi_get_txbf_conf_scheme(ar) != WMI_TXBF_CONF_BEFORE_ASSOC)
4379 return 0;
4380
Bartosz Markowski707a0c82015-09-02 13:20:19 +02004381 nsts = ath10k_mac_get_vht_cap_bf_sts(ar);
Vivek Natarajana48e2cc2015-08-04 10:45:12 +05304382 if (ar->vht_cap_info & (IEEE80211_VHT_CAP_SU_BEAMFORMEE_CAPABLE |
4383 IEEE80211_VHT_CAP_MU_BEAMFORMEE_CAPABLE))
Bartosz Markowski707a0c82015-09-02 13:20:19 +02004384 value |= SM(nsts, WMI_TXBF_STS_CAP_OFFSET);
Vivek Natarajana48e2cc2015-08-04 10:45:12 +05304385
Bartosz Markowski0c6d6f22015-09-02 13:20:20 +02004386 sound_dim = ath10k_mac_get_vht_cap_bf_sound_dim(ar);
Vivek Natarajana48e2cc2015-08-04 10:45:12 +05304387 if (ar->vht_cap_info & (IEEE80211_VHT_CAP_SU_BEAMFORMER_CAPABLE |
4388 IEEE80211_VHT_CAP_MU_BEAMFORMER_CAPABLE))
Bartosz Markowski0c6d6f22015-09-02 13:20:20 +02004389 value |= SM(sound_dim, WMI_BF_SOUND_DIM_OFFSET);
Vivek Natarajana48e2cc2015-08-04 10:45:12 +05304390
4391 if (!value)
4392 return 0;
4393
4394 if (ar->vht_cap_info & IEEE80211_VHT_CAP_SU_BEAMFORMER_CAPABLE)
4395 value |= WMI_VDEV_PARAM_TXBF_SU_TX_BFER;
4396
4397 if (ar->vht_cap_info & IEEE80211_VHT_CAP_MU_BEAMFORMER_CAPABLE)
4398 value |= (WMI_VDEV_PARAM_TXBF_MU_TX_BFER |
4399 WMI_VDEV_PARAM_TXBF_SU_TX_BFER);
4400
4401 if (ar->vht_cap_info & IEEE80211_VHT_CAP_SU_BEAMFORMEE_CAPABLE)
4402 value |= WMI_VDEV_PARAM_TXBF_SU_TX_BFEE;
4403
4404 if (ar->vht_cap_info & IEEE80211_VHT_CAP_MU_BEAMFORMEE_CAPABLE)
4405 value |= (WMI_VDEV_PARAM_TXBF_MU_TX_BFEE |
4406 WMI_VDEV_PARAM_TXBF_SU_TX_BFEE);
4407
4408 return ath10k_wmi_vdev_set_param(ar, arvif->vdev_id,
4409 ar->wmi.vdev_param->txbf, value);
4410}
4411
Kalle Valo5e3dd152013-06-12 20:52:10 +03004412/*
4413 * TODO:
4414 * Figure out how to handle WMI_VDEV_SUBTYPE_P2P_DEVICE,
4415 * because we will send mgmt frames without CCK. This requirement
4416 * for P2P_FIND/GO_NEG should be handled by checking CCK flag
4417 * in the TX packet.
4418 */
4419static int ath10k_add_interface(struct ieee80211_hw *hw,
4420 struct ieee80211_vif *vif)
4421{
4422 struct ath10k *ar = hw->priv;
4423 struct ath10k_vif *arvif = ath10k_vif_to_arvif(vif);
Michal Kaziorbb8f0c62016-03-06 16:14:27 +02004424 struct ath10k_peer *peer;
Kalle Valo5e3dd152013-06-12 20:52:10 +03004425 enum wmi_sta_powersave_param param;
4426 int ret = 0;
Kalle Valo5a13e762014-01-20 11:01:46 +02004427 u32 value;
Kalle Valo5e3dd152013-06-12 20:52:10 +03004428 int bit;
Michal Kazior96d828d2015-03-31 10:26:23 +00004429 int i;
Bartosz Markowski6d1506e2013-09-26 17:47:15 +02004430 u32 vdev_param;
Kalle Valo5e3dd152013-06-12 20:52:10 +03004431
Johannes Berg848955c2014-11-11 12:48:42 +01004432 vif->driver_flags |= IEEE80211_VIF_SUPPORTS_UAPSD;
4433
Kalle Valo5e3dd152013-06-12 20:52:10 +03004434 mutex_lock(&ar->conf_mutex);
4435
Michal Kazior0dbd09e2013-07-31 10:55:14 +02004436 memset(arvif, 0, sizeof(*arvif));
4437
Kalle Valo5e3dd152013-06-12 20:52:10 +03004438 arvif->ar = ar;
4439 arvif->vif = vif;
4440
Ben Greeare63b33f2013-10-22 14:54:14 -07004441 INIT_LIST_HEAD(&arvif->list);
Michal Kazior81a9a172015-03-05 16:02:17 +02004442 INIT_WORK(&arvif->ap_csa_work, ath10k_mac_vif_ap_csa_work);
Michal Kaziorcc9904e2015-03-10 16:22:01 +02004443 INIT_DELAYED_WORK(&arvif->connection_loss_work,
4444 ath10k_mac_vif_sta_connection_loss_work);
Michal Kaziorcc4827b2013-10-16 15:44:45 +03004445
Michal Kazior45c9abc2015-04-21 20:42:58 +03004446 for (i = 0; i < ARRAY_SIZE(arvif->bitrate_mask.control); i++) {
4447 arvif->bitrate_mask.control[i].legacy = 0xffffffff;
4448 memset(arvif->bitrate_mask.control[i].ht_mcs, 0xff,
4449 sizeof(arvif->bitrate_mask.control[i].ht_mcs));
4450 memset(arvif->bitrate_mask.control[i].vht_mcs, 0xff,
4451 sizeof(arvif->bitrate_mask.control[i].vht_mcs));
4452 }
Kalle Valo5e3dd152013-06-12 20:52:10 +03004453
Michal Kaziore04cafb2015-08-05 12:15:24 +02004454 if (ar->num_peers >= ar->max_num_peers) {
4455 ath10k_warn(ar, "refusing vdev creation due to insufficient peer entry resources in firmware\n");
Michal Kazior503422d2015-08-19 13:08:53 +02004456 ret = -ENOBUFS;
4457 goto err;
Michal Kaziore04cafb2015-08-05 12:15:24 +02004458 }
4459
Ben Greeara9aefb32014-08-12 11:02:19 +03004460 if (ar->free_vdev_map == 0) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02004461 ath10k_warn(ar, "Free vdev map is empty, no more interfaces allowed.\n");
Kalle Valo5e3dd152013-06-12 20:52:10 +03004462 ret = -EBUSY;
Michal Kazior9dad14ae2013-10-16 15:44:45 +03004463 goto err;
Kalle Valo5e3dd152013-06-12 20:52:10 +03004464 }
Ben Greear16c11172014-09-23 14:17:16 -07004465 bit = __ffs64(ar->free_vdev_map);
Kalle Valo5e3dd152013-06-12 20:52:10 +03004466
Ben Greear16c11172014-09-23 14:17:16 -07004467 ath10k_dbg(ar, ATH10K_DBG_MAC, "mac create vdev %i map %llx\n",
4468 bit, ar->free_vdev_map);
4469
4470 arvif->vdev_id = bit;
Peter Oh6e4de1a2016-01-28 13:54:10 -08004471 arvif->vdev_subtype =
4472 ath10k_wmi_get_vdev_subtype(ar, WMI_VDEV_SUBTYPE_NONE);
Kalle Valo5e3dd152013-06-12 20:52:10 +03004473
Kalle Valo5e3dd152013-06-12 20:52:10 +03004474 switch (vif->type) {
Michal Kazior75d2bd42014-12-12 12:41:39 +01004475 case NL80211_IFTYPE_P2P_DEVICE:
4476 arvif->vdev_type = WMI_VDEV_TYPE_STA;
Peter Oh6e4de1a2016-01-28 13:54:10 -08004477 arvif->vdev_subtype = ath10k_wmi_get_vdev_subtype
4478 (ar, WMI_VDEV_SUBTYPE_P2P_DEVICE);
Michal Kazior75d2bd42014-12-12 12:41:39 +01004479 break;
Kalle Valo5e3dd152013-06-12 20:52:10 +03004480 case NL80211_IFTYPE_UNSPECIFIED:
4481 case NL80211_IFTYPE_STATION:
4482 arvif->vdev_type = WMI_VDEV_TYPE_STA;
4483 if (vif->p2p)
Peter Oh6e4de1a2016-01-28 13:54:10 -08004484 arvif->vdev_subtype = ath10k_wmi_get_vdev_subtype
4485 (ar, WMI_VDEV_SUBTYPE_P2P_CLIENT);
Kalle Valo5e3dd152013-06-12 20:52:10 +03004486 break;
4487 case NL80211_IFTYPE_ADHOC:
4488 arvif->vdev_type = WMI_VDEV_TYPE_IBSS;
4489 break;
Bob Copelandb6c7baf2015-09-09 12:47:36 -04004490 case NL80211_IFTYPE_MESH_POINT:
Peter Oh0b3d76e2016-01-28 13:54:07 -08004491 if (test_bit(WMI_SERVICE_MESH_11S, ar->wmi.svc_map)) {
Peter Oh6e4de1a2016-01-28 13:54:10 -08004492 arvif->vdev_subtype = ath10k_wmi_get_vdev_subtype
4493 (ar, WMI_VDEV_SUBTYPE_MESH_11S);
Peter Ohbb58b892015-11-24 09:37:35 -08004494 } else if (!test_bit(ATH10K_FLAG_RAW_MODE, &ar->dev_flags)) {
Bob Copelandb6c7baf2015-09-09 12:47:36 -04004495 ret = -EINVAL;
4496 ath10k_warn(ar, "must load driver with rawmode=1 to add mesh interfaces\n");
4497 goto err;
4498 }
4499 arvif->vdev_type = WMI_VDEV_TYPE_AP;
4500 break;
Kalle Valo5e3dd152013-06-12 20:52:10 +03004501 case NL80211_IFTYPE_AP:
4502 arvif->vdev_type = WMI_VDEV_TYPE_AP;
4503
4504 if (vif->p2p)
Peter Oh6e4de1a2016-01-28 13:54:10 -08004505 arvif->vdev_subtype = ath10k_wmi_get_vdev_subtype
4506 (ar, WMI_VDEV_SUBTYPE_P2P_GO);
Kalle Valo5e3dd152013-06-12 20:52:10 +03004507 break;
4508 case NL80211_IFTYPE_MONITOR:
4509 arvif->vdev_type = WMI_VDEV_TYPE_MONITOR;
4510 break;
4511 default:
4512 WARN_ON(1);
4513 break;
4514 }
4515
Michal Kazior96d828d2015-03-31 10:26:23 +00004516 /* Using vdev_id as queue number will make it very easy to do per-vif
4517 * tx queue locking. This shouldn't wrap due to interface combinations
4518 * but do a modulo for correctness sake and prevent using offchannel tx
4519 * queues for regular vif tx.
4520 */
4521 vif->cab_queue = arvif->vdev_id % (IEEE80211_MAX_QUEUES - 1);
4522 for (i = 0; i < ARRAY_SIZE(vif->hw_queue); i++)
4523 vif->hw_queue[i] = arvif->vdev_id % (IEEE80211_MAX_QUEUES - 1);
4524
Michal Kazior64badcb2014-09-18 11:18:02 +03004525 /* Some firmware revisions don't wait for beacon tx completion before
4526 * sending another SWBA event. This could lead to hardware using old
4527 * (freed) beacon data in some cases, e.g. tx credit starvation
4528 * combined with missed TBTT. This is very very rare.
4529 *
4530 * On non-IOMMU-enabled hosts this could be a possible security issue
4531 * because hw could beacon some random data on the air. On
4532 * IOMMU-enabled hosts DMAR faults would occur in most cases and target
4533 * device would crash.
4534 *
4535 * Since there are no beacon tx completions (implicit nor explicit)
4536 * propagated to host the only workaround for this is to allocate a
4537 * DMA-coherent buffer for a lifetime of a vif and use it for all
4538 * beacon tx commands. Worst case for this approach is some beacons may
4539 * become corrupted, e.g. have garbled IEs or out-of-date TIM bitmap.
4540 */
4541 if (vif->type == NL80211_IFTYPE_ADHOC ||
Bob Copelandb6c7baf2015-09-09 12:47:36 -04004542 vif->type == NL80211_IFTYPE_MESH_POINT ||
Michal Kazior64badcb2014-09-18 11:18:02 +03004543 vif->type == NL80211_IFTYPE_AP) {
4544 arvif->beacon_buf = dma_zalloc_coherent(ar->dev,
4545 IEEE80211_MAX_FRAME_LEN,
4546 &arvif->beacon_paddr,
Rajkumar Manoharan82d7aba2014-10-10 17:38:27 +05304547 GFP_ATOMIC);
Michal Kazior64badcb2014-09-18 11:18:02 +03004548 if (!arvif->beacon_buf) {
4549 ret = -ENOMEM;
4550 ath10k_warn(ar, "failed to allocate beacon buffer: %d\n",
4551 ret);
4552 goto err;
4553 }
4554 }
David Liuccec9032015-07-24 20:25:32 +03004555 if (test_bit(ATH10K_FLAG_HW_CRYPTO_DISABLED, &ar->dev_flags))
4556 arvif->nohwcrypt = true;
4557
4558 if (arvif->nohwcrypt &&
4559 !test_bit(ATH10K_FLAG_RAW_MODE, &ar->dev_flags)) {
4560 ath10k_warn(ar, "cryptmode module param needed for sw crypto\n");
4561 goto err;
4562 }
Michal Kazior64badcb2014-09-18 11:18:02 +03004563
4564 ath10k_dbg(ar, ATH10K_DBG_MAC, "mac vdev create %d (add interface) type %d subtype %d bcnmode %s\n",
4565 arvif->vdev_id, arvif->vdev_type, arvif->vdev_subtype,
4566 arvif->beacon_buf ? "single-buf" : "per-skb");
Kalle Valo5e3dd152013-06-12 20:52:10 +03004567
4568 ret = ath10k_wmi_vdev_create(ar, arvif->vdev_id, arvif->vdev_type,
4569 arvif->vdev_subtype, vif->addr);
4570 if (ret) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02004571 ath10k_warn(ar, "failed to create WMI vdev %i: %d\n",
Ben Greear69244e52014-02-27 18:50:00 +02004572 arvif->vdev_id, ret);
Michal Kazior9dad14ae2013-10-16 15:44:45 +03004573 goto err;
Kalle Valo5e3dd152013-06-12 20:52:10 +03004574 }
4575
Ben Greear16c11172014-09-23 14:17:16 -07004576 ar->free_vdev_map &= ~(1LL << arvif->vdev_id);
Michal Kazior05791192013-10-16 15:44:45 +03004577 list_add(&arvif->list, &ar->arvifs);
Michal Kazior9dad14ae2013-10-16 15:44:45 +03004578
Michal Kazior46725b152015-01-28 09:57:49 +02004579 /* It makes no sense to have firmware do keepalives. mac80211 already
4580 * takes care of this with idle connection polling.
4581 */
4582 ret = ath10k_mac_vif_disable_keepalive(arvif);
Michal Kazior9dad14ae2013-10-16 15:44:45 +03004583 if (ret) {
Michal Kazior46725b152015-01-28 09:57:49 +02004584 ath10k_warn(ar, "failed to disable keepalive on vdev %i: %d\n",
Ben Greear69244e52014-02-27 18:50:00 +02004585 arvif->vdev_id, ret);
Michal Kazior9dad14ae2013-10-16 15:44:45 +03004586 goto err_vdev_delete;
4587 }
Kalle Valo5e3dd152013-06-12 20:52:10 +03004588
SenthilKumar Jegadeesan627613f2015-01-29 13:50:38 +02004589 arvif->def_wep_key_idx = -1;
Kalle Valo5e3dd152013-06-12 20:52:10 +03004590
Bartosz Markowski6d1506e2013-09-26 17:47:15 +02004591 vdev_param = ar->wmi.vdev_param->tx_encap_type;
4592 ret = ath10k_wmi_vdev_set_param(ar, arvif->vdev_id, vdev_param,
Kalle Valo5e3dd152013-06-12 20:52:10 +03004593 ATH10K_HW_TXRX_NATIVE_WIFI);
Bartosz Markowskiebc9abd2013-10-15 09:26:20 +02004594 /* 10.X firmware does not support this VDEV parameter. Do not warn */
Michal Kazior9dad14ae2013-10-16 15:44:45 +03004595 if (ret && ret != -EOPNOTSUPP) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02004596 ath10k_warn(ar, "failed to set vdev %i TX encapsulation: %d\n",
Ben Greear69244e52014-02-27 18:50:00 +02004597 arvif->vdev_id, ret);
Michal Kazior9dad14ae2013-10-16 15:44:45 +03004598 goto err_vdev_delete;
4599 }
Kalle Valo5e3dd152013-06-12 20:52:10 +03004600
Ben Greear5572a952014-11-24 16:22:10 +02004601 if (ar->cfg_tx_chainmask) {
4602 u16 nss = get_nss_from_chainmask(ar->cfg_tx_chainmask);
4603
4604 vdev_param = ar->wmi.vdev_param->nss;
4605 ret = ath10k_wmi_vdev_set_param(ar, arvif->vdev_id, vdev_param,
4606 nss);
4607 if (ret) {
4608 ath10k_warn(ar, "failed to set vdev %i chainmask 0x%x, nss %i: %d\n",
4609 arvif->vdev_id, ar->cfg_tx_chainmask, nss,
4610 ret);
4611 goto err_vdev_delete;
4612 }
4613 }
4614
Michal Kaziore57e0572015-03-24 13:14:03 +00004615 if (arvif->vdev_type == WMI_VDEV_TYPE_AP ||
4616 arvif->vdev_type == WMI_VDEV_TYPE_IBSS) {
Marek Puzyniak7390ed32015-03-30 09:51:52 +03004617 ret = ath10k_peer_create(ar, arvif->vdev_id, vif->addr,
4618 WMI_PEER_TYPE_DEFAULT);
Kalle Valo5e3dd152013-06-12 20:52:10 +03004619 if (ret) {
Michal Kaziore57e0572015-03-24 13:14:03 +00004620 ath10k_warn(ar, "failed to create vdev %i peer for AP/IBSS: %d\n",
Ben Greear69244e52014-02-27 18:50:00 +02004621 arvif->vdev_id, ret);
Michal Kazior9dad14ae2013-10-16 15:44:45 +03004622 goto err_vdev_delete;
Kalle Valo5e3dd152013-06-12 20:52:10 +03004623 }
Michal Kaziorbb8f0c62016-03-06 16:14:27 +02004624
4625 spin_lock_bh(&ar->data_lock);
4626
4627 peer = ath10k_peer_find(ar, arvif->vdev_id, vif->addr);
4628 if (!peer) {
4629 ath10k_warn(ar, "failed to lookup peer %pM on vdev %i\n",
4630 vif->addr, arvif->vdev_id);
4631 spin_unlock_bh(&ar->data_lock);
4632 ret = -ENOENT;
4633 goto err_peer_delete;
4634 }
4635
4636 arvif->peer_id = find_first_bit(peer->peer_ids,
4637 ATH10K_MAX_NUM_PEER_IDS);
4638
4639 spin_unlock_bh(&ar->data_lock);
4640 } else {
4641 arvif->peer_id = HTT_INVALID_PEERID;
Michal Kaziore57e0572015-03-24 13:14:03 +00004642 }
Marek Puzyniakcdf07402013-12-30 09:07:51 +01004643
Michal Kaziore57e0572015-03-24 13:14:03 +00004644 if (arvif->vdev_type == WMI_VDEV_TYPE_AP) {
Kalle Valo5a13e762014-01-20 11:01:46 +02004645 ret = ath10k_mac_set_kickout(arvif);
4646 if (ret) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02004647 ath10k_warn(ar, "failed to set vdev %i kickout parameters: %d\n",
Ben Greear69244e52014-02-27 18:50:00 +02004648 arvif->vdev_id, ret);
Kalle Valo5a13e762014-01-20 11:01:46 +02004649 goto err_peer_delete;
4650 }
Kalle Valo5e3dd152013-06-12 20:52:10 +03004651 }
4652
4653 if (arvif->vdev_type == WMI_VDEV_TYPE_STA) {
4654 param = WMI_STA_PS_PARAM_RX_WAKE_POLICY;
4655 value = WMI_STA_PS_RX_WAKE_POLICY_WAKE;
4656 ret = ath10k_wmi_set_sta_ps_param(ar, arvif->vdev_id,
4657 param, value);
Michal Kazior9dad14ae2013-10-16 15:44:45 +03004658 if (ret) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02004659 ath10k_warn(ar, "failed to set vdev %i RX wake policy: %d\n",
Ben Greear69244e52014-02-27 18:50:00 +02004660 arvif->vdev_id, ret);
Michal Kazior9dad14ae2013-10-16 15:44:45 +03004661 goto err_peer_delete;
4662 }
Kalle Valo5e3dd152013-06-12 20:52:10 +03004663
Michal Kazior9f9b5742014-12-12 12:41:36 +01004664 ret = ath10k_mac_vif_recalc_ps_wake_threshold(arvif);
Michal Kazior9dad14ae2013-10-16 15:44:45 +03004665 if (ret) {
Michal Kazior9f9b5742014-12-12 12:41:36 +01004666 ath10k_warn(ar, "failed to recalc ps wake threshold on vdev %i: %d\n",
Ben Greear69244e52014-02-27 18:50:00 +02004667 arvif->vdev_id, ret);
Michal Kazior9dad14ae2013-10-16 15:44:45 +03004668 goto err_peer_delete;
4669 }
Kalle Valo5e3dd152013-06-12 20:52:10 +03004670
Michal Kazior9f9b5742014-12-12 12:41:36 +01004671 ret = ath10k_mac_vif_recalc_ps_poll_count(arvif);
Michal Kazior9dad14ae2013-10-16 15:44:45 +03004672 if (ret) {
Michal Kazior9f9b5742014-12-12 12:41:36 +01004673 ath10k_warn(ar, "failed to recalc ps poll count on vdev %i: %d\n",
Ben Greear69244e52014-02-27 18:50:00 +02004674 arvif->vdev_id, ret);
Michal Kazior9dad14ae2013-10-16 15:44:45 +03004675 goto err_peer_delete;
4676 }
Kalle Valo5e3dd152013-06-12 20:52:10 +03004677 }
4678
Vivek Natarajana48e2cc2015-08-04 10:45:12 +05304679 ret = ath10k_mac_set_txbf_conf(arvif);
4680 if (ret) {
4681 ath10k_warn(ar, "failed to set txbf for vdev %d: %d\n",
4682 arvif->vdev_id, ret);
4683 goto err_peer_delete;
4684 }
4685
Michal Kazior424121c2013-07-22 14:13:31 +02004686 ret = ath10k_mac_set_rts(arvif, ar->hw->wiphy->rts_threshold);
Michal Kazior9dad14ae2013-10-16 15:44:45 +03004687 if (ret) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02004688 ath10k_warn(ar, "failed to set rts threshold for vdev %d: %d\n",
Michal Kazior679c54a2013-07-05 16:15:04 +03004689 arvif->vdev_id, ret);
Michal Kazior9dad14ae2013-10-16 15:44:45 +03004690 goto err_peer_delete;
4691 }
Michal Kazior679c54a2013-07-05 16:15:04 +03004692
Michal Kazior7d9d5582014-10-21 10:40:15 +03004693 arvif->txpower = vif->bss_conf.txpower;
4694 ret = ath10k_mac_txpower_recalc(ar);
4695 if (ret) {
4696 ath10k_warn(ar, "failed to recalc tx power: %d\n", ret);
4697 goto err_peer_delete;
4698 }
4699
Michal Kazior500ff9f2015-03-31 10:26:21 +00004700 if (vif->type == NL80211_IFTYPE_MONITOR) {
4701 ar->monitor_arvif = arvif;
4702 ret = ath10k_monitor_recalc(ar);
4703 if (ret) {
4704 ath10k_warn(ar, "failed to recalc monitor: %d\n", ret);
4705 goto err_peer_delete;
4706 }
4707 }
4708
Michal Kazior6d2d51e2015-08-07 09:08:21 +02004709 spin_lock_bh(&ar->htt.tx_lock);
4710 if (!ar->tx_paused)
4711 ieee80211_wake_queue(ar->hw, arvif->vdev_id);
4712 spin_unlock_bh(&ar->htt.tx_lock);
4713
Kalle Valo5e3dd152013-06-12 20:52:10 +03004714 mutex_unlock(&ar->conf_mutex);
Michal Kazior9dad14ae2013-10-16 15:44:45 +03004715 return 0;
4716
4717err_peer_delete:
Michal Kaziore57e0572015-03-24 13:14:03 +00004718 if (arvif->vdev_type == WMI_VDEV_TYPE_AP ||
4719 arvif->vdev_type == WMI_VDEV_TYPE_IBSS)
Michal Kazior9dad14ae2013-10-16 15:44:45 +03004720 ath10k_wmi_peer_delete(ar, arvif->vdev_id, vif->addr);
4721
4722err_vdev_delete:
4723 ath10k_wmi_vdev_delete(ar, arvif->vdev_id);
Ben Greear16c11172014-09-23 14:17:16 -07004724 ar->free_vdev_map |= 1LL << arvif->vdev_id;
Michal Kazior05791192013-10-16 15:44:45 +03004725 list_del(&arvif->list);
Michal Kazior9dad14ae2013-10-16 15:44:45 +03004726
4727err:
Michal Kazior64badcb2014-09-18 11:18:02 +03004728 if (arvif->beacon_buf) {
4729 dma_free_coherent(ar->dev, IEEE80211_MAX_FRAME_LEN,
4730 arvif->beacon_buf, arvif->beacon_paddr);
4731 arvif->beacon_buf = NULL;
4732 }
4733
Michal Kazior9dad14ae2013-10-16 15:44:45 +03004734 mutex_unlock(&ar->conf_mutex);
4735
Kalle Valo5e3dd152013-06-12 20:52:10 +03004736 return ret;
4737}
4738
Michal Kaziorb4aa5392015-03-31 10:26:24 +00004739static void ath10k_mac_vif_tx_unlock_all(struct ath10k_vif *arvif)
4740{
4741 int i;
4742
4743 for (i = 0; i < BITS_PER_LONG; i++)
4744 ath10k_mac_vif_tx_unlock(arvif, i);
4745}
4746
Kalle Valo5e3dd152013-06-12 20:52:10 +03004747static void ath10k_remove_interface(struct ieee80211_hw *hw,
4748 struct ieee80211_vif *vif)
4749{
4750 struct ath10k *ar = hw->priv;
4751 struct ath10k_vif *arvif = ath10k_vif_to_arvif(vif);
4752 int ret;
4753
Michal Kazior81a9a172015-03-05 16:02:17 +02004754 cancel_work_sync(&arvif->ap_csa_work);
Michal Kaziorcc9904e2015-03-10 16:22:01 +02004755 cancel_delayed_work_sync(&arvif->connection_loss_work);
Michal Kazior81a9a172015-03-05 16:02:17 +02004756
Sujith Manoharan5d011f52014-11-25 11:47:00 +05304757 mutex_lock(&ar->conf_mutex);
4758
Michal Kaziored543882013-09-13 14:16:56 +02004759 spin_lock_bh(&ar->data_lock);
Michal Kazior64badcb2014-09-18 11:18:02 +03004760 ath10k_mac_vif_beacon_cleanup(arvif);
Michal Kaziored543882013-09-13 14:16:56 +02004761 spin_unlock_bh(&ar->data_lock);
4762
Simon Wunderlich855aed12014-08-02 09:12:54 +03004763 ret = ath10k_spectral_vif_stop(arvif);
4764 if (ret)
Michal Kazior7aa7a722014-08-25 12:09:38 +02004765 ath10k_warn(ar, "failed to stop spectral for vdev %i: %d\n",
Simon Wunderlich855aed12014-08-02 09:12:54 +03004766 arvif->vdev_id, ret);
4767
Ben Greear16c11172014-09-23 14:17:16 -07004768 ar->free_vdev_map |= 1LL << arvif->vdev_id;
Michal Kazior05791192013-10-16 15:44:45 +03004769 list_del(&arvif->list);
Kalle Valo5e3dd152013-06-12 20:52:10 +03004770
Michal Kaziore57e0572015-03-24 13:14:03 +00004771 if (arvif->vdev_type == WMI_VDEV_TYPE_AP ||
4772 arvif->vdev_type == WMI_VDEV_TYPE_IBSS) {
Michal Kazior2c512052015-02-15 16:50:40 +02004773 ret = ath10k_wmi_peer_delete(arvif->ar, arvif->vdev_id,
4774 vif->addr);
Kalle Valo5e3dd152013-06-12 20:52:10 +03004775 if (ret)
Michal Kaziore57e0572015-03-24 13:14:03 +00004776 ath10k_warn(ar, "failed to submit AP/IBSS self-peer removal on vdev %i: %d\n",
Ben Greear69244e52014-02-27 18:50:00 +02004777 arvif->vdev_id, ret);
Kalle Valo5e3dd152013-06-12 20:52:10 +03004778
4779 kfree(arvif->u.ap.noa_data);
4780 }
4781
Michal Kazior7aa7a722014-08-25 12:09:38 +02004782 ath10k_dbg(ar, ATH10K_DBG_MAC, "mac vdev %i delete (remove interface)\n",
Kalle Valo60c3daa2013-09-08 17:56:07 +03004783 arvif->vdev_id);
4784
Kalle Valo5e3dd152013-06-12 20:52:10 +03004785 ret = ath10k_wmi_vdev_delete(ar, arvif->vdev_id);
4786 if (ret)
Michal Kazior7aa7a722014-08-25 12:09:38 +02004787 ath10k_warn(ar, "failed to delete WMI vdev %i: %d\n",
Ben Greear69244e52014-02-27 18:50:00 +02004788 arvif->vdev_id, ret);
Kalle Valo5e3dd152013-06-12 20:52:10 +03004789
Michal Kazior2c512052015-02-15 16:50:40 +02004790 /* Some firmware revisions don't notify host about self-peer removal
4791 * until after associated vdev is deleted.
4792 */
Michal Kaziore57e0572015-03-24 13:14:03 +00004793 if (arvif->vdev_type == WMI_VDEV_TYPE_AP ||
4794 arvif->vdev_type == WMI_VDEV_TYPE_IBSS) {
Michal Kazior2c512052015-02-15 16:50:40 +02004795 ret = ath10k_wait_for_peer_deleted(ar, arvif->vdev_id,
4796 vif->addr);
4797 if (ret)
4798 ath10k_warn(ar, "failed to remove AP self-peer on vdev %i: %d\n",
4799 arvif->vdev_id, ret);
4800
4801 spin_lock_bh(&ar->data_lock);
4802 ar->num_peers--;
4803 spin_unlock_bh(&ar->data_lock);
4804 }
4805
Kalle Valo5e3dd152013-06-12 20:52:10 +03004806 ath10k_peer_cleanup(ar, arvif->vdev_id);
4807
Michal Kazior500ff9f2015-03-31 10:26:21 +00004808 if (vif->type == NL80211_IFTYPE_MONITOR) {
4809 ar->monitor_arvif = NULL;
4810 ret = ath10k_monitor_recalc(ar);
4811 if (ret)
4812 ath10k_warn(ar, "failed to recalc monitor: %d\n", ret);
4813 }
4814
Michal Kaziorb4aa5392015-03-31 10:26:24 +00004815 spin_lock_bh(&ar->htt.tx_lock);
4816 ath10k_mac_vif_tx_unlock_all(arvif);
4817 spin_unlock_bh(&ar->htt.tx_lock);
4818
Kalle Valo5e3dd152013-06-12 20:52:10 +03004819 mutex_unlock(&ar->conf_mutex);
4820}
4821
4822/*
4823 * FIXME: Has to be verified.
4824 */
4825#define SUPPORTED_FILTERS \
Johannes Bergdf140462015-04-22 14:40:58 +02004826 (FIF_ALLMULTI | \
Kalle Valo5e3dd152013-06-12 20:52:10 +03004827 FIF_CONTROL | \
4828 FIF_PSPOLL | \
4829 FIF_OTHER_BSS | \
4830 FIF_BCN_PRBRESP_PROMISC | \
4831 FIF_PROBE_REQ | \
4832 FIF_FCSFAIL)
4833
4834static void ath10k_configure_filter(struct ieee80211_hw *hw,
4835 unsigned int changed_flags,
4836 unsigned int *total_flags,
4837 u64 multicast)
4838{
4839 struct ath10k *ar = hw->priv;
4840 int ret;
4841
4842 mutex_lock(&ar->conf_mutex);
4843
4844 changed_flags &= SUPPORTED_FILTERS;
4845 *total_flags &= SUPPORTED_FILTERS;
4846 ar->filter_flags = *total_flags;
4847
Michal Kazior19337472014-08-28 12:58:16 +02004848 ret = ath10k_monitor_recalc(ar);
4849 if (ret)
4850 ath10k_warn(ar, "failed to recalc montior: %d\n", ret);
Kalle Valo5e3dd152013-06-12 20:52:10 +03004851
4852 mutex_unlock(&ar->conf_mutex);
4853}
4854
4855static void ath10k_bss_info_changed(struct ieee80211_hw *hw,
4856 struct ieee80211_vif *vif,
4857 struct ieee80211_bss_conf *info,
4858 u32 changed)
4859{
4860 struct ath10k *ar = hw->priv;
4861 struct ath10k_vif *arvif = ath10k_vif_to_arvif(vif);
4862 int ret = 0;
Kalle Valoaf762c02014-09-14 12:50:17 +03004863 u32 vdev_param, pdev_param, slottime, preamble;
Kalle Valo5e3dd152013-06-12 20:52:10 +03004864
4865 mutex_lock(&ar->conf_mutex);
4866
4867 if (changed & BSS_CHANGED_IBSS)
4868 ath10k_control_ibss(arvif, info, vif->addr);
4869
4870 if (changed & BSS_CHANGED_BEACON_INT) {
4871 arvif->beacon_interval = info->beacon_int;
Bartosz Markowski6d1506e2013-09-26 17:47:15 +02004872 vdev_param = ar->wmi.vdev_param->beacon_interval;
4873 ret = ath10k_wmi_vdev_set_param(ar, arvif->vdev_id, vdev_param,
Kalle Valo5e3dd152013-06-12 20:52:10 +03004874 arvif->beacon_interval);
Michal Kazior7aa7a722014-08-25 12:09:38 +02004875 ath10k_dbg(ar, ATH10K_DBG_MAC,
Kalle Valo60c3daa2013-09-08 17:56:07 +03004876 "mac vdev %d beacon_interval %d\n",
4877 arvif->vdev_id, arvif->beacon_interval);
4878
Kalle Valo5e3dd152013-06-12 20:52:10 +03004879 if (ret)
Michal Kazior7aa7a722014-08-25 12:09:38 +02004880 ath10k_warn(ar, "failed to set beacon interval for vdev %d: %i\n",
Ben Greear69244e52014-02-27 18:50:00 +02004881 arvif->vdev_id, ret);
Kalle Valo5e3dd152013-06-12 20:52:10 +03004882 }
4883
4884 if (changed & BSS_CHANGED_BEACON) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02004885 ath10k_dbg(ar, ATH10K_DBG_MAC,
Kalle Valo60c3daa2013-09-08 17:56:07 +03004886 "vdev %d set beacon tx mode to staggered\n",
4887 arvif->vdev_id);
4888
Bartosz Markowski226a3392013-09-26 17:47:16 +02004889 pdev_param = ar->wmi.pdev_param->beacon_tx_mode;
4890 ret = ath10k_wmi_pdev_set_param(ar, pdev_param,
Kalle Valo5e3dd152013-06-12 20:52:10 +03004891 WMI_BEACON_STAGGERED_MODE);
4892 if (ret)
Michal Kazior7aa7a722014-08-25 12:09:38 +02004893 ath10k_warn(ar, "failed to set beacon mode for vdev %d: %i\n",
Ben Greear69244e52014-02-27 18:50:00 +02004894 arvif->vdev_id, ret);
Michal Kaziorfbb8f1b2015-01-13 16:30:12 +02004895
4896 ret = ath10k_mac_setup_bcn_tmpl(arvif);
4897 if (ret)
4898 ath10k_warn(ar, "failed to update beacon template: %d\n",
4899 ret);
Bob Copelandb6c7baf2015-09-09 12:47:36 -04004900
4901 if (ieee80211_vif_is_mesh(vif)) {
4902 /* mesh doesn't use SSID but firmware needs it */
4903 strncpy(arvif->u.ap.ssid, "mesh",
4904 sizeof(arvif->u.ap.ssid));
4905 arvif->u.ap.ssid_len = 4;
4906 }
Kalle Valo5e3dd152013-06-12 20:52:10 +03004907 }
4908
Michal Kaziorfbb8f1b2015-01-13 16:30:12 +02004909 if (changed & BSS_CHANGED_AP_PROBE_RESP) {
4910 ret = ath10k_mac_setup_prb_tmpl(arvif);
4911 if (ret)
4912 ath10k_warn(ar, "failed to setup probe resp template on vdev %i: %d\n",
4913 arvif->vdev_id, ret);
Kalle Valo5e3dd152013-06-12 20:52:10 +03004914 }
4915
Michal Kaziorba2479f2015-01-24 12:14:51 +02004916 if (changed & (BSS_CHANGED_BEACON_INFO | BSS_CHANGED_BEACON)) {
Kalle Valo5e3dd152013-06-12 20:52:10 +03004917 arvif->dtim_period = info->dtim_period;
4918
Michal Kazior7aa7a722014-08-25 12:09:38 +02004919 ath10k_dbg(ar, ATH10K_DBG_MAC,
Kalle Valo60c3daa2013-09-08 17:56:07 +03004920 "mac vdev %d dtim_period %d\n",
4921 arvif->vdev_id, arvif->dtim_period);
4922
Bartosz Markowski6d1506e2013-09-26 17:47:15 +02004923 vdev_param = ar->wmi.vdev_param->dtim_period;
4924 ret = ath10k_wmi_vdev_set_param(ar, arvif->vdev_id, vdev_param,
Kalle Valo5e3dd152013-06-12 20:52:10 +03004925 arvif->dtim_period);
4926 if (ret)
Michal Kazior7aa7a722014-08-25 12:09:38 +02004927 ath10k_warn(ar, "failed to set dtim period for vdev %d: %i\n",
Ben Greear69244e52014-02-27 18:50:00 +02004928 arvif->vdev_id, ret);
Kalle Valo5e3dd152013-06-12 20:52:10 +03004929 }
4930
4931 if (changed & BSS_CHANGED_SSID &&
4932 vif->type == NL80211_IFTYPE_AP) {
4933 arvif->u.ap.ssid_len = info->ssid_len;
4934 if (info->ssid_len)
4935 memcpy(arvif->u.ap.ssid, info->ssid, info->ssid_len);
4936 arvif->u.ap.hidden_ssid = info->hidden_ssid;
4937 }
4938
Michal Kazior077efc82014-10-21 10:10:29 +03004939 if (changed & BSS_CHANGED_BSSID && !is_zero_ether_addr(info->bssid))
4940 ether_addr_copy(arvif->bssid, info->bssid);
Kalle Valo5e3dd152013-06-12 20:52:10 +03004941
4942 if (changed & BSS_CHANGED_BEACON_ENABLED)
4943 ath10k_control_beaconing(arvif, info);
4944
4945 if (changed & BSS_CHANGED_ERP_CTS_PROT) {
Marek Kwaczynskie81bd102014-03-11 12:58:00 +02004946 arvif->use_cts_prot = info->use_cts_prot;
Michal Kazior7aa7a722014-08-25 12:09:38 +02004947 ath10k_dbg(ar, ATH10K_DBG_MAC, "mac vdev %d cts_prot %d\n",
Marek Kwaczynskie81bd102014-03-11 12:58:00 +02004948 arvif->vdev_id, info->use_cts_prot);
Kalle Valo60c3daa2013-09-08 17:56:07 +03004949
Marek Kwaczynskie81bd102014-03-11 12:58:00 +02004950 ret = ath10k_recalc_rtscts_prot(arvif);
Kalle Valo5e3dd152013-06-12 20:52:10 +03004951 if (ret)
Michal Kazior7aa7a722014-08-25 12:09:38 +02004952 ath10k_warn(ar, "failed to recalculate rts/cts prot for vdev %d: %d\n",
Ben Greear69244e52014-02-27 18:50:00 +02004953 arvif->vdev_id, ret);
Michal Kaziora87fd4b2015-03-02 11:21:17 +01004954
4955 vdev_param = ar->wmi.vdev_param->protection_mode;
4956 ret = ath10k_wmi_vdev_set_param(ar, arvif->vdev_id, vdev_param,
4957 info->use_cts_prot ? 1 : 0);
4958 if (ret)
4959 ath10k_warn(ar, "failed to set protection mode %d on vdev %i: %d\n",
Kalle Valo617b0f42015-10-05 17:56:35 +03004960 info->use_cts_prot, arvif->vdev_id, ret);
Kalle Valo5e3dd152013-06-12 20:52:10 +03004961 }
4962
4963 if (changed & BSS_CHANGED_ERP_SLOT) {
Kalle Valo5e3dd152013-06-12 20:52:10 +03004964 if (info->use_short_slot)
4965 slottime = WMI_VDEV_SLOT_TIME_SHORT; /* 9us */
4966
4967 else
4968 slottime = WMI_VDEV_SLOT_TIME_LONG; /* 20us */
4969
Michal Kazior7aa7a722014-08-25 12:09:38 +02004970 ath10k_dbg(ar, ATH10K_DBG_MAC, "mac vdev %d slot_time %d\n",
Kalle Valo60c3daa2013-09-08 17:56:07 +03004971 arvif->vdev_id, slottime);
4972
Bartosz Markowski6d1506e2013-09-26 17:47:15 +02004973 vdev_param = ar->wmi.vdev_param->slot_time;
4974 ret = ath10k_wmi_vdev_set_param(ar, arvif->vdev_id, vdev_param,
Kalle Valo5e3dd152013-06-12 20:52:10 +03004975 slottime);
4976 if (ret)
Michal Kazior7aa7a722014-08-25 12:09:38 +02004977 ath10k_warn(ar, "failed to set erp slot for vdev %d: %i\n",
Ben Greear69244e52014-02-27 18:50:00 +02004978 arvif->vdev_id, ret);
Kalle Valo5e3dd152013-06-12 20:52:10 +03004979 }
4980
4981 if (changed & BSS_CHANGED_ERP_PREAMBLE) {
Kalle Valo5e3dd152013-06-12 20:52:10 +03004982 if (info->use_short_preamble)
4983 preamble = WMI_VDEV_PREAMBLE_SHORT;
4984 else
4985 preamble = WMI_VDEV_PREAMBLE_LONG;
4986
Michal Kazior7aa7a722014-08-25 12:09:38 +02004987 ath10k_dbg(ar, ATH10K_DBG_MAC,
Kalle Valo60c3daa2013-09-08 17:56:07 +03004988 "mac vdev %d preamble %dn",
4989 arvif->vdev_id, preamble);
4990
Bartosz Markowski6d1506e2013-09-26 17:47:15 +02004991 vdev_param = ar->wmi.vdev_param->preamble;
4992 ret = ath10k_wmi_vdev_set_param(ar, arvif->vdev_id, vdev_param,
Kalle Valo5e3dd152013-06-12 20:52:10 +03004993 preamble);
4994 if (ret)
Michal Kazior7aa7a722014-08-25 12:09:38 +02004995 ath10k_warn(ar, "failed to set preamble for vdev %d: %i\n",
Ben Greear69244e52014-02-27 18:50:00 +02004996 arvif->vdev_id, ret);
Kalle Valo5e3dd152013-06-12 20:52:10 +03004997 }
4998
4999 if (changed & BSS_CHANGED_ASSOC) {
Michal Kaziore556f112014-08-28 12:58:17 +02005000 if (info->assoc) {
5001 /* Workaround: Make sure monitor vdev is not running
5002 * when associating to prevent some firmware revisions
5003 * (e.g. 10.1 and 10.2) from crashing.
5004 */
5005 if (ar->monitor_started)
5006 ath10k_monitor_stop(ar);
Kalle Valo5e3dd152013-06-12 20:52:10 +03005007 ath10k_bss_assoc(hw, vif, info);
Michal Kaziore556f112014-08-28 12:58:17 +02005008 ath10k_monitor_recalc(ar);
Michal Kazior077efc82014-10-21 10:10:29 +03005009 } else {
5010 ath10k_bss_disassoc(hw, vif);
Michal Kaziore556f112014-08-28 12:58:17 +02005011 }
Kalle Valo5e3dd152013-06-12 20:52:10 +03005012 }
5013
Michal Kazior7d9d5582014-10-21 10:40:15 +03005014 if (changed & BSS_CHANGED_TXPOWER) {
5015 ath10k_dbg(ar, ATH10K_DBG_MAC, "mac vdev_id %i txpower %d\n",
5016 arvif->vdev_id, info->txpower);
5017
5018 arvif->txpower = info->txpower;
5019 ret = ath10k_mac_txpower_recalc(ar);
5020 if (ret)
5021 ath10k_warn(ar, "failed to recalc tx power: %d\n", ret);
5022 }
5023
Michal Kaziorbf14e652014-12-12 12:41:38 +01005024 if (changed & BSS_CHANGED_PS) {
Michal Kaziorcffb41f2015-02-13 13:30:16 +01005025 arvif->ps = vif->bss_conf.ps;
5026
5027 ret = ath10k_config_ps(ar);
Michal Kaziorbf14e652014-12-12 12:41:38 +01005028 if (ret)
5029 ath10k_warn(ar, "failed to setup ps on vdev %i: %d\n",
5030 arvif->vdev_id, ret);
5031 }
5032
Kalle Valo5e3dd152013-06-12 20:52:10 +03005033 mutex_unlock(&ar->conf_mutex);
5034}
5035
5036static int ath10k_hw_scan(struct ieee80211_hw *hw,
5037 struct ieee80211_vif *vif,
David Spinadelc56ef672014-02-05 15:21:13 +02005038 struct ieee80211_scan_request *hw_req)
Kalle Valo5e3dd152013-06-12 20:52:10 +03005039{
5040 struct ath10k *ar = hw->priv;
5041 struct ath10k_vif *arvif = ath10k_vif_to_arvif(vif);
David Spinadelc56ef672014-02-05 15:21:13 +02005042 struct cfg80211_scan_request *req = &hw_req->req;
Kalle Valo5e3dd152013-06-12 20:52:10 +03005043 struct wmi_start_scan_arg arg;
5044 int ret = 0;
5045 int i;
5046
5047 mutex_lock(&ar->conf_mutex);
5048
5049 spin_lock_bh(&ar->data_lock);
Michal Kazior5c81c7f2014-08-05 14:54:44 +02005050 switch (ar->scan.state) {
5051 case ATH10K_SCAN_IDLE:
5052 reinit_completion(&ar->scan.started);
5053 reinit_completion(&ar->scan.completed);
5054 ar->scan.state = ATH10K_SCAN_STARTING;
5055 ar->scan.is_roc = false;
5056 ar->scan.vdev_id = arvif->vdev_id;
5057 ret = 0;
5058 break;
5059 case ATH10K_SCAN_STARTING:
5060 case ATH10K_SCAN_RUNNING:
5061 case ATH10K_SCAN_ABORTING:
Kalle Valo5e3dd152013-06-12 20:52:10 +03005062 ret = -EBUSY;
Michal Kazior5c81c7f2014-08-05 14:54:44 +02005063 break;
Kalle Valo5e3dd152013-06-12 20:52:10 +03005064 }
Kalle Valo5e3dd152013-06-12 20:52:10 +03005065 spin_unlock_bh(&ar->data_lock);
5066
Michal Kazior5c81c7f2014-08-05 14:54:44 +02005067 if (ret)
5068 goto exit;
5069
Kalle Valo5e3dd152013-06-12 20:52:10 +03005070 memset(&arg, 0, sizeof(arg));
5071 ath10k_wmi_start_scan_init(ar, &arg);
5072 arg.vdev_id = arvif->vdev_id;
5073 arg.scan_id = ATH10K_SCAN_ID;
5074
Kalle Valo5e3dd152013-06-12 20:52:10 +03005075 if (req->ie_len) {
5076 arg.ie_len = req->ie_len;
5077 memcpy(arg.ie, req->ie, arg.ie_len);
5078 }
5079
5080 if (req->n_ssids) {
5081 arg.n_ssids = req->n_ssids;
5082 for (i = 0; i < arg.n_ssids; i++) {
5083 arg.ssids[i].len = req->ssids[i].ssid_len;
5084 arg.ssids[i].ssid = req->ssids[i].ssid;
5085 }
Michal Kaziordcd4a562013-07-31 10:55:12 +02005086 } else {
5087 arg.scan_ctrl_flags |= WMI_SCAN_FLAG_PASSIVE;
Kalle Valo5e3dd152013-06-12 20:52:10 +03005088 }
5089
5090 if (req->n_channels) {
5091 arg.n_channels = req->n_channels;
5092 for (i = 0; i < arg.n_channels; i++)
5093 arg.channels[i] = req->channels[i]->center_freq;
5094 }
5095
5096 ret = ath10k_start_scan(ar, &arg);
5097 if (ret) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02005098 ath10k_warn(ar, "failed to start hw scan: %d\n", ret);
Kalle Valo5e3dd152013-06-12 20:52:10 +03005099 spin_lock_bh(&ar->data_lock);
Michal Kazior5c81c7f2014-08-05 14:54:44 +02005100 ar->scan.state = ATH10K_SCAN_IDLE;
Kalle Valo5e3dd152013-06-12 20:52:10 +03005101 spin_unlock_bh(&ar->data_lock);
5102 }
5103
Michal Kazior634349b2015-09-03 10:43:45 +02005104 /* Add a 200ms margin to account for event/command processing */
5105 ieee80211_queue_delayed_work(ar->hw, &ar->scan.timeout,
5106 msecs_to_jiffies(arg.max_scan_time +
5107 200));
5108
Kalle Valo5e3dd152013-06-12 20:52:10 +03005109exit:
5110 mutex_unlock(&ar->conf_mutex);
5111 return ret;
5112}
5113
5114static void ath10k_cancel_hw_scan(struct ieee80211_hw *hw,
5115 struct ieee80211_vif *vif)
5116{
5117 struct ath10k *ar = hw->priv;
Kalle Valo5e3dd152013-06-12 20:52:10 +03005118
5119 mutex_lock(&ar->conf_mutex);
Michal Kazior5c81c7f2014-08-05 14:54:44 +02005120 ath10k_scan_abort(ar);
Kalle Valo5e3dd152013-06-12 20:52:10 +03005121 mutex_unlock(&ar->conf_mutex);
Michal Kazior4eb2e162014-10-28 10:23:09 +01005122
5123 cancel_delayed_work_sync(&ar->scan.timeout);
Kalle Valo5e3dd152013-06-12 20:52:10 +03005124}
5125
Michal Kaziorcfb27d22013-12-02 09:06:36 +01005126static void ath10k_set_key_h_def_keyidx(struct ath10k *ar,
5127 struct ath10k_vif *arvif,
5128 enum set_key_cmd cmd,
5129 struct ieee80211_key_conf *key)
5130{
5131 u32 vdev_param = arvif->ar->wmi.vdev_param->def_keyid;
5132 int ret;
5133
5134 /* 10.1 firmware branch requires default key index to be set to group
5135 * key index after installing it. Otherwise FW/HW Txes corrupted
5136 * frames with multi-vif APs. This is not required for main firmware
5137 * branch (e.g. 636).
5138 *
Michal Kazior8461baf2015-04-10 13:23:22 +00005139 * This is also needed for 636 fw for IBSS-RSN to work more reliably.
5140 *
5141 * FIXME: It remains unknown if this is required for multi-vif STA
5142 * interfaces on 10.1.
5143 */
Michal Kaziorcfb27d22013-12-02 09:06:36 +01005144
Michal Kazior8461baf2015-04-10 13:23:22 +00005145 if (arvif->vdev_type != WMI_VDEV_TYPE_AP &&
5146 arvif->vdev_type != WMI_VDEV_TYPE_IBSS)
Michal Kaziorcfb27d22013-12-02 09:06:36 +01005147 return;
5148
5149 if (key->cipher == WLAN_CIPHER_SUITE_WEP40)
5150 return;
5151
5152 if (key->cipher == WLAN_CIPHER_SUITE_WEP104)
5153 return;
5154
5155 if (key->flags & IEEE80211_KEY_FLAG_PAIRWISE)
5156 return;
5157
5158 if (cmd != SET_KEY)
5159 return;
5160
5161 ret = ath10k_wmi_vdev_set_param(ar, arvif->vdev_id, vdev_param,
5162 key->keyidx);
5163 if (ret)
Michal Kazior7aa7a722014-08-25 12:09:38 +02005164 ath10k_warn(ar, "failed to set vdev %i group key as default key: %d\n",
Ben Greear69244e52014-02-27 18:50:00 +02005165 arvif->vdev_id, ret);
Michal Kaziorcfb27d22013-12-02 09:06:36 +01005166}
5167
Kalle Valo5e3dd152013-06-12 20:52:10 +03005168static int ath10k_set_key(struct ieee80211_hw *hw, enum set_key_cmd cmd,
5169 struct ieee80211_vif *vif, struct ieee80211_sta *sta,
5170 struct ieee80211_key_conf *key)
5171{
5172 struct ath10k *ar = hw->priv;
5173 struct ath10k_vif *arvif = ath10k_vif_to_arvif(vif);
5174 struct ath10k_peer *peer;
5175 const u8 *peer_addr;
5176 bool is_wep = key->cipher == WLAN_CIPHER_SUITE_WEP40 ||
5177 key->cipher == WLAN_CIPHER_SUITE_WEP104;
5178 int ret = 0;
Michal Kazior29a10002015-04-10 13:05:58 +00005179 int ret2;
Michal Kazior370e5672015-02-18 14:02:26 +01005180 u32 flags = 0;
Michal Kazior29a10002015-04-10 13:05:58 +00005181 u32 flags2;
Kalle Valo5e3dd152013-06-12 20:52:10 +03005182
Bartosz Markowskid7131c02015-03-10 14:32:19 +01005183 /* this one needs to be done in software */
5184 if (key->cipher == WLAN_CIPHER_SUITE_AES_CMAC)
5185 return 1;
Kalle Valo5e3dd152013-06-12 20:52:10 +03005186
David Liuccec9032015-07-24 20:25:32 +03005187 if (arvif->nohwcrypt)
5188 return 1;
5189
Kalle Valo5e3dd152013-06-12 20:52:10 +03005190 if (key->keyidx > WMI_MAX_KEY_INDEX)
5191 return -ENOSPC;
5192
5193 mutex_lock(&ar->conf_mutex);
5194
5195 if (sta)
5196 peer_addr = sta->addr;
5197 else if (arvif->vdev_type == WMI_VDEV_TYPE_STA)
5198 peer_addr = vif->bss_conf.bssid;
5199 else
5200 peer_addr = vif->addr;
5201
5202 key->hw_key_idx = key->keyidx;
5203
Michal Kazior7c8cc7e2015-04-01 22:53:19 +03005204 if (is_wep) {
5205 if (cmd == SET_KEY)
5206 arvif->wep_keys[key->keyidx] = key;
5207 else
5208 arvif->wep_keys[key->keyidx] = NULL;
5209 }
5210
Kalle Valo5e3dd152013-06-12 20:52:10 +03005211 /* the peer should not disappear in mid-way (unless FW goes awry) since
5212 * we already hold conf_mutex. we just make sure its there now. */
5213 spin_lock_bh(&ar->data_lock);
5214 peer = ath10k_peer_find(ar, arvif->vdev_id, peer_addr);
5215 spin_unlock_bh(&ar->data_lock);
5216
5217 if (!peer) {
5218 if (cmd == SET_KEY) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02005219 ath10k_warn(ar, "failed to install key for non-existent peer %pM\n",
Kalle Valo5e3dd152013-06-12 20:52:10 +03005220 peer_addr);
5221 ret = -EOPNOTSUPP;
5222 goto exit;
5223 } else {
5224 /* if the peer doesn't exist there is no key to disable
5225 * anymore */
5226 goto exit;
5227 }
5228 }
5229
Michal Kazior7cc45732015-03-09 14:24:17 +01005230 if (key->flags & IEEE80211_KEY_FLAG_PAIRWISE)
5231 flags |= WMI_KEY_PAIRWISE;
5232 else
5233 flags |= WMI_KEY_GROUP;
Kalle Valo5e3dd152013-06-12 20:52:10 +03005234
Kalle Valo5e3dd152013-06-12 20:52:10 +03005235 if (is_wep) {
Kalle Valo5e3dd152013-06-12 20:52:10 +03005236 if (cmd == DISABLE_KEY)
5237 ath10k_clear_vdev_key(arvif, key);
Michal Kazior370e5672015-02-18 14:02:26 +01005238
Michal Kaziorad325cb2015-02-18 14:02:27 +01005239 /* When WEP keys are uploaded it's possible that there are
5240 * stations associated already (e.g. when merging) without any
5241 * keys. Static WEP needs an explicit per-peer key upload.
5242 */
5243 if (vif->type == NL80211_IFTYPE_ADHOC &&
5244 cmd == SET_KEY)
5245 ath10k_mac_vif_update_wep_key(arvif, key);
5246
Michal Kazior370e5672015-02-18 14:02:26 +01005247 /* 802.1x never sets the def_wep_key_idx so each set_key()
5248 * call changes default tx key.
5249 *
5250 * Static WEP sets def_wep_key_idx via .set_default_unicast_key
5251 * after first set_key().
5252 */
5253 if (cmd == SET_KEY && arvif->def_wep_key_idx == -1)
5254 flags |= WMI_KEY_TX_USAGE;
Kalle Valo5e3dd152013-06-12 20:52:10 +03005255 }
5256
Michal Kazior370e5672015-02-18 14:02:26 +01005257 ret = ath10k_install_key(arvif, key, cmd, peer_addr, flags);
Kalle Valo5e3dd152013-06-12 20:52:10 +03005258 if (ret) {
David Liuccec9032015-07-24 20:25:32 +03005259 WARN_ON(ret > 0);
Michal Kazior7aa7a722014-08-25 12:09:38 +02005260 ath10k_warn(ar, "failed to install key for vdev %i peer %pM: %d\n",
Ben Greear69244e52014-02-27 18:50:00 +02005261 arvif->vdev_id, peer_addr, ret);
Kalle Valo5e3dd152013-06-12 20:52:10 +03005262 goto exit;
5263 }
5264
Michal Kazior29a10002015-04-10 13:05:58 +00005265 /* mac80211 sets static WEP keys as groupwise while firmware requires
5266 * them to be installed twice as both pairwise and groupwise.
5267 */
5268 if (is_wep && !sta && vif->type == NL80211_IFTYPE_STATION) {
5269 flags2 = flags;
5270 flags2 &= ~WMI_KEY_GROUP;
5271 flags2 |= WMI_KEY_PAIRWISE;
5272
5273 ret = ath10k_install_key(arvif, key, cmd, peer_addr, flags2);
5274 if (ret) {
David Liuccec9032015-07-24 20:25:32 +03005275 WARN_ON(ret > 0);
Michal Kazior29a10002015-04-10 13:05:58 +00005276 ath10k_warn(ar, "failed to install (ucast) key for vdev %i peer %pM: %d\n",
5277 arvif->vdev_id, peer_addr, ret);
5278 ret2 = ath10k_install_key(arvif, key, DISABLE_KEY,
5279 peer_addr, flags);
David Liuccec9032015-07-24 20:25:32 +03005280 if (ret2) {
5281 WARN_ON(ret2 > 0);
Michal Kazior29a10002015-04-10 13:05:58 +00005282 ath10k_warn(ar, "failed to disable (mcast) key for vdev %i peer %pM: %d\n",
5283 arvif->vdev_id, peer_addr, ret2);
David Liuccec9032015-07-24 20:25:32 +03005284 }
Michal Kazior29a10002015-04-10 13:05:58 +00005285 goto exit;
5286 }
5287 }
5288
Michal Kaziorcfb27d22013-12-02 09:06:36 +01005289 ath10k_set_key_h_def_keyidx(ar, arvif, cmd, key);
5290
Kalle Valo5e3dd152013-06-12 20:52:10 +03005291 spin_lock_bh(&ar->data_lock);
5292 peer = ath10k_peer_find(ar, arvif->vdev_id, peer_addr);
5293 if (peer && cmd == SET_KEY)
5294 peer->keys[key->keyidx] = key;
5295 else if (peer && cmd == DISABLE_KEY)
5296 peer->keys[key->keyidx] = NULL;
5297 else if (peer == NULL)
5298 /* impossible unless FW goes crazy */
Michal Kazior7aa7a722014-08-25 12:09:38 +02005299 ath10k_warn(ar, "Peer %pM disappeared!\n", peer_addr);
Kalle Valo5e3dd152013-06-12 20:52:10 +03005300 spin_unlock_bh(&ar->data_lock);
5301
5302exit:
5303 mutex_unlock(&ar->conf_mutex);
5304 return ret;
5305}
5306
SenthilKumar Jegadeesan627613f2015-01-29 13:50:38 +02005307static void ath10k_set_default_unicast_key(struct ieee80211_hw *hw,
5308 struct ieee80211_vif *vif,
5309 int keyidx)
5310{
5311 struct ath10k *ar = hw->priv;
5312 struct ath10k_vif *arvif = ath10k_vif_to_arvif(vif);
5313 int ret;
5314
5315 mutex_lock(&arvif->ar->conf_mutex);
5316
5317 if (arvif->ar->state != ATH10K_STATE_ON)
5318 goto unlock;
5319
5320 ath10k_dbg(ar, ATH10K_DBG_MAC, "mac vdev %d set keyidx %d\n",
5321 arvif->vdev_id, keyidx);
5322
5323 ret = ath10k_wmi_vdev_set_param(arvif->ar,
5324 arvif->vdev_id,
5325 arvif->ar->wmi.vdev_param->def_keyid,
5326 keyidx);
5327
5328 if (ret) {
5329 ath10k_warn(ar, "failed to update wep key index for vdev %d: %d\n",
5330 arvif->vdev_id,
5331 ret);
5332 goto unlock;
5333 }
5334
5335 arvif->def_wep_key_idx = keyidx;
Michal Kazior370e5672015-02-18 14:02:26 +01005336
SenthilKumar Jegadeesan627613f2015-01-29 13:50:38 +02005337unlock:
5338 mutex_unlock(&arvif->ar->conf_mutex);
5339}
5340
Michal Kazior9797feb2014-02-14 14:49:48 +01005341static void ath10k_sta_rc_update_wk(struct work_struct *wk)
5342{
5343 struct ath10k *ar;
5344 struct ath10k_vif *arvif;
5345 struct ath10k_sta *arsta;
5346 struct ieee80211_sta *sta;
Michal Kazior45c9abc2015-04-21 20:42:58 +03005347 struct cfg80211_chan_def def;
5348 enum ieee80211_band band;
5349 const u8 *ht_mcs_mask;
5350 const u16 *vht_mcs_mask;
Michal Kazior9797feb2014-02-14 14:49:48 +01005351 u32 changed, bw, nss, smps;
5352 int err;
5353
5354 arsta = container_of(wk, struct ath10k_sta, update_wk);
5355 sta = container_of((void *)arsta, struct ieee80211_sta, drv_priv);
5356 arvif = arsta->arvif;
5357 ar = arvif->ar;
5358
Michal Kazior45c9abc2015-04-21 20:42:58 +03005359 if (WARN_ON(ath10k_mac_vif_chan(arvif->vif, &def)))
5360 return;
5361
5362 band = def.chan->band;
5363 ht_mcs_mask = arvif->bitrate_mask.control[band].ht_mcs;
5364 vht_mcs_mask = arvif->bitrate_mask.control[band].vht_mcs;
5365
Michal Kazior9797feb2014-02-14 14:49:48 +01005366 spin_lock_bh(&ar->data_lock);
5367
5368 changed = arsta->changed;
5369 arsta->changed = 0;
5370
5371 bw = arsta->bw;
5372 nss = arsta->nss;
5373 smps = arsta->smps;
5374
5375 spin_unlock_bh(&ar->data_lock);
5376
5377 mutex_lock(&ar->conf_mutex);
5378
Michal Kazior45c9abc2015-04-21 20:42:58 +03005379 nss = max_t(u32, 1, nss);
5380 nss = min(nss, max(ath10k_mac_max_ht_nss(ht_mcs_mask),
5381 ath10k_mac_max_vht_nss(vht_mcs_mask)));
5382
Michal Kazior9797feb2014-02-14 14:49:48 +01005383 if (changed & IEEE80211_RC_BW_CHANGED) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02005384 ath10k_dbg(ar, ATH10K_DBG_MAC, "mac update sta %pM peer bw %d\n",
Michal Kazior9797feb2014-02-14 14:49:48 +01005385 sta->addr, bw);
5386
5387 err = ath10k_wmi_peer_set_param(ar, arvif->vdev_id, sta->addr,
5388 WMI_PEER_CHAN_WIDTH, bw);
5389 if (err)
Michal Kazior7aa7a722014-08-25 12:09:38 +02005390 ath10k_warn(ar, "failed to update STA %pM peer bw %d: %d\n",
Michal Kazior9797feb2014-02-14 14:49:48 +01005391 sta->addr, bw, err);
5392 }
5393
5394 if (changed & IEEE80211_RC_NSS_CHANGED) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02005395 ath10k_dbg(ar, ATH10K_DBG_MAC, "mac update sta %pM nss %d\n",
Michal Kazior9797feb2014-02-14 14:49:48 +01005396 sta->addr, nss);
5397
5398 err = ath10k_wmi_peer_set_param(ar, arvif->vdev_id, sta->addr,
5399 WMI_PEER_NSS, nss);
5400 if (err)
Michal Kazior7aa7a722014-08-25 12:09:38 +02005401 ath10k_warn(ar, "failed to update STA %pM nss %d: %d\n",
Michal Kazior9797feb2014-02-14 14:49:48 +01005402 sta->addr, nss, err);
5403 }
5404
5405 if (changed & IEEE80211_RC_SMPS_CHANGED) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02005406 ath10k_dbg(ar, ATH10K_DBG_MAC, "mac update sta %pM smps %d\n",
Michal Kazior9797feb2014-02-14 14:49:48 +01005407 sta->addr, smps);
5408
5409 err = ath10k_wmi_peer_set_param(ar, arvif->vdev_id, sta->addr,
5410 WMI_PEER_SMPS_STATE, smps);
5411 if (err)
Michal Kazior7aa7a722014-08-25 12:09:38 +02005412 ath10k_warn(ar, "failed to update STA %pM smps %d: %d\n",
Michal Kazior9797feb2014-02-14 14:49:48 +01005413 sta->addr, smps, err);
5414 }
5415
Janusz Dziedzic55884c02014-12-17 12:30:02 +02005416 if (changed & IEEE80211_RC_SUPP_RATES_CHANGED ||
5417 changed & IEEE80211_RC_NSS_CHANGED) {
5418 ath10k_dbg(ar, ATH10K_DBG_MAC, "mac update sta %pM supp rates/nss\n",
Chun-Yeow Yeoh44d6fa92014-03-07 10:19:30 +02005419 sta->addr);
5420
Michal Kazior590922a2014-10-21 10:10:29 +03005421 err = ath10k_station_assoc(ar, arvif->vif, sta, true);
Chun-Yeow Yeoh44d6fa92014-03-07 10:19:30 +02005422 if (err)
Michal Kazior7aa7a722014-08-25 12:09:38 +02005423 ath10k_warn(ar, "failed to reassociate station: %pM\n",
Chun-Yeow Yeoh44d6fa92014-03-07 10:19:30 +02005424 sta->addr);
5425 }
5426
Michal Kazior9797feb2014-02-14 14:49:48 +01005427 mutex_unlock(&ar->conf_mutex);
5428}
5429
Marek Puzyniak7c354242015-03-30 09:51:52 +03005430static int ath10k_mac_inc_num_stations(struct ath10k_vif *arvif,
5431 struct ieee80211_sta *sta)
Michal Kaziorcfd10612014-11-25 15:16:05 +01005432{
5433 struct ath10k *ar = arvif->ar;
5434
5435 lockdep_assert_held(&ar->conf_mutex);
5436
Marek Puzyniak7c354242015-03-30 09:51:52 +03005437 if (arvif->vdev_type == WMI_VDEV_TYPE_STA && !sta->tdls)
Michal Kaziorcfd10612014-11-25 15:16:05 +01005438 return 0;
5439
5440 if (ar->num_stations >= ar->max_num_stations)
5441 return -ENOBUFS;
5442
5443 ar->num_stations++;
5444
5445 return 0;
5446}
5447
Marek Puzyniak7c354242015-03-30 09:51:52 +03005448static void ath10k_mac_dec_num_stations(struct ath10k_vif *arvif,
5449 struct ieee80211_sta *sta)
Michal Kaziorcfd10612014-11-25 15:16:05 +01005450{
5451 struct ath10k *ar = arvif->ar;
5452
5453 lockdep_assert_held(&ar->conf_mutex);
5454
Marek Puzyniak7c354242015-03-30 09:51:52 +03005455 if (arvif->vdev_type == WMI_VDEV_TYPE_STA && !sta->tdls)
Michal Kaziorcfd10612014-11-25 15:16:05 +01005456 return;
5457
5458 ar->num_stations--;
5459}
5460
Marek Puzyniak75d85fd2015-03-30 09:51:53 +03005461struct ath10k_mac_tdls_iter_data {
5462 u32 num_tdls_stations;
5463 struct ieee80211_vif *curr_vif;
5464};
5465
5466static void ath10k_mac_tdls_vif_stations_count_iter(void *data,
5467 struct ieee80211_sta *sta)
5468{
5469 struct ath10k_mac_tdls_iter_data *iter_data = data;
5470 struct ath10k_sta *arsta = (struct ath10k_sta *)sta->drv_priv;
5471 struct ieee80211_vif *sta_vif = arsta->arvif->vif;
5472
5473 if (sta->tdls && sta_vif == iter_data->curr_vif)
5474 iter_data->num_tdls_stations++;
5475}
5476
5477static int ath10k_mac_tdls_vif_stations_count(struct ieee80211_hw *hw,
5478 struct ieee80211_vif *vif)
5479{
5480 struct ath10k_mac_tdls_iter_data data = {};
5481
5482 data.curr_vif = vif;
5483
5484 ieee80211_iterate_stations_atomic(hw,
5485 ath10k_mac_tdls_vif_stations_count_iter,
5486 &data);
5487 return data.num_tdls_stations;
5488}
5489
5490static void ath10k_mac_tdls_vifs_count_iter(void *data, u8 *mac,
5491 struct ieee80211_vif *vif)
5492{
5493 struct ath10k_vif *arvif = ath10k_vif_to_arvif(vif);
5494 int *num_tdls_vifs = data;
5495
5496 if (vif->type != NL80211_IFTYPE_STATION)
5497 return;
5498
5499 if (ath10k_mac_tdls_vif_stations_count(arvif->ar->hw, vif) > 0)
5500 (*num_tdls_vifs)++;
5501}
5502
5503static int ath10k_mac_tdls_vifs_count(struct ieee80211_hw *hw)
5504{
5505 int num_tdls_vifs = 0;
5506
5507 ieee80211_iterate_active_interfaces_atomic(hw,
5508 IEEE80211_IFACE_ITER_NORMAL,
5509 ath10k_mac_tdls_vifs_count_iter,
5510 &num_tdls_vifs);
5511 return num_tdls_vifs;
5512}
5513
Kalle Valo5e3dd152013-06-12 20:52:10 +03005514static int ath10k_sta_state(struct ieee80211_hw *hw,
5515 struct ieee80211_vif *vif,
5516 struct ieee80211_sta *sta,
5517 enum ieee80211_sta_state old_state,
5518 enum ieee80211_sta_state new_state)
5519{
5520 struct ath10k *ar = hw->priv;
5521 struct ath10k_vif *arvif = ath10k_vif_to_arvif(vif);
Michal Kazior9797feb2014-02-14 14:49:48 +01005522 struct ath10k_sta *arsta = (struct ath10k_sta *)sta->drv_priv;
Michal Kaziorbb8f0c62016-03-06 16:14:27 +02005523 struct ath10k_peer *peer;
Kalle Valo5e3dd152013-06-12 20:52:10 +03005524 int ret = 0;
5525
Michal Kazior76f90022014-02-25 09:29:57 +02005526 if (old_state == IEEE80211_STA_NOTEXIST &&
5527 new_state == IEEE80211_STA_NONE) {
5528 memset(arsta, 0, sizeof(*arsta));
5529 arsta->arvif = arvif;
5530 INIT_WORK(&arsta->update_wk, ath10k_sta_rc_update_wk);
5531 }
5532
Michal Kazior9797feb2014-02-14 14:49:48 +01005533 /* cancel must be done outside the mutex to avoid deadlock */
5534 if ((old_state == IEEE80211_STA_NONE &&
5535 new_state == IEEE80211_STA_NOTEXIST))
5536 cancel_work_sync(&arsta->update_wk);
5537
Kalle Valo5e3dd152013-06-12 20:52:10 +03005538 mutex_lock(&ar->conf_mutex);
5539
5540 if (old_state == IEEE80211_STA_NOTEXIST &&
Michal Kazior077efc82014-10-21 10:10:29 +03005541 new_state == IEEE80211_STA_NONE) {
Kalle Valo5e3dd152013-06-12 20:52:10 +03005542 /*
5543 * New station addition.
5544 */
Marek Puzyniak75d85fd2015-03-30 09:51:53 +03005545 enum wmi_peer_type peer_type = WMI_PEER_TYPE_DEFAULT;
5546 u32 num_tdls_stations;
5547 u32 num_tdls_vifs;
5548
Michal Kaziorcfd10612014-11-25 15:16:05 +01005549 ath10k_dbg(ar, ATH10K_DBG_MAC,
5550 "mac vdev %d peer create %pM (new sta) sta %d / %d peer %d / %d\n",
5551 arvif->vdev_id, sta->addr,
5552 ar->num_stations + 1, ar->max_num_stations,
5553 ar->num_peers + 1, ar->max_num_peers);
Bartosz Markowski0e759f32014-01-02 14:38:33 +01005554
Marek Puzyniak7c354242015-03-30 09:51:52 +03005555 ret = ath10k_mac_inc_num_stations(arvif, sta);
Michal Kaziorcfd10612014-11-25 15:16:05 +01005556 if (ret) {
5557 ath10k_warn(ar, "refusing to associate station: too many connected already (%d)\n",
5558 ar->max_num_stations);
Bartosz Markowski0e759f32014-01-02 14:38:33 +01005559 goto exit;
5560 }
5561
Marek Puzyniak75d85fd2015-03-30 09:51:53 +03005562 if (sta->tdls)
5563 peer_type = WMI_PEER_TYPE_TDLS;
5564
Marek Puzyniak7390ed32015-03-30 09:51:52 +03005565 ret = ath10k_peer_create(ar, arvif->vdev_id, sta->addr,
Marek Puzyniak75d85fd2015-03-30 09:51:53 +03005566 peer_type);
Michal Kaziora52c0282014-11-25 15:16:03 +01005567 if (ret) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02005568 ath10k_warn(ar, "failed to add peer %pM for vdev %d when adding a new sta: %i\n",
Ben Greear479398b2013-11-04 09:19:34 -08005569 sta->addr, arvif->vdev_id, ret);
Marek Puzyniak7c354242015-03-30 09:51:52 +03005570 ath10k_mac_dec_num_stations(arvif, sta);
Michal Kaziora52c0282014-11-25 15:16:03 +01005571 goto exit;
5572 }
Michal Kazior077efc82014-10-21 10:10:29 +03005573
Michal Kaziorbb8f0c62016-03-06 16:14:27 +02005574 spin_lock_bh(&ar->data_lock);
5575
5576 peer = ath10k_peer_find(ar, arvif->vdev_id, sta->addr);
5577 if (!peer) {
5578 ath10k_warn(ar, "failed to lookup peer %pM on vdev %i\n",
5579 vif->addr, arvif->vdev_id);
5580 spin_unlock_bh(&ar->data_lock);
5581 ath10k_peer_delete(ar, arvif->vdev_id, sta->addr);
5582 ath10k_mac_dec_num_stations(arvif, sta);
5583 ret = -ENOENT;
5584 goto exit;
5585 }
5586
5587 arsta->peer_id = find_first_bit(peer->peer_ids,
5588 ATH10K_MAX_NUM_PEER_IDS);
5589
5590 spin_unlock_bh(&ar->data_lock);
5591
Marek Puzyniak75d85fd2015-03-30 09:51:53 +03005592 if (!sta->tdls)
5593 goto exit;
Michal Kazior077efc82014-10-21 10:10:29 +03005594
Marek Puzyniak75d85fd2015-03-30 09:51:53 +03005595 num_tdls_stations = ath10k_mac_tdls_vif_stations_count(hw, vif);
5596 num_tdls_vifs = ath10k_mac_tdls_vifs_count(hw);
5597
5598 if (num_tdls_vifs >= ar->max_num_tdls_vdevs &&
5599 num_tdls_stations == 0) {
5600 ath10k_warn(ar, "vdev %i exceeded maximum number of tdls vdevs %i\n",
5601 arvif->vdev_id, ar->max_num_tdls_vdevs);
5602 ath10k_peer_delete(ar, arvif->vdev_id, sta->addr);
5603 ath10k_mac_dec_num_stations(arvif, sta);
5604 ret = -ENOBUFS;
5605 goto exit;
5606 }
5607
5608 if (num_tdls_stations == 0) {
5609 /* This is the first tdls peer in current vif */
5610 enum wmi_tdls_state state = WMI_TDLS_ENABLE_ACTIVE;
5611
5612 ret = ath10k_wmi_update_fw_tdls_state(ar, arvif->vdev_id,
5613 state);
Michal Kazior077efc82014-10-21 10:10:29 +03005614 if (ret) {
Marek Puzyniak75d85fd2015-03-30 09:51:53 +03005615 ath10k_warn(ar, "failed to update fw tdls state on vdev %i: %i\n",
Michal Kazior077efc82014-10-21 10:10:29 +03005616 arvif->vdev_id, ret);
Marek Puzyniak75d85fd2015-03-30 09:51:53 +03005617 ath10k_peer_delete(ar, arvif->vdev_id,
5618 sta->addr);
5619 ath10k_mac_dec_num_stations(arvif, sta);
Michal Kazior077efc82014-10-21 10:10:29 +03005620 goto exit;
5621 }
Marek Puzyniak75d85fd2015-03-30 09:51:53 +03005622 }
Michal Kazior077efc82014-10-21 10:10:29 +03005623
Marek Puzyniak75d85fd2015-03-30 09:51:53 +03005624 ret = ath10k_mac_tdls_peer_update(ar, arvif->vdev_id, sta,
5625 WMI_TDLS_PEER_STATE_PEERING);
5626 if (ret) {
5627 ath10k_warn(ar,
5628 "failed to update tdls peer %pM for vdev %d when adding a new sta: %i\n",
5629 sta->addr, arvif->vdev_id, ret);
5630 ath10k_peer_delete(ar, arvif->vdev_id, sta->addr);
5631 ath10k_mac_dec_num_stations(arvif, sta);
5632
5633 if (num_tdls_stations != 0)
5634 goto exit;
5635 ath10k_wmi_update_fw_tdls_state(ar, arvif->vdev_id,
5636 WMI_TDLS_DISABLE);
Michal Kazior077efc82014-10-21 10:10:29 +03005637 }
Kalle Valo5e3dd152013-06-12 20:52:10 +03005638 } else if ((old_state == IEEE80211_STA_NONE &&
5639 new_state == IEEE80211_STA_NOTEXIST)) {
5640 /*
5641 * Existing station deletion.
5642 */
Michal Kazior7aa7a722014-08-25 12:09:38 +02005643 ath10k_dbg(ar, ATH10K_DBG_MAC,
Kalle Valo60c3daa2013-09-08 17:56:07 +03005644 "mac vdev %d peer delete %pM (sta gone)\n",
5645 arvif->vdev_id, sta->addr);
Michal Kazior077efc82014-10-21 10:10:29 +03005646
Kalle Valo5e3dd152013-06-12 20:52:10 +03005647 ret = ath10k_peer_delete(ar, arvif->vdev_id, sta->addr);
5648 if (ret)
Michal Kazior7aa7a722014-08-25 12:09:38 +02005649 ath10k_warn(ar, "failed to delete peer %pM for vdev %d: %i\n",
Ben Greear69244e52014-02-27 18:50:00 +02005650 sta->addr, arvif->vdev_id, ret);
Kalle Valo5e3dd152013-06-12 20:52:10 +03005651
Marek Puzyniak7c354242015-03-30 09:51:52 +03005652 ath10k_mac_dec_num_stations(arvif, sta);
Marek Puzyniak75d85fd2015-03-30 09:51:53 +03005653
5654 if (!sta->tdls)
5655 goto exit;
5656
5657 if (ath10k_mac_tdls_vif_stations_count(hw, vif))
5658 goto exit;
5659
5660 /* This was the last tdls peer in current vif */
5661 ret = ath10k_wmi_update_fw_tdls_state(ar, arvif->vdev_id,
5662 WMI_TDLS_DISABLE);
5663 if (ret) {
5664 ath10k_warn(ar, "failed to update fw tdls state on vdev %i: %i\n",
5665 arvif->vdev_id, ret);
5666 }
Kalle Valo5e3dd152013-06-12 20:52:10 +03005667 } else if (old_state == IEEE80211_STA_AUTH &&
5668 new_state == IEEE80211_STA_ASSOC &&
5669 (vif->type == NL80211_IFTYPE_AP ||
Bob Copelandb6c7baf2015-09-09 12:47:36 -04005670 vif->type == NL80211_IFTYPE_MESH_POINT ||
Kalle Valo5e3dd152013-06-12 20:52:10 +03005671 vif->type == NL80211_IFTYPE_ADHOC)) {
5672 /*
5673 * New association.
5674 */
Michal Kazior7aa7a722014-08-25 12:09:38 +02005675 ath10k_dbg(ar, ATH10K_DBG_MAC, "mac sta %pM associated\n",
Kalle Valo60c3daa2013-09-08 17:56:07 +03005676 sta->addr);
5677
Michal Kazior590922a2014-10-21 10:10:29 +03005678 ret = ath10k_station_assoc(ar, vif, sta, false);
Kalle Valo5e3dd152013-06-12 20:52:10 +03005679 if (ret)
Michal Kazior7aa7a722014-08-25 12:09:38 +02005680 ath10k_warn(ar, "failed to associate station %pM for vdev %i: %i\n",
Ben Greear69244e52014-02-27 18:50:00 +02005681 sta->addr, arvif->vdev_id, ret);
Kalle Valo5e3dd152013-06-12 20:52:10 +03005682 } else if (old_state == IEEE80211_STA_ASSOC &&
Marek Puzyniak75d85fd2015-03-30 09:51:53 +03005683 new_state == IEEE80211_STA_AUTHORIZED &&
5684 sta->tdls) {
5685 /*
5686 * Tdls station authorized.
5687 */
5688 ath10k_dbg(ar, ATH10K_DBG_MAC, "mac tdls sta %pM authorized\n",
5689 sta->addr);
5690
5691 ret = ath10k_station_assoc(ar, vif, sta, false);
5692 if (ret) {
5693 ath10k_warn(ar, "failed to associate tdls station %pM for vdev %i: %i\n",
5694 sta->addr, arvif->vdev_id, ret);
5695 goto exit;
5696 }
5697
5698 ret = ath10k_mac_tdls_peer_update(ar, arvif->vdev_id, sta,
5699 WMI_TDLS_PEER_STATE_CONNECTED);
5700 if (ret)
5701 ath10k_warn(ar, "failed to update tdls peer %pM for vdev %i: %i\n",
5702 sta->addr, arvif->vdev_id, ret);
5703 } else if (old_state == IEEE80211_STA_ASSOC &&
5704 new_state == IEEE80211_STA_AUTH &&
5705 (vif->type == NL80211_IFTYPE_AP ||
Bob Copelandb6c7baf2015-09-09 12:47:36 -04005706 vif->type == NL80211_IFTYPE_MESH_POINT ||
Marek Puzyniak75d85fd2015-03-30 09:51:53 +03005707 vif->type == NL80211_IFTYPE_ADHOC)) {
Kalle Valo5e3dd152013-06-12 20:52:10 +03005708 /*
5709 * Disassociation.
5710 */
Michal Kazior7aa7a722014-08-25 12:09:38 +02005711 ath10k_dbg(ar, ATH10K_DBG_MAC, "mac sta %pM disassociated\n",
Kalle Valo60c3daa2013-09-08 17:56:07 +03005712 sta->addr);
5713
Michal Kazior590922a2014-10-21 10:10:29 +03005714 ret = ath10k_station_disassoc(ar, vif, sta);
Kalle Valo5e3dd152013-06-12 20:52:10 +03005715 if (ret)
Michal Kazior7aa7a722014-08-25 12:09:38 +02005716 ath10k_warn(ar, "failed to disassociate station: %pM vdev %i: %i\n",
Ben Greear69244e52014-02-27 18:50:00 +02005717 sta->addr, arvif->vdev_id, ret);
Kalle Valo5e3dd152013-06-12 20:52:10 +03005718 }
Bartosz Markowski0e759f32014-01-02 14:38:33 +01005719exit:
Kalle Valo5e3dd152013-06-12 20:52:10 +03005720 mutex_unlock(&ar->conf_mutex);
5721 return ret;
5722}
5723
5724static int ath10k_conf_tx_uapsd(struct ath10k *ar, struct ieee80211_vif *vif,
Kalle Valo5b07e072014-09-14 12:50:06 +03005725 u16 ac, bool enable)
Kalle Valo5e3dd152013-06-12 20:52:10 +03005726{
5727 struct ath10k_vif *arvif = ath10k_vif_to_arvif(vif);
Michal Kaziorb0e56152015-01-24 12:14:52 +02005728 struct wmi_sta_uapsd_auto_trig_arg arg = {};
5729 u32 prio = 0, acc = 0;
Kalle Valo5e3dd152013-06-12 20:52:10 +03005730 u32 value = 0;
5731 int ret = 0;
5732
Michal Kazior548db542013-07-05 16:15:15 +03005733 lockdep_assert_held(&ar->conf_mutex);
5734
Kalle Valo5e3dd152013-06-12 20:52:10 +03005735 if (arvif->vdev_type != WMI_VDEV_TYPE_STA)
5736 return 0;
5737
5738 switch (ac) {
5739 case IEEE80211_AC_VO:
5740 value = WMI_STA_PS_UAPSD_AC3_DELIVERY_EN |
5741 WMI_STA_PS_UAPSD_AC3_TRIGGER_EN;
Michal Kaziorb0e56152015-01-24 12:14:52 +02005742 prio = 7;
5743 acc = 3;
Kalle Valo5e3dd152013-06-12 20:52:10 +03005744 break;
5745 case IEEE80211_AC_VI:
5746 value = WMI_STA_PS_UAPSD_AC2_DELIVERY_EN |
5747 WMI_STA_PS_UAPSD_AC2_TRIGGER_EN;
Michal Kaziorb0e56152015-01-24 12:14:52 +02005748 prio = 5;
5749 acc = 2;
Kalle Valo5e3dd152013-06-12 20:52:10 +03005750 break;
5751 case IEEE80211_AC_BE:
5752 value = WMI_STA_PS_UAPSD_AC1_DELIVERY_EN |
5753 WMI_STA_PS_UAPSD_AC1_TRIGGER_EN;
Michal Kaziorb0e56152015-01-24 12:14:52 +02005754 prio = 2;
5755 acc = 1;
Kalle Valo5e3dd152013-06-12 20:52:10 +03005756 break;
5757 case IEEE80211_AC_BK:
5758 value = WMI_STA_PS_UAPSD_AC0_DELIVERY_EN |
5759 WMI_STA_PS_UAPSD_AC0_TRIGGER_EN;
Michal Kaziorb0e56152015-01-24 12:14:52 +02005760 prio = 0;
5761 acc = 0;
Kalle Valo5e3dd152013-06-12 20:52:10 +03005762 break;
5763 }
5764
5765 if (enable)
5766 arvif->u.sta.uapsd |= value;
5767 else
5768 arvif->u.sta.uapsd &= ~value;
5769
5770 ret = ath10k_wmi_set_sta_ps_param(ar, arvif->vdev_id,
5771 WMI_STA_PS_PARAM_UAPSD,
5772 arvif->u.sta.uapsd);
5773 if (ret) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02005774 ath10k_warn(ar, "failed to set uapsd params: %d\n", ret);
Kalle Valo5e3dd152013-06-12 20:52:10 +03005775 goto exit;
5776 }
5777
5778 if (arvif->u.sta.uapsd)
5779 value = WMI_STA_PS_RX_WAKE_POLICY_POLL_UAPSD;
5780 else
5781 value = WMI_STA_PS_RX_WAKE_POLICY_WAKE;
5782
5783 ret = ath10k_wmi_set_sta_ps_param(ar, arvif->vdev_id,
5784 WMI_STA_PS_PARAM_RX_WAKE_POLICY,
5785 value);
5786 if (ret)
Michal Kazior7aa7a722014-08-25 12:09:38 +02005787 ath10k_warn(ar, "failed to set rx wake param: %d\n", ret);
Kalle Valo5e3dd152013-06-12 20:52:10 +03005788
Michal Kazior9f9b5742014-12-12 12:41:36 +01005789 ret = ath10k_mac_vif_recalc_ps_wake_threshold(arvif);
5790 if (ret) {
5791 ath10k_warn(ar, "failed to recalc ps wake threshold on vdev %i: %d\n",
5792 arvif->vdev_id, ret);
5793 return ret;
5794 }
5795
5796 ret = ath10k_mac_vif_recalc_ps_poll_count(arvif);
5797 if (ret) {
5798 ath10k_warn(ar, "failed to recalc ps poll count on vdev %i: %d\n",
5799 arvif->vdev_id, ret);
5800 return ret;
5801 }
5802
Michal Kaziorb0e56152015-01-24 12:14:52 +02005803 if (test_bit(WMI_SERVICE_STA_UAPSD_BASIC_AUTO_TRIG, ar->wmi.svc_map) ||
5804 test_bit(WMI_SERVICE_STA_UAPSD_VAR_AUTO_TRIG, ar->wmi.svc_map)) {
5805 /* Only userspace can make an educated decision when to send
5806 * trigger frame. The following effectively disables u-UAPSD
5807 * autotrigger in firmware (which is enabled by default
5808 * provided the autotrigger service is available).
5809 */
5810
5811 arg.wmm_ac = acc;
5812 arg.user_priority = prio;
5813 arg.service_interval = 0;
5814 arg.suspend_interval = WMI_STA_UAPSD_MAX_INTERVAL_MSEC;
5815 arg.delay_interval = WMI_STA_UAPSD_MAX_INTERVAL_MSEC;
5816
5817 ret = ath10k_wmi_vdev_sta_uapsd(ar, arvif->vdev_id,
5818 arvif->bssid, &arg, 1);
5819 if (ret) {
5820 ath10k_warn(ar, "failed to set uapsd auto trigger %d\n",
5821 ret);
5822 return ret;
5823 }
5824 }
5825
Kalle Valo5e3dd152013-06-12 20:52:10 +03005826exit:
5827 return ret;
5828}
5829
5830static int ath10k_conf_tx(struct ieee80211_hw *hw,
5831 struct ieee80211_vif *vif, u16 ac,
5832 const struct ieee80211_tx_queue_params *params)
5833{
5834 struct ath10k *ar = hw->priv;
Michal Kazior5e752e42015-01-19 09:53:41 +01005835 struct ath10k_vif *arvif = ath10k_vif_to_arvif(vif);
Kalle Valo5e3dd152013-06-12 20:52:10 +03005836 struct wmi_wmm_params_arg *p = NULL;
5837 int ret;
5838
5839 mutex_lock(&ar->conf_mutex);
5840
5841 switch (ac) {
5842 case IEEE80211_AC_VO:
Michal Kazior5e752e42015-01-19 09:53:41 +01005843 p = &arvif->wmm_params.ac_vo;
Kalle Valo5e3dd152013-06-12 20:52:10 +03005844 break;
5845 case IEEE80211_AC_VI:
Michal Kazior5e752e42015-01-19 09:53:41 +01005846 p = &arvif->wmm_params.ac_vi;
Kalle Valo5e3dd152013-06-12 20:52:10 +03005847 break;
5848 case IEEE80211_AC_BE:
Michal Kazior5e752e42015-01-19 09:53:41 +01005849 p = &arvif->wmm_params.ac_be;
Kalle Valo5e3dd152013-06-12 20:52:10 +03005850 break;
5851 case IEEE80211_AC_BK:
Michal Kazior5e752e42015-01-19 09:53:41 +01005852 p = &arvif->wmm_params.ac_bk;
Kalle Valo5e3dd152013-06-12 20:52:10 +03005853 break;
5854 }
5855
5856 if (WARN_ON(!p)) {
5857 ret = -EINVAL;
5858 goto exit;
5859 }
5860
5861 p->cwmin = params->cw_min;
5862 p->cwmax = params->cw_max;
5863 p->aifs = params->aifs;
5864
5865 /*
5866 * The channel time duration programmed in the HW is in absolute
5867 * microseconds, while mac80211 gives the txop in units of
5868 * 32 microseconds.
5869 */
5870 p->txop = params->txop * 32;
5871
Michal Kazior7fc979a2015-01-28 09:57:28 +02005872 if (ar->wmi.ops->gen_vdev_wmm_conf) {
5873 ret = ath10k_wmi_vdev_wmm_conf(ar, arvif->vdev_id,
5874 &arvif->wmm_params);
5875 if (ret) {
5876 ath10k_warn(ar, "failed to set vdev wmm params on vdev %i: %d\n",
5877 arvif->vdev_id, ret);
5878 goto exit;
5879 }
5880 } else {
5881 /* This won't work well with multi-interface cases but it's
5882 * better than nothing.
5883 */
5884 ret = ath10k_wmi_pdev_set_wmm_params(ar, &arvif->wmm_params);
5885 if (ret) {
5886 ath10k_warn(ar, "failed to set wmm params: %d\n", ret);
5887 goto exit;
5888 }
Kalle Valo5e3dd152013-06-12 20:52:10 +03005889 }
5890
5891 ret = ath10k_conf_tx_uapsd(ar, vif, ac, params->uapsd);
5892 if (ret)
Michal Kazior7aa7a722014-08-25 12:09:38 +02005893 ath10k_warn(ar, "failed to set sta uapsd: %d\n", ret);
Kalle Valo5e3dd152013-06-12 20:52:10 +03005894
5895exit:
5896 mutex_unlock(&ar->conf_mutex);
5897 return ret;
5898}
5899
5900#define ATH10K_ROC_TIMEOUT_HZ (2*HZ)
5901
5902static int ath10k_remain_on_channel(struct ieee80211_hw *hw,
5903 struct ieee80211_vif *vif,
5904 struct ieee80211_channel *chan,
5905 int duration,
5906 enum ieee80211_roc_type type)
5907{
5908 struct ath10k *ar = hw->priv;
5909 struct ath10k_vif *arvif = ath10k_vif_to_arvif(vif);
5910 struct wmi_start_scan_arg arg;
Michal Kazior5c81c7f2014-08-05 14:54:44 +02005911 int ret = 0;
Michal Kaziorfcf98442015-03-31 11:03:47 +00005912 u32 scan_time_msec;
Kalle Valo5e3dd152013-06-12 20:52:10 +03005913
5914 mutex_lock(&ar->conf_mutex);
5915
5916 spin_lock_bh(&ar->data_lock);
Michal Kazior5c81c7f2014-08-05 14:54:44 +02005917 switch (ar->scan.state) {
5918 case ATH10K_SCAN_IDLE:
5919 reinit_completion(&ar->scan.started);
5920 reinit_completion(&ar->scan.completed);
5921 reinit_completion(&ar->scan.on_channel);
5922 ar->scan.state = ATH10K_SCAN_STARTING;
5923 ar->scan.is_roc = true;
5924 ar->scan.vdev_id = arvif->vdev_id;
5925 ar->scan.roc_freq = chan->center_freq;
Michal Kaziord710e752015-07-09 13:08:36 +02005926 ar->scan.roc_notify = true;
Michal Kazior5c81c7f2014-08-05 14:54:44 +02005927 ret = 0;
5928 break;
5929 case ATH10K_SCAN_STARTING:
5930 case ATH10K_SCAN_RUNNING:
5931 case ATH10K_SCAN_ABORTING:
Kalle Valo5e3dd152013-06-12 20:52:10 +03005932 ret = -EBUSY;
Michal Kazior5c81c7f2014-08-05 14:54:44 +02005933 break;
Kalle Valo5e3dd152013-06-12 20:52:10 +03005934 }
Kalle Valo5e3dd152013-06-12 20:52:10 +03005935 spin_unlock_bh(&ar->data_lock);
5936
Michal Kazior5c81c7f2014-08-05 14:54:44 +02005937 if (ret)
5938 goto exit;
5939
Michal Kaziorfcf98442015-03-31 11:03:47 +00005940 scan_time_msec = ar->hw->wiphy->max_remain_on_channel_duration * 2;
Michal Kaziordcca0bd2014-11-24 14:58:32 +01005941
Kalle Valo5e3dd152013-06-12 20:52:10 +03005942 memset(&arg, 0, sizeof(arg));
5943 ath10k_wmi_start_scan_init(ar, &arg);
5944 arg.vdev_id = arvif->vdev_id;
5945 arg.scan_id = ATH10K_SCAN_ID;
5946 arg.n_channels = 1;
5947 arg.channels[0] = chan->center_freq;
Michal Kaziorfcf98442015-03-31 11:03:47 +00005948 arg.dwell_time_active = scan_time_msec;
5949 arg.dwell_time_passive = scan_time_msec;
5950 arg.max_scan_time = scan_time_msec;
Kalle Valo5e3dd152013-06-12 20:52:10 +03005951 arg.scan_ctrl_flags |= WMI_SCAN_FLAG_PASSIVE;
5952 arg.scan_ctrl_flags |= WMI_SCAN_FILTER_PROBE_REQ;
Michal Kaziordbd3f9f2015-03-31 11:03:48 +00005953 arg.burst_duration_ms = duration;
Kalle Valo5e3dd152013-06-12 20:52:10 +03005954
5955 ret = ath10k_start_scan(ar, &arg);
5956 if (ret) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02005957 ath10k_warn(ar, "failed to start roc scan: %d\n", ret);
Kalle Valo5e3dd152013-06-12 20:52:10 +03005958 spin_lock_bh(&ar->data_lock);
Michal Kazior5c81c7f2014-08-05 14:54:44 +02005959 ar->scan.state = ATH10K_SCAN_IDLE;
Kalle Valo5e3dd152013-06-12 20:52:10 +03005960 spin_unlock_bh(&ar->data_lock);
5961 goto exit;
5962 }
5963
5964 ret = wait_for_completion_timeout(&ar->scan.on_channel, 3*HZ);
5965 if (ret == 0) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02005966 ath10k_warn(ar, "failed to switch to channel for roc scan\n");
Michal Kazior5c81c7f2014-08-05 14:54:44 +02005967
5968 ret = ath10k_scan_stop(ar);
5969 if (ret)
Michal Kazior7aa7a722014-08-25 12:09:38 +02005970 ath10k_warn(ar, "failed to stop scan: %d\n", ret);
Michal Kazior5c81c7f2014-08-05 14:54:44 +02005971
Kalle Valo5e3dd152013-06-12 20:52:10 +03005972 ret = -ETIMEDOUT;
5973 goto exit;
5974 }
5975
Michal Kaziorfcf98442015-03-31 11:03:47 +00005976 ieee80211_queue_delayed_work(ar->hw, &ar->scan.timeout,
5977 msecs_to_jiffies(duration));
5978
Kalle Valo5e3dd152013-06-12 20:52:10 +03005979 ret = 0;
5980exit:
5981 mutex_unlock(&ar->conf_mutex);
5982 return ret;
5983}
5984
5985static int ath10k_cancel_remain_on_channel(struct ieee80211_hw *hw)
5986{
5987 struct ath10k *ar = hw->priv;
5988
5989 mutex_lock(&ar->conf_mutex);
Michal Kaziord710e752015-07-09 13:08:36 +02005990
5991 spin_lock_bh(&ar->data_lock);
5992 ar->scan.roc_notify = false;
5993 spin_unlock_bh(&ar->data_lock);
5994
Michal Kazior5c81c7f2014-08-05 14:54:44 +02005995 ath10k_scan_abort(ar);
Michal Kaziord710e752015-07-09 13:08:36 +02005996
Kalle Valo5e3dd152013-06-12 20:52:10 +03005997 mutex_unlock(&ar->conf_mutex);
5998
Michal Kazior4eb2e162014-10-28 10:23:09 +01005999 cancel_delayed_work_sync(&ar->scan.timeout);
6000
Kalle Valo5e3dd152013-06-12 20:52:10 +03006001 return 0;
6002}
6003
6004/*
6005 * Both RTS and Fragmentation threshold are interface-specific
6006 * in ath10k, but device-specific in mac80211.
6007 */
Kalle Valo5e3dd152013-06-12 20:52:10 +03006008
6009static int ath10k_set_rts_threshold(struct ieee80211_hw *hw, u32 value)
6010{
Kalle Valo5e3dd152013-06-12 20:52:10 +03006011 struct ath10k *ar = hw->priv;
Michal Kaziorad088bf2013-10-16 15:44:46 +03006012 struct ath10k_vif *arvif;
6013 int ret = 0;
Michal Kazior548db542013-07-05 16:15:15 +03006014
Michal Kaziorad088bf2013-10-16 15:44:46 +03006015 mutex_lock(&ar->conf_mutex);
6016 list_for_each_entry(arvif, &ar->arvifs, list) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02006017 ath10k_dbg(ar, ATH10K_DBG_MAC, "mac vdev %d rts threshold %d\n",
Michal Kaziorad088bf2013-10-16 15:44:46 +03006018 arvif->vdev_id, value);
Kalle Valo60c3daa2013-09-08 17:56:07 +03006019
Michal Kaziorad088bf2013-10-16 15:44:46 +03006020 ret = ath10k_mac_set_rts(arvif, value);
6021 if (ret) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02006022 ath10k_warn(ar, "failed to set rts threshold for vdev %d: %d\n",
Michal Kaziorad088bf2013-10-16 15:44:46 +03006023 arvif->vdev_id, ret);
6024 break;
6025 }
6026 }
6027 mutex_unlock(&ar->conf_mutex);
6028
6029 return ret;
Kalle Valo5e3dd152013-06-12 20:52:10 +03006030}
6031
Michal Kazior92092fe2015-08-03 11:16:43 +02006032static int ath10k_mac_op_set_frag_threshold(struct ieee80211_hw *hw, u32 value)
6033{
6034 /* Even though there's a WMI enum for fragmentation threshold no known
6035 * firmware actually implements it. Moreover it is not possible to rely
6036 * frame fragmentation to mac80211 because firmware clears the "more
6037 * fragments" bit in frame control making it impossible for remote
6038 * devices to reassemble frames.
6039 *
6040 * Hence implement a dummy callback just to say fragmentation isn't
6041 * supported. This effectively prevents mac80211 from doing frame
6042 * fragmentation in software.
6043 */
6044 return -EOPNOTSUPP;
6045}
6046
Emmanuel Grumbach77be2c52014-03-27 11:30:29 +02006047static void ath10k_flush(struct ieee80211_hw *hw, struct ieee80211_vif *vif,
6048 u32 queues, bool drop)
Kalle Valo5e3dd152013-06-12 20:52:10 +03006049{
6050 struct ath10k *ar = hw->priv;
Michal Kazioraffd3212013-07-16 09:54:35 +02006051 bool skip;
Nicholas Mc Guired4298a32015-06-15 14:46:43 +03006052 long time_left;
Kalle Valo5e3dd152013-06-12 20:52:10 +03006053
6054 /* mac80211 doesn't care if we really xmit queued frames or not
6055 * we'll collect those frames either way if we stop/delete vdevs */
6056 if (drop)
6057 return;
6058
Michal Kazior548db542013-07-05 16:15:15 +03006059 mutex_lock(&ar->conf_mutex);
6060
Michal Kazioraffd3212013-07-16 09:54:35 +02006061 if (ar->state == ATH10K_STATE_WEDGED)
6062 goto skip;
6063
Nicholas Mc Guired4298a32015-06-15 14:46:43 +03006064 time_left = wait_event_timeout(ar->htt.empty_tx_wq, ({
Kalle Valo5e3dd152013-06-12 20:52:10 +03006065 bool empty;
Michal Kazioraffd3212013-07-16 09:54:35 +02006066
Michal Kazioredb82362013-07-05 16:15:14 +03006067 spin_lock_bh(&ar->htt.tx_lock);
Michal Kazior0945baf2013-09-18 14:43:18 +02006068 empty = (ar->htt.num_pending_tx == 0);
Michal Kazioredb82362013-07-05 16:15:14 +03006069 spin_unlock_bh(&ar->htt.tx_lock);
Michal Kazioraffd3212013-07-16 09:54:35 +02006070
Michal Kazior7962b0d2014-10-28 10:34:38 +01006071 skip = (ar->state == ATH10K_STATE_WEDGED) ||
6072 test_bit(ATH10K_FLAG_CRASH_FLUSH,
6073 &ar->dev_flags);
Michal Kazioraffd3212013-07-16 09:54:35 +02006074
6075 (empty || skip);
Kalle Valo5e3dd152013-06-12 20:52:10 +03006076 }), ATH10K_FLUSH_TIMEOUT_HZ);
Michal Kazioraffd3212013-07-16 09:54:35 +02006077
Nicholas Mc Guired4298a32015-06-15 14:46:43 +03006078 if (time_left == 0 || skip)
6079 ath10k_warn(ar, "failed to flush transmit queue (skip %i ar-state %i): %ld\n",
6080 skip, ar->state, time_left);
Michal Kazior548db542013-07-05 16:15:15 +03006081
Michal Kazioraffd3212013-07-16 09:54:35 +02006082skip:
Michal Kazior548db542013-07-05 16:15:15 +03006083 mutex_unlock(&ar->conf_mutex);
Kalle Valo5e3dd152013-06-12 20:52:10 +03006084}
6085
6086/* TODO: Implement this function properly
6087 * For now it is needed to reply to Probe Requests in IBSS mode.
6088 * Propably we need this information from FW.
6089 */
6090static int ath10k_tx_last_beacon(struct ieee80211_hw *hw)
6091{
6092 return 1;
6093}
6094
Eliad Pellercf2c92d2014-11-04 11:43:54 +02006095static void ath10k_reconfig_complete(struct ieee80211_hw *hw,
6096 enum ieee80211_reconfig_type reconfig_type)
Michal Kazioraffd3212013-07-16 09:54:35 +02006097{
6098 struct ath10k *ar = hw->priv;
6099
Eliad Pellercf2c92d2014-11-04 11:43:54 +02006100 if (reconfig_type != IEEE80211_RECONFIG_TYPE_RESTART)
6101 return;
6102
Michal Kazioraffd3212013-07-16 09:54:35 +02006103 mutex_lock(&ar->conf_mutex);
6104
6105 /* If device failed to restart it will be in a different state, e.g.
6106 * ATH10K_STATE_WEDGED */
6107 if (ar->state == ATH10K_STATE_RESTARTED) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02006108 ath10k_info(ar, "device successfully recovered\n");
Michal Kazioraffd3212013-07-16 09:54:35 +02006109 ar->state = ATH10K_STATE_ON;
Michal Kazior7962b0d2014-10-28 10:34:38 +01006110 ieee80211_wake_queues(ar->hw);
Michal Kazioraffd3212013-07-16 09:54:35 +02006111 }
6112
6113 mutex_unlock(&ar->conf_mutex);
6114}
6115
Michal Kazior2e1dea42013-07-31 10:32:40 +02006116static int ath10k_get_survey(struct ieee80211_hw *hw, int idx,
6117 struct survey_info *survey)
6118{
6119 struct ath10k *ar = hw->priv;
6120 struct ieee80211_supported_band *sband;
6121 struct survey_info *ar_survey = &ar->survey[idx];
6122 int ret = 0;
6123
6124 mutex_lock(&ar->conf_mutex);
6125
6126 sband = hw->wiphy->bands[IEEE80211_BAND_2GHZ];
6127 if (sband && idx >= sband->n_channels) {
6128 idx -= sband->n_channels;
6129 sband = NULL;
6130 }
6131
6132 if (!sband)
6133 sband = hw->wiphy->bands[IEEE80211_BAND_5GHZ];
6134
6135 if (!sband || idx >= sband->n_channels) {
6136 ret = -ENOENT;
6137 goto exit;
6138 }
6139
6140 spin_lock_bh(&ar->data_lock);
6141 memcpy(survey, ar_survey, sizeof(*survey));
6142 spin_unlock_bh(&ar->data_lock);
6143
6144 survey->channel = &sband->channels[idx];
6145
Felix Fietkaufa1d4df2014-10-23 17:04:28 +03006146 if (ar->rx_channel == survey->channel)
6147 survey->filled |= SURVEY_INFO_IN_USE;
6148
Michal Kazior2e1dea42013-07-31 10:32:40 +02006149exit:
6150 mutex_unlock(&ar->conf_mutex);
6151 return ret;
6152}
6153
Michal Kazior3ae54222015-03-31 10:49:20 +00006154static bool
6155ath10k_mac_bitrate_mask_has_single_rate(struct ath10k *ar,
6156 enum ieee80211_band band,
6157 const struct cfg80211_bitrate_mask *mask)
Janusz Dziedzic51ab1a02014-01-08 09:08:33 +01006158{
Michal Kazior3ae54222015-03-31 10:49:20 +00006159 int num_rates = 0;
6160 int i;
Janusz Dziedzic51ab1a02014-01-08 09:08:33 +01006161
Michal Kazior3ae54222015-03-31 10:49:20 +00006162 num_rates += hweight32(mask->control[band].legacy);
6163
6164 for (i = 0; i < ARRAY_SIZE(mask->control[band].ht_mcs); i++)
6165 num_rates += hweight8(mask->control[band].ht_mcs[i]);
6166
6167 for (i = 0; i < ARRAY_SIZE(mask->control[band].vht_mcs); i++)
6168 num_rates += hweight16(mask->control[band].vht_mcs[i]);
6169
6170 return num_rates == 1;
6171}
6172
6173static bool
6174ath10k_mac_bitrate_mask_get_single_nss(struct ath10k *ar,
6175 enum ieee80211_band band,
6176 const struct cfg80211_bitrate_mask *mask,
6177 int *nss)
6178{
6179 struct ieee80211_supported_band *sband = &ar->mac.sbands[band];
6180 u16 vht_mcs_map = le16_to_cpu(sband->vht_cap.vht_mcs.tx_mcs_map);
6181 u8 ht_nss_mask = 0;
6182 u8 vht_nss_mask = 0;
6183 int i;
6184
6185 if (mask->control[band].legacy)
6186 return false;
6187
6188 for (i = 0; i < ARRAY_SIZE(mask->control[band].ht_mcs); i++) {
6189 if (mask->control[band].ht_mcs[i] == 0)
6190 continue;
6191 else if (mask->control[band].ht_mcs[i] ==
6192 sband->ht_cap.mcs.rx_mask[i])
6193 ht_nss_mask |= BIT(i);
6194 else
6195 return false;
6196 }
6197
6198 for (i = 0; i < ARRAY_SIZE(mask->control[band].vht_mcs); i++) {
6199 if (mask->control[band].vht_mcs[i] == 0)
6200 continue;
6201 else if (mask->control[band].vht_mcs[i] ==
6202 ath10k_mac_get_max_vht_mcs_map(vht_mcs_map, i))
6203 vht_nss_mask |= BIT(i);
6204 else
6205 return false;
6206 }
6207
6208 if (ht_nss_mask != vht_nss_mask)
6209 return false;
6210
6211 if (ht_nss_mask == 0)
6212 return false;
6213
6214 if (BIT(fls(ht_nss_mask)) - 1 != ht_nss_mask)
6215 return false;
6216
6217 *nss = fls(ht_nss_mask);
6218
6219 return true;
6220}
6221
6222static int
6223ath10k_mac_bitrate_mask_get_single_rate(struct ath10k *ar,
6224 enum ieee80211_band band,
6225 const struct cfg80211_bitrate_mask *mask,
6226 u8 *rate, u8 *nss)
6227{
6228 struct ieee80211_supported_band *sband = &ar->mac.sbands[band];
6229 int rate_idx;
6230 int i;
6231 u16 bitrate;
6232 u8 preamble;
6233 u8 hw_rate;
6234
6235 if (hweight32(mask->control[band].legacy) == 1) {
6236 rate_idx = ffs(mask->control[band].legacy) - 1;
6237
6238 hw_rate = sband->bitrates[rate_idx].hw_value;
6239 bitrate = sband->bitrates[rate_idx].bitrate;
6240
6241 if (ath10k_mac_bitrate_is_cck(bitrate))
6242 preamble = WMI_RATE_PREAMBLE_CCK;
6243 else
6244 preamble = WMI_RATE_PREAMBLE_OFDM;
6245
6246 *nss = 1;
6247 *rate = preamble << 6 |
6248 (*nss - 1) << 4 |
6249 hw_rate << 0;
6250
Janusz Dziedzic51ab1a02014-01-08 09:08:33 +01006251 return 0;
Janusz Dziedzic51ab1a02014-01-08 09:08:33 +01006252 }
6253
Michal Kazior3ae54222015-03-31 10:49:20 +00006254 for (i = 0; i < ARRAY_SIZE(mask->control[band].ht_mcs); i++) {
6255 if (hweight8(mask->control[band].ht_mcs[i]) == 1) {
6256 *nss = i + 1;
6257 *rate = WMI_RATE_PREAMBLE_HT << 6 |
6258 (*nss - 1) << 4 |
6259 (ffs(mask->control[band].ht_mcs[i]) - 1);
Janusz Dziedzic51ab1a02014-01-08 09:08:33 +01006260
Michal Kazior3ae54222015-03-31 10:49:20 +00006261 return 0;
6262 }
Janusz Dziedzic51ab1a02014-01-08 09:08:33 +01006263 }
6264
Michal Kazior3ae54222015-03-31 10:49:20 +00006265 for (i = 0; i < ARRAY_SIZE(mask->control[band].vht_mcs); i++) {
6266 if (hweight16(mask->control[band].vht_mcs[i]) == 1) {
6267 *nss = i + 1;
6268 *rate = WMI_RATE_PREAMBLE_VHT << 6 |
6269 (*nss - 1) << 4 |
6270 (ffs(mask->control[band].vht_mcs[i]) - 1);
Janusz Dziedzic51ab1a02014-01-08 09:08:33 +01006271
Michal Kazior3ae54222015-03-31 10:49:20 +00006272 return 0;
6273 }
Janusz Dziedzic51ab1a02014-01-08 09:08:33 +01006274 }
6275
Michal Kazior3ae54222015-03-31 10:49:20 +00006276 return -EINVAL;
Janusz Dziedzic51ab1a02014-01-08 09:08:33 +01006277}
6278
Michal Kazior3ae54222015-03-31 10:49:20 +00006279static int ath10k_mac_set_fixed_rate_params(struct ath10k_vif *arvif,
Rajkumar Manoharanbd4a41e2015-09-16 13:19:00 +05306280 u8 rate, u8 nss, u8 sgi, u8 ldpc)
Janusz Dziedzic51ab1a02014-01-08 09:08:33 +01006281{
6282 struct ath10k *ar = arvif->ar;
6283 u32 vdev_param;
Michal Kazior3ae54222015-03-31 10:49:20 +00006284 int ret;
Janusz Dziedzic51ab1a02014-01-08 09:08:33 +01006285
Michal Kazior3ae54222015-03-31 10:49:20 +00006286 lockdep_assert_held(&ar->conf_mutex);
Janusz Dziedzic51ab1a02014-01-08 09:08:33 +01006287
Michal Kazior3ae54222015-03-31 10:49:20 +00006288 ath10k_dbg(ar, ATH10K_DBG_MAC, "mac set fixed rate params vdev %i rate 0x%02hhx nss %hhu sgi %hhu\n",
6289 arvif->vdev_id, rate, nss, sgi);
Janusz Dziedzic9f81f722014-01-17 20:04:14 +01006290
Janusz Dziedzic51ab1a02014-01-08 09:08:33 +01006291 vdev_param = ar->wmi.vdev_param->fixed_rate;
Michal Kazior3ae54222015-03-31 10:49:20 +00006292 ret = ath10k_wmi_vdev_set_param(ar, arvif->vdev_id, vdev_param, rate);
Janusz Dziedzic51ab1a02014-01-08 09:08:33 +01006293 if (ret) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02006294 ath10k_warn(ar, "failed to set fixed rate param 0x%02x: %d\n",
Michal Kazior3ae54222015-03-31 10:49:20 +00006295 rate, ret);
6296 return ret;
Janusz Dziedzic51ab1a02014-01-08 09:08:33 +01006297 }
6298
Janusz Dziedzic51ab1a02014-01-08 09:08:33 +01006299 vdev_param = ar->wmi.vdev_param->nss;
Michal Kazior3ae54222015-03-31 10:49:20 +00006300 ret = ath10k_wmi_vdev_set_param(ar, arvif->vdev_id, vdev_param, nss);
Janusz Dziedzic51ab1a02014-01-08 09:08:33 +01006301 if (ret) {
Michal Kazior3ae54222015-03-31 10:49:20 +00006302 ath10k_warn(ar, "failed to set nss param %d: %d\n", nss, ret);
6303 return ret;
Janusz Dziedzic51ab1a02014-01-08 09:08:33 +01006304 }
6305
Janusz Dziedzic9f81f722014-01-17 20:04:14 +01006306 vdev_param = ar->wmi.vdev_param->sgi;
Michal Kazior3ae54222015-03-31 10:49:20 +00006307 ret = ath10k_wmi_vdev_set_param(ar, arvif->vdev_id, vdev_param, sgi);
Janusz Dziedzic9f81f722014-01-17 20:04:14 +01006308 if (ret) {
Michal Kazior3ae54222015-03-31 10:49:20 +00006309 ath10k_warn(ar, "failed to set sgi param %d: %d\n", sgi, ret);
6310 return ret;
Janusz Dziedzic9f81f722014-01-17 20:04:14 +01006311 }
6312
Rajkumar Manoharanbd4a41e2015-09-16 13:19:00 +05306313 vdev_param = ar->wmi.vdev_param->ldpc;
6314 ret = ath10k_wmi_vdev_set_param(ar, arvif->vdev_id, vdev_param, ldpc);
6315 if (ret) {
6316 ath10k_warn(ar, "failed to set ldpc param %d: %d\n", ldpc, ret);
6317 return ret;
6318 }
6319
Michal Kazior3ae54222015-03-31 10:49:20 +00006320 return 0;
Janusz Dziedzic51ab1a02014-01-08 09:08:33 +01006321}
6322
Michal Kazior45c9abc2015-04-21 20:42:58 +03006323static bool
6324ath10k_mac_can_set_bitrate_mask(struct ath10k *ar,
6325 enum ieee80211_band band,
6326 const struct cfg80211_bitrate_mask *mask)
6327{
6328 int i;
6329 u16 vht_mcs;
6330
6331 /* Due to firmware limitation in WMI_PEER_ASSOC_CMDID it is impossible
6332 * to express all VHT MCS rate masks. Effectively only the following
6333 * ranges can be used: none, 0-7, 0-8 and 0-9.
6334 */
6335 for (i = 0; i < NL80211_VHT_NSS_MAX; i++) {
6336 vht_mcs = mask->control[band].vht_mcs[i];
6337
6338 switch (vht_mcs) {
6339 case 0:
6340 case BIT(8) - 1:
6341 case BIT(9) - 1:
6342 case BIT(10) - 1:
6343 break;
6344 default:
6345 ath10k_warn(ar, "refusing bitrate mask with missing 0-7 VHT MCS rates\n");
6346 return false;
6347 }
6348 }
6349
6350 return true;
6351}
6352
6353static void ath10k_mac_set_bitrate_mask_iter(void *data,
6354 struct ieee80211_sta *sta)
6355{
6356 struct ath10k_vif *arvif = data;
6357 struct ath10k_sta *arsta = (struct ath10k_sta *)sta->drv_priv;
6358 struct ath10k *ar = arvif->ar;
6359
6360 if (arsta->arvif != arvif)
6361 return;
6362
6363 spin_lock_bh(&ar->data_lock);
6364 arsta->changed |= IEEE80211_RC_SUPP_RATES_CHANGED;
6365 spin_unlock_bh(&ar->data_lock);
6366
6367 ieee80211_queue_work(ar->hw, &arsta->update_wk);
6368}
6369
Michal Kazior3ae54222015-03-31 10:49:20 +00006370static int ath10k_mac_op_set_bitrate_mask(struct ieee80211_hw *hw,
6371 struct ieee80211_vif *vif,
6372 const struct cfg80211_bitrate_mask *mask)
Janusz Dziedzic51ab1a02014-01-08 09:08:33 +01006373{
6374 struct ath10k_vif *arvif = ath10k_vif_to_arvif(vif);
Michal Kazior500ff9f2015-03-31 10:26:21 +00006375 struct cfg80211_chan_def def;
Janusz Dziedzic51ab1a02014-01-08 09:08:33 +01006376 struct ath10k *ar = arvif->ar;
Michal Kazior500ff9f2015-03-31 10:26:21 +00006377 enum ieee80211_band band;
Michal Kazior45c9abc2015-04-21 20:42:58 +03006378 const u8 *ht_mcs_mask;
6379 const u16 *vht_mcs_mask;
Michal Kazior3ae54222015-03-31 10:49:20 +00006380 u8 rate;
6381 u8 nss;
6382 u8 sgi;
Rajkumar Manoharanbd4a41e2015-09-16 13:19:00 +05306383 u8 ldpc;
Michal Kazior3ae54222015-03-31 10:49:20 +00006384 int single_nss;
6385 int ret;
Janusz Dziedzic9f81f722014-01-17 20:04:14 +01006386
Michal Kazior500ff9f2015-03-31 10:26:21 +00006387 if (ath10k_mac_vif_chan(vif, &def))
6388 return -EPERM;
6389
Michal Kazior500ff9f2015-03-31 10:26:21 +00006390 band = def.chan->band;
Michal Kazior45c9abc2015-04-21 20:42:58 +03006391 ht_mcs_mask = mask->control[band].ht_mcs;
6392 vht_mcs_mask = mask->control[band].vht_mcs;
Rajkumar Manoharanbd4a41e2015-09-16 13:19:00 +05306393 ldpc = !!(ar->ht_cap_info & WMI_HT_CAP_LDPC);
Michal Kazior500ff9f2015-03-31 10:26:21 +00006394
Michal Kazior3ae54222015-03-31 10:49:20 +00006395 sgi = mask->control[band].gi;
6396 if (sgi == NL80211_TXRATE_FORCE_LGI)
Janusz Dziedzic9f81f722014-01-17 20:04:14 +01006397 return -EINVAL;
Janusz Dziedzic51ab1a02014-01-08 09:08:33 +01006398
Michal Kazior3ae54222015-03-31 10:49:20 +00006399 if (ath10k_mac_bitrate_mask_has_single_rate(ar, band, mask)) {
6400 ret = ath10k_mac_bitrate_mask_get_single_rate(ar, band, mask,
6401 &rate, &nss);
6402 if (ret) {
6403 ath10k_warn(ar, "failed to get single rate for vdev %i: %d\n",
6404 arvif->vdev_id, ret);
6405 return ret;
6406 }
6407 } else if (ath10k_mac_bitrate_mask_get_single_nss(ar, band, mask,
6408 &single_nss)) {
6409 rate = WMI_FIXED_RATE_NONE;
6410 nss = single_nss;
6411 } else {
6412 rate = WMI_FIXED_RATE_NONE;
Michal Kazior45c9abc2015-04-21 20:42:58 +03006413 nss = min(ar->num_rf_chains,
6414 max(ath10k_mac_max_ht_nss(ht_mcs_mask),
6415 ath10k_mac_max_vht_nss(vht_mcs_mask)));
6416
6417 if (!ath10k_mac_can_set_bitrate_mask(ar, band, mask))
6418 return -EINVAL;
6419
6420 mutex_lock(&ar->conf_mutex);
6421
6422 arvif->bitrate_mask = *mask;
6423 ieee80211_iterate_stations_atomic(ar->hw,
6424 ath10k_mac_set_bitrate_mask_iter,
6425 arvif);
6426
6427 mutex_unlock(&ar->conf_mutex);
Janusz Dziedzic51ab1a02014-01-08 09:08:33 +01006428 }
Janusz Dziedzic51ab1a02014-01-08 09:08:33 +01006429
6430 mutex_lock(&ar->conf_mutex);
6431
Rajkumar Manoharanbd4a41e2015-09-16 13:19:00 +05306432 ret = ath10k_mac_set_fixed_rate_params(arvif, rate, nss, sgi, ldpc);
Janusz Dziedzic51ab1a02014-01-08 09:08:33 +01006433 if (ret) {
Michal Kazior3ae54222015-03-31 10:49:20 +00006434 ath10k_warn(ar, "failed to set fixed rate params on vdev %i: %d\n",
6435 arvif->vdev_id, ret);
Janusz Dziedzic51ab1a02014-01-08 09:08:33 +01006436 goto exit;
6437 }
6438
Janusz Dziedzic51ab1a02014-01-08 09:08:33 +01006439exit:
6440 mutex_unlock(&ar->conf_mutex);
Michal Kazior3ae54222015-03-31 10:49:20 +00006441
Janusz Dziedzic51ab1a02014-01-08 09:08:33 +01006442 return ret;
6443}
6444
Michal Kazior9797feb2014-02-14 14:49:48 +01006445static void ath10k_sta_rc_update(struct ieee80211_hw *hw,
6446 struct ieee80211_vif *vif,
6447 struct ieee80211_sta *sta,
6448 u32 changed)
6449{
6450 struct ath10k *ar = hw->priv;
6451 struct ath10k_sta *arsta = (struct ath10k_sta *)sta->drv_priv;
6452 u32 bw, smps;
6453
6454 spin_lock_bh(&ar->data_lock);
6455
Michal Kazior7aa7a722014-08-25 12:09:38 +02006456 ath10k_dbg(ar, ATH10K_DBG_MAC,
Michal Kazior9797feb2014-02-14 14:49:48 +01006457 "mac sta rc update for %pM changed %08x bw %d nss %d smps %d\n",
6458 sta->addr, changed, sta->bandwidth, sta->rx_nss,
6459 sta->smps_mode);
6460
6461 if (changed & IEEE80211_RC_BW_CHANGED) {
6462 bw = WMI_PEER_CHWIDTH_20MHZ;
6463
6464 switch (sta->bandwidth) {
6465 case IEEE80211_STA_RX_BW_20:
6466 bw = WMI_PEER_CHWIDTH_20MHZ;
6467 break;
6468 case IEEE80211_STA_RX_BW_40:
6469 bw = WMI_PEER_CHWIDTH_40MHZ;
6470 break;
6471 case IEEE80211_STA_RX_BW_80:
6472 bw = WMI_PEER_CHWIDTH_80MHZ;
6473 break;
6474 case IEEE80211_STA_RX_BW_160:
Masanari Iidad939be32015-02-27 23:52:31 +09006475 ath10k_warn(ar, "Invalid bandwidth %d in rc update for %pM\n",
Kalle Valobe6546f2014-03-25 14:18:51 +02006476 sta->bandwidth, sta->addr);
Michal Kazior9797feb2014-02-14 14:49:48 +01006477 bw = WMI_PEER_CHWIDTH_20MHZ;
6478 break;
6479 }
6480
6481 arsta->bw = bw;
6482 }
6483
6484 if (changed & IEEE80211_RC_NSS_CHANGED)
6485 arsta->nss = sta->rx_nss;
6486
6487 if (changed & IEEE80211_RC_SMPS_CHANGED) {
6488 smps = WMI_PEER_SMPS_PS_NONE;
6489
6490 switch (sta->smps_mode) {
6491 case IEEE80211_SMPS_AUTOMATIC:
6492 case IEEE80211_SMPS_OFF:
6493 smps = WMI_PEER_SMPS_PS_NONE;
6494 break;
6495 case IEEE80211_SMPS_STATIC:
6496 smps = WMI_PEER_SMPS_STATIC;
6497 break;
6498 case IEEE80211_SMPS_DYNAMIC:
6499 smps = WMI_PEER_SMPS_DYNAMIC;
6500 break;
6501 case IEEE80211_SMPS_NUM_MODES:
Michal Kazior7aa7a722014-08-25 12:09:38 +02006502 ath10k_warn(ar, "Invalid smps %d in sta rc update for %pM\n",
Kalle Valobe6546f2014-03-25 14:18:51 +02006503 sta->smps_mode, sta->addr);
Michal Kazior9797feb2014-02-14 14:49:48 +01006504 smps = WMI_PEER_SMPS_PS_NONE;
6505 break;
6506 }
6507
6508 arsta->smps = smps;
6509 }
6510
Michal Kazior9797feb2014-02-14 14:49:48 +01006511 arsta->changed |= changed;
6512
6513 spin_unlock_bh(&ar->data_lock);
6514
6515 ieee80211_queue_work(hw, &arsta->update_wk);
6516}
6517
Chun-Yeow Yeoh26ebbcc2014-02-25 09:29:54 +02006518static u64 ath10k_get_tsf(struct ieee80211_hw *hw, struct ieee80211_vif *vif)
6519{
6520 /*
6521 * FIXME: Return 0 for time being. Need to figure out whether FW
6522 * has the API to fetch 64-bit local TSF
6523 */
6524
6525 return 0;
6526}
6527
Michal Kazioraa5b4fb2014-07-23 12:20:33 +02006528static int ath10k_ampdu_action(struct ieee80211_hw *hw,
6529 struct ieee80211_vif *vif,
Sara Sharon50ea05e2015-12-30 16:06:04 +02006530 struct ieee80211_ampdu_params *params)
Michal Kazioraa5b4fb2014-07-23 12:20:33 +02006531{
Michal Kazior7aa7a722014-08-25 12:09:38 +02006532 struct ath10k *ar = hw->priv;
Michal Kazioraa5b4fb2014-07-23 12:20:33 +02006533 struct ath10k_vif *arvif = ath10k_vif_to_arvif(vif);
Sara Sharon50ea05e2015-12-30 16:06:04 +02006534 struct ieee80211_sta *sta = params->sta;
6535 enum ieee80211_ampdu_mlme_action action = params->action;
6536 u16 tid = params->tid;
Michal Kazioraa5b4fb2014-07-23 12:20:33 +02006537
Michal Kazior7aa7a722014-08-25 12:09:38 +02006538 ath10k_dbg(ar, ATH10K_DBG_MAC, "mac ampdu vdev_id %i sta %pM tid %hu action %d\n",
Michal Kazioraa5b4fb2014-07-23 12:20:33 +02006539 arvif->vdev_id, sta->addr, tid, action);
6540
6541 switch (action) {
6542 case IEEE80211_AMPDU_RX_START:
6543 case IEEE80211_AMPDU_RX_STOP:
6544 /* HTT AddBa/DelBa events trigger mac80211 Rx BA session
6545 * creation/removal. Do we need to verify this?
6546 */
6547 return 0;
6548 case IEEE80211_AMPDU_TX_START:
6549 case IEEE80211_AMPDU_TX_STOP_CONT:
6550 case IEEE80211_AMPDU_TX_STOP_FLUSH:
6551 case IEEE80211_AMPDU_TX_STOP_FLUSH_CONT:
6552 case IEEE80211_AMPDU_TX_OPERATIONAL:
6553 /* Firmware offloads Tx aggregation entirely so deny mac80211
6554 * Tx aggregation requests.
6555 */
6556 return -EOPNOTSUPP;
6557 }
6558
6559 return -EINVAL;
6560}
6561
Michal Kazior500ff9f2015-03-31 10:26:21 +00006562static void
Michal Kaziord7bf4b42015-06-03 12:16:54 +02006563ath10k_mac_update_rx_channel(struct ath10k *ar,
6564 struct ieee80211_chanctx_conf *ctx,
6565 struct ieee80211_vif_chanctx_switch *vifs,
6566 int n_vifs)
Michal Kazior500ff9f2015-03-31 10:26:21 +00006567{
6568 struct cfg80211_chan_def *def = NULL;
6569
6570 /* Both locks are required because ar->rx_channel is modified. This
6571 * allows readers to hold either lock.
6572 */
6573 lockdep_assert_held(&ar->conf_mutex);
6574 lockdep_assert_held(&ar->data_lock);
6575
Michal Kaziord7bf4b42015-06-03 12:16:54 +02006576 WARN_ON(ctx && vifs);
6577 WARN_ON(vifs && n_vifs != 1);
6578
Michal Kazior500ff9f2015-03-31 10:26:21 +00006579 /* FIXME: Sort of an optimization and a workaround. Peers and vifs are
6580 * on a linked list now. Doing a lookup peer -> vif -> chanctx for each
6581 * ppdu on Rx may reduce performance on low-end systems. It should be
6582 * possible to make tables/hashmaps to speed the lookup up (be vary of
6583 * cpu data cache lines though regarding sizes) but to keep the initial
6584 * implementation simple and less intrusive fallback to the slow lookup
6585 * only for multi-channel cases. Single-channel cases will remain to
6586 * use the old channel derival and thus performance should not be
6587 * affected much.
6588 */
6589 rcu_read_lock();
Michal Kaziord7bf4b42015-06-03 12:16:54 +02006590 if (!ctx && ath10k_mac_num_chanctxs(ar) == 1) {
Michal Kazior500ff9f2015-03-31 10:26:21 +00006591 ieee80211_iter_chan_contexts_atomic(ar->hw,
Kalle Valo617b0f42015-10-05 17:56:35 +03006592 ath10k_mac_get_any_chandef_iter,
6593 &def);
Michal Kaziord7bf4b42015-06-03 12:16:54 +02006594
6595 if (vifs)
6596 def = &vifs[0].new_ctx->def;
6597
Michal Kazior500ff9f2015-03-31 10:26:21 +00006598 ar->rx_channel = def->chan;
Michal Kaziord7bf4b42015-06-03 12:16:54 +02006599 } else if (ctx && ath10k_mac_num_chanctxs(ar) == 0) {
6600 ar->rx_channel = ctx->def.chan;
Michal Kazior500ff9f2015-03-31 10:26:21 +00006601 } else {
6602 ar->rx_channel = NULL;
6603 }
6604 rcu_read_unlock();
6605}
6606
Michal Kazior7be6d1b2015-09-03 10:44:51 +02006607static void
6608ath10k_mac_update_vif_chan(struct ath10k *ar,
6609 struct ieee80211_vif_chanctx_switch *vifs,
6610 int n_vifs)
6611{
6612 struct ath10k_vif *arvif;
6613 int ret;
6614 int i;
6615
6616 lockdep_assert_held(&ar->conf_mutex);
6617
6618 /* First stop monitor interface. Some FW versions crash if there's a
6619 * lone monitor interface.
6620 */
6621 if (ar->monitor_started)
6622 ath10k_monitor_stop(ar);
6623
6624 for (i = 0; i < n_vifs; i++) {
6625 arvif = ath10k_vif_to_arvif(vifs[i].vif);
6626
6627 ath10k_dbg(ar, ATH10K_DBG_MAC,
6628 "mac chanctx switch vdev_id %i freq %hu->%hu width %d->%d\n",
6629 arvif->vdev_id,
6630 vifs[i].old_ctx->def.chan->center_freq,
6631 vifs[i].new_ctx->def.chan->center_freq,
6632 vifs[i].old_ctx->def.width,
6633 vifs[i].new_ctx->def.width);
6634
6635 if (WARN_ON(!arvif->is_started))
6636 continue;
6637
6638 if (WARN_ON(!arvif->is_up))
6639 continue;
6640
6641 ret = ath10k_wmi_vdev_down(ar, arvif->vdev_id);
6642 if (ret) {
6643 ath10k_warn(ar, "failed to down vdev %d: %d\n",
6644 arvif->vdev_id, ret);
6645 continue;
6646 }
6647 }
6648
6649 /* All relevant vdevs are downed and associated channel resources
6650 * should be available for the channel switch now.
6651 */
6652
6653 spin_lock_bh(&ar->data_lock);
6654 ath10k_mac_update_rx_channel(ar, NULL, vifs, n_vifs);
6655 spin_unlock_bh(&ar->data_lock);
6656
6657 for (i = 0; i < n_vifs; i++) {
6658 arvif = ath10k_vif_to_arvif(vifs[i].vif);
6659
6660 if (WARN_ON(!arvif->is_started))
6661 continue;
6662
6663 if (WARN_ON(!arvif->is_up))
6664 continue;
6665
6666 ret = ath10k_mac_setup_bcn_tmpl(arvif);
6667 if (ret)
6668 ath10k_warn(ar, "failed to update bcn tmpl during csa: %d\n",
6669 ret);
6670
6671 ret = ath10k_mac_setup_prb_tmpl(arvif);
6672 if (ret)
6673 ath10k_warn(ar, "failed to update prb tmpl during csa: %d\n",
6674 ret);
6675
6676 ret = ath10k_vdev_restart(arvif, &vifs[i].new_ctx->def);
6677 if (ret) {
6678 ath10k_warn(ar, "failed to restart vdev %d: %d\n",
6679 arvif->vdev_id, ret);
6680 continue;
6681 }
6682
6683 ret = ath10k_wmi_vdev_up(arvif->ar, arvif->vdev_id, arvif->aid,
6684 arvif->bssid);
6685 if (ret) {
6686 ath10k_warn(ar, "failed to bring vdev up %d: %d\n",
6687 arvif->vdev_id, ret);
6688 continue;
6689 }
6690 }
6691
6692 ath10k_monitor_recalc(ar);
6693}
6694
Michal Kazior500ff9f2015-03-31 10:26:21 +00006695static int
6696ath10k_mac_op_add_chanctx(struct ieee80211_hw *hw,
6697 struct ieee80211_chanctx_conf *ctx)
6698{
6699 struct ath10k *ar = hw->priv;
Michal Kazior500ff9f2015-03-31 10:26:21 +00006700
6701 ath10k_dbg(ar, ATH10K_DBG_MAC,
6702 "mac chanctx add freq %hu width %d ptr %p\n",
6703 ctx->def.chan->center_freq, ctx->def.width, ctx);
6704
6705 mutex_lock(&ar->conf_mutex);
6706
6707 spin_lock_bh(&ar->data_lock);
Michal Kaziord7bf4b42015-06-03 12:16:54 +02006708 ath10k_mac_update_rx_channel(ar, ctx, NULL, 0);
Michal Kazior500ff9f2015-03-31 10:26:21 +00006709 spin_unlock_bh(&ar->data_lock);
6710
6711 ath10k_recalc_radar_detection(ar);
6712 ath10k_monitor_recalc(ar);
6713
6714 mutex_unlock(&ar->conf_mutex);
6715
6716 return 0;
6717}
6718
6719static void
6720ath10k_mac_op_remove_chanctx(struct ieee80211_hw *hw,
6721 struct ieee80211_chanctx_conf *ctx)
6722{
6723 struct ath10k *ar = hw->priv;
6724
6725 ath10k_dbg(ar, ATH10K_DBG_MAC,
6726 "mac chanctx remove freq %hu width %d ptr %p\n",
6727 ctx->def.chan->center_freq, ctx->def.width, ctx);
6728
6729 mutex_lock(&ar->conf_mutex);
6730
6731 spin_lock_bh(&ar->data_lock);
Michal Kaziord7bf4b42015-06-03 12:16:54 +02006732 ath10k_mac_update_rx_channel(ar, NULL, NULL, 0);
Michal Kazior500ff9f2015-03-31 10:26:21 +00006733 spin_unlock_bh(&ar->data_lock);
6734
6735 ath10k_recalc_radar_detection(ar);
6736 ath10k_monitor_recalc(ar);
6737
6738 mutex_unlock(&ar->conf_mutex);
6739}
6740
Michal Kazior9713e3d2015-09-03 10:44:52 +02006741struct ath10k_mac_change_chanctx_arg {
6742 struct ieee80211_chanctx_conf *ctx;
6743 struct ieee80211_vif_chanctx_switch *vifs;
6744 int n_vifs;
6745 int next_vif;
6746};
6747
6748static void
6749ath10k_mac_change_chanctx_cnt_iter(void *data, u8 *mac,
6750 struct ieee80211_vif *vif)
6751{
6752 struct ath10k_mac_change_chanctx_arg *arg = data;
6753
6754 if (rcu_access_pointer(vif->chanctx_conf) != arg->ctx)
6755 return;
6756
6757 arg->n_vifs++;
6758}
6759
6760static void
6761ath10k_mac_change_chanctx_fill_iter(void *data, u8 *mac,
6762 struct ieee80211_vif *vif)
6763{
6764 struct ath10k_mac_change_chanctx_arg *arg = data;
6765 struct ieee80211_chanctx_conf *ctx;
6766
6767 ctx = rcu_access_pointer(vif->chanctx_conf);
6768 if (ctx != arg->ctx)
6769 return;
6770
6771 if (WARN_ON(arg->next_vif == arg->n_vifs))
6772 return;
6773
6774 arg->vifs[arg->next_vif].vif = vif;
6775 arg->vifs[arg->next_vif].old_ctx = ctx;
6776 arg->vifs[arg->next_vif].new_ctx = ctx;
6777 arg->next_vif++;
6778}
6779
Michal Kazior500ff9f2015-03-31 10:26:21 +00006780static void
6781ath10k_mac_op_change_chanctx(struct ieee80211_hw *hw,
6782 struct ieee80211_chanctx_conf *ctx,
6783 u32 changed)
6784{
6785 struct ath10k *ar = hw->priv;
Michal Kazior9713e3d2015-09-03 10:44:52 +02006786 struct ath10k_mac_change_chanctx_arg arg = { .ctx = ctx };
Michal Kazior500ff9f2015-03-31 10:26:21 +00006787
6788 mutex_lock(&ar->conf_mutex);
6789
6790 ath10k_dbg(ar, ATH10K_DBG_MAC,
Michal Kazior089ab7a2015-06-03 12:16:55 +02006791 "mac chanctx change freq %hu width %d ptr %p changed %x\n",
6792 ctx->def.chan->center_freq, ctx->def.width, ctx, changed);
Michal Kazior500ff9f2015-03-31 10:26:21 +00006793
6794 /* This shouldn't really happen because channel switching should use
6795 * switch_vif_chanctx().
6796 */
6797 if (WARN_ON(changed & IEEE80211_CHANCTX_CHANGE_CHANNEL))
6798 goto unlock;
6799
Michal Kazior9713e3d2015-09-03 10:44:52 +02006800 if (changed & IEEE80211_CHANCTX_CHANGE_WIDTH) {
6801 ieee80211_iterate_active_interfaces_atomic(
6802 hw,
6803 IEEE80211_IFACE_ITER_NORMAL,
6804 ath10k_mac_change_chanctx_cnt_iter,
6805 &arg);
6806 if (arg.n_vifs == 0)
6807 goto radar;
6808
6809 arg.vifs = kcalloc(arg.n_vifs, sizeof(arg.vifs[0]),
6810 GFP_KERNEL);
6811 if (!arg.vifs)
6812 goto radar;
6813
6814 ieee80211_iterate_active_interfaces_atomic(
6815 hw,
6816 IEEE80211_IFACE_ITER_NORMAL,
6817 ath10k_mac_change_chanctx_fill_iter,
6818 &arg);
6819 ath10k_mac_update_vif_chan(ar, arg.vifs, arg.n_vifs);
6820 kfree(arg.vifs);
6821 }
6822
6823radar:
Michal Kazior500ff9f2015-03-31 10:26:21 +00006824 ath10k_recalc_radar_detection(ar);
6825
6826 /* FIXME: How to configure Rx chains properly? */
6827
6828 /* No other actions are actually necessary. Firmware maintains channel
6829 * definitions per vdev internally and there's no host-side channel
6830 * context abstraction to configure, e.g. channel width.
6831 */
6832
6833unlock:
6834 mutex_unlock(&ar->conf_mutex);
6835}
6836
6837static int
6838ath10k_mac_op_assign_vif_chanctx(struct ieee80211_hw *hw,
6839 struct ieee80211_vif *vif,
6840 struct ieee80211_chanctx_conf *ctx)
6841{
6842 struct ath10k *ar = hw->priv;
Michal Kazior500ff9f2015-03-31 10:26:21 +00006843 struct ath10k_vif *arvif = (void *)vif->drv_priv;
6844 int ret;
6845
6846 mutex_lock(&ar->conf_mutex);
6847
6848 ath10k_dbg(ar, ATH10K_DBG_MAC,
6849 "mac chanctx assign ptr %p vdev_id %i\n",
6850 ctx, arvif->vdev_id);
6851
6852 if (WARN_ON(arvif->is_started)) {
6853 mutex_unlock(&ar->conf_mutex);
6854 return -EBUSY;
6855 }
6856
Michal Kazior089ab7a2015-06-03 12:16:55 +02006857 ret = ath10k_vdev_start(arvif, &ctx->def);
Michal Kazior500ff9f2015-03-31 10:26:21 +00006858 if (ret) {
6859 ath10k_warn(ar, "failed to start vdev %i addr %pM on freq %d: %d\n",
6860 arvif->vdev_id, vif->addr,
Michal Kazior089ab7a2015-06-03 12:16:55 +02006861 ctx->def.chan->center_freq, ret);
Michal Kazior500ff9f2015-03-31 10:26:21 +00006862 goto err;
6863 }
6864
6865 arvif->is_started = true;
6866
Michal Kaziorf23e587e2015-07-09 13:08:37 +02006867 ret = ath10k_mac_vif_setup_ps(arvif);
6868 if (ret) {
6869 ath10k_warn(ar, "failed to update vdev %i ps: %d\n",
6870 arvif->vdev_id, ret);
6871 goto err_stop;
6872 }
6873
Michal Kazior500ff9f2015-03-31 10:26:21 +00006874 if (vif->type == NL80211_IFTYPE_MONITOR) {
6875 ret = ath10k_wmi_vdev_up(ar, arvif->vdev_id, 0, vif->addr);
6876 if (ret) {
6877 ath10k_warn(ar, "failed to up monitor vdev %i: %d\n",
6878 arvif->vdev_id, ret);
6879 goto err_stop;
6880 }
6881
6882 arvif->is_up = true;
6883 }
6884
6885 mutex_unlock(&ar->conf_mutex);
6886 return 0;
6887
6888err_stop:
6889 ath10k_vdev_stop(arvif);
6890 arvif->is_started = false;
Michal Kaziorf23e587e2015-07-09 13:08:37 +02006891 ath10k_mac_vif_setup_ps(arvif);
Michal Kazior500ff9f2015-03-31 10:26:21 +00006892
6893err:
6894 mutex_unlock(&ar->conf_mutex);
6895 return ret;
6896}
6897
6898static void
6899ath10k_mac_op_unassign_vif_chanctx(struct ieee80211_hw *hw,
6900 struct ieee80211_vif *vif,
6901 struct ieee80211_chanctx_conf *ctx)
6902{
6903 struct ath10k *ar = hw->priv;
6904 struct ath10k_vif *arvif = (void *)vif->drv_priv;
6905 int ret;
6906
6907 mutex_lock(&ar->conf_mutex);
6908
6909 ath10k_dbg(ar, ATH10K_DBG_MAC,
6910 "mac chanctx unassign ptr %p vdev_id %i\n",
6911 ctx, arvif->vdev_id);
6912
6913 WARN_ON(!arvif->is_started);
6914
6915 if (vif->type == NL80211_IFTYPE_MONITOR) {
6916 WARN_ON(!arvif->is_up);
6917
6918 ret = ath10k_wmi_vdev_down(ar, arvif->vdev_id);
6919 if (ret)
6920 ath10k_warn(ar, "failed to down monitor vdev %i: %d\n",
6921 arvif->vdev_id, ret);
6922
6923 arvif->is_up = false;
6924 }
6925
6926 ret = ath10k_vdev_stop(arvif);
6927 if (ret)
6928 ath10k_warn(ar, "failed to stop vdev %i: %d\n",
6929 arvif->vdev_id, ret);
6930
6931 arvif->is_started = false;
6932
6933 mutex_unlock(&ar->conf_mutex);
6934}
6935
6936static int
6937ath10k_mac_op_switch_vif_chanctx(struct ieee80211_hw *hw,
6938 struct ieee80211_vif_chanctx_switch *vifs,
6939 int n_vifs,
6940 enum ieee80211_chanctx_switch_mode mode)
6941{
6942 struct ath10k *ar = hw->priv;
Michal Kazior500ff9f2015-03-31 10:26:21 +00006943
6944 mutex_lock(&ar->conf_mutex);
6945
6946 ath10k_dbg(ar, ATH10K_DBG_MAC,
6947 "mac chanctx switch n_vifs %d mode %d\n",
6948 n_vifs, mode);
Michal Kazior7be6d1b2015-09-03 10:44:51 +02006949 ath10k_mac_update_vif_chan(ar, vifs, n_vifs);
Michal Kazior500ff9f2015-03-31 10:26:21 +00006950
6951 mutex_unlock(&ar->conf_mutex);
6952 return 0;
6953}
6954
Kalle Valo5e3dd152013-06-12 20:52:10 +03006955static const struct ieee80211_ops ath10k_ops = {
Michal Kaziorf2f6eca2016-03-01 11:32:46 +01006956 .tx = ath10k_mac_op_tx,
Kalle Valo5e3dd152013-06-12 20:52:10 +03006957 .start = ath10k_start,
6958 .stop = ath10k_stop,
6959 .config = ath10k_config,
6960 .add_interface = ath10k_add_interface,
6961 .remove_interface = ath10k_remove_interface,
6962 .configure_filter = ath10k_configure_filter,
6963 .bss_info_changed = ath10k_bss_info_changed,
6964 .hw_scan = ath10k_hw_scan,
6965 .cancel_hw_scan = ath10k_cancel_hw_scan,
6966 .set_key = ath10k_set_key,
SenthilKumar Jegadeesan627613f2015-01-29 13:50:38 +02006967 .set_default_unicast_key = ath10k_set_default_unicast_key,
Kalle Valo5e3dd152013-06-12 20:52:10 +03006968 .sta_state = ath10k_sta_state,
6969 .conf_tx = ath10k_conf_tx,
6970 .remain_on_channel = ath10k_remain_on_channel,
6971 .cancel_remain_on_channel = ath10k_cancel_remain_on_channel,
6972 .set_rts_threshold = ath10k_set_rts_threshold,
Michal Kazior92092fe2015-08-03 11:16:43 +02006973 .set_frag_threshold = ath10k_mac_op_set_frag_threshold,
Kalle Valo5e3dd152013-06-12 20:52:10 +03006974 .flush = ath10k_flush,
6975 .tx_last_beacon = ath10k_tx_last_beacon,
Ben Greear46acf7bb2014-05-16 17:15:38 +03006976 .set_antenna = ath10k_set_antenna,
6977 .get_antenna = ath10k_get_antenna,
Eliad Pellercf2c92d2014-11-04 11:43:54 +02006978 .reconfig_complete = ath10k_reconfig_complete,
Michal Kazior2e1dea42013-07-31 10:32:40 +02006979 .get_survey = ath10k_get_survey,
Michal Kazior3ae54222015-03-31 10:49:20 +00006980 .set_bitrate_mask = ath10k_mac_op_set_bitrate_mask,
Michal Kazior9797feb2014-02-14 14:49:48 +01006981 .sta_rc_update = ath10k_sta_rc_update,
Chun-Yeow Yeoh26ebbcc2014-02-25 09:29:54 +02006982 .get_tsf = ath10k_get_tsf,
Michal Kazioraa5b4fb2014-07-23 12:20:33 +02006983 .ampdu_action = ath10k_ampdu_action,
Ben Greear6cddcc72014-09-29 14:41:46 +03006984 .get_et_sset_count = ath10k_debug_get_et_sset_count,
6985 .get_et_stats = ath10k_debug_get_et_stats,
6986 .get_et_strings = ath10k_debug_get_et_strings,
Michal Kazior500ff9f2015-03-31 10:26:21 +00006987 .add_chanctx = ath10k_mac_op_add_chanctx,
6988 .remove_chanctx = ath10k_mac_op_remove_chanctx,
6989 .change_chanctx = ath10k_mac_op_change_chanctx,
6990 .assign_vif_chanctx = ath10k_mac_op_assign_vif_chanctx,
6991 .unassign_vif_chanctx = ath10k_mac_op_unassign_vif_chanctx,
6992 .switch_vif_chanctx = ath10k_mac_op_switch_vif_chanctx,
Kalle Valo43d2a302014-09-10 18:23:30 +03006993
6994 CFG80211_TESTMODE_CMD(ath10k_tm_cmd)
6995
Michal Kazior8cd13ca2013-07-16 09:38:54 +02006996#ifdef CONFIG_PM
Janusz Dziedzic5fd3ac32015-03-23 17:32:53 +02006997 .suspend = ath10k_wow_op_suspend,
6998 .resume = ath10k_wow_op_resume,
Michal Kazior8cd13ca2013-07-16 09:38:54 +02006999#endif
Rajkumar Manoharanf5045982015-01-12 14:07:27 +02007000#ifdef CONFIG_MAC80211_DEBUGFS
7001 .sta_add_debugfs = ath10k_sta_add_debugfs,
7002#endif
Kalle Valo5e3dd152013-06-12 20:52:10 +03007003};
7004
Kalle Valo5e3dd152013-06-12 20:52:10 +03007005#define CHAN2G(_channel, _freq, _flags) { \
7006 .band = IEEE80211_BAND_2GHZ, \
7007 .hw_value = (_channel), \
7008 .center_freq = (_freq), \
7009 .flags = (_flags), \
7010 .max_antenna_gain = 0, \
7011 .max_power = 30, \
7012}
7013
7014#define CHAN5G(_channel, _freq, _flags) { \
7015 .band = IEEE80211_BAND_5GHZ, \
7016 .hw_value = (_channel), \
7017 .center_freq = (_freq), \
7018 .flags = (_flags), \
7019 .max_antenna_gain = 0, \
7020 .max_power = 30, \
7021}
7022
7023static const struct ieee80211_channel ath10k_2ghz_channels[] = {
7024 CHAN2G(1, 2412, 0),
7025 CHAN2G(2, 2417, 0),
7026 CHAN2G(3, 2422, 0),
7027 CHAN2G(4, 2427, 0),
7028 CHAN2G(5, 2432, 0),
7029 CHAN2G(6, 2437, 0),
7030 CHAN2G(7, 2442, 0),
7031 CHAN2G(8, 2447, 0),
7032 CHAN2G(9, 2452, 0),
7033 CHAN2G(10, 2457, 0),
7034 CHAN2G(11, 2462, 0),
7035 CHAN2G(12, 2467, 0),
7036 CHAN2G(13, 2472, 0),
7037 CHAN2G(14, 2484, 0),
7038};
7039
7040static const struct ieee80211_channel ath10k_5ghz_channels[] = {
Michal Kazior429ff562013-06-26 08:54:54 +02007041 CHAN5G(36, 5180, 0),
7042 CHAN5G(40, 5200, 0),
7043 CHAN5G(44, 5220, 0),
7044 CHAN5G(48, 5240, 0),
7045 CHAN5G(52, 5260, 0),
7046 CHAN5G(56, 5280, 0),
7047 CHAN5G(60, 5300, 0),
7048 CHAN5G(64, 5320, 0),
7049 CHAN5G(100, 5500, 0),
7050 CHAN5G(104, 5520, 0),
7051 CHAN5G(108, 5540, 0),
7052 CHAN5G(112, 5560, 0),
7053 CHAN5G(116, 5580, 0),
7054 CHAN5G(120, 5600, 0),
7055 CHAN5G(124, 5620, 0),
7056 CHAN5G(128, 5640, 0),
7057 CHAN5G(132, 5660, 0),
7058 CHAN5G(136, 5680, 0),
7059 CHAN5G(140, 5700, 0),
Peter Oh4a7898f2015-03-18 11:39:18 -07007060 CHAN5G(144, 5720, 0),
Michal Kazior429ff562013-06-26 08:54:54 +02007061 CHAN5G(149, 5745, 0),
7062 CHAN5G(153, 5765, 0),
7063 CHAN5G(157, 5785, 0),
7064 CHAN5G(161, 5805, 0),
7065 CHAN5G(165, 5825, 0),
Kalle Valo5e3dd152013-06-12 20:52:10 +03007066};
7067
Michal Kaziore7b54192014-08-07 11:03:27 +02007068struct ath10k *ath10k_mac_create(size_t priv_size)
Kalle Valo5e3dd152013-06-12 20:52:10 +03007069{
7070 struct ieee80211_hw *hw;
7071 struct ath10k *ar;
7072
Michal Kaziore7b54192014-08-07 11:03:27 +02007073 hw = ieee80211_alloc_hw(sizeof(struct ath10k) + priv_size, &ath10k_ops);
Kalle Valo5e3dd152013-06-12 20:52:10 +03007074 if (!hw)
7075 return NULL;
7076
7077 ar = hw->priv;
7078 ar->hw = hw;
7079
7080 return ar;
7081}
7082
7083void ath10k_mac_destroy(struct ath10k *ar)
7084{
7085 ieee80211_free_hw(ar->hw);
7086}
7087
7088static const struct ieee80211_iface_limit ath10k_if_limits[] = {
7089 {
Mohammed Shafi Shajakhan78f7aeb2015-11-21 15:24:41 +05307090 .max = 8,
7091 .types = BIT(NL80211_IFTYPE_STATION)
7092 | BIT(NL80211_IFTYPE_P2P_CLIENT)
Michal Kaziord531cb82013-07-31 10:55:13 +02007093 },
7094 {
Mohammed Shafi Shajakhan78f7aeb2015-11-21 15:24:41 +05307095 .max = 3,
7096 .types = BIT(NL80211_IFTYPE_P2P_GO)
Michal Kaziord531cb82013-07-31 10:55:13 +02007097 },
7098 {
Mohammed Shafi Shajakhan78f7aeb2015-11-21 15:24:41 +05307099 .max = 1,
7100 .types = BIT(NL80211_IFTYPE_P2P_DEVICE)
Michal Kazior75d2bd42014-12-12 12:41:39 +01007101 },
7102 {
Mohammed Shafi Shajakhan78f7aeb2015-11-21 15:24:41 +05307103 .max = 7,
7104 .types = BIT(NL80211_IFTYPE_AP)
Bob Copelandb6c7baf2015-09-09 12:47:36 -04007105#ifdef CONFIG_MAC80211_MESH
Mohammed Shafi Shajakhan78f7aeb2015-11-21 15:24:41 +05307106 | BIT(NL80211_IFTYPE_MESH_POINT)
Bob Copelandb6c7baf2015-09-09 12:47:36 -04007107#endif
Michal Kaziord531cb82013-07-31 10:55:13 +02007108 },
Kalle Valo5e3dd152013-06-12 20:52:10 +03007109};
7110
Bartosz Markowskif2595092013-12-10 16:20:39 +01007111static const struct ieee80211_iface_limit ath10k_10x_if_limits[] = {
Marek Puzyniake8a50f82013-11-20 09:59:47 +02007112 {
Mohammed Shafi Shajakhan78f7aeb2015-11-21 15:24:41 +05307113 .max = 8,
7114 .types = BIT(NL80211_IFTYPE_AP)
Bob Copelandb6c7baf2015-09-09 12:47:36 -04007115#ifdef CONFIG_MAC80211_MESH
Mohammed Shafi Shajakhan78f7aeb2015-11-21 15:24:41 +05307116 | BIT(NL80211_IFTYPE_MESH_POINT)
Bob Copelandb6c7baf2015-09-09 12:47:36 -04007117#endif
Marek Puzyniake8a50f82013-11-20 09:59:47 +02007118 },
Mohammed Shafi Shajakhan78f7aeb2015-11-21 15:24:41 +05307119 {
7120 .max = 1,
7121 .types = BIT(NL80211_IFTYPE_STATION)
7122 },
Marek Puzyniake8a50f82013-11-20 09:59:47 +02007123};
Marek Puzyniake8a50f82013-11-20 09:59:47 +02007124
7125static const struct ieee80211_iface_combination ath10k_if_comb[] = {
7126 {
7127 .limits = ath10k_if_limits,
7128 .n_limits = ARRAY_SIZE(ath10k_if_limits),
7129 .max_interfaces = 8,
7130 .num_different_channels = 1,
7131 .beacon_int_infra_match = true,
7132 },
Bartosz Markowskif2595092013-12-10 16:20:39 +01007133};
7134
7135static const struct ieee80211_iface_combination ath10k_10x_if_comb[] = {
Marek Puzyniake8a50f82013-11-20 09:59:47 +02007136 {
Bartosz Markowskif2595092013-12-10 16:20:39 +01007137 .limits = ath10k_10x_if_limits,
7138 .n_limits = ARRAY_SIZE(ath10k_10x_if_limits),
Marek Puzyniake8a50f82013-11-20 09:59:47 +02007139 .max_interfaces = 8,
7140 .num_different_channels = 1,
7141 .beacon_int_infra_match = true,
Bartosz Markowskif2595092013-12-10 16:20:39 +01007142#ifdef CONFIG_ATH10K_DFS_CERTIFIED
Marek Puzyniake8a50f82013-11-20 09:59:47 +02007143 .radar_detect_widths = BIT(NL80211_CHAN_WIDTH_20_NOHT) |
7144 BIT(NL80211_CHAN_WIDTH_20) |
7145 BIT(NL80211_CHAN_WIDTH_40) |
7146 BIT(NL80211_CHAN_WIDTH_80),
Marek Puzyniake8a50f82013-11-20 09:59:47 +02007147#endif
Bartosz Markowskif2595092013-12-10 16:20:39 +01007148 },
Kalle Valo5e3dd152013-06-12 20:52:10 +03007149};
7150
Michal Kaziorcf327842015-03-31 10:26:25 +00007151static const struct ieee80211_iface_limit ath10k_tlv_if_limit[] = {
7152 {
7153 .max = 2,
Michal Kaziored25b112015-07-09 13:08:39 +02007154 .types = BIT(NL80211_IFTYPE_STATION),
7155 },
7156 {
7157 .max = 2,
7158 .types = BIT(NL80211_IFTYPE_AP) |
Bob Copelandb6c7baf2015-09-09 12:47:36 -04007159#ifdef CONFIG_MAC80211_MESH
7160 BIT(NL80211_IFTYPE_MESH_POINT) |
7161#endif
Michal Kaziorcf327842015-03-31 10:26:25 +00007162 BIT(NL80211_IFTYPE_P2P_CLIENT) |
7163 BIT(NL80211_IFTYPE_P2P_GO),
7164 },
7165 {
7166 .max = 1,
7167 .types = BIT(NL80211_IFTYPE_P2P_DEVICE),
7168 },
7169};
7170
Michal Kaziored25b112015-07-09 13:08:39 +02007171static const struct ieee80211_iface_limit ath10k_tlv_qcs_if_limit[] = {
7172 {
7173 .max = 2,
7174 .types = BIT(NL80211_IFTYPE_STATION),
7175 },
7176 {
7177 .max = 2,
7178 .types = BIT(NL80211_IFTYPE_P2P_CLIENT),
7179 },
7180 {
7181 .max = 1,
7182 .types = BIT(NL80211_IFTYPE_AP) |
Bob Copelandb6c7baf2015-09-09 12:47:36 -04007183#ifdef CONFIG_MAC80211_MESH
7184 BIT(NL80211_IFTYPE_MESH_POINT) |
7185#endif
Michal Kaziored25b112015-07-09 13:08:39 +02007186 BIT(NL80211_IFTYPE_P2P_GO),
7187 },
7188 {
7189 .max = 1,
7190 .types = BIT(NL80211_IFTYPE_P2P_DEVICE),
7191 },
7192};
7193
Michal Kaziorcf327842015-03-31 10:26:25 +00007194static const struct ieee80211_iface_limit ath10k_tlv_if_limit_ibss[] = {
7195 {
7196 .max = 1,
7197 .types = BIT(NL80211_IFTYPE_STATION),
7198 },
7199 {
7200 .max = 1,
7201 .types = BIT(NL80211_IFTYPE_ADHOC),
7202 },
7203};
7204
7205/* FIXME: This is not thouroughly tested. These combinations may over- or
7206 * underestimate hw/fw capabilities.
7207 */
7208static struct ieee80211_iface_combination ath10k_tlv_if_comb[] = {
7209 {
7210 .limits = ath10k_tlv_if_limit,
7211 .num_different_channels = 1,
Michal Kaziored25b112015-07-09 13:08:39 +02007212 .max_interfaces = 4,
Michal Kaziorcf327842015-03-31 10:26:25 +00007213 .n_limits = ARRAY_SIZE(ath10k_tlv_if_limit),
7214 },
7215 {
7216 .limits = ath10k_tlv_if_limit_ibss,
7217 .num_different_channels = 1,
7218 .max_interfaces = 2,
7219 .n_limits = ARRAY_SIZE(ath10k_tlv_if_limit_ibss),
7220 },
7221};
7222
7223static struct ieee80211_iface_combination ath10k_tlv_qcs_if_comb[] = {
7224 {
7225 .limits = ath10k_tlv_if_limit,
Michal Kaziored25b112015-07-09 13:08:39 +02007226 .num_different_channels = 1,
7227 .max_interfaces = 4,
Michal Kaziorcf327842015-03-31 10:26:25 +00007228 .n_limits = ARRAY_SIZE(ath10k_tlv_if_limit),
7229 },
7230 {
Michal Kaziored25b112015-07-09 13:08:39 +02007231 .limits = ath10k_tlv_qcs_if_limit,
7232 .num_different_channels = 2,
7233 .max_interfaces = 4,
7234 .n_limits = ARRAY_SIZE(ath10k_tlv_qcs_if_limit),
7235 },
7236 {
Michal Kaziorcf327842015-03-31 10:26:25 +00007237 .limits = ath10k_tlv_if_limit_ibss,
7238 .num_different_channels = 1,
7239 .max_interfaces = 2,
7240 .n_limits = ARRAY_SIZE(ath10k_tlv_if_limit_ibss),
7241 },
7242};
7243
Raja Manicf36fef2015-06-22 20:22:25 +05307244static const struct ieee80211_iface_limit ath10k_10_4_if_limits[] = {
7245 {
7246 .max = 1,
7247 .types = BIT(NL80211_IFTYPE_STATION),
7248 },
7249 {
7250 .max = 16,
7251 .types = BIT(NL80211_IFTYPE_AP)
Bob Copelandb6c7baf2015-09-09 12:47:36 -04007252#ifdef CONFIG_MAC80211_MESH
7253 | BIT(NL80211_IFTYPE_MESH_POINT)
7254#endif
Raja Manicf36fef2015-06-22 20:22:25 +05307255 },
7256};
7257
7258static const struct ieee80211_iface_combination ath10k_10_4_if_comb[] = {
7259 {
7260 .limits = ath10k_10_4_if_limits,
7261 .n_limits = ARRAY_SIZE(ath10k_10_4_if_limits),
7262 .max_interfaces = 16,
7263 .num_different_channels = 1,
7264 .beacon_int_infra_match = true,
7265#ifdef CONFIG_ATH10K_DFS_CERTIFIED
7266 .radar_detect_widths = BIT(NL80211_CHAN_WIDTH_20_NOHT) |
7267 BIT(NL80211_CHAN_WIDTH_20) |
7268 BIT(NL80211_CHAN_WIDTH_40) |
7269 BIT(NL80211_CHAN_WIDTH_80),
7270#endif
7271 },
7272};
7273
Kalle Valo5e3dd152013-06-12 20:52:10 +03007274static void ath10k_get_arvif_iter(void *data, u8 *mac,
7275 struct ieee80211_vif *vif)
7276{
7277 struct ath10k_vif_iter *arvif_iter = data;
7278 struct ath10k_vif *arvif = ath10k_vif_to_arvif(vif);
7279
7280 if (arvif->vdev_id == arvif_iter->vdev_id)
7281 arvif_iter->arvif = arvif;
7282}
7283
7284struct ath10k_vif *ath10k_get_arvif(struct ath10k *ar, u32 vdev_id)
7285{
7286 struct ath10k_vif_iter arvif_iter;
7287 u32 flags;
7288
7289 memset(&arvif_iter, 0, sizeof(struct ath10k_vif_iter));
7290 arvif_iter.vdev_id = vdev_id;
7291
7292 flags = IEEE80211_IFACE_ITER_RESUME_ALL;
7293 ieee80211_iterate_active_interfaces_atomic(ar->hw,
7294 flags,
7295 ath10k_get_arvif_iter,
7296 &arvif_iter);
7297 if (!arvif_iter.arvif) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02007298 ath10k_warn(ar, "No VIF found for vdev %d\n", vdev_id);
Kalle Valo5e3dd152013-06-12 20:52:10 +03007299 return NULL;
7300 }
7301
7302 return arvif_iter.arvif;
7303}
7304
7305int ath10k_mac_register(struct ath10k *ar)
7306{
Johannes Berg3cb10942015-01-22 21:38:45 +01007307 static const u32 cipher_suites[] = {
7308 WLAN_CIPHER_SUITE_WEP40,
7309 WLAN_CIPHER_SUITE_WEP104,
7310 WLAN_CIPHER_SUITE_TKIP,
7311 WLAN_CIPHER_SUITE_CCMP,
7312 WLAN_CIPHER_SUITE_AES_CMAC,
7313 };
Kalle Valo5e3dd152013-06-12 20:52:10 +03007314 struct ieee80211_supported_band *band;
Kalle Valo5e3dd152013-06-12 20:52:10 +03007315 void *channels;
7316 int ret;
7317
7318 SET_IEEE80211_PERM_ADDR(ar->hw, ar->mac_addr);
7319
7320 SET_IEEE80211_DEV(ar->hw, ar->dev);
7321
Michal Kaziorc94aa7e2015-03-24 12:38:11 +00007322 BUILD_BUG_ON((ARRAY_SIZE(ath10k_2ghz_channels) +
7323 ARRAY_SIZE(ath10k_5ghz_channels)) !=
7324 ATH10K_NUM_CHANS);
7325
Kalle Valo5e3dd152013-06-12 20:52:10 +03007326 if (ar->phy_capability & WHAL_WLAN_11G_CAPABILITY) {
7327 channels = kmemdup(ath10k_2ghz_channels,
7328 sizeof(ath10k_2ghz_channels),
7329 GFP_KERNEL);
Michal Kaziord6015b22013-07-22 14:13:30 +02007330 if (!channels) {
7331 ret = -ENOMEM;
7332 goto err_free;
7333 }
Kalle Valo5e3dd152013-06-12 20:52:10 +03007334
7335 band = &ar->mac.sbands[IEEE80211_BAND_2GHZ];
7336 band->n_channels = ARRAY_SIZE(ath10k_2ghz_channels);
7337 band->channels = channels;
7338 band->n_bitrates = ath10k_g_rates_size;
7339 band->bitrates = ath10k_g_rates;
Kalle Valo5e3dd152013-06-12 20:52:10 +03007340
7341 ar->hw->wiphy->bands[IEEE80211_BAND_2GHZ] = band;
7342 }
7343
7344 if (ar->phy_capability & WHAL_WLAN_11A_CAPABILITY) {
7345 channels = kmemdup(ath10k_5ghz_channels,
7346 sizeof(ath10k_5ghz_channels),
7347 GFP_KERNEL);
7348 if (!channels) {
Michal Kaziord6015b22013-07-22 14:13:30 +02007349 ret = -ENOMEM;
7350 goto err_free;
Kalle Valo5e3dd152013-06-12 20:52:10 +03007351 }
7352
7353 band = &ar->mac.sbands[IEEE80211_BAND_5GHZ];
7354 band->n_channels = ARRAY_SIZE(ath10k_5ghz_channels);
7355 band->channels = channels;
7356 band->n_bitrates = ath10k_a_rates_size;
7357 band->bitrates = ath10k_a_rates;
Kalle Valo5e3dd152013-06-12 20:52:10 +03007358 ar->hw->wiphy->bands[IEEE80211_BAND_5GHZ] = band;
7359 }
7360
Rajkumar Manoharan5036fe02015-10-27 17:51:14 +05307361 ath10k_mac_setup_ht_vht_cap(ar);
7362
Kalle Valo5e3dd152013-06-12 20:52:10 +03007363 ar->hw->wiphy->interface_modes =
7364 BIT(NL80211_IFTYPE_STATION) |
Bob Copelandb6c7baf2015-09-09 12:47:36 -04007365 BIT(NL80211_IFTYPE_AP) |
7366 BIT(NL80211_IFTYPE_MESH_POINT);
Bartosz Markowskid3541812013-12-10 16:20:40 +01007367
Rajkumar Manoharan166de3f2015-10-27 17:51:11 +05307368 ar->hw->wiphy->available_antennas_rx = ar->cfg_rx_chainmask;
7369 ar->hw->wiphy->available_antennas_tx = ar->cfg_tx_chainmask;
Ben Greear46acf7bb2014-05-16 17:15:38 +03007370
Bartosz Markowskid3541812013-12-10 16:20:40 +01007371 if (!test_bit(ATH10K_FW_FEATURE_NO_P2P, ar->fw_features))
7372 ar->hw->wiphy->interface_modes |=
Michal Kazior75d2bd42014-12-12 12:41:39 +01007373 BIT(NL80211_IFTYPE_P2P_DEVICE) |
Bartosz Markowskid3541812013-12-10 16:20:40 +01007374 BIT(NL80211_IFTYPE_P2P_CLIENT) |
7375 BIT(NL80211_IFTYPE_P2P_GO);
Kalle Valo5e3dd152013-06-12 20:52:10 +03007376
Johannes Berg30686bf2015-06-02 21:39:54 +02007377 ieee80211_hw_set(ar->hw, SIGNAL_DBM);
7378 ieee80211_hw_set(ar->hw, SUPPORTS_PS);
7379 ieee80211_hw_set(ar->hw, SUPPORTS_DYNAMIC_PS);
7380 ieee80211_hw_set(ar->hw, MFP_CAPABLE);
7381 ieee80211_hw_set(ar->hw, REPORTS_TX_ACK_STATUS);
7382 ieee80211_hw_set(ar->hw, HAS_RATE_CONTROL);
7383 ieee80211_hw_set(ar->hw, AP_LINK_PS);
7384 ieee80211_hw_set(ar->hw, SPECTRUM_MGMT);
Johannes Berg30686bf2015-06-02 21:39:54 +02007385 ieee80211_hw_set(ar->hw, SUPPORT_FAST_XMIT);
7386 ieee80211_hw_set(ar->hw, CONNECTION_MONITOR);
7387 ieee80211_hw_set(ar->hw, SUPPORTS_PER_STA_GTK);
7388 ieee80211_hw_set(ar->hw, WANT_MONITOR_VIF);
7389 ieee80211_hw_set(ar->hw, CHANCTX_STA_CSA);
7390 ieee80211_hw_set(ar->hw, QUEUE_CONTROL);
Kalle Valo5e3dd152013-06-12 20:52:10 +03007391
David Liuccec9032015-07-24 20:25:32 +03007392 if (!test_bit(ATH10K_FLAG_RAW_MODE, &ar->dev_flags))
7393 ieee80211_hw_set(ar->hw, SW_CRYPTO_CONTROL);
7394
Eliad Peller0d8614b2014-09-10 14:07:36 +03007395 ar->hw->wiphy->features |= NL80211_FEATURE_STATIC_SMPS;
Janusz Dziedzic0cd9bc12015-04-10 13:23:23 +00007396 ar->hw->wiphy->flags |= WIPHY_FLAG_IBSS_RSN;
Eliad Peller0d8614b2014-09-10 14:07:36 +03007397
Kalle Valo5e3dd152013-06-12 20:52:10 +03007398 if (ar->ht_cap_info & WMI_HT_CAP_DYNAMIC_SMPS)
Eliad Peller0d8614b2014-09-10 14:07:36 +03007399 ar->hw->wiphy->features |= NL80211_FEATURE_DYNAMIC_SMPS;
Kalle Valo5e3dd152013-06-12 20:52:10 +03007400
7401 if (ar->ht_cap_info & WMI_HT_CAP_ENABLED) {
Johannes Berg30686bf2015-06-02 21:39:54 +02007402 ieee80211_hw_set(ar->hw, AMPDU_AGGREGATION);
7403 ieee80211_hw_set(ar->hw, TX_AMPDU_SETUP_IN_HW);
Kalle Valo5e3dd152013-06-12 20:52:10 +03007404 }
7405
7406 ar->hw->wiphy->max_scan_ssids = WLAN_SCAN_PARAMS_MAX_SSID;
7407 ar->hw->wiphy->max_scan_ie_len = WLAN_SCAN_PARAMS_MAX_IE_LEN;
7408
7409 ar->hw->vif_data_size = sizeof(struct ath10k_vif);
Michal Kazior9797feb2014-02-14 14:49:48 +01007410 ar->hw->sta_data_size = sizeof(struct ath10k_sta);
Kalle Valo5e3dd152013-06-12 20:52:10 +03007411
Kalle Valo5e3dd152013-06-12 20:52:10 +03007412 ar->hw->max_listen_interval = ATH10K_MAX_HW_LISTEN_INTERVAL;
7413
Michal Kaziorfbb8f1b2015-01-13 16:30:12 +02007414 if (test_bit(WMI_SERVICE_BEACON_OFFLOAD, ar->wmi.svc_map)) {
7415 ar->hw->wiphy->flags |= WIPHY_FLAG_AP_PROBE_RESP_OFFLOAD;
7416
7417 /* Firmware delivers WPS/P2P Probe Requests frames to driver so
7418 * that userspace (e.g. wpa_supplicant/hostapd) can generate
7419 * correct Probe Responses. This is more of a hack advert..
7420 */
7421 ar->hw->wiphy->probe_resp_offload |=
7422 NL80211_PROBE_RESP_OFFLOAD_SUPPORT_WPS |
7423 NL80211_PROBE_RESP_OFFLOAD_SUPPORT_WPS2 |
7424 NL80211_PROBE_RESP_OFFLOAD_SUPPORT_P2P;
7425 }
7426
Marek Puzyniak75d85fd2015-03-30 09:51:53 +03007427 if (test_bit(WMI_SERVICE_TDLS, ar->wmi.svc_map))
7428 ar->hw->wiphy->flags |= WIPHY_FLAG_SUPPORTS_TDLS;
7429
Kalle Valo5e3dd152013-06-12 20:52:10 +03007430 ar->hw->wiphy->flags |= WIPHY_FLAG_HAS_REMAIN_ON_CHANNEL;
Michal Kaziorc2df44b2014-01-23 11:38:26 +01007431 ar->hw->wiphy->flags |= WIPHY_FLAG_HAS_CHANNEL_SWITCH;
Kalle Valo5e3dd152013-06-12 20:52:10 +03007432 ar->hw->wiphy->max_remain_on_channel_duration = 5000;
7433
7434 ar->hw->wiphy->flags |= WIPHY_FLAG_AP_UAPSD;
Rajkumar Manoharan78157a12014-11-17 16:44:15 +02007435 ar->hw->wiphy->features |= NL80211_FEATURE_AP_MODE_CHAN_WIDTH_CHANGE;
7436
Janusz.Dziedzic@tieto.com37a0b392015-03-12 13:11:41 +01007437 ar->hw->wiphy->max_ap_assoc_sta = ar->max_num_stations;
7438
Janusz Dziedzic5fd3ac32015-03-23 17:32:53 +02007439 ret = ath10k_wow_init(ar);
7440 if (ret) {
7441 ath10k_warn(ar, "failed to init wow: %d\n", ret);
7442 goto err_free;
7443 }
7444
Janusz Dziedzicc7025342015-06-15 14:46:41 +03007445 wiphy_ext_feature_set(ar->hw->wiphy, NL80211_EXT_FEATURE_VHT_IBSS);
7446
Kalle Valo5e3dd152013-06-12 20:52:10 +03007447 /*
7448 * on LL hardware queues are managed entirely by the FW
7449 * so we only advertise to mac we can do the queues thing
7450 */
Michal Kazior96d828d2015-03-31 10:26:23 +00007451 ar->hw->queues = IEEE80211_MAX_QUEUES;
7452
7453 /* vdev_ids are used as hw queue numbers. Make sure offchan tx queue is
7454 * something that vdev_ids can't reach so that we don't stop the queue
7455 * accidentally.
7456 */
7457 ar->hw->offchannel_tx_hw_queue = IEEE80211_MAX_QUEUES - 1;
Kalle Valo5e3dd152013-06-12 20:52:10 +03007458
Kalle Valo5cc7caf2014-12-17 12:20:54 +02007459 switch (ar->wmi.op_version) {
7460 case ATH10K_FW_WMI_OP_VERSION_MAIN:
Bartosz Markowskif2595092013-12-10 16:20:39 +01007461 ar->hw->wiphy->iface_combinations = ath10k_if_comb;
7462 ar->hw->wiphy->n_iface_combinations =
7463 ARRAY_SIZE(ath10k_if_comb);
Michal Kaziorcf850d12014-07-24 20:07:00 +03007464 ar->hw->wiphy->interface_modes |= BIT(NL80211_IFTYPE_ADHOC);
Kalle Valo5cc7caf2014-12-17 12:20:54 +02007465 break;
Michal Kaziorcf327842015-03-31 10:26:25 +00007466 case ATH10K_FW_WMI_OP_VERSION_TLV:
7467 if (test_bit(WMI_SERVICE_ADAPTIVE_OCS, ar->wmi.svc_map)) {
7468 ar->hw->wiphy->iface_combinations =
7469 ath10k_tlv_qcs_if_comb;
7470 ar->hw->wiphy->n_iface_combinations =
7471 ARRAY_SIZE(ath10k_tlv_qcs_if_comb);
7472 } else {
7473 ar->hw->wiphy->iface_combinations = ath10k_tlv_if_comb;
7474 ar->hw->wiphy->n_iface_combinations =
7475 ARRAY_SIZE(ath10k_tlv_if_comb);
7476 }
7477 ar->hw->wiphy->interface_modes |= BIT(NL80211_IFTYPE_ADHOC);
7478 break;
Kalle Valo5cc7caf2014-12-17 12:20:54 +02007479 case ATH10K_FW_WMI_OP_VERSION_10_1:
7480 case ATH10K_FW_WMI_OP_VERSION_10_2:
Rajkumar Manoharan4a16fbe2014-12-17 12:21:12 +02007481 case ATH10K_FW_WMI_OP_VERSION_10_2_4:
Kalle Valo5cc7caf2014-12-17 12:20:54 +02007482 ar->hw->wiphy->iface_combinations = ath10k_10x_if_comb;
7483 ar->hw->wiphy->n_iface_combinations =
7484 ARRAY_SIZE(ath10k_10x_if_comb);
7485 break;
Raja Mani9bd21322015-06-22 20:10:09 +05307486 case ATH10K_FW_WMI_OP_VERSION_10_4:
Raja Manicf36fef2015-06-22 20:22:25 +05307487 ar->hw->wiphy->iface_combinations = ath10k_10_4_if_comb;
7488 ar->hw->wiphy->n_iface_combinations =
7489 ARRAY_SIZE(ath10k_10_4_if_comb);
Raja Mani9bd21322015-06-22 20:10:09 +05307490 break;
Kalle Valo5cc7caf2014-12-17 12:20:54 +02007491 case ATH10K_FW_WMI_OP_VERSION_UNSET:
7492 case ATH10K_FW_WMI_OP_VERSION_MAX:
7493 WARN_ON(1);
7494 ret = -EINVAL;
7495 goto err_free;
Bartosz Markowskif2595092013-12-10 16:20:39 +01007496 }
Kalle Valo5e3dd152013-06-12 20:52:10 +03007497
David Liuccec9032015-07-24 20:25:32 +03007498 if (!test_bit(ATH10K_FLAG_RAW_MODE, &ar->dev_flags))
7499 ar->hw->netdev_features = NETIF_F_HW_CSUM;
Michal Kazior7c199992013-07-31 10:47:57 +02007500
Janusz Dziedzic9702c682013-11-20 09:59:41 +02007501 if (config_enabled(CONFIG_ATH10K_DFS_CERTIFIED)) {
7502 /* Init ath dfs pattern detector */
7503 ar->ath_common.debug_mask = ATH_DBG_DFS;
7504 ar->dfs_detector = dfs_pattern_detector_init(&ar->ath_common,
7505 NL80211_DFS_UNSET);
7506
7507 if (!ar->dfs_detector)
Michal Kazior7aa7a722014-08-25 12:09:38 +02007508 ath10k_warn(ar, "failed to initialise DFS pattern detector\n");
Janusz Dziedzic9702c682013-11-20 09:59:41 +02007509 }
7510
Kalle Valo5e3dd152013-06-12 20:52:10 +03007511 ret = ath_regd_init(&ar->ath_common.regulatory, ar->hw->wiphy,
7512 ath10k_reg_notifier);
7513 if (ret) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02007514 ath10k_err(ar, "failed to initialise regulatory: %i\n", ret);
Jeff Johnson0e339442015-10-08 09:15:53 -07007515 goto err_dfs_detector_exit;
Kalle Valo5e3dd152013-06-12 20:52:10 +03007516 }
7517
Johannes Berg3cb10942015-01-22 21:38:45 +01007518 ar->hw->wiphy->cipher_suites = cipher_suites;
7519 ar->hw->wiphy->n_cipher_suites = ARRAY_SIZE(cipher_suites);
7520
Kalle Valo5e3dd152013-06-12 20:52:10 +03007521 ret = ieee80211_register_hw(ar->hw);
7522 if (ret) {
Michal Kazior7aa7a722014-08-25 12:09:38 +02007523 ath10k_err(ar, "failed to register ieee80211: %d\n", ret);
Jeff Johnson0e339442015-10-08 09:15:53 -07007524 goto err_dfs_detector_exit;
Kalle Valo5e3dd152013-06-12 20:52:10 +03007525 }
7526
7527 if (!ath_is_world_regd(&ar->ath_common.regulatory)) {
7528 ret = regulatory_hint(ar->hw->wiphy,
7529 ar->ath_common.regulatory.alpha2);
7530 if (ret)
Michal Kaziord6015b22013-07-22 14:13:30 +02007531 goto err_unregister;
Kalle Valo5e3dd152013-06-12 20:52:10 +03007532 }
7533
7534 return 0;
Michal Kaziord6015b22013-07-22 14:13:30 +02007535
7536err_unregister:
Kalle Valo5e3dd152013-06-12 20:52:10 +03007537 ieee80211_unregister_hw(ar->hw);
Jeff Johnson0e339442015-10-08 09:15:53 -07007538
7539err_dfs_detector_exit:
7540 if (config_enabled(CONFIG_ATH10K_DFS_CERTIFIED) && ar->dfs_detector)
7541 ar->dfs_detector->exit(ar->dfs_detector);
7542
Michal Kaziord6015b22013-07-22 14:13:30 +02007543err_free:
7544 kfree(ar->mac.sbands[IEEE80211_BAND_2GHZ].channels);
7545 kfree(ar->mac.sbands[IEEE80211_BAND_5GHZ].channels);
7546
Jeff Johnson0e339442015-10-08 09:15:53 -07007547 SET_IEEE80211_DEV(ar->hw, NULL);
Kalle Valo5e3dd152013-06-12 20:52:10 +03007548 return ret;
7549}
7550
7551void ath10k_mac_unregister(struct ath10k *ar)
7552{
7553 ieee80211_unregister_hw(ar->hw);
7554
Janusz Dziedzic9702c682013-11-20 09:59:41 +02007555 if (config_enabled(CONFIG_ATH10K_DFS_CERTIFIED) && ar->dfs_detector)
7556 ar->dfs_detector->exit(ar->dfs_detector);
7557
Kalle Valo5e3dd152013-06-12 20:52:10 +03007558 kfree(ar->mac.sbands[IEEE80211_BAND_2GHZ].channels);
7559 kfree(ar->mac.sbands[IEEE80211_BAND_5GHZ].channels);
7560
7561 SET_IEEE80211_DEV(ar->hw, NULL);
7562}