Initial import of binutils 2.22 on the new vendor branch
[dragonfly.git] / sys / dev / netif / ath / hal / ath_hal / ar5312 / ar5312_reset.c
1 /*
2  * Copyright (c) 2002-2009 Sam Leffler, Errno Consulting
3  * Copyright (c) 2002-2008 Atheros Communications, Inc.
4  *
5  * Permission to use, copy, modify, and/or distribute this software for any
6  * purpose with or without fee is hereby granted, provided that the above
7  * copyright notice and this permission notice appear in all copies.
8  *
9  * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
10  * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
11  * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
12  * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
13  * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
14  * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
15  * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
16  *
17  * $FreeBSD: head/sys/dev/ath/ath_hal/ar5312/ar5312_reset.c 187831 2009-01-28 18:00:22Z sam $
18  * $DragonFly$
19  */
20 #include "opt_ah.h"
21
22 #ifdef AH_SUPPORT_AR5312
23
24 #include "ah.h"
25 #include "ah_internal.h"
26 #include "ah_devid.h"
27
28 #include "ar5312/ar5312.h"
29 #include "ar5312/ar5312reg.h"
30 #include "ar5312/ar5312phy.h"
31
32 #include "ah_eeprom_v3.h"
33
34 /* Additional Time delay to wait after activiting the Base band */
35 #define BASE_ACTIVATE_DELAY     100     /* 100 usec */
36 #define PLL_SETTLE_DELAY        300     /* 300 usec */
37
38 extern int16_t ar5212GetNf(struct ath_hal *, const struct ieee80211_channel *);
39 extern void ar5212SetRateDurationTable(struct ath_hal *,
40                 const struct ieee80211_channel *);
41 extern HAL_BOOL ar5212SetTransmitPower(struct ath_hal *ah,
42                  const struct ieee80211_channel *chan, uint16_t *rfXpdGain);
43 extern void ar5212SetDeltaSlope(struct ath_hal *,
44                  const struct ieee80211_channel *);
45 extern HAL_BOOL ar5212SetBoardValues(struct ath_hal *,
46                  const struct ieee80211_channel *);
47 extern void ar5212SetIFSTiming(struct ath_hal *,
48                  const struct ieee80211_channel *);
49 extern HAL_BOOL ar5212IsSpurChannel(struct ath_hal *,
50                  const struct ieee80211_channel *);
51 extern HAL_BOOL ar5212ChannelChange(struct ath_hal *,
52                  const struct ieee80211_channel *);
53
54 static HAL_BOOL ar5312SetResetReg(struct ath_hal *, uint32_t resetMask);
55
56 static int
57 write_common(struct ath_hal *ah, const HAL_INI_ARRAY *ia,
58         HAL_BOOL bChannelChange, int writes)
59 {
60 #define IS_NO_RESET_TIMER_ADDR(x)                      \
61     ( (((x) >= AR_BEACON) && ((x) <= AR_CFP_DUR)) || \
62       (((x) >= AR_SLEEP1) && ((x) <= AR_SLEEP3)))
63 #define V(r, c) (ia)->data[((r)*(ia)->cols) + (c)]
64         int i;
65
66         /* Write Common Array Parameters */
67         for (i = 0; i < ia->rows; i++) {
68                 uint32_t reg = V(i, 0);
69                 /* XXX timer/beacon setup registers? */
70                 /* On channel change, don't reset the PCU registers */
71                 if (!(bChannelChange && IS_NO_RESET_TIMER_ADDR(reg))) {
72                         OS_REG_WRITE(ah, reg, V(i, 1));
73                         DMA_YIELD(writes);
74                 }
75         }
76         return writes;
77 #undef IS_NO_RESET_TIMER_ADDR
78 #undef V
79 }
80
81 /*
82  * Places the device in and out of reset and then places sane
83  * values in the registers based on EEPROM config, initialization
84  * vectors (as determined by the mode), and station configuration
85  *
86  * bChannelChange is used to preserve DMA/PCU registers across
87  * a HW Reset during channel change.
88  */
89 HAL_BOOL
90 ar5312Reset(struct ath_hal *ah, HAL_OPMODE opmode,
91         struct ieee80211_channel *chan,
92         HAL_BOOL bChannelChange, HAL_STATUS *status)
93 {
94 #define N(a)    (sizeof (a) / sizeof (a[0]))
95 #define FAIL(_code)     do { ecode = _code; goto bad; } while (0)
96         struct ath_hal_5212 *ahp = AH5212(ah);
97         HAL_CHANNEL_INTERNAL *ichan;
98         const HAL_EEPROM *ee;
99         uint32_t saveFrameSeqCount, saveDefAntenna;
100         uint32_t macStaId1, synthDelay, txFrm2TxDStart;
101         uint16_t rfXpdGain[MAX_NUM_PDGAINS_PER_CHANNEL];
102         int16_t cckOfdmPwrDelta = 0;
103         u_int modesIndex, freqIndex;
104         HAL_STATUS ecode;
105         int i, regWrites = 0;
106         uint32_t testReg;
107         uint32_t saveLedState = 0;
108
109         HALASSERT(ah->ah_magic == AR5212_MAGIC);
110         ee = AH_PRIVATE(ah)->ah_eeprom;
111
112         OS_MARK(ah, AH_MARK_RESET, bChannelChange);
113         /*
114          * Map public channel to private.
115          */
116         ichan = ath_hal_checkchannel(ah, chan);
117         if (ichan == AH_NULL) {
118                 HALDEBUG(ah, HAL_DEBUG_ANY,
119                     "%s: invalid channel %u/0x%x; no mapping\n",
120                     __func__, chan->ic_freq, chan->ic_flags);
121                 FAIL(HAL_EINVAL);
122         }
123         switch (opmode) {
124         case HAL_M_STA:
125         case HAL_M_IBSS:
126         case HAL_M_HOSTAP:
127         case HAL_M_MONITOR:
128                 break;
129         default:
130                 HALDEBUG(ah, HAL_DEBUG_ANY, "%s: invalid operating mode %u\n",
131                     __func__, opmode);
132                 FAIL(HAL_EINVAL);
133                 break;
134         }
135         HALASSERT(ahp->ah_eeversion >= AR_EEPROM_VER3);
136
137         /* Preserve certain DMA hardware registers on a channel change */
138         if (bChannelChange) {
139                 /*
140                  * On Venice, the TSF is almost preserved across a reset;
141                  * it requires the doubling writes to the RESET_TSF
142                  * bit in the AR_BEACON register; it also has the quirk
143                  * of the TSF going back in time on the station (station
144                  * latches onto the last beacon's tsf during a reset 50%
145                  * of the times); the latter is not a problem for adhoc
146                  * stations since as long as the TSF is behind, it will
147                  * get resynchronized on receiving the next beacon; the
148                  * TSF going backwards in time could be a problem for the
149                  * sleep operation (supported on infrastructure stations
150                  * only) - the best and most general fix for this situation
151                  * is to resynchronize the various sleep/beacon timers on
152                  * the receipt of the next beacon i.e. when the TSF itself
153                  * gets resynchronized to the AP's TSF - power save is
154                  * needed to be temporarily disabled until that time
155                  *
156                  * Need to save the sequence number to restore it after
157                  * the reset!
158                  */
159                 saveFrameSeqCount = OS_REG_READ(ah, AR_D_SEQNUM);
160         } else
161                 saveFrameSeqCount = 0;          /* NB: silence compiler */
162
163         /* If the channel change is across the same mode - perform a fast channel change */
164         if ((IS_2413(ah) || IS_5413(ah))) {
165                 /*
166                  * Channel change can only be used when:
167                  *  -channel change requested - so it's not the initial reset.
168                  *  -it's not a change to the current channel - often called when switching modes
169                  *   on a channel
170                  *  -the modes of the previous and requested channel are the same - some ugly code for XR
171                  */
172                 if (bChannelChange &&
173                     AH_PRIVATE(ah)->ah_curchan != AH_NULL &&
174                     (chan->ic_freq != AH_PRIVATE(ah)->ah_curchan->ic_freq) &&
175                     ((chan->ic_flags & IEEE80211_CHAN_ALLTURBO) ==
176                      (AH_PRIVATE(ah)->ah_curchan->ic_flags & IEEE80211_CHAN_ALLTURBO))) {
177                         if (ar5212ChannelChange(ah, chan))
178                                 /* If ChannelChange completed - skip the rest of reset */
179                                 return AH_TRUE;
180                 }
181         }
182
183         /*
184          * Preserve the antenna on a channel change
185          */
186         saveDefAntenna = OS_REG_READ(ah, AR_DEF_ANTENNA);
187         if (saveDefAntenna == 0)                /* XXX magic constants */
188                 saveDefAntenna = 1;
189
190         /* Save hardware flag before chip reset clears the register */
191         macStaId1 = OS_REG_READ(ah, AR_STA_ID1) & 
192                 (AR_STA_ID1_BASE_RATE_11B | AR_STA_ID1_USE_DEFANT);
193
194         /* Save led state from pci config register */
195         if (!IS_5315(ah))
196                 saveLedState = OS_REG_READ(ah, AR5312_PCICFG) &
197                         (AR_PCICFG_LEDCTL | AR_PCICFG_LEDMODE | AR_PCICFG_LEDBLINK |
198                          AR_PCICFG_LEDSLOW);
199
200         ar5312RestoreClock(ah, opmode);         /* move to refclk operation */
201
202         /*
203          * Adjust gain parameters before reset if
204          * there's an outstanding gain updated.
205          */
206         (void) ar5212GetRfgain(ah);
207
208         if (!ar5312ChipReset(ah, chan)) {
209                 HALDEBUG(ah, HAL_DEBUG_ANY, "%s: chip reset failed\n", __func__);
210                 FAIL(HAL_EIO);
211         }
212
213         /* Setup the indices for the next set of register array writes */
214         if (IEEE80211_IS_CHAN_2GHZ(chan)) {
215                 freqIndex  = 2;
216                 modesIndex = IEEE80211_IS_CHAN_108G(chan) ? 5 :
217                              IEEE80211_IS_CHAN_G(chan) ? 4 : 3;
218         } else {
219                 freqIndex  = 1;
220                 modesIndex = IEEE80211_IS_CHAN_ST(chan) ? 2 : 1;
221         }
222
223         OS_MARK(ah, AH_MARK_RESET_LINE, __LINE__);
224
225         /* Set correct Baseband to analog shift setting to access analog chips. */
226         OS_REG_WRITE(ah, AR_PHY(0), 0x00000007);
227
228         regWrites = ath_hal_ini_write(ah, &ahp->ah_ini_modes, modesIndex, 0);
229         regWrites = write_common(ah, &ahp->ah_ini_common, bChannelChange,
230                 regWrites);
231         ahp->ah_rfHal->writeRegs(ah, modesIndex, freqIndex, regWrites);
232
233         OS_MARK(ah, AH_MARK_RESET_LINE, __LINE__);
234
235         if (IEEE80211_IS_CHAN_HALF(chan) || IEEE80211_IS_CHAN_QUARTER(chan))
236                 ar5212SetIFSTiming(ah, chan);
237
238         /* Overwrite INI values for revised chipsets */
239         if (AH_PRIVATE(ah)->ah_phyRev >= AR_PHY_CHIP_ID_REV_2) {
240                 /* ADC_CTL */
241                 OS_REG_WRITE(ah, AR_PHY_ADC_CTL,
242                              SM(2, AR_PHY_ADC_CTL_OFF_INBUFGAIN) |
243                              SM(2, AR_PHY_ADC_CTL_ON_INBUFGAIN) |
244                              AR_PHY_ADC_CTL_OFF_PWDDAC |
245                              AR_PHY_ADC_CTL_OFF_PWDADC);
246                 
247                 /* TX_PWR_ADJ */
248                 if (chan->channel == 2484) {
249                         cckOfdmPwrDelta = SCALE_OC_DELTA(ee->ee_cckOfdmPwrDelta - ee->ee_scaledCh14FilterCckDelta);
250                 } else {
251                         cckOfdmPwrDelta = SCALE_OC_DELTA(ee->ee_cckOfdmPwrDelta);
252                 }
253                 
254                 if (IEEE80211_IS_CHAN_G(chan)) {
255                         OS_REG_WRITE(ah, AR_PHY_TXPWRADJ,
256                                      SM((ee->ee_cckOfdmPwrDelta*-1), AR_PHY_TXPWRADJ_CCK_GAIN_DELTA) |
257                                      SM((cckOfdmPwrDelta*-1), AR_PHY_TXPWRADJ_CCK_PCDAC_INDEX));
258                 } else {
259                         OS_REG_WRITE(ah, AR_PHY_TXPWRADJ, 0);
260                 }
261                 
262                 /* Add barker RSSI thresh enable as disabled */
263                 OS_REG_CLR_BIT(ah, AR_PHY_DAG_CTRLCCK,
264                                AR_PHY_DAG_CTRLCCK_EN_RSSI_THR);
265                 OS_REG_RMW_FIELD(ah, AR_PHY_DAG_CTRLCCK,
266                                  AR_PHY_DAG_CTRLCCK_RSSI_THR, 2);
267                 
268                 /* Set the mute mask to the correct default */
269                 OS_REG_WRITE(ah, AR_SEQ_MASK, 0x0000000F);
270         }
271         
272         if (AH_PRIVATE(ah)->ah_phyRev >= AR_PHY_CHIP_ID_REV_3) {
273                 /* Clear reg to alllow RX_CLEAR line debug */
274                 OS_REG_WRITE(ah, AR_PHY_BLUETOOTH,  0);
275         }
276         if (AH_PRIVATE(ah)->ah_phyRev >= AR_PHY_CHIP_ID_REV_4) {
277 #ifdef notyet
278                 /* Enable burst prefetch for the data queues */
279                 OS_REG_RMW_FIELD(ah, AR_D_FPCTL, ... );
280                 /* Enable double-buffering */
281                 OS_REG_CLR_BIT(ah, AR_TXCFG, AR_TXCFG_DBL_BUF_DIS);
282 #endif
283         }
284
285         if (IS_5312_2_X(ah)) {
286                 /* ADC_CTRL */
287                 OS_REG_WRITE(ah, AR_PHY_SIGMA_DELTA,
288                              SM(2, AR_PHY_SIGMA_DELTA_ADC_SEL) |
289                              SM(4, AR_PHY_SIGMA_DELTA_FILT2) |
290                              SM(0x16, AR_PHY_SIGMA_DELTA_FILT1) |
291                              SM(0, AR_PHY_SIGMA_DELTA_ADC_CLIP));
292
293                 if (IEEE80211_IS_CHAN_2GHZ(chan))
294                         OS_REG_RMW_FIELD(ah, AR_PHY_RXGAIN, AR_PHY_RXGAIN_TXRX_RF_MAX, 0x0F);
295
296                 /* CCK Short parameter adjustment in 11B mode */
297                 if (IEEE80211_IS_CHAN_B(chan))
298                         OS_REG_RMW_FIELD(ah, AR_PHY_CCK_RXCTRL4, AR_PHY_CCK_RXCTRL4_FREQ_EST_SHORT, 12);
299
300                 /* Set ADC/DAC select values */
301                 OS_REG_WRITE(ah, AR_PHY_SLEEP_SCAL, 0x04);
302
303                 /* Increase 11A AGC Settling */
304                 if (IEEE80211_IS_CHAN_A(chan))
305                         OS_REG_RMW_FIELD(ah, AR_PHY_SETTLING, AR_PHY_SETTLING_AGC, 32);
306         } else {
307                 /* Set ADC/DAC select values */
308                 OS_REG_WRITE(ah, AR_PHY_SLEEP_SCAL, 0x0e);
309         }
310
311         /* Setup the transmit power values. */
312         if (!ar5212SetTransmitPower(ah, chan, rfXpdGain)) {
313                 HALDEBUG(ah, HAL_DEBUG_ANY,
314                     "%s: error init'ing transmit power\n", __func__);
315                 FAIL(HAL_EIO);
316         }
317
318         /* Write the analog registers */
319         if (!ahp->ah_rfHal->setRfRegs(ah, chan, modesIndex, rfXpdGain)) {
320                 HALDEBUG(ah, HAL_DEBUG_ANY, "%s: ar5212SetRfRegs failed\n",
321                     __func__);
322                 FAIL(HAL_EIO);
323         }
324
325         /* Write delta slope for OFDM enabled modes (A, G, Turbo) */
326         if (IEEE80211_IS_CHAN_OFDM(chan)) {
327                 if (IS_5413(ah) ||
328                    AH_PRIVATE(ah)->ah_eeversion >= AR_EEPROM_VER5_3)
329                         ar5212SetSpurMitigation(ah, chan);
330                 ar5212SetDeltaSlope(ah, chan);
331         }
332
333         /* Setup board specific options for EEPROM version 3 */
334         if (!ar5212SetBoardValues(ah, chan)) {
335                 HALDEBUG(ah, HAL_DEBUG_ANY,
336                     "%s: error setting board options\n", __func__);
337                 FAIL(HAL_EIO);
338         }
339
340         /* Restore certain DMA hardware registers on a channel change */
341         if (bChannelChange)
342                 OS_REG_WRITE(ah, AR_D_SEQNUM, saveFrameSeqCount);
343
344         OS_MARK(ah, AH_MARK_RESET_LINE, __LINE__);
345
346         OS_REG_WRITE(ah, AR_STA_ID0, LE_READ_4(ahp->ah_macaddr));
347         OS_REG_WRITE(ah, AR_STA_ID1, LE_READ_2(ahp->ah_macaddr + 4)
348                 | macStaId1
349                 | AR_STA_ID1_RTS_USE_DEF
350                 | ahp->ah_staId1Defaults
351         );
352         ar5212SetOperatingMode(ah, opmode);
353
354         /* Set Venice BSSID mask according to current state */
355         OS_REG_WRITE(ah, AR_BSSMSKL, LE_READ_4(ahp->ah_bssidmask));
356         OS_REG_WRITE(ah, AR_BSSMSKU, LE_READ_2(ahp->ah_bssidmask + 4));
357
358         /* Restore previous led state */
359         if (!IS_5315(ah))
360                 OS_REG_WRITE(ah, AR5312_PCICFG, OS_REG_READ(ah, AR_PCICFG) | saveLedState);
361
362         /* Restore previous antenna */
363         OS_REG_WRITE(ah, AR_DEF_ANTENNA, saveDefAntenna);
364
365         /* then our BSSID */
366         OS_REG_WRITE(ah, AR_BSS_ID0, LE_READ_4(ahp->ah_bssid));
367         OS_REG_WRITE(ah, AR_BSS_ID1, LE_READ_2(ahp->ah_bssid + 4));
368
369         /* Restore bmiss rssi & count thresholds */
370         OS_REG_WRITE(ah, AR_RSSI_THR, ahp->ah_rssiThr);
371
372         OS_REG_WRITE(ah, AR_ISR, ~0);           /* cleared on write */
373
374         if (!ar5212SetChannel(ah, chan))
375                 FAIL(HAL_EIO);
376
377         OS_MARK(ah, AH_MARK_RESET_LINE, __LINE__);
378
379         ar5212SetCoverageClass(ah, AH_PRIVATE(ah)->ah_coverageClass, 1);
380
381         ar5212SetRateDurationTable(ah, chan);
382
383         /* Set Tx frame start to tx data start delay */
384         if (IS_RAD5112_ANY(ah) &&
385             (IEEE80211_IS_CHAN_HALF(chan) || IEEE80211_IS_CHAN_QUARTER(chan))) {
386                 txFrm2TxDStart = 
387                         IEEE80211_IS_CHAN_HALF(chan) ?
388                                         TX_FRAME_D_START_HALF_RATE:
389                                         TX_FRAME_D_START_QUARTER_RATE;
390                 OS_REG_RMW_FIELD(ah, AR_PHY_TX_CTL, 
391                         AR_PHY_TX_FRAME_TO_TX_DATA_START, txFrm2TxDStart);
392         }
393
394         /*
395          * Setup fast diversity.
396          * Fast diversity can be enabled or disabled via regadd.txt.
397          * Default is enabled.
398          * For reference,
399          *    Disable: reg        val
400          *             0x00009860 0x00009d18 (if 11a / 11g, else no change)
401          *             0x00009970 0x192bb514
402          *             0x0000a208 0xd03e4648
403          *
404          *    Enable:  0x00009860 0x00009d10 (if 11a / 11g, else no change)
405          *             0x00009970 0x192fb514
406          *             0x0000a208 0xd03e6788
407          */
408
409         /* XXX Setup pre PHY ENABLE EAR additions */
410
411         /* flush SCAL reg */
412         if (IS_5312_2_X(ah)) {
413                 (void) OS_REG_READ(ah, AR_PHY_SLEEP_SCAL);
414         }
415
416         /*
417          * Wait for the frequency synth to settle (synth goes on
418          * via AR_PHY_ACTIVE_EN).  Read the phy active delay register.
419          * Value is in 100ns increments.
420          */
421         synthDelay = OS_REG_READ(ah, AR_PHY_RX_DELAY) & AR_PHY_RX_DELAY_DELAY;
422         if (IEEE80211_IS_CHAN_B(chan)) {
423                 synthDelay = (4 * synthDelay) / 22;
424         } else {
425                 synthDelay /= 10;
426         }
427
428         /* Activate the PHY (includes baseband activate and synthesizer on) */
429         OS_REG_WRITE(ah, AR_PHY_ACTIVE, AR_PHY_ACTIVE_EN);
430
431         /* 
432          * There is an issue if the AP starts the calibration before
433          * the base band timeout completes.  This could result in the
434          * rx_clear false triggering.  As a workaround we add delay an
435          * extra BASE_ACTIVATE_DELAY usecs to ensure this condition
436          * does not happen.
437          */
438         if (IEEE80211_IS_CHAN_HALF(chan)) {
439                 OS_DELAY((synthDelay << 1) + BASE_ACTIVATE_DELAY);
440         } else if (IEEE80211_IS_CHAN_QUARTER(chan)) {
441                 OS_DELAY((synthDelay << 2) + BASE_ACTIVATE_DELAY);
442         } else {
443                 OS_DELAY(synthDelay + BASE_ACTIVATE_DELAY);
444         }
445
446         /*
447          * The udelay method is not reliable with notebooks.
448          * Need to check to see if the baseband is ready
449          */
450         testReg = OS_REG_READ(ah, AR_PHY_TESTCTRL);
451         /* Selects the Tx hold */
452         OS_REG_WRITE(ah, AR_PHY_TESTCTRL, AR_PHY_TESTCTRL_TXHOLD);
453         i = 0;
454         while ((i++ < 20) &&
455                (OS_REG_READ(ah, 0x9c24) & 0x10)) /* test if baseband not ready */               OS_DELAY(200);
456         OS_REG_WRITE(ah, AR_PHY_TESTCTRL, testReg);
457
458         /* Calibrate the AGC and start a NF calculation */
459         OS_REG_WRITE(ah, AR_PHY_AGC_CONTROL,
460                   OS_REG_READ(ah, AR_PHY_AGC_CONTROL)
461                 | AR_PHY_AGC_CONTROL_CAL
462                 | AR_PHY_AGC_CONTROL_NF);
463
464         if (!IEEE80211_IS_CHAN_B(chan) && ahp->ah_bIQCalibration != IQ_CAL_DONE) {
465                 /* Start IQ calibration w/ 2^(INIT_IQCAL_LOG_COUNT_MAX+1) samples */
466                 OS_REG_RMW_FIELD(ah, AR_PHY_TIMING_CTRL4, 
467                         AR_PHY_TIMING_CTRL4_IQCAL_LOG_COUNT_MAX,
468                         INIT_IQCAL_LOG_COUNT_MAX);
469                 OS_REG_SET_BIT(ah, AR_PHY_TIMING_CTRL4,
470                         AR_PHY_TIMING_CTRL4_DO_IQCAL);
471                 ahp->ah_bIQCalibration = IQ_CAL_RUNNING;
472         } else
473                 ahp->ah_bIQCalibration = IQ_CAL_INACTIVE;
474
475         /* Setup compression registers */
476         ar5212SetCompRegs(ah);
477
478         /* Set 1:1 QCU to DCU mapping for all queues */
479         for (i = 0; i < AR_NUM_DCU; i++)
480                 OS_REG_WRITE(ah, AR_DQCUMASK(i), 1 << i);
481
482         ahp->ah_intrTxqs = 0;
483         for (i = 0; i < AH_PRIVATE(ah)->ah_caps.halTotalQueues; i++)
484                 ar5212ResetTxQueue(ah, i);
485
486         /*
487          * Setup interrupt handling.  Note that ar5212ResetTxQueue
488          * manipulates the secondary IMR's as queues are enabled
489          * and disabled.  This is done with RMW ops to insure the
490          * settings we make here are preserved.
491          */
492         ahp->ah_maskReg = AR_IMR_TXOK | AR_IMR_TXERR | AR_IMR_TXURN
493                         | AR_IMR_RXOK | AR_IMR_RXERR | AR_IMR_RXORN
494                         | AR_IMR_HIUERR
495                         ;
496         if (opmode == HAL_M_HOSTAP)
497                 ahp->ah_maskReg |= AR_IMR_MIB;
498         OS_REG_WRITE(ah, AR_IMR, ahp->ah_maskReg);
499         /* Enable bus errors that are OR'd to set the HIUERR bit */
500         OS_REG_WRITE(ah, AR_IMR_S2,
501                 OS_REG_READ(ah, AR_IMR_S2)
502                 | AR_IMR_S2_MCABT | AR_IMR_S2_SSERR | AR_IMR_S2_DPERR);
503
504         if (AH_PRIVATE(ah)->ah_rfkillEnabled)
505                 ar5212EnableRfKill(ah);
506
507         if (!ath_hal_wait(ah, AR_PHY_AGC_CONTROL, AR_PHY_AGC_CONTROL_CAL, 0)) {
508                 HALDEBUG(ah, HAL_DEBUG_ANY,
509                     "%s: offset calibration failed to complete in 1ms;"
510                     " noisy environment?\n", __func__);
511         }
512
513         /*
514          * Set clocks back to 32kHz if they had been using refClk, then
515          * use an external 32kHz crystal when sleeping, if one exists.
516          */
517         ar5312SetupClock(ah, opmode);
518
519         /*
520          * Writing to AR_BEACON will start timers. Hence it should
521          * be the last register to be written. Do not reset tsf, do
522          * not enable beacons at this point, but preserve other values
523          * like beaconInterval.
524          */
525         OS_REG_WRITE(ah, AR_BEACON,
526                 (OS_REG_READ(ah, AR_BEACON) &~ (AR_BEACON_EN | AR_BEACON_RESET_TSF)));
527
528         /* XXX Setup post reset EAR additions */
529
530         /*  QoS support */
531         if (AH_PRIVATE(ah)->ah_macVersion > AR_SREV_VERSION_VENICE ||
532             (AH_PRIVATE(ah)->ah_macVersion == AR_SREV_VERSION_VENICE &&
533              AH_PRIVATE(ah)->ah_macRev >= AR_SREV_GRIFFIN_LITE)) {
534                 OS_REG_WRITE(ah, AR_QOS_CONTROL, 0x100aa);      /* XXX magic */
535                 OS_REG_WRITE(ah, AR_QOS_SELECT, 0x3210);        /* XXX magic */
536         }
537
538         /* Turn on NOACK Support for QoS packets */
539         OS_REG_WRITE(ah, AR_NOACK,
540                      SM(2, AR_NOACK_2BIT_VALUE) |
541                      SM(5, AR_NOACK_BIT_OFFSET) |
542                      SM(0, AR_NOACK_BYTE_OFFSET));
543
544         /* Restore user-specified settings */
545         if (ahp->ah_miscMode != 0)
546                 OS_REG_WRITE(ah, AR_MISC_MODE, ahp->ah_miscMode);
547         if (ahp->ah_slottime != (u_int) -1)
548                 ar5212SetSlotTime(ah, ahp->ah_slottime);
549         if (ahp->ah_acktimeout != (u_int) -1)
550                 ar5212SetAckTimeout(ah, ahp->ah_acktimeout);
551         if (ahp->ah_ctstimeout != (u_int) -1)
552                 ar5212SetCTSTimeout(ah, ahp->ah_ctstimeout);
553         if (ahp->ah_sifstime != (u_int) -1)
554                 ar5212SetSifsTime(ah, ahp->ah_sifstime);
555         if (AH_PRIVATE(ah)->ah_diagreg != 0)
556                 OS_REG_WRITE(ah, AR_DIAG_SW, AH_PRIVATE(ah)->ah_diagreg);
557
558         AH_PRIVATE(ah)->ah_opmode = opmode;     /* record operating mode */
559
560         if (bChannelChange && !IEEE80211_IS_CHAN_DFS(chan)) 
561                 chan->ic_state &= ~IEEE80211_CHANSTATE_CWINT;
562
563         HALDEBUG(ah, HAL_DEBUG_RESET, "%s: done\n", __func__);
564
565         OS_MARK(ah, AH_MARK_RESET_DONE, 0);
566
567         return AH_TRUE;
568 bad:
569         OS_MARK(ah, AH_MARK_RESET_DONE, ecode);
570         if (status != AH_NULL)
571                 *status = ecode;
572         return AH_FALSE;
573 #undef FAIL
574 #undef N
575 }
576
577 /*
578  * Places the PHY and Radio chips into reset.  A full reset
579  * must be called to leave this state.  The PCI/MAC/PCU are
580  * not placed into reset as we must receive interrupt to
581  * re-enable the hardware.
582  */
583 HAL_BOOL
584 ar5312PhyDisable(struct ath_hal *ah)
585 {
586     return ar5312SetResetReg(ah, AR_RC_BB);
587 }
588
589 /*
590  * Places all of hardware into reset
591  */
592 HAL_BOOL
593 ar5312Disable(struct ath_hal *ah)
594 {
595         if (!ar5312SetPowerMode(ah, HAL_PM_AWAKE, AH_TRUE))
596                 return AH_FALSE;
597         /*
598          * Reset the HW - PCI must be reset after the rest of the
599          * device has been reset.
600          */
601         return ar5312SetResetReg(ah, AR_RC_MAC | AR_RC_BB);
602 }
603
604 /*
605  * Places the hardware into reset and then pulls it out of reset
606  *
607  * TODO: Only write the PLL if we're changing to or from CCK mode
608  * 
609  * WARNING: The order of the PLL and mode registers must be correct.
610  */
611 HAL_BOOL
612 ar5312ChipReset(struct ath_hal *ah, const struct ieee80211_channel *chan)
613 {
614
615         OS_MARK(ah, AH_MARK_CHIPRESET, chan ? chan->ic_freq : 0);
616
617         /*
618          * Reset the HW 
619          */
620         if (!ar5312SetResetReg(ah, AR_RC_MAC | AR_RC_BB)) {
621                 HALDEBUG(ah, HAL_DEBUG_ANY, "%s: ar5312SetResetReg failed\n",
622                     __func__);
623                 return AH_FALSE;
624         }
625
626         /* Bring out of sleep mode (AGAIN) */
627         if (!ar5312SetPowerMode(ah, HAL_PM_AWAKE, AH_TRUE)) {
628                 HALDEBUG(ah, HAL_DEBUG_ANY, "%s: ar5312SetPowerMode failed\n",
629                     __func__);
630                 return AH_FALSE;
631         }
632
633         /* Clear warm reset register */
634         if (!ar5312SetResetReg(ah, 0)) {
635                 HALDEBUG(ah, HAL_DEBUG_ANY, "%s: ar5312SetResetReg failed\n",
636                     __func__);
637                 return AH_FALSE;
638         }
639
640         /*
641          * Perform warm reset before the mode/PLL/turbo registers
642          * are changed in order to deactivate the radio.  Mode changes
643          * with an active radio can result in corrupted shifts to the
644          * radio device.
645          */
646
647         /*
648          * Set CCK and Turbo modes correctly.
649          */
650         if (chan != AH_NULL) {          /* NB: can be null during attach */
651                 uint32_t rfMode, phyPLL = 0, curPhyPLL, turbo;
652
653                 if (IS_RAD5112_ANY(ah)) {
654                         rfMode = AR_PHY_MODE_AR5112;
655                         if (!IS_5315(ah)) {
656                                 if (IEEE80211_IS_CHAN_CCK(chan)) {
657                                         phyPLL = AR_PHY_PLL_CTL_44_5312;
658                                 } else {
659                                         if (IEEE80211_IS_CHAN_HALF(chan)) {
660                                                 phyPLL = AR_PHY_PLL_CTL_40_5312_HALF;
661                                         } else if (IEEE80211_IS_CHAN_QUARTER(chan)) {
662                                                 phyPLL = AR_PHY_PLL_CTL_40_5312_QUARTER;
663                                         } else {
664                                                 phyPLL = AR_PHY_PLL_CTL_40_5312;
665                                         }
666                                 }
667                         } else {
668                                 if (IEEE80211_IS_CHAN_CCK(chan))
669                                         phyPLL = AR_PHY_PLL_CTL_44_5112;
670                                 else
671                                         phyPLL = AR_PHY_PLL_CTL_40_5112;
672                                 if (IEEE80211_IS_CHAN_HALF(chan))
673                                         phyPLL |= AR_PHY_PLL_CTL_HALF;
674                                 else if (IEEE80211_IS_CHAN_QUARTER(chan))
675                                         phyPLL |= AR_PHY_PLL_CTL_QUARTER;
676                         }
677                 } else {
678                         rfMode = AR_PHY_MODE_AR5111;
679                         if (IEEE80211_IS_CHAN_CCK(chan))
680                                 phyPLL = AR_PHY_PLL_CTL_44;
681                         else
682                                 phyPLL = AR_PHY_PLL_CTL_40;
683                         if (IEEE80211_IS_CHAN_HALF(chan))
684                                 phyPLL = AR_PHY_PLL_CTL_HALF;
685                         else if (IEEE80211_IS_CHAN_QUARTER(chan))
686                                 phyPLL = AR_PHY_PLL_CTL_QUARTER;
687                 }
688                 if (IEEE80211_IS_CHAN_G(chan))
689                         rfMode |= AR_PHY_MODE_DYNAMIC;
690                 else if (IEEE80211_IS_CHAN_OFDM(chan))
691                         rfMode |= AR_PHY_MODE_OFDM;
692                 else
693                         rfMode |= AR_PHY_MODE_CCK;
694                 if (IEEE80211_IS_CHAN_5GHZ(chan))
695                         rfMode |= AR_PHY_MODE_RF5GHZ;
696                 else
697                         rfMode |= AR_PHY_MODE_RF2GHZ;
698                 turbo = IEEE80211_IS_CHAN_TURBO(chan) ?
699                         (AR_PHY_FC_TURBO_MODE | AR_PHY_FC_TURBO_SHORT) : 0;
700                 curPhyPLL = OS_REG_READ(ah, AR_PHY_PLL_CTL);
701                 /*
702                  * PLL, Mode, and Turbo values must be written in the correct
703                  * order to ensure:
704                  * - The PLL cannot be set to 44 unless the CCK or DYNAMIC
705                  *   mode bit is set
706                  * - Turbo cannot be set at the same time as CCK or DYNAMIC
707                  */
708                 if (IEEE80211_IS_CHAN_CCK(chan)) {
709                         OS_REG_WRITE(ah, AR_PHY_TURBO, turbo);
710                         OS_REG_WRITE(ah, AR_PHY_MODE, rfMode);
711                         if (curPhyPLL != phyPLL) {
712                                 OS_REG_WRITE(ah,  AR_PHY_PLL_CTL,  phyPLL);
713                                 /* Wait for the PLL to settle */
714                                 OS_DELAY(PLL_SETTLE_DELAY);
715                         }
716                 } else {
717                         if (curPhyPLL != phyPLL) {
718                                 OS_REG_WRITE(ah,  AR_PHY_PLL_CTL,  phyPLL);
719                                 /* Wait for the PLL to settle */
720                                 OS_DELAY(PLL_SETTLE_DELAY);
721                         }
722                         OS_REG_WRITE(ah, AR_PHY_TURBO, turbo);
723                         OS_REG_WRITE(ah, AR_PHY_MODE, rfMode);
724                 }
725         }
726         return AH_TRUE;
727 }
728
729 /*
730  * Write the given reset bit mask into the reset register
731  */
732 static HAL_BOOL
733 ar5312SetResetReg(struct ath_hal *ah, uint32_t resetMask)
734 {
735         uint32_t mask = resetMask ? resetMask : ~0;
736         HAL_BOOL rt;
737
738         if ((rt = ar5312MacReset(ah, mask)) == AH_FALSE) {
739                 return rt;
740         }
741         if ((resetMask & AR_RC_MAC) == 0) {
742                 if (isBigEndian()) {
743                         /*
744                          * Set CFG, little-endian for register
745                          * and descriptor accesses.
746                          */
747 #ifdef AH_NEED_DESC_SWAP
748                         mask = INIT_CONFIG_STATUS | AR_CFG_SWRD;
749 #else
750                         mask = INIT_CONFIG_STATUS |
751                                 AR_CFG_SWTD | AR_CFG_SWRD;
752 #endif
753                         OS_REG_WRITE(ah, AR_CFG, mask);
754                 } else
755                         OS_REG_WRITE(ah, AR_CFG, INIT_CONFIG_STATUS);
756         }
757         return rt;
758 }
759
760 /*
761  * ar5312MacReset resets (and then un-resets) the specified
762  * wireless components.
763  * Note: The RCMask cannot be zero on entering from ar5312SetResetReg.
764  */
765
766 HAL_BOOL
767 ar5312MacReset(struct ath_hal *ah, unsigned int RCMask)
768 {
769         int wlanNum = AR5312_UNIT(ah);
770         uint32_t resetBB, resetBits, regMask;
771         uint32_t reg;
772
773         if (RCMask == 0)
774                 return(AH_FALSE);
775 #if ( AH_SUPPORT_2316 || AH_SUPPORT_2317 )
776             if (IS_5315(ah)) {
777                         switch(wlanNum) {
778                         case 0:
779                                 resetBB = AR5315_RC_BB0_CRES | AR5315_RC_WBB0_RES; 
780                                 /* Warm and cold reset bits for wbb */
781                                 resetBits = AR5315_RC_WMAC0_RES;
782                                 break;
783                         case 1:
784                                 resetBB = AR5315_RC_BB1_CRES | AR5315_RC_WBB1_RES; 
785                                 /* Warm and cold reset bits for wbb */
786                                 resetBits = AR5315_RC_WMAC1_RES;
787                                 break;
788                         default:
789                                 return(AH_FALSE);
790                         }               
791                         regMask = ~(resetBB | resetBits);
792
793                         /* read before */
794                         reg = OS_REG_READ(ah, 
795                                                           (AR5315_RSTIMER_BASE - ((uint32_t) ah->ah_sh) + AR5315_RESET));
796
797                         if (RCMask == AR_RC_BB) {
798                                 /* Put baseband in reset */
799                                 reg |= resetBB;    /* Cold and warm reset the baseband bits */
800                         } else {
801                                 /*
802                                  * Reset the MAC and baseband.  This is a bit different than
803                                  * the PCI version, but holding in reset causes problems.
804                                  */
805                                 reg &= regMask;
806                                 reg |= (resetBits | resetBB) ;
807                         }
808                         OS_REG_WRITE(ah, 
809                                                  (AR5315_RSTIMER_BASE - ((uint32_t) ah->ah_sh)+AR5315_RESET),
810                                                  reg);
811                         /* read after */
812                         OS_REG_READ(ah, 
813                                                 (AR5315_RSTIMER_BASE - ((uint32_t) ah->ah_sh) +AR5315_RESET));
814                         OS_DELAY(100);
815
816                         /* Bring MAC and baseband out of reset */
817                         reg &= regMask;
818                         /* read before */
819                         OS_REG_READ(ah, 
820                                                 (AR5315_RSTIMER_BASE- ((uint32_t) ah->ah_sh) +AR5315_RESET));
821                         OS_REG_WRITE(ah, 
822                                                  (AR5315_RSTIMER_BASE - ((uint32_t) ah->ah_sh)+AR5315_RESET),
823                                                  reg);
824                         /* read after */
825                         OS_REG_READ(ah,
826                                                 (AR5315_RSTIMER_BASE- ((uint32_t) ah->ah_sh) +AR5315_RESET));
827
828
829                 } 
830         else 
831 #endif
832                 {
833
834                         switch(wlanNum) {
835                         case 0:
836                                 resetBB = AR5312_RC_BB0_CRES | AR5312_RC_WBB0_RES;
837                                 /* Warm and cold reset bits for wbb */
838                                 resetBits = AR5312_RC_WMAC0_RES;
839                                 break;
840                         case 1:
841                                 resetBB = AR5312_RC_BB1_CRES | AR5312_RC_WBB1_RES;
842                                 /* Warm and cold reset bits for wbb */
843                                 resetBits = AR5312_RC_WMAC1_RES;
844                                 break;
845                         default:
846                                 return(AH_FALSE);
847                         }
848                         regMask = ~(resetBB | resetBits);
849
850                         /* read before */
851                         reg = OS_REG_READ(ah,
852                                                           (AR5312_RSTIMER_BASE - ((uint32_t) ah->ah_sh) + AR5312_RESET));
853
854                         if (RCMask == AR_RC_BB) {
855                                 /* Put baseband in reset */
856                                 reg |= resetBB;    /* Cold and warm reset the baseband bits */
857                         } else {
858                                 /*
859                                  * Reset the MAC and baseband.  This is a bit different than
860                                  * the PCI version, but holding in reset causes problems.
861                                  */
862                                 reg &= regMask;
863                                 reg |= (resetBits | resetBB) ;
864                         }
865                         OS_REG_WRITE(ah,
866                                                  (AR5312_RSTIMER_BASE - ((uint32_t) ah->ah_sh)+AR5312_RESET),
867                                                  reg);
868                         /* read after */
869                         OS_REG_READ(ah,
870                                                 (AR5312_RSTIMER_BASE - ((uint32_t) ah->ah_sh) +AR5312_RESET));
871                         OS_DELAY(100);
872
873                         /* Bring MAC and baseband out of reset */
874                         reg &= regMask;
875                         /* read before */
876                         OS_REG_READ(ah,
877                                                 (AR5312_RSTIMER_BASE- ((uint32_t) ah->ah_sh) +AR5312_RESET));
878                         OS_REG_WRITE(ah,
879                                                  (AR5312_RSTIMER_BASE - ((uint32_t) ah->ah_sh)+AR5312_RESET),
880                                                  reg);
881                         /* read after */
882                         OS_REG_READ(ah,
883                                                 (AR5312_RSTIMER_BASE- ((uint32_t) ah->ah_sh) +AR5312_RESET));
884                 }
885         return(AH_TRUE);
886 }
887
888 #endif /* AH_SUPPORT_AR5312 */