staging: rtl8821ae: core.c: Remove version specific code
[cascardo/linux.git] / drivers / staging / rtl8821ae / core.c
1 /******************************************************************************
2  *
3  * Copyright(c) 2009-2010  Realtek Corporation.
4  *
5  * This program is free software; you can redistribute it and/or modify it
6  * under the terms of version 2 of the GNU General Public License as
7  * published by the Free Software Foundation.
8  *
9  * This program is distributed in the hope that it will be useful, but WITHOUT
10  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
11  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
12  * more details.
13  *
14  * You should have received a copy of the GNU General Public License along with
15  * this program; if not, write to the Free Software Foundation, Inc.,
16  * 51 Franklin Street, Fifth Floor, Boston, MA 02110, USA
17  *
18  * The full GNU General Public License is included in this distribution in the
19  * file called LICENSE.
20  *
21  * Contact Information:
22  * wlanfae <wlanfae@realtek.com>
23  * Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
24  * Hsinchu 300, Taiwan.
25  *
26  * Larry Finger <Larry.Finger@lwfinger.net>
27  *
28  *****************************************************************************/
29
30 #include "wifi.h"
31 #include "core.h"
32 #include "cam.h"
33 #include "base.h"
34 #include "ps.h"
35
36 #include "btcoexist/rtl_btc.h"
37
38 /*mutex for start & stop is must here. */
39 static int rtl_op_start(struct ieee80211_hw *hw)
40 {
41         int err = 0;
42         struct rtl_priv *rtlpriv = rtl_priv(hw);
43         struct rtl_hal *rtlhal = rtl_hal(rtl_priv(hw));
44
45         if (!is_hal_stop(rtlhal))
46                 return 0;
47         if (!test_bit(RTL_STATUS_INTERFACE_START, &rtlpriv->status))
48                 return 0;
49         mutex_lock(&rtlpriv->locks.conf_mutex);
50         err = rtlpriv->intf_ops->adapter_start(hw);
51         if (err)
52                 goto out;
53         rtl_watch_dog_timer_callback((unsigned long)hw);
54
55 out:
56         mutex_unlock(&rtlpriv->locks.conf_mutex);
57         return err;
58 }
59
60 static void rtl_op_stop(struct ieee80211_hw *hw)
61 {
62         struct rtl_priv *rtlpriv = rtl_priv(hw);
63         struct rtl_mac *mac = rtl_mac(rtl_priv(hw));
64         struct rtl_hal *rtlhal = rtl_hal(rtl_priv(hw));
65         struct rtl_ps_ctl *ppsc = rtl_psc(rtl_priv(hw));
66
67         if (is_hal_stop(rtlhal))
68                 return;
69
70         /* here is must, because adhoc do stop and start,
71          * but stop with RFOFF may cause something wrong,
72          * like adhoc TP */
73         if (unlikely(ppsc->rfpwr_state == ERFOFF))
74                 rtl_ips_nic_on(hw);
75
76         mutex_lock(&rtlpriv->locks.conf_mutex);
77
78         mac->link_state = MAC80211_NOLINK;
79         memset(mac->bssid, 0, 6);
80         mac->vendor = PEER_UNKNOWN;
81
82         /*reset sec info */
83         rtl_cam_reset_sec_info(hw);
84
85         rtl_deinit_deferred_work(hw);
86         rtlpriv->intf_ops->adapter_stop(hw);
87
88         mutex_unlock(&rtlpriv->locks.conf_mutex);
89 }
90
91 static void rtl_op_tx(struct ieee80211_hw *hw,
92                       struct ieee80211_tx_control *control,
93                       struct sk_buff *skb)
94 {
95         struct rtl_priv *rtlpriv = rtl_priv(hw);
96         struct rtl_hal *rtlhal = rtl_hal(rtl_priv(hw));
97         struct rtl_ps_ctl *ppsc = rtl_psc(rtl_priv(hw));
98         struct rtl_tcb_desc tcb_desc;
99         memset(&tcb_desc, 0, sizeof(struct rtl_tcb_desc));
100
101         if (unlikely(is_hal_stop(rtlhal) || ppsc->rfpwr_state != ERFON))
102                 goto err_free;
103
104         if (!test_bit(RTL_STATUS_INTERFACE_START, &rtlpriv->status))
105                 goto err_free;
106
107         if (!rtlpriv->intf_ops->waitq_insert(hw, control->sta, skb))
108                 rtlpriv->intf_ops->adapter_tx(hw, control->sta, skb, &tcb_desc);
109         return;
110
111 err_free:
112         dev_kfree_skb_any(skb);
113         return;
114 }
115
116 static int rtl_op_add_interface(struct ieee80211_hw *hw,
117                 struct ieee80211_vif *vif)
118 {
119         struct rtl_priv *rtlpriv = rtl_priv(hw);
120         struct rtl_mac *mac = rtl_mac(rtl_priv(hw));
121         int err = 0;
122
123         if (mac->vif) {
124                 RT_TRACE(COMP_ERR, DBG_WARNING,
125                          ("vif has been set!! mac->vif = 0x%p\n", mac->vif));
126                 return -EOPNOTSUPP;
127         }
128
129         vif->driver_flags |= IEEE80211_VIF_BEACON_FILTER;
130
131         rtl_ips_nic_on(hw);
132
133         mutex_lock(&rtlpriv->locks.conf_mutex);
134         switch (ieee80211_vif_type_p2p(vif)) {
135         case NL80211_IFTYPE_P2P_CLIENT:
136                 mac->p2p = P2P_ROLE_CLIENT;
137                 /*fall through*/
138         case NL80211_IFTYPE_STATION:
139                 if (mac->beacon_enabled == 1) {
140                         RT_TRACE(COMP_MAC80211, DBG_LOUD,
141                                  ("NL80211_IFTYPE_STATION \n"));
142                         mac->beacon_enabled = 0;
143                         rtlpriv->cfg->ops->update_interrupt_mask(hw, 0,
144                                         rtlpriv->cfg->maps[RTL_IBSS_INT_MASKS]);
145                 }
146                 break;
147         case NL80211_IFTYPE_ADHOC:
148                 RT_TRACE(COMP_MAC80211, DBG_LOUD,
149                          ("NL80211_IFTYPE_ADHOC \n"));
150
151                 mac->link_state = MAC80211_LINKED;
152                 rtlpriv->cfg->ops->set_bcn_reg(hw);
153                 if (rtlpriv->rtlhal.current_bandtype == BAND_ON_2_4G)
154                         mac->basic_rates = 0xfff;
155                 else
156                         mac->basic_rates = 0xff0;
157                 rtlpriv->cfg->ops->set_hw_reg(hw, HW_VAR_BASIC_RATE,
158                                 (u8 *) (&mac->basic_rates));
159
160                 break;
161         case NL80211_IFTYPE_P2P_GO:
162                 mac->p2p = P2P_ROLE_GO;
163                 /*fall through*/
164         case NL80211_IFTYPE_AP:
165                 RT_TRACE(COMP_MAC80211, DBG_LOUD,
166                          ("NL80211_IFTYPE_AP \n"));
167
168                 mac->link_state = MAC80211_LINKED;
169                 rtlpriv->cfg->ops->set_bcn_reg(hw);
170                 if (rtlpriv->rtlhal.current_bandtype == BAND_ON_2_4G)
171                         mac->basic_rates = 0xfff;
172                 else
173                         mac->basic_rates = 0xff0;
174                 rtlpriv->cfg->ops->set_hw_reg(hw, HW_VAR_BASIC_RATE,
175                                               (u8 *) (&mac->basic_rates));
176                 break;
177         case NL80211_IFTYPE_MESH_POINT:
178                 RT_TRACE(COMP_MAC80211, DBG_LOUD,
179                          ("NL80211_IFTYPE_MESH_POINT \n"));
180
181                 mac->link_state = MAC80211_LINKED;
182                 rtlpriv->cfg->ops->set_bcn_reg(hw);
183                 if (rtlpriv->rtlhal.current_bandtype == BAND_ON_2_4G)
184                         mac->basic_rates = 0xfff;
185                 else
186                         mac->basic_rates = 0xff0;
187                 rtlpriv->cfg->ops->set_hw_reg(hw, HW_VAR_BASIC_RATE,
188                                 (u8 *) (&mac->basic_rates));
189                 break;
190         default:
191                 RT_TRACE(COMP_ERR, DBG_EMERG,
192                          ("operation mode %d is not support!\n", vif->type));
193                 err = -EOPNOTSUPP;
194                 goto out;
195         }
196
197 #ifdef VIF_TODO
198         if (!rtl_set_vif_info(hw, vif))
199                 goto out;
200 #endif
201
202         if (mac->p2p) {
203                 RT_TRACE(COMP_MAC80211, DBG_LOUD,
204                          ("p2p role %x \n",vif->type));
205                 mac->basic_rates = 0xff0;/*disable cck rate for p2p*/
206                 rtlpriv->cfg->ops->set_hw_reg(hw, HW_VAR_BASIC_RATE,
207                                 (u8 *) (&mac->basic_rates));
208         }
209         mac->vif = vif;
210         mac->opmode = vif->type;
211         rtlpriv->cfg->ops->set_network_type(hw, vif->type);
212         memcpy(mac->mac_addr, vif->addr, ETH_ALEN);
213         rtlpriv->cfg->ops->set_hw_reg(hw, HW_VAR_ETHER_ADDR, mac->mac_addr);
214
215 out:
216         mutex_unlock(&rtlpriv->locks.conf_mutex);
217         return err;
218 }
219
220 static void rtl_op_remove_interface(struct ieee80211_hw *hw,
221                 struct ieee80211_vif *vif)
222 {
223         struct rtl_priv *rtlpriv = rtl_priv(hw);
224         struct rtl_mac *mac = rtl_mac(rtl_priv(hw));
225
226         mutex_lock(&rtlpriv->locks.conf_mutex);
227
228         /* Free beacon resources */
229         if ((vif->type == NL80211_IFTYPE_AP) ||
230             (vif->type == NL80211_IFTYPE_ADHOC) ||
231             (vif->type == NL80211_IFTYPE_MESH_POINT)) {
232                 if (mac->beacon_enabled == 1) {
233                         mac->beacon_enabled = 0;
234                         rtlpriv->cfg->ops->update_interrupt_mask(hw, 0,
235                                         rtlpriv->cfg->maps[RTL_IBSS_INT_MASKS]);
236                 }
237         }
238
239         /*
240          *Note: We assume NL80211_IFTYPE_UNSPECIFIED as
241          *NO LINK for our hardware.
242          */
243         mac->p2p = 0;
244         mac->vif = NULL;
245         mac->link_state = MAC80211_NOLINK;
246         memset(mac->bssid, 0, 6);
247         mac->vendor = PEER_UNKNOWN;
248         mac->opmode = NL80211_IFTYPE_UNSPECIFIED;
249         rtlpriv->cfg->ops->set_network_type(hw, mac->opmode);
250
251         mutex_unlock(&rtlpriv->locks.conf_mutex);
252 }
253
254 static int rtl_op_change_interface(struct ieee80211_hw *hw,
255                                    struct ieee80211_vif *vif,
256                                    enum nl80211_iftype new_type, bool p2p)
257 {
258         struct rtl_priv *rtlpriv = rtl_priv(hw);
259         int ret;
260         rtl_op_remove_interface(hw, vif);
261
262         vif->type = new_type;
263         vif->p2p = p2p;
264         ret = rtl_op_add_interface(hw, vif);
265         RT_TRACE(COMP_MAC80211, DBG_LOUD,
266                  (" p2p  %x\n",p2p));
267         return ret;
268 }
269
270 static int rtl_op_config(struct ieee80211_hw *hw, u32 changed)
271 {
272         struct rtl_priv *rtlpriv = rtl_priv(hw);
273         struct rtl_phy *rtlphy = &(rtlpriv->phy);
274         struct rtl_mac *mac = rtl_mac(rtl_priv(hw));
275         struct rtl_ps_ctl *ppsc = rtl_psc(rtl_priv(hw));
276         struct ieee80211_conf *conf = &hw->conf;
277
278         if (mac->skip_scan)
279                 return 1;
280
281
282         mutex_lock(&rtlpriv->locks.conf_mutex);
283         if (changed & IEEE80211_CONF_CHANGE_LISTEN_INTERVAL) {  /* BIT(2) */
284                 RT_TRACE(COMP_MAC80211, DBG_LOUD,
285                          ("IEEE80211_CONF_CHANGE_LISTEN_INTERVAL\n"));
286         }
287
288         /*For IPS */
289         if (changed & IEEE80211_CONF_CHANGE_IDLE) {
290                 if (hw->conf.flags & IEEE80211_CONF_IDLE)
291                         rtl_ips_nic_off(hw);
292                 else
293                         rtl_ips_nic_on(hw);
294         } else {
295                 /*
296                  *although rfoff may not cause by ips, but we will
297                  *check the reason in set_rf_power_state function
298                  */
299                 if (unlikely(ppsc->rfpwr_state == ERFOFF))
300                         rtl_ips_nic_on(hw);
301         }
302
303         /*For LPS */
304         if (changed & IEEE80211_CONF_CHANGE_PS) {
305                 cancel_delayed_work(&rtlpriv->works.ps_work);
306                 cancel_delayed_work(&rtlpriv->works.ps_rfon_wq);
307                 if (conf->flags & IEEE80211_CONF_PS) {
308                         rtlpriv->psc.sw_ps_enabled = true;
309                         /* sleep here is must, or we may recv the beacon and
310                          * cause mac80211 into wrong ps state, this will cause
311                          * power save nullfunc send fail, and further cause
312                          * pkt loss, So sleep must quickly but not immediately
313                          * because that will cause nullfunc send by mac80211
314                          * fail, and cause pkt loss, we have tested that 5mA
315                          * is worked very well */
316                         if (!rtlpriv->psc.multi_buffered)
317                                 queue_delayed_work(rtlpriv->works.rtl_wq,
318                                                    &rtlpriv->works.ps_work,
319                                                    MSECS(5));
320                 } else {
321                         rtl_swlps_rf_awake(hw);
322                         rtlpriv->psc.sw_ps_enabled = false;
323                 }
324         }
325
326         if (changed & IEEE80211_CONF_CHANGE_RETRY_LIMITS) {
327                 RT_TRACE(COMP_MAC80211, DBG_LOUD,
328                          ("IEEE80211_CONF_CHANGE_RETRY_LIMITS %x\n",
329                           hw->conf.long_frame_max_tx_count));
330                 mac->retry_long = hw->conf.long_frame_max_tx_count;
331                 mac->retry_short = hw->conf.long_frame_max_tx_count;
332                 rtlpriv->cfg->ops->set_hw_reg(hw, HW_VAR_RETRY_LIMIT,
333                                 (u8 *) (&hw->conf.long_frame_max_tx_count));
334         }
335
336         if (changed & IEEE80211_CONF_CHANGE_CHANNEL) {
337                 struct ieee80211_channel *channel = hw->conf.chandef.chan;
338                 enum nl80211_channel_type channel_type =
339                                 cfg80211_get_chandef_type(&(hw->conf.chandef));
340                 u8 wide_chan = (u8) channel->hw_value;
341
342                 if (mac->act_scanning)
343                         mac->n_channels++;
344
345                 if (rtlpriv->dm.supp_phymode_switch &&
346                         mac->link_state < MAC80211_LINKED &&
347                         !mac->act_scanning) {
348                         if (rtlpriv->cfg->ops->check_switch_to_dmdp)
349                                 rtlpriv->cfg->ops->check_switch_to_dmdp(hw);
350                 }
351
352                 /*
353                  *because we should back channel to
354                  *current_network.chan in in scanning,
355                  *So if set_chan == current_network.chan
356                  *we should set it.
357                  *because mac80211 tell us wrong bw40
358                  *info for cisco1253 bw20, so we modify
359                  *it here based on UPPER & LOWER
360                  */
361                 switch (channel_type) {
362                         case NL80211_CHAN_HT20:
363                         case NL80211_CHAN_NO_HT:
364                                 /* SC */
365                                 mac->cur_40_prime_sc =
366                                         PRIME_CHNL_OFFSET_DONT_CARE;
367                                 rtlphy->current_chan_bw = HT_CHANNEL_WIDTH_20;
368                                 mac->bw_40 = false;
369                                 break;
370                         case NL80211_CHAN_HT40MINUS:
371                                 /* SC */
372                                 mac->cur_40_prime_sc = PRIME_CHNL_OFFSET_UPPER;
373                                 rtlphy->current_chan_bw =
374                                         HT_CHANNEL_WIDTH_20_40;
375                                 mac->bw_40 = true;
376
377                                 /*wide channel */
378                                 wide_chan -= 2;
379
380                                 break;
381                         case NL80211_CHAN_HT40PLUS:
382                                 /* SC */
383                                 mac->cur_40_prime_sc = PRIME_CHNL_OFFSET_LOWER;
384                                 rtlphy->current_chan_bw =
385                                         HT_CHANNEL_WIDTH_20_40;
386                                 mac->bw_40 = true;
387
388                                 /*wide channel */
389                                 wide_chan += 2;
390
391                                 break;
392                         default:
393                                 mac->bw_40 = false;
394                                 RT_TRACE(COMP_ERR, DBG_EMERG,
395                                                 ("switch case not processed \n"));
396                                 break;
397                 }
398
399                 if (wide_chan <= 0)
400                         wide_chan = 1;
401
402                 /* in scanning, when before we offchannel we may send a ps=1
403                  * null to AP, and then we may send a ps = 0 null to AP quickly,
404                  * but first null have cause AP's put lots of packet to hw tx
405                  * buffer, these packet must be tx before off channel so we must
406                  * delay more time to let AP flush these packets before
407                  * offchannel, or dis-association or delete BA will happen by AP
408                  */
409                 if (rtlpriv->mac80211.offchan_deley) {
410                         rtlpriv->mac80211.offchan_deley = false;
411                         mdelay(50);
412                 }
413
414                 rtlphy->current_channel = wide_chan;
415
416                 rtlpriv->cfg->ops->switch_channel(hw);
417                 rtlpriv->cfg->ops->set_channel_access(hw);
418                 rtlpriv->cfg->ops->set_bw_mode(hw,
419                         channel_type);
420         }
421
422         mutex_unlock(&rtlpriv->locks.conf_mutex);
423
424         return 0;
425 }
426
427 static void rtl_op_configure_filter(struct ieee80211_hw *hw,
428                                     unsigned int changed_flags,
429                                     unsigned int *new_flags, u64 multicast)
430 {
431         struct rtl_priv *rtlpriv = rtl_priv(hw);
432         struct rtl_mac *mac = rtl_mac(rtl_priv(hw));
433
434         *new_flags &= RTL_SUPPORTED_FILTERS;
435         if (0 == changed_flags)
436                 return;
437
438         /*TODO: we disable broadcase now, so enable here */
439         if (changed_flags & FIF_ALLMULTI) {
440                 if (*new_flags & FIF_ALLMULTI) {
441                         mac->rx_conf |= rtlpriv->cfg->maps[MAC_RCR_AM] |
442                             rtlpriv->cfg->maps[MAC_RCR_AB];
443                         RT_TRACE(COMP_MAC80211, DBG_LOUD,
444                                  ("Enable receive multicast frame.\n"));
445                 } else {
446                         mac->rx_conf &= ~(rtlpriv->cfg->maps[MAC_RCR_AM] |
447                                           rtlpriv->cfg->maps[MAC_RCR_AB]);
448                         RT_TRACE(COMP_MAC80211, DBG_LOUD,
449                                  ("Disable receive multicast frame.\n"));
450                 }
451         }
452
453         if (changed_flags & FIF_FCSFAIL) {
454                 if (*new_flags & FIF_FCSFAIL) {
455                         mac->rx_conf |= rtlpriv->cfg->maps[MAC_RCR_ACRC32];
456                         RT_TRACE(COMP_MAC80211, DBG_LOUD,
457                                  ("Enable receive FCS error frame.\n"));
458                 } else {
459                         mac->rx_conf &= ~rtlpriv->cfg->maps[MAC_RCR_ACRC32];
460                         RT_TRACE(COMP_MAC80211, DBG_LOUD,
461                                  ("Disable receive FCS error frame.\n"));
462                 }
463         }
464
465         /* if ssid not set to hw don't check bssid
466          * here just used for linked scanning, & linked
467          * and nolink check bssid is set in set network_type */
468         if ((changed_flags & FIF_BCN_PRBRESP_PROMISC) &&
469                 (mac->link_state >= MAC80211_LINKED)) {
470                 if (mac->opmode != NL80211_IFTYPE_AP &&
471                         mac->opmode != NL80211_IFTYPE_MESH_POINT) {
472                         if (*new_flags & FIF_BCN_PRBRESP_PROMISC) {
473                                 rtlpriv->cfg->ops->set_chk_bssid(hw, false);
474                         } else {
475                                 rtlpriv->cfg->ops->set_chk_bssid(hw, true);
476                         }
477                 }
478         }
479
480         if (changed_flags & FIF_CONTROL) {
481                 if (*new_flags & FIF_CONTROL) {
482                         mac->rx_conf |= rtlpriv->cfg->maps[MAC_RCR_ACF];
483
484                         RT_TRACE(COMP_MAC80211, DBG_LOUD,
485                                  ("Enable receive control frame.\n"));
486                 } else {
487                         mac->rx_conf &= ~rtlpriv->cfg->maps[MAC_RCR_ACF];
488                         RT_TRACE(COMP_MAC80211, DBG_LOUD,
489                                  ("Disable receive control frame.\n"));
490                 }
491         }
492
493         if (changed_flags & FIF_OTHER_BSS) {
494                 if (*new_flags & FIF_OTHER_BSS) {
495                         mac->rx_conf |= rtlpriv->cfg->maps[MAC_RCR_AAP];
496                         RT_TRACE(COMP_MAC80211, DBG_LOUD,
497                                  ("Enable receive other BSS's frame.\n"));
498                 } else {
499                         mac->rx_conf &= ~rtlpriv->cfg->maps[MAC_RCR_AAP];
500                         RT_TRACE(COMP_MAC80211, DBG_LOUD,
501                                  ("Disable receive other BSS's frame.\n"));
502                 }
503         }
504 }
505 static int rtl_op_sta_add(struct ieee80211_hw *hw,
506                          struct ieee80211_vif *vif,
507                          struct ieee80211_sta *sta)
508 {
509         struct rtl_priv *rtlpriv = rtl_priv(hw);
510         struct rtl_hal *rtlhal= rtl_hal(rtl_priv(hw));
511         struct rtl_mac *mac = rtl_mac(rtl_priv(hw));
512         struct rtl_sta_info *sta_entry;
513
514         if (sta) {
515                 sta_entry = (struct rtl_sta_info *) sta->drv_priv;
516                 spin_lock_bh(&rtlpriv->locks.entry_list_lock);
517                 list_add_tail(&sta_entry->list, &rtlpriv->entry_list);
518                 spin_unlock_bh(&rtlpriv->locks.entry_list_lock);
519                 if (rtlhal->current_bandtype == BAND_ON_2_4G) {
520                         sta_entry->wireless_mode = WIRELESS_MODE_G;
521                         if (sta->supp_rates[0] <= 0xf)
522                                 sta_entry->wireless_mode = WIRELESS_MODE_B;
523                         if (sta->ht_cap.ht_supported == true)
524                                 sta_entry->wireless_mode = WIRELESS_MODE_N_24G;
525
526                         if (vif->type == NL80211_IFTYPE_ADHOC)
527                                 sta_entry->wireless_mode = WIRELESS_MODE_G;
528                 } else if (rtlhal->current_bandtype == BAND_ON_5G) {
529                         sta_entry->wireless_mode = WIRELESS_MODE_A;
530                         if (sta->ht_cap.ht_supported == true)
531                                 sta_entry->wireless_mode = WIRELESS_MODE_N_24G;
532
533                         if (vif->type == NL80211_IFTYPE_ADHOC)
534                                 sta_entry->wireless_mode = WIRELESS_MODE_A;
535                 }
536                 /*disable cck rate for p2p*/
537                 if (mac->p2p)
538                         sta->supp_rates[0] &= 0xfffffff0;
539
540                 memcpy(sta_entry->mac_addr, sta->addr, ETH_ALEN);
541                 RT_TRACE(COMP_MAC80211, DBG_DMESG,
542                         ("Add sta addr is %pM\n",sta->addr));
543                 rtlpriv->cfg->ops->update_rate_tbl(hw, sta, 0);
544         }
545
546         return 0;
547 }
548
549 static int rtl_op_sta_remove(struct ieee80211_hw *hw,
550                                 struct ieee80211_vif *vif,
551                                 struct ieee80211_sta *sta)
552 {
553         struct rtl_priv *rtlpriv = rtl_priv(hw);
554         struct rtl_sta_info *sta_entry;
555         if (sta) {
556                 RT_TRACE(COMP_MAC80211, DBG_DMESG,
557                         ("Remove sta addr is %pM\n",sta->addr));
558                 sta_entry = (struct rtl_sta_info *) sta->drv_priv;
559                 sta_entry->wireless_mode = 0;
560                 sta_entry->ratr_index = 0;
561                 spin_lock_bh(&rtlpriv->locks.entry_list_lock);
562                 list_del(&sta_entry->list);
563                 spin_unlock_bh(&rtlpriv->locks.entry_list_lock);
564         }
565         return 0;
566 }
567 static int _rtl_get_hal_qnum(u16 queue)
568 {
569         int qnum;
570
571         switch (queue) {
572         case 0:
573                 qnum = AC3_VO;
574                 break;
575         case 1:
576                 qnum = AC2_VI;
577                 break;
578         case 2:
579                 qnum = AC0_BE;
580                 break;
581         case 3:
582                 qnum = AC1_BK;
583                 break;
584         default:
585                 qnum = AC0_BE;
586                 break;
587         }
588         return qnum;
589 }
590
591 /*
592  *for mac80211 VO=0, VI=1, BE=2, BK=3
593  *for rtl819x  BE=0, BK=1, VI=2, VO=3
594  */
595 static int rtl_op_conf_tx(struct ieee80211_hw *hw,
596                           struct ieee80211_vif *vif, u16 queue,
597                           const struct ieee80211_tx_queue_params *param)
598 {
599         struct rtl_priv *rtlpriv = rtl_priv(hw);
600         struct rtl_mac *mac = rtl_mac(rtl_priv(hw));
601         int aci;
602
603         if (queue >= AC_MAX) {
604                 RT_TRACE(COMP_ERR, DBG_WARNING,
605                          ("queue number %d is incorrect!\n", queue));
606                 return -EINVAL;
607         }
608
609         aci = _rtl_get_hal_qnum(queue);
610         mac->ac[aci].aifs = param->aifs;
611         mac->ac[aci].cw_min = param->cw_min;
612         mac->ac[aci].cw_max = param->cw_max;
613         mac->ac[aci].tx_op = param->txop;
614         memcpy(&mac->edca_param[aci], param, sizeof(*param));
615         rtlpriv->cfg->ops->set_qos(hw, aci);
616         return 0;
617 }
618
619 static void rtl_op_bss_info_changed(struct ieee80211_hw *hw,
620                                     struct ieee80211_vif *vif,
621                                     struct ieee80211_bss_conf *bss_conf,
622                                     u32 changed)
623 {
624         struct rtl_priv *rtlpriv = rtl_priv(hw);
625         struct rtl_hal *rtlhal = rtl_hal(rtlpriv);
626         struct rtl_mac *mac = rtl_mac(rtl_priv(hw));
627         struct rtl_ps_ctl *ppsc = rtl_psc(rtl_priv(hw));
628
629         mutex_lock(&rtlpriv->locks.conf_mutex);
630         if ((vif->type == NL80211_IFTYPE_ADHOC) ||
631             (vif->type == NL80211_IFTYPE_AP) ||
632             (vif->type == NL80211_IFTYPE_MESH_POINT)) {
633                 if ((changed & BSS_CHANGED_BEACON) ||
634                     (changed & BSS_CHANGED_BEACON_ENABLED &&
635                      bss_conf->enable_beacon)) {
636                         if (mac->beacon_enabled == 0) {
637                                 RT_TRACE(COMP_MAC80211, DBG_DMESG,
638                                          ("BSS_CHANGED_BEACON_ENABLED \n"));
639
640                                 /*start hw beacon interrupt. */
641                                 /*rtlpriv->cfg->ops->set_bcn_reg(hw); */
642                                 mac->beacon_enabled = 1;
643                                 rtlpriv->cfg->ops->update_interrupt_mask(hw,
644                                                 rtlpriv->cfg->maps
645                                                 [RTL_IBSS_INT_MASKS], 0);
646
647                                 if (rtlpriv->cfg->ops->linked_set_reg)
648                                         rtlpriv->cfg->ops->linked_set_reg(hw);
649                         }
650                 }
651                 if ((changed & BSS_CHANGED_BEACON_ENABLED &&
652                         !bss_conf->enable_beacon)){
653                         if (mac->beacon_enabled == 1) {
654                                 RT_TRACE(COMP_MAC80211, DBG_DMESG,
655                                          ("ADHOC DISABLE BEACON\n"));
656
657                                 mac->beacon_enabled = 0;
658                                 rtlpriv->cfg->ops->update_interrupt_mask(hw, 0,
659                                                 rtlpriv->cfg->maps
660                                                 [RTL_IBSS_INT_MASKS]);
661                         }
662                 }
663                 if (changed & BSS_CHANGED_BEACON_INT) {
664                         RT_TRACE(COMP_BEACON, DBG_TRACE,
665                                  ("BSS_CHANGED_BEACON_INT\n"));
666                         mac->beacon_interval = bss_conf->beacon_int;
667                         rtlpriv->cfg->ops->set_bcn_intv(hw);
668                 }
669         }
670
671         /*TODO: reference to enum ieee80211_bss_change */
672         if (changed & BSS_CHANGED_ASSOC) {
673                 if (bss_conf->assoc) {
674                         struct ieee80211_sta *sta = NULL;
675                         /* we should reset all sec info & cam
676                          * before set cam after linked, we should not
677                          * reset in disassoc, that will cause tkip->wep
678                          * fail because some flag will be wrong */
679                         /* reset sec info */
680                         rtl_cam_reset_sec_info(hw);
681                         /* reset cam to fix wep fail issue
682                          * when change from wpa to wep */
683                         rtl_cam_reset_all_entry(hw);
684
685                         mac->link_state = MAC80211_LINKED;
686                         mac->cnt_after_linked = 0;
687                         mac->assoc_id = bss_conf->aid;
688                         memcpy(mac->bssid, bss_conf->bssid, 6);
689
690                         if (rtlpriv->cfg->ops->linked_set_reg)
691                                 rtlpriv->cfg->ops->linked_set_reg(hw);
692
693                         rcu_read_lock();
694                         sta = ieee80211_find_sta(vif, (u8*)bss_conf->bssid);
695
696                         if (vif->type == NL80211_IFTYPE_STATION && sta)
697                                 rtlpriv->cfg->ops->update_rate_tbl(hw, sta, 0);
698                         RT_TRACE(COMP_EASY_CONCURRENT, DBG_LOUD,
699                                         ("send PS STATIC frame \n"));
700                         if (rtlpriv->dm.supp_phymode_switch) {
701                                 if (sta->ht_cap.ht_supported)
702                                         rtl_send_smps_action(hw, sta,
703                                                         IEEE80211_SMPS_STATIC);
704                         }
705                         rcu_read_unlock();
706
707                         RT_TRACE(COMP_MAC80211, DBG_DMESG,
708                                  ("BSS_CHANGED_ASSOC\n"));
709                 } else {
710                         if (mac->link_state == MAC80211_LINKED)
711                                 rtl_lps_leave(hw);
712                         if (ppsc->p2p_ps_info.p2p_ps_mode> P2P_PS_NONE)
713                                 rtl_p2p_ps_cmd(hw, P2P_PS_DISABLE);
714                         mac->link_state = MAC80211_NOLINK;
715                         memset(mac->bssid, 0, 6);
716                         mac->vendor = PEER_UNKNOWN;
717
718                         if (rtlpriv->dm.supp_phymode_switch) {
719                                 if (rtlpriv->cfg->ops->check_switch_to_dmdp)
720                                         rtlpriv->cfg->ops->check_switch_to_dmdp(hw);
721                         }
722                         RT_TRACE(COMP_MAC80211, DBG_DMESG,
723                                  ("BSS_CHANGED_UN_ASSOC\n"));
724                 }
725         }
726
727         if (changed & BSS_CHANGED_ERP_CTS_PROT) {
728                 RT_TRACE(COMP_MAC80211, DBG_TRACE,
729                          ("BSS_CHANGED_ERP_CTS_PROT\n"));
730                 mac->use_cts_protect = bss_conf->use_cts_prot;
731         }
732
733         if (changed & BSS_CHANGED_ERP_PREAMBLE) {
734                 RT_TRACE(COMP_MAC80211, DBG_LOUD,
735                          ("BSS_CHANGED_ERP_PREAMBLE use short preamble:%x \n",
736                           bss_conf->use_short_preamble));
737
738                 mac->short_preamble = bss_conf->use_short_preamble;
739                 rtlpriv->cfg->ops->set_hw_reg(hw, HW_VAR_ACK_PREAMBLE,
740                                               (u8 *) (&mac->short_preamble));
741         }
742
743         if (changed & BSS_CHANGED_ERP_SLOT) {
744                 RT_TRACE(COMP_MAC80211, DBG_TRACE,
745                          ("BSS_CHANGED_ERP_SLOT\n"));
746
747                 if (bss_conf->use_short_slot)
748                         mac->slot_time = RTL_SLOT_TIME_9;
749                 else
750                         mac->slot_time = RTL_SLOT_TIME_20;
751
752                 rtlpriv->cfg->ops->set_hw_reg(hw, HW_VAR_SLOT_TIME,
753                                               (u8 *) (&mac->slot_time));
754         }
755
756         if (changed & BSS_CHANGED_HT) {
757                 struct ieee80211_sta *sta = NULL;
758
759                 RT_TRACE(COMP_MAC80211, DBG_TRACE,
760                          ("BSS_CHANGED_HT\n"));
761
762                 rcu_read_lock();
763                 sta = ieee80211_find_sta(vif, (u8*)bss_conf->bssid);
764                 if (sta) {
765                         if (sta->ht_cap.ampdu_density >
766                             mac->current_ampdu_density)
767                                 mac->current_ampdu_density =
768                                     sta->ht_cap.ampdu_density;
769                         if (sta->ht_cap.ampdu_factor <
770                             mac->current_ampdu_factor)
771                                 mac->current_ampdu_factor =
772                                     sta->ht_cap.ampdu_factor;
773                 }
774                 rcu_read_unlock();
775
776                 rtlpriv->cfg->ops->set_hw_reg(hw, HW_VAR_SHORTGI_DENSITY,
777                                               (u8 *) (&mac->max_mss_density));
778                 rtlpriv->cfg->ops->set_hw_reg(hw, HW_VAR_AMPDU_FACTOR,
779                                               &mac->current_ampdu_factor);
780                 rtlpriv->cfg->ops->set_hw_reg(hw, HW_VAR_AMPDU_MIN_SPACE,
781                                               &mac->current_ampdu_density);
782         }
783
784         if (changed & BSS_CHANGED_BSSID) {
785                 u32 basic_rates;
786                 struct ieee80211_sta *sta = NULL;
787
788                 rtlpriv->cfg->ops->set_hw_reg(hw, HW_VAR_BSSID,
789                                               (u8 *) bss_conf->bssid);
790
791                 RT_TRACE(COMP_MAC80211, DBG_DMESG,
792                          ("bssid: %pM\n", bss_conf->bssid));
793
794                 mac->vendor = PEER_UNKNOWN;
795                 memcpy(mac->bssid, bss_conf->bssid, 6);
796                 rtlpriv->cfg->ops->set_network_type(hw, vif->type);
797
798                 rcu_read_lock();
799                 sta = ieee80211_find_sta(vif, (u8*)bss_conf->bssid);
800                 if (!sta) {
801                         rcu_read_unlock();
802                         goto out;
803                 }
804
805                 if (rtlhal->current_bandtype == BAND_ON_5G) {
806                         mac->mode = WIRELESS_MODE_A;
807                 } else {
808                         if (sta->supp_rates[0] <= 0xf)
809                                 mac->mode = WIRELESS_MODE_B;
810                         else
811                                 mac->mode = WIRELESS_MODE_G;
812                 }
813
814                 if (sta->ht_cap.ht_supported) {
815                         if (rtlhal->current_bandtype == BAND_ON_2_4G)
816                                 mac->mode = WIRELESS_MODE_N_24G;
817                         else
818                                 mac->mode = WIRELESS_MODE_N_5G;
819                 }
820
821                 /* just station need it, because ibss & ap mode will
822                  * set in sta_add, and will be NULL here */
823                 if (vif->type == NL80211_IFTYPE_STATION) {
824                         struct rtl_sta_info *sta_entry;
825                         sta_entry = (struct rtl_sta_info *) sta->drv_priv;
826                         sta_entry->wireless_mode = mac->mode;
827                 }
828
829                 if (sta->ht_cap.ht_supported) {
830                         mac->ht_enable = true;
831
832                         /*
833                          * for cisco 1252 bw20 it's wrong
834                          * if (ht_cap & IEEE80211_HT_CAP_SUP_WIDTH_20_40) {
835                          *      mac->bw_40 = true;
836                          * }
837                          * */
838                 }
839
840                 if (changed & BSS_CHANGED_BASIC_RATES) {
841                         /* for 5G must << RATE_6M_INDEX=4,
842                          * because 5G have no cck rate*/
843                         if (rtlhal->current_bandtype == BAND_ON_5G)
844                                 basic_rates = sta->supp_rates[1] << 4;
845                         else
846                                 basic_rates = sta->supp_rates[0];
847
848                         mac->basic_rates = basic_rates;
849                         rtlpriv->cfg->ops->set_hw_reg(hw, HW_VAR_BASIC_RATE,
850                                         (u8 *) (&basic_rates));
851                 }
852                 rcu_read_unlock();
853         }
854
855         /*
856          * For FW LPS and Keep Alive:
857          * To tell firmware we have connected
858          * to an AP. For 92SE/CE power save v2.
859          */
860         if (changed & BSS_CHANGED_ASSOC) {
861                 if (bss_conf->assoc) {
862                         u8 keep_alive = 10;
863                         u8 mstatus = RT_MEDIA_CONNECT;
864                         rtlpriv->cfg->ops->set_hw_reg(hw,
865                                                       HW_VAR_KEEP_ALIVE,
866                                                       (u8 *) (&keep_alive));
867
868                         rtlpriv->cfg->ops->set_hw_reg(hw,
869                                                       HW_VAR_H2C_FW_JOINBSSRPT,
870                                                       (u8 *) (&mstatus));
871                         ppsc->report_linked = true;
872
873                 } else {
874
875                         u8 mstatus = RT_MEDIA_DISCONNECT;
876                         rtlpriv->cfg->ops->set_hw_reg(hw,
877                                                       HW_VAR_H2C_FW_JOINBSSRPT,
878                                                       (u8 *) (&mstatus));
879                         ppsc->report_linked = false;
880
881                 }
882
883                 if (rtlpriv->cfg->ops->get_btc_status()){
884                         rtlpriv->btcoexist.btc_ops->btc_mediastatus_notify(
885                                                 rtlpriv, ppsc->report_linked);
886                 }
887         }
888
889 out:
890         mutex_unlock(&rtlpriv->locks.conf_mutex);
891 }
892
893 static u64 rtl_op_get_tsf(struct ieee80211_hw *hw, struct ieee80211_vif *vif)
894 {
895         struct rtl_priv *rtlpriv = rtl_priv(hw);
896         u64 tsf;
897
898         rtlpriv->cfg->ops->get_hw_reg(hw, HW_VAR_CORRECT_TSF, (u8 *) (&tsf));
899         return tsf;
900 }
901
902 static void rtl_op_set_tsf(struct ieee80211_hw *hw,
903                            struct ieee80211_vif *vif, u64 tsf)
904 {
905         struct rtl_priv *rtlpriv = rtl_priv(hw);
906         struct rtl_mac *mac = rtl_mac(rtl_priv(hw));
907         u8 bibss = (mac->opmode == NL80211_IFTYPE_ADHOC) ? 1 : 0;
908
909         mac->tsf = tsf;
910         rtlpriv->cfg->ops->set_hw_reg(hw, HW_VAR_CORRECT_TSF, (u8 *) (&bibss));
911 }
912
913 static void rtl_op_reset_tsf(struct ieee80211_hw *hw, struct ieee80211_vif *vif)
914 {
915         struct rtl_priv *rtlpriv = rtl_priv(hw);
916         u8 tmp = 0;
917
918         rtlpriv->cfg->ops->set_hw_reg(hw, HW_VAR_DUAL_TSF_RST, (u8 *) (&tmp));
919 }
920
921 static void rtl_op_sta_notify(struct ieee80211_hw *hw,
922                               struct ieee80211_vif *vif,
923                               enum sta_notify_cmd cmd,
924                               struct ieee80211_sta *sta)
925 {
926         switch (cmd) {
927         case STA_NOTIFY_SLEEP:
928                 break;
929         case STA_NOTIFY_AWAKE:
930                 break;
931         default:
932                 break;
933         }
934 }
935
936 static int rtl_op_ampdu_action(struct ieee80211_hw *hw,
937                                struct ieee80211_vif *vif,
938                                enum ieee80211_ampdu_mlme_action action,
939                                struct ieee80211_sta *sta, u16 tid, u16 * ssn
940                                ,u8 buf_size
941                                )
942 {
943         struct rtl_priv *rtlpriv = rtl_priv(hw);
944
945         switch (action) {
946         case IEEE80211_AMPDU_TX_START:
947                 RT_TRACE(COMP_MAC80211, DBG_TRACE,
948                          ("IEEE80211_AMPDU_TX_START: TID:%d\n", tid));
949                 return rtl_tx_agg_start(hw, vif, sta, tid, ssn);
950                 break;
951         case IEEE80211_AMPDU_TX_STOP_CONT:
952         case IEEE80211_AMPDU_TX_STOP_FLUSH:
953         case IEEE80211_AMPDU_TX_STOP_FLUSH_CONT:
954                 RT_TRACE(COMP_MAC80211, DBG_TRACE,
955                          ("IEEE80211_AMPDU_TX_STOP: TID:%d\n", tid));
956                 return rtl_tx_agg_stop(hw, vif, sta, tid);
957                 break;
958         case IEEE80211_AMPDU_TX_OPERATIONAL:
959                 RT_TRACE(COMP_MAC80211, DBG_TRACE,
960                          ("IEEE80211_AMPDU_TX_OPERATIONAL:TID:%d\n", tid));
961                 rtl_tx_agg_oper(hw, sta, tid);
962                 break;
963         case IEEE80211_AMPDU_RX_START:
964                 RT_TRACE(COMP_MAC80211, DBG_TRACE,
965                          ("IEEE80211_AMPDU_RX_START:TID:%d\n", tid));
966                 return rtl_rx_agg_start(hw, sta, tid);
967                 break;
968         case IEEE80211_AMPDU_RX_STOP:
969                 RT_TRACE(COMP_MAC80211, DBG_TRACE,
970                          ("IEEE80211_AMPDU_RX_STOP:TID:%d\n", tid));
971                 return rtl_rx_agg_stop(hw, sta, tid);
972                 break;
973         default:
974                 RT_TRACE(COMP_ERR, DBG_EMERG,
975                          ("IEEE80211_AMPDU_ERR!!!!:\n"));
976                 return -EOPNOTSUPP;
977         }
978         return 0;
979 }
980
981 static void rtl_op_sw_scan_start(struct ieee80211_hw *hw)
982 {
983         struct rtl_priv *rtlpriv = rtl_priv(hw);
984         struct rtl_mac *mac = rtl_mac(rtl_priv(hw));
985
986         RT_TRACE(COMP_MAC80211, DBG_LOUD, ("\n"));
987         mac->act_scanning = true;
988         /*rtlpriv->btcops->btc_scan_notify(rtlpriv, 0); */
989         if (rtlpriv->link_info.b_higher_busytraffic) {
990                 mac->skip_scan = true;
991                 return;
992         }
993
994         if (rtlpriv->dm.supp_phymode_switch) {
995                 if (rtlpriv->cfg->ops->check_switch_to_dmdp)
996                         rtlpriv->cfg->ops->check_switch_to_dmdp(hw);
997         }
998
999         if (mac->link_state == MAC80211_LINKED) {
1000                 rtl_lps_leave(hw);
1001                 mac->link_state = MAC80211_LINKED_SCANNING;
1002         } else {
1003                 rtl_ips_nic_on(hw);
1004         }
1005
1006         /* Dul mac */
1007         rtlpriv->rtlhal.b_load_imrandiqk_setting_for2g = false;
1008
1009         rtlpriv->cfg->ops->led_control(hw, LED_CTL_SITE_SURVEY);
1010
1011         rtlpriv->cfg->ops->scan_operation_backup(hw, SCAN_OPT_BACKUP_BAND0);
1012
1013 }
1014
1015 static void rtl_op_sw_scan_complete(struct ieee80211_hw *hw)
1016 {
1017         struct rtl_priv *rtlpriv = rtl_priv(hw);
1018         struct rtl_mac *mac = rtl_mac(rtl_priv(hw));
1019
1020         RT_TRACE(COMP_MAC80211, DBG_LOUD, ("\n"));
1021         mac->act_scanning = false;
1022         mac->skip_scan = false;
1023         if (rtlpriv->link_info.b_higher_busytraffic) {
1024                 return;
1025         }
1026
1027         /* p2p will use 1/6/11 to scan */
1028         if (mac->n_channels == 3)
1029                 mac->p2p_in_use = true;
1030         else
1031                 mac->p2p_in_use = false;
1032         mac->n_channels = 0;
1033         /* Dul mac */
1034         rtlpriv->rtlhal.b_load_imrandiqk_setting_for2g = false;
1035
1036         if (mac->link_state == MAC80211_LINKED_SCANNING) {
1037                 mac->link_state = MAC80211_LINKED;
1038                 if (mac->opmode == NL80211_IFTYPE_STATION) {
1039                         /* fix fwlps issue */
1040                         rtlpriv->cfg->ops->set_network_type(hw, mac->opmode);
1041                 }
1042         }
1043
1044         rtlpriv->cfg->ops->scan_operation_backup(hw, SCAN_OPT_RESTORE);
1045         /* rtlpriv->btcops->btc_scan_notify(rtlpriv, 1); */
1046 }
1047
1048 static int rtl_op_set_key(struct ieee80211_hw *hw, enum set_key_cmd cmd,
1049                           struct ieee80211_vif *vif, struct ieee80211_sta *sta,
1050                           struct ieee80211_key_conf *key)
1051 {
1052         struct rtl_priv *rtlpriv = rtl_priv(hw);
1053         u8 key_type = NO_ENCRYPTION;
1054         u8 key_idx;
1055         bool group_key = false;
1056         bool wep_only = false;
1057         int err = 0;
1058         u8 mac_addr[ETH_ALEN];
1059         u8 bcast_addr[ETH_ALEN] = { 0xff, 0xff, 0xff, 0xff, 0xff, 0xff };
1060         u8 zero_addr[ETH_ALEN] = { 0 };
1061
1062         if (rtlpriv->cfg->mod_params->sw_crypto || rtlpriv->sec.use_sw_sec) {
1063                 RT_TRACE(COMP_ERR, DBG_WARNING,
1064                          ("not open hw encryption\n"));
1065                 return -ENOSPC; /*User disabled HW-crypto */
1066         }
1067         /* To support IBSS, use sw-crypto for GTK */
1068         if(((vif->type == NL80211_IFTYPE_ADHOC) ||
1069             (vif->type == NL80211_IFTYPE_MESH_POINT)) &&
1070            !(key->flags & IEEE80211_KEY_FLAG_PAIRWISE))
1071                 return -ENOSPC;
1072         RT_TRACE(COMP_SEC, DBG_DMESG,
1073                  ("%s hardware based encryption for keyidx: %d, mac: %pM\n",
1074                   cmd == SET_KEY ? "Using" : "Disabling", key->keyidx,
1075                   sta ? sta->addr : bcast_addr));
1076         rtlpriv->sec.being_setkey = true;
1077         rtl_ips_nic_on(hw);
1078         mutex_lock(&rtlpriv->locks.conf_mutex);
1079         /* <1> get encryption alg */
1080
1081         switch (key->cipher) {
1082         case WLAN_CIPHER_SUITE_WEP40:
1083                 key_type = WEP40_ENCRYPTION;
1084                 RT_TRACE(COMP_SEC, DBG_DMESG, ("alg:WEP40\n"));
1085                 break;
1086         case WLAN_CIPHER_SUITE_WEP104:
1087                 RT_TRACE(COMP_SEC, DBG_DMESG, ("alg:WEP104\n"));
1088                 key_type = WEP104_ENCRYPTION;
1089                 break;
1090         case WLAN_CIPHER_SUITE_TKIP:
1091                 key_type = TKIP_ENCRYPTION;
1092                 RT_TRACE(COMP_SEC, DBG_DMESG, ("alg:TKIP\n"));
1093                 break;
1094         case WLAN_CIPHER_SUITE_CCMP:
1095                 key_type = AESCCMP_ENCRYPTION;
1096                 RT_TRACE(COMP_SEC, DBG_DMESG, ("alg:CCMP\n"));
1097                 break;
1098         case WLAN_CIPHER_SUITE_AES_CMAC:
1099                 /* HW don't support CMAC encryption,
1100                  * use software CMAC encryption */
1101                 key_type = AESCMAC_ENCRYPTION;
1102                 RT_TRACE(COMP_SEC, DBG_DMESG, ("alg:CMAC\n"));
1103                 RT_TRACE(COMP_SEC, DBG_DMESG,
1104                                 ("HW don't support CMAC encryption, "
1105                                 "use software CMAC encryption\n"));
1106                 err = -EOPNOTSUPP;
1107                 goto out_unlock;
1108         default:
1109                 RT_TRACE(COMP_ERR, DBG_EMERG,
1110                          ("alg_err:%x!!!!:\n", key->cipher));
1111                 goto out_unlock;
1112         }
1113         if(key_type == WEP40_ENCRYPTION ||
1114                         key_type == WEP104_ENCRYPTION ||
1115                         vif->type == NL80211_IFTYPE_ADHOC)
1116                 rtlpriv->sec.use_defaultkey = true;
1117
1118         /* <2> get key_idx */
1119         key_idx = (u8) (key->keyidx);
1120         if (key_idx > 3)
1121                 goto out_unlock;
1122         /* <3> if pairwise key enable_hw_sec */
1123         group_key = !(key->flags & IEEE80211_KEY_FLAG_PAIRWISE);
1124
1125         /* wep always be group key, but there are two conditions:
1126          * 1) wep only: is just for wep enc, in this condition
1127          * rtlpriv->sec.pairwise_enc_algorithm == NO_ENCRYPTION
1128          * will be true & enable_hw_sec will be set when wep
1129          * ke setting.
1130          * 2) wep(group) + AES(pairwise): some AP like cisco
1131          * may use it, in this condition enable_hw_sec will not
1132          * be set when wep key setting */
1133         /* we must reset sec_info after lingked before set key,
1134          * or some flag will be wrong*/
1135         if (vif->type == NL80211_IFTYPE_AP ||
1136                 vif->type == NL80211_IFTYPE_MESH_POINT) {
1137                 if (!group_key || key_type == WEP40_ENCRYPTION ||
1138                         key_type == WEP104_ENCRYPTION) {
1139                         if (group_key) {
1140                                 wep_only = true;
1141                         }
1142                         rtlpriv->cfg->ops->enable_hw_sec(hw);
1143                 }
1144         } else {
1145                 if ((!group_key) || (vif->type == NL80211_IFTYPE_ADHOC) ||
1146                     rtlpriv->sec.pairwise_enc_algorithm == NO_ENCRYPTION) {
1147                         if (rtlpriv->sec.pairwise_enc_algorithm ==
1148                             NO_ENCRYPTION &&
1149                            (key_type == WEP40_ENCRYPTION ||
1150                             key_type == WEP104_ENCRYPTION))
1151                                 wep_only = true;
1152                         rtlpriv->sec.pairwise_enc_algorithm = key_type;
1153                         RT_TRACE(COMP_SEC, DBG_DMESG,
1154                                  ("set enable_hw_sec, key_type:%x(OPEN:0 WEP40:"
1155                                   "1 TKIP:2 AES:4 WEP104:5)\n", key_type));
1156                         rtlpriv->cfg->ops->enable_hw_sec(hw);
1157                 }
1158         }
1159         /* <4> set key based on cmd */
1160         switch (cmd) {
1161         case SET_KEY:
1162                 if (wep_only) {
1163                         RT_TRACE(COMP_SEC, DBG_DMESG,
1164                                  ("set WEP(group/pairwise) key\n"));
1165                         /* Pairwise key with an assigned MAC address. */
1166                         rtlpriv->sec.pairwise_enc_algorithm = key_type;
1167                         rtlpriv->sec.group_enc_algorithm = key_type;
1168                         /*set local buf about wep key. */
1169                         memcpy(rtlpriv->sec.key_buf[key_idx],
1170                                key->key, key->keylen);
1171                         rtlpriv->sec.key_len[key_idx] = key->keylen;
1172                         memcpy(mac_addr, zero_addr, ETH_ALEN);
1173                 } else if (group_key) { /* group key */
1174                         RT_TRACE(COMP_SEC, DBG_DMESG,
1175                                  ("set group key\n"));
1176                         /* group key */
1177                         rtlpriv->sec.group_enc_algorithm = key_type;
1178                         /*set local buf about group key. */
1179                         memcpy(rtlpriv->sec.key_buf[key_idx],
1180                                key->key, key->keylen);
1181                         rtlpriv->sec.key_len[key_idx] = key->keylen;
1182                         memcpy(mac_addr, bcast_addr, ETH_ALEN);
1183                 } else {        /* pairwise key */
1184                         RT_TRACE(COMP_SEC, DBG_DMESG,
1185                                  ("set pairwise key\n"));
1186                         if (!sta) {
1187                                 RT_ASSERT(false, ("pairwise key withnot"
1188                                                   "mac_addr\n"));
1189
1190                                 err = -EOPNOTSUPP;
1191                                 goto out_unlock;
1192                         }
1193                         /* Pairwise key with an assigned MAC address. */
1194                         rtlpriv->sec.pairwise_enc_algorithm = key_type;
1195                         /*set local buf about pairwise key. */
1196                         memcpy(rtlpriv->sec.key_buf[PAIRWISE_KEYIDX],
1197                                key->key, key->keylen);
1198                         rtlpriv->sec.key_len[PAIRWISE_KEYIDX] = key->keylen;
1199                         rtlpriv->sec.pairwise_key =
1200                             rtlpriv->sec.key_buf[PAIRWISE_KEYIDX];
1201                         memcpy(mac_addr, sta->addr, ETH_ALEN);
1202                 }
1203                 rtlpriv->cfg->ops->set_key(hw, key_idx, mac_addr,
1204                                            group_key, key_type, wep_only,
1205                                            false);
1206                 /* <5> tell mac80211 do something: */
1207                 /*must use sw generate IV, or can not work !!!!. */
1208                 key->flags |= IEEE80211_KEY_FLAG_GENERATE_IV;
1209                 key->hw_key_idx = key_idx;
1210                 if (key_type == TKIP_ENCRYPTION)
1211                         key->flags |= IEEE80211_KEY_FLAG_GENERATE_MMIC;
1212                 /*use software CCMP encryption for management frames (MFP) */
1213                 if (key_type == AESCCMP_ENCRYPTION)
1214                         key->flags |= IEEE80211_KEY_FLAG_SW_MGMT;
1215                 break;
1216         case DISABLE_KEY:
1217                 RT_TRACE(COMP_SEC, DBG_DMESG,
1218                          ("disable key delete one entry\n"));
1219                 /*set local buf about wep key. */
1220                 if (vif->type == NL80211_IFTYPE_AP ||
1221                         vif->type == NL80211_IFTYPE_MESH_POINT) {
1222                         if (sta)
1223                                 rtl_cam_del_entry(hw, sta->addr);
1224                 }
1225                 memset(rtlpriv->sec.key_buf[key_idx], 0, key->keylen);
1226                 rtlpriv->sec.key_len[key_idx] = 0;
1227                 memcpy(mac_addr, zero_addr, ETH_ALEN);
1228                 /*
1229                  *mac80211 will delete entrys one by one,
1230                  *so don't use rtl_cam_reset_all_entry
1231                  *or clear all entry here.
1232                  */
1233                 rtl_cam_delete_one_entry(hw, mac_addr, key_idx);
1234                 break;
1235         default:
1236                 RT_TRACE(COMP_ERR, DBG_EMERG,
1237                          ("cmd_err:%x!!!!:\n", cmd));
1238         }
1239 out_unlock:
1240         mutex_unlock(&rtlpriv->locks.conf_mutex);
1241         rtlpriv->sec.being_setkey = false;
1242         return err;
1243 }
1244
1245 static void rtl_op_rfkill_poll(struct ieee80211_hw *hw)
1246 {
1247         struct rtl_priv *rtlpriv = rtl_priv(hw);
1248
1249         bool radio_state;
1250         bool blocked;
1251         u8 valid = 0;
1252
1253         if (!test_bit(RTL_STATUS_INTERFACE_START, &rtlpriv->status))
1254                 return;
1255
1256         mutex_lock(&rtlpriv->locks.conf_mutex);
1257
1258         /*if Radio On return true here */
1259         radio_state = rtlpriv->cfg->ops->radio_onoff_checking(hw, &valid);
1260
1261         if (valid) {
1262                 if (unlikely(radio_state != rtlpriv->rfkill.rfkill_state)) {
1263                         rtlpriv->rfkill.rfkill_state = radio_state;
1264
1265                         RT_TRACE(COMP_RF, DBG_DMESG,
1266                                  (KERN_INFO "wireless radio switch turned %s\n",
1267                                   radio_state ? "on" : "off"));
1268
1269                         blocked = (rtlpriv->rfkill.rfkill_state == 1) ? 0 : 1;
1270                         wiphy_rfkill_set_hw_state(hw->wiphy, blocked);
1271                 }
1272         }
1273
1274         mutex_unlock(&rtlpriv->locks.conf_mutex);
1275 }
1276
1277 /* this function is called by mac80211 to flush tx buffer
1278  * before switch channel or power save, or tx buffer packet
1279  * maybe send after offchannel or rf sleep, this may cause
1280  * dis-association by AP */
1281 static void rtl_op_flush(struct ieee80211_hw *hw, u32 queues, bool drop)
1282 {
1283         struct rtl_priv *rtlpriv = rtl_priv(hw);
1284
1285         if (rtlpriv->intf_ops->flush)
1286                 rtlpriv->intf_ops->flush(hw, queues, drop);
1287 }
1288
1289 const struct ieee80211_ops rtl_ops = {
1290         .start = rtl_op_start,
1291         .stop = rtl_op_stop,
1292         .tx = rtl_op_tx,
1293         .add_interface = rtl_op_add_interface,
1294         .remove_interface = rtl_op_remove_interface,
1295         .change_interface = rtl_op_change_interface,
1296         .config = rtl_op_config,
1297         .configure_filter = rtl_op_configure_filter,
1298         .set_key = rtl_op_set_key,
1299         .conf_tx = rtl_op_conf_tx,
1300         .bss_info_changed = rtl_op_bss_info_changed,
1301         .get_tsf = rtl_op_get_tsf,
1302         .set_tsf = rtl_op_set_tsf,
1303         .reset_tsf = rtl_op_reset_tsf,
1304         .sta_notify = rtl_op_sta_notify,
1305         .ampdu_action = rtl_op_ampdu_action,
1306         .sw_scan_start = rtl_op_sw_scan_start,
1307         .sw_scan_complete = rtl_op_sw_scan_complete,
1308         .rfkill_poll = rtl_op_rfkill_poll,
1309         .sta_add = rtl_op_sta_add,
1310         .sta_remove = rtl_op_sta_remove,
1311         .flush = rtl_op_flush,
1312 };