linux/drivers/net/wireless/rtlwifi/rtl8821ae/trx.c
<<
>>
Prefs
   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 * The full GNU General Public License is included in this distribution in the
  15 * file called LICENSE.
  16 *
  17 * Contact Information:
  18 * wlanfae <wlanfae@realtek.com>
  19 * Realtek Corporation, No. 2, Innovation Road II, Hsinchu Science Park,
  20 * Hsinchu 300, Taiwan.
  21 *
  22 * Larry Finger <Larry.Finger@lwfinger.net>
  23 *
  24 *****************************************************************************/
  25
  26#include "../wifi.h"
  27#include "../pci.h"
  28#include "../base.h"
  29#include "../stats.h"
  30#include "reg.h"
  31#include "def.h"
  32#include "phy.h"
  33#include "trx.h"
  34#include "led.h"
  35#include "dm.h"
  36#include "phy.h"
  37#include "fw.h"
  38
  39static u8 _rtl8821ae_map_hwqueue_to_fwqueue(struct sk_buff *skb, u8 hw_queue)
  40{
  41        __le16 fc = rtl_get_fc(skb);
  42
  43        if (unlikely(ieee80211_is_beacon(fc)))
  44                return QSLT_BEACON;
  45        if (ieee80211_is_mgmt(fc) || ieee80211_is_ctl(fc))
  46                return QSLT_MGNT;
  47
  48        return skb->priority;
  49}
  50
  51/* mac80211's rate_idx is like this:
  52 *
  53 * 2.4G band:rx_status->band == IEEE80211_BAND_2GHZ
  54 *
  55 * B/G rate:
  56 * (rx_status->flag & RX_FLAG_HT) = 0,
  57 * DESC_RATE1M-->DESC_RATE54M ==> idx is 0-->11,
  58 *
  59 * N rate:
  60 * (rx_status->flag & RX_FLAG_HT) = 1,
  61 * DESC_RATEMCS0-->DESC_RATEMCS15 ==> idx is 0-->15
  62 *
  63 * 5G band:rx_status->band == IEEE80211_BAND_5GHZ
  64 * A rate:
  65 * (rx_status->flag & RX_FLAG_HT) = 0,
  66 * DESC_RATE6M-->DESC_RATE54M ==> idx is 0-->7,
  67 *
  68 * N rate:
  69 * (rx_status->flag & RX_FLAG_HT) = 1,
  70 * DESC_RATEMCS0-->DESC_RATEMCS15 ==> idx is 0-->15
  71 */
  72static int _rtl8821ae_rate_mapping(struct ieee80211_hw *hw,
  73                                   bool isht, bool isvht, u8 desc_rate)
  74{
  75        int rate_idx;
  76
  77        if (!isht) {
  78                if (IEEE80211_BAND_2GHZ == hw->conf.chandef.chan->band) {
  79                        switch (desc_rate) {
  80                        case DESC_RATE1M:
  81                                rate_idx = 0;
  82                                break;
  83                        case DESC_RATE2M:
  84                                rate_idx = 1;
  85                                break;
  86                        case DESC_RATE5_5M:
  87                                rate_idx = 2;
  88                                break;
  89                        case DESC_RATE11M:
  90                                rate_idx = 3;
  91                                break;
  92                        case DESC_RATE6M:
  93                                rate_idx = 4;
  94                                break;
  95                        case DESC_RATE9M:
  96                                rate_idx = 5;
  97                                break;
  98                        case DESC_RATE12M:
  99                                rate_idx = 6;
 100                                break;
 101                        case DESC_RATE18M:
 102                                rate_idx = 7;
 103                                break;
 104                        case DESC_RATE24M:
 105                                rate_idx = 8;
 106                                break;
 107                        case DESC_RATE36M:
 108                                rate_idx = 9;
 109                                break;
 110                        case DESC_RATE48M:
 111                                rate_idx = 10;
 112                                break;
 113                        case DESC_RATE54M:
 114                                rate_idx = 11;
 115                                break;
 116                        default:
 117                                rate_idx = 0;
 118                                break;
 119                        }
 120                } else {
 121                        switch (desc_rate) {
 122                        case DESC_RATE6M:
 123                                rate_idx = 0;
 124                                break;
 125                        case DESC_RATE9M:
 126                                rate_idx = 1;
 127                                break;
 128                        case DESC_RATE12M:
 129                                rate_idx = 2;
 130                                break;
 131                        case DESC_RATE18M:
 132                                rate_idx = 3;
 133                                break;
 134                        case DESC_RATE24M:
 135                                rate_idx = 4;
 136                                break;
 137                        case DESC_RATE36M:
 138                                rate_idx = 5;
 139                                break;
 140                        case DESC_RATE48M:
 141                                rate_idx = 6;
 142                                break;
 143                        case DESC_RATE54M:
 144                                rate_idx = 7;
 145                                break;
 146                        default:
 147                                rate_idx = 0;
 148                                break;
 149                        }
 150                }
 151        } else {
 152                switch (desc_rate) {
 153                case DESC_RATEMCS0:
 154                        rate_idx = 0;
 155                        break;
 156                case DESC_RATEMCS1:
 157                        rate_idx = 1;
 158                        break;
 159                case DESC_RATEMCS2:
 160                        rate_idx = 2;
 161                        break;
 162                case DESC_RATEMCS3:
 163                        rate_idx = 3;
 164                        break;
 165                case DESC_RATEMCS4:
 166                        rate_idx = 4;
 167                        break;
 168                case DESC_RATEMCS5:
 169                        rate_idx = 5;
 170                        break;
 171                case DESC_RATEMCS6:
 172                        rate_idx = 6;
 173                        break;
 174                case DESC_RATEMCS7:
 175                        rate_idx = 7;
 176                        break;
 177                case DESC_RATEMCS8:
 178                        rate_idx = 8;
 179                        break;
 180                case DESC_RATEMCS9:
 181                        rate_idx = 9;
 182                        break;
 183                case DESC_RATEMCS10:
 184                        rate_idx = 10;
 185                        break;
 186                case DESC_RATEMCS11:
 187                        rate_idx = 11;
 188                        break;
 189                case DESC_RATEMCS12:
 190                        rate_idx = 12;
 191                        break;
 192                case DESC_RATEMCS13:
 193                        rate_idx = 13;
 194                        break;
 195                case DESC_RATEMCS14:
 196                        rate_idx = 14;
 197                        break;
 198                case DESC_RATEMCS15:
 199                        rate_idx = 15;
 200                        break;
 201                default:
 202                        rate_idx = 0;
 203                        break;
 204                }
 205        }
 206
 207        if (isvht) {
 208                switch (desc_rate) {
 209                case DESC_RATEVHT1SS_MCS0:
 210                        rate_idx = 0;
 211                        break;
 212                case DESC_RATEVHT1SS_MCS1:
 213                        rate_idx = 1;
 214                        break;
 215                case DESC_RATEVHT1SS_MCS2:
 216                        rate_idx = 2;
 217                        break;
 218                case DESC_RATEVHT1SS_MCS3:
 219                        rate_idx = 3;
 220                        break;
 221                case DESC_RATEVHT1SS_MCS4:
 222                        rate_idx = 4;
 223                        break;
 224                case DESC_RATEVHT1SS_MCS5:
 225                        rate_idx = 5;
 226                        break;
 227                case DESC_RATEVHT1SS_MCS6:
 228                        rate_idx = 6;
 229                        break;
 230                case DESC_RATEVHT1SS_MCS7:
 231                        rate_idx = 7;
 232                        break;
 233                case DESC_RATEVHT1SS_MCS8:
 234                        rate_idx = 8;
 235                        break;
 236                case DESC_RATEVHT1SS_MCS9:
 237                        rate_idx = 9;
 238                        break;
 239                case DESC_RATEVHT2SS_MCS0:
 240                        rate_idx = 0;
 241                        break;
 242                case DESC_RATEVHT2SS_MCS1:
 243                        rate_idx = 1;
 244                        break;
 245                case DESC_RATEVHT2SS_MCS2:
 246                        rate_idx = 2;
 247                        break;
 248                case DESC_RATEVHT2SS_MCS3:
 249                        rate_idx = 3;
 250                        break;
 251                case DESC_RATEVHT2SS_MCS4:
 252                        rate_idx = 4;
 253                        break;
 254                case DESC_RATEVHT2SS_MCS5:
 255                        rate_idx = 5;
 256                        break;
 257                case DESC_RATEVHT2SS_MCS6:
 258                        rate_idx = 6;
 259                        break;
 260                case DESC_RATEVHT2SS_MCS7:
 261                        rate_idx = 7;
 262                        break;
 263                case DESC_RATEVHT2SS_MCS8:
 264                        rate_idx = 8;
 265                        break;
 266                case DESC_RATEVHT2SS_MCS9:
 267                        rate_idx = 9;
 268                        break;
 269                default:
 270                        rate_idx = 0;
 271                        break;
 272                }
 273        }
 274        return rate_idx;
 275}
 276
 277static u16 odm_cfo(char value)
 278{
 279        int ret_val;
 280
 281        if (value < 0) {
 282                ret_val = 0 - value;
 283                ret_val = (ret_val << 1) + (ret_val >> 1);
 284                /* set bit12 as 1 for negative cfo */
 285                ret_val = ret_val | BIT(12);
 286        } else {
 287                ret_val = value;
 288                ret_val = (ret_val << 1) + (ret_val >> 1);
 289        }
 290        return ret_val;
 291}
 292
 293static void query_rxphystatus(struct ieee80211_hw *hw,
 294                              struct rtl_stats *pstatus, u8 *pdesc,
 295                              struct rx_fwinfo_8821ae *p_drvinfo,
 296                              bool bpacket_match_bssid,
 297                              bool bpacket_toself, bool packet_beacon)
 298{
 299        struct rtl_priv *rtlpriv = rtl_priv(hw);
 300        struct phy_status_rpt *p_phystrpt = (struct phy_status_rpt *)p_drvinfo;
 301        struct rtl_dm *rtldm = rtl_dm(rtl_priv(hw));
 302        struct rtl_phy *rtlphy = &rtlpriv->phy;
 303        char rx_pwr_all = 0, rx_pwr[4];
 304        u8 rf_rx_num = 0, evm, evmdbm, pwdb_all;
 305        u8 i, max_spatial_stream;
 306        u32 rssi, total_rssi = 0;
 307        bool is_cck = pstatus->is_cck;
 308        u8 lan_idx, vga_idx;
 309
 310        /* Record it for next packet processing */
 311        pstatus->packet_matchbssid = bpacket_match_bssid;
 312        pstatus->packet_toself = bpacket_toself;
 313        pstatus->packet_beacon = packet_beacon;
 314        pstatus->rx_mimo_signalquality[0] = -1;
 315        pstatus->rx_mimo_signalquality[1] = -1;
 316
 317        if (is_cck) {
 318                u8 cck_highpwr;
 319                u8 cck_agc_rpt;
 320
 321                cck_agc_rpt = p_phystrpt->cfosho[0];
 322
 323                /* (1)Hardware does not provide RSSI for CCK
 324                 * (2)PWDB, Average PWDB cacluated by
 325                 * hardware (for rate adaptive)
 326                 */
 327                cck_highpwr = (u8)rtlphy->cck_high_power;
 328
 329                lan_idx = ((cck_agc_rpt & 0xE0) >> 5);
 330                vga_idx = (cck_agc_rpt & 0x1f);
 331                if (rtlpriv->rtlhal.hw_type == HARDWARE_TYPE_RTL8812AE) {
 332                        switch (lan_idx) {
 333                        case 7:
 334                                if (vga_idx <= 27)
 335                                        /*VGA_idx = 27~2*/
 336                                        rx_pwr_all = -100 + 2*(27-vga_idx);
 337                                else
 338                                        rx_pwr_all = -100;
 339                                break;
 340                        case 6:
 341                                /*VGA_idx = 2~0*/
 342                                rx_pwr_all = -48 + 2*(2-vga_idx);
 343                                break;
 344                        case 5:
 345                                /*VGA_idx = 7~5*/
 346                                rx_pwr_all = -42 + 2*(7-vga_idx);
 347                                break;
 348                        case 4:
 349                                /*VGA_idx = 7~4*/
 350                                rx_pwr_all = -36 + 2*(7-vga_idx);
 351                                break;
 352                        case 3:
 353                                /*VGA_idx = 7~0*/
 354                                rx_pwr_all = -24 + 2*(7-vga_idx);
 355                                break;
 356                        case 2:
 357                                if (cck_highpwr)
 358                                        /*VGA_idx = 5~0*/
 359                                        rx_pwr_all = -12 + 2*(5-vga_idx);
 360                                else
 361                                        rx_pwr_all = -6 + 2*(5-vga_idx);
 362                                break;
 363                        case 1:
 364                                rx_pwr_all = 8-2*vga_idx;
 365                                break;
 366                        case 0:
 367                                rx_pwr_all = 14-2*vga_idx;
 368                                break;
 369                        default:
 370                                break;
 371                        }
 372                        rx_pwr_all += 6;
 373                        pwdb_all = rtl_query_rxpwrpercentage(rx_pwr_all);
 374                        if (!cck_highpwr) {
 375                                if (pwdb_all >= 80)
 376                                        pwdb_all =
 377                                          ((pwdb_all - 80)<<1) +
 378                                         ((pwdb_all - 80)>>1) + 80;
 379                                else if ((pwdb_all <= 78) && (pwdb_all >= 20))
 380                                        pwdb_all += 3;
 381                                if (pwdb_all > 100)
 382                                        pwdb_all = 100;
 383                        }
 384                } else { /* 8821 */
 385                        char pout = -6;
 386
 387                        switch (lan_idx) {
 388                        case 5:
 389                                rx_pwr_all = pout - 32 - (2*vga_idx);
 390                                        break;
 391                        case 4:
 392                                rx_pwr_all = pout - 24 - (2*vga_idx);
 393                                        break;
 394                        case 2:
 395                                rx_pwr_all = pout - 11 - (2*vga_idx);
 396                                        break;
 397                        case 1:
 398                                rx_pwr_all = pout + 5 - (2*vga_idx);
 399                                        break;
 400                        case 0:
 401                                rx_pwr_all = pout + 21 - (2*vga_idx);
 402                                        break;
 403                        }
 404                        pwdb_all = rtl_query_rxpwrpercentage(rx_pwr_all);
 405                }
 406
 407                pstatus->rx_pwdb_all = pwdb_all;
 408                pstatus->recvsignalpower = rx_pwr_all;
 409
 410                /* (3) Get Signal Quality (EVM) */
 411                if (bpacket_match_bssid) {
 412                        u8 sq;
 413
 414                        if (pstatus->rx_pwdb_all > 40) {
 415                                sq = 100;
 416                        } else {
 417                                sq = p_phystrpt->pwdb_all;
 418                                if (sq > 64)
 419                                        sq = 0;
 420                                else if (sq < 20)
 421                                        sq = 100;
 422                                else
 423                                        sq = ((64 - sq) * 100) / 44;
 424                        }
 425
 426                        pstatus->signalquality = sq;
 427                        pstatus->rx_mimo_signalquality[0] = sq;
 428                        pstatus->rx_mimo_signalquality[1] = -1;
 429                }
 430        } else {
 431                /* (1)Get RSSI for HT rate */
 432                for (i = RF90_PATH_A; i < RF6052_MAX_PATH; i++) {
 433                        /* we will judge RF RX path now. */
 434                        if (rtlpriv->dm.rfpath_rxenable[i])
 435                                rf_rx_num++;
 436
 437                        rx_pwr[i] = (p_phystrpt->gain_trsw[i] & 0x7f) - 110;
 438
 439                        /* Translate DBM to percentage. */
 440                        rssi = rtl_query_rxpwrpercentage(rx_pwr[i]);
 441                        total_rssi += rssi;
 442
 443                        /* Get Rx snr value in DB */
 444                        pstatus->rx_snr[i] = p_phystrpt->rxsnr[i] / 2;
 445                        rtlpriv->stats.rx_snr_db[i] = p_phystrpt->rxsnr[i] / 2;
 446
 447                        pstatus->cfo_short[i] = odm_cfo(p_phystrpt->cfosho[i]);
 448                        pstatus->cfo_tail[i] = odm_cfo(p_phystrpt->cfotail[i]);
 449                        /* Record Signal Strength for next packet */
 450                        pstatus->rx_mimo_signalstrength[i] = (u8)rssi;
 451                }
 452
 453                /* (2)PWDB, Average PWDB cacluated by
 454                 * hardware (for rate adaptive)
 455                 */
 456                rx_pwr_all = ((p_drvinfo->pwdb_all >> 1) & 0x7f) - 110;
 457
 458                pwdb_all = rtl_query_rxpwrpercentage(rx_pwr_all);
 459                pstatus->rx_pwdb_all = pwdb_all;
 460                pstatus->rxpower = rx_pwr_all;
 461                pstatus->recvsignalpower = rx_pwr_all;
 462
 463                /* (3)EVM of HT rate */
 464                if ((pstatus->is_ht && pstatus->rate >= DESC_RATEMCS8 &&
 465                     pstatus->rate <= DESC_RATEMCS15) ||
 466                    (pstatus->is_vht &&
 467                     pstatus->rate >= DESC_RATEVHT2SS_MCS0 &&
 468                     pstatus->rate <= DESC_RATEVHT2SS_MCS9))
 469                        max_spatial_stream = 2;
 470                else
 471                        max_spatial_stream = 1;
 472
 473                for (i = 0; i < max_spatial_stream; i++) {
 474                        evm = rtl_evm_db_to_percentage(p_phystrpt->rxevm[i]);
 475                        evmdbm = rtl_evm_dbm_jaguar(p_phystrpt->rxevm[i]);
 476
 477                        if (bpacket_match_bssid) {
 478                                /* Fill value in RFD, Get the first
 479                                 * spatial stream only
 480                                 */
 481                                if (i == 0)
 482                                        pstatus->signalquality = evm;
 483                                pstatus->rx_mimo_signalquality[i] = evm;
 484                                pstatus->rx_mimo_evm_dbm[i] = evmdbm;
 485                        }
 486                }
 487                if (bpacket_match_bssid) {
 488                        for (i = RF90_PATH_A; i <= RF90_PATH_B; i++)
 489                                rtl_priv(hw)->dm.cfo_tail[i] =
 490                                        (char)p_phystrpt->cfotail[i];
 491
 492                        rtl_priv(hw)->dm.packet_count++;
 493                }
 494        }
 495
 496        /* UI BSS List signal strength(in percentage),
 497         * make it good looking, from 0~100.
 498         */
 499        if (is_cck)
 500                pstatus->signalstrength = (u8)(rtl_signal_scale_mapping(hw,
 501                        pwdb_all));
 502        else if (rf_rx_num != 0)
 503                pstatus->signalstrength = (u8)(rtl_signal_scale_mapping(hw,
 504                        total_rssi /= rf_rx_num));
 505        /*HW antenna diversity*/
 506        rtldm->fat_table.antsel_rx_keep_0 = p_phystrpt->antidx_anta;
 507        rtldm->fat_table.antsel_rx_keep_1 = p_phystrpt->antidx_antb;
 508}
 509
 510static void translate_rx_signal_stuff(struct ieee80211_hw *hw,
 511                                      struct sk_buff *skb,
 512                                      struct rtl_stats *pstatus, u8 *pdesc,
 513                                      struct rx_fwinfo_8821ae *p_drvinfo)
 514{
 515        struct rtl_mac *mac = rtl_mac(rtl_priv(hw));
 516        struct rtl_efuse *rtlefuse = rtl_efuse(rtl_priv(hw));
 517        struct ieee80211_hdr *hdr;
 518        u8 *tmp_buf;
 519        u8 *praddr;
 520        u8 *psaddr;
 521        __le16 fc;
 522        u16 type;
 523        bool packet_matchbssid, packet_toself, packet_beacon;
 524
 525        tmp_buf = skb->data + pstatus->rx_drvinfo_size + pstatus->rx_bufshift;
 526
 527        hdr = (struct ieee80211_hdr *)tmp_buf;
 528        fc = hdr->frame_control;
 529        type = WLAN_FC_GET_TYPE(hdr->frame_control);
 530        praddr = hdr->addr1;
 531        psaddr = ieee80211_get_SA(hdr);
 532        ether_addr_copy(pstatus->psaddr, psaddr);
 533
 534        packet_matchbssid = (!ieee80211_is_ctl(fc) &&
 535                             (ether_addr_equal(mac->bssid,
 536                                               ieee80211_has_tods(fc) ?
 537                                               hdr->addr1 :
 538                                               ieee80211_has_fromds(fc) ?
 539                                               hdr->addr2 : hdr->addr3)) &&
 540                              (!pstatus->hwerror) &&
 541                              (!pstatus->crc) && (!pstatus->icv));
 542
 543        packet_toself = packet_matchbssid &&
 544            (ether_addr_equal(praddr, rtlefuse->dev_addr));
 545
 546        if (ieee80211_is_beacon(hdr->frame_control))
 547                packet_beacon = true;
 548        else
 549                packet_beacon = false;
 550
 551        if (packet_beacon && packet_matchbssid)
 552                rtl_priv(hw)->dm.dbginfo.num_qry_beacon_pkt++;
 553
 554        if (packet_matchbssid &&
 555            ieee80211_is_data_qos(hdr->frame_control) &&
 556            !is_multicast_ether_addr(ieee80211_get_DA(hdr))) {
 557                struct ieee80211_qos_hdr *hdr_qos =
 558                        (struct ieee80211_qos_hdr *)tmp_buf;
 559                u16 tid = le16_to_cpu(hdr_qos->qos_ctrl) & 0xf;
 560
 561                if (tid != 0 && tid != 3)
 562                        rtl_priv(hw)->dm.dbginfo.num_non_be_pkt++;
 563        }
 564
 565        query_rxphystatus(hw, pstatus, pdesc, p_drvinfo,
 566                          packet_matchbssid, packet_toself,
 567                          packet_beacon);
 568        /*_rtl8821ae_smart_antenna(hw, pstatus); */
 569        rtl_process_phyinfo(hw, tmp_buf, pstatus);
 570}
 571
 572static void _rtl8821ae_insert_emcontent(struct rtl_tcb_desc *ptcb_desc,
 573                                        u8 *virtualaddress)
 574{
 575        u32 dwtmp = 0;
 576
 577        memset(virtualaddress, 0, 8);
 578
 579        SET_EARLYMODE_PKTNUM(virtualaddress, ptcb_desc->empkt_num);
 580        if (ptcb_desc->empkt_num == 1) {
 581                dwtmp = ptcb_desc->empkt_len[0];
 582        } else {
 583                dwtmp = ptcb_desc->empkt_len[0];
 584                dwtmp += ((dwtmp % 4) ? (4 - dwtmp % 4) : 0)+4;
 585                dwtmp += ptcb_desc->empkt_len[1];
 586        }
 587        SET_EARLYMODE_LEN0(virtualaddress, dwtmp);
 588
 589        if (ptcb_desc->empkt_num <= 3) {
 590                dwtmp = ptcb_desc->empkt_len[2];
 591        } else {
 592                dwtmp = ptcb_desc->empkt_len[2];
 593                dwtmp += ((dwtmp % 4) ? (4 - dwtmp % 4) : 0)+4;
 594                dwtmp += ptcb_desc->empkt_len[3];
 595        }
 596        SET_EARLYMODE_LEN1(virtualaddress, dwtmp);
 597        if (ptcb_desc->empkt_num <= 5) {
 598                dwtmp = ptcb_desc->empkt_len[4];
 599        } else {
 600                dwtmp = ptcb_desc->empkt_len[4];
 601                dwtmp += ((dwtmp % 4) ? (4 - dwtmp % 4) : 0)+4;
 602                dwtmp += ptcb_desc->empkt_len[5];
 603        }
 604        SET_EARLYMODE_LEN2_1(virtualaddress, dwtmp & 0xF);
 605        SET_EARLYMODE_LEN2_2(virtualaddress, dwtmp >> 4);
 606        if (ptcb_desc->empkt_num <= 7) {
 607                dwtmp = ptcb_desc->empkt_len[6];
 608        } else {
 609                dwtmp = ptcb_desc->empkt_len[6];
 610                dwtmp += ((dwtmp % 4) ? (4 - dwtmp % 4) : 0)+4;
 611                dwtmp += ptcb_desc->empkt_len[7];
 612        }
 613        SET_EARLYMODE_LEN3(virtualaddress, dwtmp);
 614        if (ptcb_desc->empkt_num <= 9) {
 615                dwtmp = ptcb_desc->empkt_len[8];
 616        } else {
 617                dwtmp = ptcb_desc->empkt_len[8];
 618                dwtmp += ((dwtmp % 4) ? (4 - dwtmp % 4) : 0)+4;
 619                dwtmp += ptcb_desc->empkt_len[9];
 620        }
 621        SET_EARLYMODE_LEN4(virtualaddress, dwtmp);
 622}
 623
 624static bool rtl8821ae_get_rxdesc_is_ht(struct ieee80211_hw *hw, u8 *pdesc)
 625{
 626        struct rtl_priv *rtlpriv = rtl_priv(hw);
 627        u8 rx_rate = 0;
 628
 629        rx_rate = GET_RX_DESC_RXMCS(pdesc);
 630
 631        RT_TRACE(rtlpriv, COMP_RXDESC, DBG_LOUD, "rx_rate=0x%02x.\n", rx_rate);
 632
 633        if ((rx_rate >= DESC_RATEMCS0) && (rx_rate <= DESC_RATEMCS15))
 634                return true;
 635        return false;
 636}
 637
 638static bool rtl8821ae_get_rxdesc_is_vht(struct ieee80211_hw *hw, u8 *pdesc)
 639{
 640        struct rtl_priv *rtlpriv = rtl_priv(hw);
 641        u8 rx_rate = 0;
 642
 643        rx_rate = GET_RX_DESC_RXMCS(pdesc);
 644
 645        RT_TRACE(rtlpriv, COMP_RXDESC, DBG_LOUD, "rx_rate=0x%02x.\n", rx_rate);
 646
 647        if (rx_rate >= DESC_RATEVHT1SS_MCS0)
 648                return true;
 649        return false;
 650}
 651
 652static u8 rtl8821ae_get_rx_vht_nss(struct ieee80211_hw *hw, u8 *pdesc)
 653{
 654        u8 rx_rate = 0;
 655        u8 vht_nss = 0;
 656
 657        rx_rate = GET_RX_DESC_RXMCS(pdesc);
 658        if ((rx_rate >= DESC_RATEVHT1SS_MCS0) &&
 659            (rx_rate <= DESC_RATEVHT1SS_MCS9))
 660                vht_nss = 1;
 661        else if ((rx_rate >= DESC_RATEVHT2SS_MCS0) &&
 662                 (rx_rate <= DESC_RATEVHT2SS_MCS9))
 663                vht_nss = 2;
 664
 665        return vht_nss;
 666}
 667
 668bool rtl8821ae_rx_query_desc(struct ieee80211_hw *hw,
 669                             struct rtl_stats *status,
 670                             struct ieee80211_rx_status *rx_status,
 671                             u8 *pdesc, struct sk_buff *skb)
 672{
 673        struct rtl_priv *rtlpriv = rtl_priv(hw);
 674        struct rx_fwinfo_8821ae *p_drvinfo;
 675        struct ieee80211_hdr *hdr;
 676
 677        u32 phystatus = GET_RX_DESC_PHYST(pdesc);
 678
 679        status->length = (u16)GET_RX_DESC_PKT_LEN(pdesc);
 680        status->rx_drvinfo_size = (u8)GET_RX_DESC_DRV_INFO_SIZE(pdesc) *
 681            RX_DRV_INFO_SIZE_UNIT;
 682        status->rx_bufshift = (u8)(GET_RX_DESC_SHIFT(pdesc) & 0x03);
 683        status->icv = (u16)GET_RX_DESC_ICV(pdesc);
 684        status->crc = (u16)GET_RX_DESC_CRC32(pdesc);
 685        status->hwerror = (status->crc | status->icv);
 686        status->decrypted = !GET_RX_DESC_SWDEC(pdesc);
 687        status->rate = (u8)GET_RX_DESC_RXMCS(pdesc);
 688        status->shortpreamble = (u16)GET_RX_DESC_SPLCP(pdesc);
 689        status->isampdu = (bool)(GET_RX_DESC_PAGGR(pdesc) == 1);
 690        status->isfirst_ampdu = (bool)(GET_RX_DESC_PAGGR(pdesc) == 1);
 691        status->timestamp_low = GET_RX_DESC_TSFL(pdesc);
 692        status->rx_packet_bw = GET_RX_DESC_BW(pdesc);
 693        status->macid = GET_RX_DESC_MACID(pdesc);
 694        status->is_short_gi = !(bool)GET_RX_DESC_SPLCP(pdesc);
 695        status->is_ht = rtl8821ae_get_rxdesc_is_ht(hw, pdesc);
 696        status->is_vht = rtl8821ae_get_rxdesc_is_vht(hw, pdesc);
 697        status->vht_nss = rtl8821ae_get_rx_vht_nss(hw, pdesc);
 698        status->is_cck = RTL8821AE_RX_HAL_IS_CCK_RATE(status->rate);
 699
 700        RT_TRACE(rtlpriv, COMP_RXDESC, DBG_LOUD,
 701                 "rx_packet_bw=%s,is_ht %d, is_vht %d, vht_nss=%d,is_short_gi %d.\n",
 702                 (status->rx_packet_bw == 2) ? "80M" :
 703                 (status->rx_packet_bw == 1) ? "40M" : "20M",
 704                 status->is_ht, status->is_vht, status->vht_nss,
 705                 status->is_short_gi);
 706
 707        if (GET_RX_STATUS_DESC_RPT_SEL(pdesc))
 708                status->packet_report_type = C2H_PACKET;
 709        else
 710                status->packet_report_type = NORMAL_RX;
 711
 712        if (GET_RX_STATUS_DESC_PATTERN_MATCH(pdesc))
 713                status->wake_match = BIT(2);
 714        else if (GET_RX_STATUS_DESC_MAGIC_MATCH(pdesc))
 715                status->wake_match = BIT(1);
 716        else if (GET_RX_STATUS_DESC_UNICAST_MATCH(pdesc))
 717                status->wake_match = BIT(0);
 718        else
 719                status->wake_match = 0;
 720
 721        if (status->wake_match)
 722                RT_TRACE(rtlpriv, COMP_RXDESC, DBG_LOUD,
 723                         "GGGGGGGGGGGGGet Wakeup Packet!! WakeMatch=%d\n",
 724                         status->wake_match);
 725        rx_status->freq = hw->conf.chandef.chan->center_freq;
 726        rx_status->band = hw->conf.chandef.chan->band;
 727
 728        hdr = (struct ieee80211_hdr *)(skb->data +
 729              status->rx_drvinfo_size + status->rx_bufshift);
 730
 731        if (status->crc)
 732                rx_status->flag |= RX_FLAG_FAILED_FCS_CRC;
 733
 734        if (status->rx_packet_bw == HT_CHANNEL_WIDTH_20_40)
 735                rx_status->flag |= RX_FLAG_40MHZ;
 736        else if (status->rx_packet_bw == HT_CHANNEL_WIDTH_80)
 737                rx_status->vht_flag |= RX_VHT_FLAG_80MHZ;
 738        if (status->is_ht)
 739                rx_status->flag |= RX_FLAG_HT;
 740        if (status->is_vht)
 741                rx_status->flag |= RX_FLAG_VHT;
 742
 743        if (status->is_short_gi)
 744                rx_status->flag |= RX_FLAG_SHORT_GI;
 745
 746        rx_status->vht_nss = status->vht_nss;
 747        rx_status->flag |= RX_FLAG_MACTIME_START;
 748
 749        /* hw will set status->decrypted true, if it finds the
 750         * frame is open data frame or mgmt frame.
 751         * So hw will not decryption robust managment frame
 752         * for IEEE80211w but still set status->decrypted
 753         * true, so here we should set it back to undecrypted
 754         * for IEEE80211w frame, and mac80211 sw will help
 755         * to decrypt it
 756         */
 757        if (status->decrypted) {
 758                if ((!_ieee80211_is_robust_mgmt_frame(hdr)) &&
 759                    (ieee80211_has_protected(hdr->frame_control)))
 760                        rx_status->flag |= RX_FLAG_DECRYPTED;
 761                else
 762                        rx_status->flag &= ~RX_FLAG_DECRYPTED;
 763        }
 764
 765        /* rate_idx: index of data rate into band's
 766         * supported rates or MCS index if HT rates
 767         * are use (RX_FLAG_HT)
 768         */
 769        rx_status->rate_idx =
 770          _rtl8821ae_rate_mapping(hw, status->is_ht,
 771                                  status->is_vht, status->rate);
 772
 773        rx_status->mactime = status->timestamp_low;
 774        if (phystatus) {
 775                p_drvinfo = (struct rx_fwinfo_8821ae *)(skb->data +
 776                            status->rx_bufshift);
 777
 778                translate_rx_signal_stuff(hw, skb, status, pdesc, p_drvinfo);
 779        }
 780        rx_status->signal = status->recvsignalpower + 10;
 781        if (status->packet_report_type == TX_REPORT2) {
 782                status->macid_valid_entry[0] =
 783                  GET_RX_RPT2_DESC_MACID_VALID_1(pdesc);
 784                status->macid_valid_entry[1] =
 785                  GET_RX_RPT2_DESC_MACID_VALID_2(pdesc);
 786        }
 787        return true;
 788}
 789
 790static u8 rtl8821ae_bw_mapping(struct ieee80211_hw *hw,
 791                               struct rtl_tcb_desc *ptcb_desc)
 792{
 793        struct rtl_priv *rtlpriv = rtl_priv(hw);
 794        struct rtl_phy *rtlphy = &rtlpriv->phy;
 795        u8 bw_setting_of_desc = 0;
 796
 797        RT_TRACE(rtlpriv, COMP_SEND, DBG_TRACE,
 798                 "rtl8821ae_bw_mapping, current_chan_bw %d, packet_bw %d\n",
 799                 rtlphy->current_chan_bw, ptcb_desc->packet_bw);
 800
 801        if (rtlphy->current_chan_bw == HT_CHANNEL_WIDTH_80) {
 802                if (ptcb_desc->packet_bw == HT_CHANNEL_WIDTH_80)
 803                        bw_setting_of_desc = 2;
 804                else if (ptcb_desc->packet_bw == HT_CHANNEL_WIDTH_20_40)
 805                        bw_setting_of_desc = 1;
 806                else
 807                        bw_setting_of_desc = 0;
 808        } else if (rtlphy->current_chan_bw == HT_CHANNEL_WIDTH_20_40) {
 809                if ((ptcb_desc->packet_bw == HT_CHANNEL_WIDTH_20_40) ||
 810                    (ptcb_desc->packet_bw == HT_CHANNEL_WIDTH_80))
 811                        bw_setting_of_desc = 1;
 812                else
 813                        bw_setting_of_desc = 0;
 814        } else {
 815                bw_setting_of_desc = 0;
 816        }
 817        return bw_setting_of_desc;
 818}
 819
 820static u8 rtl8821ae_sc_mapping(struct ieee80211_hw *hw,
 821                               struct rtl_tcb_desc *ptcb_desc)
 822{
 823        struct rtl_priv *rtlpriv = rtl_priv(hw);
 824        struct rtl_phy *rtlphy = &rtlpriv->phy;
 825        struct rtl_mac *mac = rtl_mac(rtlpriv);
 826        u8 sc_setting_of_desc = 0;
 827
 828        if (rtlphy->current_chan_bw == HT_CHANNEL_WIDTH_80) {
 829                if (ptcb_desc->packet_bw == HT_CHANNEL_WIDTH_80) {
 830                        sc_setting_of_desc = VHT_DATA_SC_DONOT_CARE;
 831                } else if (ptcb_desc->packet_bw == HT_CHANNEL_WIDTH_20_40) {
 832                        if (mac->cur_80_prime_sc ==
 833                            HAL_PRIME_CHNL_OFFSET_LOWER)
 834                                sc_setting_of_desc =
 835                                        VHT_DATA_SC_40_LOWER_OF_80MHZ;
 836                        else if (mac->cur_80_prime_sc ==
 837                                 HAL_PRIME_CHNL_OFFSET_UPPER)
 838                                sc_setting_of_desc =
 839                                        VHT_DATA_SC_40_UPPER_OF_80MHZ;
 840                        else
 841                                RT_TRACE(rtlpriv, COMP_SEND, DBG_LOUD,
 842                                         "rtl8821ae_sc_mapping: Not Correct Primary40MHz Setting\n");
 843                } else {
 844                        if ((mac->cur_40_prime_sc ==
 845                             HAL_PRIME_CHNL_OFFSET_LOWER) &&
 846                            (mac->cur_80_prime_sc  ==
 847                             HAL_PRIME_CHNL_OFFSET_LOWER))
 848                                sc_setting_of_desc =
 849                                        VHT_DATA_SC_20_LOWEST_OF_80MHZ;
 850                        else if ((mac->cur_40_prime_sc ==
 851                                  HAL_PRIME_CHNL_OFFSET_UPPER) &&
 852                                 (mac->cur_80_prime_sc ==
 853                                  HAL_PRIME_CHNL_OFFSET_LOWER))
 854                                sc_setting_of_desc =
 855                                        VHT_DATA_SC_20_LOWER_OF_80MHZ;
 856                        else if ((mac->cur_40_prime_sc ==
 857                                  HAL_PRIME_CHNL_OFFSET_LOWER) &&
 858                                 (mac->cur_80_prime_sc ==
 859                                  HAL_PRIME_CHNL_OFFSET_UPPER))
 860                                sc_setting_of_desc =
 861                                        VHT_DATA_SC_20_UPPER_OF_80MHZ;
 862                        else if ((mac->cur_40_prime_sc ==
 863                                  HAL_PRIME_CHNL_OFFSET_UPPER) &&
 864                                 (mac->cur_80_prime_sc ==
 865                                  HAL_PRIME_CHNL_OFFSET_UPPER))
 866                                sc_setting_of_desc =
 867                                        VHT_DATA_SC_20_UPPERST_OF_80MHZ;
 868                        else
 869                                RT_TRACE(rtlpriv, COMP_SEND, DBG_LOUD,
 870                                         "rtl8821ae_sc_mapping: Not Correct Primary40MHz Setting\n");
 871                }
 872        } else if (rtlphy->current_chan_bw == HT_CHANNEL_WIDTH_20_40) {
 873                if (ptcb_desc->packet_bw == HT_CHANNEL_WIDTH_20_40) {
 874                        sc_setting_of_desc = VHT_DATA_SC_DONOT_CARE;
 875                } else if (ptcb_desc->packet_bw == HT_CHANNEL_WIDTH_20) {
 876                        if (mac->cur_40_prime_sc ==
 877                                HAL_PRIME_CHNL_OFFSET_UPPER) {
 878                                sc_setting_of_desc =
 879                                        VHT_DATA_SC_20_UPPER_OF_80MHZ;
 880                        } else if (mac->cur_40_prime_sc ==
 881                                HAL_PRIME_CHNL_OFFSET_LOWER){
 882                                sc_setting_of_desc =
 883                                        VHT_DATA_SC_20_LOWER_OF_80MHZ;
 884                        } else {
 885                                sc_setting_of_desc = VHT_DATA_SC_DONOT_CARE;
 886                        }
 887                }
 888        } else {
 889                sc_setting_of_desc = VHT_DATA_SC_DONOT_CARE;
 890        }
 891
 892        return sc_setting_of_desc;
 893}
 894
 895void rtl8821ae_tx_fill_desc(struct ieee80211_hw *hw,
 896                            struct ieee80211_hdr *hdr, u8 *pdesc_tx, u8 *txbd,
 897                            struct ieee80211_tx_info *info,
 898                            struct ieee80211_sta *sta,
 899                            struct sk_buff *skb,
 900                            u8 hw_queue, struct rtl_tcb_desc *ptcb_desc)
 901{
 902        struct rtl_priv *rtlpriv = rtl_priv(hw);
 903        struct rtl_mac *mac = rtl_mac(rtl_priv(hw));
 904        struct rtl_pci *rtlpci = rtl_pcidev(rtl_pcipriv(hw));
 905        struct rtl_hal *rtlhal = rtl_hal(rtlpriv);
 906        u8 *pdesc = (u8 *)pdesc_tx;
 907        u16 seq_number;
 908        __le16 fc = hdr->frame_control;
 909        unsigned int buf_len = 0;
 910        unsigned int skb_len = skb->len;
 911        u8 fw_qsel = _rtl8821ae_map_hwqueue_to_fwqueue(skb, hw_queue);
 912        bool firstseg = ((hdr->seq_ctrl &
 913                          cpu_to_le16(IEEE80211_SCTL_FRAG)) == 0);
 914        bool lastseg = ((hdr->frame_control &
 915                         cpu_to_le16(IEEE80211_FCTL_MOREFRAGS)) == 0);
 916        dma_addr_t mapping;
 917        u8 short_gi = 0;
 918
 919        seq_number = (le16_to_cpu(hdr->seq_ctrl) & IEEE80211_SCTL_SEQ) >> 4;
 920        rtl_get_tcb_desc(hw, info, sta, skb, ptcb_desc);
 921        /* reserve 8 byte for AMPDU early mode */
 922        if (rtlhal->earlymode_enable) {
 923                skb_push(skb, EM_HDR_LEN);
 924                memset(skb->data, 0, EM_HDR_LEN);
 925        }
 926        buf_len = skb->len;
 927        mapping = pci_map_single(rtlpci->pdev, skb->data, skb->len,
 928                                 PCI_DMA_TODEVICE);
 929        if (pci_dma_mapping_error(rtlpci->pdev, mapping)) {
 930                RT_TRACE(rtlpriv, COMP_SEND, DBG_TRACE,
 931                         "DMA mapping error");
 932                return;
 933        }
 934        CLEAR_PCI_TX_DESC_CONTENT(pdesc, sizeof(struct tx_desc_8821ae));
 935        if (ieee80211_is_nullfunc(fc) || ieee80211_is_ctl(fc)) {
 936                firstseg = true;
 937                lastseg = true;
 938        }
 939        if (firstseg) {
 940                if (rtlhal->earlymode_enable) {
 941                        SET_TX_DESC_PKT_OFFSET(pdesc, 1);
 942                        SET_TX_DESC_OFFSET(pdesc, USB_HWDESC_HEADER_LEN +
 943                                           EM_HDR_LEN);
 944                        if (ptcb_desc->empkt_num) {
 945                                RT_TRACE(rtlpriv, COMP_SEND, DBG_TRACE,
 946                                         "Insert 8 byte.pTcb->EMPktNum:%d\n",
 947                                          ptcb_desc->empkt_num);
 948                                _rtl8821ae_insert_emcontent(ptcb_desc,
 949                                         (u8 *)(skb->data));
 950                        }
 951                } else {
 952                        SET_TX_DESC_OFFSET(pdesc, USB_HWDESC_HEADER_LEN);
 953                }
 954
 955                /* ptcb_desc->use_driver_rate = true; */
 956                SET_TX_DESC_TX_RATE(pdesc, ptcb_desc->hw_rate);
 957                if (ptcb_desc->hw_rate > DESC_RATEMCS0)
 958                        short_gi = (ptcb_desc->use_shortgi) ? 1 : 0;
 959                else
 960                        short_gi = (ptcb_desc->use_shortpreamble) ? 1 : 0;
 961
 962                SET_TX_DESC_DATA_SHORTGI(pdesc, short_gi);
 963
 964                if (info->flags & IEEE80211_TX_CTL_AMPDU) {
 965                        SET_TX_DESC_AGG_ENABLE(pdesc, 1);
 966                        SET_TX_DESC_MAX_AGG_NUM(pdesc, 0x1f);
 967                }
 968                SET_TX_DESC_SEQ(pdesc, seq_number);
 969                SET_TX_DESC_RTS_ENABLE(pdesc, ((ptcb_desc->rts_enable &&
 970                                        !ptcb_desc->cts_enable) ? 1 : 0));
 971                SET_TX_DESC_HW_RTS_ENABLE(pdesc, 0);
 972                SET_TX_DESC_CTS2SELF(pdesc, ((ptcb_desc->cts_enable) ? 1 : 0));
 973
 974                SET_TX_DESC_RTS_RATE(pdesc, ptcb_desc->rts_rate);
 975                SET_TX_DESC_RTS_SC(pdesc, ptcb_desc->rts_sc);
 976                SET_TX_DESC_RTS_SHORT(pdesc,
 977                        ((ptcb_desc->rts_rate <= DESC_RATE54M) ?
 978                        (ptcb_desc->rts_use_shortpreamble ? 1 : 0) :
 979                        (ptcb_desc->rts_use_shortgi ? 1 : 0)));
 980
 981                if (ptcb_desc->tx_enable_sw_calc_duration)
 982                        SET_TX_DESC_NAV_USE_HDR(pdesc, 1);
 983
 984                SET_TX_DESC_DATA_BW(pdesc,
 985                        rtl8821ae_bw_mapping(hw, ptcb_desc));
 986
 987                SET_TX_DESC_TX_SUB_CARRIER(pdesc,
 988                        rtl8821ae_sc_mapping(hw, ptcb_desc));
 989
 990                SET_TX_DESC_LINIP(pdesc, 0);
 991                SET_TX_DESC_PKT_SIZE(pdesc, (u16)skb_len);
 992                if (sta) {
 993                        u8 ampdu_density = sta->ht_cap.ampdu_density;
 994
 995                        SET_TX_DESC_AMPDU_DENSITY(pdesc, ampdu_density);
 996                }
 997                if (info->control.hw_key) {
 998                        struct ieee80211_key_conf *keyconf =
 999                                info->control.hw_key;
1000                        switch (keyconf->cipher) {
1001                        case WLAN_CIPHER_SUITE_WEP40:
1002                        case WLAN_CIPHER_SUITE_WEP104:
1003                        case WLAN_CIPHER_SUITE_TKIP:
1004                                SET_TX_DESC_SEC_TYPE(pdesc, 0x1);
1005                                break;
1006                        case WLAN_CIPHER_SUITE_CCMP:
1007                                SET_TX_DESC_SEC_TYPE(pdesc, 0x3);
1008                                break;
1009                        default:
1010                                SET_TX_DESC_SEC_TYPE(pdesc, 0x0);
1011                                break;
1012                        }
1013                }
1014
1015                SET_TX_DESC_QUEUE_SEL(pdesc, fw_qsel);
1016                SET_TX_DESC_DATA_RATE_FB_LIMIT(pdesc, 0x1F);
1017                SET_TX_DESC_RTS_RATE_FB_LIMIT(pdesc, 0xF);
1018                SET_TX_DESC_DISABLE_FB(pdesc, ptcb_desc->disable_ratefallback ?
1019                                       1 : 0);
1020                SET_TX_DESC_USE_RATE(pdesc, ptcb_desc->use_driver_rate ? 1 : 0);
1021
1022                if (ieee80211_is_data_qos(fc)) {
1023                        if (mac->rdg_en) {
1024                                RT_TRACE(rtlpriv, COMP_SEND, DBG_TRACE,
1025                                         "Enable RDG function.\n");
1026                                SET_TX_DESC_RDG_ENABLE(pdesc, 1);
1027                                SET_TX_DESC_HTC(pdesc, 1);
1028                        }
1029                }
1030        }
1031
1032        SET_TX_DESC_FIRST_SEG(pdesc, (firstseg ? 1 : 0));
1033        SET_TX_DESC_LAST_SEG(pdesc, (lastseg ? 1 : 0));
1034        SET_TX_DESC_TX_BUFFER_SIZE(pdesc, (u16)buf_len);
1035        SET_TX_DESC_TX_BUFFER_ADDRESS(pdesc, mapping);
1036        /* if (rtlpriv->dm.useramask) { */
1037        if (1) {
1038                SET_TX_DESC_RATE_ID(pdesc, ptcb_desc->ratr_index);
1039                SET_TX_DESC_MACID(pdesc, ptcb_desc->mac_id);
1040        } else {
1041                SET_TX_DESC_RATE_ID(pdesc, 0xC + ptcb_desc->ratr_index);
1042                SET_TX_DESC_MACID(pdesc, ptcb_desc->mac_id);
1043        }
1044        if (!ieee80211_is_data_qos(fc))  {
1045                SET_TX_DESC_HWSEQ_EN(pdesc, 1);
1046                SET_TX_DESC_HWSEQ_SEL(pdesc, 0);
1047        }
1048        SET_TX_DESC_MORE_FRAG(pdesc, (lastseg ? 0 : 1));
1049        if (is_multicast_ether_addr(ieee80211_get_DA(hdr)) ||
1050            is_broadcast_ether_addr(ieee80211_get_DA(hdr))) {
1051                SET_TX_DESC_BMC(pdesc, 1);
1052        }
1053
1054        rtl8821ae_dm_set_tx_ant_by_tx_info(hw, pdesc, ptcb_desc->mac_id);
1055        RT_TRACE(rtlpriv, COMP_SEND, DBG_TRACE, "\n");
1056}
1057
1058void rtl8821ae_tx_fill_cmddesc(struct ieee80211_hw *hw,
1059                               u8 *pdesc, bool firstseg,
1060                               bool lastseg, struct sk_buff *skb)
1061{
1062        struct rtl_priv *rtlpriv = rtl_priv(hw);
1063        struct rtl_pci *rtlpci = rtl_pcidev(rtl_pcipriv(hw));
1064        u8 fw_queue = QSLT_BEACON;
1065
1066        dma_addr_t mapping = pci_map_single(rtlpci->pdev,
1067                                            skb->data, skb->len,
1068                                            PCI_DMA_TODEVICE);
1069
1070        if (pci_dma_mapping_error(rtlpci->pdev, mapping)) {
1071                RT_TRACE(rtlpriv, COMP_SEND, DBG_TRACE,
1072                         "DMA mapping error");
1073                return;
1074        }
1075        CLEAR_PCI_TX_DESC_CONTENT(pdesc, TX_DESC_SIZE);
1076
1077        SET_TX_DESC_FIRST_SEG(pdesc, 1);
1078        SET_TX_DESC_LAST_SEG(pdesc, 1);
1079
1080        SET_TX_DESC_PKT_SIZE((u8 *)pdesc, (u16)(skb->len));
1081
1082        SET_TX_DESC_OFFSET(pdesc, USB_HWDESC_HEADER_LEN);
1083
1084        SET_TX_DESC_USE_RATE(pdesc, 1);
1085        SET_TX_DESC_TX_RATE(pdesc, DESC_RATE1M);
1086        SET_TX_DESC_DISABLE_FB(pdesc, 1);
1087
1088        SET_TX_DESC_DATA_BW(pdesc, 0);
1089
1090        SET_TX_DESC_HWSEQ_EN(pdesc, 1);
1091
1092        SET_TX_DESC_QUEUE_SEL(pdesc, fw_queue);
1093
1094        SET_TX_DESC_TX_BUFFER_SIZE(pdesc, (u16)(skb->len));
1095
1096        SET_TX_DESC_TX_BUFFER_ADDRESS(pdesc, mapping);
1097
1098        SET_TX_DESC_MACID(pdesc, 0);
1099
1100        SET_TX_DESC_OWN(pdesc, 1);
1101
1102        RT_PRINT_DATA(rtlpriv, COMP_CMD, DBG_LOUD,
1103                      "H2C Tx Cmd Content\n",
1104                      pdesc, TX_DESC_SIZE);
1105}
1106
1107void rtl8821ae_set_desc(struct ieee80211_hw *hw, u8 *pdesc,
1108                        bool istx, u8 desc_name, u8 *val)
1109{
1110        if (istx) {
1111                switch (desc_name) {
1112                case HW_DESC_OWN:
1113                        SET_TX_DESC_OWN(pdesc, 1);
1114                        break;
1115                case HW_DESC_TX_NEXTDESC_ADDR:
1116                        SET_TX_DESC_NEXT_DESC_ADDRESS(pdesc, *(u32 *)val);
1117                        break;
1118                default:
1119                        RT_ASSERT(false,
1120                                  "ERR txdesc :%d not process\n", desc_name);
1121                        break;
1122                }
1123        } else {
1124                switch (desc_name) {
1125                case HW_DESC_RXOWN:
1126                        SET_RX_DESC_OWN(pdesc, 1);
1127                        break;
1128                case HW_DESC_RXBUFF_ADDR:
1129                        SET_RX_DESC_BUFF_ADDR(pdesc, *(u32 *)val);
1130                        break;
1131                case HW_DESC_RXPKT_LEN:
1132                        SET_RX_DESC_PKT_LEN(pdesc, *(u32 *)val);
1133                        break;
1134                case HW_DESC_RXERO:
1135                        SET_RX_DESC_EOR(pdesc, 1);
1136                        break;
1137                default:
1138                        RT_ASSERT(false,
1139                                  "ERR rxdesc :%d not process\n", desc_name);
1140                        break;
1141                }
1142        }
1143}
1144
1145u32 rtl8821ae_get_desc(u8 *pdesc, bool istx, u8 desc_name)
1146{
1147        u32 ret = 0;
1148
1149        if (istx) {
1150                switch (desc_name) {
1151                case HW_DESC_OWN:
1152                        ret = GET_TX_DESC_OWN(pdesc);
1153                        break;
1154                case HW_DESC_TXBUFF_ADDR:
1155                        ret = GET_TX_DESC_TX_BUFFER_ADDRESS(pdesc);
1156                        break;
1157                default:
1158                        RT_ASSERT(false,
1159                                  "ERR txdesc :%d not process\n", desc_name);
1160                        break;
1161                }
1162        } else {
1163                switch (desc_name) {
1164                case HW_DESC_OWN:
1165                        ret = GET_RX_DESC_OWN(pdesc);
1166                        break;
1167                case HW_DESC_RXPKT_LEN:
1168                        ret = GET_RX_DESC_PKT_LEN(pdesc);
1169                        break;
1170                case HW_DESC_RXBUFF_ADDR:
1171                        ret = GET_RX_DESC_BUFF_ADDR(pdesc);
1172                        break;
1173                default:
1174                        RT_ASSERT(false,
1175                                  "ERR rxdesc :%d not process\n", desc_name);
1176                        break;
1177                }
1178        }
1179        return ret;
1180}
1181
1182bool rtl8821ae_is_tx_desc_closed(struct ieee80211_hw *hw,
1183                                 u8 hw_queue, u16 index)
1184{
1185        struct rtl_pci *rtlpci = rtl_pcidev(rtl_pcipriv(hw));
1186        struct rtl8192_tx_ring *ring = &rtlpci->tx_ring[hw_queue];
1187        u8 *entry = (u8 *)(&ring->desc[ring->idx]);
1188        u8 own = (u8)rtl8821ae_get_desc(entry, true, HW_DESC_OWN);
1189
1190        /**
1191         *beacon packet will only use the first
1192         *descriptor defautly,and the own may not
1193         *be cleared by the hardware
1194         */
1195        if (own)
1196                return false;
1197        return true;
1198}
1199
1200void rtl8821ae_tx_polling(struct ieee80211_hw *hw, u8 hw_queue)
1201{
1202        struct rtl_priv *rtlpriv = rtl_priv(hw);
1203
1204        if (hw_queue == BEACON_QUEUE) {
1205                rtl_write_word(rtlpriv, REG_PCIE_CTRL_REG, BIT(4));
1206        } else {
1207                rtl_write_word(rtlpriv, REG_PCIE_CTRL_REG,
1208                               BIT(0) << (hw_queue));
1209        }
1210}
1211
1212u32 rtl8821ae_rx_command_packet(struct ieee80211_hw *hw,
1213                                struct rtl_stats status,
1214                                struct sk_buff *skb)
1215{
1216        u32 result = 0;
1217        struct rtl_priv *rtlpriv = rtl_priv(hw);
1218
1219        switch (status.packet_report_type) {
1220        case NORMAL_RX:
1221                result = 0;
1222                break;
1223        case C2H_PACKET:
1224                rtl8821ae_c2h_packet_handler(hw, skb->data, (u8)skb->len);
1225                result = 1;
1226                RT_TRACE(rtlpriv, COMP_RECV, DBG_LOUD,
1227                         "skb->len=%d\n\n", skb->len);
1228                break;
1229        default:
1230                RT_TRACE(rtlpriv, COMP_RECV, DBG_LOUD,
1231                         "No this packet type!!\n");
1232                break;
1233        }
1234
1235        return result;
1236}
1237