ar9300_reset.c revision 250008
1/* 2 * Copyright (c) 2013 Qualcomm Atheros, Inc. 3 * 4 * Permission to use, copy, modify, and/or distribute this software for any 5 * purpose with or without fee is hereby granted, provided that the above 6 * copyright notice and this permission notice appear in all copies. 7 * 8 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH 9 * REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY 10 * AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, 11 * INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM 12 * LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR 13 * OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR 14 * PERFORMANCE OF THIS SOFTWARE. 15 */ 16 17 18 19#include "opt_ah.h" 20 21#include "ah.h" 22#include "ah_internal.h" 23#include "ah_devid.h" 24#include "ah_desc.h" 25 26#include "ar9300.h" 27#include "ar9300reg.h" 28#include "ar9300phy.h" 29#include "ar9300desc.h" 30 31#define FIX_NOISE_FLOOR 1 32 33 34 35/* Additional Time delay to wait after activiting the Base band */ 36#define BASE_ACTIVATE_DELAY 100 /* usec */ 37#define RTC_PLL_SETTLE_DELAY 100 /* usec */ 38#define COEF_SCALE_S 24 39#define HT40_CHANNEL_CENTER_SHIFT 10 /* MHz */ 40 41#define DELPT 32 42 43/* XXX Duplicates! (in ar9300desc.h) */ 44#if 0 45extern HAL_BOOL ar9300_reset_tx_queue(struct ath_hal *ah, u_int q); 46extern u_int32_t ar9300_num_tx_pending(struct ath_hal *ah, u_int q); 47#endif 48 49 50#define MAX_MEASUREMENT 8 51#define MAXIQCAL 3 52struct coeff_t { 53 int32_t mag_coeff[AR9300_MAX_CHAINS][MAX_MEASUREMENT][MAXIQCAL]; 54 int32_t phs_coeff[AR9300_MAX_CHAINS][MAX_MEASUREMENT][MAXIQCAL]; 55 int32_t iqc_coeff[2]; 56 int last_nmeasurement; 57 HAL_BOOL last_cal; 58}; 59 60static HAL_BOOL ar9300_tx_iq_cal_hw_run(struct ath_hal *ah); 61static void ar9300_tx_iq_cal_post_proc(struct ath_hal *ah,HAL_CHANNEL_INTERNAL *ichan, 62 int iqcal_idx, int max_iqcal, HAL_BOOL is_cal_reusable, HAL_BOOL apply_last_corr); 63static void ar9300_tx_iq_cal_outlier_detection(struct ath_hal *ah,HAL_CHANNEL_INTERNAL *ichan, 64 u_int32_t num_chains, struct coeff_t *coeff, HAL_BOOL is_cal_reusable); 65#if ATH_SUPPORT_CAL_REUSE 66static void ar9300_tx_iq_cal_apply(struct ath_hal *ah, HAL_CHANNEL_INTERNAL *ichan); 67#endif 68 69 70static inline void ar9300_prog_ini(struct ath_hal *ah, struct ar9300_ini_array *ini_arr, int column); 71static inline void ar9300_set_rf_mode(struct ath_hal *ah, struct ieee80211_channel *chan); 72static inline HAL_BOOL ar9300_init_cal(struct ath_hal *ah, struct ieee80211_channel *chan, HAL_BOOL skip_if_none, HAL_BOOL apply_last_corr); 73static inline void ar9300_init_user_settings(struct ath_hal *ah); 74 75#ifdef HOST_OFFLOAD 76/* 77 * For usb offload solution, some USB registers must be tuned 78 * to gain better stability/performance but these registers 79 * might be changed while doing wlan reset so do this here 80 */ 81#define WAR_USB_DISABLE_PLL_LOCK_DETECT(__ah) \ 82do { \ 83 if (AR_SREV_HORNET(__ah) || AR_SREV_WASP(__ah)) { \ 84 volatile u_int32_t *usb_ctrl_r1 = (u_int32_t *) 0xb8116c84; \ 85 volatile u_int32_t *usb_ctrl_r2 = (u_int32_t *) 0xb8116c88; \ 86 *usb_ctrl_r1 = (*usb_ctrl_r1 & 0xffefffff); \ 87 *usb_ctrl_r2 = (*usb_ctrl_r2 & 0xfc1fffff) | (1 << 21) | (3 << 22); \ 88 } \ 89} while (0) 90#else 91#define WAR_USB_DISABLE_PLL_LOCK_DETECT(__ah) 92#endif 93 94static inline void 95ar9300_attach_hw_platform(struct ath_hal *ah) 96{ 97 struct ath_hal_9300 *ahp = AH9300(ah); 98 99 ahp->ah_hwp = HAL_TRUE_CHIP; 100 return; 101} 102 103/* Adjust various register settings based on half/quarter rate clock setting. 104 * This includes: +USEC, TX/RX latency, 105 * + IFS params: slot, eifs, misc etc. 106 * SIFS stays the same. 107 */ 108static void 109ar9300_set_ifs_timing(struct ath_hal *ah, struct ieee80211_channel *chan) 110{ 111 u_int32_t tx_lat, rx_lat, usec, slot, regval, eifs; 112 113 regval = OS_REG_READ(ah, AR_USEC); 114 regval &= ~(AR_USEC_RX_LATENCY | AR_USEC_TX_LATENCY | AR_USEC_USEC); 115 if (IEEE80211_IS_CHAN_HALF(chan)) { /* half rates */ 116 slot = ar9300_mac_to_clks(ah, AR_SLOT_HALF); 117 eifs = ar9300_mac_to_clks(ah, AR_EIFS_HALF); 118 if (IS_5GHZ_FAST_CLOCK_EN(ah, chan)) { /* fast clock */ 119 rx_lat = SM(AR_RX_LATENCY_HALF_FAST_CLOCK, AR_USEC_RX_LATENCY); 120 tx_lat = SM(AR_TX_LATENCY_HALF_FAST_CLOCK, AR_USEC_TX_LATENCY); 121 usec = SM(AR_USEC_HALF_FAST_CLOCK, AR_USEC_USEC); 122 } else { 123 rx_lat = SM(AR_RX_LATENCY_HALF, AR_USEC_RX_LATENCY); 124 tx_lat = SM(AR_TX_LATENCY_HALF, AR_USEC_TX_LATENCY); 125 usec = SM(AR_USEC_HALF, AR_USEC_USEC); 126 } 127 } else { /* quarter rate */ 128 slot = ar9300_mac_to_clks(ah, AR_SLOT_QUARTER); 129 eifs = ar9300_mac_to_clks(ah, AR_EIFS_QUARTER); 130 if (IS_5GHZ_FAST_CLOCK_EN(ah, chan)) { /* fast clock */ 131 rx_lat = SM(AR_RX_LATENCY_QUARTER_FAST_CLOCK, AR_USEC_RX_LATENCY); 132 tx_lat = SM(AR_TX_LATENCY_QUARTER_FAST_CLOCK, AR_USEC_TX_LATENCY); 133 usec = SM(AR_USEC_QUARTER_FAST_CLOCK, AR_USEC_USEC); 134 } else { 135 rx_lat = SM(AR_RX_LATENCY_QUARTER, AR_USEC_RX_LATENCY); 136 tx_lat = SM(AR_TX_LATENCY_QUARTER, AR_USEC_TX_LATENCY); 137 usec = SM(AR_USEC_QUARTER, AR_USEC_USEC); 138 } 139 } 140 141 OS_REG_WRITE(ah, AR_USEC, (usec | regval | tx_lat | rx_lat)); 142 OS_REG_WRITE(ah, AR_D_GBL_IFS_SLOT, slot); 143 OS_REG_WRITE(ah, AR_D_GBL_IFS_EIFS, eifs); 144} 145 146 147/* 148 * This inline function configures the chip either 149 * to encrypt/decrypt management frames or pass thru 150 */ 151static inline void 152ar9300_init_mfp(struct ath_hal * ah) 153{ 154 u_int32_t mfpcap, mfp_qos; 155 156 ath_hal_getcapability(ah, HAL_CAP_MFP, 0, &mfpcap); 157 158 if (mfpcap == HAL_MFP_QOSDATA) { 159 /* Treat like legacy hardware. Do not touch the MFP registers. */ 160 HALDEBUG(ah, HAL_DEBUG_RESET, "%s forced to use QOSDATA\n", __func__); 161 return; 162 } 163 164 /* MFP support (Sowl 1.0 or greater) */ 165 if (mfpcap == HAL_MFP_HW_CRYPTO) { 166 /* configure hardware MFP support */ 167 HALDEBUG(ah, HAL_DEBUG_RESET, "%s using HW crypto\n", __func__); 168 OS_REG_RMW_FIELD(ah, 169 AR_AES_MUTE_MASK1, AR_AES_MUTE_MASK1_FC_MGMT, AR_AES_MUTE_MASK1_FC_MGMT_MFP); 170 OS_REG_RMW(ah, 171 AR_PCU_MISC_MODE2, AR_PCU_MISC_MODE2_MGMT_CRYPTO_ENABLE, 172 AR_PCU_MISC_MODE2_NO_CRYPTO_FOR_NON_DATA_PKT); 173 /* 174 * Mask used to construct AAD for CCMP-AES 175 * Cisco spec defined bits 0-3 as mask 176 * IEEE802.11w defined as bit 4. 177 */ 178 if (ath_hal_get_mfp_qos(ah)) { 179 mfp_qos = AR_MFP_QOS_MASK_IEEE; 180 } else { 181 mfp_qos = AR_MFP_QOS_MASK_CISCO; 182 } 183 OS_REG_RMW_FIELD(ah, 184 AR_PCU_MISC_MODE2, AR_PCU_MISC_MODE2_MGMT_QOS, mfp_qos); 185 } else if (mfpcap == HAL_MFP_PASSTHRU) { 186 /* Disable en/decrypt by hardware */ 187 HALDEBUG(ah, HAL_DEBUG_RESET, "%s using passthru\n", __func__); 188 OS_REG_RMW(ah, 189 AR_PCU_MISC_MODE2, 190 AR_PCU_MISC_MODE2_NO_CRYPTO_FOR_NON_DATA_PKT, 191 AR_PCU_MISC_MODE2_MGMT_CRYPTO_ENABLE); 192 } 193} 194 195void 196ar9300_get_channel_centers(struct ath_hal *ah, const struct ieee80211_channel *chan, 197 CHAN_CENTERS *centers) 198{ 199 int8_t extoff; 200 struct ath_hal_9300 *ahp = AH9300(ah); 201 HAL_CHANNEL_INTERNAL *ichan = ath_hal_checkchannel(ah, chan); 202 203 if (!IEEE80211_IS_CHAN_HT40(chan)) { 204 centers->ctl_center = centers->ext_center = 205 centers->synth_center = ichan->channel; 206 return; 207 } 208 209 HALASSERT(IEEE80211_IS_CHAN_HT40(chan)); 210 211 /* 212 * In 20/40 phy mode, the center frequency is 213 * "between" the primary and extension channels. 214 */ 215 if (IEEE80211_IS_CHAN_HT40U(chan)) { 216 centers->synth_center = ichan->channel + HT40_CHANNEL_CENTER_SHIFT; 217 extoff = 1; 218 } else { 219 centers->synth_center = ichan->channel - HT40_CHANNEL_CENTER_SHIFT; 220 extoff = -1; 221 } 222 223 centers->ctl_center = 224 centers->synth_center - (extoff * HT40_CHANNEL_CENTER_SHIFT); 225 centers->ext_center = 226 centers->synth_center + 227 (extoff * ((ahp->ah_ext_prot_spacing == HAL_HT_EXTPROTSPACING_20) ? 228 HT40_CHANNEL_CENTER_SHIFT : 15)); 229} 230 231/* 232 * Read the noise-floor values from the HW. 233 * Specifically, read the minimum clear-channel assessment value for 234 * each chain, for both the control and extension channels. 235 * (The received power level during clear-channel periods is the 236 * noise floor.) 237 * These noise floor values computed by the HW will be stored in the 238 * NF history buffer. 239 * The HW sometimes produces bogus NF values. To avoid using these 240 * bogus values, the NF data is (a) range-limited, and (b) filtered. 241 * However, this data-processing is done when reading the NF values 242 * out of the history buffer. The history buffer stores the raw values. 243 * This allows the NF history buffer to be used to check for interference. 244 * A single high NF reading might be a bogus HW value, but if the NF 245 * readings are consistently high, it must be due to interference. 246 * This is the purpose of storing raw NF values in the history buffer, 247 * rather than processed values. By looking at a history of NF values 248 * that have not been range-limited, we can check if they are consistently 249 * high (due to interference). 250 */ 251#define AH_NF_SIGN_EXTEND(nf) \ 252 ((nf) & 0x100) ? \ 253 0 - (((nf) ^ 0x1ff) + 1) : \ 254 (nf) 255void 256ar9300_upload_noise_floor(struct ath_hal *ah, int is_2g, 257 int16_t nfarray[HAL_NUM_NF_READINGS]) 258{ 259 int16_t nf; 260 int chan, chain; 261 u_int32_t regs[HAL_NUM_NF_READINGS] = { 262 /* control channel */ 263 AR_PHY_CCA_0, /* chain 0 */ 264 AR_PHY_CCA_1, /* chain 1 */ 265 AR_PHY_CCA_2, /* chain 2 */ 266 /* extension channel */ 267 AR_PHY_EXT_CCA, /* chain 0 */ 268 AR_PHY_EXT_CCA_1, /* chain 1 */ 269 AR_PHY_EXT_CCA_2, /* chain 2 */ 270 }; 271 u_int8_t chainmask; 272 273 /* 274 * Within a given channel (ctl vs. ext), the CH0, CH1, and CH2 275 * masks and shifts are the same, though they differ for the 276 * control vs. extension channels. 277 */ 278 u_int32_t masks[2] = { 279 AR_PHY_MINCCA_PWR, /* control channel */ 280 AR_PHY_EXT_MINCCA_PWR, /* extention channel */ 281 }; 282 u_int8_t shifts[2] = { 283 AR_PHY_MINCCA_PWR_S, /* control channel */ 284 AR_PHY_EXT_MINCCA_PWR_S, /* extention channel */ 285 }; 286 287 /* 288 * Force NF calibration for all chains. 289 */ 290 if (AR_SREV_HORNET(ah) || AR_SREV_POSEIDON(ah) || AR_SREV_APHRODITE(ah)) { 291 chainmask = 0x01; 292 } else if (AR_SREV_WASP(ah) || AR_SREV_JUPITER(ah)) { 293 chainmask = 0x03; 294 } else { 295 chainmask = 0x07; 296 } 297 298 for (chan = 0; chan < 2 /*ctl,ext*/; chan++) { 299 for (chain = 0; chain < AR9300_MAX_CHAINS; chain++) { 300 int i; 301 302 if (!((chainmask >> chain) & 0x1)) { 303 continue; 304 } 305 i = chan * AR9300_MAX_CHAINS + chain; 306 nf = (OS_REG_READ(ah, regs[i]) & masks[chan]) >> shifts[chan]; 307 nfarray[i] = AH_NF_SIGN_EXTEND(nf); 308 } 309 } 310} 311 312/* ar9300_get_min_cca_pwr - 313 * Used by the scan function for a quick read of the noise floor. 314 * This is used to detect presence of CW interference such as video bridge. 315 * The noise floor is assumed to have been already started during reset 316 * called during channel change. The function checks if the noise floor 317 * reading is done. In case it has been done, it reads the noise floor value. 318 * If the noise floor calibration has not been finished, it assumes this is 319 * due to presence of CW interference an returns a high value for noise floor, 320 * derived from the CW interference threshold + margin fudge factor. 321 */ 322#define BAD_SCAN_NF_MARGIN (30) 323int16_t ar9300_get_min_cca_pwr(struct ath_hal *ah) 324{ 325 int16_t nf; 326// struct ath_hal_private *ahpriv = AH_PRIVATE(ah); 327 328 if ((OS_REG_READ(ah, AR_PHY_AGC_CONTROL) & AR_PHY_AGC_CONTROL_NF) == 0) { 329 nf = MS(OS_REG_READ(ah, AR_PHY_CCA_0), AR9280_PHY_MINCCA_PWR); 330 if (nf & 0x100) { 331 nf = 0 - ((nf ^ 0x1ff) + 1); 332 } 333 } else { 334 /* NF calibration is not done, assume CW interference */ 335 nf = AH9300(ah)->nfp->nominal + AH9300(ah)->nf_cw_int_delta + 336 BAD_SCAN_NF_MARGIN; 337 } 338 return nf; 339} 340 341 342/* 343 * Noise Floor values for all chains. 344 * Most recently updated values from the NF history buffer are used. 345 */ 346void ar9300_chain_noise_floor(struct ath_hal *ah, int16_t *nf_buf, 347 struct ieee80211_channel *chan, int is_scan) 348{ 349 struct ath_hal_9300 *ahp = AH9300(ah); 350 int i, nf_hist_len, recent_nf_index = 0; 351 HAL_NFCAL_HIST_FULL *h; 352 u_int8_t rx_chainmask = ahp->ah_rx_chainmask | (ahp->ah_rx_chainmask << 3); 353 HAL_CHANNEL_INTERNAL *ichan = ath_hal_checkchannel(ah, chan); 354 HALASSERT(ichan); 355 356#ifdef ATH_NF_PER_CHAN 357 /* Fill 0 if valid internal channel is not found */ 358 if (ichan == AH_NULL) { 359 OS_MEMZERO(nf_buf, sizeof(nf_buf[0])*HAL_NUM_NF_READINGS); 360 return; 361 } 362 h = &ichan->nf_cal_hist; 363 nf_hist_len = HAL_NF_CAL_HIST_LEN_FULL; 364#else 365 /* 366 * If a scan is not in progress, then the most recent value goes 367 * into ahpriv->nf_cal_hist. If a scan is in progress, then 368 * the most recent value goes into ichan->nf_cal_hist. 369 * Thus, return the value from ahpriv->nf_cal_hist if there's 370 * no scan, and if the specified channel is the current channel. 371 * Otherwise, return the noise floor from ichan->nf_cal_hist. 372 */ 373 if ((!is_scan) && chan == AH_PRIVATE(ah)->ah_curchan) { 374 h = &AH_PRIVATE(ah)->nf_cal_hist; 375 nf_hist_len = HAL_NF_CAL_HIST_LEN_FULL; 376 } else { 377 /* Fill 0 if valid internal channel is not found */ 378 if (ichan == AH_NULL) { 379 OS_MEMZERO(nf_buf, sizeof(nf_buf[0])*HAL_NUM_NF_READINGS); 380 return; 381 } 382 /* 383 * It is okay to treat a HAL_NFCAL_HIST_SMALL struct as if it were a 384 * HAL_NFCAL_HIST_FULL struct, as long as only the index 0 of the 385 * nf_cal_buffer is used (nf_cal_buffer[0][0:HAL_NUM_NF_READINGS-1]) 386 */ 387 h = (HAL_NFCAL_HIST_FULL *) &ichan->nf_cal_hist; 388 nf_hist_len = HAL_NF_CAL_HIST_LEN_SMALL; 389 } 390#endif 391 /* Get most recently updated values from nf cal history buffer */ 392 recent_nf_index = 393 (h->base.curr_index) ? h->base.curr_index - 1 : nf_hist_len - 1; 394 395 for (i = 0; i < HAL_NUM_NF_READINGS; i++) { 396 /* Fill 0 for unsupported chains */ 397 if (!(rx_chainmask & (1 << i))) { 398 nf_buf[i] = 0; 399 continue; 400 } 401 nf_buf[i] = h->nf_cal_buffer[recent_nf_index][i]; 402 } 403} 404 405 406/* 407 * Pick up the medium one in the noise floor buffer and update the 408 * corresponding range for valid noise floor values 409 */ 410static int16_t 411ar9300_get_nf_hist_mid(struct ath_hal *ah, HAL_NFCAL_HIST_FULL *h, int reading, 412 int hist_len) 413{ 414 int16_t nfval; 415 int16_t sort[HAL_NF_CAL_HIST_LEN_FULL]; /* upper bound for hist_len */ 416 int i, j; 417 418 for (i = 0; i < hist_len; i++) { 419 sort[i] = h->nf_cal_buffer[i][reading]; 420 HALDEBUG(ah, HAL_DEBUG_NFCAL, 421 "nf_cal_buffer[%d][%d] = %d\n", i, reading, (int)sort[i]); 422 } 423 for (i = 0; i < hist_len - 1; i++) { 424 for (j = 1; j < hist_len - i; j++) { 425 if (sort[j] > sort[j - 1]) { 426 nfval = sort[j]; 427 sort[j] = sort[j - 1]; 428 sort[j - 1] = nfval; 429 } 430 } 431 } 432 nfval = sort[(hist_len - 1) >> 1]; 433 434 return nfval; 435} 436 437static int16_t ar9300_limit_nf_range(struct ath_hal *ah, int16_t nf) 438{ 439 if (nf < AH9300(ah)->nfp->min) { 440 return AH9300(ah)->nfp->nominal; 441 } else if (nf > AH9300(ah)->nfp->max) { 442 return AH9300(ah)->nfp->max; 443 } 444 return nf; 445} 446 447#ifndef ATH_NF_PER_CHAN 448inline static void 449ar9300_reset_nf_hist_buff(struct ath_hal *ah, HAL_CHANNEL_INTERNAL *ichan) 450{ 451 HAL_CHAN_NFCAL_HIST *h = &ichan->nf_cal_hist; 452 HAL_NFCAL_HIST_FULL *home = &AH_PRIVATE(ah)->nf_cal_hist; 453 int i; 454 455 /* 456 * Copy the value for the channel in question into the home-channel 457 * NF history buffer. The channel NF is probably a value filled in by 458 * a prior background channel scan, but if no scan has been done then 459 * it is the nominal noise floor filled in by ath_hal_init_NF_buffer 460 * for this chip and the channel's band. 461 * Replicate this channel NF into all entries of the home-channel NF 462 * history buffer. 463 * If the channel NF was filled in by a channel scan, it has not had 464 * bounds limits applied to it yet - do so now. It is important to 465 * apply bounds limits to the priv_nf value that gets loaded into the 466 * WLAN chip's min_cca_pwr register field. It is also necessary to 467 * apply bounds limits to the nf_cal_buffer[] elements. Since we are 468 * replicating a single NF reading into all nf_cal_buffer elements, 469 * if the single reading were above the CW_INT threshold, the CW_INT 470 * check in ar9300_get_nf would immediately conclude that CW interference 471 * is present, even though we're not supposed to set CW_INT unless 472 * NF values are _consistently_ above the CW_INT threshold. 473 * Applying the bounds limits to the nf_cal_buffer contents fixes this 474 * problem. 475 */ 476 for (i = 0; i < HAL_NUM_NF_READINGS; i ++) { 477 int j; 478 int16_t nf; 479 /* 480 * No need to set curr_index, since it already has a value in 481 * the range [0..HAL_NF_CAL_HIST_LEN_FULL), and all nf_cal_buffer 482 * values will be the same. 483 */ 484 nf = ar9300_limit_nf_range(ah, h->nf_cal_buffer[0][i]); 485 for (j = 0; j < HAL_NF_CAL_HIST_LEN_FULL; j++) { 486 home->nf_cal_buffer[j][i] = nf; 487 } 488 AH_PRIVATE(ah)->nf_cal_hist.base.priv_nf[i] = nf; 489 } 490} 491#endif 492 493/* 494 * Update the noise floor buffer as a ring buffer 495 */ 496static int16_t 497ar9300_update_nf_hist_buff(struct ath_hal *ah, HAL_NFCAL_HIST_FULL *h, 498 int16_t *nfarray, int hist_len) 499{ 500 int i, nr; 501 int16_t nf_no_lim_chain0; 502 503 nf_no_lim_chain0 = ar9300_get_nf_hist_mid(ah, h, 0, hist_len); 504 505 HALDEBUG(ah, HAL_DEBUG_NFCAL, "%s[%d] BEFORE\n", __func__, __LINE__); 506 for (nr = 0; nr < HAL_NF_CAL_HIST_LEN_FULL; nr++) { 507 for (i = 0; i < HAL_NUM_NF_READINGS; i++) { 508 HALDEBUG(ah, HAL_DEBUG_NFCAL, 509 "nf_cal_buffer[%d][%d] = %d\n", 510 nr, i, (int)h->nf_cal_buffer[nr][i]); 511 } 512 } 513 for (i = 0; i < HAL_NUM_NF_READINGS; i++) { 514 h->nf_cal_buffer[h->base.curr_index][i] = nfarray[i]; 515 h->base.priv_nf[i] = ar9300_limit_nf_range( 516 ah, ar9300_get_nf_hist_mid(ah, h, i, hist_len)); 517 } 518 HALDEBUG(ah, HAL_DEBUG_NFCAL, "%s[%d] AFTER\n", __func__, __LINE__); 519 for (nr = 0; nr < HAL_NF_CAL_HIST_LEN_FULL; nr++) { 520 for (i = 0; i < HAL_NUM_NF_READINGS; i++) { 521 HALDEBUG(ah, HAL_DEBUG_NFCAL, 522 "nf_cal_buffer[%d][%d] = %d\n", 523 nr, i, (int)h->nf_cal_buffer[nr][i]); 524 } 525 } 526 527 if (++h->base.curr_index >= hist_len) { 528 h->base.curr_index = 0; 529 } 530 531 return nf_no_lim_chain0; 532} 533 534#ifdef UNUSED 535static HAL_BOOL 536get_noise_floor_thresh(struct ath_hal *ah, const HAL_CHANNEL_INTERNAL *chan, 537 int16_t *nft) 538{ 539 struct ath_hal_9300 *ahp = AH9300(ah); 540 541 switch (chan->channel_flags & CHANNEL_ALL_NOTURBO) { 542 case CHANNEL_A: 543 case CHANNEL_A_HT20: 544 case CHANNEL_A_HT40PLUS: 545 case CHANNEL_A_HT40MINUS: 546 *nft = (int8_t)ar9300_eeprom_get(ahp, EEP_NFTHRESH_5); 547 break; 548 case CHANNEL_B: 549 case CHANNEL_G: 550 case CHANNEL_G_HT20: 551 case CHANNEL_G_HT40PLUS: 552 case CHANNEL_G_HT40MINUS: 553 *nft = (int8_t)ar9300_eeprom_get(ahp, EEP_NFTHRESH_2); 554 break; 555 default: 556 HALDEBUG(ah, HAL_DEBUG_CHANNEL, "%s: invalid channel flags 0x%x\n", 557 __func__, chan->channel_flags); 558 return AH_FALSE; 559 } 560 return AH_TRUE; 561} 562#endif 563 564/* 565 * Read the NF and check it against the noise floor threshhold 566 */ 567#define IS(_c, _f) (((_c)->channel_flags & _f) || 0) 568static int 569ar9300_store_new_nf(struct ath_hal *ah, struct ieee80211_channel *chan, 570 int is_scan) 571{ 572// struct ath_hal_private *ahpriv = AH_PRIVATE(ah); 573 int nf_hist_len; 574 int16_t nf_no_lim; 575 int16_t nfarray[HAL_NUM_NF_READINGS] = {0}; 576 HAL_NFCAL_HIST_FULL *h; 577 int is_2g = 0; 578 HAL_CHANNEL_INTERNAL *ichan = ath_hal_checkchannel(ah, chan); 579 struct ath_hal_9300 *ahp = AH9300(ah); 580 581 if (OS_REG_READ(ah, AR_PHY_AGC_CONTROL) & AR_PHY_AGC_CONTROL_NF) { 582 u_int32_t tsf32, nf_cal_dur_tsf; 583 /* 584 * The reason the NF calibration did not complete may just be that 585 * not enough time has passed since the NF calibration was started, 586 * because under certain conditions (when first moving to a new 587 * channel) the NF calibration may be checked very repeatedly. 588 * Or, there may be CW interference keeping the NF calibration 589 * from completing. Check the delta time between when the NF 590 * calibration was started and now to see whether the NF calibration 591 * should have already completed (but hasn't, probably due to CW 592 * interference), or hasn't had enough time to finish yet. 593 */ 594 /* 595 * AH_NF_CAL_DUR_MAX_TSF - A conservative maximum time that the 596 * HW should need to finish a NF calibration. If the HW 597 * does not complete a NF calibration within this time period, 598 * there must be a problem - probably CW interference. 599 * AH_NF_CAL_PERIOD_MAX_TSF - A conservative maximum time between 600 * check of the HW's NF calibration being finished. 601 * If the difference between the current TSF and the TSF 602 * recorded when the NF calibration started is larger than this 603 * value, the TSF must have been reset. 604 * In general, we expect the TSF to only be reset during 605 * regular operation for STAs, not for APs. However, an 606 * AP's TSF could be reset when joining an IBSS. 607 * There's an outside chance that this could result in the 608 * CW_INT flag being erroneously set, if the TSF adjustment 609 * is smaller than AH_NF_CAL_PERIOD_MAX_TSF but larger than 610 * AH_NF_CAL_DUR_TSF. However, even if this does happen, 611 * it shouldn't matter, as the IBSS case shouldn't be 612 * concerned about CW_INT. 613 */ 614 /* AH_NF_CAL_DUR_TSF - 90 sec in usec units */ 615 #define AH_NF_CAL_DUR_TSF (90 * 1000 * 1000) 616 /* AH_NF_CAL_PERIOD_MAX_TSF - 180 sec in usec units */ 617 #define AH_NF_CAL_PERIOD_MAX_TSF (180 * 1000 * 1000) 618 /* wraparound handled by using unsigned values */ 619 tsf32 = ar9300_get_tsf32(ah); 620 nf_cal_dur_tsf = tsf32 - AH9300(ah)->nf_tsf32; 621 if (nf_cal_dur_tsf > AH_NF_CAL_PERIOD_MAX_TSF) { 622 /* 623 * The TSF must have gotten reset during the NF cal - 624 * just reset the NF TSF timestamp, so the next time 625 * this function is called, the timestamp comparison 626 * will be valid. 627 */ 628 AH9300(ah)->nf_tsf32 = tsf32; 629 } else if (nf_cal_dur_tsf > AH_NF_CAL_DUR_TSF) { 630 HALDEBUG(ah, HAL_DEBUG_CALIBRATE, 631 "%s: NF did not complete in calibration window\n", __func__); 632 /* the NF incompletion is probably due to CW interference */ 633 chan->ic_state |= IEEE80211_CHANSTATE_CWINT; 634 } 635 return 0; /* HW's NF measurement not finished */ 636 } 637 HALDEBUG(ah, HAL_DEBUG_NFCAL, 638 "%s[%d] chan %d\n", __func__, __LINE__, ichan->channel); 639 is_2g = !! IS_CHAN_2GHZ(ichan); 640 ar9300_upload_noise_floor(ah, is_2g, nfarray); 641 642 /* Update the NF buffer for each chain masked by chainmask */ 643#ifdef ATH_NF_PER_CHAN 644 h = &ichan->nf_cal_hist; 645 nf_hist_len = HAL_NF_CAL_HIST_LEN_FULL; 646#else 647 if (is_scan) { 648 /* 649 * This channel's NF cal info is just a HAL_NFCAL_HIST_SMALL struct 650 * rather than a HAL_NFCAL_HIST_FULL struct. 651 * As long as we only use the first history element of nf_cal_buffer 652 * (nf_cal_buffer[0][0:HAL_NUM_NF_READINGS-1]), we can use 653 * HAL_NFCAL_HIST_SMALL and HAL_NFCAL_HIST_FULL interchangeably. 654 */ 655 h = (HAL_NFCAL_HIST_FULL *) &ichan->nf_cal_hist; 656 nf_hist_len = HAL_NF_CAL_HIST_LEN_SMALL; 657 } else { 658 h = &AH_PRIVATE(ah)->nf_cal_hist; 659 nf_hist_len = HAL_NF_CAL_HIST_LEN_FULL; 660 } 661#endif 662 663 /* 664 * nf_no_lim = median value from NF history buffer without bounds limits, 665 * priv_nf = median value from NF history buffer with bounds limits. 666 */ 667 nf_no_lim = ar9300_update_nf_hist_buff(ah, h, nfarray, nf_hist_len); 668 ichan->rawNoiseFloor = h->base.priv_nf[0]; 669 670 /* check if there is interference */ 671// ichan->channel_flags &= (~CHANNEL_CW_INT); 672 /* 673 * Use AR9300_EMULATION to check for emulation purpose as PCIE Device ID 674 * 0xABCD is recognized as valid Osprey as WAR in some EVs. 675 */ 676 if (nf_no_lim > ahp->nfp->nominal + ahp->nf_cw_int_delta) { 677 /* 678 * Since this CW interference check is being applied to the 679 * median element of the NF history buffer, this indicates that 680 * the CW interference is persistent. A single high NF reading 681 * will not show up in the median, and thus will not cause the 682 * CW_INT flag to be set. 683 */ 684 HALDEBUG(ah, HAL_DEBUG_NFCAL, 685 "%s: NF Cal: CW interferer detected through NF: %d\n", 686 __func__, nf_no_lim); 687 chan->ic_state |= IEEE80211_CHANSTATE_CWINT; 688 } 689 return 1; /* HW's NF measurement finished */ 690} 691#undef IS 692 693static inline void 694ar9300_get_delta_slope_values(struct ath_hal *ah, u_int32_t coef_scaled, 695 u_int32_t *coef_mantissa, u_int32_t *coef_exponent) 696{ 697 u_int32_t coef_exp, coef_man; 698 699 /* 700 * ALGO -> coef_exp = 14-floor(log2(coef)); 701 * floor(log2(x)) is the highest set bit position 702 */ 703 for (coef_exp = 31; coef_exp > 0; coef_exp--) { 704 if ((coef_scaled >> coef_exp) & 0x1) { 705 break; 706 } 707 } 708 /* A coef_exp of 0 is a legal bit position but an unexpected coef_exp */ 709 HALASSERT(coef_exp); 710 coef_exp = 14 - (coef_exp - COEF_SCALE_S); 711 712 713 /* 714 * ALGO -> coef_man = floor(coef* 2^coef_exp+0.5); 715 * The coefficient is already shifted up for scaling 716 */ 717 coef_man = coef_scaled + (1 << (COEF_SCALE_S - coef_exp - 1)); 718 719 *coef_mantissa = coef_man >> (COEF_SCALE_S - coef_exp); 720 *coef_exponent = coef_exp - 16; 721} 722 723#define MAX_ANALOG_START 319 /* XXX */ 724 725/* 726 * Delta slope coefficient computation. 727 * Required for OFDM operation. 728 */ 729static void 730ar9300_set_delta_slope(struct ath_hal *ah, struct ieee80211_channel *chan) 731{ 732 u_int32_t coef_scaled, ds_coef_exp, ds_coef_man; 733 u_int32_t fclk = COEFF; /* clock * 2.5 */ 734 735 u_int32_t clock_mhz_scaled = 0x1000000 * fclk; 736 CHAN_CENTERS centers; 737 738 /* 739 * half and quarter rate can divide the scaled clock by 2 or 4 740 * scale for selected channel bandwidth 741 */ 742 if (IEEE80211_IS_CHAN_HALF(chan)) { 743 clock_mhz_scaled = clock_mhz_scaled >> 1; 744 } else if (IEEE80211_IS_CHAN_QUARTER(chan)) { 745 clock_mhz_scaled = clock_mhz_scaled >> 2; 746 } 747 748 /* 749 * ALGO -> coef = 1e8/fcarrier*fclock/40; 750 * scaled coef to provide precision for this floating calculation 751 */ 752 ar9300_get_channel_centers(ah, chan, ¢ers); 753 coef_scaled = clock_mhz_scaled / centers.synth_center; 754 755 ar9300_get_delta_slope_values(ah, coef_scaled, &ds_coef_man, &ds_coef_exp); 756 757 OS_REG_RMW_FIELD(ah, AR_PHY_TIMING3, AR_PHY_TIMING3_DSC_MAN, ds_coef_man); 758 OS_REG_RMW_FIELD(ah, AR_PHY_TIMING3, AR_PHY_TIMING3_DSC_EXP, ds_coef_exp); 759 760 /* 761 * For Short GI, 762 * scaled coeff is 9/10 that of normal coeff 763 */ 764 coef_scaled = (9 * coef_scaled) / 10; 765 766 ar9300_get_delta_slope_values(ah, coef_scaled, &ds_coef_man, &ds_coef_exp); 767 768 /* for short gi */ 769 OS_REG_RMW_FIELD(ah, AR_PHY_SGI_DELTA, AR_PHY_SGI_DSC_MAN, ds_coef_man); 770 OS_REG_RMW_FIELD(ah, AR_PHY_SGI_DELTA, AR_PHY_SGI_DSC_EXP, ds_coef_exp); 771} 772 773#define IS(_c, _f) (IEEE80211_IS_ ## _f(_c)) 774 775/* 776 * XXX FreeBSD: This should be turned into something generic in ath_hal! 777 */ 778HAL_CHANNEL_INTERNAL * 779ar9300_check_chan(struct ath_hal *ah, const struct ieee80211_channel *chan) 780{ 781 if ((IS(chan, CHAN_2GHZ) ^ IS(chan, CHAN_5GHZ)) == 0) { 782 HALDEBUG(ah, HAL_DEBUG_CHANNEL, 783 "%s: invalid channel %u/0x%x; not marked as 2GHz or 5GHz\n", 784 __func__, chan->ic_freq , chan->ic_flags); 785 return AH_NULL; 786 } 787 788 /* 789 * FreeBSD sets multiple flags, so this will fail. 790 */ 791#if 0 792 if ((IS(chan, CHAN_OFDM) ^ IS(chan, CHAN_CCK) ^ IS(chan, CHAN_DYN) ^ 793 IS(chan, CHAN_HT20) ^ IS(chan, CHAN_HT40U) ^ 794 IS(chan, CHAN_HT40D)) == 0) 795 { 796 HALDEBUG(ah, HAL_DEBUG_CHANNEL, 797 "%s: invalid channel %u/0x%x; not marked as " 798 "OFDM or CCK or DYN or HT20 or HT40PLUS or HT40MINUS\n", 799 __func__, chan->ic_freq , chan->ic_flags); 800 return AH_NULL; 801 } 802#endif 803 804 return (ath_hal_checkchannel(ah, chan)); 805} 806#undef IS 807 808static void 809ar9300_set_11n_regs(struct ath_hal *ah, struct ieee80211_channel *chan, 810 HAL_HT_MACMODE macmode) 811{ 812 u_int32_t phymode; 813// struct ath_hal_9300 *ahp = AH9300(ah); 814 u_int32_t enable_dac_fifo; 815 816 /* XXX */ 817 enable_dac_fifo = 818 OS_REG_READ(ah, AR_PHY_GEN_CTRL) & AR_PHY_GC_ENABLE_DAC_FIFO; 819 820 /* Enable 11n HT, 20 MHz */ 821 phymode = 822 AR_PHY_GC_HT_EN | AR_PHY_GC_SINGLE_HT_LTF1 | AR_PHY_GC_SHORT_GI_40 823 | enable_dac_fifo; 824 /* Configure baseband for dynamic 20/40 operation */ 825 if (IEEE80211_IS_CHAN_HT40(chan)) { 826 phymode |= AR_PHY_GC_DYN2040_EN; 827 /* Configure control (primary) channel at +-10MHz */ 828 if (IEEE80211_IS_CHAN_HT40U(chan)) { 829 phymode |= AR_PHY_GC_DYN2040_PRI_CH; 830 } 831 832#if 0 833 /* Configure 20/25 spacing */ 834 if (ahp->ah_ext_prot_spacing == HAL_HT_EXTPROTSPACING_25) { 835 phymode |= AR_PHY_GC_DYN2040_EXT_CH; 836 } 837#endif 838 } 839 840 /* make sure we preserve INI settings */ 841 phymode |= OS_REG_READ(ah, AR_PHY_GEN_CTRL); 842 843 /* EV 62881/64991 - turn off Green Field detection for Maverick STA beta */ 844 phymode &= ~AR_PHY_GC_GF_DETECT_EN; 845 846 OS_REG_WRITE(ah, AR_PHY_GEN_CTRL, phymode); 847 848 /* Set IFS timing for half/quarter rates */ 849 if (IEEE80211_IS_CHAN_HALF(chan) || IEEE80211_IS_CHAN_QUARTER(chan)) { 850 u_int32_t modeselect = OS_REG_READ(ah, AR_PHY_MODE); 851 852 if (IEEE80211_IS_CHAN_HALF(chan)) { 853 modeselect |= AR_PHY_MS_HALF_RATE; 854 } else if (IEEE80211_IS_CHAN_QUARTER(chan)) { 855 modeselect |= AR_PHY_MS_QUARTER_RATE; 856 } 857 OS_REG_WRITE(ah, AR_PHY_MODE, modeselect); 858 859 ar9300_set_ifs_timing(ah, chan); 860 OS_REG_RMW_FIELD( 861 ah, AR_PHY_FRAME_CTL, AR_PHY_FRAME_CTL_CF_OVERLAP_WINDOW, 0x3); 862 } 863 864 /* Configure MAC for 20/40 operation */ 865 ar9300_set_11n_mac2040(ah, macmode); 866 867 /* global transmit timeout (25 TUs default)*/ 868 /* XXX - put this elsewhere??? */ 869 OS_REG_WRITE(ah, AR_GTXTO, 25 << AR_GTXTO_TIMEOUT_LIMIT_S); 870 871 /* carrier sense timeout */ 872 OS_REG_WRITE(ah, AR_CST, 0xF << AR_CST_TIMEOUT_LIMIT_S); 873} 874 875/* 876 * Spur mitigation for MRC CCK 877 */ 878static void 879ar9300_spur_mitigate_mrc_cck(struct ath_hal *ah, struct ieee80211_channel *chan) 880{ 881 int i; 882 /* spur_freq_for_osprey - hardcoded by Systems team for now. */ 883 u_int32_t spur_freq_for_osprey[4] = { 2420, 2440, 2464, 2480 }; 884 u_int32_t spur_freq_for_jupiter[2] = { 2440, 2464}; 885 int cur_bb_spur, negative = 0, cck_spur_freq; 886 u_int8_t* spur_fbin_ptr = NULL; 887 int synth_freq; 888 int range = 10; 889 int max_spurcounts = OSPREY_EEPROM_MODAL_SPURS; 890 HAL_CHANNEL_INTERNAL *ichan = ath_hal_checkchannel(ah, chan); 891 892 /* 893 * Need to verify range +/- 10 MHz in control channel, otherwise spur 894 * is out-of-band and can be ignored. 895 */ 896 if (AR_SREV_HORNET(ah) || AR_SREV_POSEIDON(ah) || 897 AR_SREV_WASP(ah) || AR_SREV_SCORPION(ah)) { 898 spur_fbin_ptr = ar9300_eeprom_get_spur_chans_ptr(ah, 1); 899 if (spur_fbin_ptr[0] == 0) { 900 return; /* No spur in the mode */ 901 } 902 if (IEEE80211_IS_CHAN_HT40(chan)) { 903 range = 19; 904 if (OS_REG_READ_FIELD(ah, AR_PHY_GEN_CTRL, AR_PHY_GC_DYN2040_PRI_CH) 905 == 0x0) 906 { 907 synth_freq = ichan->channel + 10; 908 } else { 909 synth_freq = ichan->channel - 10; 910 } 911 } else { 912 range = 10; 913 synth_freq = ichan->channel; 914 } 915 } else if(AR_SREV_JUPITER(ah)) { 916 range = 5; 917 max_spurcounts = 2; /* Hardcoded by Jupiter Systems team for now. */ 918 synth_freq = ichan->channel; 919 } else { 920 range = 10; 921 max_spurcounts = 4; /* Hardcoded by Osprey Systems team for now. */ 922 synth_freq = ichan->channel; 923 } 924 925 for (i = 0; i < max_spurcounts; i++) { 926 negative = 0; 927 928 if (AR_SREV_HORNET(ah) || AR_SREV_POSEIDON(ah) || 929 AR_SREV_WASP(ah) || AR_SREV_SCORPION(ah)) { 930 cur_bb_spur = 931 FBIN2FREQ(spur_fbin_ptr[i], HAL_FREQ_BAND_2GHZ) - synth_freq; 932 } else if(AR_SREV_JUPITER(ah)) { 933 cur_bb_spur = spur_freq_for_jupiter[i] - synth_freq; 934 } else { 935 cur_bb_spur = spur_freq_for_osprey[i] - synth_freq; 936 } 937 938 if (cur_bb_spur < 0) { 939 negative = 1; 940 cur_bb_spur = -cur_bb_spur; 941 } 942 if (cur_bb_spur < range) { 943 cck_spur_freq = (int)((cur_bb_spur << 19) / 11); 944 if (negative == 1) { 945 cck_spur_freq = -cck_spur_freq; 946 } 947 cck_spur_freq = cck_spur_freq & 0xfffff; 948 /*OS_REG_WRITE_field(ah, BB_agc_control.ycok_max, 0x7);*/ 949 OS_REG_RMW_FIELD(ah, 950 AR_PHY_AGC_CONTROL, AR_PHY_AGC_CONTROL_YCOK_MAX, 0x7); 951 /*OS_REG_WRITE_field(ah, BB_cck_spur_mit.spur_rssi_thr, 0x7f);*/ 952 OS_REG_RMW_FIELD(ah, 953 AR_PHY_CCK_SPUR_MIT, AR_PHY_CCK_SPUR_MIT_SPUR_RSSI_THR, 0x7f); 954 /*OS_REG_WRITE(ah, BB_cck_spur_mit.spur_filter_type, 0x2);*/ 955 OS_REG_RMW_FIELD(ah, 956 AR_PHY_CCK_SPUR_MIT, AR_PHY_CCK_SPUR_MIT_SPUR_FILTER_TYPE, 0x2); 957 /*OS_REG_WRITE(ah, BB_cck_spur_mit.use_cck_spur_mit, 0x1);*/ 958 OS_REG_RMW_FIELD(ah, 959 AR_PHY_CCK_SPUR_MIT, AR_PHY_CCK_SPUR_MIT_USE_CCK_SPUR_MIT, 0x1); 960 /*OS_REG_WRITE(ah, BB_cck_spur_mit.cck_spur_freq, cck_spur_freq);*/ 961 OS_REG_RMW_FIELD(ah, 962 AR_PHY_CCK_SPUR_MIT, AR_PHY_CCK_SPUR_MIT_CCK_SPUR_FREQ, 963 cck_spur_freq); 964 return; 965 } 966 } 967 968 /*OS_REG_WRITE(ah, BB_agc_control.ycok_max, 0x5);*/ 969 OS_REG_RMW_FIELD(ah, AR_PHY_AGC_CONTROL, AR_PHY_AGC_CONTROL_YCOK_MAX, 0x5); 970 /*OS_REG_WRITE(ah, BB_cck_spur_mit.use_cck_spur_mit, 0x0);*/ 971 OS_REG_RMW_FIELD(ah, 972 AR_PHY_CCK_SPUR_MIT, AR_PHY_CCK_SPUR_MIT_USE_CCK_SPUR_MIT, 0x0); 973 /*OS_REG_WRITE(ah, BB_cck_spur_mit.cck_spur_freq, 0x0);*/ 974 OS_REG_RMW_FIELD(ah, 975 AR_PHY_CCK_SPUR_MIT, AR_PHY_CCK_SPUR_MIT_CCK_SPUR_FREQ, 0x0); 976} 977 978/* Spur mitigation for OFDM */ 979static void 980ar9300_spur_mitigate_ofdm(struct ath_hal *ah, struct ieee80211_channel *chan) 981{ 982 int synth_freq; 983 int range = 10; 984 int freq_offset = 0; 985 int spur_freq_sd = 0; 986 int spur_subchannel_sd = 0; 987 int spur_delta_phase = 0; 988 int mask_index = 0; 989 int i; 990 int mode; 991 u_int8_t* spur_chans_ptr; 992 struct ath_hal_9300 *ahp; 993 ahp = AH9300(ah); 994 HAL_CHANNEL_INTERNAL *ichan = ath_hal_checkchannel(ah, chan); 995 996 if (IS_CHAN_5GHZ(ichan)) { 997 spur_chans_ptr = ar9300_eeprom_get_spur_chans_ptr(ah, 0); 998 mode = 0; 999 } else { 1000 spur_chans_ptr = ar9300_eeprom_get_spur_chans_ptr(ah, 1); 1001 mode = 1; 1002 } 1003 1004 if (IEEE80211_IS_CHAN_HT40(chan)) { 1005 range = 19; 1006 if (OS_REG_READ_FIELD(ah, AR_PHY_GEN_CTRL, AR_PHY_GC_DYN2040_PRI_CH) 1007 == 0x0) 1008 { 1009 synth_freq = ichan->channel - 10; 1010 } else { 1011 synth_freq = ichan->channel + 10; 1012 } 1013 } else { 1014 range = 10; 1015 synth_freq = ichan->channel; 1016 } 1017 1018 /* Clean all spur register fields */ 1019 OS_REG_RMW_FIELD(ah, AR_PHY_TIMING4, AR_PHY_TIMING4_ENABLE_SPUR_FILTER, 0); 1020 OS_REG_RMW_FIELD(ah, AR_PHY_TIMING11, AR_PHY_TIMING11_SPUR_FREQ_SD, 0); 1021 OS_REG_RMW_FIELD(ah, AR_PHY_TIMING11, AR_PHY_TIMING11_SPUR_DELTA_PHASE, 0); 1022 OS_REG_RMW_FIELD(ah, 1023 AR_PHY_SFCORR_EXT, AR_PHY_SFCORR_EXT_SPUR_SUBCHANNEL_SD, 0); 1024 OS_REG_RMW_FIELD(ah, 1025 AR_PHY_TIMING11, AR_PHY_TIMING11_USE_SPUR_FILTER_IN_AGC, 0); 1026 OS_REG_RMW_FIELD(ah, 1027 AR_PHY_TIMING11, AR_PHY_TIMING11_USE_SPUR_FILTER_IN_SELFCOR, 0); 1028 OS_REG_RMW_FIELD(ah, AR_PHY_TIMING4, AR_PHY_TIMING4_ENABLE_SPUR_RSSI, 0); 1029 OS_REG_RMW_FIELD(ah, AR_PHY_SPUR_REG, AR_PHY_SPUR_REG_EN_VIT_SPUR_RSSI, 0); 1030 OS_REG_RMW_FIELD(ah, 1031 AR_PHY_SPUR_REG, AR_PHY_SPUR_REG_ENABLE_NF_RSSI_SPUR_MIT, 0); 1032 OS_REG_RMW_FIELD(ah, AR_PHY_SPUR_REG, AR_PHY_SPUR_REG_ENABLE_MASK_PPM, 0); 1033 OS_REG_RMW_FIELD(ah, AR_PHY_TIMING4, AR_PHY_TIMING4_ENABLE_PILOT_MASK, 0); 1034 OS_REG_RMW_FIELD(ah, AR_PHY_TIMING4, AR_PHY_TIMING4_ENABLE_CHAN_MASK, 0); 1035 OS_REG_RMW_FIELD(ah, 1036 AR_PHY_PILOT_SPUR_MASK, AR_PHY_PILOT_SPUR_MASK_CF_PILOT_MASK_IDX_A, 0); 1037 OS_REG_RMW_FIELD(ah, 1038 AR_PHY_SPUR_MASK_A, AR_PHY_SPUR_MASK_A_CF_PUNC_MASK_IDX_A, 0); 1039 OS_REG_RMW_FIELD(ah, 1040 AR_PHY_CHAN_SPUR_MASK, AR_PHY_CHAN_SPUR_MASK_CF_CHAN_MASK_IDX_A, 0); 1041 OS_REG_RMW_FIELD(ah, 1042 AR_PHY_PILOT_SPUR_MASK, AR_PHY_PILOT_SPUR_MASK_CF_PILOT_MASK_A, 0); 1043 OS_REG_RMW_FIELD(ah, 1044 AR_PHY_CHAN_SPUR_MASK, AR_PHY_CHAN_SPUR_MASK_CF_CHAN_MASK_A, 0); 1045 OS_REG_RMW_FIELD(ah, 1046 AR_PHY_SPUR_MASK_A, AR_PHY_SPUR_MASK_A_CF_PUNC_MASK_A, 0); 1047 OS_REG_RMW_FIELD(ah, AR_PHY_SPUR_REG, AR_PHY_SPUR_REG_MASK_RATE_CNTL, 0); 1048 1049 i = 0; 1050 while (spur_chans_ptr[i] && i < 5) { 1051 freq_offset = FBIN2FREQ(spur_chans_ptr[i], mode) - synth_freq; 1052 if (abs(freq_offset) < range) { 1053 /* 1054 printf( 1055 "Spur Mitigation for OFDM: Synth Frequency = %d, " 1056 "Spur Frequency = %d\n", 1057 synth_freq, FBIN2FREQ(spur_chans_ptr[i], mode)); 1058 */ 1059 if (IEEE80211_IS_CHAN_HT40(chan)) { 1060 if (freq_offset < 0) { 1061 if (OS_REG_READ_FIELD( 1062 ah, AR_PHY_GEN_CTRL, AR_PHY_GC_DYN2040_PRI_CH) == 0x0) 1063 { 1064 spur_subchannel_sd = 1; 1065 } else { 1066 spur_subchannel_sd = 0; 1067 } 1068 spur_freq_sd = ((freq_offset + 10) << 9) / 11; 1069 } else { 1070 if (OS_REG_READ_FIELD(ah, 1071 AR_PHY_GEN_CTRL, AR_PHY_GC_DYN2040_PRI_CH) == 0x0) 1072 { 1073 spur_subchannel_sd = 0; 1074 } else { 1075 spur_subchannel_sd = 1; 1076 } 1077 spur_freq_sd = ((freq_offset - 10) << 9) / 11; 1078 } 1079 spur_delta_phase = (freq_offset << 17) / 5; 1080 } else { 1081 spur_subchannel_sd = 0; 1082 spur_freq_sd = (freq_offset << 9) / 11; 1083 spur_delta_phase = (freq_offset << 18) / 5; 1084 } 1085 spur_freq_sd = spur_freq_sd & 0x3ff; 1086 spur_delta_phase = spur_delta_phase & 0xfffff; 1087 /* 1088 printf( 1089 "spur_subchannel_sd = %d, spur_freq_sd = 0x%x, " 1090 "spur_delta_phase = 0x%x\n", spur_subchannel_sd, 1091 spur_freq_sd, spur_delta_phase); 1092 */ 1093 1094 /* OFDM Spur mitigation */ 1095 OS_REG_RMW_FIELD(ah, 1096 AR_PHY_TIMING4, AR_PHY_TIMING4_ENABLE_SPUR_FILTER, 0x1); 1097 OS_REG_RMW_FIELD(ah, 1098 AR_PHY_TIMING11, AR_PHY_TIMING11_SPUR_FREQ_SD, spur_freq_sd); 1099 OS_REG_RMW_FIELD(ah, 1100 AR_PHY_TIMING11, AR_PHY_TIMING11_SPUR_DELTA_PHASE, 1101 spur_delta_phase); 1102 OS_REG_RMW_FIELD(ah, 1103 AR_PHY_SFCORR_EXT, AR_PHY_SFCORR_EXT_SPUR_SUBCHANNEL_SD, 1104 spur_subchannel_sd); 1105 OS_REG_RMW_FIELD(ah, 1106 AR_PHY_TIMING11, AR_PHY_TIMING11_USE_SPUR_FILTER_IN_AGC, 0x1); 1107 OS_REG_RMW_FIELD(ah, 1108 AR_PHY_TIMING11, AR_PHY_TIMING11_USE_SPUR_FILTER_IN_SELFCOR, 1109 0x1); 1110 OS_REG_RMW_FIELD(ah, 1111 AR_PHY_TIMING4, AR_PHY_TIMING4_ENABLE_SPUR_RSSI, 0x1); 1112 OS_REG_RMW_FIELD(ah, 1113 AR_PHY_SPUR_REG, AR_PHY_SPUR_REG_SPUR_RSSI_THRESH, 34); 1114 OS_REG_RMW_FIELD(ah, 1115 AR_PHY_SPUR_REG, AR_PHY_SPUR_REG_EN_VIT_SPUR_RSSI, 1); 1116 1117 /* 1118 * Do not subtract spur power from noise floor for wasp. 1119 * This causes the maximum client test (on Veriwave) to fail 1120 * when run on spur channel (2464 MHz). 1121 * Refer to ev#82746 and ev#82744. 1122 */ 1123 if (!AR_SREV_WASP(ah) && (OS_REG_READ_FIELD(ah, AR_PHY_MODE, 1124 AR_PHY_MODE_DYNAMIC) == 0x1)) { 1125 OS_REG_RMW_FIELD(ah, AR_PHY_SPUR_REG, 1126 AR_PHY_SPUR_REG_ENABLE_NF_RSSI_SPUR_MIT, 1); 1127 } 1128 1129 mask_index = (freq_offset << 4) / 5; 1130 if (mask_index < 0) { 1131 mask_index = mask_index - 1; 1132 } 1133 mask_index = mask_index & 0x7f; 1134 /*printf("Bin 0x%x\n", mask_index);*/ 1135 1136 OS_REG_RMW_FIELD(ah, 1137 AR_PHY_SPUR_REG, AR_PHY_SPUR_REG_ENABLE_MASK_PPM, 0x1); 1138 OS_REG_RMW_FIELD(ah, 1139 AR_PHY_TIMING4, AR_PHY_TIMING4_ENABLE_PILOT_MASK, 0x1); 1140 OS_REG_RMW_FIELD(ah, 1141 AR_PHY_TIMING4, AR_PHY_TIMING4_ENABLE_CHAN_MASK, 0x1); 1142 OS_REG_RMW_FIELD(ah, 1143 AR_PHY_PILOT_SPUR_MASK, 1144 AR_PHY_PILOT_SPUR_MASK_CF_PILOT_MASK_IDX_A, mask_index); 1145 OS_REG_RMW_FIELD(ah, 1146 AR_PHY_SPUR_MASK_A, AR_PHY_SPUR_MASK_A_CF_PUNC_MASK_IDX_A, 1147 mask_index); 1148 OS_REG_RMW_FIELD(ah, 1149 AR_PHY_CHAN_SPUR_MASK, 1150 AR_PHY_CHAN_SPUR_MASK_CF_CHAN_MASK_IDX_A, mask_index); 1151 OS_REG_RMW_FIELD(ah, 1152 AR_PHY_PILOT_SPUR_MASK, AR_PHY_PILOT_SPUR_MASK_CF_PILOT_MASK_A, 1153 0xc); 1154 OS_REG_RMW_FIELD(ah, 1155 AR_PHY_CHAN_SPUR_MASK, AR_PHY_CHAN_SPUR_MASK_CF_CHAN_MASK_A, 1156 0xc); 1157 OS_REG_RMW_FIELD(ah, 1158 AR_PHY_SPUR_MASK_A, AR_PHY_SPUR_MASK_A_CF_PUNC_MASK_A, 0xa0); 1159 OS_REG_RMW_FIELD(ah, 1160 AR_PHY_SPUR_REG, AR_PHY_SPUR_REG_MASK_RATE_CNTL, 0xff); 1161 /* 1162 printf("BB_timing_control_4 = 0x%x\n", 1163 OS_REG_READ(ah, AR_PHY_TIMING4)); 1164 printf("BB_timing_control_11 = 0x%x\n", 1165 OS_REG_READ(ah, AR_PHY_TIMING11)); 1166 printf("BB_ext_chan_scorr_thr = 0x%x\n", 1167 OS_REG_READ(ah, AR_PHY_SFCORR_EXT)); 1168 printf("BB_spur_mask_controls = 0x%x\n", 1169 OS_REG_READ(ah, AR_PHY_SPUR_REG)); 1170 printf("BB_pilot_spur_mask = 0x%x\n", 1171 OS_REG_READ(ah, AR_PHY_PILOT_SPUR_MASK)); 1172 printf("BB_chan_spur_mask = 0x%x\n", 1173 OS_REG_READ(ah, AR_PHY_CHAN_SPUR_MASK)); 1174 printf("BB_vit_spur_mask_A = 0x%x\n", 1175 OS_REG_READ(ah, AR_PHY_SPUR_MASK_A)); 1176 */ 1177 break; 1178 } 1179 i++; 1180 } 1181} 1182 1183 1184/* 1185 * Convert to baseband spur frequency given input channel frequency 1186 * and compute register settings below. 1187 */ 1188static void 1189ar9300_spur_mitigate(struct ath_hal *ah, struct ieee80211_channel *chan) 1190{ 1191 ar9300_spur_mitigate_ofdm(ah, chan); 1192 ar9300_spur_mitigate_mrc_cck(ah, chan); 1193} 1194 1195/************************************************************** 1196 * ar9300_channel_change 1197 * Assumes caller wants to change channel, and not reset. 1198 */ 1199static inline HAL_BOOL 1200ar9300_channel_change(struct ath_hal *ah, struct ieee80211_channel *chan, 1201 HAL_CHANNEL_INTERNAL *ichan, HAL_HT_MACMODE macmode) 1202{ 1203 1204 u_int32_t synth_delay, qnum; 1205 struct ath_hal_9300 *ahp = AH9300(ah); 1206 1207 /* TX must be stopped by now */ 1208 for (qnum = 0; qnum < AR_NUM_QCU; qnum++) { 1209 if (ar9300_num_tx_pending(ah, qnum)) { 1210 HALDEBUG(ah, HAL_DEBUG_QUEUE, 1211 "%s: Transmit frames pending on queue %d\n", __func__, qnum); 1212 HALASSERT(0); 1213 return AH_FALSE; 1214 } 1215 } 1216 1217 1218 /* 1219 * Kill last Baseband Rx Frame - Request analog bus grant 1220 */ 1221 OS_REG_WRITE(ah, AR_PHY_RFBUS_REQ, AR_PHY_RFBUS_REQ_EN); 1222 if (!ath_hal_wait(ah, AR_PHY_RFBUS_GRANT, AR_PHY_RFBUS_GRANT_EN, 1223 AR_PHY_RFBUS_GRANT_EN)) 1224 { 1225 HALDEBUG(ah, HAL_DEBUG_PHYIO, 1226 "%s: Could not kill baseband RX\n", __func__); 1227 return AH_FALSE; 1228 } 1229 1230 1231 /* Setup 11n MAC/Phy mode registers */ 1232 ar9300_set_11n_regs(ah, chan, macmode); 1233 1234 /* 1235 * Change the synth 1236 */ 1237 if (!ahp->ah_rf_hal.set_channel(ah, chan)) { 1238 HALDEBUG(ah, HAL_DEBUG_CHANNEL, "%s: failed to set channel\n", __func__); 1239 return AH_FALSE; 1240 } 1241 1242 /* 1243 * Some registers get reinitialized during ATH_INI_POST INI programming. 1244 */ 1245 ar9300_init_user_settings(ah); 1246 1247 /* 1248 * Setup the transmit power values. 1249 * 1250 * After the public to private hal channel mapping, ichan contains the 1251 * valid regulatory power value. 1252 * ath_hal_getctl and ath_hal_getantennaallowed look up ichan from chan. 1253 */ 1254 if (ar9300_eeprom_set_transmit_power( 1255 ah, &ahp->ah_eeprom, chan, ath_hal_getctl(ah, chan), 1256 ath_hal_getantennaallowed(ah, chan), 1257 ath_hal_get_twice_max_regpower(AH_PRIVATE(ah), ichan, chan), 1258 AH_MIN(MAX_RATE_POWER, AH_PRIVATE(ah)->ah_powerLimit)) != HAL_OK) 1259 { 1260 HALDEBUG(ah, HAL_DEBUG_EEPROM, 1261 "%s: error init'ing transmit power\n", __func__); 1262 return AH_FALSE; 1263 } 1264 1265 /* 1266 * Release the RFBus Grant. 1267 */ 1268 OS_REG_WRITE(ah, AR_PHY_RFBUS_REQ, 0); 1269 1270 /* 1271 * Write spur immunity and delta slope for OFDM enabled modes (A, G, Turbo) 1272 */ 1273 if (IEEE80211_IS_CHAN_OFDM(chan) || IEEE80211_IS_CHAN_HT(chan)) { 1274 ar9300_set_delta_slope(ah, chan); 1275 } else { 1276 /* Set to Ini default */ 1277 OS_REG_WRITE(ah, AR_PHY_TIMING3, 0x9c0a9f6b); 1278 OS_REG_WRITE(ah, AR_PHY_SGI_DELTA, 0x00046384); 1279 } 1280 1281 ar9300_spur_mitigate(ah, chan); 1282 1283 1284 /* 1285 * Wait for the frequency synth to settle (synth goes on via PHY_ACTIVE_EN). 1286 * Read the phy active delay register. Value is in 100ns increments. 1287 */ 1288 synth_delay = OS_REG_READ(ah, AR_PHY_RX_DELAY) & AR_PHY_RX_DELAY_DELAY; 1289 if (IEEE80211_IS_CHAN_CCK(chan)) { 1290 synth_delay = (4 * synth_delay) / 22; 1291 } else { 1292 synth_delay /= 10; 1293 } 1294 1295 OS_DELAY(synth_delay + BASE_ACTIVATE_DELAY); 1296 1297 /* 1298 * Do calibration. 1299 */ 1300 1301 return AH_TRUE; 1302} 1303 1304void 1305ar9300_set_operating_mode(struct ath_hal *ah, int opmode) 1306{ 1307 u_int32_t val; 1308 1309 val = OS_REG_READ(ah, AR_STA_ID1); 1310 val &= ~(AR_STA_ID1_STA_AP | AR_STA_ID1_ADHOC); 1311 switch (opmode) { 1312 case HAL_M_HOSTAP: 1313 OS_REG_WRITE(ah, AR_STA_ID1, 1314 val | AR_STA_ID1_STA_AP | AR_STA_ID1_KSRCH_MODE); 1315 OS_REG_CLR_BIT(ah, AR_CFG, AR_CFG_AP_ADHOC_INDICATION); 1316 break; 1317 case HAL_M_IBSS: 1318 OS_REG_WRITE(ah, AR_STA_ID1, 1319 val | AR_STA_ID1_ADHOC | AR_STA_ID1_KSRCH_MODE); 1320 OS_REG_SET_BIT(ah, AR_CFG, AR_CFG_AP_ADHOC_INDICATION); 1321 break; 1322 case HAL_M_STA: 1323 case HAL_M_MONITOR: 1324 OS_REG_WRITE(ah, AR_STA_ID1, val | AR_STA_ID1_KSRCH_MODE); 1325 break; 1326 } 1327} 1328 1329/* XXX need the logic for Osprey */ 1330inline void 1331ar9300_init_pll(struct ath_hal *ah, struct ieee80211_channel *chan) 1332{ 1333 u_int32_t pll; 1334 u_int8_t clk_25mhz = AH9300(ah)->clk_25mhz; 1335 HAL_CHANNEL_INTERNAL *ichan = NULL; 1336 1337 if (chan) 1338 ichan = ath_hal_checkchannel(ah, chan); 1339 1340 if (AR_SREV_HORNET(ah)) { 1341 if (clk_25mhz) { 1342 /* Hornet uses PLL_CONTROL_2. Xtal is 25MHz for Hornet. 1343 * REFDIV set to 0x1. 1344 * $xtal_freq = 25; 1345 * $PLL2_div = (704/$xtal_freq); # 176 * 4 = 704. 1346 * MAC and BB run at 176 MHz. 1347 * $PLL2_divint = int($PLL2_div); 1348 * $PLL2_divfrac = $PLL2_div - $PLL2_divint; 1349 * $PLL2_divfrac = int($PLL2_divfrac * 0x4000); # 2^14 1350 * $PLL2_Val = ($PLL2_divint & 0x3f) << 19 | (0x1) << 14 | 1351 * $PLL2_divfrac & 0x3fff; 1352 * Therefore, $PLL2_Val = 0xe04a3d 1353 */ 1354#define DPLL2_KD_VAL 0x1D 1355#define DPLL2_KI_VAL 0x06 1356#define DPLL3_PHASE_SHIFT_VAL 0x1 1357 1358 /* Rewrite DDR PLL2 and PLL3 */ 1359 /* program DDR PLL ki and kd value, ki=0x6, kd=0x1d */ 1360 OS_REG_WRITE(ah, AR_HORNET_CH0_DDR_DPLL2, 0x18e82f01); 1361 1362 /* program DDR PLL phase_shift to 0x1 */ 1363 OS_REG_RMW_FIELD(ah, AR_HORNET_CH0_DDR_DPLL3, 1364 AR_PHY_BB_DPLL3_PHASE_SHIFT, DPLL3_PHASE_SHIFT_VAL); 1365 1366 OS_REG_WRITE(ah, AR_RTC_PLL_CONTROL, 0x1142c); 1367 OS_DELAY(1000); 1368 1369 /* program refdiv, nint, frac to RTC register */ 1370 OS_REG_WRITE(ah, AR_RTC_PLL_CONTROL2, 0xe04a3d); 1371 1372 /* program BB PLL ki and kd value, ki=0x6, kd=0x1d */ 1373 OS_REG_RMW_FIELD(ah, AR_PHY_BB_DPLL2, 1374 AR_PHY_BB_DPLL2_KD, DPLL2_KD_VAL); 1375 OS_REG_RMW_FIELD(ah, AR_PHY_BB_DPLL2, 1376 AR_PHY_BB_DPLL2_KI, DPLL2_KI_VAL); 1377 1378 /* program BB PLL phase_shift to 0x1 */ 1379 OS_REG_RMW_FIELD(ah, AR_PHY_BB_DPLL3, 1380 AR_PHY_BB_DPLL3_PHASE_SHIFT, DPLL3_PHASE_SHIFT_VAL); 1381 } else { /* 40MHz */ 1382#undef DPLL2_KD_VAL 1383#undef DPLL2_KI_VAL 1384#define DPLL2_KD_VAL 0x3D 1385#define DPLL2_KI_VAL 0x06 1386 /* Rewrite DDR PLL2 and PLL3 */ 1387 /* program DDR PLL ki and kd value, ki=0x6, kd=0x3d */ 1388 OS_REG_WRITE(ah, AR_HORNET_CH0_DDR_DPLL2, 0x19e82f01); 1389 1390 /* program DDR PLL phase_shift to 0x1 */ 1391 OS_REG_RMW_FIELD(ah, AR_HORNET_CH0_DDR_DPLL3, 1392 AR_PHY_BB_DPLL3_PHASE_SHIFT, DPLL3_PHASE_SHIFT_VAL); 1393 1394 OS_REG_WRITE(ah, AR_RTC_PLL_CONTROL, 0x1142c); 1395 OS_DELAY(1000); 1396 1397 /* program refdiv, nint, frac to RTC register */ 1398 OS_REG_WRITE(ah, AR_RTC_PLL_CONTROL2, 0x886666); 1399 1400 /* program BB PLL ki and kd value, ki=0x6, kd=0x3d */ 1401 OS_REG_RMW_FIELD(ah, AR_PHY_BB_DPLL2, 1402 AR_PHY_BB_DPLL2_KD, DPLL2_KD_VAL); 1403 OS_REG_RMW_FIELD(ah, AR_PHY_BB_DPLL2, 1404 AR_PHY_BB_DPLL2_KI, DPLL2_KI_VAL); 1405 1406 /* program BB PLL phase_shift to 0x1 */ 1407 OS_REG_RMW_FIELD(ah, AR_PHY_BB_DPLL3, 1408 AR_PHY_BB_DPLL3_PHASE_SHIFT, DPLL3_PHASE_SHIFT_VAL); 1409 } 1410 OS_REG_WRITE(ah, AR_RTC_PLL_CONTROL, 0x142c); 1411 OS_DELAY(1000); 1412 } else if (AR_SREV_POSEIDON(ah) || AR_SREV_APHRODITE(ah)) { 1413 OS_REG_RMW_FIELD(ah, AR_PHY_BB_DPLL2, AR_PHY_BB_DPLL2_PLL_PWD, 0x1); 1414 1415 /* program BB PLL ki and kd value, ki=0x4, kd=0x40 */ 1416 OS_REG_RMW_FIELD(ah, AR_PHY_BB_DPLL2, 1417 AR_PHY_BB_DPLL2_KD, 0x40); 1418 OS_REG_RMW_FIELD(ah, AR_PHY_BB_DPLL2, 1419 AR_PHY_BB_DPLL2_KI, 0x4); 1420 1421 OS_REG_RMW_FIELD(ah, AR_PHY_BB_DPLL1, 1422 AR_PHY_BB_DPLL1_REFDIV, 0x5); 1423 OS_REG_RMW_FIELD(ah, AR_PHY_BB_DPLL1, 1424 AR_PHY_BB_DPLL1_NINI, 0x58); 1425 OS_REG_RMW_FIELD(ah, AR_PHY_BB_DPLL1, 1426 AR_PHY_BB_DPLL1_NFRAC, 0x0); 1427 1428 OS_REG_RMW_FIELD(ah, AR_PHY_BB_DPLL2, 1429 AR_PHY_BB_DPLL2_OUTDIV, 0x1); 1430 OS_REG_RMW_FIELD(ah, AR_PHY_BB_DPLL2, 1431 AR_PHY_BB_DPLL2_LOCAL_PLL, 0x1); 1432 OS_REG_RMW_FIELD(ah, AR_PHY_BB_DPLL2, 1433 AR_PHY_BB_DPLL2_EN_NEGTRIG, 0x1); 1434 1435 /* program BB PLL phase_shift to 0x6 */ 1436 OS_REG_RMW_FIELD(ah, AR_PHY_BB_DPLL3, 1437 AR_PHY_BB_DPLL3_PHASE_SHIFT, 0x6); 1438 1439 OS_REG_RMW_FIELD(ah, AR_PHY_BB_DPLL2, 1440 AR_PHY_BB_DPLL2_PLL_PWD, 0x0); 1441 OS_DELAY(1000); 1442 1443 OS_REG_WRITE(ah, AR_RTC_PLL_CONTROL, 0x142c); 1444 OS_DELAY(1000); 1445 } else if (AR_SREV_WASP(ah) || AR_SREV_SCORPION(ah)) { 1446#define SRIF_PLL 1 1447 u_int32_t regdata, pll2_divint, pll2_divfrac; 1448 1449#ifndef SRIF_PLL 1450 u_int32_t pll2_clkmode; 1451#endif 1452 1453#ifdef SRIF_PLL 1454 u_int32_t refdiv; 1455#endif 1456 if (clk_25mhz) { 1457#ifndef SRIF_PLL 1458 pll2_divint = 0x1c; 1459 pll2_divfrac = 0xa3d7; 1460#else 1461 pll2_divint = 0x54; 1462 pll2_divfrac = 0x1eb85; 1463 refdiv = 3; 1464#endif 1465 } else { 1466#ifndef SRIF_PLL 1467 pll2_divint = 0x11; 1468 pll2_divfrac = 0x26666; 1469#else 1470 if (AR_SREV_WASP(ah)) { 1471 pll2_divint = 88; 1472 pll2_divfrac = 0; 1473 refdiv = 5; 1474 } else { 1475 pll2_divint = 0x11; 1476 pll2_divfrac = 0x26666; 1477 refdiv = 1; 1478 } 1479#endif 1480 } 1481#ifndef SRIF_PLL 1482 pll2_clkmode = 0x3d; 1483#endif 1484 /* PLL programming through SRIF Local Mode */ 1485 OS_REG_WRITE(ah, AR_RTC_PLL_CONTROL, 0x1142c); /* Bypass mode */ 1486 OS_DELAY(1000); 1487 do { 1488 regdata = OS_REG_READ(ah, AR_PHY_PLL_MODE); 1489 regdata = regdata | (0x1 << 16); 1490 OS_REG_WRITE(ah, AR_PHY_PLL_MODE, regdata); /* PWD_PLL set to 1 */ 1491 OS_DELAY(100); 1492 /* override int, frac, refdiv */ 1493#ifndef SRIF_PLL 1494 OS_REG_WRITE(ah, AR_PHY_PLL_CONTROL, 1495 ((1 << 27) | (pll2_divint << 18) | pll2_divfrac)); 1496#else 1497 OS_REG_WRITE(ah, AR_PHY_PLL_CONTROL, 1498 ((refdiv << 27) | (pll2_divint << 18) | pll2_divfrac)); 1499#endif 1500 OS_DELAY(100); 1501 regdata = OS_REG_READ(ah, AR_PHY_PLL_MODE); 1502#ifndef SRIF_PLL 1503 regdata = (regdata & 0x80071fff) | 1504 (0x1 << 30) | (0x1 << 13) | (0x6 << 26) | (pll2_clkmode << 19); 1505#else 1506 if (AR_SREV_WASP(ah)) { 1507 regdata = (regdata & 0x80071fff) | 1508 (0x1 << 30) | (0x1 << 13) | (0x4 << 26) | (0x18 << 19); 1509 } else { 1510 regdata = (regdata & 0x80071fff) | 1511 (0x3 << 30) | (0x1 << 13) | (0x4 << 26) | (0x60 << 19); 1512 } 1513#endif 1514 /* Ki, Kd, Local PLL, Outdiv */ 1515 OS_REG_WRITE(ah, AR_PHY_PLL_MODE, regdata); 1516 regdata = OS_REG_READ(ah, AR_PHY_PLL_MODE); 1517 regdata = (regdata & 0xfffeffff); 1518 OS_REG_WRITE(ah, AR_PHY_PLL_MODE, regdata); /* PWD_PLL set to 0 */ 1519 OS_DELAY(1000); 1520 if (AR_SREV_WASP(ah)) { 1521 /* clear do measure */ 1522 regdata = OS_REG_READ(ah, AR_PHY_PLL_BB_DPLL3); 1523 regdata &= ~(1 << 30); 1524 OS_REG_WRITE(ah, AR_PHY_PLL_BB_DPLL3, regdata); 1525 OS_DELAY(100); 1526 1527 /* set do measure */ 1528 regdata = OS_REG_READ(ah, AR_PHY_PLL_BB_DPLL3); 1529 regdata |= (1 << 30); 1530 OS_REG_WRITE(ah, AR_PHY_PLL_BB_DPLL3, regdata); 1531 1532 /* wait for measure done */ 1533 do { 1534 regdata = OS_REG_READ(ah, AR_PHY_PLL_BB_DPLL4); 1535 } while ((regdata & (1 << 3)) == 0); 1536 1537 /* clear do measure */ 1538 regdata = OS_REG_READ(ah, AR_PHY_PLL_BB_DPLL3); 1539 regdata &= ~(1 << 30); 1540 OS_REG_WRITE(ah, AR_PHY_PLL_BB_DPLL3, regdata); 1541 1542 /* get measure sqsum dvc */ 1543 regdata = (OS_REG_READ(ah, AR_PHY_PLL_BB_DPLL3) & 0x007FFFF8) >> 3; 1544 } else { 1545 break; 1546 } 1547 } while (regdata >= 0x40000); 1548 1549 /* Remove from Bypass mode */ 1550 OS_REG_WRITE(ah, AR_RTC_PLL_CONTROL, 0x142c); 1551 OS_DELAY(1000); 1552 } else { 1553 pll = SM(0x5, AR_RTC_PLL_REFDIV); 1554 1555 /* Supposedly not needed on Osprey */ 1556#if 0 1557 if (chan && IS_CHAN_HALF_RATE(chan)) { 1558 pll |= SM(0x1, AR_RTC_PLL_CLKSEL); 1559 } else if (chan && IS_CHAN_QUARTER_RATE(chan)) { 1560 pll |= SM(0x2, AR_RTC_PLL_CLKSEL); 1561 } 1562#endif 1563 if (ichan && IS_CHAN_5GHZ(ichan)) { 1564 pll |= SM(0x28, AR_RTC_PLL_DIV); 1565 /* 1566 * When doing fast clock, set PLL to 0x142c 1567 */ 1568 if (IS_5GHZ_FAST_CLOCK_EN(ah, chan)) { 1569 pll = 0x142c; 1570 } 1571 } else { 1572 pll |= SM(0x2c, AR_RTC_PLL_DIV); 1573 } 1574 1575 OS_REG_WRITE(ah, AR_RTC_PLL_CONTROL, pll); 1576 } 1577 1578 /* TODO: 1579 * For multi-band owl, switch between bands by reiniting the PLL. 1580 */ 1581 OS_DELAY(RTC_PLL_SETTLE_DELAY); 1582 1583 OS_REG_WRITE(ah, AR_RTC_SLEEP_CLK, 1584 AR_RTC_FORCE_DERIVED_CLK | AR_RTC_PCIE_RST_PWDN_EN); 1585 1586 if (AR_SREV_WASP(ah) || AR_SREV_SCORPION(ah)) { 1587 if (clk_25mhz) { 1588 OS_REG_WRITE(ah, 1589 AR_RTC_DERIVED_RTC_CLK, (0x17c << 1)); /* 32KHz sleep clk */ 1590 OS_REG_WRITE(ah, AR_SLP32_MODE, 0x0010f3d7); 1591 OS_REG_WRITE(ah, AR_SLP32_INC, 0x0001e7ae); 1592 } else { 1593 OS_REG_WRITE(ah, 1594 AR_RTC_DERIVED_RTC_CLK, (0x261 << 1)); /* 32KHz sleep clk */ 1595 OS_REG_WRITE(ah, AR_SLP32_MODE, 0x0010f400); 1596 OS_REG_WRITE(ah, AR_SLP32_INC, 0x0001e800); 1597 } 1598 OS_DELAY(100); 1599 } 1600} 1601 1602static inline HAL_BOOL 1603ar9300_set_reset(struct ath_hal *ah, int type) 1604{ 1605 u_int32_t rst_flags; 1606 u_int32_t tmp_reg; 1607 1608 HALASSERT(type == HAL_RESET_WARM || type == HAL_RESET_COLD); 1609 1610 /* 1611 * RTC Force wake should be done before resetting the MAC. 1612 * MDK/ART does it that way. 1613 */ 1614 OS_REG_WRITE(ah, AR_HOSTIF_REG(ah, AR_WA), AH9300(ah)->ah_wa_reg_val); 1615 OS_DELAY(10); /* delay to allow AR_WA reg write to kick in */ 1616 OS_REG_WRITE(ah, 1617 AR_RTC_FORCE_WAKE, AR_RTC_FORCE_WAKE_EN | AR_RTC_FORCE_WAKE_ON_INT); 1618 1619 /* Reset AHB */ 1620 /* Bug26871 */ 1621 tmp_reg = OS_REG_READ(ah, AR_HOSTIF_REG(ah, AR_INTR_SYNC_CAUSE)); 1622 if (AR_SREV_WASP(ah)) { 1623 if (tmp_reg & (AR9340_INTR_SYNC_LOCAL_TIMEOUT)) { 1624 OS_REG_WRITE(ah, AR_HOSTIF_REG(ah, AR_INTR_SYNC_ENABLE), 0); 1625 OS_REG_WRITE(ah, AR_HOSTIF_REG(ah, AR_RC), AR_RC_HOSTIF); 1626 } 1627 } else { 1628 if (tmp_reg & (AR9300_INTR_SYNC_LOCAL_TIMEOUT | AR9300_INTR_SYNC_RADM_CPL_TIMEOUT)) { 1629 OS_REG_WRITE(ah, AR_HOSTIF_REG(ah, AR_INTR_SYNC_ENABLE), 0); 1630 OS_REG_WRITE(ah, AR_HOSTIF_REG(ah, AR_RC), AR_RC_HOSTIF); 1631 } 1632 else { 1633 /* NO AR_RC_AHB in Osprey */ 1634 /*OS_REG_WRITE(ah, AR_HOSTIF_REG(ah, AR_RC), AR_RC_AHB);*/ 1635 } 1636 } 1637 1638 rst_flags = AR_RTC_RC_MAC_WARM; 1639 if (type == HAL_RESET_COLD) { 1640 rst_flags |= AR_RTC_RC_MAC_COLD; 1641 } 1642 1643#ifdef AH_SUPPORT_HORNET 1644 /* Hornet WAR: trigger SoC to reset WMAC if ... 1645 * (1) doing cold reset. Ref: EV 69254 1646 * (2) beacon pending. Ref: EV 70983 1647 */ 1648 if (AR_SREV_HORNET(ah) && 1649 (ar9300_num_tx_pending( 1650 ah, AH_PRIVATE(ah)->ah_caps.halTotalQueues - 1) != 0 || 1651 type == HAL_RESET_COLD)) 1652 { 1653 u_int32_t time_out; 1654#define AR_SOC_RST_RESET 0xB806001C 1655#define AR_SOC_BOOT_STRAP 0xB80600AC 1656#define AR_SOC_WLAN_RST 0x00000800 /* WLAN reset */ 1657#define REG_WRITE(_reg, _val) *((volatile u_int32_t *)(_reg)) = (_val); 1658#define REG_READ(_reg) *((volatile u_int32_t *)(_reg)) 1659 HALDEBUG(ah, HAL_DEBUG_RESET, "%s: Hornet SoC reset WMAC.\n", __func__); 1660 1661 REG_WRITE(AR_SOC_RST_RESET, 1662 REG_READ(AR_SOC_RST_RESET) | AR_SOC_WLAN_RST); 1663 REG_WRITE(AR_SOC_RST_RESET, 1664 REG_READ(AR_SOC_RST_RESET) & (~AR_SOC_WLAN_RST)); 1665 1666 time_out = 0; 1667 1668 while (1) { 1669 tmp_reg = REG_READ(AR_SOC_BOOT_STRAP); 1670 if ((tmp_reg & 0x10) == 0) { 1671 break; 1672 } 1673 if (time_out > 20) { 1674 break; 1675 } 1676 OS_DELAY(10000); 1677 time_out++; 1678 } 1679 1680 OS_REG_WRITE(ah, AR_RTC_RESET, 1); 1681#undef REG_READ 1682#undef REG_WRITE 1683#undef AR_SOC_WLAN_RST 1684#undef AR_SOC_RST_RESET 1685#undef AR_SOC_BOOT_STRAP 1686 } 1687#endif /* AH_SUPPORT_HORNET */ 1688 1689#ifdef AH_SUPPORT_SCORPION 1690 if (AR_SREV_SCORPION(ah)) { 1691#define DDR_CTL_CONFIG_ADDRESS 0xb8000000 1692#define DDR_CTL_CONFIG_OFFSET 0x0108 1693#define DDR_CTL_CONFIG_CLIENT_ACTIVITY_MSB 29 1694#define DDR_CTL_CONFIG_CLIENT_ACTIVITY_LSB 21 1695#define DDR_CTL_CONFIG_CLIENT_ACTIVITY_MASK 0x3fe00000 1696#define DDR_CTL_CONFIG_CLIENT_ACTIVITY_GET(x) (((x) & DDR_CTL_CONFIG_CLIENT_ACTIVITY_MASK) >> DDR_CTL_CONFIG_CLIENT_ACTIVITY_LSB) 1697#define DDR_CTL_CONFIG_CLIENT_ACTIVITY_SET(x) (((x) << DDR_CTL_CONFIG_CLIENT_ACTIVITY_LSB) & DDR_CTL_CONFIG_CLIENT_ACTIVITY_MASK) 1698#define MAC_DMA_CFG_ADDRESS 0xb8100000 1699#define MAC_DMA_CFG_OFFSET 0x0014 1700 1701#define MAC_DMA_CFG_HALT_REQ_MSB 11 1702#define MAC_DMA_CFG_HALT_REQ_LSB 11 1703#define MAC_DMA_CFG_HALT_REQ_MASK 0x00000800 1704#define MAC_DMA_CFG_HALT_REQ_GET(x) (((x) & MAC_DMA_CFG_HALT_REQ_MASK) >> MAC_DMA_CFG_HALT_REQ_LSB) 1705#define MAC_DMA_CFG_HALT_REQ_SET(x) (((x) << MAC_DMA_CFG_HALT_REQ_LSB) & MAC_DMA_CFG_HALT_REQ_MASK) 1706#define MAC_DMA_CFG_HALT_ACK_MSB 12 1707#define MAC_DMA_CFG_HALT_ACK_LSB 12 1708#define MAC_DMA_CFG_HALT_ACK_MASK 0x00001000 1709#define MAC_DMA_CFG_HALT_ACK_GET(x) (((x) & MAC_DMA_CFG_HALT_ACK_MASK) >> MAC_DMA_CFG_HALT_ACK_LSB) 1710#define MAC_DMA_CFG_HALT_ACK_SET(x) (((x) << MAC_DMA_CFG_HALT_ACK_LSB) & MAC_DMA_CFG_HALT_ACK_MASK) 1711 1712#define RST_RESET 0xB806001c 1713#define RTC_RESET (1<<27) 1714 1715#define REG_READ(_reg) *((volatile u_int32_t *)(_reg)) 1716#define REG_WRITE(_reg, _val) *((volatile u_int32_t *)(_reg)) = (_val); 1717 1718#define DDR_REG_READ(_ah, _reg) \ 1719 *((volatile u_int32_t *)( DDR_CTL_CONFIG_ADDRESS + (_reg))) 1720#define DDR_REG_WRITE(_ah, _reg, _val) \ 1721 *((volatile u_int32_t *)(DDR_CTL_CONFIG_ADDRESS + (_reg))) = (_val) 1722 1723 OS_REG_WRITE(ah,MAC_DMA_CFG_OFFSET, (OS_REG_READ(ah,MAC_DMA_CFG_OFFSET) & ~MAC_DMA_CFG_HALT_REQ_MASK) | 1724 MAC_DMA_CFG_HALT_REQ_SET(1)); 1725 1726 { 1727 int count; 1728 u_int32_t data; 1729 1730 count = 0; 1731 while (!MAC_DMA_CFG_HALT_ACK_GET(OS_REG_READ(ah, MAC_DMA_CFG_OFFSET) )) 1732 { 1733 count++; 1734 if (count > 10) { 1735 ath_hal_printf(ah, "Halt ACK timeout\n"); 1736 break; 1737 } 1738 OS_DELAY(10); 1739 } 1740 1741 data = DDR_REG_READ(ah,DDR_CTL_CONFIG_OFFSET); 1742 ath_hal_printf(ah, "check DDR Activity - HIGH\n"); 1743 1744 count = 0; 1745 while (DDR_CTL_CONFIG_CLIENT_ACTIVITY_GET(data)) { 1746 // AVE_DEBUG(0,"DDR Activity - HIGH\n"); 1747 ath_hal_printf(ah, "DDR Activity - HIGH\n"); 1748 count++; 1749 OS_DELAY(10); 1750 data = DDR_REG_READ(ah,DDR_CTL_CONFIG_OFFSET); 1751 if (count > 10) { 1752 ath_hal_printf(ah, "DDR Activity timeout\n"); 1753 break; 1754 } 1755 } 1756 } 1757 1758 1759 { 1760 //Force RTC reset 1761 REG_WRITE(RST_RESET, (REG_READ(RST_RESET) | RTC_RESET)); 1762 OS_DELAY(10); 1763 REG_WRITE(RST_RESET, (REG_READ(RST_RESET) & ~RTC_RESET)); 1764 OS_DELAY(10); 1765 OS_REG_WRITE(ah, AR_RTC_RESET, 0); 1766 OS_DELAY(10); 1767 OS_REG_WRITE(ah, AR_RTC_RESET, 1); 1768 OS_DELAY(10); 1769 ath_hal_printf(ah,"%s: Scorpion SoC RTC reset done.\n", __func__); 1770 } 1771#undef REG_READ 1772#undef REG_WRITE 1773 } 1774#endif /* AH_SUPPORT_SCORPION */ 1775 1776 /* 1777 * Set Mac(BB,Phy) Warm Reset 1778 */ 1779 OS_REG_WRITE(ah, AR_RTC_RC, rst_flags); 1780 1781 OS_DELAY(50); /* XXX 50 usec */ 1782 1783 /* 1784 * Clear resets and force wakeup 1785 */ 1786 OS_REG_WRITE(ah, AR_RTC_RC, 0); 1787 if (!ath_hal_wait(ah, AR_RTC_RC, AR_RTC_RC_M, 0)) { 1788 HALDEBUG(ah, HAL_DEBUG_UNMASKABLE, 1789 "%s: RTC stuck in MAC reset\n", __FUNCTION__); 1790 HALDEBUG(ah, HAL_DEBUG_UNMASKABLE, 1791 "%s: AR_RTC_RC = 0x%x\n", __func__, OS_REG_READ(ah, AR_RTC_RC)); 1792 return AH_FALSE; 1793 } 1794 1795 /* Clear AHB reset */ 1796 OS_REG_WRITE(ah, AR_HOSTIF_REG(ah, AR_RC), 0); 1797 1798 ar9300_attach_hw_platform(ah); 1799 1800 return AH_TRUE; 1801} 1802 1803static inline HAL_BOOL 1804ar9300_set_reset_power_on(struct ath_hal *ah) 1805{ 1806 /* Force wake */ 1807 OS_REG_WRITE(ah, AR_HOSTIF_REG(ah, AR_WA), AH9300(ah)->ah_wa_reg_val); 1808 OS_DELAY(10); /* delay to allow AR_WA reg write to kick in */ 1809 OS_REG_WRITE(ah, AR_RTC_FORCE_WAKE, 1810 AR_RTC_FORCE_WAKE_EN | AR_RTC_FORCE_WAKE_ON_INT); 1811 /* 1812 * RTC reset and clear. Some delay in between is needed 1813 * to give the chip time to settle. 1814 */ 1815 OS_REG_WRITE(ah, AR_RTC_RESET, 0); 1816 OS_DELAY(2); 1817 OS_REG_WRITE(ah, AR_RTC_RESET, 1); 1818 1819 /* 1820 * Poll till RTC is ON 1821 */ 1822 if (!ath_hal_wait(ah, 1823 AR_RTC_STATUS, AR_RTC_STATUS_M, 1824 AR_RTC_STATUS_ON)) 1825 { 1826 HALDEBUG(ah, HAL_DEBUG_UNMASKABLE, 1827 "%s: RTC not waking up for %d\n", __FUNCTION__, 1000); 1828 return AH_FALSE; 1829 } 1830 1831 /* 1832 * Read Revisions from Chip right after RTC is on for the first time. 1833 * This helps us detect the chip type early and initialize it accordingly. 1834 */ 1835 ar9300_read_revisions(ah); 1836 1837 /* 1838 * Warm reset if we aren't really powering on, 1839 * just restarting the driver. 1840 */ 1841 return ar9300_set_reset(ah, HAL_RESET_WARM); 1842} 1843 1844/* 1845 * Write the given reset bit mask into the reset register 1846 */ 1847HAL_BOOL 1848ar9300_set_reset_reg(struct ath_hal *ah, u_int32_t type) 1849{ 1850 HAL_BOOL ret = AH_FALSE; 1851 1852 /* 1853 * Set force wake 1854 */ 1855 OS_REG_WRITE(ah, AR_HOSTIF_REG(ah, AR_WA), AH9300(ah)->ah_wa_reg_val); 1856 OS_DELAY(10); /* delay to allow AR_WA reg write to kick in */ 1857 OS_REG_WRITE(ah, AR_RTC_FORCE_WAKE, 1858 AR_RTC_FORCE_WAKE_EN | AR_RTC_FORCE_WAKE_ON_INT); 1859 1860 switch (type) { 1861 case HAL_RESET_POWER_ON: 1862 ret = ar9300_set_reset_power_on(ah); 1863 break; 1864 case HAL_RESET_WARM: 1865 case HAL_RESET_COLD: 1866 ret = ar9300_set_reset(ah, type); 1867 break; 1868 default: 1869 break; 1870 } 1871 1872#if ATH_SUPPORT_MCI 1873 if (AH_PRIVATE(ah)->ah_caps.halMciSupport) { 1874 OS_REG_WRITE(ah, AR_RTC_KEEP_AWAKE, 0x2); 1875 } 1876#endif 1877 1878 return ret; 1879} 1880 1881/* 1882 * Places the PHY and Radio chips into reset. A full reset 1883 * must be called to leave this state. The PCI/MAC/PCU are 1884 * not placed into reset as we must receive interrupt to 1885 * re-enable the hardware. 1886 */ 1887HAL_BOOL 1888ar9300_phy_disable(struct ath_hal *ah) 1889{ 1890 if (!ar9300_set_reset_reg(ah, HAL_RESET_WARM)) { 1891 return AH_FALSE; 1892 } 1893 1894#ifdef ATH_SUPPORT_LED 1895#define REG_READ(_reg) *((volatile u_int32_t *)(_reg)) 1896#define REG_WRITE(_reg, _val) *((volatile u_int32_t *)(_reg)) = (_val); 1897#define ATH_GPIO_OE 0xB8040000 1898#define ATH_GPIO_OUT 0xB8040008 /* GPIO Ouput Value reg.*/ 1899 if (AR_SREV_WASP(ah)) { 1900 if (IS_CHAN_2GHZ((AH_PRIVATE(ah)->ah_curchan))) { 1901 REG_WRITE(ATH_GPIO_OE, (REG_READ(ATH_GPIO_OE) | (0x1 << 13))); 1902 } 1903 else { 1904 REG_WRITE(ATH_GPIO_OE, (REG_READ(ATH_GPIO_OE) | (0x1 << 12))); 1905 } 1906 } 1907 else if (AR_SREV_SCORPION(ah)) { 1908 if (IS_CHAN_2GHZ((AH_PRIVATE(ah)->ah_curchan))) { 1909 REG_WRITE(ATH_GPIO_OE, (REG_READ(ATH_GPIO_OE) | (0x1 << 13))); 1910 } 1911 else { 1912 REG_WRITE(ATH_GPIO_OE, (REG_READ(ATH_GPIO_OE) | (0x1 << 12))); 1913 } 1914 /* Turn off JMPST led */ 1915 REG_WRITE(ATH_GPIO_OUT, (REG_READ(ATH_GPIO_OUT) | (0x1 << 15))); 1916 } 1917#undef REG_READ 1918#undef REG_WRITE 1919#endif 1920 1921 if ( AR_SREV_OSPREY(ah) ) { 1922 OS_REG_RMW(ah, AR_HOSTIF_REG(ah, AR_GPIO_OUTPUT_MUX1), 0x0, 0x1f); 1923 } 1924 1925 1926 ar9300_init_pll(ah, AH_NULL); 1927 1928 return AH_TRUE; 1929} 1930 1931/* 1932 * Places all of hardware into reset 1933 */ 1934HAL_BOOL 1935ar9300_disable(struct ath_hal *ah) 1936{ 1937 if (!ar9300_set_power_mode(ah, HAL_PM_AWAKE, AH_TRUE)) { 1938 return AH_FALSE; 1939 } 1940 if (!ar9300_set_reset_reg(ah, HAL_RESET_COLD)) { 1941 return AH_FALSE; 1942 } 1943 1944 ar9300_init_pll(ah, AH_NULL); 1945 1946 return AH_TRUE; 1947} 1948 1949/* 1950 * TODO: Only write the PLL if we're changing to or from CCK mode 1951 * 1952 * WARNING: The order of the PLL and mode registers must be correct. 1953 */ 1954static inline void 1955ar9300_set_rf_mode(struct ath_hal *ah, struct ieee80211_channel *chan) 1956{ 1957 u_int32_t rf_mode = 0; 1958 1959 if (chan == AH_NULL) { 1960 return; 1961 } 1962 switch (AH9300(ah)->ah_hwp) { 1963 case HAL_TRUE_CHIP: 1964 rf_mode |= (IEEE80211_IS_CHAN_B(chan) || IEEE80211_IS_CHAN_G(chan)) ? 1965 AR_PHY_MODE_DYNAMIC : AR_PHY_MODE_OFDM; 1966 break; 1967 default: 1968 HALASSERT(0); 1969 break; 1970 } 1971 /* Phy mode bits for 5GHz channels requiring Fast Clock */ 1972 if ( IS_5GHZ_FAST_CLOCK_EN(ah, chan)) { 1973 rf_mode |= (AR_PHY_MODE_DYNAMIC | AR_PHY_MODE_DYN_CCK_DISABLE); 1974 } 1975 OS_REG_WRITE(ah, AR_PHY_MODE, rf_mode); 1976} 1977 1978/* 1979 * Places the hardware into reset and then pulls it out of reset 1980 */ 1981HAL_BOOL 1982ar9300_chip_reset(struct ath_hal *ah, struct ieee80211_channel *chan) 1983{ 1984 struct ath_hal_9300 *ahp = AH9300(ah); 1985 1986 OS_MARK(ah, AH_MARK_CHIPRESET, chan ? chan->ic_freq : 0); 1987 1988 /* 1989 * Warm reset is optimistic. 1990 */ 1991 if (!ar9300_set_reset_reg(ah, HAL_RESET_WARM)) { 1992 return AH_FALSE; 1993 } 1994 1995 /* Bring out of sleep mode (AGAIN) */ 1996 if (!ar9300_set_power_mode(ah, HAL_PM_AWAKE, AH_TRUE)) { 1997 return AH_FALSE; 1998 } 1999 2000 ahp->ah_chip_full_sleep = AH_FALSE; 2001 2002 if (AR_SREV_HORNET(ah)) { 2003 ar9300_internal_regulator_apply(ah); 2004 } 2005 2006 ar9300_init_pll(ah, chan); 2007 2008 /* 2009 * Perform warm reset before the mode/PLL/turbo registers 2010 * are changed in order to deactivate the radio. Mode changes 2011 * with an active radio can result in corrupted shifts to the 2012 * radio device. 2013 */ 2014 ar9300_set_rf_mode(ah, chan); 2015 2016 return AH_TRUE; 2017} 2018 2019/* ar9300_setup_calibration 2020 * Setup HW to collect samples used for current cal 2021 */ 2022inline static void 2023ar9300_setup_calibration(struct ath_hal *ah, HAL_CAL_LIST *curr_cal) 2024{ 2025 /* Select calibration to run */ 2026 switch (curr_cal->cal_data->cal_type) { 2027 case IQ_MISMATCH_CAL: 2028 /* Start calibration w/ 2^(INIT_IQCAL_LOG_COUNT_MAX+1) samples */ 2029 OS_REG_RMW_FIELD(ah, AR_PHY_TIMING4, 2030 AR_PHY_TIMING4_IQCAL_LOG_COUNT_MAX, 2031 curr_cal->cal_data->cal_count_max); 2032 OS_REG_WRITE(ah, AR_PHY_CALMODE, AR_PHY_CALMODE_IQ); 2033 2034 HALDEBUG(ah, HAL_DEBUG_CALIBRATE, 2035 "%s: starting IQ Mismatch Calibration\n", __func__); 2036 2037 /* Kick-off cal */ 2038 OS_REG_SET_BIT(ah, AR_PHY_TIMING4, AR_PHY_TIMING4_DO_CAL); 2039 2040 break; 2041 case TEMP_COMP_CAL: 2042 if (AR_SREV_HORNET(ah) || AR_SREV_POSEIDON(ah) || 2043 AR_SREV_WASP(ah) || AR_SREV_SCORPION(ah)) { 2044 OS_REG_RMW_FIELD(ah, 2045 AR_HORNET_CH0_THERM, AR_PHY_65NM_CH0_THERM_LOCAL, 1); 2046 OS_REG_RMW_FIELD(ah, 2047 AR_HORNET_CH0_THERM, AR_PHY_65NM_CH0_THERM_START, 1); 2048 } else if (AR_SREV_JUPITER(ah) || AR_SREV_APHRODITE(ah)) { 2049 OS_REG_RMW_FIELD(ah, 2050 AR_PHY_65NM_CH0_THERM_JUPITER, AR_PHY_65NM_CH0_THERM_LOCAL, 1); 2051 OS_REG_RMW_FIELD(ah, 2052 AR_PHY_65NM_CH0_THERM_JUPITER, AR_PHY_65NM_CH0_THERM_START, 1); 2053 } else { 2054 OS_REG_RMW_FIELD(ah, 2055 AR_PHY_65NM_CH0_THERM, AR_PHY_65NM_CH0_THERM_LOCAL, 1); 2056 OS_REG_RMW_FIELD(ah, 2057 AR_PHY_65NM_CH0_THERM, AR_PHY_65NM_CH0_THERM_START, 1); 2058 } 2059 2060 HALDEBUG(ah, HAL_DEBUG_CALIBRATE, 2061 "%s: starting Temperature Compensation Calibration\n", __func__); 2062 break; 2063 default: 2064 HALDEBUG(ah, HAL_DEBUG_UNMASKABLE, 2065 "%s called with incorrect calibration type.\n", __func__); 2066 } 2067} 2068 2069/* ar9300_reset_calibration 2070 * Initialize shared data structures and prepare a cal to be run. 2071 */ 2072inline static void 2073ar9300_reset_calibration(struct ath_hal *ah, HAL_CAL_LIST *curr_cal) 2074{ 2075 struct ath_hal_9300 *ahp = AH9300(ah); 2076 int i; 2077 2078 /* Setup HW for new calibration */ 2079 ar9300_setup_calibration(ah, curr_cal); 2080 2081 /* Change SW state to RUNNING for this calibration */ 2082 curr_cal->cal_state = CAL_RUNNING; 2083 2084 /* Reset data structures shared between different calibrations */ 2085 for (i = 0; i < AR9300_MAX_CHAINS; i++) { 2086 ahp->ah_meas0.sign[i] = 0; 2087 ahp->ah_meas1.sign[i] = 0; 2088 ahp->ah_meas2.sign[i] = 0; 2089 ahp->ah_meas3.sign[i] = 0; 2090 } 2091 2092 ahp->ah_cal_samples = 0; 2093} 2094 2095#ifdef XXX_UNUSED_FUNCTION 2096/* 2097 * Find out which of the RX chains are enabled 2098 */ 2099static u_int32_t 2100ar9300_get_rx_chain_mask(struct ath_hal *ah) 2101{ 2102 u_int32_t ret_val = OS_REG_READ(ah, AR_PHY_RX_CHAINMASK); 2103 /* The bits [2:0] indicate the rx chain mask and are to be 2104 * interpreted as follows: 2105 * 00x => Only chain 0 is enabled 2106 * 01x => Chain 1 and 0 enabled 2107 * 1xx => Chain 2,1 and 0 enabled 2108 */ 2109 return (ret_val & 0x7); 2110} 2111#endif 2112 2113static void 2114ar9300_get_nf_hist_base(struct ath_hal *ah, HAL_CHANNEL_INTERNAL *chan, 2115 int is_scan, int16_t nf[]) 2116{ 2117 HAL_NFCAL_BASE *h_base; 2118 2119#ifdef ATH_NF_PER_CHAN 2120 h_base = &chan->nf_cal_hist.base; 2121#else 2122 if (is_scan) { 2123 /* 2124 * The channel we are currently on is not the home channel, 2125 * so we shouldn't use the home channel NF buffer's values on 2126 * this channel. Instead, use the NF single value already 2127 * read for this channel. (Or, if we haven't read the NF for 2128 * this channel yet, the SW default for this chip/band will 2129 * be used.) 2130 */ 2131 h_base = &chan->nf_cal_hist.base; 2132 } else { 2133 /* use the home channel NF info */ 2134 h_base = &AH_PRIVATE(ah)->nf_cal_hist.base; 2135 } 2136#endif 2137 OS_MEMCPY(nf, h_base->priv_nf, sizeof(h_base->priv_nf)); 2138} 2139 2140HAL_BOOL 2141ar9300_load_nf(struct ath_hal *ah, int16_t nf[]) 2142{ 2143 int i, j; 2144 int32_t val; 2145 /* XXX where are EXT regs defined */ 2146 const u_int32_t ar9300_cca_regs[] = { 2147 AR_PHY_CCA_0, 2148 AR_PHY_CCA_1, 2149 AR_PHY_CCA_2, 2150 AR_PHY_EXT_CCA, 2151 AR_PHY_EXT_CCA_1, 2152 AR_PHY_EXT_CCA_2, 2153 }; 2154 u_int8_t chainmask; 2155 2156 /* 2157 * Force NF calibration for all chains, otherwise Vista station 2158 * would conduct a bad performance 2159 */ 2160 if (AR_SREV_HORNET(ah) || AR_SREV_POSEIDON(ah) || AR_SREV_APHRODITE(ah)) { 2161 chainmask = 0x9; 2162 } else if (AR_SREV_WASP(ah) || AR_SREV_JUPITER(ah)) { 2163 chainmask = 0x1b; 2164 } else { 2165 chainmask = 0x3F; 2166 } 2167 2168 /* 2169 * Write filtered NF values into max_cca_pwr register parameter 2170 * so we can load below. 2171 */ 2172 for (i = 0; i < HAL_NUM_NF_READINGS; i++) { 2173 if (chainmask & (1 << i)) { 2174 val = OS_REG_READ(ah, ar9300_cca_regs[i]); 2175 val &= 0xFFFFFE00; 2176 val |= (((u_int32_t)(nf[i]) << 1) & 0x1ff); 2177 OS_REG_WRITE(ah, ar9300_cca_regs[i], val); 2178 } 2179 } 2180 2181 HALDEBUG(ah, HAL_DEBUG_NFCAL, "%s: load %d %d %d %d %d %d\n", 2182 __func__, 2183 nf[0], nf[1], nf[2], 2184 nf[3], nf[4], nf[5]); 2185 2186 /* 2187 * Load software filtered NF value into baseband internal min_cca_pwr 2188 * variable. 2189 */ 2190 OS_REG_CLR_BIT(ah, AR_PHY_AGC_CONTROL, AR_PHY_AGC_CONTROL_ENABLE_NF); 2191 OS_REG_CLR_BIT(ah, AR_PHY_AGC_CONTROL, AR_PHY_AGC_CONTROL_NO_UPDATE_NF); 2192 OS_REG_SET_BIT(ah, AR_PHY_AGC_CONTROL, AR_PHY_AGC_CONTROL_NF); 2193 2194 /* Wait for load to complete, should be fast, a few 10s of us. */ 2195 /* Changed the max delay 250us back to 10000us, since 250us often 2196 * results in NF load timeout and causes deaf condition 2197 * during stress testing 12/12/2009 2198 */ 2199 for (j = 0; j < 10000; j++) { 2200 if ((OS_REG_READ(ah, AR_PHY_AGC_CONTROL) & AR_PHY_AGC_CONTROL_NF) == 0){ 2201 break; 2202 } 2203 OS_DELAY(10); 2204 } 2205 if (j == 10000) { 2206 /* 2207 * We timed out waiting for the noisefloor to load, probably 2208 * due to an in-progress rx. Simply return here and allow 2209 * the load plenty of time to complete before the next 2210 * calibration interval. We need to avoid trying to load -50 2211 * (which happens below) while the previous load is still in 2212 * progress as this can cause rx deafness (see EV 66368,62830). 2213 * Instead by returning here, the baseband nf cal will 2214 * just be capped by our present noisefloor until the next 2215 * calibration timer. 2216 */ 2217 HALDEBUG(AH_NULL, HAL_DEBUG_UNMASKABLE, 2218 "%s: *** TIMEOUT while waiting for nf to load: " 2219 "AR_PHY_AGC_CONTROL=0x%x ***\n", 2220 __func__, OS_REG_READ(ah, AR_PHY_AGC_CONTROL)); 2221 return AH_FALSE; 2222 } 2223 2224 /* 2225 * Restore max_cca_power register parameter again so that we're not capped 2226 * by the median we just loaded. This will be initial (and max) value 2227 * of next noise floor calibration the baseband does. 2228 */ 2229 for (i = 0; i < HAL_NUM_NF_READINGS; i++) { 2230 if (chainmask & (1 << i)) { 2231 val = OS_REG_READ(ah, ar9300_cca_regs[i]); 2232 val &= 0xFFFFFE00; 2233 val |= (((u_int32_t)(-50) << 1) & 0x1ff); 2234 OS_REG_WRITE(ah, ar9300_cca_regs[i], val); 2235 } 2236 } 2237 return AH_TRUE; 2238} 2239 2240/* ar9300_per_calibration 2241 * Generic calibration routine. 2242 * Recalibrate the lower PHY chips to account for temperature/environment 2243 * changes. 2244 */ 2245inline static void 2246ar9300_per_calibration(struct ath_hal *ah, HAL_CHANNEL_INTERNAL *ichan, 2247 u_int8_t rxchainmask, HAL_CAL_LIST *curr_cal, HAL_BOOL *is_cal_done) 2248{ 2249 struct ath_hal_9300 *ahp = AH9300(ah); 2250 2251 /* Cal is assumed not done until explicitly set below */ 2252 *is_cal_done = AH_FALSE; 2253 2254 /* Calibration in progress. */ 2255 if (curr_cal->cal_state == CAL_RUNNING) { 2256 /* Check to see if it has finished. */ 2257 if (!(OS_REG_READ(ah, AR_PHY_TIMING4) & AR_PHY_TIMING4_DO_CAL)) { 2258 int i, num_chains = 0; 2259 for (i = 0; i < AR9300_MAX_CHAINS; i++) { 2260 if (rxchainmask & (1 << i)) { 2261 num_chains++; 2262 } 2263 } 2264 2265 /* 2266 * Accumulate cal measures for active chains 2267 */ 2268 curr_cal->cal_data->cal_collect(ah, num_chains); 2269 2270 ahp->ah_cal_samples++; 2271 2272 if (ahp->ah_cal_samples >= curr_cal->cal_data->cal_num_samples) { 2273 /* 2274 * Process accumulated data 2275 */ 2276 curr_cal->cal_data->cal_post_proc(ah, num_chains); 2277 2278 /* Calibration has finished. */ 2279 ichan->calValid |= curr_cal->cal_data->cal_type; 2280 curr_cal->cal_state = CAL_DONE; 2281 *is_cal_done = AH_TRUE; 2282 } else { 2283 /* Set-up collection of another sub-sample until we 2284 * get desired number 2285 */ 2286 ar9300_setup_calibration(ah, curr_cal); 2287 } 2288 } 2289 } else if (!(ichan->calValid & curr_cal->cal_data->cal_type)) { 2290 /* If current cal is marked invalid in channel, kick it off */ 2291 ar9300_reset_calibration(ah, curr_cal); 2292 } 2293} 2294 2295static void 2296ar9300_start_nf_cal(struct ath_hal *ah) 2297{ 2298 OS_REG_SET_BIT(ah, AR_PHY_AGC_CONTROL, AR_PHY_AGC_CONTROL_ENABLE_NF); 2299 OS_REG_SET_BIT(ah, AR_PHY_AGC_CONTROL, AR_PHY_AGC_CONTROL_NO_UPDATE_NF); 2300 OS_REG_SET_BIT(ah, AR_PHY_AGC_CONTROL, AR_PHY_AGC_CONTROL_NF); 2301 AH9300(ah)->nf_tsf32 = ar9300_get_tsf32(ah); 2302} 2303 2304/* ar9300_calibration 2305 * Wrapper for a more generic Calibration routine. Primarily to abstract to 2306 * upper layers whether there is 1 or more calibrations to be run. 2307 */ 2308HAL_BOOL 2309ar9300_calibration(struct ath_hal *ah, struct ieee80211_channel *chan, u_int8_t rxchainmask, 2310 HAL_BOOL do_nf_cal, HAL_BOOL *is_cal_done, int is_scan, 2311 u_int32_t *sched_cals) 2312{ 2313 struct ath_hal_9300 *ahp = AH9300(ah); 2314 HAL_CAL_LIST *curr_cal = ahp->ah_cal_list_curr; 2315 HAL_CHANNEL_INTERNAL *ichan = ath_hal_checkchannel(ah, chan); 2316 int16_t nf_buf[HAL_NUM_NF_READINGS]; 2317 2318 *is_cal_done = AH_TRUE; 2319 2320 2321 /* XXX: For initial wasp bringup - disable periodic calibration */ 2322 /* Invalid channel check */ 2323 if (ichan == AH_NULL) { 2324 HALDEBUG(ah, HAL_DEBUG_CHANNEL, 2325 "%s: invalid channel %u/0x%x; no mapping\n", 2326 __func__, chan->ic_freq, chan->ic_flags); 2327 return AH_FALSE; 2328 } 2329 2330 HALDEBUG(ah, HAL_DEBUG_CALIBRATE, 2331 "%s: Entering, Doing NF Cal = %d\n", __func__, do_nf_cal); 2332 HALDEBUG(ah, HAL_DEBUG_CALIBRATE, "%s: Chain 0 Rx IQ Cal Correction 0x%08x\n", 2333 __func__, OS_REG_READ(ah, AR_PHY_RX_IQCAL_CORR_B0)); 2334 if (!AR_SREV_HORNET(ah) && !AR_SREV_POSEIDON(ah) && !AR_SREV_APHRODITE(ah)) { 2335 HALDEBUG(ah, HAL_DEBUG_CALIBRATE, 2336 "%s: Chain 1 Rx IQ Cal Correction 0x%08x\n", 2337 __func__, OS_REG_READ(ah, AR_PHY_RX_IQCAL_CORR_B1)); 2338 if (!AR_SREV_WASP(ah) && !AR_SREV_JUPITER(ah)) { 2339 HALDEBUG(ah, HAL_DEBUG_CALIBRATE, 2340 "%s: Chain 2 Rx IQ Cal Correction 0x%08x\n", 2341 __func__, OS_REG_READ(ah, AR_PHY_RX_IQCAL_CORR_B2)); 2342 } 2343 } 2344 2345 OS_MARK(ah, AH_MARK_PERCAL, chan->ic_freq); 2346 2347 /* For given calibration: 2348 * 1. Call generic cal routine 2349 * 2. When this cal is done (is_cal_done) if we have more cals waiting 2350 * (eg after reset), mask this to upper layers by not propagating 2351 * is_cal_done if it is set to TRUE. 2352 * Instead, change is_cal_done to FALSE and setup the waiting cal(s) 2353 * to be run. 2354 */ 2355 if (curr_cal && (curr_cal->cal_data->cal_type & *sched_cals) && 2356 (curr_cal->cal_state == CAL_RUNNING || 2357 curr_cal->cal_state == CAL_WAITING)) 2358 { 2359 ar9300_per_calibration(ah, ichan, rxchainmask, curr_cal, is_cal_done); 2360 2361 if (*is_cal_done == AH_TRUE) { 2362 ahp->ah_cal_list_curr = curr_cal = curr_cal->cal_next; 2363 2364 if (curr_cal && curr_cal->cal_state == CAL_WAITING) { 2365 *is_cal_done = AH_FALSE; 2366 ar9300_reset_calibration(ah, curr_cal); 2367 } else { 2368 *sched_cals &= ~IQ_MISMATCH_CAL; 2369 } 2370 } 2371 } 2372 2373 /* Do NF cal only at longer intervals */ 2374 if (do_nf_cal) { 2375 int nf_done; 2376 2377 /* Get the value from the previous NF cal and update history buffer */ 2378 nf_done = ar9300_store_new_nf(ah, chan, is_scan); 2379#if 0 2380 if (ichan->channel_flags & CHANNEL_CW_INT) { 2381 chan->channel_flags |= CHANNEL_CW_INT; 2382 } 2383#endif 2384 chan->ic_state &= ~IEEE80211_CHANSTATE_CWINT; 2385 2386 if (nf_done) { 2387 /* 2388 * Load the NF from history buffer of the current channel. 2389 * NF is slow time-variant, so it is OK to use a historical value. 2390 */ 2391 ar9300_get_nf_hist_base(ah, ichan, is_scan, nf_buf); 2392 ar9300_load_nf(ah, nf_buf); 2393 2394 /* start NF calibration, without updating BB NF register*/ 2395 ar9300_start_nf_cal(ah); 2396 } 2397 } 2398 return AH_TRUE; 2399} 2400 2401/* ar9300_iq_cal_collect 2402 * Collect data from HW to later perform IQ Mismatch Calibration 2403 */ 2404void 2405ar9300_iq_cal_collect(struct ath_hal *ah, u_int8_t num_chains) 2406{ 2407 struct ath_hal_9300 *ahp = AH9300(ah); 2408 int i; 2409 2410 /* 2411 * Accumulate IQ cal measures for active chains 2412 */ 2413 for (i = 0; i < num_chains; i++) { 2414 ahp->ah_total_power_meas_i[i] = OS_REG_READ(ah, AR_PHY_CAL_MEAS_0(i)); 2415 ahp->ah_total_power_meas_q[i] = OS_REG_READ(ah, AR_PHY_CAL_MEAS_1(i)); 2416 ahp->ah_total_iq_corr_meas[i] = 2417 (int32_t) OS_REG_READ(ah, AR_PHY_CAL_MEAS_2(i)); 2418 HALDEBUG(ah, HAL_DEBUG_CALIBRATE, 2419 "%d: Chn %d " 2420 "Reg Offset(0x%04x)pmi=0x%08x; " 2421 "Reg Offset(0x%04x)pmq=0x%08x; " 2422 "Reg Offset (0x%04x)iqcm=0x%08x;\n", 2423 ahp->ah_cal_samples, 2424 i, 2425 (unsigned) AR_PHY_CAL_MEAS_0(i), 2426 ahp->ah_total_power_meas_i[i], 2427 (unsigned) AR_PHY_CAL_MEAS_1(i), 2428 ahp->ah_total_power_meas_q[i], 2429 (unsigned) AR_PHY_CAL_MEAS_2(i), 2430 ahp->ah_total_iq_corr_meas[i]); 2431 } 2432} 2433 2434/* ar9300_iq_calibration 2435 * Use HW data to perform IQ Mismatch Calibration 2436 */ 2437void 2438ar9300_iq_calibration(struct ath_hal *ah, u_int8_t num_chains) 2439{ 2440 struct ath_hal_9300 *ahp = AH9300(ah); 2441 u_int32_t power_meas_q, power_meas_i, iq_corr_meas; 2442 u_int32_t q_coff_denom, i_coff_denom; 2443 int32_t q_coff, i_coff; 2444 int iq_corr_neg, i; 2445 static const u_int32_t offset_array[3] = { 2446 AR_PHY_RX_IQCAL_CORR_B0, 2447 AR_PHY_RX_IQCAL_CORR_B1, 2448 AR_PHY_RX_IQCAL_CORR_B2, 2449 }; 2450 2451 for (i = 0; i < num_chains; i++) { 2452 power_meas_i = ahp->ah_total_power_meas_i[i]; 2453 power_meas_q = ahp->ah_total_power_meas_q[i]; 2454 iq_corr_meas = ahp->ah_total_iq_corr_meas[i]; 2455 2456 HALDEBUG(ah, HAL_DEBUG_CALIBRATE, 2457 "Starting IQ Cal and Correction for Chain %d\n", i); 2458 HALDEBUG(ah, HAL_DEBUG_CALIBRATE, 2459 "Orignal: Chn %diq_corr_meas = 0x%08x\n", 2460 i, ahp->ah_total_iq_corr_meas[i]); 2461 2462 iq_corr_neg = 0; 2463 2464 /* iq_corr_meas is always negative. */ 2465 if (iq_corr_meas > 0x80000000) { 2466 iq_corr_meas = (0xffffffff - iq_corr_meas) + 1; 2467 iq_corr_neg = 1; 2468 } 2469 2470 HALDEBUG(ah, HAL_DEBUG_CALIBRATE, 2471 "Chn %d pwr_meas_i = 0x%08x\n", i, power_meas_i); 2472 HALDEBUG(ah, HAL_DEBUG_CALIBRATE, 2473 "Chn %d pwr_meas_q = 0x%08x\n", i, power_meas_q); 2474 HALDEBUG(ah, HAL_DEBUG_CALIBRATE, 2475 "iq_corr_neg is 0x%08x\n", iq_corr_neg); 2476 2477 i_coff_denom = (power_meas_i / 2 + power_meas_q / 2) / 256; 2478 q_coff_denom = power_meas_q / 64; 2479 2480 /* Protect against divide-by-0 */ 2481 if ((i_coff_denom != 0) && (q_coff_denom != 0)) { 2482 /* IQ corr_meas is already negated if iqcorr_neg == 1 */ 2483 i_coff = iq_corr_meas / i_coff_denom; 2484 q_coff = power_meas_i / q_coff_denom - 64; 2485 HALDEBUG(ah, HAL_DEBUG_CALIBRATE, 2486 "Chn %d i_coff = 0x%08x\n", i, i_coff); 2487 HALDEBUG(ah, HAL_DEBUG_CALIBRATE, 2488 "Chn %d q_coff = 0x%08x\n", i, q_coff); 2489 2490 /* Force bounds on i_coff */ 2491 if (i_coff >= 63) { 2492 i_coff = 63; 2493 } else if (i_coff <= -63) { 2494 i_coff = -63; 2495 } 2496 2497 /* Negate i_coff if iq_corr_neg == 0 */ 2498 if (iq_corr_neg == 0x0) { 2499 i_coff = -i_coff; 2500 } 2501 2502 /* Force bounds on q_coff */ 2503 if (q_coff >= 63) { 2504 q_coff = 63; 2505 } else if (q_coff <= -63) { 2506 q_coff = -63; 2507 } 2508 2509 i_coff = i_coff & 0x7f; 2510 q_coff = q_coff & 0x7f; 2511 2512 HALDEBUG(ah, HAL_DEBUG_CALIBRATE, 2513 "Chn %d : i_coff = 0x%x q_coff = 0x%x\n", i, i_coff, q_coff); 2514 HALDEBUG(ah, HAL_DEBUG_CALIBRATE, 2515 "Register offset (0x%04x) before update = 0x%x\n", 2516 offset_array[i], OS_REG_READ(ah, offset_array[i])); 2517 2518 OS_REG_RMW_FIELD(ah, offset_array[i], 2519 AR_PHY_RX_IQCAL_CORR_IQCORR_Q_I_COFF, i_coff); 2520 OS_REG_RMW_FIELD(ah, offset_array[i], 2521 AR_PHY_RX_IQCAL_CORR_IQCORR_Q_Q_COFF, q_coff); 2522 2523 HALDEBUG(ah, HAL_DEBUG_CALIBRATE, 2524 "Register offset (0x%04x) QI COFF (bitfields 0x%08x) " 2525 "after update = 0x%x\n", 2526 offset_array[i], AR_PHY_RX_IQCAL_CORR_IQCORR_Q_I_COFF, 2527 OS_REG_READ(ah, offset_array[i])); 2528 HALDEBUG(ah, HAL_DEBUG_CALIBRATE, 2529 "Register offset (0x%04x) QQ COFF (bitfields 0x%08x) " 2530 "after update = 0x%x\n", 2531 offset_array[i], AR_PHY_RX_IQCAL_CORR_IQCORR_Q_Q_COFF, 2532 OS_REG_READ(ah, offset_array[i])); 2533 HALDEBUG(ah, HAL_DEBUG_CALIBRATE, 2534 "IQ Cal and Correction done for Chain %d\n", i); 2535 } 2536 } 2537 2538 OS_REG_SET_BIT(ah, 2539 AR_PHY_RX_IQCAL_CORR_B0, AR_PHY_RX_IQCAL_CORR_IQCORR_ENABLE); 2540 HALDEBUG(ah, HAL_DEBUG_CALIBRATE, 2541 "IQ Cal and Correction (offset 0x%04x) enabled " 2542 "(bit position 0x%08x). New Value 0x%08x\n", 2543 (unsigned) (AR_PHY_RX_IQCAL_CORR_B0), 2544 AR_PHY_RX_IQCAL_CORR_IQCORR_ENABLE, 2545 OS_REG_READ(ah, AR_PHY_RX_IQCAL_CORR_B0)); 2546} 2547 2548/* 2549 * Set a limit on the overall output power. Used for dynamic 2550 * transmit power control and the like. 2551 * 2552 * NB: limit is in units of 0.5 dbM. 2553 */ 2554HAL_BOOL 2555ar9300_set_tx_power_limit(struct ath_hal *ah, u_int32_t limit, 2556 u_int16_t extra_txpow, u_int16_t tpc_in_db) 2557{ 2558 struct ath_hal_9300 *ahp = AH9300(ah); 2559 struct ath_hal_private *ahpriv = AH_PRIVATE(ah); 2560 const struct ieee80211_channel *chan = ahpriv->ah_curchan; 2561 HAL_CHANNEL_INTERNAL *ichan = ath_hal_checkchannel(ah, chan); 2562 2563 if (NULL == chan) { 2564 return AH_FALSE; 2565 } 2566 2567 ahpriv->ah_powerLimit = AH_MIN(limit, MAX_RATE_POWER); 2568 ahpriv->ah_extraTxPow = extra_txpow; 2569 2570 if(chan == NULL) { 2571 return AH_FALSE; 2572 } 2573 if (ar9300_eeprom_set_transmit_power(ah, &ahp->ah_eeprom, chan, 2574 ath_hal_getctl(ah, chan), ath_hal_getantennaallowed(ah, chan), 2575 ath_hal_get_twice_max_regpower(ahpriv, ichan, chan), 2576 AH_MIN(MAX_RATE_POWER, ahpriv->ah_powerLimit)) != HAL_OK) 2577 { 2578 return AH_FALSE; 2579 } 2580 return AH_TRUE; 2581} 2582 2583/* 2584 * Exported call to check for a recent gain reading and return 2585 * the current state of the thermal calibration gain engine. 2586 */ 2587HAL_RFGAIN 2588ar9300_get_rfgain(struct ath_hal *ah) 2589{ 2590 return HAL_RFGAIN_INACTIVE; 2591} 2592 2593#define HAL_GREEN_AP_RX_MASK 0x1 2594 2595static inline void 2596ar9300_init_chain_masks(struct ath_hal *ah, int rx_chainmask, int tx_chainmask) 2597{ 2598 if (AH9300(ah)->green_ap_ps_on) { 2599 rx_chainmask = HAL_GREEN_AP_RX_MASK; 2600 } 2601 if (rx_chainmask == 0x5) { 2602 OS_REG_SET_BIT(ah, AR_PHY_ANALOG_SWAP, AR_PHY_SWAP_ALT_CHAIN); 2603 } 2604 OS_REG_WRITE(ah, AR_PHY_RX_CHAINMASK, rx_chainmask); 2605 OS_REG_WRITE(ah, AR_PHY_CAL_CHAINMASK, rx_chainmask); 2606 2607 /* 2608 * Adaptive Power Management: 2609 * Some 3 stream chips exceed the PCIe power requirements. 2610 * This workaround will reduce power consumption by using 2 tx chains 2611 * for 1 and 2 stream rates (5 GHz only). 2612 * 2613 * Set the self gen mask to 2 tx chains when APM is enabled. 2614 * 2615 */ 2616 if (AH_PRIVATE(ah)->ah_caps.halApmEnable && (tx_chainmask == 0x7)) { 2617 OS_REG_WRITE(ah, AR_SELFGEN_MASK, 0x3); 2618 } 2619 else { 2620 OS_REG_WRITE(ah, AR_SELFGEN_MASK, tx_chainmask); 2621 } 2622 2623 if (tx_chainmask == 0x5) { 2624 OS_REG_SET_BIT(ah, AR_PHY_ANALOG_SWAP, AR_PHY_SWAP_ALT_CHAIN); 2625 } 2626} 2627 2628/* 2629 * Override INI values with chip specific configuration. 2630 */ 2631static inline void 2632ar9300_override_ini(struct ath_hal *ah, struct ieee80211_channel *chan) 2633{ 2634 u_int32_t val; 2635 HAL_CAPABILITIES *p_cap = &AH_PRIVATE(ah)->ah_caps; 2636 2637 /* 2638 * Set the RX_ABORT and RX_DIS and clear it only after 2639 * RXE is set for MAC. This prevents frames with 2640 * corrupted descriptor status. 2641 */ 2642 OS_REG_SET_BIT(ah, AR_DIAG_SW, (AR_DIAG_RX_DIS | AR_DIAG_RX_ABORT)); 2643 /* 2644 * For Merlin and above, there is a new feature that allows Multicast 2645 * search based on both MAC Address and Key ID. 2646 * By default, this feature is enabled. 2647 * But since the driver is not using this feature, we switch it off; 2648 * otherwise multicast search based on MAC addr only will fail. 2649 */ 2650 val = OS_REG_READ(ah, AR_PCU_MISC_MODE2) & (~AR_ADHOC_MCAST_KEYID_ENABLE); 2651 OS_REG_WRITE(ah, AR_PCU_MISC_MODE2, 2652 val | AR_BUG_58603_FIX_ENABLE | AR_AGG_WEP_ENABLE); 2653 2654 2655 /* Osprey revision specific configuration */ 2656 2657 /* Osprey 2.0+ - if SW RAC support is disabled, must also disable 2658 * the Osprey 2.0 hardware RAC fix. 2659 */ 2660 if (p_cap->halIsrRacSupport == AH_FALSE) { 2661 OS_REG_CLR_BIT(ah, AR_CFG, AR_CFG_MISSING_TX_INTR_FIX_ENABLE); 2662 } 2663 2664 /* try to enable old pal if it is needed for h/w green tx */ 2665 ar9300_hwgreentx_set_pal_spare(ah, 1); 2666} 2667 2668static inline void 2669ar9300_prog_ini(struct ath_hal *ah, struct ar9300_ini_array *ini_arr, 2670 int column) 2671{ 2672 int i, reg_writes = 0; 2673 2674 /* New INI format: Array may be undefined (pre, core, post arrays) */ 2675 if (ini_arr->ia_array == NULL) { 2676 return; 2677 } 2678 2679 /* 2680 * New INI format: Pre, core, and post arrays for a given subsystem may be 2681 * modal (> 2 columns) or non-modal (2 columns). 2682 * Determine if the array is non-modal and force the column to 1. 2683 */ 2684 if (column >= ini_arr->ia_columns) { 2685 column = 1; 2686 } 2687 2688 for (i = 0; i < ini_arr->ia_rows; i++) { 2689 u_int32_t reg = INI_RA(ini_arr, i, 0); 2690 u_int32_t val = INI_RA(ini_arr, i, column); 2691 2692 /* 2693 ** Determine if this is a shift register value 2694 ** (reg >= 0x16000 && reg < 0x17000 for Osprey) , 2695 ** and insert the configured delay if so. 2696 ** -this delay is not required for Osprey (EV#71410) 2697 */ 2698 OS_REG_WRITE(ah, reg, val); 2699 WAR_6773(reg_writes); 2700 2701 } 2702} 2703 2704static inline HAL_STATUS 2705ar9300_process_ini(struct ath_hal *ah, struct ieee80211_channel *chan, 2706 HAL_CHANNEL_INTERNAL *ichan, HAL_HT_MACMODE macmode) 2707{ 2708 int reg_writes = 0; 2709 struct ath_hal_9300 *ahp = AH9300(ah); 2710 u_int modes_index, modes_txgaintable_index = 0; 2711 int i; 2712 HAL_STATUS status; 2713 struct ath_hal_private *ahpriv = AH_PRIVATE(ah); 2714 /* Setup the indices for the next set of register array writes */ 2715 /* TODO: 2716 * If the channel marker is indicative of the current mode rather 2717 * than capability, we do not need to check the phy mode below. 2718 */ 2719#if 0 2720 switch (chan->channel_flags & CHANNEL_ALL) { 2721 case CHANNEL_A: 2722 case CHANNEL_A_HT20: 2723 if (AR_SREV_SCORPION(ah)){ 2724 if (chan->channel <= 5350){ 2725 modes_txgaintable_index = 1; 2726 }else if ((chan->channel > 5350) && (chan->channel <= 5600)){ 2727 modes_txgaintable_index = 3; 2728 }else if (chan->channel > 5600){ 2729 modes_txgaintable_index = 5; 2730 } 2731 } 2732 modes_index = 1; 2733 break; 2734 2735 case CHANNEL_A_HT40PLUS: 2736 case CHANNEL_A_HT40MINUS: 2737 if (AR_SREV_SCORPION(ah)){ 2738 if (chan->channel <= 5350){ 2739 modes_txgaintable_index = 2; 2740 }else if ((chan->channel > 5350) && (chan->channel <= 5600)){ 2741 modes_txgaintable_index = 4; 2742 }else if (chan->channel > 5600){ 2743 modes_txgaintable_index = 6; 2744 } 2745 } 2746 modes_index = 2; 2747 break; 2748 2749 case CHANNEL_PUREG: 2750 case CHANNEL_G_HT20: 2751 case CHANNEL_B: 2752 if (AR_SREV_SCORPION(ah)){ 2753 modes_txgaintable_index = 8; 2754 } 2755 modes_index = 4; 2756 break; 2757 2758 case CHANNEL_G_HT40PLUS: 2759 case CHANNEL_G_HT40MINUS: 2760 if (AR_SREV_SCORPION(ah)){ 2761 modes_txgaintable_index = 7; 2762 } 2763 modes_index = 3; 2764 break; 2765 2766 case CHANNEL_108G: 2767 modes_index = 5; 2768 break; 2769 2770 default: 2771 HALASSERT(0); 2772 return HAL_EINVAL; 2773 } 2774#endif 2775 2776 /* FreeBSD */ 2777 if (IS_CHAN_5GHZ(ichan)) { 2778 if (IEEE80211_IS_CHAN_HT40U(chan) || IEEE80211_IS_CHAN_HT40D(chan)) { 2779 if (AR_SREV_SCORPION(ah)){ 2780 if (ichan->channel <= 5350){ 2781 modes_txgaintable_index = 2; 2782 }else if ((ichan->channel > 5350) && (ichan->channel <= 5600)){ 2783 modes_txgaintable_index = 4; 2784 }else if (ichan->channel > 5600){ 2785 modes_txgaintable_index = 6; 2786 } 2787 } 2788 modes_index = 2; 2789 } else if (IEEE80211_IS_CHAN_A(chan) || IEEE80211_IS_CHAN_HT20(chan)) { 2790 if (AR_SREV_SCORPION(ah)){ 2791 if (ichan->channel <= 5350){ 2792 modes_txgaintable_index = 1; 2793 }else if ((ichan->channel > 5350) && (ichan->channel <= 5600)){ 2794 modes_txgaintable_index = 3; 2795 }else if (ichan->channel > 5600){ 2796 modes_txgaintable_index = 5; 2797 } 2798 } 2799 modes_index = 1; 2800 } else 2801 return HAL_EINVAL; 2802 } else if (IS_CHAN_2GHZ(ichan)) { 2803 if (IEEE80211_IS_CHAN_108G(chan)) { 2804 modes_index = 5; 2805 } else if (IEEE80211_IS_CHAN_HT40U(chan) || IEEE80211_IS_CHAN_HT40D(chan)) { 2806 if (AR_SREV_SCORPION(ah)){ 2807 modes_txgaintable_index = 7; 2808 } 2809 modes_index = 3; 2810 } else if (IEEE80211_IS_CHAN_HT20(chan) || IEEE80211_IS_CHAN_G(chan) || IEEE80211_IS_CHAN_B(chan) || IEEE80211_IS_CHAN_PUREG(chan)) { 2811 if (AR_SREV_SCORPION(ah)){ 2812 modes_txgaintable_index = 8; 2813 } 2814 modes_index = 4; 2815 } else 2816 return HAL_EINVAL; 2817 } else 2818 return HAL_EINVAL; 2819 2820#if 0 2821 /* Set correct Baseband to analog shift setting to access analog chips. */ 2822 OS_REG_WRITE(ah, AR_PHY(0), 0x00000007); 2823#endif 2824 2825 HALDEBUG(ah, HAL_DEBUG_RESET, 2826 "ar9300_process_ini: " 2827 "Skipping OS-REG-WRITE(ah, AR-PHY(0), 0x00000007)\n"); 2828 HALDEBUG(ah, HAL_DEBUG_RESET, 2829 "ar9300_process_ini: no ADDac programming\n"); 2830 2831 2832 /* 2833 * Osprey 2.0+ - new INI format. 2834 * Each subsystem has a pre, core, and post array. 2835 */ 2836 for (i = 0; i < ATH_INI_NUM_SPLIT; i++) { 2837 ar9300_prog_ini(ah, &ahp->ah_ini_soc[i], modes_index); 2838 ar9300_prog_ini(ah, &ahp->ah_ini_mac[i], modes_index); 2839 ar9300_prog_ini(ah, &ahp->ah_ini_bb[i], modes_index); 2840 ar9300_prog_ini(ah, &ahp->ah_ini_radio[i], modes_index); 2841 if ((i == ATH_INI_POST) && (AR_SREV_JUPITER_20(ah) || AR_SREV_APHRODITE(ah))) { 2842 ar9300_prog_ini(ah, &ahp->ah_ini_radio_post_sys2ant, modes_index); 2843 } 2844 2845 } 2846 2847 if (!(AR_SREV_SOC(ah))) { 2848 /* Doubler issue : Some board doesn't work well with MCS15. Turn off doubler after freq locking is complete*/ 2849 //ath_hal_printf(ah, "%s[%d] ==== before reg[0x%08x] = 0x%08x\n", __func__, __LINE__, AR_PHY_65NM_CH0_RXTX2, OS_REG_READ(ah, AR_PHY_65NM_CH0_RXTX2)); 2850 OS_REG_RMW(ah, AR_PHY_65NM_CH0_RXTX2, 1 << AR_PHY_65NM_CH0_RXTX2_SYNTHON_MASK_S | 2851 1 << AR_PHY_65NM_CH0_RXTX2_SYNTHOVR_MASK_S, 0); /*Set synthon, synthover */ 2852 //ath_hal_printf(ah, "%s[%d] ==== after reg[0x%08x] = 0x%08x\n", __func__, __LINE__, AR_PHY_65NM_CH0_RXTX2, OS_REG_READ(ah, AR_PHY_65NM_CH0_RXTX2)); 2853 2854 OS_REG_RMW(ah, AR_PHY_65NM_CH1_RXTX2, 1 << AR_PHY_65NM_CH0_RXTX2_SYNTHON_MASK_S | 2855 1 << AR_PHY_65NM_CH0_RXTX2_SYNTHOVR_MASK_S, 0); /*Set synthon, synthover */ 2856 OS_REG_RMW(ah, AR_PHY_65NM_CH2_RXTX2, 1 << AR_PHY_65NM_CH0_RXTX2_SYNTHON_MASK_S | 2857 1 << AR_PHY_65NM_CH0_RXTX2_SYNTHOVR_MASK_S, 0); /*Set synthon, synthover */ 2858 OS_DELAY(200); 2859 2860 //ath_hal_printf(ah, "%s[%d] ==== before reg[0x%08x] = 0x%08x\n", __func__, __LINE__, AR_PHY_65NM_CH0_RXTX2, OS_REG_READ(ah, AR_PHY_65NM_CH0_RXTX2)); 2861 OS_REG_CLR_BIT(ah, AR_PHY_65NM_CH0_RXTX2, AR_PHY_65NM_CH0_RXTX2_SYNTHON_MASK); /* clr synthon */ 2862 OS_REG_CLR_BIT(ah, AR_PHY_65NM_CH1_RXTX2, AR_PHY_65NM_CH0_RXTX2_SYNTHON_MASK); /* clr synthon */ 2863 OS_REG_CLR_BIT(ah, AR_PHY_65NM_CH2_RXTX2, AR_PHY_65NM_CH0_RXTX2_SYNTHON_MASK); /* clr synthon */ 2864 //ath_hal_printf(ah, "%s[%d] ==== after reg[0x%08x] = 0x%08x\n", __func__, __LINE__, AR_PHY_65NM_CH0_RXTX2, OS_REG_READ(ah, AR_PHY_65NM_CH0_RXTX2)); 2865 2866 OS_DELAY(1); 2867 2868 //ath_hal_printf(ah, "%s[%d] ==== before reg[0x%08x] = 0x%08x\n", __func__, __LINE__, AR_PHY_65NM_CH0_RXTX2, OS_REG_READ(ah, AR_PHY_65NM_CH0_RXTX2)); 2869 OS_REG_RMW_FIELD(ah, AR_PHY_65NM_CH0_RXTX2, AR_PHY_65NM_CH0_RXTX2_SYNTHON_MASK, 1); /* set synthon */ 2870 OS_REG_RMW_FIELD(ah, AR_PHY_65NM_CH1_RXTX2, AR_PHY_65NM_CH0_RXTX2_SYNTHON_MASK, 1); /* set synthon */ 2871 OS_REG_RMW_FIELD(ah, AR_PHY_65NM_CH2_RXTX2, AR_PHY_65NM_CH0_RXTX2_SYNTHON_MASK, 1); /* set synthon */ 2872 //ath_hal_printf(ah, "%s[%d] ==== after reg[0x%08x] = 0x%08x\n", __func__, __LINE__, AR_PHY_65NM_CH0_RXTX2, OS_REG_READ(ah, AR_PHY_65NM_CH0_RXTX2)); 2873 2874 OS_DELAY(200); 2875 2876 //ath_hal_printf(ah, "%s[%d] ==== before reg[0x%08x] = 0x%08x\n", __func__, __LINE__, AR_PHY_65NM_CH0_SYNTH12, OS_REG_READ(ah, AR_PHY_65NM_CH0_SYNTH12)); 2877 OS_REG_RMW_FIELD(ah, AR_PHY_65NM_CH0_SYNTH12, AR_PHY_65NM_CH0_SYNTH12_VREFMUL3, 0xf); 2878 //OS_REG_CLR_BIT(ah, AR_PHY_65NM_CH0_SYNTH12, 1<< 16); /* clr charge pump */ 2879 //ath_hal_printf(ah, "%s[%d] ==== After reg[0x%08x] = 0x%08x\n", __func__, __LINE__, AR_PHY_65NM_CH0_SYNTH12, OS_REG_READ(ah, AR_PHY_65NM_CH0_SYNTH12)); 2880 2881 OS_REG_RMW(ah, AR_PHY_65NM_CH0_RXTX2, 0, 1 << AR_PHY_65NM_CH0_RXTX2_SYNTHON_MASK_S | 2882 1 << AR_PHY_65NM_CH0_RXTX2_SYNTHOVR_MASK_S); /*Clr synthon, synthover */ 2883 OS_REG_RMW(ah, AR_PHY_65NM_CH1_RXTX2, 0, 1 << AR_PHY_65NM_CH0_RXTX2_SYNTHON_MASK_S | 2884 1 << AR_PHY_65NM_CH0_RXTX2_SYNTHOVR_MASK_S); /*Clr synthon, synthover */ 2885 OS_REG_RMW(ah, AR_PHY_65NM_CH2_RXTX2, 0, 1 << AR_PHY_65NM_CH0_RXTX2_SYNTHON_MASK_S | 2886 1 << AR_PHY_65NM_CH0_RXTX2_SYNTHOVR_MASK_S); /*Clr synthon, synthover */ 2887 //ath_hal_printf(ah, "%s[%d] ==== after reg[0x%08x] = 0x%08x\n", __func__, __LINE__, AR_PHY_65NM_CH0_RXTX2, OS_REG_READ(ah, AR_PHY_65NM_CH0_RXTX2)); 2888 } 2889 2890 /* Write rxgain Array Parameters */ 2891 REG_WRITE_ARRAY(&ahp->ah_ini_modes_rxgain, 1, reg_writes); 2892 HALDEBUG(ah, HAL_DEBUG_RESET, "ar9300_process_ini: Rx Gain programming\n"); 2893 2894 if (AR_SREV_SCORPION(ah)) { 2895 /* Write rxgain bounds Array */ 2896 REG_WRITE_ARRAY(&ahp->ah_ini_modes_rxgain_bounds, modes_index, reg_writes); 2897 HALDEBUG(ah, HAL_DEBUG_RESET, "ar9300_process_ini: Rx Gain table bounds programming\n"); 2898 } 2899 /* UB124 xLNA settings */ 2900 if (AR_SREV_WASP(ah) && ar9300_rx_gain_index_get(ah) == 2) { 2901#define REG_WRITE(_reg,_val) *((volatile u_int32_t *)(_reg)) = (_val); 2902#define REG_READ(_reg) *((volatile u_int32_t *)(_reg)) 2903 u_int32_t val; 2904 /* B8040000: bit[0]=0, bit[3]=0; */ 2905 val = REG_READ(0xB8040000); 2906 val &= 0xfffffff6; 2907 REG_WRITE(0xB8040000, val); 2908 /* B804002c: bit[31:24]=0x2e; bit[7:0]=0x2f; */ 2909 val = REG_READ(0xB804002c); 2910 val &= 0x00ffff00; 2911 val |= 0x2e00002f; 2912 REG_WRITE(0xB804002c, val); 2913 /* B804006c: bit[1]=1; */ 2914 val = REG_READ(0xB804006c); 2915 val |= 0x2; 2916 REG_WRITE(0xB804006c, val); 2917#undef REG_READ 2918#undef REG_WRITE 2919 } 2920 2921 2922 /* Write txgain Array Parameters */ 2923 if (AR_SREV_SCORPION(ah)) { 2924 REG_WRITE_ARRAY(&ahp->ah_ini_modes_txgain, modes_txgaintable_index, 2925 reg_writes); 2926 }else{ 2927 REG_WRITE_ARRAY(&ahp->ah_ini_modes_txgain, modes_index, reg_writes); 2928 } 2929 HALDEBUG(ah, HAL_DEBUG_RESET, "ar9300_process_ini: Tx Gain programming\n"); 2930 2931 2932 /* For 5GHz channels requiring Fast Clock, apply different modal values */ 2933 if (IS_5GHZ_FAST_CLOCK_EN(ah, chan)) { 2934 HALDEBUG(ah, HAL_DEBUG_RESET, 2935 "%s: Fast clock enabled, use special ini values\n", __func__); 2936 REG_WRITE_ARRAY(&ahp->ah_ini_modes_additional, modes_index, reg_writes); 2937 } 2938 2939 if (AR_SREV_HORNET(ah) || AR_SREV_POSEIDON(ah)) { 2940 HALDEBUG(ah, HAL_DEBUG_RESET, 2941 "%s: use xtal ini for AH9300(ah)->clk_25mhz: %d\n", 2942 __func__, AH9300(ah)->clk_25mhz); 2943 REG_WRITE_ARRAY( 2944 &ahp->ah_ini_modes_additional, 1/*modes_index*/, reg_writes); 2945 } 2946 2947 if (AR_SREV_WASP(ah) && (AH9300(ah)->clk_25mhz == 0)) { 2948 HALDEBUG(ah, HAL_DEBUG_RESET, "%s: Apply 40MHz ini settings\n", __func__); 2949 REG_WRITE_ARRAY( 2950 &ahp->ah_ini_modes_additional_40mhz, 1/*modesIndex*/, reg_writes); 2951 } 2952 2953 /* Handle Japan Channel 14 channel spreading */ 2954 if (2484 == ichan->channel) { 2955 ar9300_prog_ini(ah, &ahp->ah_ini_japan2484, 1); 2956 } 2957 2958#if 0 2959 if (AR_SREV_JUPITER_20(ah) || AR_SREV_APHRODITE(ah)) { 2960 ar9300_prog_ini(ah, &ahp->ah_ini_BTCOEX_MAX_TXPWR, 1); 2961 } 2962#endif 2963 2964 /* Override INI with chip specific configuration */ 2965 ar9300_override_ini(ah, chan); 2966 2967 /* Setup 11n MAC/Phy mode registers */ 2968 ar9300_set_11n_regs(ah, chan, macmode); 2969 2970 /* 2971 * Moved ar9300_init_chain_masks() here to ensure the swap bit is set before 2972 * the pdadc table is written. Swap must occur before any radio dependent 2973 * replicated register access. The pdadc curve addressing in particular 2974 * depends on the consistent setting of the swap bit. 2975 */ 2976 ar9300_init_chain_masks(ah, ahp->ah_rx_chainmask, ahp->ah_tx_chainmask); 2977 2978 /* 2979 * Setup the transmit power values. 2980 * 2981 * After the public to private hal channel mapping, ichan contains the 2982 * valid regulatory power value. 2983 * ath_hal_getctl and ath_hal_getantennaallowed look up ichan from chan. 2984 */ 2985 status = ar9300_eeprom_set_transmit_power(ah, &ahp->ah_eeprom, chan, 2986 ath_hal_getctl(ah, chan), ath_hal_getantennaallowed(ah, chan), 2987 ath_hal_get_twice_max_regpower(ahpriv, ichan, chan), 2988 AH_MIN(MAX_RATE_POWER, ahpriv->ah_powerLimit)); 2989 if (status != HAL_OK) { 2990 HALDEBUG(ah, HAL_DEBUG_POWER_MGMT, 2991 "%s: error init'ing transmit power\n", __func__); 2992 return HAL_EIO; 2993 } 2994 2995 2996 return HAL_OK; 2997#undef N 2998} 2999 3000/* ar9300_is_cal_supp 3001 * Determine if calibration is supported by device and channel flags 3002 */ 3003inline static HAL_BOOL 3004ar9300_is_cal_supp(struct ath_hal *ah, const struct ieee80211_channel *chan, 3005 HAL_CAL_TYPES cal_type) 3006{ 3007 struct ath_hal_9300 *ahp = AH9300(ah); 3008 HAL_BOOL retval = AH_FALSE; 3009 3010 switch (cal_type & ahp->ah_supp_cals) { 3011 case IQ_MISMATCH_CAL: 3012 /* Run IQ Mismatch for non-CCK only */ 3013 if (!IEEE80211_IS_CHAN_B(chan)) { 3014 retval = AH_TRUE; 3015 } 3016 break; 3017 case TEMP_COMP_CAL: 3018 retval = AH_TRUE; 3019 break; 3020 } 3021 3022 return retval; 3023} 3024 3025 3026#if 0 3027/* ar9285_pa_cal 3028 * PA Calibration for Kite 1.1 and later versions of Kite. 3029 * - from system's team. 3030 */ 3031static inline void 3032ar9285_pa_cal(struct ath_hal *ah) 3033{ 3034 u_int32_t reg_val; 3035 int i, lo_gn, offs_6_1, offs_0; 3036 u_int8_t reflo; 3037 u_int32_t phy_test2_reg_val, phy_adc_ctl_reg_val; 3038 u_int32_t an_top2_reg_val, phy_tst_dac_reg_val; 3039 3040 3041 /* Kite 1.1 WAR for Bug 35666 3042 * Increase the LDO value to 1.28V before accessing analog Reg */ 3043 if (AR_SREV_KITE_11(ah)) { 3044 OS_REG_WRITE(ah, AR9285_AN_TOP4, (AR9285_AN_TOP4_DEFAULT | 0x14) ); 3045 } 3046 an_top2_reg_val = OS_REG_READ(ah, AR9285_AN_TOP2); 3047 3048 /* set pdv2i pdrxtxbb */ 3049 reg_val = OS_REG_READ(ah, AR9285_AN_RXTXBB1); 3050 reg_val |= ((0x1 << 5) | (0x1 << 7)); 3051 OS_REG_WRITE(ah, AR9285_AN_RXTXBB1, reg_val); 3052 3053 /* clear pwddb */ 3054 reg_val = OS_REG_READ(ah, AR9285_AN_RF2G7); 3055 reg_val &= 0xfffffffd; 3056 OS_REG_WRITE(ah, AR9285_AN_RF2G7, reg_val); 3057 3058 /* clear enpacal */ 3059 reg_val = OS_REG_READ(ah, AR9285_AN_RF2G1); 3060 reg_val &= 0xfffff7ff; 3061 OS_REG_WRITE(ah, AR9285_AN_RF2G1, reg_val); 3062 3063 /* set offcal */ 3064 reg_val = OS_REG_READ(ah, AR9285_AN_RF2G2); 3065 reg_val |= (0x1 << 12); 3066 OS_REG_WRITE(ah, AR9285_AN_RF2G2, reg_val); 3067 3068 /* set pdpadrv1=pdpadrv2=pdpaout=1 */ 3069 reg_val = OS_REG_READ(ah, AR9285_AN_RF2G1); 3070 reg_val |= (0x7 << 23); 3071 OS_REG_WRITE(ah, AR9285_AN_RF2G1, reg_val); 3072 3073 /* Read back reflo, increase it by 1 and write it. */ 3074 reg_val = OS_REG_READ(ah, AR9285_AN_RF2G3); 3075 reflo = ((reg_val >> 26) & 0x7); 3076 3077 if (reflo < 0x7) { 3078 reflo++; 3079 } 3080 reg_val = ((reg_val & 0xe3ffffff) | (reflo << 26)); 3081 OS_REG_WRITE(ah, AR9285_AN_RF2G3, reg_val); 3082 3083 reg_val = OS_REG_READ(ah, AR9285_AN_RF2G3); 3084 reflo = ((reg_val >> 26) & 0x7); 3085 3086 /* use TX single carrier to transmit 3087 * dac const 3088 * reg. 15 3089 */ 3090 phy_tst_dac_reg_val = OS_REG_READ(ah, AR_PHY_TSTDAC_CONST); 3091 OS_REG_WRITE(ah, AR_PHY_TSTDAC_CONST, ((0x7ff << 11) | 0x7ff)); 3092 reg_val = OS_REG_READ(ah, AR_PHY_TSTDAC_CONST); 3093 3094 /* source is dac const 3095 * reg. 2 3096 */ 3097 phy_test2_reg_val = OS_REG_READ(ah, AR_PHY_TEST2); 3098 OS_REG_WRITE(ah, AR_PHY_TEST2, ((0x1 << 7) | (0x1 << 1))); 3099 reg_val = OS_REG_READ(ah, AR_PHY_TEST2); 3100 3101 /* set dac on 3102 * reg. 11 3103 */ 3104 phy_adc_ctl_reg_val = OS_REG_READ(ah, AR_PHY_ADC_CTL); 3105 OS_REG_WRITE(ah, AR_PHY_ADC_CTL, 0x80008000); 3106 reg_val = OS_REG_READ(ah, AR_PHY_ADC_CTL); 3107 3108 OS_REG_WRITE(ah, AR9285_AN_TOP2, (0x1 << 27) | (0x1 << 17) | (0x1 << 16) | 3109 (0x1 << 14) | (0x1 << 12) | (0x1 << 11) | 3110 (0x1 << 7) | (0x1 << 5)); 3111 3112 OS_DELAY(10); /* 10 usec */ 3113 3114 /* clear off[6:0] */ 3115 reg_val = OS_REG_READ(ah, AR9285_AN_RF2G6); 3116 reg_val &= 0xfc0fffff; 3117 OS_REG_WRITE(ah, AR9285_AN_RF2G6, reg_val); 3118 reg_val = OS_REG_READ(ah, AR9285_AN_RF2G3); 3119 reg_val &= 0xfdffffff; 3120 OS_REG_WRITE(ah, AR9285_AN_RF2G3, reg_val); 3121 3122 offs_6_1 = 0; 3123 for (i = 6; i > 0; i--) { 3124 /* sef off[$k]==1 */ 3125 reg_val = OS_REG_READ(ah, AR9285_AN_RF2G6); 3126 reg_val &= 0xfc0fffff; 3127 reg_val = reg_val | (0x1 << (19 + i)) | ((offs_6_1) << 20); 3128 OS_REG_WRITE(ah, AR9285_AN_RF2G6, reg_val); 3129 lo_gn = (OS_REG_READ(ah, AR9285_AN_RF2G9)) & 0x1; 3130 offs_6_1 = offs_6_1 | (lo_gn << (i - 1)); 3131 } 3132 3133 reg_val = OS_REG_READ(ah, AR9285_AN_RF2G6); 3134 reg_val &= 0xfc0fffff; 3135 reg_val = reg_val | ((offs_6_1 - 1) << 20); 3136 OS_REG_WRITE(ah, AR9285_AN_RF2G6, reg_val); 3137 3138 /* set off_0=1; */ 3139 reg_val = OS_REG_READ(ah, AR9285_AN_RF2G3); 3140 reg_val &= 0xfdffffff; 3141 reg_val = reg_val | (0x1 << 25); 3142 OS_REG_WRITE(ah, AR9285_AN_RF2G3, reg_val); 3143 3144 lo_gn = OS_REG_READ(ah, AR9285_AN_RF2G9) & 0x1; 3145 offs_0 = lo_gn; 3146 3147 reg_val = OS_REG_READ(ah, AR9285_AN_RF2G3); 3148 reg_val &= 0xfdffffff; 3149 reg_val = reg_val | (offs_0 << 25); 3150 OS_REG_WRITE(ah, AR9285_AN_RF2G3, reg_val); 3151 3152 /* clear pdv2i */ 3153 reg_val = OS_REG_READ(ah, AR9285_AN_RXTXBB1); 3154 reg_val &= 0xffffff5f; 3155 OS_REG_WRITE(ah, AR9285_AN_RXTXBB1, reg_val); 3156 3157 /* set enpacal */ 3158 reg_val = OS_REG_READ(ah, AR9285_AN_RF2G1); 3159 reg_val |= (0x1 << 11); 3160 OS_REG_WRITE(ah, AR9285_AN_RF2G1, reg_val); 3161 3162 /* clear offcal */ 3163 reg_val = OS_REG_READ(ah, AR9285_AN_RF2G2); 3164 reg_val &= 0xffffefff; 3165 OS_REG_WRITE(ah, AR9285_AN_RF2G2, reg_val); 3166 3167 /* set pdpadrv1=pdpadrv2=pdpaout=0 */ 3168 reg_val = OS_REG_READ(ah, AR9285_AN_RF2G1); 3169 reg_val &= 0xfc7fffff; 3170 OS_REG_WRITE(ah, AR9285_AN_RF2G1, reg_val); 3171 3172 /* Read back reflo, decrease it by 1 and write it. */ 3173 reg_val = OS_REG_READ(ah, AR9285_AN_RF2G3); 3174 reflo = (reg_val >> 26) & 0x7; 3175 if (reflo) { 3176 reflo--; 3177 } 3178 reg_val = ((reg_val & 0xe3ffffff) | (reflo << 26)); 3179 OS_REG_WRITE(ah, AR9285_AN_RF2G3, reg_val); 3180 reg_val = OS_REG_READ(ah, AR9285_AN_RF2G3); 3181 reflo = (reg_val >> 26) & 0x7; 3182 3183 /* write back registers */ 3184 OS_REG_WRITE(ah, AR_PHY_TSTDAC_CONST, phy_tst_dac_reg_val); 3185 OS_REG_WRITE(ah, AR_PHY_TEST2, phy_test2_reg_val); 3186 OS_REG_WRITE(ah, AR_PHY_ADC_CTL, phy_adc_ctl_reg_val); 3187 OS_REG_WRITE(ah, AR9285_AN_TOP2, an_top2_reg_val); 3188 3189 /* Kite 1.1 WAR for Bug 35666 3190 * Decrease the LDO value back to 1.20V */ 3191 if (AR_SREV_KITE_11(ah)) { 3192 OS_REG_WRITE(ah, AR9285_AN_TOP4, AR9285_AN_TOP4_DEFAULT); 3193 } 3194} 3195#endif 3196 3197/* ar9300_run_init_cals 3198 * Runs non-periodic calibrations 3199 */ 3200inline static HAL_BOOL 3201ar9300_run_init_cals(struct ath_hal *ah, int init_cal_count) 3202{ 3203 struct ath_hal_9300 *ahp = AH9300(ah); 3204 HAL_CHANNEL_INTERNAL ichan; /* bogus */ 3205 HAL_BOOL is_cal_done; 3206 HAL_CAL_LIST *curr_cal; 3207 const HAL_PERCAL_DATA *cal_data; 3208 int i; 3209 3210 curr_cal = ahp->ah_cal_list_curr; 3211 if (curr_cal == AH_NULL) { 3212 return AH_FALSE; 3213 } 3214 cal_data = curr_cal->cal_data; 3215 ichan.calValid = 0; 3216 3217 for (i = 0; i < init_cal_count; i++) { 3218 /* Reset this Cal */ 3219 ar9300_reset_calibration(ah, curr_cal); 3220 /* Poll for offset calibration complete */ 3221 if (!ath_hal_wait( 3222 ah, AR_PHY_TIMING4, AR_PHY_TIMING4_DO_CAL, 0)) 3223 { 3224 HALDEBUG(ah, HAL_DEBUG_CALIBRATE, 3225 "%s: Cal %d failed to complete in 100ms.\n", 3226 __func__, curr_cal->cal_data->cal_type); 3227 /* Re-initialize list pointers for periodic cals */ 3228 ahp->ah_cal_list = ahp->ah_cal_list_last = ahp->ah_cal_list_curr 3229 = AH_NULL; 3230 return AH_FALSE; 3231 } 3232 /* Run this cal */ 3233 ar9300_per_calibration( 3234 ah, &ichan, ahp->ah_rx_chainmask, curr_cal, &is_cal_done); 3235 if (is_cal_done == AH_FALSE) { 3236 HALDEBUG(ah, HAL_DEBUG_CALIBRATE, 3237 "%s: Not able to run Init Cal %d.\n", __func__, 3238 curr_cal->cal_data->cal_type); 3239 } 3240 if (curr_cal->cal_next) { 3241 curr_cal = curr_cal->cal_next; 3242 } 3243 } 3244 3245 /* Re-initialize list pointers for periodic cals */ 3246 ahp->ah_cal_list = ahp->ah_cal_list_last = ahp->ah_cal_list_curr = AH_NULL; 3247 return AH_TRUE; 3248} 3249 3250#if 0 3251static void 3252ar9300_tx_carrier_leak_war(struct ath_hal *ah) 3253{ 3254 unsigned long tx_gain_table_max; 3255 unsigned long reg_bb_cl_map_0_b0 = 0xffffffff; 3256 unsigned long reg_bb_cl_map_1_b0 = 0xffffffff; 3257 unsigned long reg_bb_cl_map_2_b0 = 0xffffffff; 3258 unsigned long reg_bb_cl_map_3_b0 = 0xffffffff; 3259 unsigned long tx_gain, cal_run = 0; 3260 unsigned long cal_gain[AR_PHY_TPC_7_TX_GAIN_TABLE_MAX + 1]; 3261 unsigned long cal_gain_index[AR_PHY_TPC_7_TX_GAIN_TABLE_MAX + 1]; 3262 unsigned long new_gain[AR_PHY_TPC_7_TX_GAIN_TABLE_MAX + 1]; 3263 int i, j; 3264 3265 OS_MEMSET(new_gain, 0, sizeof(new_gain)); 3266 /*printf(" Running TxCarrierLeakWAR\n");*/ 3267 3268 /* process tx gain table, we use cl_map_hw_gen=0. */ 3269 OS_REG_RMW_FIELD(ah, AR_PHY_CL_CAL_CTL, AR_PHY_CL_MAP_HW_GEN, 0); 3270 3271 //the table we used is txbb_gc[2:0], 1dB[2:1]. 3272 tx_gain_table_max = OS_REG_READ_FIELD(ah, 3273 AR_PHY_TPC_7, AR_PHY_TPC_7_TX_GAIN_TABLE_MAX); 3274 3275 for (i = 0; i <= tx_gain_table_max; i++) { 3276 tx_gain = OS_REG_READ(ah, AR_PHY_TXGAIN_TAB(1) + i * 4); 3277 cal_gain[i] = (((tx_gain >> 5)& 0x7) << 2) | 3278 (((tx_gain >> 1) & 0x3) << 0); 3279 if (i == 0) { 3280 cal_gain_index[i] = cal_run; 3281 new_gain[i] = 1; 3282 cal_run++; 3283 } else { 3284 new_gain[i] = 1; 3285 for (j = 0; j < i; j++) { 3286 /* 3287 printf("i=%d, j=%d cal_gain[$i]=0x%04x\n", i, j, cal_gain[i]); 3288 */ 3289 if (new_gain[i]) { 3290 if ((cal_gain[i] != cal_gain[j])) { 3291 new_gain[i] = 1; 3292 } else { 3293 /* if old gain found, use old cal_run value. */ 3294 new_gain[i] = 0; 3295 cal_gain_index[i] = cal_gain_index[j]; 3296 } 3297 } 3298 } 3299 /* if new gain found, increase cal_run */ 3300 if (new_gain[i] == 1) { 3301 cal_gain_index[i] = cal_run; 3302 cal_run++; 3303 } 3304 } 3305 3306 reg_bb_cl_map_0_b0 = (reg_bb_cl_map_0_b0 & ~(0x1 << i)) | 3307 ((cal_gain_index[i] >> 0 & 0x1) << i); 3308 reg_bb_cl_map_1_b0 = (reg_bb_cl_map_1_b0 & ~(0x1 << i)) | 3309 ((cal_gain_index[i] >> 1 & 0x1) << i); 3310 reg_bb_cl_map_2_b0 = (reg_bb_cl_map_2_b0 & ~(0x1 << i)) | 3311 ((cal_gain_index[i] >> 2 & 0x1) << i); 3312 reg_bb_cl_map_3_b0 = (reg_bb_cl_map_3_b0 & ~(0x1 << i)) | 3313 ((cal_gain_index[i] >> 3 & 0x1) << i); 3314 3315 /* 3316 printf("i=%2d, cal_gain[$i]= 0x%04x, cal_run= %d, " 3317 "cal_gain_index[i]=%d, new_gain[i] = %d\n", 3318 i, cal_gain[i], cal_run, cal_gain_index[i], new_gain[i]); 3319 */ 3320 } 3321 OS_REG_WRITE(ah, AR_PHY_CL_MAP_0_B0, reg_bb_cl_map_0_b0); 3322 OS_REG_WRITE(ah, AR_PHY_CL_MAP_1_B0, reg_bb_cl_map_1_b0); 3323 OS_REG_WRITE(ah, AR_PHY_CL_MAP_2_B0, reg_bb_cl_map_2_b0); 3324 OS_REG_WRITE(ah, AR_PHY_CL_MAP_3_B0, reg_bb_cl_map_3_b0); 3325 if (AR_SREV_WASP(ah)) { 3326 OS_REG_WRITE(ah, AR_PHY_CL_MAP_0_B1, reg_bb_cl_map_0_b0); 3327 OS_REG_WRITE(ah, AR_PHY_CL_MAP_1_B1, reg_bb_cl_map_1_b0); 3328 OS_REG_WRITE(ah, AR_PHY_CL_MAP_2_B1, reg_bb_cl_map_2_b0); 3329 OS_REG_WRITE(ah, AR_PHY_CL_MAP_3_B1, reg_bb_cl_map_3_b0); 3330 } 3331} 3332#endif 3333 3334 3335static inline void 3336ar9300_invalidate_saved_cals(struct ath_hal *ah, HAL_CHANNEL_INTERNAL *ichan) 3337{ 3338#if ATH_SUPPORT_CAL_REUSE 3339 if (AH_PRIVATE(ah)->ah_config.ath_hal_cal_reuse & 3340 ATH_CAL_REUSE_REDO_IN_FULL_RESET) 3341 { 3342 ichan->one_time_txiqcal_done = AH_FALSE; 3343 ichan->one_time_txclcal_done = AH_FALSE; 3344 } 3345#endif 3346} 3347 3348static inline HAL_BOOL 3349ar9300_restore_rtt_cals(struct ath_hal *ah, HAL_CHANNEL_INTERNAL *ichan) 3350{ 3351 HAL_BOOL restore_status = AH_FALSE; 3352 3353 return restore_status; 3354} 3355 3356/* ar9300_init_cal 3357 * Initialize Calibration infrastructure 3358 */ 3359static inline HAL_BOOL 3360ar9300_init_cal_internal(struct ath_hal *ah, struct ieee80211_channel *chan, 3361 HAL_CHANNEL_INTERNAL *ichan, 3362 HAL_BOOL enable_rtt, HAL_BOOL do_rtt_cal, HAL_BOOL skip_if_none, HAL_BOOL apply_last_iqcorr) 3363{ 3364 struct ath_hal_9300 *ahp = AH9300(ah); 3365 HAL_BOOL txiqcal_success_flag = AH_FALSE; 3366 HAL_BOOL cal_done = AH_FALSE; 3367 int iqcal_idx = 0; 3368 HAL_BOOL do_sep_iq_cal = AH_FALSE; 3369 HAL_BOOL do_agc_cal = do_rtt_cal; 3370 HAL_BOOL is_cal_reusable = AH_TRUE; 3371#if ATH_SUPPORT_CAL_REUSE 3372 HAL_BOOL cal_reuse_enable = AH_PRIVATE(ah)->ah_config.ath_hal_cal_reuse & 3373 ATH_CAL_REUSE_ENABLE; 3374 HAL_BOOL clc_success = AH_FALSE; 3375 int32_t ch_idx, j, cl_tab_reg; 3376 u_int32_t BB_cl_tab_entry = MAX_BB_CL_TABLE_ENTRY; 3377 u_int32_t BB_cl_tab_b[AR9300_MAX_CHAINS] = { 3378 AR_PHY_CL_TAB_0, 3379 AR_PHY_CL_TAB_1, 3380 AR_PHY_CL_TAB_2 3381 }; 3382#endif 3383 3384 if (AR_SREV_HORNET(ah) || AR_SREV_POSEIDON(ah) || AR_SREV_APHRODITE(ah)) { 3385 /* Hornet: 1 x 1 */ 3386 ahp->ah_rx_cal_chainmask = 0x1; 3387 ahp->ah_tx_cal_chainmask = 0x1; 3388 } else if (AR_SREV_WASP(ah) || AR_SREV_JUPITER(ah)) { 3389 /* Wasp/Jupiter: 2 x 2 */ 3390 ahp->ah_rx_cal_chainmask = 0x3; 3391 ahp->ah_tx_cal_chainmask = 0x3; 3392 } else { 3393 /* 3394 * Osprey needs to be configured for the correct chain mode 3395 * before running AGC/TxIQ cals. 3396 */ 3397 if (ahp->ah_enterprise_mode & AR_ENT_OTP_CHAIN2_DISABLE) { 3398 /* chain 2 disabled - 2 chain mode */ 3399 ahp->ah_rx_cal_chainmask = 0x3; 3400 ahp->ah_tx_cal_chainmask = 0x3; 3401 } else { 3402 ahp->ah_rx_cal_chainmask = 0x7; 3403 ahp->ah_tx_cal_chainmask = 0x7; 3404 } 3405 } 3406 ar9300_init_chain_masks(ah, ahp->ah_rx_cal_chainmask, ahp->ah_tx_cal_chainmask); 3407 3408 3409 if (ahp->tx_cl_cal_enable) { 3410#if ATH_SUPPORT_CAL_REUSE 3411 /* disable Carrie Leak or set do_agc_cal accordingly */ 3412 if (cal_reuse_enable && ichan->one_time_txclcal_done) 3413 { 3414 OS_REG_CLR_BIT(ah, AR_PHY_CL_CAL_CTL, AR_PHY_CL_CAL_ENABLE); 3415 } else 3416#endif /* ATH_SUPPORT_CAL_REUSE */ 3417 { 3418 OS_REG_SET_BIT(ah, AR_PHY_CL_CAL_CTL, AR_PHY_CL_CAL_ENABLE); 3419 do_agc_cal = AH_TRUE; 3420 } 3421 } 3422 3423 /* Do Tx IQ Calibration here for osprey hornet and wasp */ 3424 /* XXX: For initial wasp bringup - check and enable this */ 3425 /* EV 74233: Tx IQ fails to complete for half/quarter rates */ 3426 if (!(IEEE80211_IS_CHAN_HALF(chan) || IEEE80211_IS_CHAN_QUARTER(chan))) { 3427 if (ahp->tx_iq_cal_enable) { 3428 /* this should be eventually moved to INI file */ 3429 OS_REG_RMW_FIELD(ah, AR_PHY_TX_IQCAL_CONTROL_1(ah), 3430 AR_PHY_TX_IQCAL_CONTROL_1_IQCORR_I_Q_COFF_DELPT, DELPT); 3431 3432 /* 3433 * For poseidon and later chips, 3434 * Tx IQ cal HW run will be a part of AGC calibration 3435 */ 3436 if (ahp->tx_iq_cal_during_agc_cal) { 3437 /* 3438 * txiqcal_success_flag always set to 1 to run 3439 * ar9300_tx_iq_cal_post_proc 3440 * if following AGC cal passes 3441 */ 3442#if ATH_SUPPORT_CAL_REUSE 3443 if (!cal_reuse_enable || !ichan->one_time_txiqcal_done) 3444 { 3445 txiqcal_success_flag = AH_TRUE; 3446 OS_REG_WRITE(ah, AR_PHY_TX_IQCAL_CONTROL_0(ah), 3447 OS_REG_READ(ah, AR_PHY_TX_IQCAL_CONTROL_0(ah)) | 3448 AR_PHY_TX_IQCAL_CONTROL_0_ENABLE_TXIQ_CAL); 3449 } else { 3450 OS_REG_WRITE(ah, AR_PHY_TX_IQCAL_CONTROL_0(ah), 3451 OS_REG_READ(ah, AR_PHY_TX_IQCAL_CONTROL_0(ah)) & 3452 (~AR_PHY_TX_IQCAL_CONTROL_0_ENABLE_TXIQ_CAL)); 3453 } 3454#else 3455 if (OS_REG_READ_FIELD(ah, 3456 AR_PHY_TX_IQCAL_CONTROL_0(ah), 3457 AR_PHY_TX_IQCAL_CONTROL_0_ENABLE_TXIQ_CAL)){ 3458 if (apply_last_iqcorr == AH_TRUE) { 3459 OS_REG_CLR_BIT(ah, AR_PHY_TX_IQCAL_CONTROL_0(ah), 3460 AR_PHY_TX_IQCAL_CONTROL_0_ENABLE_TXIQ_CAL); 3461 txiqcal_success_flag = AH_FALSE; 3462 } else { 3463 txiqcal_success_flag = AH_TRUE; 3464 } 3465 }else{ 3466 txiqcal_success_flag = AH_FALSE; 3467 } 3468#endif 3469 if (txiqcal_success_flag) { 3470 do_agc_cal = AH_TRUE; 3471 } 3472 } else 3473#if ATH_SUPPORT_CAL_REUSE 3474 if (!cal_reuse_enable || !ichan->one_time_txiqcal_done) 3475#endif 3476 { 3477 do_sep_iq_cal = AH_TRUE; 3478 do_agc_cal = AH_TRUE; 3479 } 3480 } 3481 } 3482 3483#if ATH_SUPPORT_MCI 3484 if (AH_PRIVATE(ah)->ah_caps.halMciSupport && 3485 IS_CHAN_2GHZ(ichan) && 3486 (ahp->ah_mci_bt_state == MCI_BT_AWAKE) && 3487 do_agc_cal && 3488 !(ah->ah_config.ath_hal_mci_config & 3489 ATH_MCI_CONFIG_DISABLE_MCI_CAL)) 3490 { 3491 u_int32_t payload[4] = {0, 0, 0, 0}; 3492 3493 /* Send CAL_REQ only when BT is AWAKE. */ 3494 HALDEBUG(ah, HAL_DEBUG_BT_COEX, "(MCI) %s: Send WLAN_CAL_REQ 0x%X\n", 3495 __func__, ahp->ah_mci_wlan_cal_seq); 3496 MCI_GPM_SET_CAL_TYPE(payload, MCI_GPM_WLAN_CAL_REQ); 3497 payload[MCI_GPM_WLAN_CAL_W_SEQUENCE] = ahp->ah_mci_wlan_cal_seq++; 3498 ar9300_mci_send_message(ah, MCI_GPM, 0, payload, 16, AH_TRUE, AH_FALSE); 3499 3500 /* Wait BT_CAL_GRANT for 50ms */ 3501 HALDEBUG(ah, HAL_DEBUG_BT_COEX, 3502 "(MCI) %s: Wait for BT_CAL_GRANT\n", __func__); 3503 if (ar9300_mci_wait_for_gpm(ah, MCI_GPM_BT_CAL_GRANT, 0, 50000)) 3504 { 3505 HALDEBUG(ah, HAL_DEBUG_BT_COEX, 3506 "(MCI) %s: Got BT_CAL_GRANT.\n", __func__); 3507 } 3508 else { 3509 is_cal_reusable = AH_FALSE; 3510 HALDEBUG(ah, HAL_DEBUG_BT_COEX, 3511 "(MCI) %s: BT is not responding.\n", __func__); 3512 } 3513 } 3514#endif /* ATH_SUPPORT_MCI */ 3515 3516 if (do_sep_iq_cal) 3517 { 3518 /* enable Tx IQ Calibration HW for osprey/hornet/wasp */ 3519 txiqcal_success_flag = ar9300_tx_iq_cal_hw_run(ah); 3520 OS_REG_WRITE(ah, AR_PHY_ACTIVE, AR_PHY_ACTIVE_DIS); 3521 OS_DELAY(5); 3522 OS_REG_WRITE(ah, AR_PHY_ACTIVE, AR_PHY_ACTIVE_EN); 3523 } 3524#if 0 3525 if (AR_SREV_HORNET(ah) || AR_SREV_POSEIDON(ah)) { 3526 ar9300_tx_carrier_leak_war(ah); 3527 } 3528#endif 3529 /* 3530 * Calibrate the AGC 3531 * 3532 * Tx IQ cal is a part of AGC cal for Jupiter/Poseidon, etc. 3533 * please enable the bit of txiqcal_control_0[31] in INI file 3534 * for Jupiter/Poseidon/etc. 3535 */ 3536 if(!AR_SREV_SCORPION(ah)) { 3537 if (do_agc_cal || !skip_if_none) { 3538 OS_REG_WRITE(ah, AR_PHY_AGC_CONTROL, 3539 OS_REG_READ(ah, AR_PHY_AGC_CONTROL) | AR_PHY_AGC_CONTROL_CAL); 3540 3541 /* Poll for offset calibration complete */ 3542 cal_done = ath_hal_wait(ah, 3543 AR_PHY_AGC_CONTROL, AR_PHY_AGC_CONTROL_CAL, 0); 3544 if (!cal_done) { 3545 HALDEBUG(ah, HAL_DEBUG_FCS_RTT, 3546 "(FCS) CAL NOT DONE!!! - %d\n", ichan->channel); 3547 } 3548 } else { 3549 cal_done = AH_TRUE; 3550 } 3551 /* 3552 * Tx IQ cal post-processing in SW 3553 * This part of code should be common to all chips, 3554 * no chip specific code for Jupiter/Posdeion except for register names. 3555 */ 3556 if (txiqcal_success_flag) { 3557 ar9300_tx_iq_cal_post_proc(ah,ichan, 1, 1,is_cal_reusable,false); 3558 } 3559 } else { 3560 if (!txiqcal_success_flag) { 3561 OS_REG_WRITE(ah, AR_PHY_AGC_CONTROL, 3562 OS_REG_READ(ah, AR_PHY_AGC_CONTROL) | AR_PHY_AGC_CONTROL_CAL); 3563 if (!ath_hal_wait(ah, AR_PHY_AGC_CONTROL, AR_PHY_AGC_CONTROL_CAL, 3564 0)) { 3565 HALDEBUG(ah, HAL_DEBUG_CALIBRATE, 3566 "%s: offset calibration failed to complete in 1ms; " 3567 "noisy environment?\n", __func__); 3568 return AH_FALSE; 3569 } 3570 if (apply_last_iqcorr == AH_TRUE) { 3571 ar9300_tx_iq_cal_post_proc(ah, ichan, 0, 0, is_cal_reusable, AH_TRUE); 3572 } 3573 } else { 3574 for (iqcal_idx=0;iqcal_idx<MAXIQCAL;iqcal_idx++) { 3575 OS_REG_WRITE(ah, AR_PHY_AGC_CONTROL, 3576 OS_REG_READ(ah, AR_PHY_AGC_CONTROL) | AR_PHY_AGC_CONTROL_CAL); 3577 3578 /* Poll for offset calibration complete */ 3579 if (!ath_hal_wait(ah, AR_PHY_AGC_CONTROL, 3580 AR_PHY_AGC_CONTROL_CAL, 0)) { 3581 HALDEBUG(ah, HAL_DEBUG_CALIBRATE, 3582 "%s: offset calibration failed to complete in 1ms; " 3583 "noisy environment?\n", __func__); 3584 return AH_FALSE; 3585 } 3586 /* 3587 * Tx IQ cal post-processing in SW 3588 * This part of code should be common to all chips, 3589 * no chip specific code for Jupiter/Posdeion except for register names. 3590 */ 3591 ar9300_tx_iq_cal_post_proc(ah, ichan, iqcal_idx+1, MAXIQCAL, is_cal_reusable, AH_FALSE); 3592 } 3593 } 3594 } 3595 3596 3597#if ATH_SUPPORT_MCI 3598 if (AH_PRIVATE(ah)->ah_caps.halMciSupport && 3599 IS_CHAN_2GHZ(ichan) && 3600 (ahp->ah_mci_bt_state == MCI_BT_AWAKE) && 3601 do_agc_cal && 3602 !(ah->ah_config.ath_hal_mci_config & 3603 ATH_MCI_CONFIG_DISABLE_MCI_CAL)) 3604 { 3605 u_int32_t payload[4] = {0, 0, 0, 0}; 3606 3607 HALDEBUG(ah, HAL_DEBUG_BT_COEX, "(MCI) %s: Send WLAN_CAL_DONE 0x%X\n", 3608 __func__, ahp->ah_mci_wlan_cal_done); 3609 MCI_GPM_SET_CAL_TYPE(payload, MCI_GPM_WLAN_CAL_DONE); 3610 payload[MCI_GPM_WLAN_CAL_W_SEQUENCE] = ahp->ah_mci_wlan_cal_done++; 3611 ar9300_mci_send_message(ah, MCI_GPM, 0, payload, 16, AH_TRUE, AH_FALSE); 3612 } 3613#endif /* ATH_SUPPORT_MCI */ 3614 3615 3616 if (!cal_done && !AR_SREV_SCORPION(ah) ) 3617 { 3618 HALDEBUG(ah, HAL_DEBUG_CALIBRATE, 3619 "%s: offset calibration failed to complete in 1ms; " 3620 "noisy environment?\n", __func__); 3621 return AH_FALSE; 3622 } 3623 3624#if 0 3625 /* Beacon stuck fix, refer to EV 120056 */ 3626 if(IS_CHAN_2GHZ(chan) && AR_SREV_SCORPION(ah)) 3627 OS_REG_WRITE(ah, AR_PHY_TIMING5, OS_REG_READ(ah,AR_PHY_TIMING5) & ~AR_PHY_TIMING5_CYCPWR_THR1_ENABLE); 3628#endif 3629 3630#if 0 3631 /* Do PA Calibration */ 3632 if (AR_SREV_KITE(ah) && AR_SREV_KITE_11_OR_LATER(ah)) { 3633 ar9285_pa_cal(ah); 3634 } 3635#endif 3636 3637#if ATH_SUPPORT_CAL_REUSE 3638 if (ichan->one_time_txiqcal_done) { 3639 ar9300_tx_iq_cal_apply(ah, ichan); 3640 HALDEBUG(ah, HAL_DEBUG_FCS_RTT, 3641 "(FCS) TXIQCAL applied - %d\n", ichan->channel); 3642 } 3643#endif /* ATH_SUPPORT_CAL_REUSE */ 3644 3645#if ATH_SUPPORT_CAL_REUSE 3646 if (cal_reuse_enable && ahp->tx_cl_cal_enable) 3647 { 3648 clc_success = (OS_REG_READ(ah, AR_PHY_AGC_CONTROL) & 3649 AR_PHY_AGC_CONTROL_CLC_SUCCESS) ? 1 : 0; 3650 3651 if (ichan->one_time_txclcal_done) 3652 { 3653 /* reapply CL cal results */ 3654 for (ch_idx = 0; ch_idx < AR9300_MAX_CHAINS; ch_idx++) { 3655 if ((ahp->ah_tx_cal_chainmask & (1 << ch_idx)) == 0) { 3656 continue; 3657 } 3658 cl_tab_reg = BB_cl_tab_b[ch_idx]; 3659 for (j = 0; j < BB_cl_tab_entry; j++) { 3660 OS_REG_WRITE(ah, cl_tab_reg, ichan->tx_clcal[ch_idx][j]); 3661 cl_tab_reg += 4;; 3662 } 3663 } 3664 HALDEBUG(ah, HAL_DEBUG_FCS_RTT, 3665 "(FCS) TX CL CAL applied - %d\n", ichan->channel); 3666 } 3667 else if (is_cal_reusable && clc_success) { 3668 /* save CL cal results */ 3669 for (ch_idx = 0; ch_idx < AR9300_MAX_CHAINS; ch_idx++) { 3670 if ((ahp->ah_tx_cal_chainmask & (1 << ch_idx)) == 0) { 3671 continue; 3672 } 3673 cl_tab_reg = BB_cl_tab_b[ch_idx]; 3674 for (j = 0; j < BB_cl_tab_entry; j++) { 3675 ichan->tx_clcal[ch_idx][j] = OS_REG_READ(ah, cl_tab_reg); 3676 cl_tab_reg += 4; 3677 } 3678 } 3679 ichan->one_time_txclcal_done = AH_TRUE; 3680 HALDEBUG(ah, HAL_DEBUG_FCS_RTT, 3681 "(FCS) TX CL CAL saved - %d\n", ichan->channel); 3682 } 3683 } 3684#endif /* ATH_SUPPORT_CAL_REUSE */ 3685 3686 /* Revert chainmasks to their original values before NF cal */ 3687 ar9300_init_chain_masks(ah, ahp->ah_rx_chainmask, ahp->ah_tx_chainmask); 3688 3689#if !FIX_NOISE_FLOOR 3690 /* 3691 * Do NF calibration after DC offset and other CALs. 3692 * Per system engineers, noise floor value can sometimes be 20 dB 3693 * higher than normal value if DC offset and noise floor cal are 3694 * triggered at the same time. 3695 */ 3696 OS_REG_WRITE(ah, AR_PHY_AGC_CONTROL, 3697 OS_REG_READ(ah, AR_PHY_AGC_CONTROL) | AR_PHY_AGC_CONTROL_NF); 3698#endif 3699 3700 /* Initialize list pointers */ 3701 ahp->ah_cal_list = ahp->ah_cal_list_last = ahp->ah_cal_list_curr = AH_NULL; 3702 3703 /* 3704 * Enable IQ, ADC Gain, ADC DC Offset Cals 3705 */ 3706 /* Setup all non-periodic, init time only calibrations */ 3707 /* XXX: Init DC Offset not working yet */ 3708#ifdef not_yet 3709 if (AH_TRUE == ar9300_is_cal_supp(ah, chan, ADC_DC_INIT_CAL)) { 3710 INIT_CAL(&ahp->ah_adc_dc_cal_init_data); 3711 INSERT_CAL(ahp, &ahp->ah_adc_dc_cal_init_data); 3712 } 3713 3714 /* Initialize current pointer to first element in list */ 3715 ahp->ah_cal_list_curr = ahp->ah_cal_list; 3716 3717 if (ahp->ah_cal_list_curr) { 3718 if (ar9300_run_init_cals(ah, 0) == AH_FALSE) { 3719 return AH_FALSE; 3720 } 3721 } 3722#endif 3723 /* end - Init time calibrations */ 3724 3725 /* If Cals are supported, add them to list via INIT/INSERT_CAL */ 3726 if (AH_TRUE == ar9300_is_cal_supp(ah, chan, IQ_MISMATCH_CAL)) { 3727 INIT_CAL(&ahp->ah_iq_cal_data); 3728 INSERT_CAL(ahp, &ahp->ah_iq_cal_data); 3729 HALDEBUG(ah, HAL_DEBUG_CALIBRATE, 3730 "%s: enabling IQ Calibration.\n", __func__); 3731 } 3732 if (AH_TRUE == ar9300_is_cal_supp(ah, chan, TEMP_COMP_CAL)) { 3733 INIT_CAL(&ahp->ah_temp_comp_cal_data); 3734 INSERT_CAL(ahp, &ahp->ah_temp_comp_cal_data); 3735 HALDEBUG(ah, HAL_DEBUG_CALIBRATE, 3736 "%s: enabling Temperature Compensation Calibration.\n", __func__); 3737 } 3738 3739 /* Initialize current pointer to first element in list */ 3740 ahp->ah_cal_list_curr = ahp->ah_cal_list; 3741 3742 /* Reset state within current cal */ 3743 if (ahp->ah_cal_list_curr) { 3744 ar9300_reset_calibration(ah, ahp->ah_cal_list_curr); 3745 } 3746 3747 /* Mark all calibrations on this channel as being invalid */ 3748 ichan->calValid = 0; 3749 3750 return AH_TRUE; 3751} 3752 3753static inline HAL_BOOL 3754ar9300_init_cal(struct ath_hal *ah, struct ieee80211_channel *chan, HAL_BOOL skip_if_none, HAL_BOOL apply_last_iqcorr) 3755{ 3756 HAL_CHANNEL_INTERNAL *ichan = ath_hal_checkchannel(ah, chan); 3757 HAL_BOOL do_rtt_cal = AH_TRUE; 3758 HAL_BOOL enable_rtt = AH_FALSE; 3759 3760 HALASSERT(ichan); 3761 3762 return ar9300_init_cal_internal(ah, chan, ichan, enable_rtt, do_rtt_cal, skip_if_none, apply_last_iqcorr); 3763} 3764 3765/* ar9300_reset_cal_valid 3766 * Entry point for upper layers to restart current cal. 3767 * Reset the calibration valid bit in channel. 3768 */ 3769void 3770ar9300_reset_cal_valid(struct ath_hal *ah, const struct ieee80211_channel *chan, 3771 HAL_BOOL *is_cal_done, u_int32_t cal_type) 3772{ 3773 struct ath_hal_9300 *ahp = AH9300(ah); 3774 HAL_CHANNEL_INTERNAL *ichan = ath_hal_checkchannel(ah, chan); 3775 HAL_CAL_LIST *curr_cal = ahp->ah_cal_list_curr; 3776 3777 *is_cal_done = AH_TRUE; 3778 3779 if (curr_cal == AH_NULL) { 3780 return; 3781 } 3782 if (ichan == AH_NULL) { 3783 HALDEBUG(ah, HAL_DEBUG_CALIBRATE, 3784 "%s: invalid channel %u/0x%x; no mapping\n", 3785 __func__, chan->ic_freq, chan->ic_flags); 3786 return; 3787 } 3788 3789 if (!(cal_type & IQ_MISMATCH_CAL)) { 3790 *is_cal_done = AH_FALSE; 3791 return; 3792 } 3793 3794 /* Expected that this calibration has run before, post-reset. 3795 * Current state should be done 3796 */ 3797 if (curr_cal->cal_state != CAL_DONE) { 3798 HALDEBUG(ah, HAL_DEBUG_CALIBRATE, 3799 "%s: Calibration state incorrect, %d\n", 3800 __func__, curr_cal->cal_state); 3801 return; 3802 } 3803 3804 /* Verify Cal is supported on this channel */ 3805 if (ar9300_is_cal_supp(ah, chan, curr_cal->cal_data->cal_type) == AH_FALSE) { 3806 return; 3807 } 3808 3809 HALDEBUG(ah, HAL_DEBUG_CALIBRATE, 3810 "%s: Resetting Cal %d state for channel %u/0x%x\n", __func__, 3811 curr_cal->cal_data->cal_type, chan->ic_freq, chan->ic_flags); 3812 3813 /* Disable cal validity in channel */ 3814 ichan->calValid &= ~curr_cal->cal_data->cal_type; 3815 curr_cal->cal_state = CAL_WAITING; 3816 /* Indicate to upper layers that we need polling */ 3817 *is_cal_done = AH_FALSE; 3818} 3819 3820static inline void 3821ar9300_set_dma(struct ath_hal *ah) 3822{ 3823 u_int32_t regval; 3824 struct ath_hal_9300 *ahp = AH9300(ah); 3825 3826#if 0 3827 /* 3828 * set AHB_MODE not to do cacheline prefetches 3829 */ 3830 regval = OS_REG_READ(ah, AR_AHB_MODE); 3831 OS_REG_WRITE(ah, AR_AHB_MODE, regval | AR_AHB_PREFETCH_RD_EN); 3832#endif 3833 3834 /* 3835 * let mac dma reads be in 128 byte chunks 3836 */ 3837 regval = OS_REG_READ(ah, AR_TXCFG) & ~AR_TXCFG_DMASZ_MASK; 3838 OS_REG_WRITE(ah, AR_TXCFG, regval | AR_TXCFG_DMASZ_128B); 3839 3840 /* 3841 * Restore TX Trigger Level to its pre-reset value. 3842 * The initial value depends on whether aggregation is enabled, and is 3843 * adjusted whenever underruns are detected. 3844 */ 3845 /* 3846 OS_REG_RMW_FIELD(ah, AR_TXCFG, AR_FTRIG, AH_PRIVATE(ah)->ah_tx_trig_level); 3847 */ 3848 /* 3849 * Osprey 1.0 bug (EV 61936). Don't change trigger level from .ini default. 3850 * Osprey 2.0 - hardware recommends using the default INI settings. 3851 */ 3852#if 0 3853 OS_REG_RMW_FIELD(ah, AR_TXCFG, AR_FTRIG, 0x3f); 3854#endif 3855 /* 3856 * let mac dma writes be in 128 byte chunks 3857 */ 3858 regval = OS_REG_READ(ah, AR_RXCFG) & ~AR_RXCFG_DMASZ_MASK; 3859 OS_REG_WRITE(ah, AR_RXCFG, regval | AR_RXCFG_DMASZ_128B); 3860 3861 /* 3862 * Setup receive FIFO threshold to hold off TX activities 3863 */ 3864 OS_REG_WRITE(ah, AR_RXFIFO_CFG, 0x200); 3865 3866 /* 3867 * reduce the number of usable entries in PCU TXBUF to avoid 3868 * wrap around bugs. (bug 20428) 3869 */ 3870 3871 if (AR_SREV_WASP(ah) && 3872 (AH_PRIVATE((ah))->ah_macRev > AR_SREV_REVISION_WASP_12)) { 3873 /* Wasp 1.3 fix for EV#85395 requires usable entries 3874 * to be set to 0x500 3875 */ 3876 OS_REG_WRITE(ah, AR_PCU_TXBUF_CTRL, 0x500); 3877 } else { 3878 OS_REG_WRITE(ah, AR_PCU_TXBUF_CTRL, AR_PCU_TXBUF_CTRL_USABLE_SIZE); 3879 } 3880 3881 /* 3882 * Enable HPQ for UAPSD 3883 */ 3884 if (AH_PRIVATE(ah)->ah_opmode == HAL_M_HOSTAP) { 3885 OS_REG_WRITE(ah, AR_HP_Q_CONTROL, 3886 AR_HPQ_ENABLE | AR_HPQ_UAPSD | AR_HPQ_UAPSD_TRIGGER_EN); 3887 } 3888 3889 /* 3890 * set the transmit status ring 3891 */ 3892 ar9300_reset_tx_status_ring(ah); 3893 3894 /* 3895 * set rxbp threshold. Must be non-zero for RX_EOL to occur. 3896 * For Osprey 2.0+, keep the original thresholds 3897 * otherwise performance is lost due to excessive RX EOL interrupts. 3898 */ 3899 OS_REG_RMW_FIELD(ah, AR_RXBP_THRESH, AR_RXBP_THRESH_HP, 0x1); 3900 OS_REG_RMW_FIELD(ah, AR_RXBP_THRESH, AR_RXBP_THRESH_LP, 0x1); 3901 3902 /* 3903 * set receive buffer size. 3904 */ 3905 if (ahp->rx_buf_size) { 3906 OS_REG_WRITE(ah, AR_DATABUF, ahp->rx_buf_size); 3907 } 3908} 3909 3910static inline void 3911ar9300_init_bb(struct ath_hal *ah, struct ieee80211_channel *chan) 3912{ 3913 u_int32_t synth_delay; 3914 3915 /* 3916 * Wait for the frequency synth to settle (synth goes on 3917 * via AR_PHY_ACTIVE_EN). Read the phy active delay register. 3918 * Value is in 100ns increments. 3919 */ 3920 synth_delay = OS_REG_READ(ah, AR_PHY_RX_DELAY) & AR_PHY_RX_DELAY_DELAY; 3921 if (IEEE80211_IS_CHAN_CCK(chan)) { 3922 synth_delay = (4 * synth_delay) / 22; 3923 } else { 3924 synth_delay /= 10; 3925 } 3926 3927 /* Activate the PHY (includes baseband activate + synthesizer on) */ 3928 OS_REG_WRITE(ah, AR_PHY_ACTIVE, AR_PHY_ACTIVE_EN); 3929 3930 /* 3931 * There is an issue if the AP starts the calibration before 3932 * the base band timeout completes. This could result in the 3933 * rx_clear AH_FALSE triggering. As a workaround we add delay an 3934 * extra BASE_ACTIVATE_DELAY usecs to ensure this condition 3935 * does not happen. 3936 */ 3937 OS_DELAY(synth_delay + BASE_ACTIVATE_DELAY); 3938} 3939 3940static inline void 3941ar9300_init_interrupt_masks(struct ath_hal *ah, HAL_OPMODE opmode) 3942{ 3943 struct ath_hal_9300 *ahp = AH9300(ah); 3944 u_int32_t msi_cfg = 0; 3945 u_int32_t sync_en_def = AR9300_INTR_SYNC_DEFAULT; 3946 3947 /* 3948 * Setup interrupt handling. Note that ar9300_reset_tx_queue 3949 * manipulates the secondary IMR's as queues are enabled 3950 * and disabled. This is done with RMW ops to insure the 3951 * settings we make here are preserved. 3952 */ 3953 ahp->ah_mask_reg = 3954 AR_IMR_TXERR | AR_IMR_TXURN | 3955 AR_IMR_RXERR | AR_IMR_RXORN | 3956 AR_IMR_BCNMISC; 3957 3958 if (ahp->ah_intr_mitigation_rx) { 3959 /* enable interrupt mitigation for rx */ 3960 ahp->ah_mask_reg |= AR_IMR_RXINTM | AR_IMR_RXMINTR | AR_IMR_RXOK_HP; 3961 msi_cfg |= AR_INTCFG_MSI_RXINTM | AR_INTCFG_MSI_RXMINTR; 3962 } else { 3963 ahp->ah_mask_reg |= AR_IMR_RXOK_LP | AR_IMR_RXOK_HP; 3964 msi_cfg |= AR_INTCFG_MSI_RXOK; 3965 } 3966 if (ahp->ah_intr_mitigation_tx) { 3967 /* enable interrupt mitigation for tx */ 3968 ahp->ah_mask_reg |= AR_IMR_TXINTM | AR_IMR_TXMINTR; 3969 msi_cfg |= AR_INTCFG_MSI_TXINTM | AR_INTCFG_MSI_TXMINTR; 3970 } else { 3971 ahp->ah_mask_reg |= AR_IMR_TXOK; 3972 msi_cfg |= AR_INTCFG_MSI_TXOK; 3973 } 3974 if (opmode == HAL_M_HOSTAP) { 3975 ahp->ah_mask_reg |= AR_IMR_MIB; 3976 } 3977 3978 OS_REG_WRITE(ah, AR_IMR, ahp->ah_mask_reg); 3979 OS_REG_WRITE(ah, AR_IMR_S2, OS_REG_READ(ah, AR_IMR_S2) | AR_IMR_S2_GTT); 3980 ahp->ah_mask2Reg = OS_REG_READ(ah, AR_IMR_S2); 3981 3982 if (ah->ah_config.ath_hal_enable_msi) { 3983 /* Cache MSI register value */ 3984 ahp->ah_msi_reg = OS_REG_READ(ah, AR_HOSTIF_REG(ah, AR_PCIE_MSI)); 3985 ahp->ah_msi_reg |= AR_PCIE_MSI_HW_DBI_WR_EN; 3986 if (AR_SREV_POSEIDON(ah)) { 3987 ahp->ah_msi_reg &= AR_PCIE_MSI_HW_INT_PENDING_ADDR_MSI_64; 3988 } else { 3989 ahp->ah_msi_reg &= AR_PCIE_MSI_HW_INT_PENDING_ADDR; 3990 } 3991 /* Program MSI configuration */ 3992 OS_REG_WRITE(ah, AR_INTCFG, msi_cfg); 3993 } 3994 3995 /* 3996 * debug - enable to see all synchronous interrupts status 3997 */ 3998 /* Clear any pending sync cause interrupts */ 3999 OS_REG_WRITE(ah, AR_HOSTIF_REG(ah, AR_INTR_SYNC_CAUSE), 0xFFFFFFFF); 4000 4001 /* Allow host interface sync interrupt sources to set cause bit */ 4002 if (AR_SREV_POSEIDON(ah)) { 4003 sync_en_def = AR9300_INTR_SYNC_DEF_NO_HOST1_PERR; 4004 } 4005 else if (AR_SREV_WASP(ah)) { 4006 sync_en_def = AR9340_INTR_SYNC_DEFAULT; 4007 } 4008 OS_REG_WRITE(ah, 4009 AR_HOSTIF_REG(ah, AR_INTR_SYNC_ENABLE), sync_en_def); 4010 4011 /* _Disable_ host interface sync interrupt when cause bits set */ 4012 OS_REG_WRITE(ah, AR_HOSTIF_REG(ah, AR_INTR_SYNC_MASK), 0); 4013 4014 OS_REG_WRITE(ah, AR_HOSTIF_REG(ah, AR_INTR_PRIO_ASYNC_ENABLE), 0); 4015 OS_REG_WRITE(ah, AR_HOSTIF_REG(ah, AR_INTR_PRIO_ASYNC_MASK), 0); 4016 OS_REG_WRITE(ah, AR_HOSTIF_REG(ah, AR_INTR_PRIO_SYNC_ENABLE), 0); 4017 OS_REG_WRITE(ah, AR_HOSTIF_REG(ah, AR_INTR_PRIO_SYNC_MASK), 0); 4018} 4019 4020static inline void 4021ar9300_init_qos(struct ath_hal *ah) 4022{ 4023 OS_REG_WRITE(ah, AR_MIC_QOS_CONTROL, 0x100aa); /* XXX magic */ 4024 OS_REG_WRITE(ah, AR_MIC_QOS_SELECT, 0x3210); /* XXX magic */ 4025 4026 /* Turn on NOACK Support for QoS packets */ 4027 OS_REG_WRITE(ah, AR_QOS_NO_ACK, 4028 SM(2, AR_QOS_NO_ACK_TWO_BIT) | 4029 SM(5, AR_QOS_NO_ACK_BIT_OFF) | 4030 SM(0, AR_QOS_NO_ACK_BYTE_OFF)); 4031 4032 /* 4033 * initialize TXOP for all TIDs 4034 */ 4035 OS_REG_WRITE(ah, AR_TXOP_X, AR_TXOP_X_VAL); 4036 OS_REG_WRITE(ah, AR_TXOP_0_3, 0xFFFFFFFF); 4037 OS_REG_WRITE(ah, AR_TXOP_4_7, 0xFFFFFFFF); 4038 OS_REG_WRITE(ah, AR_TXOP_8_11, 0xFFFFFFFF); 4039 OS_REG_WRITE(ah, AR_TXOP_12_15, 0xFFFFFFFF); 4040} 4041 4042static inline void 4043ar9300_init_user_settings(struct ath_hal *ah) 4044{ 4045 struct ath_hal_9300 *ahp = AH9300(ah); 4046 4047 /* Restore user-specified settings */ 4048 HALDEBUG(ah, HAL_DEBUG_RESET, 4049 "--AP %s ahp->ah_misc_mode 0x%x\n", __func__, ahp->ah_misc_mode); 4050 if (ahp->ah_misc_mode != 0) { 4051 OS_REG_WRITE(ah, 4052 AR_PCU_MISC, OS_REG_READ(ah, AR_PCU_MISC) | ahp->ah_misc_mode); 4053 } 4054 if (ahp->ah_get_plcp_hdr) { 4055 OS_REG_CLR_BIT(ah, AR_PCU_MISC, AR_PCU_SEL_EVM); 4056 } 4057 if (ahp->ah_slot_time != (u_int) -1) { 4058 ar9300_set_slot_time(ah, ahp->ah_slot_time); 4059 } 4060 if (ahp->ah_ack_timeout != (u_int) -1) { 4061 ar9300_set_ack_timeout(ah, ahp->ah_ack_timeout); 4062 } 4063 if (AH_PRIVATE(ah)->ah_diagreg != 0) { 4064 OS_REG_SET_BIT(ah, AR_DIAG_SW, AH_PRIVATE(ah)->ah_diagreg); 4065 } 4066 if (ahp->ah_beacon_rssi_threshold != 0) { 4067 ar9300_set_hw_beacon_rssi_threshold(ah, ahp->ah_beacon_rssi_threshold); 4068 } 4069#ifdef ATH_SUPPORT_DFS 4070 if (ahp->ah_cac_quiet_enabled) { 4071 ar9300_cac_tx_quiet(ah, 1); 4072 } 4073#endif /* ATH_SUPPORT_DFS */ 4074} 4075 4076int 4077ar9300_get_spur_info(struct ath_hal * ah, int *enable, int len, u_int16_t *freq) 4078{ 4079// struct ath_hal_private *ap = AH_PRIVATE(ah); 4080 int i, j; 4081 4082 for (i = 0; i < len; i++) { 4083 freq[i] = 0; 4084 } 4085 4086 *enable = ah->ah_config.ath_hal_spur_mode; 4087 for (i = 0, j = 0; i < AR_EEPROM_MODAL_SPURS; i++) { 4088 if (AH9300(ah)->ath_hal_spur_chans[i][0] != AR_NO_SPUR) { 4089 freq[j++] = AH9300(ah)->ath_hal_spur_chans[i][0]; 4090 HALDEBUG(ah, HAL_DEBUG_ANI, 4091 "1. get spur %d\n", AH9300(ah)->ath_hal_spur_chans[i][0]); 4092 } 4093 if (AH9300(ah)->ath_hal_spur_chans[i][1] != AR_NO_SPUR) { 4094 freq[j++] = AH9300(ah)->ath_hal_spur_chans[i][1]; 4095 HALDEBUG(ah, HAL_DEBUG_ANI, 4096 "2. get spur %d\n", AH9300(ah)->ath_hal_spur_chans[i][1]); 4097 } 4098 } 4099 4100 return 0; 4101} 4102 4103#define ATH_HAL_2GHZ_FREQ_MIN 20000 4104#define ATH_HAL_2GHZ_FREQ_MAX 29999 4105#define ATH_HAL_5GHZ_FREQ_MIN 50000 4106#define ATH_HAL_5GHZ_FREQ_MAX 59999 4107 4108#if 0 4109int 4110ar9300_set_spur_info(struct ath_hal * ah, int enable, int len, u_int16_t *freq) 4111{ 4112 struct ath_hal_private *ap = AH_PRIVATE(ah); 4113 int i, j, k; 4114 4115 ap->ah_config.ath_hal_spur_mode = enable; 4116 4117 if (ap->ah_config.ath_hal_spur_mode == SPUR_ENABLE_IOCTL) { 4118 for (i = 0; i < AR_EEPROM_MODAL_SPURS; i++) { 4119 AH9300(ah)->ath_hal_spur_chans[i][0] = AR_NO_SPUR; 4120 AH9300(ah)->ath_hal_spur_chans[i][1] = AR_NO_SPUR; 4121 } 4122 for (i = 0, j = 0, k = 0; i < len; i++) { 4123 if (freq[i] > ATH_HAL_2GHZ_FREQ_MIN && 4124 freq[i] < ATH_HAL_2GHZ_FREQ_MAX) 4125 { 4126 /* 2GHz Spur */ 4127 if (j < AR_EEPROM_MODAL_SPURS) { 4128 AH9300(ah)->ath_hal_spur_chans[j++][1] = freq[i]; 4129 HALDEBUG(ah, HAL_DEBUG_ANI, "1 set spur %d\n", freq[i]); 4130 } 4131 } else if (freq[i] > ATH_HAL_5GHZ_FREQ_MIN && 4132 freq[i] < ATH_HAL_5GHZ_FREQ_MAX) 4133 { 4134 /* 5Ghz Spur */ 4135 if (k < AR_EEPROM_MODAL_SPURS) { 4136 AH9300(ah)->ath_hal_spur_chans[k++][0] = freq[i]; 4137 HALDEBUG(ah, HAL_DEBUG_ANI, "2 set spur %d\n", freq[i]); 4138 } 4139 } 4140 } 4141 } 4142 4143 return 0; 4144} 4145#endif 4146 4147#define ar9300_check_op_mode(_opmode) \ 4148 ((_opmode == HAL_M_STA) || (_opmode == HAL_M_IBSS) ||\ 4149 (_opmode == HAL_M_HOSTAP) || (_opmode == HAL_M_MONITOR)) 4150 4151 4152 4153 4154#ifndef ATH_NF_PER_CHAN 4155/* 4156* To fixed first reset noise floor value not correct issue 4157* For ART need it to fixed low rate sens too low issue 4158*/ 4159static int 4160First_NFCal(struct ath_hal *ah, HAL_CHANNEL_INTERNAL *ichan, 4161 int is_scan, struct ieee80211_channel *chan) 4162{ 4163 HAL_NFCAL_HIST_FULL *nfh; 4164 int i, j, k; 4165 int16_t nfarray[HAL_NUM_NF_READINGS] = {0}; 4166 int is_2g = 0; 4167 int nf_hist_len; 4168 int stats = 0; 4169 4170 int16_t nf_buf[HAL_NUM_NF_READINGS]; 4171#define IS(_c, _f) (((_c)->channel_flags & _f) || 0) 4172 4173 4174 if ((!is_scan) && 4175 chan->ic_freq == AH_PRIVATE(ah)->ah_curchan->ic_freq) 4176 { 4177 nfh = &AH_PRIVATE(ah)->nf_cal_hist; 4178 } else { 4179 nfh = (HAL_NFCAL_HIST_FULL *) &ichan->nf_cal_hist; 4180 } 4181 4182 ar9300_start_nf_cal(ah); 4183 for (j = 0; j < 10000; j++) { 4184 if ((OS_REG_READ(ah, AR_PHY_AGC_CONTROL) & AR_PHY_AGC_CONTROL_NF) == 0){ 4185 break; 4186 } 4187 OS_DELAY(10); 4188 } 4189 if (j < 10000) { 4190 is_2g = IEEE80211_IS_CHAN_2GHZ(chan); 4191 ar9300_upload_noise_floor(ah, is_2g, nfarray); 4192 4193 if (is_scan) { 4194 /* 4195 * This channel's NF cal info is just a HAL_NFCAL_HIST_SMALL struct 4196 * rather than a HAL_NFCAL_HIST_FULL struct. 4197 * As long as we only use the first history element of nf_cal_buffer 4198 * (nf_cal_buffer[0][0:HAL_NUM_NF_READINGS-1]), we can use 4199 * HAL_NFCAL_HIST_SMALL and HAL_NFCAL_HIST_FULL interchangeably. 4200 */ 4201 nfh = (HAL_NFCAL_HIST_FULL *) &ichan->nf_cal_hist; 4202 nf_hist_len = HAL_NF_CAL_HIST_LEN_SMALL; 4203 } else { 4204 nfh = &AH_PRIVATE(ah)->nf_cal_hist; 4205 nf_hist_len = HAL_NF_CAL_HIST_LEN_FULL; 4206 } 4207 4208 for (i = 0; i < HAL_NUM_NF_READINGS; i ++) { 4209 for (k = 0; k < HAL_NF_CAL_HIST_LEN_FULL; k++) { 4210 nfh->nf_cal_buffer[k][i] = nfarray[i]; 4211 } 4212 nfh->base.priv_nf[i] = ar9300_limit_nf_range(ah, 4213 ar9300_get_nf_hist_mid(ah, nfh, i, nf_hist_len)); 4214 } 4215 4216 4217 //ar9300StoreNewNf(ah, ichan, is_scan); 4218 4219 /* 4220 * See if the NF value from the old channel should be 4221 * retained when switching to a new channel. 4222 * TBD: this may need to be changed, as it wipes out the 4223 * purpose of saving NF values for each channel. 4224 */ 4225 for (i = 0; i < HAL_NUM_NF_READINGS; i++) 4226 { 4227 if (IEEE80211_IS_CHAN_2GHZ(chan)) 4228 { 4229 if (nfh->nf_cal_buffer[0][i] < 4230 AR_PHY_CCA_MAX_GOOD_VAL_OSPREY_2GHZ) 4231 { 4232 ichan->nf_cal_hist.nf_cal_buffer[0][i] = 4233 AH_PRIVATE(ah)->nf_cal_hist.nf_cal_buffer[0][i]; 4234 } 4235 } else { 4236 if (AR_SREV_AR9580(ah)) { 4237 if (nfh->nf_cal_buffer[0][i] < 4238 AR_PHY_CCA_NOM_VAL_PEACOCK_5GHZ) 4239 { 4240 ichan->nf_cal_hist.nf_cal_buffer[0][i] = 4241 AH_PRIVATE(ah)->nf_cal_hist.nf_cal_buffer[0][i]; 4242 } 4243 } else { 4244 if (nfh->nf_cal_buffer[0][i] < 4245 AR_PHY_CCA_NOM_VAL_OSPREY_5GHZ) 4246 { 4247 ichan->nf_cal_hist.nf_cal_buffer[0][i] = 4248 AH_PRIVATE(ah)->nf_cal_hist.nf_cal_buffer[0][i]; 4249 } 4250 } 4251 } 4252 } 4253 /* 4254 * Copy the channel's NF buffer, which may have been modified 4255 * just above here, to the full NF history buffer. 4256 */ 4257 ar9300_reset_nf_hist_buff(ah, ichan); 4258 ar9300_get_nf_hist_base(ah, ichan, is_scan, nf_buf); 4259 ar9300_load_nf(ah, nf_buf); 4260 stats = 0; 4261 } else { 4262 stats = 1; 4263 } 4264#undef IS 4265 return stats; 4266} 4267#endif 4268 4269 4270/* 4271 * Places the device in and out of reset and then places sane 4272 * values in the registers based on EEPROM config, initialization 4273 * vectors (as determined by the mode), and station configuration 4274 * 4275 * b_channel_change is used to preserve DMA/PCU registers across 4276 * a HW Reset during channel change. 4277 */ 4278HAL_BOOL 4279ar9300_reset(struct ath_hal *ah, HAL_OPMODE opmode, struct ieee80211_channel *chan, 4280 HAL_HT_MACMODE macmode, u_int8_t txchainmask, u_int8_t rxchainmask, 4281 HAL_HT_EXTPROTSPACING extprotspacing, HAL_BOOL b_channel_change, 4282 HAL_STATUS *status, int is_scan) 4283{ 4284#define FAIL(_code) do { ecode = _code; goto bad; } while (0) 4285 u_int32_t save_led_state; 4286 struct ath_hal_9300 *ahp = AH9300(ah); 4287 struct ath_hal_private *ap = AH_PRIVATE(ah); 4288 HAL_CHANNEL_INTERNAL *ichan; 4289 //const struct ieee80211_channel *curchan = ap->ah_curchan; 4290#if ATH_SUPPORT_MCI 4291 HAL_BOOL save_full_sleep = ahp->ah_chip_full_sleep; 4292#endif 4293 u_int32_t save_def_antenna; 4294 u_int32_t mac_sta_id1; 4295 HAL_STATUS ecode; 4296 int i, rx_chainmask; 4297 int nf_hist_buff_reset = 0; 4298 int16_t nf_buf[HAL_NUM_NF_READINGS]; 4299#ifdef ATH_FORCE_PPM 4300 u_int32_t save_force_val, tmp_reg; 4301#endif 4302 HAL_BOOL stopped, cal_ret; 4303 HAL_BOOL apply_last_iqcorr = AH_FALSE; 4304 4305 if (OS_REG_READ(ah, AR_IER) == AR_IER_ENABLE) { 4306 HALDEBUG(AH_NULL, HAL_DEBUG_UNMASKABLE, "** Reset called with WLAN " 4307 "interrupt enabled %08x **\n", ar9300_get_interrupts(ah)); 4308 } 4309 4310 /* 4311 * Set the status to "ok" by default to cover the cases 4312 * where we return AH_FALSE without going to "bad" 4313 */ 4314 HALASSERT(status); 4315 *status = HAL_OK; 4316 if ((ah->ah_config.ath_hal_sta_update_tx_pwr_enable)) { 4317 AH9300(ah)->green_tx_status = HAL_RSSI_TX_POWER_NONE; 4318 } 4319 4320#if ATH_SUPPORT_MCI 4321 if (AH_PRIVATE(ah)->ah_caps.halMciSupport && 4322 (AR_SREV_JUPITER_20(ah) || AR_SREV_APHRODITE(ah))) 4323 { 4324 ar9300_mci_2g5g_changed(ah, IEEE80211_IS_CHAN_2GHZ(chan)); 4325 } 4326#endif 4327 4328 ahp->ah_ext_prot_spacing = extprotspacing; 4329 ahp->ah_tx_chainmask = txchainmask & ap->ah_caps.halTxChainMask; 4330 ahp->ah_rx_chainmask = rxchainmask & ap->ah_caps.halRxChainMask; 4331 ahp->ah_tx_cal_chainmask = ap->ah_caps.halTxChainMask; 4332 ahp->ah_rx_cal_chainmask = ap->ah_caps.halRxChainMask; 4333 HALASSERT(ar9300_check_op_mode(opmode)); 4334 4335 OS_MARK(ah, AH_MARK_RESET, b_channel_change); 4336 4337 /* 4338 * Map public channel to private. 4339 */ 4340 ichan = ar9300_check_chan(ah, chan); 4341 if (ichan == AH_NULL) { 4342 HALDEBUG(ah, HAL_DEBUG_CHANNEL, 4343 "%s: invalid channel %u/0x%x; no mapping\n", 4344 __func__, chan->ic_freq, chan->ic_flags); 4345 FAIL(HAL_EINVAL); 4346 } 4347 4348 ichan->paprd_table_write_done = 0; /* Clear PAPRD table write flag */ 4349#if 0 4350 chan->paprd_table_write_done = 0; /* Clear PAPRD table write flag */ 4351#endif 4352 4353 if (ar9300_get_power_mode(ah) != HAL_PM_FULL_SLEEP) { 4354 /* Need to stop RX DMA before reset otherwise chip might hang */ 4355 stopped = ar9300_set_rx_abort(ah, AH_TRUE); /* abort and disable PCU */ 4356 ar9300_set_rx_filter(ah, 0); 4357 stopped &= ar9300_stop_dma_receive(ah, 0); /* stop and disable RX DMA */ 4358 if (!stopped) { 4359 /* 4360 * During the transition from full sleep to reset, 4361 * recv DMA regs are not available to be read 4362 */ 4363 HALDEBUG(ah, HAL_DEBUG_UNMASKABLE, 4364 "%s[%d]: ar9300_stop_dma_receive failed\n", __func__, __LINE__); 4365 b_channel_change = AH_FALSE; 4366 } 4367 } else { 4368 HALDEBUG(ah, HAL_DEBUG_UNMASKABLE, 4369 "%s[%d]: Chip is already in full sleep\n", __func__, __LINE__); 4370 } 4371 4372#if ATH_SUPPORT_MCI 4373 if ((AH_PRIVATE(ah)->ah_caps.halMciSupport) && 4374 (ahp->ah_mci_bt_state == MCI_BT_CAL_START)) 4375 { 4376 u_int32_t payload[4] = {0, 0, 0, 0}; 4377 4378 HALDEBUG(ah, HAL_DEBUG_BT_COEX, 4379 "(MCI) %s: Stop rx for BT cal.\n", __func__); 4380 ahp->ah_mci_bt_state = MCI_BT_CAL; 4381 4382 /* 4383 * MCIFIX: disable mci interrupt here. This is to avoid SW_MSG_DONE or 4384 * RX_MSG bits to trigger MCI_INT and lead to mci_intr reentry. 4385 */ 4386 ar9300_mci_disable_interrupt(ah); 4387 4388 HALDEBUG(ah, HAL_DEBUG_BT_COEX, 4389 "(MCI) %s: Send WLAN_CAL_GRANT\n", __func__); 4390 MCI_GPM_SET_CAL_TYPE(payload, MCI_GPM_WLAN_CAL_GRANT); 4391 ar9300_mci_send_message(ah, MCI_GPM, 0, payload, 16, AH_TRUE, AH_FALSE); 4392 4393 /* Wait BT calibration to be completed for 25ms */ 4394 HALDEBUG(ah, HAL_DEBUG_BT_COEX, 4395 "(MCI) %s: BT is calibrating.\n", __func__); 4396 if (ar9300_mci_wait_for_gpm(ah, MCI_GPM_BT_CAL_DONE, 0, 25000)) { 4397 HALDEBUG(ah, HAL_DEBUG_BT_COEX, 4398 "(MCI) %s: Got BT_CAL_DONE.\n", __func__); 4399 } 4400 else { 4401 HALDEBUG(ah, HAL_DEBUG_BT_COEX, 4402 "(MCI) %s: ### BT cal takes too long. Force bt_state to be bt_awake.\n", 4403 __func__); 4404 } 4405 ahp->ah_mci_bt_state = MCI_BT_AWAKE; 4406 /* MCIFIX: enable mci interrupt here */ 4407 ar9300_mci_enable_interrupt(ah); 4408 4409 return AH_TRUE; 4410 } 4411#endif 4412 4413 /* Bring out of sleep mode */ 4414 if (!ar9300_set_power_mode(ah, HAL_PM_AWAKE, AH_TRUE)) { 4415 *status = HAL_INV_PMODE; 4416 return AH_FALSE; 4417 } 4418 4419 /* Check the Rx mitigation config again, it might have changed 4420 * during attach in ath_vap_attach. 4421 */ 4422 if (ah->ah_config.ath_hal_intr_mitigation_rx != 0) { 4423 ahp->ah_intr_mitigation_rx = AH_TRUE; 4424 } else { 4425 ahp->ah_intr_mitigation_rx = AH_FALSE; 4426 } 4427 4428 /* 4429 * XXX TODO FreeBSD: 4430 * 4431 * This is painful because we don't have a non-const channel pointer 4432 * at this stage. 4433 * 4434 * Make sure this gets fixed! 4435 */ 4436#if 0 4437 /* Get the value from the previous NF cal and update history buffer */ 4438 if (curchan && (ahp->ah_chip_full_sleep != AH_TRUE)) { 4439 ar9300_store_new_nf(ah, curchan, is_scan); 4440 } 4441#endif 4442 4443 /* 4444 * Account for the effect of being in either the 2 GHz or 5 GHz band 4445 * on the nominal, max allowable, and min allowable noise floor values. 4446 */ 4447 AH9300(ah)->nfp = IS_CHAN_2GHZ(ichan) ? &ahp->nf_2GHz : &ahp->nf_5GHz; 4448 4449 /* 4450 * XXX For now, don't apply the last IQ correction. 4451 * 4452 * This should be done when scorpion is enabled on FreeBSD; just be 4453 * sure to fix this channel match code so it uses net80211 flags 4454 * instead. 4455 */ 4456#if 0 4457 if (AR_SREV_SCORPION(ah) && curchan && (chan->channel == curchan->channel) && 4458 ((chan->channel_flags & (CHANNEL_ALL|CHANNEL_HALF|CHANNEL_QUARTER)) == 4459 (curchan->channel_flags & 4460 (CHANNEL_ALL | CHANNEL_HALF | CHANNEL_QUARTER)))) { 4461 apply_last_iqcorr = AH_TRUE; 4462 } 4463#endif 4464 apply_last_iqcorr = AH_FALSE; 4465 4466 4467#ifndef ATH_NF_PER_CHAN 4468 /* 4469 * If there's only one full-size home-channel NF history buffer 4470 * rather than a full-size NF history buffer per channel, decide 4471 * whether to (re)initialize the home-channel NF buffer. 4472 * If this is just a channel change for a scan, or if the channel 4473 * is not being changed, don't mess up the home channel NF history 4474 * buffer with NF values from this scanned channel. If we're 4475 * changing the home channel to a new channel, reset the home-channel 4476 * NF history buffer with the most accurate NF known for the new channel. 4477 */ 4478 if (!is_scan && (!ap->ah_curchan || 4479 ap->ah_curchan->ic_freq != chan->ic_freq)) // || 4480// ap->ah_curchan->channel_flags != chan->channel_flags)) 4481 { 4482 nf_hist_buff_reset = 1; 4483 ar9300_reset_nf_hist_buff(ah, ichan); 4484 } 4485#endif 4486 /* 4487 * Fast channel change (Change synthesizer based on channel freq 4488 * without resetting chip) 4489 * Don't do it when 4490 * - Flag is not set 4491 * - Chip is just coming out of full sleep 4492 * - Channel to be set is same as current channel 4493 * - Channel flags are different, like when moving from 2GHz to 5GHz 4494 * channels 4495 * - Merlin: Switching in/out of fast clock enabled channels 4496 * (not currently coded, since fast clock is enabled 4497 * across the 5GHz band 4498 * and we already do a full reset when switching in/out 4499 * of 5GHz channels) 4500 */ 4501#if 0 4502 if (b_channel_change && 4503 (ahp->ah_chip_full_sleep != AH_TRUE) && 4504 (AH_PRIVATE(ah)->ah_curchan != AH_NULL) && 4505 ((chan->channel != AH_PRIVATE(ah)->ah_curchan->channel) && 4506 (((CHANNEL_ALL|CHANNEL_HALF|CHANNEL_QUARTER) & chan->channel_flags) == 4507 ((CHANNEL_ALL|CHANNEL_HALF|CHANNEL_QUARTER) & AH_PRIVATE(ah)->ah_curchan->channel_flags)))) 4508 { 4509 if (ar9300_channel_change(ah, chan, ichan, macmode)) { 4510 chan->channel_flags = ichan->channel_flags; 4511 chan->priv_flags = ichan->priv_flags; 4512 AH_PRIVATE(ah)->ah_curchan->ah_channel_time = 0; 4513 AH_PRIVATE(ah)->ah_curchan->ah_tsf_last = ar9300_get_tsf64(ah); 4514 4515 /* 4516 * Load the NF from history buffer of the current channel. 4517 * NF is slow time-variant, so it is OK to use a historical value. 4518 */ 4519 ar9300_get_nf_hist_base(ah, 4520 AH_PRIVATE(ah)->ah_curchan, is_scan, nf_buf); 4521 ar9300_load_nf(ah, nf_buf); 4522 4523 /* start NF calibration, without updating BB NF register*/ 4524 ar9300_start_nf_cal(ah); 4525 4526 /* 4527 * If channel_change completed and DMA was stopped 4528 * successfully - skip the rest of reset 4529 */ 4530 if (AH9300(ah)->ah_dma_stuck != AH_TRUE) { 4531 WAR_USB_DISABLE_PLL_LOCK_DETECT(ah); 4532#if ATH_SUPPORT_MCI 4533 if (AH_PRIVATE(ah)->ah_caps.halMciSupport && ahp->ah_mci_ready) 4534 { 4535 ar9300_mci_2g5g_switch(ah, AH_TRUE); 4536 } 4537#endif 4538 return HAL_OK; 4539 } 4540 } 4541 } 4542#endif /* #if 0 */ 4543 4544#if ATH_SUPPORT_MCI 4545 if (AH_PRIVATE(ah)->ah_caps.halMciSupport) { 4546 ar9300_mci_disable_interrupt(ah); 4547 if (ahp->ah_mci_ready && !save_full_sleep) { 4548 ar9300_mci_mute_bt(ah); 4549 OS_DELAY(20); 4550 OS_REG_WRITE(ah, AR_BTCOEX_CTRL, 0); 4551 } 4552 4553 ahp->ah_mci_bt_state = MCI_BT_SLEEP; 4554 ahp->ah_mci_ready = AH_FALSE; 4555 } 4556#endif 4557 4558 AH9300(ah)->ah_dma_stuck = AH_FALSE; 4559#ifdef ATH_FORCE_PPM 4560 /* Preserve force ppm state */ 4561 save_force_val = 4562 OS_REG_READ(ah, AR_PHY_TIMING2) & 4563 (AR_PHY_TIMING2_USE_FORCE | AR_PHY_TIMING2_FORCE_VAL); 4564#endif 4565 /* 4566 * Preserve the antenna on a channel change 4567 */ 4568 save_def_antenna = OS_REG_READ(ah, AR_DEF_ANTENNA); 4569 if (0 == ahp->ah_smartantenna_enable ) 4570 { 4571 if (save_def_antenna == 0) { 4572 save_def_antenna = 1; 4573 } 4574 } 4575 4576 /* Save hardware flag before chip reset clears the register */ 4577 mac_sta_id1 = OS_REG_READ(ah, AR_STA_ID1) & AR_STA_ID1_BASE_RATE_11B; 4578 4579 /* Save led state from pci config register */ 4580 save_led_state = OS_REG_READ(ah, AR_CFG_LED) & 4581 (AR_CFG_LED_ASSOC_CTL | AR_CFG_LED_MODE_SEL | 4582 AR_CFG_LED_BLINK_THRESH_SEL | AR_CFG_LED_BLINK_SLOW); 4583 4584 /* Mark PHY inactive prior to reset, to be undone in ar9300_init_bb () */ 4585 ar9300_mark_phy_inactive(ah); 4586 4587 if (!ar9300_chip_reset(ah, chan)) { 4588 HALDEBUG(ah, HAL_DEBUG_RESET, "%s: chip reset failed\n", __func__); 4589 FAIL(HAL_EIO); 4590 } 4591 4592 OS_MARK(ah, AH_MARK_RESET_LINE, __LINE__); 4593 4594 4595 /* Disable JTAG */ 4596 OS_REG_SET_BIT(ah, 4597 AR_HOSTIF_REG(ah, AR_GPIO_INPUT_EN_VAL), AR_GPIO_JTAG_DISABLE); 4598 4599 /* 4600 * Note that ar9300_init_chain_masks() is called from within 4601 * ar9300_process_ini() to ensure the swap bit is set before 4602 * the pdadc table is written. 4603 */ 4604 ecode = ar9300_process_ini(ah, chan, ichan, macmode); 4605 if (ecode != HAL_OK) { 4606 goto bad; 4607 } 4608 4609 ahp->ah_immunity_on = AH_FALSE; 4610 4611 if (AR_SREV_JUPITER(ah) || AR_SREV_APHRODITE(ah)) { 4612 ahp->tx_iq_cal_enable = OS_REG_READ_FIELD(ah, 4613 AR_PHY_TX_IQCAL_CONTROL_0(ah), 4614 AR_PHY_TX_IQCAL_CONTROL_0_ENABLE_TXIQ_CAL) ? 4615 1 : 0; 4616 } 4617 ahp->tx_cl_cal_enable = (OS_REG_READ(ah, AR_PHY_CL_CAL_CTL) & 4618 AR_PHY_CL_CAL_ENABLE) ? 1 : 0; 4619 4620 /* For devices with full HW RIFS Rx support (Sowl/Howl/Merlin, etc), 4621 * restore register settings from prior to reset. 4622 */ 4623 if ((AH_PRIVATE(ah)->ah_curchan != AH_NULL) && 4624 (ar9300_get_capability(ah, HAL_CAP_LDPCWAR, 0, AH_NULL) == HAL_OK)) 4625 { 4626 /* Re-program RIFS Rx policy after reset */ 4627 ar9300_set_rifs_delay(ah, ahp->ah_rifs_enabled); 4628 } 4629 4630#if ATH_SUPPORT_MCI 4631 if (AH_PRIVATE(ah)->ah_caps.halMciSupport) { 4632 ar9300_mci_reset(ah, AH_FALSE, IS_CHAN_2GHZ(ichan), save_full_sleep); 4633 } 4634#endif 4635 4636 /* Initialize Management Frame Protection */ 4637 ar9300_init_mfp(ah); 4638 4639 ahp->ah_immunity_vals[0] = OS_REG_READ_FIELD(ah, AR_PHY_SFCORR_LOW, 4640 AR_PHY_SFCORR_LOW_M1_THRESH_LOW); 4641 ahp->ah_immunity_vals[1] = OS_REG_READ_FIELD(ah, AR_PHY_SFCORR_LOW, 4642 AR_PHY_SFCORR_LOW_M2_THRESH_LOW); 4643 ahp->ah_immunity_vals[2] = OS_REG_READ_FIELD(ah, AR_PHY_SFCORR, 4644 AR_PHY_SFCORR_M1_THRESH); 4645 ahp->ah_immunity_vals[3] = OS_REG_READ_FIELD(ah, AR_PHY_SFCORR, 4646 AR_PHY_SFCORR_M2_THRESH); 4647 ahp->ah_immunity_vals[4] = OS_REG_READ_FIELD(ah, AR_PHY_SFCORR, 4648 AR_PHY_SFCORR_M2COUNT_THR); 4649 ahp->ah_immunity_vals[5] = OS_REG_READ_FIELD(ah, AR_PHY_SFCORR_LOW, 4650 AR_PHY_SFCORR_LOW_M2COUNT_THR_LOW); 4651 4652 /* Write delta slope for OFDM enabled modes (A, G, Turbo) */ 4653 if (IEEE80211_IS_CHAN_OFDM(chan) || IEEE80211_IS_CHAN_HT(chan)) { 4654 ar9300_set_delta_slope(ah, chan); 4655 } 4656 4657 ar9300_spur_mitigate(ah, chan); 4658 if (!ar9300_eeprom_set_board_values(ah, chan)) { 4659 HALDEBUG(ah, HAL_DEBUG_EEPROM, 4660 "%s: error setting board options\n", __func__); 4661 FAIL(HAL_EIO); 4662 } 4663 4664#ifdef ATH_HAL_WAR_REG16284_APH128 4665 /* temp work around, will be removed. */ 4666 if (AR_SREV_WASP(ah)) { 4667 OS_REG_WRITE(ah, 0x16284, 0x1553e000); 4668 } 4669#endif 4670 4671 OS_MARK(ah, AH_MARK_RESET_LINE, __LINE__); 4672 4673 OS_REG_WRITE(ah, AR_STA_ID0, LE_READ_4(ahp->ah_macaddr)); 4674 OS_REG_WRITE(ah, AR_STA_ID1, LE_READ_2(ahp->ah_macaddr + 4) 4675 | mac_sta_id1 4676 | AR_STA_ID1_RTS_USE_DEF 4677 | (ah->ah_config.ath_hal_6mb_ack ? AR_STA_ID1_ACKCTS_6MB : 0) 4678 | ahp->ah_sta_id1_defaults 4679 ); 4680 ar9300_set_operating_mode(ah, opmode); 4681 4682 /* Set Venice BSSID mask according to current state */ 4683 OS_REG_WRITE(ah, AR_BSSMSKL, LE_READ_4(ahp->ah_bssid_mask)); 4684 OS_REG_WRITE(ah, AR_BSSMSKU, LE_READ_2(ahp->ah_bssid_mask + 4)); 4685 4686 /* Restore previous antenna */ 4687 OS_REG_WRITE(ah, AR_DEF_ANTENNA, save_def_antenna); 4688#ifdef ATH_FORCE_PPM 4689 /* Restore force ppm state */ 4690 tmp_reg = OS_REG_READ(ah, AR_PHY_TIMING2) & 4691 ~(AR_PHY_TIMING2_USE_FORCE | AR_PHY_TIMING2_FORCE_VAL); 4692 OS_REG_WRITE(ah, AR_PHY_TIMING2, tmp_reg | save_force_val); 4693#endif 4694 4695 /* then our BSSID and assocID */ 4696 OS_REG_WRITE(ah, AR_BSS_ID0, LE_READ_4(ahp->ah_bssid)); 4697 OS_REG_WRITE(ah, AR_BSS_ID1, 4698 LE_READ_2(ahp->ah_bssid + 4) | 4699 ((ahp->ah_assoc_id & 0x3fff) << AR_BSS_ID1_AID_S)); 4700 4701 OS_REG_WRITE(ah, AR_ISR, ~0); /* cleared on write */ 4702 4703 OS_REG_RMW_FIELD(ah, AR_RSSI_THR, AR_RSSI_THR_BM_THR, INIT_RSSI_THR); 4704 4705 /* HW beacon processing */ 4706 /* 4707 * XXX what happens if I just leave filter_interval=0? 4708 * it stays disabled? 4709 */ 4710 OS_REG_RMW_FIELD(ah, AR_RSSI_THR, AR_RSSI_BCN_WEIGHT, 4711 INIT_RSSI_BEACON_WEIGHT); 4712 OS_REG_SET_BIT(ah, AR_HWBCNPROC1, AR_HWBCNPROC1_CRC_ENABLE | 4713 AR_HWBCNPROC1_EXCLUDE_TIM_ELM); 4714 if (ah->ah_config.ath_hal_beacon_filter_interval) { 4715 OS_REG_RMW_FIELD(ah, AR_HWBCNPROC2, AR_HWBCNPROC2_FILTER_INTERVAL, 4716 ah->ah_config.ath_hal_beacon_filter_interval); 4717 OS_REG_SET_BIT(ah, AR_HWBCNPROC2, 4718 AR_HWBCNPROC2_FILTER_INTERVAL_ENABLE); 4719 } 4720 4721 4722 /* 4723 * Set Channel now modifies bank 6 parameters for FOWL workaround 4724 * to force rf_pwd_icsyndiv bias current as function of synth 4725 * frequency.Thus must be called after ar9300_process_ini() to ensure 4726 * analog register cache is valid. 4727 */ 4728 if (!ahp->ah_rf_hal.set_channel(ah, chan)) { 4729 FAIL(HAL_EIO); 4730 } 4731 4732 4733 OS_MARK(ah, AH_MARK_RESET_LINE, __LINE__); 4734 4735 /* Set 1:1 QCU to DCU mapping for all queues */ 4736 for (i = 0; i < AR_NUM_DCU; i++) { 4737 OS_REG_WRITE(ah, AR_DQCUMASK(i), 1 << i); 4738 } 4739 4740 ahp->ah_intr_txqs = 0; 4741 for (i = 0; i < AH_PRIVATE(ah)->ah_caps.halTotalQueues; i++) { 4742 ar9300_reset_tx_queue(ah, i); 4743 } 4744 4745 ar9300_init_interrupt_masks(ah, opmode); 4746 4747 /* Reset ier reference count to disabled */ 4748// OS_ATOMIC_SET(&ahp->ah_ier_ref_count, 1); 4749 if (ath_hal_isrfkillenabled(ah)) { 4750 ar9300_enable_rf_kill(ah); 4751 } 4752 4753 /* must be called AFTER ini is processed */ 4754 ar9300_ani_init_defaults(ah, macmode); 4755 4756 ar9300_init_qos(ah); 4757 4758 ar9300_init_user_settings(ah); 4759 4760 4761 AH_PRIVATE(ah)->ah_opmode = opmode; /* record operating mode */ 4762 4763 OS_MARK(ah, AH_MARK_RESET_DONE, 0); 4764 4765 /* 4766 * disable seq number generation in hw 4767 */ 4768 OS_REG_WRITE(ah, AR_STA_ID1, 4769 OS_REG_READ(ah, AR_STA_ID1) | AR_STA_ID1_PRESERVE_SEQNUM); 4770 4771 ar9300_set_dma(ah); 4772 4773 /* 4774 * program OBS bus to see MAC interrupts 4775 */ 4776#if ATH_SUPPORT_MCI 4777 if (!AH_PRIVATE(ah)->ah_caps.halMciSupport) { 4778 OS_REG_WRITE(ah, AR_HOSTIF_REG(ah, AR_OBS), 8); 4779 } 4780#else 4781 OS_REG_WRITE(ah, AR_HOSTIF_REG(ah, AR_OBS), 8); 4782#endif 4783 4784 4785 /* enabling AR_GTTM_IGNORE_IDLE in GTTM register so that 4786 GTT timer will not increment if the channel idle indicates 4787 the air is busy or NAV is still counting down */ 4788 OS_REG_WRITE(ah, AR_GTTM, AR_GTTM_IGNORE_IDLE); 4789 4790 /* 4791 * GTT debug mode setting 4792 */ 4793 /* 4794 OS_REG_WRITE(ah, 0x64, 0x00320000); 4795 OS_REG_WRITE(ah, 0x68, 7); 4796 OS_REG_WRITE(ah, 0x4080, 0xC); 4797 */ 4798 /* 4799 * Disable general interrupt mitigation by setting MIRT = 0x0 4800 * Rx and tx interrupt mitigation are conditionally enabled below. 4801 */ 4802 OS_REG_WRITE(ah, AR_MIRT, 0); 4803 if (ahp->ah_intr_mitigation_rx) { 4804 /* 4805 * Enable Interrupt Mitigation for Rx. 4806 * If no build-specific limits for the rx interrupt mitigation 4807 * timer have been specified, use conservative defaults. 4808 */ 4809 #ifndef AH_RIMT_VAL_LAST 4810 #define AH_RIMT_LAST_MICROSEC 500 4811 #endif 4812 #ifndef AH_RIMT_VAL_FIRST 4813 #define AH_RIMT_FIRST_MICROSEC 2000 4814 #endif 4815#ifndef HOST_OFFLOAD 4816 OS_REG_RMW_FIELD(ah, AR_RIMT, AR_RIMT_LAST, AH_RIMT_LAST_MICROSEC); 4817 OS_REG_RMW_FIELD(ah, AR_RIMT, AR_RIMT_FIRST, AH_RIMT_FIRST_MICROSEC); 4818#else 4819 /* lower mitigation level to reduce latency for offload arch. */ 4820 OS_REG_RMW_FIELD(ah, AR_RIMT, AR_RIMT_LAST, 4821 (AH_RIMT_LAST_MICROSEC >> 2)); 4822 OS_REG_RMW_FIELD(ah, AR_RIMT, AR_RIMT_FIRST, 4823 (AH_RIMT_FIRST_MICROSEC >> 2)); 4824#endif 4825 } 4826 4827 if (ahp->ah_intr_mitigation_tx) { 4828 /* 4829 * Enable Interrupt Mitigation for Tx. 4830 * If no build-specific limits for the tx interrupt mitigation 4831 * timer have been specified, use the values preferred for 4832 * the carrier group's products. 4833 */ 4834 #ifndef AH_TIMT_LAST 4835 #define AH_TIMT_LAST_MICROSEC 300 4836 #endif 4837 #ifndef AH_TIMT_FIRST 4838 #define AH_TIMT_FIRST_MICROSEC 750 4839 #endif 4840 OS_REG_RMW_FIELD(ah, AR_TIMT, AR_TIMT_LAST, AH_TIMT_LAST_MICROSEC); 4841 OS_REG_RMW_FIELD(ah, AR_TIMT, AR_TIMT_FIRST, AH_TIMT_FIRST_MICROSEC); 4842 } 4843 4844 rx_chainmask = ahp->ah_rx_chainmask; 4845 4846 OS_REG_WRITE(ah, AR_PHY_RX_CHAINMASK, rx_chainmask); 4847 OS_REG_WRITE(ah, AR_PHY_CAL_CHAINMASK, rx_chainmask); 4848 4849 ar9300_init_bb(ah, chan); 4850 4851 /* BB Step 7: Calibration */ 4852 ar9300_invalidate_saved_cals(ah, ichan); 4853 cal_ret = ar9300_init_cal(ah, chan, AH_FALSE, apply_last_iqcorr); 4854 4855#if ATH_SUPPORT_MCI 4856 if (AH_PRIVATE(ah)->ah_caps.halMciSupport && ahp->ah_mci_ready) { 4857 if (IS_CHAN_2GHZ(ichan) && 4858 (ahp->ah_mci_bt_state == MCI_BT_SLEEP)) 4859 { 4860 if (ar9300_mci_check_int(ah, AR_MCI_INTERRUPT_RX_MSG_REMOTE_RESET) || 4861 ar9300_mci_check_int(ah, AR_MCI_INTERRUPT_RX_MSG_REQ_WAKE)) 4862 { 4863 /* 4864 * BT is sleeping. Check if BT wakes up duing WLAN 4865 * calibration. If BT wakes up during WLAN calibration, need 4866 * to go through all message exchanges again and recal. 4867 */ 4868 HALDEBUG(ah, HAL_DEBUG_BT_COEX, 4869 "(MCI) ### %s: BT wakes up during WLAN calibration.\n", 4870 __func__); 4871 OS_REG_WRITE(ah, AR_MCI_INTERRUPT_RX_MSG_RAW, 4872 AR_MCI_INTERRUPT_RX_MSG_REMOTE_RESET | 4873 AR_MCI_INTERRUPT_RX_MSG_REQ_WAKE); 4874 HALDEBUG(ah, HAL_DEBUG_BT_COEX, "(MCI) send REMOTE_RESET\n"); 4875 ar9300_mci_remote_reset(ah, AH_TRUE); 4876 ar9300_mci_send_sys_waking(ah, AH_TRUE); 4877 OS_DELAY(1); 4878 if (IS_CHAN_2GHZ(ichan)) { 4879 ar9300_mci_send_lna_transfer(ah, AH_TRUE); 4880 } 4881 ahp->ah_mci_bt_state = MCI_BT_AWAKE; 4882 4883 /* Redo calibration */ 4884 HALDEBUG(ah, HAL_DEBUG_BT_COEX, "(MCI) %s: Re-calibrate.\n", 4885 __func__); 4886 ar9300_invalidate_saved_cals(ah, ichan); 4887 cal_ret = ar9300_init_cal(ah, chan, AH_FALSE, apply_last_iqcorr); 4888 } 4889 } 4890 ar9300_mci_enable_interrupt(ah); 4891 } 4892#endif 4893 4894 if (!cal_ret) { 4895 HALDEBUG(ah, HAL_DEBUG_RESET, "%s: Init Cal Failed\n", __func__); 4896 FAIL(HAL_ESELFTEST); 4897 } 4898 4899 ar9300_init_txbf(ah); 4900#if 0 4901 /* 4902 * WAR for owl 1.0 - restore chain mask for 2-chain cfgs after cal 4903 */ 4904 rx_chainmask = ahp->ah_rx_chainmask; 4905 if ((rx_chainmask == 0x5) || (rx_chainmask == 0x3)) { 4906 OS_REG_WRITE(ah, AR_PHY_RX_CHAINMASK, rx_chainmask); 4907 OS_REG_WRITE(ah, AR_PHY_CAL_CHAINMASK, rx_chainmask); 4908 } 4909#endif 4910 4911 /* Restore previous led state */ 4912 OS_REG_WRITE(ah, AR_CFG_LED, save_led_state | AR_CFG_SCLK_32KHZ); 4913 4914#if ATH_BT_COEX 4915 if (ahp->ah_bt_coex_config_type != HAL_BT_COEX_CFG_NONE) { 4916 ar9300_init_bt_coex(ah); 4917 4918#if ATH_SUPPORT_MCI 4919 if (AH_PRIVATE(ah)->ah_caps.halMciSupport && ahp->ah_mci_ready) { 4920 /* Check BT state again to make sure it's not changed. */ 4921 ar9300_mci_sync_bt_state(ah); 4922 ar9300_mci_2g5g_switch(ah, AH_TRUE); 4923 4924 if ((ahp->ah_mci_bt_state == MCI_BT_AWAKE) && 4925 (ahp->ah_mci_query_bt == AH_TRUE)) 4926 { 4927 ahp->ah_mci_need_flush_btinfo = AH_TRUE; 4928 } 4929 } 4930#endif 4931 } 4932#endif 4933 4934 /* Start TSF2 for generic timer 8-15. */ 4935 ar9300_start_tsf2(ah); 4936 4937 /* MIMO Power save setting */ 4938 if (ar9300_get_capability(ah, HAL_CAP_DYNAMIC_SMPS, 0, AH_NULL) == HAL_OK) { 4939 ar9300_set_sm_power_mode(ah, ahp->ah_sm_power_mode); 4940 } 4941 4942 /* 4943 * For big endian systems turn on swapping for descriptors 4944 */ 4945#if AH_BYTE_ORDER == AH_BIG_ENDIAN 4946 if (AR_SREV_HORNET(ah) || AR_SREV_WASP(ah) || AR_SREV_SCORPION(ah)) { 4947 OS_REG_RMW(ah, AR_CFG, AR_CFG_SWTB | AR_CFG_SWRB, 0); 4948 } else { 4949 ar9300_init_cfg_reg(ah); 4950 } 4951#endif 4952 4953 if ( AR_SREV_OSPREY(ah) || AR_SREV_WASP(ah) || AR_SREV_SCORPION(ah)) { 4954 OS_REG_RMW(ah, AR_CFG_LED, AR_CFG_LED_ASSOC_CTL, AR_CFG_LED_ASSOC_CTL); 4955 } 4956 4957#if !(defined(ART_BUILD)) && defined(ATH_SUPPORT_LED) 4958#define REG_WRITE(_reg, _val) *((volatile u_int32_t *)(_reg)) = (_val); 4959#define REG_READ(_reg) *((volatile u_int32_t *)(_reg)) 4960#define ATH_GPIO_OUT_FUNCTION3 0xB8040038 4961#define ATH_GPIO_OE 0xB8040000 4962 if ( AR_SREV_WASP(ah)) { 4963 if (IS_CHAN_2GHZ((AH_PRIVATE(ah)->ah_curchan))) { 4964 REG_WRITE(ATH_GPIO_OUT_FUNCTION3, ( REG_READ(ATH_GPIO_OUT_FUNCTION3) & (~(0xff << 8))) | (0x33 << 8) ); 4965 REG_WRITE(ATH_GPIO_OE, ( REG_READ(ATH_GPIO_OE) & (~(0x1 << 13) ))); 4966 } 4967 else { 4968 4969 /* Disable 2G WLAN LED. During ath_open, reset function is called even before channel is set. 4970 So 2GHz is taken as default and it also blinks. Hence 4971 to avoid both from blinking, disable 2G led while in 5G mode */ 4972 4973 REG_WRITE(ATH_GPIO_OE, ( REG_READ(ATH_GPIO_OE) | (1 << 13) )); 4974 REG_WRITE(ATH_GPIO_OUT_FUNCTION3, ( REG_READ(ATH_GPIO_OUT_FUNCTION3) & (~(0xff))) | (0x33) ); 4975 REG_WRITE(ATH_GPIO_OE, ( REG_READ(ATH_GPIO_OE) & (~(0x1 << 12) ))); 4976 } 4977 4978 } 4979 else if (AR_SREV_SCORPION(ah)) { 4980 if (IS_CHAN_2GHZ((AH_PRIVATE(ah)->ah_curchan))) { 4981 REG_WRITE(ATH_GPIO_OUT_FUNCTION3, ( REG_READ(ATH_GPIO_OUT_FUNCTION3) & (~(0xff << 8))) | (0x2F << 8) ); 4982 REG_WRITE(ATH_GPIO_OE, (( REG_READ(ATH_GPIO_OE) & (~(0x1 << 13) )) | (0x1 << 12))); 4983 } else if (IS_CHAN_5GHZ((AH_PRIVATE(ah)->ah_curchan))) { 4984 REG_WRITE(ATH_GPIO_OUT_FUNCTION3, ( REG_READ(ATH_GPIO_OUT_FUNCTION3) & (~(0xff))) | (0x2F) ); 4985 REG_WRITE(ATH_GPIO_OE, (( REG_READ(ATH_GPIO_OE) & (~(0x1 << 12) )) | (0x1 << 13))); 4986 } 4987 } 4988#undef REG_READ 4989#undef REG_WRITE 4990#endif 4991 4992 /* XXX FreeBSD What's this? -adrian */ 4993#if 0 4994 chan->channel_flags = ichan->channel_flags; 4995 chan->priv_flags = ichan->priv_flags; 4996#endif 4997 4998#if FIX_NOISE_FLOOR 4999 /* XXX FreeBSD is ichan appropariate? It was curchan.. */ 5000 ar9300_get_nf_hist_base(ah, ichan, is_scan, nf_buf); 5001 ar9300_load_nf(ah, nf_buf); 5002 if (nf_hist_buff_reset == 1) 5003 { 5004 nf_hist_buff_reset = 0; 5005 #ifndef ATH_NF_PER_CHAN 5006 if (First_NFCal(ah, ichan, is_scan, chan)){ 5007 } 5008 #endif /* ATH_NF_PER_CHAN */ 5009 } 5010 else{ 5011 ar9300_start_nf_cal(ah); 5012 } 5013#endif 5014 5015#ifdef AH_SUPPORT_AR9300 5016 /* BB Panic Watchdog */ 5017 if (ar9300_get_capability(ah, HAL_CAP_BB_PANIC_WATCHDOG, 0, AH_NULL) == 5018 HAL_OK) 5019 { 5020 ar9300_config_bb_panic_watchdog(ah); 5021 } 5022#endif 5023 5024 /* While receiving unsupported rate frame receive state machine 5025 * gets into a state 0xb and if phy_restart happens when rx 5026 * state machine is in 0xb state, BB would go hang, if we 5027 * see 0xb state after first bb panic, make sure that we 5028 * disable the phy_restart. 5029 * 5030 * There may be multiple panics, make sure that we always do 5031 * this if we see this panic at least once. This is required 5032 * because reset seems to be writing from INI file. 5033 */ 5034 if ((ar9300_get_capability(ah, HAL_CAP_PHYRESTART_CLR_WAR, 0, AH_NULL) 5035 == HAL_OK) && (((MS((AH9300(ah)->ah_bb_panic_last_status), 5036 AR_PHY_BB_WD_RX_OFDM_SM)) == 0xb) || 5037 AH9300(ah)->ah_phyrestart_disabled) ) 5038 { 5039 ar9300_disable_phy_restart(ah, 1); 5040 } 5041 5042 5043 5044 ahp->ah_radar1 = MS(OS_REG_READ(ah, AR_PHY_RADAR_1), 5045 AR_PHY_RADAR_1_CF_BIN_THRESH); 5046 ahp->ah_dc_offset = MS(OS_REG_READ(ah, AR_PHY_TIMING2), 5047 AR_PHY_TIMING2_DC_OFFSET); 5048 ahp->ah_disable_cck = MS(OS_REG_READ(ah, AR_PHY_MODE), 5049 AR_PHY_MODE_DISABLE_CCK); 5050 5051 if (AH9300(ah)->ah_enable_keysearch_always) { 5052 ar9300_enable_keysearch_always(ah, 1); 5053 } 5054 5055#if ATH_LOW_POWER_ENABLE 5056#define REG_WRITE(_reg, _val) *((volatile u_int32_t *)(_reg)) = (_val) 5057#define REG_READ(_reg) *((volatile u_int32_t *)(_reg)) 5058 if (AR_SREV_OSPREY(ah)) { 5059 REG_WRITE(0xb4000080, REG_READ(0xb4000080) | 3); 5060 OS_REG_WRITE(ah, AR_RTC_RESET, 1); 5061 OS_REG_SET_BIT(ah, AR_HOSTIF_REG(ah, AR_PCIE_PM_CTRL), 5062 AR_PCIE_PM_CTRL_ENA); 5063 OS_REG_SET_BIT(ah, AR_HOSTIF_REG(ah, AR_SPARE), 0xffffffff); 5064 } 5065#undef REG_READ 5066#undef REG_WRITE 5067#endif /* ATH_LOW_POWER_ENABLE */ 5068 5069 WAR_USB_DISABLE_PLL_LOCK_DETECT(ah); 5070 5071 /* H/W Green TX */ 5072 ar9300_control_signals_for_green_tx_mode(ah); 5073 /* Smart Antenna, only for 5GHz on Scropion */ 5074 if (IEEE80211_IS_CHAN_2GHZ((AH_PRIVATE(ah)->ah_curchan)) && AR_SREV_SCORPION(ah)) { 5075 ahp->ah_smartantenna_enable = 0; 5076 } 5077 5078 ar9300_set_smart_antenna(ah, ahp->ah_smartantenna_enable); 5079 5080 5081 return AH_TRUE; 5082bad: 5083 OS_MARK(ah, AH_MARK_RESET_DONE, ecode); 5084 *status = ecode; 5085 5086 return AH_FALSE; 5087#undef FAIL 5088} 5089 5090void 5091ar9300_green_ap_ps_on_off( struct ath_hal *ah, u_int16_t on_off) 5092{ 5093 /* Set/reset the ps flag */ 5094 AH9300(ah)->green_ap_ps_on = !!on_off; 5095} 5096 5097/* 5098 * This function returns 1, where it is possible to do 5099 * single-chain power save. 5100 */ 5101u_int16_t 5102ar9300_is_single_ant_power_save_possible(struct ath_hal *ah) 5103{ 5104 return AH_TRUE; 5105} 5106 5107/* To avoid compilation warnings. Functions not used when EMULATION. */ 5108/* 5109 * ar9300_find_mag_approx() 5110 */ 5111static int32_t 5112ar9300_find_mag_approx(struct ath_hal *ah, int32_t in_re, int32_t in_im) 5113{ 5114 int32_t abs_i = abs(in_re); 5115 int32_t abs_q = abs(in_im); 5116 int32_t max_abs, min_abs; 5117 5118 if (abs_i > abs_q) { 5119 max_abs = abs_i; 5120 min_abs = abs_q; 5121 } else { 5122 max_abs = abs_q; 5123 min_abs = abs_i; 5124 } 5125 5126 return (max_abs - (max_abs / 32) + (min_abs / 8) + (min_abs / 4)); 5127} 5128 5129/* 5130 * ar9300_solve_iq_cal() 5131 * solve 4x4 linear equation used in loopback iq cal. 5132 */ 5133static HAL_BOOL 5134ar9300_solve_iq_cal( 5135 struct ath_hal *ah, 5136 int32_t sin_2phi_1, 5137 int32_t cos_2phi_1, 5138 int32_t sin_2phi_2, 5139 int32_t cos_2phi_2, 5140 int32_t mag_a0_d0, 5141 int32_t phs_a0_d0, 5142 int32_t mag_a1_d0, 5143 int32_t phs_a1_d0, 5144 int32_t solved_eq[]) 5145{ 5146 int32_t f1 = cos_2phi_1 - cos_2phi_2; 5147 int32_t f3 = sin_2phi_1 - sin_2phi_2; 5148 int32_t f2; 5149 int32_t mag_tx, phs_tx, mag_rx, phs_rx; 5150 const int32_t result_shift = 1 << 15; 5151 5152 f2 = (((int64_t)f1 * (int64_t)f1) / result_shift) + (((int64_t)f3 * (int64_t)f3) / result_shift); 5153 5154 if (0 == f2) { 5155 HALDEBUG(ah, HAL_DEBUG_CALIBRATE, "%s: Divide by 0(%d).\n", 5156 __func__, __LINE__); 5157 return AH_FALSE; 5158 } 5159 5160 /* magnitude mismatch, tx */ 5161 mag_tx = f1 * (mag_a0_d0 - mag_a1_d0) + f3 * (phs_a0_d0 - phs_a1_d0); 5162 /* phase mismatch, tx */ 5163 phs_tx = f3 * (-mag_a0_d0 + mag_a1_d0) + f1 * (phs_a0_d0 - phs_a1_d0); 5164 5165 mag_tx = (mag_tx / f2); 5166 phs_tx = (phs_tx / f2); 5167 5168 /* magnitude mismatch, rx */ 5169 mag_rx = 5170 mag_a0_d0 - (cos_2phi_1 * mag_tx + sin_2phi_1 * phs_tx) / result_shift; 5171 /* phase mismatch, rx */ 5172 phs_rx = 5173 phs_a0_d0 + (sin_2phi_1 * mag_tx - cos_2phi_1 * phs_tx) / result_shift; 5174 5175 solved_eq[0] = mag_tx; 5176 solved_eq[1] = phs_tx; 5177 solved_eq[2] = mag_rx; 5178 solved_eq[3] = phs_rx; 5179 5180 return AH_TRUE; 5181} 5182 5183/* 5184 * ar9300_calc_iq_corr() 5185 */ 5186static HAL_BOOL 5187ar9300_calc_iq_corr(struct ath_hal *ah, int32_t chain_idx, 5188 const int32_t iq_res[], int32_t iqc_coeff[]) 5189{ 5190 int32_t i2_m_q2_a0_d0, i2_p_q2_a0_d0, iq_corr_a0_d0; 5191 int32_t i2_m_q2_a0_d1, i2_p_q2_a0_d1, iq_corr_a0_d1; 5192 int32_t i2_m_q2_a1_d0, i2_p_q2_a1_d0, iq_corr_a1_d0; 5193 int32_t i2_m_q2_a1_d1, i2_p_q2_a1_d1, iq_corr_a1_d1; 5194 int32_t mag_a0_d0, mag_a1_d0, mag_a0_d1, mag_a1_d1; 5195 int32_t phs_a0_d0, phs_a1_d0, phs_a0_d1, phs_a1_d1; 5196 int32_t sin_2phi_1, cos_2phi_1, sin_2phi_2, cos_2phi_2; 5197 int32_t mag_tx, phs_tx, mag_rx, phs_rx; 5198 int32_t solved_eq[4], mag_corr_tx, phs_corr_tx, mag_corr_rx, phs_corr_rx; 5199 int32_t q_q_coff, q_i_coff; 5200 const int32_t res_scale = 1 << 15; 5201 const int32_t delpt_shift = 1 << 8; 5202 int32_t mag1, mag2; 5203 5204 i2_m_q2_a0_d0 = iq_res[0] & 0xfff; 5205 i2_p_q2_a0_d0 = (iq_res[0] >> 12) & 0xfff; 5206 iq_corr_a0_d0 = ((iq_res[0] >> 24) & 0xff) + ((iq_res[1] & 0xf) << 8); 5207 5208 if (i2_m_q2_a0_d0 > 0x800) { 5209 i2_m_q2_a0_d0 = -((0xfff - i2_m_q2_a0_d0) + 1); 5210 } 5211 if (iq_corr_a0_d0 > 0x800) { 5212 iq_corr_a0_d0 = -((0xfff - iq_corr_a0_d0) + 1); 5213 } 5214 5215 i2_m_q2_a0_d1 = (iq_res[1] >> 4) & 0xfff; 5216 i2_p_q2_a0_d1 = (iq_res[2] & 0xfff); 5217 iq_corr_a0_d1 = (iq_res[2] >> 12) & 0xfff; 5218 5219 if (i2_m_q2_a0_d1 > 0x800) { 5220 i2_m_q2_a0_d1 = -((0xfff - i2_m_q2_a0_d1) + 1); 5221 } 5222 if (iq_corr_a0_d1 > 0x800) { 5223 iq_corr_a0_d1 = -((0xfff - iq_corr_a0_d1) + 1); 5224 } 5225 5226 i2_m_q2_a1_d0 = ((iq_res[2] >> 24) & 0xff) + ((iq_res[3] & 0xf) << 8); 5227 i2_p_q2_a1_d0 = (iq_res[3] >> 4) & 0xfff; 5228 iq_corr_a1_d0 = iq_res[4] & 0xfff; 5229 5230 if (i2_m_q2_a1_d0 > 0x800) { 5231 i2_m_q2_a1_d0 = -((0xfff - i2_m_q2_a1_d0) + 1); 5232 } 5233 if (iq_corr_a1_d0 > 0x800) { 5234 iq_corr_a1_d0 = -((0xfff - iq_corr_a1_d0) + 1); 5235 } 5236 5237 i2_m_q2_a1_d1 = (iq_res[4] >> 12) & 0xfff; 5238 i2_p_q2_a1_d1 = ((iq_res[4] >> 24) & 0xff) + ((iq_res[5] & 0xf) << 8); 5239 iq_corr_a1_d1 = (iq_res[5] >> 4) & 0xfff; 5240 5241 if (i2_m_q2_a1_d1 > 0x800) { 5242 i2_m_q2_a1_d1 = -((0xfff - i2_m_q2_a1_d1) + 1); 5243 } 5244 if (iq_corr_a1_d1 > 0x800) { 5245 iq_corr_a1_d1 = -((0xfff - iq_corr_a1_d1) + 1); 5246 } 5247 5248 if ((i2_p_q2_a0_d0 == 0) || 5249 (i2_p_q2_a0_d1 == 0) || 5250 (i2_p_q2_a1_d0 == 0) || 5251 (i2_p_q2_a1_d1 == 0)) { 5252 HALDEBUG(ah, HAL_DEBUG_CALIBRATE, 5253 "%s: Divide by 0(%d):\na0_d0=%d\na0_d1=%d\na2_d0=%d\na1_d1=%d\n", 5254 __func__, __LINE__, 5255 i2_p_q2_a0_d0, i2_p_q2_a0_d1, i2_p_q2_a1_d0, i2_p_q2_a1_d1); 5256 return AH_FALSE; 5257 } 5258 5259 if ((i2_p_q2_a0_d0 <= 1024) || (i2_p_q2_a0_d0 > 2047) || 5260 (i2_p_q2_a1_d0 < 0) || (i2_p_q2_a1_d1 < 0) || 5261 (i2_p_q2_a0_d0 <= i2_m_q2_a0_d0) || 5262 (i2_p_q2_a0_d0 <= iq_corr_a0_d0) || 5263 (i2_p_q2_a0_d1 <= i2_m_q2_a0_d1) || 5264 (i2_p_q2_a0_d1 <= iq_corr_a0_d1) || 5265 (i2_p_q2_a1_d0 <= i2_m_q2_a1_d0) || 5266 (i2_p_q2_a1_d0 <= iq_corr_a1_d0) || 5267 (i2_p_q2_a1_d1 <= i2_m_q2_a1_d1) || 5268 (i2_p_q2_a1_d1 <= iq_corr_a1_d1)) { 5269 return AH_FALSE; 5270 } 5271 5272 mag_a0_d0 = (i2_m_q2_a0_d0 * res_scale) / i2_p_q2_a0_d0; 5273 phs_a0_d0 = (iq_corr_a0_d0 * res_scale) / i2_p_q2_a0_d0; 5274 5275 mag_a0_d1 = (i2_m_q2_a0_d1 * res_scale) / i2_p_q2_a0_d1; 5276 phs_a0_d1 = (iq_corr_a0_d1 * res_scale) / i2_p_q2_a0_d1; 5277 5278 mag_a1_d0 = (i2_m_q2_a1_d0 * res_scale) / i2_p_q2_a1_d0; 5279 phs_a1_d0 = (iq_corr_a1_d0 * res_scale) / i2_p_q2_a1_d0; 5280 5281 mag_a1_d1 = (i2_m_q2_a1_d1 * res_scale) / i2_p_q2_a1_d1; 5282 phs_a1_d1 = (iq_corr_a1_d1 * res_scale) / i2_p_q2_a1_d1; 5283 5284 /* without analog phase shift */ 5285 sin_2phi_1 = (((mag_a0_d0 - mag_a0_d1) * delpt_shift) / DELPT); 5286 /* without analog phase shift */ 5287 cos_2phi_1 = (((phs_a0_d1 - phs_a0_d0) * delpt_shift) / DELPT); 5288 /* with analog phase shift */ 5289 sin_2phi_2 = (((mag_a1_d0 - mag_a1_d1) * delpt_shift) / DELPT); 5290 /* with analog phase shift */ 5291 cos_2phi_2 = (((phs_a1_d1 - phs_a1_d0) * delpt_shift) / DELPT); 5292 5293 /* force sin^2 + cos^2 = 1; */ 5294 /* find magnitude by approximation */ 5295 mag1 = ar9300_find_mag_approx(ah, cos_2phi_1, sin_2phi_1); 5296 mag2 = ar9300_find_mag_approx(ah, cos_2phi_2, sin_2phi_2); 5297 5298 if ((mag1 == 0) || (mag2 == 0)) { 5299 HALDEBUG(ah, HAL_DEBUG_CALIBRATE, 5300 "%s: Divide by 0(%d): mag1=%d, mag2=%d\n", 5301 __func__, __LINE__, mag1, mag2); 5302 return AH_FALSE; 5303 } 5304 5305 /* normalization sin and cos by mag */ 5306 sin_2phi_1 = (sin_2phi_1 * res_scale / mag1); 5307 cos_2phi_1 = (cos_2phi_1 * res_scale / mag1); 5308 sin_2phi_2 = (sin_2phi_2 * res_scale / mag2); 5309 cos_2phi_2 = (cos_2phi_2 * res_scale / mag2); 5310 5311 /* calculate IQ mismatch */ 5312 if (AH_FALSE == ar9300_solve_iq_cal(ah, 5313 sin_2phi_1, cos_2phi_1, sin_2phi_2, cos_2phi_2, mag_a0_d0, 5314 phs_a0_d0, mag_a1_d0, phs_a1_d0, solved_eq)) 5315 { 5316 HALDEBUG(ah, HAL_DEBUG_CALIBRATE, 5317 "%s: Call to ar9300_solve_iq_cal failed.\n", __func__); 5318 return AH_FALSE; 5319 } 5320 5321 mag_tx = solved_eq[0]; 5322 phs_tx = solved_eq[1]; 5323 mag_rx = solved_eq[2]; 5324 phs_rx = solved_eq[3]; 5325 5326 HALDEBUG(ah, HAL_DEBUG_CALIBRATE, 5327 "%s: chain %d: mag mismatch=%d phase mismatch=%d\n", 5328 __func__, chain_idx, mag_tx / res_scale, phs_tx / res_scale); 5329 5330 if (res_scale == mag_tx) { 5331 HALDEBUG(ah, HAL_DEBUG_CALIBRATE, 5332 "%s: Divide by 0(%d): mag_tx=%d, res_scale=%d\n", 5333 __func__, __LINE__, mag_tx, res_scale); 5334 return AH_FALSE; 5335 } 5336 5337 /* calculate and quantize Tx IQ correction factor */ 5338 mag_corr_tx = (mag_tx * res_scale) / (res_scale - mag_tx); 5339 phs_corr_tx = -phs_tx; 5340 5341 q_q_coff = (mag_corr_tx * 128 / res_scale); 5342 q_i_coff = (phs_corr_tx * 256 / res_scale); 5343 5344 HALDEBUG(ah, HAL_DEBUG_CALIBRATE, 5345 "%s: tx chain %d: mag corr=%d phase corr=%d\n", 5346 __func__, chain_idx, q_q_coff, q_i_coff); 5347 5348 if (q_i_coff < -63) { 5349 q_i_coff = -63; 5350 } 5351 if (q_i_coff > 63) { 5352 q_i_coff = 63; 5353 } 5354 if (q_q_coff < -63) { 5355 q_q_coff = -63; 5356 } 5357 if (q_q_coff > 63) { 5358 q_q_coff = 63; 5359 } 5360 5361 iqc_coeff[0] = (q_q_coff * 128) + (0x7f & q_i_coff); 5362 5363 HALDEBUG(ah, HAL_DEBUG_CALIBRATE, "%s: tx chain %d: iq corr coeff=%x\n", 5364 __func__, chain_idx, iqc_coeff[0]); 5365 5366 if (-mag_rx == res_scale) { 5367 HALDEBUG(ah, HAL_DEBUG_CALIBRATE, 5368 "%s: Divide by 0(%d): mag_rx=%d, res_scale=%d\n", 5369 __func__, __LINE__, mag_rx, res_scale); 5370 return AH_FALSE; 5371 } 5372 5373 /* calculate and quantize Rx IQ correction factors */ 5374 mag_corr_rx = (-mag_rx * res_scale) / (res_scale + mag_rx); 5375 phs_corr_rx = -phs_rx; 5376 5377 q_q_coff = (mag_corr_rx * 128 / res_scale); 5378 q_i_coff = (phs_corr_rx * 256 / res_scale); 5379 5380 HALDEBUG(ah, HAL_DEBUG_CALIBRATE, 5381 "%s: rx chain %d: mag corr=%d phase corr=%d\n", 5382 __func__, chain_idx, q_q_coff, q_i_coff); 5383 5384 if (q_i_coff < -63) { 5385 q_i_coff = -63; 5386 } 5387 if (q_i_coff > 63) { 5388 q_i_coff = 63; 5389 } 5390 if (q_q_coff < -63) { 5391 q_q_coff = -63; 5392 } 5393 if (q_q_coff > 63) { 5394 q_q_coff = 63; 5395 } 5396 5397 iqc_coeff[1] = (q_q_coff * 128) + (0x7f & q_i_coff); 5398 5399 HALDEBUG(ah, HAL_DEBUG_CALIBRATE, "%s: rx chain %d: iq corr coeff=%x\n", 5400 __func__, chain_idx, iqc_coeff[1]); 5401 5402 return AH_TRUE; 5403} 5404 5405#define MAX_MAG_DELTA 11 //maximum magnitude mismatch delta across gains 5406#define MAX_PHS_DELTA 10 //maximum phase mismatch delta across gains 5407#define ABS(x) ((x) >= 0 ? (x) : (-(x))) 5408 5409 u_int32_t tx_corr_coeff[MAX_MEASUREMENT][AR9300_MAX_CHAINS] = { 5410 { AR_PHY_TX_IQCAL_CORR_COEFF_01_B0, 5411 AR_PHY_TX_IQCAL_CORR_COEFF_01_B1, 5412 AR_PHY_TX_IQCAL_CORR_COEFF_01_B2}, 5413 { AR_PHY_TX_IQCAL_CORR_COEFF_01_B0, 5414 AR_PHY_TX_IQCAL_CORR_COEFF_01_B1, 5415 AR_PHY_TX_IQCAL_CORR_COEFF_01_B2}, 5416 { AR_PHY_TX_IQCAL_CORR_COEFF_23_B0, 5417 AR_PHY_TX_IQCAL_CORR_COEFF_23_B1, 5418 AR_PHY_TX_IQCAL_CORR_COEFF_23_B2}, 5419 { AR_PHY_TX_IQCAL_CORR_COEFF_23_B0, 5420 AR_PHY_TX_IQCAL_CORR_COEFF_23_B1, 5421 AR_PHY_TX_IQCAL_CORR_COEFF_23_B2}, 5422 { AR_PHY_TX_IQCAL_CORR_COEFF_45_B0, 5423 AR_PHY_TX_IQCAL_CORR_COEFF_45_B1, 5424 AR_PHY_TX_IQCAL_CORR_COEFF_45_B2}, 5425 { AR_PHY_TX_IQCAL_CORR_COEFF_45_B0, 5426 AR_PHY_TX_IQCAL_CORR_COEFF_45_B1, 5427 AR_PHY_TX_IQCAL_CORR_COEFF_45_B2}, 5428 { AR_PHY_TX_IQCAL_CORR_COEFF_67_B0, 5429 AR_PHY_TX_IQCAL_CORR_COEFF_67_B1, 5430 AR_PHY_TX_IQCAL_CORR_COEFF_67_B2}, 5431 { AR_PHY_TX_IQCAL_CORR_COEFF_67_B0, 5432 AR_PHY_TX_IQCAL_CORR_COEFF_67_B1, 5433 AR_PHY_TX_IQCAL_CORR_COEFF_67_B2}, 5434 }; 5435 5436static void 5437ar9300_tx_iq_cal_outlier_detection(struct ath_hal *ah, HAL_CHANNEL_INTERNAL *ichan, u_int32_t num_chains, 5438 struct coeff_t *coeff, HAL_BOOL is_cal_reusable) 5439{ 5440 int nmeasurement, ch_idx, im; 5441 int32_t magnitude, phase; 5442 int32_t magnitude_max, phase_max; 5443 int32_t magnitude_min, phase_min; 5444 5445 int32_t magnitude_max_idx, phase_max_idx; 5446 int32_t magnitude_min_idx, phase_min_idx; 5447 5448 int32_t magnitude_avg, phase_avg; 5449 int32_t outlier_mag_idx = 0; 5450 int32_t outlier_phs_idx = 0; 5451 5452 5453 if (AR_SREV_POSEIDON(ah)) { 5454 HALASSERT(num_chains == 0x1); 5455 5456 tx_corr_coeff[0][0] = AR_PHY_TX_IQCAL_CORR_COEFF_01_B0_POSEIDON; 5457 tx_corr_coeff[1][0] = AR_PHY_TX_IQCAL_CORR_COEFF_01_B0_POSEIDON; 5458 tx_corr_coeff[2][0] = AR_PHY_TX_IQCAL_CORR_COEFF_23_B0_POSEIDON; 5459 tx_corr_coeff[3][0] = AR_PHY_TX_IQCAL_CORR_COEFF_23_B0_POSEIDON; 5460 tx_corr_coeff[4][0] = AR_PHY_TX_IQCAL_CORR_COEFF_45_B0_POSEIDON; 5461 tx_corr_coeff[5][0] = AR_PHY_TX_IQCAL_CORR_COEFF_45_B0_POSEIDON; 5462 tx_corr_coeff[6][0] = AR_PHY_TX_IQCAL_CORR_COEFF_67_B0_POSEIDON; 5463 tx_corr_coeff[7][0] = AR_PHY_TX_IQCAL_CORR_COEFF_67_B0_POSEIDON; 5464 } 5465 5466 for (ch_idx = 0; ch_idx < num_chains; ch_idx++) { 5467 nmeasurement = OS_REG_READ_FIELD(ah, 5468 AR_PHY_TX_IQCAL_STATUS_B0(ah), AR_PHY_CALIBRATED_GAINS_0); 5469 if (nmeasurement > MAX_MEASUREMENT) { 5470 nmeasurement = MAX_MEASUREMENT; 5471 } 5472 5473 if (!AR_SREV_SCORPION(ah)) { 5474 /* 5475 * reset max/min variable to min/max values so that 5476 * we always start with 1st calibrated gain value 5477 */ 5478 magnitude_max = -64; 5479 phase_max = -64; 5480 magnitude_min = 63; 5481 phase_min = 63; 5482 magnitude_avg = 0; 5483 phase_avg = 0; 5484 magnitude_max_idx = 0; 5485 magnitude_min_idx = 0; 5486 phase_max_idx = 0; 5487 phase_min_idx = 0; 5488 5489 /* detect outlier only if nmeasurement > 1 */ 5490 if (nmeasurement > 1) { 5491 /* printf("----------- start outlier detection -----------\n"); */ 5492 /* 5493 * find max/min and phase/mag mismatch across all calibrated gains 5494 */ 5495 for (im = 0; im < nmeasurement; im++) { 5496 magnitude = coeff->mag_coeff[ch_idx][im][0]; 5497 phase = coeff->phs_coeff[ch_idx][im][0]; 5498 5499 magnitude_avg = magnitude_avg + magnitude; 5500 phase_avg = phase_avg + phase; 5501 if (magnitude > magnitude_max) { 5502 magnitude_max = magnitude; 5503 magnitude_max_idx = im; 5504 } 5505 if (magnitude < magnitude_min) { 5506 magnitude_min = magnitude; 5507 magnitude_min_idx = im; 5508 } 5509 if (phase > phase_max) { 5510 phase_max = phase; 5511 phase_max_idx = im; 5512 } 5513 if (phase < phase_min) { 5514 phase_min = phase; 5515 phase_min_idx = im; 5516 } 5517 } 5518 /* find average (exclude max abs value) */ 5519 for (im = 0; im < nmeasurement; im++) { 5520 magnitude = coeff->mag_coeff[ch_idx][im][0]; 5521 phase = coeff->phs_coeff[ch_idx][im][0]; 5522 if ((ABS(magnitude) < ABS(magnitude_max)) || 5523 (ABS(magnitude) < ABS(magnitude_min))) 5524 { 5525 magnitude_avg = magnitude_avg + magnitude; 5526 } 5527 if ((ABS(phase) < ABS(phase_max)) || 5528 (ABS(phase) < ABS(phase_min))) 5529 { 5530 phase_avg = phase_avg + phase; 5531 } 5532 } 5533 magnitude_avg = magnitude_avg / (nmeasurement - 1); 5534 phase_avg = phase_avg / (nmeasurement - 1); 5535 5536 /* detect magnitude outlier */ 5537 if (ABS(magnitude_max - magnitude_min) > MAX_MAG_DELTA) { 5538 if (ABS(magnitude_max - magnitude_avg) > 5539 ABS(magnitude_min - magnitude_avg)) 5540 { 5541 /* max is outlier, force to avg */ 5542 outlier_mag_idx = magnitude_max_idx; 5543 } else { 5544 /* min is outlier, force to avg */ 5545 outlier_mag_idx = magnitude_min_idx; 5546 } 5547 coeff->mag_coeff[ch_idx][outlier_mag_idx][0] = magnitude_avg; 5548 coeff->phs_coeff[ch_idx][outlier_mag_idx][0] = phase_avg; 5549 HALDEBUG(ah, HAL_DEBUG_CALIBRATE, 5550 "[ch%d][outlier mag gain%d]:: " 5551 "mag_avg = %d (/128), phase_avg = %d (/256)\n", 5552 ch_idx, outlier_mag_idx, magnitude_avg, phase_avg); 5553 } 5554 /* detect phase outlier */ 5555 if (ABS(phase_max - phase_min) > MAX_PHS_DELTA) { 5556 if (ABS(phase_max-phase_avg) > ABS(phase_min - phase_avg)) { 5557 /* max is outlier, force to avg */ 5558 outlier_phs_idx = phase_max_idx; 5559 } else{ 5560 /* min is outlier, force to avg */ 5561 outlier_phs_idx = phase_min_idx; 5562 } 5563 coeff->mag_coeff[ch_idx][outlier_phs_idx][0] = magnitude_avg; 5564 coeff->phs_coeff[ch_idx][outlier_phs_idx][0] = phase_avg; 5565 HALDEBUG(ah, HAL_DEBUG_CALIBRATE, 5566 "[ch%d][outlier phs gain%d]:: " 5567 "mag_avg = %d (/128), phase_avg = %d (/256)\n", 5568 ch_idx, outlier_phs_idx, magnitude_avg, phase_avg); 5569 } 5570 } 5571 } 5572 5573 /*printf("------------ after outlier detection -------------\n");*/ 5574 for (im = 0; im < nmeasurement; im++) { 5575 magnitude = coeff->mag_coeff[ch_idx][im][0]; 5576 phase = coeff->phs_coeff[ch_idx][im][0]; 5577 5578 #if 0 5579 printf("[ch%d][gain%d]:: mag = %d (/128), phase = %d (/256)\n", 5580 ch_idx, im, magnitude, phase); 5581 #endif 5582 5583 coeff->iqc_coeff[0] = (phase & 0x7f) | ((magnitude & 0x7f) << 7); 5584 5585 if ((im % 2) == 0) { 5586 OS_REG_RMW_FIELD(ah, 5587 tx_corr_coeff[im][ch_idx], 5588 AR_PHY_TX_IQCAL_CORR_COEFF_00_COEFF_TABLE, 5589 coeff->iqc_coeff[0]); 5590 } else { 5591 OS_REG_RMW_FIELD(ah, 5592 tx_corr_coeff[im][ch_idx], 5593 AR_PHY_TX_IQCAL_CORR_COEFF_01_COEFF_TABLE, 5594 coeff->iqc_coeff[0]); 5595 } 5596#if ATH_SUPPORT_CAL_REUSE 5597 ichan->tx_corr_coeff[im][ch_idx] = coeff->iqc_coeff[0]; 5598#endif 5599 } 5600#if ATH_SUPPORT_CAL_REUSE 5601 ichan->num_measures[ch_idx] = nmeasurement; 5602#endif 5603 } 5604 5605 OS_REG_RMW_FIELD(ah, AR_PHY_TX_IQCAL_CONTROL_3, 5606 AR_PHY_TX_IQCAL_CONTROL_3_IQCORR_EN, 0x1); 5607 OS_REG_RMW_FIELD(ah, AR_PHY_RX_IQCAL_CORR_B0, 5608 AR_PHY_RX_IQCAL_CORR_B0_LOOPBACK_IQCORR_EN, 0x1); 5609 5610#if ATH_SUPPORT_CAL_REUSE 5611 if (is_cal_reusable) { 5612 ichan->one_time_txiqcal_done = AH_TRUE; 5613 HALDEBUG(ah, HAL_DEBUG_FCS_RTT, 5614 "(FCS) TXIQCAL saved - %d\n", ichan->channel); 5615 } 5616#endif 5617} 5618 5619#if ATH_SUPPORT_CAL_REUSE 5620static void 5621ar9300_tx_iq_cal_apply(struct ath_hal *ah, HAL_CHANNEL_INTERNAL *ichan) 5622{ 5623 struct ath_hal_9300 *ahp = AH9300(ah); 5624 int nmeasurement, ch_idx, im; 5625 5626 u_int32_t tx_corr_coeff[MAX_MEASUREMENT][AR9300_MAX_CHAINS] = { 5627 { AR_PHY_TX_IQCAL_CORR_COEFF_01_B0, 5628 AR_PHY_TX_IQCAL_CORR_COEFF_01_B1, 5629 AR_PHY_TX_IQCAL_CORR_COEFF_01_B2}, 5630 { AR_PHY_TX_IQCAL_CORR_COEFF_01_B0, 5631 AR_PHY_TX_IQCAL_CORR_COEFF_01_B1, 5632 AR_PHY_TX_IQCAL_CORR_COEFF_01_B2}, 5633 { AR_PHY_TX_IQCAL_CORR_COEFF_23_B0, 5634 AR_PHY_TX_IQCAL_CORR_COEFF_23_B1, 5635 AR_PHY_TX_IQCAL_CORR_COEFF_23_B2}, 5636 { AR_PHY_TX_IQCAL_CORR_COEFF_23_B0, 5637 AR_PHY_TX_IQCAL_CORR_COEFF_23_B1, 5638 AR_PHY_TX_IQCAL_CORR_COEFF_23_B2}, 5639 { AR_PHY_TX_IQCAL_CORR_COEFF_45_B0, 5640 AR_PHY_TX_IQCAL_CORR_COEFF_45_B1, 5641 AR_PHY_TX_IQCAL_CORR_COEFF_45_B2}, 5642 { AR_PHY_TX_IQCAL_CORR_COEFF_45_B0, 5643 AR_PHY_TX_IQCAL_CORR_COEFF_45_B1, 5644 AR_PHY_TX_IQCAL_CORR_COEFF_45_B2}, 5645 { AR_PHY_TX_IQCAL_CORR_COEFF_67_B0, 5646 AR_PHY_TX_IQCAL_CORR_COEFF_67_B1, 5647 AR_PHY_TX_IQCAL_CORR_COEFF_67_B2}, 5648 { AR_PHY_TX_IQCAL_CORR_COEFF_67_B0, 5649 AR_PHY_TX_IQCAL_CORR_COEFF_67_B1, 5650 AR_PHY_TX_IQCAL_CORR_COEFF_67_B2}, 5651 }; 5652 5653 if (AR_SREV_POSEIDON(ah)) { 5654 HALASSERT(ahp->ah_tx_cal_chainmask == 0x1); 5655 5656 tx_corr_coeff[0][0] = AR_PHY_TX_IQCAL_CORR_COEFF_01_B0_POSEIDON; 5657 tx_corr_coeff[1][0] = AR_PHY_TX_IQCAL_CORR_COEFF_01_B0_POSEIDON; 5658 tx_corr_coeff[2][0] = AR_PHY_TX_IQCAL_CORR_COEFF_23_B0_POSEIDON; 5659 tx_corr_coeff[3][0] = AR_PHY_TX_IQCAL_CORR_COEFF_23_B0_POSEIDON; 5660 tx_corr_coeff[4][0] = AR_PHY_TX_IQCAL_CORR_COEFF_45_B0_POSEIDON; 5661 tx_corr_coeff[5][0] = AR_PHY_TX_IQCAL_CORR_COEFF_45_B0_POSEIDON; 5662 tx_corr_coeff[6][0] = AR_PHY_TX_IQCAL_CORR_COEFF_67_B0_POSEIDON; 5663 tx_corr_coeff[7][0] = AR_PHY_TX_IQCAL_CORR_COEFF_67_B0_POSEIDON; 5664 } 5665 5666 for (ch_idx = 0; ch_idx < AR9300_MAX_CHAINS; ch_idx++) { 5667 if ((ahp->ah_tx_cal_chainmask & (1 << ch_idx)) == 0) { 5668 continue; 5669 } 5670 nmeasurement = ichan->num_measures[ch_idx]; 5671 5672 for (im = 0; im < nmeasurement; im++) { 5673 if ((im % 2) == 0) { 5674 OS_REG_RMW_FIELD(ah, 5675 tx_corr_coeff[im][ch_idx], 5676 AR_PHY_TX_IQCAL_CORR_COEFF_00_COEFF_TABLE, 5677 ichan->tx_corr_coeff[im][ch_idx]); 5678 } else { 5679 OS_REG_RMW_FIELD(ah, 5680 tx_corr_coeff[im][ch_idx], 5681 AR_PHY_TX_IQCAL_CORR_COEFF_01_COEFF_TABLE, 5682 ichan->tx_corr_coeff[im][ch_idx]); 5683 } 5684 } 5685 } 5686 5687 OS_REG_RMW_FIELD(ah, AR_PHY_TX_IQCAL_CONTROL_3, 5688 AR_PHY_TX_IQCAL_CONTROL_3_IQCORR_EN, 0x1); 5689 OS_REG_RMW_FIELD(ah, AR_PHY_RX_IQCAL_CORR_B0, 5690 AR_PHY_RX_IQCAL_CORR_B0_LOOPBACK_IQCORR_EN, 0x1); 5691} 5692#endif 5693 5694/* 5695 * ar9300_tx_iq_cal_hw_run is only needed for osprey/wasp/hornet 5696 * It is not needed for jupiter/poseidon. 5697 */ 5698HAL_BOOL 5699ar9300_tx_iq_cal_hw_run(struct ath_hal *ah) 5700{ 5701 int is_tx_gain_forced; 5702 5703 is_tx_gain_forced = OS_REG_READ_FIELD(ah, 5704 AR_PHY_TX_FORCED_GAIN, AR_PHY_TXGAIN_FORCE); 5705 if (is_tx_gain_forced) { 5706 /*printf("Tx gain can not be forced during tx I/Q cal!\n");*/ 5707 OS_REG_RMW_FIELD(ah, AR_PHY_TX_FORCED_GAIN, AR_PHY_TXGAIN_FORCE, 0); 5708 } 5709 5710 /* enable tx IQ cal */ 5711 OS_REG_RMW_FIELD(ah, AR_PHY_TX_IQCAL_START(ah), 5712 AR_PHY_TX_IQCAL_START_DO_CAL, AR_PHY_TX_IQCAL_START_DO_CAL); 5713 5714 if (!ath_hal_wait(ah, 5715 AR_PHY_TX_IQCAL_START(ah), AR_PHY_TX_IQCAL_START_DO_CAL, 0)) 5716 { 5717 HALDEBUG(ah, HAL_DEBUG_CALIBRATE, 5718 "%s: Tx IQ Cal is never completed.\n", __func__); 5719 return AH_FALSE; 5720 } 5721 return AH_TRUE; 5722} 5723 5724static void 5725ar9300_tx_iq_cal_post_proc(struct ath_hal *ah,HAL_CHANNEL_INTERNAL *ichan, 5726 int iqcal_idx, int max_iqcal,HAL_BOOL is_cal_reusable, HAL_BOOL apply_last_corr) 5727{ 5728 int nmeasurement=0, im, ix, iy, temp; 5729 struct ath_hal_9300 *ahp = AH9300(ah); 5730 u_int32_t txiqcal_status[AR9300_MAX_CHAINS] = { 5731 AR_PHY_TX_IQCAL_STATUS_B0(ah), 5732 AR_PHY_TX_IQCAL_STATUS_B1, 5733 AR_PHY_TX_IQCAL_STATUS_B2, 5734 }; 5735 const u_int32_t chan_info_tab[] = { 5736 AR_PHY_CHAN_INFO_TAB_0, 5737 AR_PHY_CHAN_INFO_TAB_1, 5738 AR_PHY_CHAN_INFO_TAB_2, 5739 }; 5740 int32_t iq_res[6]; 5741 int32_t ch_idx, j; 5742 u_int32_t num_chains = 0; 5743 static struct coeff_t coeff; 5744 txiqcal_status[0] = AR_PHY_TX_IQCAL_STATUS_B0(ah); 5745 5746 for (ch_idx = 0; ch_idx < AR9300_MAX_CHAINS; ch_idx++) { 5747 if (ahp->ah_tx_chainmask & (1 << ch_idx)) { 5748 num_chains++; 5749 } 5750 } 5751 5752 if (apply_last_corr) { 5753 if (coeff.last_cal == AH_TRUE) { 5754 int32_t magnitude, phase; 5755 int ch_idx, im; 5756 u_int32_t tx_corr_coeff[MAX_MEASUREMENT][AR9300_MAX_CHAINS] = { 5757 { AR_PHY_TX_IQCAL_CORR_COEFF_01_B0, 5758 AR_PHY_TX_IQCAL_CORR_COEFF_01_B1, 5759 AR_PHY_TX_IQCAL_CORR_COEFF_01_B2}, 5760 { AR_PHY_TX_IQCAL_CORR_COEFF_01_B0, 5761 AR_PHY_TX_IQCAL_CORR_COEFF_01_B1, 5762 AR_PHY_TX_IQCAL_CORR_COEFF_01_B2}, 5763 { AR_PHY_TX_IQCAL_CORR_COEFF_23_B0, 5764 AR_PHY_TX_IQCAL_CORR_COEFF_23_B1, 5765 AR_PHY_TX_IQCAL_CORR_COEFF_23_B2}, 5766 { AR_PHY_TX_IQCAL_CORR_COEFF_23_B0, 5767 AR_PHY_TX_IQCAL_CORR_COEFF_23_B1, 5768 AR_PHY_TX_IQCAL_CORR_COEFF_23_B2}, 5769 { AR_PHY_TX_IQCAL_CORR_COEFF_45_B0, 5770 AR_PHY_TX_IQCAL_CORR_COEFF_45_B1, 5771 AR_PHY_TX_IQCAL_CORR_COEFF_45_B2}, 5772 { AR_PHY_TX_IQCAL_CORR_COEFF_45_B0, 5773 AR_PHY_TX_IQCAL_CORR_COEFF_45_B1, 5774 AR_PHY_TX_IQCAL_CORR_COEFF_45_B2}, 5775 { AR_PHY_TX_IQCAL_CORR_COEFF_67_B0, 5776 AR_PHY_TX_IQCAL_CORR_COEFF_67_B1, 5777 AR_PHY_TX_IQCAL_CORR_COEFF_67_B2}, 5778 { AR_PHY_TX_IQCAL_CORR_COEFF_67_B0, 5779 AR_PHY_TX_IQCAL_CORR_COEFF_67_B1, 5780 AR_PHY_TX_IQCAL_CORR_COEFF_67_B2}, 5781 }; 5782 for (ch_idx = 0; ch_idx < num_chains; ch_idx++) { 5783 for (im = 0; im < coeff.last_nmeasurement; im++) { 5784 magnitude = coeff.mag_coeff[ch_idx][im][0]; 5785 phase = coeff.phs_coeff[ch_idx][im][0]; 5786 5787#if 0 5788 printf("[ch%d][gain%d]:: mag = %d (/128), phase = %d (/256)\n", 5789 ch_idx, im, magnitude, phase); 5790#endif 5791 5792 coeff.iqc_coeff[0] = (phase & 0x7f) | ((magnitude & 0x7f) << 7); 5793 if ((im % 2) == 0) { 5794 OS_REG_RMW_FIELD(ah, 5795 tx_corr_coeff[im][ch_idx], 5796 AR_PHY_TX_IQCAL_CORR_COEFF_00_COEFF_TABLE, 5797 coeff.iqc_coeff[0]); 5798 } else { 5799 OS_REG_RMW_FIELD(ah, 5800 tx_corr_coeff[im][ch_idx], 5801 AR_PHY_TX_IQCAL_CORR_COEFF_01_COEFF_TABLE, 5802 coeff.iqc_coeff[0]); 5803 } 5804 } 5805 } 5806 OS_REG_RMW_FIELD(ah, AR_PHY_TX_IQCAL_CONTROL_3, 5807 AR_PHY_TX_IQCAL_CONTROL_3_IQCORR_EN, 0x1); 5808 } 5809 return; 5810 } 5811 5812 5813 for (ch_idx = 0; ch_idx < num_chains; ch_idx++) { 5814 nmeasurement = OS_REG_READ_FIELD(ah, 5815 AR_PHY_TX_IQCAL_STATUS_B0(ah), AR_PHY_CALIBRATED_GAINS_0); 5816 if (nmeasurement > MAX_MEASUREMENT) { 5817 nmeasurement = MAX_MEASUREMENT; 5818 } 5819 5820 for (im = 0; im < nmeasurement; im++) { 5821 HALDEBUG(ah, HAL_DEBUG_CALIBRATE, 5822 "%s: Doing Tx IQ Cal for chain %d.\n", __func__, ch_idx); 5823 if (OS_REG_READ(ah, txiqcal_status[ch_idx]) & 5824 AR_PHY_TX_IQCAL_STATUS_FAILED) 5825 { 5826 HALDEBUG(ah, HAL_DEBUG_CALIBRATE, 5827 "%s: Tx IQ Cal failed for chain %d.\n", __func__, ch_idx); 5828 goto TX_IQ_CAL_FAILED_; 5829 } 5830 5831 for (j = 0; j < 3; j++) { 5832 u_int32_t idx = 2 * j; 5833 /* 3 registers for each calibration result */ 5834 u_int32_t offset = 4 * (3 * im + j); 5835 5836 OS_REG_RMW_FIELD(ah, AR_PHY_CHAN_INFO_MEMORY, 5837 AR_PHY_CHAN_INFO_TAB_S2_READ, 0); 5838 /* 32 bits */ 5839 iq_res[idx] = OS_REG_READ(ah, chan_info_tab[ch_idx] + offset); 5840 OS_REG_RMW_FIELD(ah, AR_PHY_CHAN_INFO_MEMORY, 5841 AR_PHY_CHAN_INFO_TAB_S2_READ, 1); 5842 /* 16 bits */ 5843 iq_res[idx + 1] = 0xffff & 5844 OS_REG_READ(ah, chan_info_tab[ch_idx] + offset); 5845 5846 HALDEBUG(ah, HAL_DEBUG_CALIBRATE, 5847 "%s: IQ RES[%d]=0x%x IQ_RES[%d]=0x%x\n", 5848 __func__, idx, iq_res[idx], idx + 1, iq_res[idx + 1]); 5849 } 5850 5851 if (AH_FALSE == ar9300_calc_iq_corr( 5852 ah, ch_idx, iq_res, coeff.iqc_coeff)) 5853 { 5854 HALDEBUG(ah, HAL_DEBUG_CALIBRATE, 5855 "%s: Failed in calculation of IQ correction.\n", 5856 __func__); 5857 goto TX_IQ_CAL_FAILED_; 5858 } 5859 5860 coeff.phs_coeff[ch_idx][im][iqcal_idx-1] = coeff.iqc_coeff[0] & 0x7f; 5861 coeff.mag_coeff[ch_idx][im][iqcal_idx-1] = (coeff.iqc_coeff[0] >> 7) & 0x7f; 5862 if (coeff.mag_coeff[ch_idx][im][iqcal_idx-1] > 63) { 5863 coeff.mag_coeff[ch_idx][im][iqcal_idx-1] -= 128; 5864 } 5865 if (coeff.phs_coeff[ch_idx][im][iqcal_idx-1] > 63) { 5866 coeff.phs_coeff[ch_idx][im][iqcal_idx-1] -= 128; 5867 } 5868#if 0 5869 ath_hal_printf(ah, "IQCAL::[ch%d][gain%d]:: mag = %d phase = %d \n", 5870 ch_idx, im, coeff.mag_coeff[ch_idx][im][iqcal_idx-1], 5871 coeff.phs_coeff[ch_idx][im][iqcal_idx-1]); 5872#endif 5873 } 5874 } 5875 //last iteration; calculate mag and phs 5876 if (iqcal_idx == max_iqcal) { 5877 if (max_iqcal>1) { 5878 for (ch_idx = 0; ch_idx < num_chains; ch_idx++) { 5879 for (im = 0; im < nmeasurement; im++) { 5880 //sort mag and phs 5881 for( ix=0;ix<max_iqcal-1;ix++){ 5882 for( iy=ix+1;iy<=max_iqcal-1;iy++){ 5883 if(coeff.mag_coeff[ch_idx][im][iy] < 5884 coeff.mag_coeff[ch_idx][im][ix]) { 5885 //swap 5886 temp=coeff.mag_coeff[ch_idx][im][ix]; 5887 coeff.mag_coeff[ch_idx][im][ix] = coeff.mag_coeff[ch_idx][im][iy]; 5888 coeff.mag_coeff[ch_idx][im][iy] = temp; 5889 } 5890 if(coeff.phs_coeff[ch_idx][im][iy] < 5891 coeff.phs_coeff[ch_idx][im][ix]){ 5892 //swap 5893 temp=coeff.phs_coeff[ch_idx][im][ix]; 5894 coeff.phs_coeff[ch_idx][im][ix]=coeff.phs_coeff[ch_idx][im][iy]; 5895 coeff.phs_coeff[ch_idx][im][iy]=temp; 5896 } 5897 } 5898 } 5899 //select median; 3rd entry in the sorted array 5900 coeff.mag_coeff[ch_idx][im][0] = 5901 coeff.mag_coeff[ch_idx][im][max_iqcal/2]; 5902 coeff.phs_coeff[ch_idx][im][0] = 5903 coeff.phs_coeff[ch_idx][im][max_iqcal/2]; 5904 HALDEBUG(ah, HAL_DEBUG_CALIBRATE, 5905 "IQCAL: Median [ch%d][gain%d]:: mag = %d phase = %d \n", 5906 ch_idx, im,coeff.mag_coeff[ch_idx][im][0], 5907 coeff.phs_coeff[ch_idx][im][0]); 5908 } 5909 } 5910 } 5911 ar9300_tx_iq_cal_outlier_detection(ah,ichan, num_chains, &coeff,is_cal_reusable); 5912 } 5913 5914 5915 coeff.last_nmeasurement = nmeasurement; 5916 coeff.last_cal = AH_TRUE; 5917 5918 return; 5919 5920TX_IQ_CAL_FAILED_: 5921 /* no need to print this, it is AGC failure not chip stuck */ 5922 /*ath_hal_printf(ah, "Tx IQ Cal failed(%d)\n", line);*/ 5923 coeff.last_cal = AH_FALSE; 5924 return; 5925} 5926 5927 5928/* 5929 * ar9300_disable_phy_restart 5930 * 5931 * In some BBpanics, we can disable the phyrestart 5932 * disable_phy_restart 5933 * != 0, disable the phy restart in h/w 5934 * == 0, enable the phy restart in h/w 5935 */ 5936void ar9300_disable_phy_restart(struct ath_hal *ah, int disable_phy_restart) 5937{ 5938 u_int32_t val; 5939 5940 val = OS_REG_READ(ah, AR_PHY_RESTART); 5941 if (disable_phy_restart) { 5942 val &= ~AR_PHY_RESTART_ENA; 5943 AH9300(ah)->ah_phyrestart_disabled = 1; 5944 } else { 5945 val |= AR_PHY_RESTART_ENA; 5946 AH9300(ah)->ah_phyrestart_disabled = 0; 5947 } 5948 OS_REG_WRITE(ah, AR_PHY_RESTART, val); 5949 5950 val = OS_REG_READ(ah, AR_PHY_RESTART); 5951} 5952 5953HAL_BOOL 5954ar9300_interference_is_present(struct ath_hal *ah) 5955{ 5956 int i; 5957 struct ath_hal_private *ahpriv = AH_PRIVATE(ah); 5958 const struct ieee80211_channel *chan = ahpriv->ah_curchan; 5959 HAL_CHANNEL_INTERNAL *ichan = ath_hal_checkchannel(ah, chan); 5960 5961 if (ichan == NULL) { 5962 ath_hal_printf(ah, "%s: called with ichan=NULL\n", __func__); 5963 return AH_FALSE; 5964 } 5965 5966 /* This function is called after a stuck beacon, if EACS is enabled. 5967 * If CW interference is severe, then HW goes into a loop of continuous 5968 * stuck beacons and resets. On reset the NF cal history is cleared. 5969 * So the median value of the history cannot be used - 5970 * hence check if any value (Chain 0/Primary Channel) 5971 * is outside the bounds. 5972 */ 5973 HAL_NFCAL_HIST_FULL *h = AH_HOME_CHAN_NFCAL_HIST(ah, ichan); 5974 for (i = 0; i < HAL_NF_CAL_HIST_LEN_FULL; i++) { 5975 if (h->nf_cal_buffer[i][0] > 5976 AH9300(ah)->nfp->nominal + AH9300(ah)->nf_cw_int_delta) 5977 { 5978 return AH_TRUE; 5979 } 5980 5981 } 5982 return AH_FALSE; 5983} 5984 5985#if ATH_SUPPORT_CRDC 5986void 5987ar9300_crdc_rx_notify(struct ath_hal *ah, struct ath_rx_status *rxs) 5988{ 5989 struct ath_hal_private *ahpriv = AH_PRIVATE(ah); 5990 int rssi_index; 5991 5992 if ((!AR_SREV_WASP(ah)) || 5993 (!ahpriv->ah_config.ath_hal_crdc_enable)) { 5994 return; 5995 } 5996 5997 if (rxs->rs_isaggr && rxs->rs_moreaggr) { 5998 return; 5999 } 6000 6001 if ((rxs->rs_rssi_ctl0 >= HAL_RSSI_BAD) || 6002 (rxs->rs_rssi_ctl1 >= HAL_RSSI_BAD)) { 6003 return; 6004 } 6005 6006 rssi_index = ah->ah_crdc_rssi_ptr % HAL_MAX_CRDC_RSSI_SAMPLE; 6007 6008 ah->ah_crdc_rssi_sample[0][rssi_index] = rxs->rs_rssi_ctl0; 6009 ah->ah_crdc_rssi_sample[1][rssi_index] = rxs->rs_rssi_ctl1; 6010 6011 ah->ah_crdc_rssi_ptr++; 6012} 6013 6014static int 6015ar9300_crdc_avg_rssi(struct ath_hal *ah, int chain) 6016{ 6017 int crdc_rssi_sum = 0; 6018 int crdc_rssi_ptr = ah->ah_crdc_rssi_ptr, i; 6019 struct ath_hal_private *ahpriv = AH_PRIVATE(ah); 6020 int crdc_window = ahpriv->ah_config.ath_hal_crdc_window; 6021 6022 if (crdc_window > HAL_MAX_CRDC_RSSI_SAMPLE) { 6023 crdc_window = HAL_MAX_CRDC_RSSI_SAMPLE; 6024 } 6025 6026 for (i = 1; i <= crdc_window; i++) { 6027 crdc_rssi_sum += 6028 ah->ah_crdc_rssi_sample[chain] 6029 [(crdc_rssi_ptr - i) % HAL_MAX_CRDC_RSSI_SAMPLE]; 6030 } 6031 6032 return crdc_rssi_sum / crdc_window; 6033} 6034 6035static void 6036ar9300_crdc_activate(struct ath_hal *ah, int rssi_diff, int enable) 6037{ 6038 int val, orig_val; 6039 struct ath_hal_private *ahpriv = AH_PRIVATE(ah); 6040 int crdc_numerator = ahpriv->ah_config.ath_hal_crdc_numerator; 6041 int crdc_denominator = ahpriv->ah_config.ath_hal_crdc_denominator; 6042 int c = (rssi_diff * crdc_numerator) / crdc_denominator; 6043 6044 val = orig_val = OS_REG_READ(ah, AR_PHY_MULTICHAIN_CTRL); 6045 val &= 0xffffff00; 6046 if (enable) { 6047 val |= 0x1; 6048 val |= ((c << 1) & 0xff); 6049 } 6050 OS_REG_WRITE(ah, AR_PHY_MULTICHAIN_CTRL, val); 6051 HALDEBUG(ah, HAL_DEBUG_CALIBRATE, "diff: %02d comp: %02d reg: %08x %08x\n", 6052 rssi_diff, c, orig_val, val); 6053} 6054 6055 6056void ar9300_chain_rssi_diff_compensation(struct ath_hal *ah) 6057{ 6058 struct ath_hal_private *ahpriv = AH_PRIVATE(ah); 6059 int crdc_window = ahpriv->ah_config.ath_hal_crdc_window; 6060 int crdc_rssi_ptr = ah->ah_crdc_rssi_ptr; 6061 int crdc_rssi_thresh = ahpriv->ah_config.ath_hal_crdc_rssithresh; 6062 int crdc_diff_thresh = ahpriv->ah_config.ath_hal_crdc_diffthresh; 6063 int avg_rssi[2], avg_rssi_diff; 6064 6065 if ((!AR_SREV_WASP(ah)) || 6066 (!ahpriv->ah_config.ath_hal_crdc_enable)) { 6067 if (ah->ah_crdc_rssi_ptr) { 6068 ar9300_crdc_activate(ah, 0, 0); 6069 ah->ah_crdc_rssi_ptr = 0; 6070 } 6071 return; 6072 } 6073 6074 if (crdc_window > HAL_MAX_CRDC_RSSI_SAMPLE) { 6075 crdc_window = HAL_MAX_CRDC_RSSI_SAMPLE; 6076 } 6077 6078 if (crdc_rssi_ptr < crdc_window) { 6079 return; 6080 } 6081 6082 avg_rssi[0] = ar9300_crdc_avg_rssi(ah, 0); 6083 avg_rssi[1] = ar9300_crdc_avg_rssi(ah, 1); 6084 avg_rssi_diff = avg_rssi[1] - avg_rssi[0]; 6085 6086 HALDEBUG(ah, HAL_DEBUG_CALIBRATE, "crdc: avg: %02d %02d ", 6087 avg_rssi[0], avg_rssi[1]); 6088 6089 if ((avg_rssi[0] < crdc_rssi_thresh) && 6090 (avg_rssi[1] < crdc_rssi_thresh)) { 6091 ar9300_crdc_activate(ah, 0, 0); 6092 } else { 6093 if (ABS(avg_rssi_diff) >= crdc_diff_thresh) { 6094 ar9300_crdc_activate(ah, avg_rssi_diff, 1); 6095 } else { 6096 ar9300_crdc_activate(ah, 0, 1); 6097 } 6098 } 6099} 6100#endif 6101 6102#if ATH_ANT_DIV_COMB 6103HAL_BOOL 6104ar9300_ant_ctrl_set_lna_div_use_bt_ant(struct ath_hal *ah, HAL_BOOL enable, const struct ieee80211_channel *chan) 6105{ 6106 u_int32_t value; 6107 u_int32_t regval; 6108 struct ath_hal_9300 *ahp = AH9300(ah); 6109 HAL_CHANNEL_INTERNAL *ichan; 6110 struct ath_hal_private *ahpriv = AH_PRIVATE(ah); 6111 HAL_CAPABILITIES *pcap = &ahpriv->ah_caps; 6112 6113 if (AR_SREV_POSEIDON(ah)) { 6114 // Make sure this scheme is only used for WB225(Astra) 6115 ahp->ah_lna_div_use_bt_ant_enable = enable; 6116 6117 ichan = ar9300_check_chan(ah, chan); 6118 if ( ichan == AH_NULL ) { 6119 HALDEBUG(ah, HAL_DEBUG_CHANNEL, "%s: invalid channel %u/0x%x; no mapping\n", 6120 __func__, chan->ic_freq, chan->ic_flags); 6121 return AH_FALSE; 6122 } 6123 6124 if ( enable == TRUE ) { 6125 pcap->halAntDivCombSupport = TRUE; 6126 } else { 6127 pcap->halAntDivCombSupport = pcap->halAntDivCombSupportOrg; 6128 } 6129 6130#define AR_SWITCH_TABLE_COM2_ALL (0xffffff) 6131#define AR_SWITCH_TABLE_COM2_ALL_S (0) 6132 value = ar9300_ant_ctrl_common2_get(ah, IS_CHAN_2GHZ(ichan)); 6133 if ( enable == TRUE ) { 6134 value &= ~AR_SWITCH_TABLE_COM2_ALL; 6135 value |= ah->ah_config.ath_hal_ant_ctrl_comm2g_switch_enable; 6136 } 6137 OS_REG_RMW_FIELD(ah, AR_PHY_SWITCH_COM_2, AR_SWITCH_TABLE_COM2_ALL, value); 6138 6139 value = ar9300_eeprom_get(ahp, EEP_ANTDIV_control); 6140 /* main_lnaconf, alt_lnaconf, main_tb, alt_tb */ 6141 regval = OS_REG_READ(ah, AR_PHY_MC_GAIN_CTRL); 6142 regval &= (~ANT_DIV_CONTROL_ALL); /* clear bit 25~30 */ 6143 regval |= (value & 0x3f) << ANT_DIV_CONTROL_ALL_S; 6144 /* enable_lnadiv */ 6145 regval &= (~MULTICHAIN_GAIN_CTRL__ENABLE_ANT_DIV_LNADIV__MASK); 6146 regval |= ((value >> 6) & 0x1) << 6147 MULTICHAIN_GAIN_CTRL__ENABLE_ANT_DIV_LNADIV__SHIFT; 6148 if ( enable == TRUE ) { 6149 regval |= ANT_DIV_ENABLE; 6150 } 6151 OS_REG_WRITE(ah, AR_PHY_MC_GAIN_CTRL, regval); 6152 6153 /* enable fast_div */ 6154 regval = OS_REG_READ(ah, AR_PHY_CCK_DETECT); 6155 regval &= (~BBB_SIG_DETECT__ENABLE_ANT_FAST_DIV__MASK); 6156 regval |= ((value >> 7) & 0x1) << 6157 BBB_SIG_DETECT__ENABLE_ANT_FAST_DIV__SHIFT; 6158 if ( enable == TRUE ) { 6159 regval |= FAST_DIV_ENABLE; 6160 } 6161 OS_REG_WRITE(ah, AR_PHY_CCK_DETECT, regval); 6162 6163 if ( AR_SREV_POSEIDON_11_OR_LATER(ah) ) { 6164 if (pcap->halAntDivCombSupport) { 6165 /* If support DivComb, set MAIN to LNA1 and ALT to LNA2 at the first beginning */ 6166 regval = OS_REG_READ(ah, AR_PHY_MC_GAIN_CTRL); 6167 /* clear bit 25~30 main_lnaconf, alt_lnaconf, main_tb, alt_tb */ 6168 regval &= (~(MULTICHAIN_GAIN_CTRL__ANT_DIV_MAIN_LNACONF__MASK | 6169 MULTICHAIN_GAIN_CTRL__ANT_DIV_ALT_LNACONF__MASK | 6170 MULTICHAIN_GAIN_CTRL__ANT_DIV_ALT_GAINTB__MASK | 6171 MULTICHAIN_GAIN_CTRL__ANT_DIV_MAIN_GAINTB__MASK)); 6172 regval |= (HAL_ANT_DIV_COMB_LNA1 << 6173 MULTICHAIN_GAIN_CTRL__ANT_DIV_MAIN_LNACONF__SHIFT); 6174 regval |= (HAL_ANT_DIV_COMB_LNA2 << 6175 MULTICHAIN_GAIN_CTRL__ANT_DIV_ALT_LNACONF__SHIFT); 6176 OS_REG_WRITE(ah, AR_PHY_MC_GAIN_CTRL, regval); 6177 } 6178 } 6179 6180 return AH_TRUE; 6181 } else { 6182 return AH_TRUE; 6183 } 6184} 6185#endif /* ATH_ANT_DIV_COMB */ 6186