remove ar5416phy.h, we do not use it
[open-ath9k-htc-firmware.git] / target_firmware / wlan / ar5416_hw.c
1 /*
2  * Copyright (c) 2013 Qualcomm Atheros, Inc.
3  * All rights reserved.
4  *
5  * Redistribution and use in source and binary forms, with or without
6  * modification, are permitted (subject to the limitations in the
7  * disclaimer below) provided that the following conditions are met:
8  *
9  *  * Redistributions of source code must retain the above copyright
10  *    notice, this list of conditions and the following disclaimer.
11  *
12  *  * Redistributions in binary form must reproduce the above copyright
13  *    notice, this list of conditions and the following disclaimer in the
14  *    documentation and/or other materials provided with the
15  *    distribution.
16  *
17  *  * Neither the name of Qualcomm Atheros nor the names of its
18  *    contributors may be used to endorse or promote products derived
19  *    from this software without specific prior written permission.
20  *
21  * NO EXPRESS OR IMPLIED LICENSES TO ANY PARTY'S PATENT RIGHTS ARE
22  * GRANTED BY THIS LICENSE.  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT
23  * HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED
24  * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
25  * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
26  * DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
27  * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
28  * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
29  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR
30  * BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
31  * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
32  * OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN
33  * IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
34  */
35
36 #include "opt_ah.h"
37 #include "ah.h"
38 #include "ah_internal.h"
39 #include "ar5416.h"
40 #include "ar5416reg.h"
41 #include "ar5416desc.h"
42
43 #define N(a) (sizeof(a)/sizeof(a[0]))
44 #define AR_INTR_SPURIOUS 0xffffffff
45 #define ar5416_desc ar5416_desc_20
46 #define AR5416_ABORT_LOOPS 1000
47 #define AR5416_ABORT_WAIT  5
48 #define AR5416DESC         AR5416DESC_20
49 #define AR5416DESC_CONST   AR5416DESC_CONST_20
50
51 /*****************/
52 /* Attach/Detach */
53 /*****************/
54
55 static const struct ath_hal_private ar5416hal_10 = {{
56                 .ah_getRateTable        = ar5416GetRateTable,
57                 .ah_detach              = ar5416Detach,
58
59                 /* Transmit functions */
60                 .ah_updateTxTrigLevel   = ar5416UpdateTxTrigLevel,
61                 .ah_getTxDP             = ar5416GetTxDP,
62                 .ah_setTxDP             = ar5416SetTxDP,
63                 .ah_numTxPending        = ar5416NumTxPending,    
64                 .ah_startTxDma          = ar5416StartTxDma,
65                 .ah_stopTxDma           = ar5416StopTxDma,
66         
67                 .ah_getTxIntrQueue      = ar5416GetTxIntrQueue,
68                 .ah_abortTxDma          = ar5416AbortTxDma,
69
70                 /* Misc Functions */
71                 .ah_getCapability       = ar5416GetCapability,
72                 .ah_getTsf32            = ar5416GetTsf32,
73                 .ah_getTsf64            = ar5416GetTsf64,
74                 .ah_resetTsf            = ar5416ResetTsf,
75                 .ah_setRxFilter         = ar5416SetRxFilter,
76
77                 /* RX Functions */
78                 .ah_getRxDP             = ar5416GetRxDP,
79                 .ah_setRxDP             = ar5416SetRxDP,
80                 .ah_stopDmaReceive      = ar5416StopDmaReceive,
81                 .ah_enableReceive       = ar5416EnableReceive,
82                 .ah_startPcuReceive     = ar5416StartPcuReceive,
83                 .ah_stopPcuReceive      = ar5416StopPcuReceive,
84
85                 /* Interrupt Functions */
86                 .ah_isInterruptPending   = ar5416IsInterruptPending,
87                 .ah_getPendingInterrupts = ar5416GetPendingInterrupts,
88                 .ah_getInterrupts        = ar5416GetInterrupts,
89                 .ah_setInterrupts        = ar5416SetInterrupts,
90         },
91 };
92
93 void ar5416Detach(struct ath_hal *ah)
94 {
95         HALASSERT(ah != AH_NULL);
96         ath_hal_free(ah);
97 }
98
99 struct ath_hal *
100 ar5416Attach(a_uint32_t devid,HAL_SOFTC sc, adf_os_device_t dev,
101              a_uint32_t flags, HAL_STATUS *status)
102 {
103         struct ath_hal_5416 *ahp;
104         struct ath_hal *ah;
105
106         ahp = ath_hal_malloc(sizeof (struct ath_hal_5416));
107         if (ahp == AH_NULL) {
108                 *status = HAL_ENOMEM;
109                 return AH_NULL;
110         }
111         ah = &ahp->ah_priv.h;
112
113         OS_MEMCPY(&ahp->ah_priv, &ar5416hal_10, sizeof(struct ath_hal_private));
114
115         ah->ah_dev = dev;
116         ah->ah_sc = sc;
117         
118         /* If its a Owl 2.0 chip then change the hal structure to
119            point to the Owl 2.0 ar5416_hal_20 structure */
120         if(1) {
121                 ah->ah_set11nTxDesc        = ar5416Set11nTxDesc_20;
122                 ah->ah_set11nRateScenario  = ar5416Set11nRateScenario_20;
123                 ah->ah_set11nAggrFirst     = ar5416Set11nAggrFirst_20;
124                 ah->ah_set11nAggrMiddle    = ar5416Set11nAggrMiddle_20;
125                 ah->ah_set11nAggrLast      = ar5416Set11nAggrLast_20;
126                 ah->ah_clr11nAggr          = ar5416Clr11nAggr_20;
127                 ah->ah_set11nBurstDuration = ar5416Set11nBurstDuration_20;
128                 ah->ah_setupRxDesc         = ar5416SetupRxDesc_20;
129                 ah->ah_procRxDescFast      = ar5416ProcRxDescFast_20;
130                 ah->ah_updateCTSForBursting = NULL;
131                 ah->ah_setupTxDesc         = ar5416SetupTxDesc_20;
132                 ah->ah_reqTxIntrDesc       = ar5416IntrReqTxDesc_20;
133                 ah->ah_fillTxDesc          = ar5416FillTxDesc_20;
134                 ah->ah_fillKeyTxDesc       = ar5416FillKeyTxDesc_20;
135                 ah->ah_procTxDesc          = ar5416ProcTxDesc_20;
136                 ah->ah_set11nVirtualMoreFrag = ar5416Set11nVirtualMoreFrag_20;
137         }
138
139         return ah;
140 }
141
142 /**********************/
143 /* Interrupt Handling */
144 /**********************/
145
146 HAL_BOOL ar5416IsInterruptPending(struct ath_hal *ah)
147 {
148         a_uint32_t host_isr = OS_REG_READ(ah, AR_INTR_ASYNC_CAUSE);
149         /*
150          * Some platforms trigger our ISR before applying power to
151          * the card, so make sure.
152          */
153         return ((host_isr != AR_INTR_SPURIOUS) && (host_isr & AR_INTR_MAC_IRQ));
154 }
155
156 HAL_BOOL ar5416GetPendingInterrupts(struct ath_hal *ah, HAL_INT *masked)
157 {
158         a_uint32_t isr;
159 #ifndef AR9100
160         HAL_BOOL fatal_int = AH_FALSE;
161         a_uint32_t sync_cause;
162
163         if (OS_REG_READ(ah, AR_INTR_ASYNC_CAUSE) & AR_INTR_MAC_IRQ) {
164                 if ((OS_REG_READ(ah, AR_RTC_STATUS) & AR_RTC_STATUS_M) != AR_RTC_STATUS_ON) {
165                         *masked = 0;
166                         return AH_FALSE;
167                 }
168         } else {
169                 *masked = 0;
170                 return AH_FALSE;
171         }
172 #endif
173         isr = OS_REG_READ(ah, AR_ISR_RAC);
174         if (isr == 0xffffffff) {
175                 *masked = 0;
176                 return AH_FALSE;
177         }
178
179         *masked = isr & HAL_INT_COMMON;
180
181 #ifdef AR5416_INT_MITIGATION
182         if (isr & (AR_ISR_RXMINTR | AR_ISR_RXINTM)) {
183                 *masked |= HAL_INT_RX;
184         }
185         if (isr & (AR_ISR_TXMINTR | AR_ISR_TXINTM)) {
186                 *masked |= HAL_INT_TX;
187         }
188 #endif
189
190         if (isr & AR_ISR_BCNMISC) {
191                 a_uint32_t s2_s;
192
193                 s2_s = OS_REG_READ(ah, AR_ISR_S2_S);
194
195                 if (s2_s & AR_ISR_S2_GTT) {
196                         *masked |= HAL_INT_GTT;
197                 }
198
199                 if (s2_s & AR_ISR_S2_CST) {
200                         *masked |= HAL_INT_CST;
201                 }
202         }
203
204         if (isr & (AR_ISR_RXOK | AR_ISR_RXERR))
205                 *masked |= HAL_INT_RX;
206         if (isr & (AR_ISR_TXOK | AR_ISR_TXDESC | AR_ISR_TXERR | AR_ISR_TXEOL)) {
207                 struct ath_hal_5416 *ahp = AH5416(ah);
208                 a_uint32_t           s0_s, s1_s;
209
210                 *masked |= HAL_INT_TX;
211                 s0_s = OS_REG_READ(ah, AR_ISR_S0_S);
212                 s1_s = OS_REG_READ(ah, AR_ISR_S1_S);
213                 ahp->ah_intrTxqs |= MS(s0_s, AR_ISR_S0_QCU_TXOK);
214                 ahp->ah_intrTxqs |= MS(s0_s, AR_ISR_S0_QCU_TXDESC);
215                 ahp->ah_intrTxqs |= MS(s1_s, AR_ISR_S1_QCU_TXERR);
216                 ahp->ah_intrTxqs |= MS(s1_s, AR_ISR_S1_QCU_TXEOL);
217         }
218
219 #ifndef AR9100
220         sync_cause = OS_REG_READ(ah, AR_INTR_SYNC_CAUSE);
221         fatal_int = ((sync_cause != AR_INTR_SPURIOUS) &&
222                      (sync_cause & (AR_INTR_SYNC_HOST1_FATAL | AR_INTR_SYNC_HOST1_PERR))) ?
223                 AH_TRUE : AH_FALSE;
224
225         if (AH_TRUE == fatal_int) {
226                 OS_REG_WRITE(ah, AR_INTR_SYNC_CAUSE_CLR, sync_cause);
227                 (void) OS_REG_READ(ah, AR_INTR_SYNC_CAUSE_CLR);
228         }
229 #endif
230         return AH_TRUE;
231 }
232
233 HAL_INT ar5416GetInterrupts(struct ath_hal *ah)
234 {
235         return AH5416(ah)->ah_maskReg;
236 }
237
238 HAL_INT
239 ar5416SetInterrupts(struct ath_hal *ah, HAL_INT ints)
240 {
241         struct ath_hal_5416 *ahp = AH5416(ah);
242         a_uint32_t omask = ahp->ah_maskReg;
243         a_uint32_t mask;
244
245         if (omask & HAL_INT_GLOBAL) {
246                 OS_REG_WRITE(ah, AR_IER, AR_IER_DISABLE);
247                 (void) OS_REG_READ(ah, AR_IER);
248         }
249
250         mask = ints & HAL_INT_COMMON;
251         if (ints & HAL_INT_TX) {
252 #ifdef AR5416_INT_MITIGATION
253                 mask |= AR_IMR_TXMINTR | AR_IMR_TXINTM;
254 #else
255                 mask |= AR_IMR_TXOK;
256                 mask |= AR_IMR_TXDESC;
257 #endif
258                 mask |= AR_IMR_TXERR;
259                 mask |= AR_IMR_TXEOL;
260         }
261         if (ints & HAL_INT_RX) {
262                 mask |= AR_IMR_RXERR;
263 #ifdef AR5416_INT_MITIGATION
264                 mask |=  AR_IMR_RXMINTR | AR_IMR_RXINTM;
265 #else
266                 mask |= AR_IMR_RXOK | AR_IMR_RXDESC;
267 #endif
268         }
269
270         if (ints & (HAL_INT_GTT | HAL_INT_CST)) {
271                 mask |= AR_IMR_BCNMISC;
272         }
273
274         OS_REG_WRITE(ah, AR_IMR, mask);
275         (void) OS_REG_READ(ah, AR_IMR);
276         ahp->ah_maskReg = ints;
277
278         /* Re-enable interrupts if they were enabled before. */
279         if (ints & HAL_INT_GLOBAL) {
280                 OS_REG_WRITE(ah, AR_IER, AR_IER_ENABLE);
281                 /* See explanation above... */
282                 (void) OS_REG_READ(ah, AR_IER);
283         }
284
285         OS_REG_WRITE(ah, AR_INTR_ASYNC_ENABLE, AR_INTR_MAC_IRQ);
286         OS_REG_WRITE(ah, AR_INTR_ASYNC_MASK, AR_INTR_MAC_IRQ);
287         OS_REG_WRITE(ah, AR_INTR_SYNC_ENABLE, AR_INTR_SYNC_ALL);
288
289         return omask;
290 }
291
292 /****************/
293 /* Capabilities */
294 /****************/
295
296 HAL_STATUS ar5416GetCapability(struct ath_hal *ah, HAL_CAPABILITY_TYPE type,
297                                a_uint32_t capability, a_uint32_t *result)
298
299 {
300         return ath_hal_getcapability(ah, type, capability, result);
301 }
302
303 /****************/
304 /* TSF Handling */
305 /****************/
306
307 u_int64_t ar5416GetTsf64(struct ath_hal *ah)
308 {
309         u_int64_t tsf;
310
311         tsf = OS_REG_READ(ah, AR_TSF_U32);
312         tsf = (tsf << 32) | OS_REG_READ(ah, AR_TSF_L32);
313
314         return tsf;
315 }
316
317 a_uint32_t ar5416GetTsf32(struct ath_hal *ah)
318 {
319         return OS_REG_READ(ah, AR_TSF_L32);
320 }
321
322 void ar5416ResetTsf(struct ath_hal *ah)
323 {
324         a_int32_t count;
325
326         count = 0;
327
328         while (OS_REG_READ(ah, AR_SLP32_MODE) & AR_SLP32_TSF_WRITE_STATUS) {
329                 count++;
330                 if (count > 10) {
331                         break;
332                 }
333                 OS_DELAY(10);
334         }
335         OS_REG_WRITE(ah, AR_RESET_TSF, AR_RESET_TSF_ONCE);
336 }
337
338 /******/
339 /* RX */
340 /******/
341
342 a_uint32_t ar5416GetRxDP(struct ath_hal *ath)
343 {
344         return OS_REG_READ(ath, AR_RXDP);
345 }
346
347
348 void ar5416SetRxDP(struct ath_hal *ah, a_uint32_t rxdp)
349 {
350         OS_REG_WRITE(ah, AR_RXDP, rxdp);
351         HALASSERT(OS_REG_READ(ah, AR_RXDP) == rxdp);
352 }
353
354 void ar5416SetMulticastFilter(struct ath_hal *ah, a_uint32_t filter0, a_uint32_t filter1)
355 {
356         OS_REG_WRITE(ah, AR_MCAST_FIL0, filter0);
357         OS_REG_WRITE(ah, AR_MCAST_FIL1, filter1);
358 }
359
360 HAL_BOOL ar5416ClrMulticastFilterIndex(struct ath_hal *ah, a_uint32_t ix)
361 {
362         a_uint32_t val;
363
364         if (ix >= 64)
365                 return AH_FALSE;
366         if (ix >= 32) {
367                 val = OS_REG_READ(ah, AR_MCAST_FIL1);
368                 OS_REG_WRITE(ah, AR_MCAST_FIL1, (val &~ (1<<(ix-32))));
369         } else {
370                 val = OS_REG_READ(ah, AR_MCAST_FIL0);
371                 OS_REG_WRITE(ah, AR_MCAST_FIL0, (val &~ (1<<ix)));
372         }
373         return AH_TRUE;
374 }
375
376 HAL_BOOL ar5416StopDmaReceive(struct ath_hal *ah)
377 {
378         OS_REG_WRITE(ah, AR_CR, AR_CR_RXD); /* Set receive disable bit */
379         if (!ath_hal_wait(ah, AR_CR, AR_CR_RXE, 0)) {
380                 return AH_FALSE;
381         } else {
382                 return AH_TRUE;
383         }
384 }
385
386 HAL_BOOL ar5416SetMulticastFilterIndex(struct ath_hal *ah, a_uint32_t ix)
387 {
388         a_uint32_t val;
389
390         if (ix >= 64)
391                 return AH_FALSE;
392         if (ix >= 32) {
393                 val = OS_REG_READ(ah, AR_MCAST_FIL1);
394                 OS_REG_WRITE(ah, AR_MCAST_FIL1, (val | (1<<(ix-32))));
395         } else {
396                 val = OS_REG_READ(ah, AR_MCAST_FIL0);
397                 OS_REG_WRITE(ah, AR_MCAST_FIL0, (val | (1<<ix)));
398         }
399         return AH_TRUE;
400 }
401
402 void ar5416StartPcuReceive(struct ath_hal *ah)
403 {
404         OS_REG_CLR_BIT(ah, AR_DIAG_SW,
405                        (AR_DIAG_RX_DIS | AR_DIAG_RX_ABORT));
406 }
407
408 void ar5416SetRxFilter(struct ath_hal *ah, a_uint32_t bits)
409 {
410         a_uint32_t phybits;
411     
412         OS_REG_WRITE(ah, AR_RX_FILTER, (bits & 0xff) | AR_RX_COMPR_BAR);
413         phybits = 0;
414         if (bits & HAL_RX_FILTER_PHYRADAR)
415                 phybits |= AR_PHY_ERR_RADAR;
416         if (bits & HAL_RX_FILTER_PHYERR)
417                 phybits |= AR_PHY_ERR_OFDM_TIMING | AR_PHY_ERR_CCK_TIMING;
418         OS_REG_WRITE(ah, AR_PHY_ERR, phybits);
419         if (phybits) {
420                 OS_REG_WRITE(ah, AR_RXCFG,OS_REG_READ(ah, AR_RXCFG) | AR_RXCFG_ZLFDMA);
421         } else {
422                 OS_REG_WRITE(ah, AR_RXCFG,OS_REG_READ(ah, AR_RXCFG) &~ AR_RXCFG_ZLFDMA);
423         }
424 }
425
426 void ar5416EnableReceive(struct ath_hal *ah)
427 {
428         OS_REG_WRITE(ah, AR_CR, AR_CR_RXE);
429 }
430
431 void ar5416StopPcuReceive(struct ath_hal *ah)
432 {
433         OS_REG_SET_BIT(ah, AR_DIAG_SW, AR_DIAG_RX_DIS);
434 }
435
436 HAL_BOOL ar5416SetupRxDesc_20(struct ath_hal *ah, struct ath_rx_desc *ds,
437                               a_uint32_t size, a_uint32_t flags)
438 {
439         struct ar5416_desc *ads = AR5416DESC(ds);
440
441         HALASSERT((size &~ AR_BufLen) == 0);
442
443         ads->ds_ctl1 = size & AR_BufLen;
444         if (flags & HAL_RXDESC_INTREQ)
445                 ads->ds_ctl1 |= AR_RxIntrReq;
446
447         /* this should be enough */
448         ads->ds_rxstatus8 &= ~AR_RxDone;
449
450         return AH_TRUE;
451 }
452
453 HAL_STATUS ar5416ProcRxDescFast_20(struct ath_hal *ah, struct ath_rx_desc *ds,
454                                    a_uint32_t pa, struct ath_desc *nds,
455                                    struct ath_rx_status *rx_stats)
456 {
457         struct ar5416_desc ads;
458         struct ar5416_desc *adsp = AR5416DESC(ds);
459         struct ar5416_desc *ands = AR5416DESC(nds);
460
461         if ((adsp->ds_rxstatus8 & AR_RxDone) == 0)
462                 return HAL_EINPROGRESS;
463         /*
464          * Given the use of a self-linked tail be very sure that the hw is
465          * done with this descriptor; the hw may have done this descriptor
466          * once and picked it up again...make sure the hw has moved on.
467          */
468         if ((ands->ds_rxstatus8 & AR_RxDone) == 0
469             && OS_REG_READ(ah, AR_RXDP) == pa)
470                 return HAL_EINPROGRESS;
471
472         /*
473          * Now we need to get the stats from the descriptor. Since desc are 
474          * uncached, lets make a copy of the stats first. Note that, since we
475          * touch most of the rx stats, a memcpy would always be more efficient
476          *
477          * Next we fill in all values in a caller passed stack variable.
478          * This reduces the number of uncached accesses.
479          * Do this copy here, after the check so that when the checks fail, we
480          * dont end up copying the entire stats uselessly.
481          */
482         ads.u.rx = adsp->u.rx;
483
484         rx_stats->rs_status = 0;
485         rx_stats->rs_flags = 0;
486
487         rx_stats->rs_datalen = ads.ds_rxstatus1 & AR_DataLen;
488         rx_stats->rs_tstamp =  ads.AR_RcvTimestamp;
489
490         /* XXX what about KeyCacheMiss? */
491         rx_stats->rs_rssi_combined = 
492                 MS(ads.ds_rxstatus4, AR_RxRSSICombined);
493         rx_stats->rs_rssi_ctl0 = MS(ads.ds_rxstatus0, AR_RxRSSIAnt00);
494         rx_stats->rs_rssi_ctl1 = MS(ads.ds_rxstatus0, AR_RxRSSIAnt01);
495         rx_stats->rs_rssi_ctl2 = MS(ads.ds_rxstatus0, AR_RxRSSIAnt02);
496         rx_stats->rs_rssi_ext0 = MS(ads.ds_rxstatus4, AR_RxRSSIAnt10);
497         rx_stats->rs_rssi_ext1 = MS(ads.ds_rxstatus4, AR_RxRSSIAnt11);
498         rx_stats->rs_rssi_ext2 = MS(ads.ds_rxstatus4, AR_RxRSSIAnt12);
499         if (ads.ds_rxstatus8 & AR_RxKeyIdxValid)
500                 rx_stats->rs_keyix = MS(ads.ds_rxstatus8, AR_KeyIdx);
501         else
502                 rx_stats->rs_keyix = HAL_RXKEYIX_INVALID;
503         /* NB: caller expected to do rate table mapping */
504         rx_stats->rs_rate = RXSTATUS_RATE(ah, (&ads));
505         rx_stats->rs_more = (ads.ds_rxstatus1 & AR_RxMore) ? 1 : 0;
506
507         rx_stats->rs_isaggr = (ads.ds_rxstatus8 & AR_RxAggr) ? 1 : 0;
508         rx_stats->rs_moreaggr = (ads.ds_rxstatus8 & AR_RxMoreAggr) ? 1 : 0;
509         rx_stats->rs_flags  |= (ads.ds_rxstatus3 & AR_GI) ? HAL_RX_GI : 0;
510         rx_stats->rs_flags  |= (ads.ds_rxstatus3 & AR_2040) ? HAL_RX_2040 : 0;
511
512         if (ads.ds_rxstatus8 & AR_PreDelimCRCErr)
513                 rx_stats->rs_flags |= HAL_RX_DELIM_CRC_PRE;
514         if (ads.ds_rxstatus8 & AR_PostDelimCRCErr)
515                 rx_stats->rs_flags |= HAL_RX_DELIM_CRC_POST;
516         if (ads.ds_rxstatus8 & AR_DecryptBusyErr)
517                 rx_stats->rs_flags |= HAL_RX_DECRYPT_BUSY;
518
519         if ((ads.ds_rxstatus8 & AR_RxFrameOK) == 0) {
520                 /*
521                  * These four bits should not be set together.  The
522                  * 5416 spec states a Michael error can only occur if
523                  * DecryptCRCErr not set (and TKIP is used).  Experience
524                  * indicates however that you can also get Michael errors
525                  * when a CRC error is detected, but these are specious.
526                  * Consequently we filter them out here so we don't
527                  * confuse and/or complicate drivers.
528                  */
529                 if (ads.ds_rxstatus8 & AR_CRCErr)
530                         rx_stats->rs_status |= HAL_RXERR_CRC;
531                 else if (ads.ds_rxstatus8 & AR_PHYErr) {
532                         a_uint32_t phyerr;
533
534                         rx_stats->rs_status |= HAL_RXERR_PHY;
535                         phyerr = MS(ads.ds_rxstatus8, AR_PHYErrCode);
536                         rx_stats->rs_phyerr = phyerr;
537                 } else if (ads.ds_rxstatus8 & AR_DecryptCRCErr)
538                         rx_stats->rs_status |= HAL_RXERR_DECRYPT;
539                 else if (ads.ds_rxstatus8 & AR_MichaelErr)
540                         rx_stats->rs_status |= HAL_RXERR_MIC;
541         }
542         rx_stats->evm0=ads.AR_RxEVM0;
543         rx_stats->evm1=ads.AR_RxEVM1;
544         rx_stats->evm2=ads.AR_RxEVM2;
545
546         return HAL_OK;
547 }
548
549 /******/
550 /* TX */
551 /******/
552
553 HAL_BOOL ar5416UpdateTxTrigLevel(struct ath_hal *ah, HAL_BOOL bIncTrigLevel)
554 {
555         struct ath_hal_5416 *ahp = AH5416(ah);
556         a_uint32_t txcfg, curLevel, newLevel;
557         HAL_INT omask;
558
559         /*
560          * Disable interrupts while futzing with the fifo level.
561          */
562         omask = ar5416SetInterrupts(ah, ahp->ah_maskReg &~ HAL_INT_GLOBAL);
563
564         txcfg = OS_REG_READ(ah, AR_TXCFG);
565         curLevel = MS(txcfg, AR_FTRIG);
566         newLevel = curLevel;
567
568         if (bIncTrigLevel)  {
569                 if (curLevel < MAX_TX_FIFO_THRESHOLD)
570                         newLevel ++;
571         } else if (curLevel > MIN_TX_FIFO_THRESHOLD)
572                 newLevel--;
573         if (newLevel != curLevel)
574                 OS_REG_WRITE(ah, AR_TXCFG,
575                              (txcfg &~ AR_FTRIG) | SM(newLevel, AR_FTRIG));
576
577         /* re-enable chip interrupts */
578         ar5416SetInterrupts(ah, omask);
579
580         return (newLevel != curLevel);
581 }
582
583 a_uint32_t ar5416GetTxDP(struct ath_hal *ah, a_uint32_t q)
584 {
585         HALASSERT(q < AH_PRIVATE(ah)->ah_caps.halTotalQueues);
586         return OS_REG_READ(ah, AR_QTXDP(q));
587 }
588
589 HAL_BOOL ar5416SetTxDP(struct ath_hal *ah, a_uint32_t q, a_uint32_t txdp)
590 {
591         HALASSERT(q < AH_PRIVATE(ah)->ah_caps.halTotalQueues);
592         HALASSERT(AH5416(ah)->ah_txq[q].tqi_type != HAL_TX_QUEUE_INACTIVE);
593
594         /*
595          * Make sure that TXE is deasserted before setting the TXDP.  If TXE
596          * is still asserted, setting TXDP will have no effect.
597          */
598         HALASSERT((OS_REG_READ(ah, AR_Q_TXE) & (1 << q)) == 0);
599
600         OS_REG_WRITE(ah, AR_QTXDP(q), txdp);
601
602         return AH_TRUE;
603 }
604
605 HAL_BOOL ar5416StartTxDma(struct ath_hal *ah, a_uint32_t q)
606 {
607         HALASSERT(q < AH_PRIVATE(ah)->ah_caps.halTotalQueues);
608         HALASSERT(AH5416(ah)->ah_txq[q].tqi_type != HAL_TX_QUEUE_INACTIVE);
609
610         /* Check to be sure we're not enabling a q that has its TXD bit set. */
611         HALASSERT((OS_REG_READ(ah, AR_Q_TXD) & (1 << q)) == 0);
612
613         OS_REG_WRITE(ah, AR_Q_TXE, 1 << q);
614
615         return AH_TRUE;
616 }
617
618 a_uint32_t ar5416NumTxPending(struct ath_hal *ah, a_uint32_t q)
619 {
620         a_uint32_t npend;
621
622         HALASSERT(q < AH_PRIVATE(ah)->ah_caps.halTotalQueues);
623         HALASSERT(AH5416(ah)->ah_txq[q].tqi_type != HAL_TX_QUEUE_INACTIVE);
624
625         npend = OS_REG_READ(ah, AR_QSTS(q)) & AR_Q_STS_PEND_FR_CNT;
626         if (npend == 0) {
627                 /*
628                  * Pending frame count (PFC) can momentarily go to zero
629                  * while TXE remains asserted.  In other words a PFC of
630                  * zero is not sufficient to say that the queue has stopped.
631                  */
632                 if (OS_REG_READ(ah, AR_Q_TXE) & (1 << q))
633                         npend = 1;
634         }
635 #ifdef DEBUG
636         if (npend && (AH5416(ah)->ah_txq[q].tqi_type == HAL_TX_QUEUE_CAB)) {
637                 if (OS_REG_READ(ah, AR_Q_RDYTIMESHDN) & (1 << q)) {
638                         isrPrintf("RTSD on CAB queue\n");
639                         /* Clear the ReadyTime shutdown status bits */
640                         OS_REG_WRITE(ah, AR_Q_RDYTIMESHDN, 1 << q);
641                 }
642         }
643 #endif
644         return npend;
645 }
646
647 HAL_BOOL ar5416AbortTxDma(struct ath_hal *ah)
648 {
649         a_int32_t i, q;
650
651         /*
652          * set txd on all queues
653          */
654         OS_REG_WRITE(ah, AR_Q_TXD, AR_Q_TXD_M);
655
656         /*
657          * set tx abort bits
658          */
659         OS_REG_SET_BIT(ah, AR_PCU_MISC, (AR_PCU_FORCE_QUIET_COLL | AR_PCU_CLEAR_VMF));
660         OS_REG_SET_BIT(ah, AR_DIAG_SW, AR_DIAG_FORCE_CH_IDLE_HIGH);
661         OS_REG_SET_BIT(ah, AR_D_GBL_IFS_MISC, AR_D_GBL_IFS_MISC_IGNORE_BACKOFF);
662
663         /*
664          * wait on all tx queues
665          */
666         for (q = 0; q < AR_NUM_QCU; q++) {
667                 for (i = 0; i < AR5416_ABORT_LOOPS; i++) {
668                         if (!ar5416NumTxPending(ah, q))
669                                 break;
670
671                         OS_DELAY(AR5416_ABORT_WAIT);
672                 }
673                 if (i == AR5416_ABORT_LOOPS) {
674                         return AH_FALSE;
675                 }
676         }
677
678         /*
679          * clear tx abort bits
680          */
681         OS_REG_CLR_BIT(ah, AR_PCU_MISC, (AR_PCU_FORCE_QUIET_COLL | AR_PCU_CLEAR_VMF));
682         OS_REG_CLR_BIT(ah, AR_DIAG_SW, AR_DIAG_FORCE_CH_IDLE_HIGH);
683         OS_REG_CLR_BIT(ah, AR_D_GBL_IFS_MISC, AR_D_GBL_IFS_MISC_IGNORE_BACKOFF);
684
685         /*
686          * clear txd
687          */
688         OS_REG_WRITE(ah, AR_Q_TXD, 0);
689
690         return AH_TRUE;
691 }
692
693 HAL_BOOL ar5416StopTxDma(struct ath_hal*ah, a_uint32_t q)
694 {
695         a_uint32_t i;
696         
697         HALASSERT(q < AH_PRIVATE(ah)->ah_caps.halTotalQueues);
698
699         HALASSERT(AH5416(ah)->ah_txq[q].tqi_type != HAL_TX_QUEUE_INACTIVE);
700
701         OS_REG_WRITE(ah, AR_Q_TXD, 1 << q);
702         for (i = 1000; i != 0; i--) {
703                 if (ar5416NumTxPending(ah, q) == 0)
704                         break;
705                 OS_DELAY(100);        /* XXX get actual value */
706         }
707
708         OS_REG_WRITE(ah, AR_Q_TXD, 0);
709         return (i != 0);
710 }
711
712 void ar5416GetTxIntrQueue(struct ath_hal *ah, a_uint32_t *txqs)
713 {
714         struct ath_hal_5416 *ahp = AH5416(ah);
715         *txqs &= ahp->ah_intrTxqs;
716         ahp->ah_intrTxqs &= ~(*txqs);
717 }
718
719 void ar5416IntrReqTxDesc_20(struct ath_hal *ah, struct ath_desc *ds)
720 {
721         struct ar5416_desc *ads = AR5416DESC(ds);
722         ads->ds_ctl0 |= AR_TxIntrReq;
723 }
724
725 HAL_BOOL ar5416SetupTxDesc_20(struct ath_hal *ah, struct ath_tx_desc *ds,
726                               a_uint32_t pktLen,
727                               a_uint32_t hdrLen,
728                               HAL_PKT_TYPE type,
729                               a_uint32_t txPower,
730                               a_uint32_t txRate0, a_uint32_t txTries0,
731                               a_uint32_t keyIx,
732                               a_uint32_t antMode,
733                               a_uint32_t flags,
734                               a_uint32_t rtsctsRate,
735                               a_uint32_t rtsctsDuration,
736                               a_uint32_t compicvLen,
737                               a_uint32_t compivLen,
738                               a_uint32_t comp)
739 {
740 #define RTSCTS  (HAL_TXDESC_RTSENA|HAL_TXDESC_CTSENA)
741
742         struct ar5416_desc *ads = AR5416DESC(ds);
743
744         (void) hdrLen;
745
746         ads->ds_txstatus9 &= ~AR_TxDone;
747
748         HALASSERT(txTries0 != 0);
749         HALASSERT(isValidPktType(type));
750         HALASSERT(isValidTxRate(txRate0));
751         HALASSERT((flags & RTSCTS) != RTSCTS);
752
753         if (txPower > 63)
754                 txPower=63;
755
756         ads->ds_ctl0 = (pktLen & AR_FrameLen)
757                 | (txPower << AR_XmitPower_S)
758                 | (flags & HAL_TXDESC_VEOL ? AR_VEOL : 0)
759                 | (flags & HAL_TXDESC_CLRDMASK ? AR_ClrDestMask : 0)
760                 | (flags & HAL_TXDESC_INTREQ ? AR_TxIntrReq : 0);
761
762         ads->ds_ctl1 = (type << AR_FrameType_S)
763                 | (flags & HAL_TXDESC_NOACK ? AR_NoAck : 0);
764         ads->ds_ctl2 = SM(txTries0, AR_XmitDataTries0);
765         ads->ds_ctl3 = (txRate0 << AR_XmitRate0_S);
766
767         ads->ds_ctl7 = SM(AR5416_LEGACY_CHAINMASK, AR_ChainSel0) 
768                 | SM(AR5416_LEGACY_CHAINMASK, AR_ChainSel1)
769                 | SM(AR5416_LEGACY_CHAINMASK, AR_ChainSel2) 
770                 | SM(AR5416_LEGACY_CHAINMASK, AR_ChainSel3);
771
772         if (keyIx != HAL_TXKEYIX_INVALID) {
773                 /* XXX validate key index */
774                 ads->ds_ctl1 |= SM(keyIx, AR_DestIdx);
775                 ads->ds_ctl0 |= AR_DestIdxValid;
776         }
777
778         if (flags & RTSCTS) {
779                 if (!isValidTxRate(rtsctsRate)) {
780                         return AH_FALSE;
781                 }
782                 /* XXX validate rtsctsDuration */
783                 ads->ds_ctl0 |= (flags & HAL_TXDESC_CTSENA ? AR_CTSEnable : 0)
784                         | (flags & HAL_TXDESC_RTSENA ? AR_RTSEnable : 0);
785                 ads->ds_ctl2 |= SM(rtsctsDuration, AR_BurstDur);
786                 ads->ds_ctl3 |= (rtsctsRate << AR_RTSCTSRate_S);
787         }
788         return AH_TRUE;
789
790 #undef RTSCTS
791 }
792
793 HAL_BOOL ar5416FillTxDesc_20(struct ath_hal *ah, struct ath_tx_desc *ds,
794                              a_uint32_t segLen, HAL_BOOL firstSeg, HAL_BOOL lastSeg,
795                              const struct ath_tx_desc *ds0)
796 {
797         struct ar5416_desc *ads = AR5416DESC(ds);
798
799         HALASSERT((segLen &~ AR_BufLen) == 0);
800
801         if (firstSeg) {
802                 /*
803                  * First descriptor, don't clobber xmit control data
804                  * setup by ar5416SetupTxDesc.
805                  */
806                 ads->ds_ctl1 |= segLen | (lastSeg ? 0 : AR_TxMore);
807         } else if (lastSeg) {
808                 /*
809                  * Last descriptor in a multi-descriptor frame,
810                  * copy the multi-rate transmit parameters from
811                  * the first frame for processing on completion.
812                  */
813                 ads->ds_ctl0 = 0;
814                 ads->ds_ctl1 = segLen;
815                 ads->ds_ctl2 = AR5416DESC_CONST(ds0)->ds_ctl2;
816                 ads->ds_ctl3 = AR5416DESC_CONST(ds0)->ds_ctl3;
817         } else {
818                 /*
819                  * Intermediate descriptor in a multi-descriptor frame.
820                  */
821                 ads->ds_ctl0 = 0;
822                 ads->ds_ctl1 = segLen | AR_TxMore;
823                 ads->ds_ctl2 = 0;
824                 ads->ds_ctl3 = 0;
825         }
826         ads->ds_txstatus0 = ads->ds_txstatus1 = 0;
827
828         return AH_TRUE;
829 }
830
831 HAL_BOOL ar5416FillKeyTxDesc_20(struct ath_hal *ah, struct ath_tx_desc *ds,
832                                 HAL_KEY_TYPE keyType)
833 {
834         struct ar5416_desc *ads = AR5416DESC(ds);
835
836         ads->ds_ctl6 = SM(keyType, AR_EncrType);
837         return AH_TRUE;
838 }
839
840 HAL_STATUS ar5416ProcTxDesc_20(struct ath_hal *ah, struct ath_tx_desc *gds)
841 {
842         struct ar5416_desc *ads = AR5416DESC(gds);
843         struct ath_tx_desc *ds = (struct ath_tx_desc *)gds;
844         
845         if ((ads->ds_txstatus9 & AR_TxDone) == 0)
846                 return HAL_EINPROGRESS;
847
848         ads->ds_txstatus9 &= ~AR_TxDone;
849
850         /* Update software copies of the HW status */
851         ds->ds_txstat.ts_seqnum = MS(ads->ds_txstatus9, AR_SeqNum);
852         ds->ds_txstat.ts_tstamp = ads->AR_SendTimestamp;
853         ds->ds_txstat.ts_status = 0;
854         ds->ds_txstat.ts_flags  = 0;
855
856         if (ads->ds_txstatus1 & AR_ExcessiveRetries)
857                 ds->ds_txstat.ts_status |= HAL_TXERR_XRETRY;
858         if (ads->ds_txstatus1 & AR_Filtered)
859                 ds->ds_txstat.ts_status |= HAL_TXERR_FILT;
860         if (ads->ds_txstatus1 & AR_FIFOUnderrun)
861                 ds->ds_txstat.ts_status |= HAL_TXERR_FIFO;
862         if (ads->ds_txstatus9 & AR_TxOpExceeded)
863                 ds->ds_txstat.ts_status |= HAL_TXERR_XTXOP;
864         if (ads->ds_txstatus1 & AR_TxTimerExpired)
865                 ds->ds_txstat.ts_status |= HAL_TXERR_TIMER_EXPIRED;
866
867         if (ads->ds_txstatus1 & AR_DescCfgErr)
868                 ds->ds_txstat.ts_flags |= HAL_TX_DESC_CFG_ERR;
869         if (ads->ds_txstatus1 & AR_TxDataUnderrun) {
870                 ds->ds_txstat.ts_flags |= HAL_TX_DATA_UNDERRUN;
871                 ar5416UpdateTxTrigLevel(ah, AH_TRUE);
872         }
873         if (ads->ds_txstatus1 & AR_TxDelimUnderrun) {
874                 ds->ds_txstat.ts_flags |= HAL_TX_DELIM_UNDERRUN;
875                 ar5416UpdateTxTrigLevel(ah, AH_TRUE);
876         }
877         if (ads->ds_txstatus0 & AR_TxBaStatus) {
878                 ds->ds_txstat.ts_flags |= HAL_TX_BA;
879                 ds->ds_txstat.ba_low = ads->AR_BaBitmapLow;
880                 ds->ds_txstat.ba_high = ads->AR_BaBitmapHigh;
881         }
882
883         /*
884          * Extract the transmit rate used and mark the rate as
885          * ``alternate'' if it wasn't the series 0 rate.
886          */
887         ds->ds_txstat.ts_rate = MS(ads->ds_txstatus9, AR_FinalTxIdx);
888         ds->ds_txstat.ts_rssi_combined = 
889                 MS(ads->ds_txstatus5, AR_TxRSSICombined);
890         ds->ds_txstat.ts_rssi_ctl0 = MS(ads->ds_txstatus0, AR_TxRSSIAnt00);
891         ds->ds_txstat.ts_rssi_ctl1 = MS(ads->ds_txstatus0, AR_TxRSSIAnt01);
892         ds->ds_txstat.ts_rssi_ctl2 = MS(ads->ds_txstatus0, AR_TxRSSIAnt02);
893         ds->ds_txstat.ts_rssi_ext0 = MS(ads->ds_txstatus5, AR_TxRSSIAnt10);
894         ds->ds_txstat.ts_rssi_ext1 = MS(ads->ds_txstatus5, AR_TxRSSIAnt11);
895         ds->ds_txstat.ts_rssi_ext2 = MS(ads->ds_txstatus5, AR_TxRSSIAnt12);
896         ds->ds_txstat.evm0 = ads->AR_TxEVM0;
897         ds->ds_txstat.evm1 = ads->AR_TxEVM1;
898         ds->ds_txstat.evm2 = ads->AR_TxEVM2;
899         ds->ds_txstat.ts_shortretry = MS(ads->ds_txstatus1, AR_RTSFailCnt);
900         ds->ds_txstat.ts_longretry = MS(ads->ds_txstatus1, AR_DataFailCnt);
901         ds->ds_txstat.ts_virtcol = MS(ads->ds_txstatus1, AR_VirtRetryCnt);
902         ds->ds_txstat.ts_antenna = 0;           /* ignored for owl */
903
904         return HAL_OK;
905 }
906
907 void ar5416Set11nTxDesc_20(struct ath_hal *ah, struct ath_tx_desc *ds,
908                            a_uint32_t pktLen, HAL_PKT_TYPE type, a_uint32_t txPower,
909                            a_uint32_t keyIx, HAL_KEY_TYPE keyType,
910                            a_uint32_t flags)
911 {
912         struct ar5416_desc *ads = AR5416DESC(ds);
913
914         HALASSERT(isValidPktType(type));
915         HALASSERT(isValidKeyType(keyType));
916
917         if (txPower > 63)
918                 txPower = 63;
919
920         ads->ds_ctl0 = (pktLen & AR_FrameLen)
921                 | (flags & HAL_TXDESC_VMF ? AR_VirtMoreFrag : 0)
922                 | SM(txPower, AR_XmitPower)
923                 | (flags & HAL_TXDESC_RTSENA ? AR_RTSEnable : 0)
924                 | (flags & HAL_TXDESC_VEOL ? AR_VEOL : 0)
925                 | (flags & HAL_TXDESC_CLRDMASK ? AR_ClrDestMask : 0)
926                 | (flags & HAL_TXDESC_INTREQ ? AR_TxIntrReq : 0)
927                 | (keyIx != HAL_TXKEYIX_INVALID ? AR_DestIdxValid : 0)
928                 | (flags & HAL_TXDESC_CTSENA ? AR_CTSEnable : 0);
929
930         ads->ds_ctl1 = (keyIx != HAL_TXKEYIX_INVALID ? SM(keyIx, AR_DestIdx) : 0)
931                 | SM(type, AR_FrameType)
932                 | (flags & HAL_TXDESC_NOACK ? AR_NoAck : 0)
933                 | (flags & HAL_TXDESC_EXT_ONLY ? AR_ExtOnly : 0)
934                 | (flags & HAL_TXDESC_EXT_AND_CTL ? AR_ExtAndCtl : 0);
935
936         ads->ds_ctl6 = SM(keyType, AR_EncrType);
937 }
938
939 #ifdef MAGPIE_MERLIN
940
941 void ar5416Set11nRateScenario_20(struct ath_hal *ah, struct ath_tx_desc *ds,
942                                  a_uint32_t durUpdateEn, a_uint32_t rtsctsRate,
943                                  a_uint32_t rtsctsDuration,
944                                  HAL_11N_RATE_SERIES series[], a_uint32_t nseries,
945                                  a_uint32_t flags)
946 {
947         struct ar5416_desc *ads = AR5416DESC(ds);
948         a_uint32_t ds_ctl0;
949
950         HALASSERT(nseries == 4);
951         (void)nseries;
952
953         /*
954          * Rate control settings override
955          */
956         ds_ctl0 = ads->ds_ctl0;
957
958         if (flags & (HAL_TXDESC_RTSENA | HAL_TXDESC_CTSENA)) {
959                 if (flags & HAL_TXDESC_RTSENA) {
960                         ds_ctl0 &= ~AR_CTSEnable;
961                         ds_ctl0 |= AR_RTSEnable;
962                 } else {
963                         ds_ctl0 &= ~AR_RTSEnable;
964                         ds_ctl0 |= AR_CTSEnable;
965                 }
966         } else {
967                 ds_ctl0 = (ds_ctl0 & ~(AR_RTSEnable | AR_CTSEnable));
968         }
969
970         ads->ds_ctl0 = ds_ctl0;
971
972         ads->ds_ctl2 = set11nTries(series, 0)
973                 |  set11nTries(series, 1)
974                 |  set11nTries(series, 2)
975                 |  set11nTries(series, 3)
976                 |  (durUpdateEn ? AR_DurUpdateEn : 0);
977
978         ads->ds_ctl3 = set11nRate(series, 0)
979                 |  set11nRate(series, 1)
980                 |  set11nRate(series, 2)
981                 |  set11nRate(series, 3);
982
983         ads->ds_ctl4 = set11nPktDurRTSCTS(series, 0)
984                 |  set11nPktDurRTSCTS(series, 1);
985
986         ads->ds_ctl5 = set11nPktDurRTSCTS(series, 2)
987                 |  set11nPktDurRTSCTS(series, 3);
988
989         ads->ds_ctl7 = set11nRateFlags(series, 0)
990                 |  set11nRateFlags(series, 1)
991                 |  set11nRateFlags(series, 2)
992                 |  set11nRateFlags(series, 3)
993                 | SM(rtsctsRate, AR_RTSCTSRate);
994 }
995
996 #else
997
998 void ar5416Set11nRateScenario_20(struct ath_hal *ah, struct ath_tx_desc *ds,
999                                  a_uint32_t durUpdateEn, a_uint32_t rtsctsRate,
1000                                  a_uint32_t rtsctsDuration,
1001                                  HAL_11N_RATE_SERIES series[], a_uint32_t nseries,
1002                                  a_uint32_t flags)
1003 {
1004         struct ar5416_desc *ads = AR5416DESC(ds);
1005         a_uint32_t ds_ctl0;
1006
1007         HALASSERT(nseries == 4);
1008         (void)nseries;
1009
1010         /*
1011          * Rate control settings override
1012          */
1013         if (flags & (HAL_TXDESC_RTSENA | HAL_TXDESC_CTSENA)) {
1014                 ds_ctl0 = ads->ds_ctl0;
1015
1016                 if (flags & HAL_TXDESC_RTSENA) {
1017                         ds_ctl0 &= ~AR_CTSEnable;
1018                         ds_ctl0 |= AR_RTSEnable;
1019                 } else {
1020                         ds_ctl0 &= ~AR_RTSEnable;
1021                         ds_ctl0 |= AR_CTSEnable;
1022                 }
1023
1024                 ads->ds_ctl0 = ds_ctl0;
1025         }
1026
1027         ads->ds_ctl2 = set11nTries(series, 0)
1028                 |  set11nTries(series, 1)
1029                 |  set11nTries(series, 2)
1030                 |  set11nTries(series, 3)
1031                 |  (durUpdateEn ? AR_DurUpdateEn : 0);
1032
1033         ads->ds_ctl3 = set11nRate(series, 0)
1034                 |  set11nRate(series, 1)
1035                 |  set11nRate(series, 2)
1036                 |  set11nRate(series, 3);
1037
1038         ads->ds_ctl4 = set11nPktDurRTSCTS(series, 0)
1039                 |  set11nPktDurRTSCTS(series, 1);
1040
1041         ads->ds_ctl5 = set11nPktDurRTSCTS(series, 2)
1042                 |  set11nPktDurRTSCTS(series, 3);
1043
1044         ads->ds_ctl7 = set11nRateFlags(series, 0)
1045                 |  set11nRateFlags(series, 1)
1046                 |  set11nRateFlags(series, 2)
1047                 |  set11nRateFlags(series, 3)
1048                 | SM(rtsctsRate, AR_RTSCTSRate);
1049 }
1050
1051 #endif
1052
1053 void ar5416Set11nAggrFirst_20(struct ath_hal *ah, struct ath_tx_desc *ds, a_uint32_t aggrLen,
1054                               a_uint32_t numDelims)
1055 {
1056         struct ar5416_desc *ads = AR5416DESC(ds);
1057
1058         ads->ds_ctl1 |= (AR_IsAggr | AR_MoreAggr);
1059
1060         ads->ds_ctl6 &= ~(AR_AggrLen | AR_PadDelim);
1061         ads->ds_ctl6 |= SM(aggrLen, AR_AggrLen) |
1062                 SM(numDelims, AR_PadDelim);
1063 }
1064
1065 void ar5416Set11nAggrMiddle_20(struct ath_hal *ah, struct ath_tx_desc *ds, a_uint32_t numDelims)
1066 {
1067         struct ar5416_desc *ads = AR5416DESC(ds);
1068         a_uint32_t ctl6;
1069
1070         ads->ds_ctl1 |= (AR_IsAggr | AR_MoreAggr);
1071
1072         /*
1073          * We use a stack variable to manipulate ctl6 to reduce uncached 
1074          * read modify, modfiy, write.
1075          */
1076         ctl6 = ads->ds_ctl6;
1077         ctl6 &= ~AR_PadDelim;
1078         ctl6 |= SM(numDelims, AR_PadDelim);
1079         ads->ds_ctl6 = ctl6;
1080 }
1081
1082 void ar5416Set11nAggrLast_20(struct ath_hal *ah, struct ath_tx_desc *ds)
1083 {
1084         struct ar5416_desc *ads = AR5416DESC(ds);
1085
1086         ads->ds_ctl1 |= AR_IsAggr;
1087         ads->ds_ctl1 &= ~AR_MoreAggr;
1088         ads->ds_ctl6 &= ~AR_PadDelim;
1089 }
1090
1091 void ar5416Clr11nAggr_20(struct ath_hal *ah, struct ath_tx_desc *ds)
1092 {
1093         struct ar5416_desc *ads = AR5416DESC(ds);
1094
1095         ads->ds_ctl1 &= (~AR_IsAggr & ~AR_MoreAggr);
1096 }
1097
1098 void ar5416Set11nBurstDuration_20(struct ath_hal *ah, struct ath_tx_desc *ds,
1099                                   a_uint32_t burstDuration)
1100 {
1101         struct ar5416_desc *ads = AR5416DESC(ds);
1102
1103         ads->ds_ctl2 &= ~AR_BurstDur;
1104         ads->ds_ctl2 |= SM(burstDuration, AR_BurstDur);
1105 }
1106
1107 void ar5416Set11nVirtualMoreFrag_20(struct ath_hal *ah, struct ath_tx_desc *ds,
1108                                     a_uint32_t vmf)
1109 {
1110         struct ar5416_desc *ads = AR5416DESC(ds);
1111
1112         if (vmf) {
1113                 ads->ds_ctl0 |= AR_VirtMoreFrag;
1114         } else {
1115                 ads->ds_ctl0 &= ~AR_VirtMoreFrag;
1116         }
1117 }