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