Linux Kernel  3.7.1
 All Data Structures Namespaces Files Functions Variables Typedefs Enumerations Enumerator Macros Groups Pages
ar9003_phy.c
Go to the documentation of this file.
1 /*
2  * Copyright (c) 2010-2011 Atheros Communications 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
9  * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
10  * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
11  * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
12  * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
13  * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
14  * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
15  */
16 
17 #include <linux/export.h>
18 #include "hw.h"
19 #include "ar9003_phy.h"
20 
21 static const int firstep_table[] =
22 /* level: 0 1 2 3 4 5 6 7 8 */
23  { -4, -2, 0, 2, 4, 6, 8, 10, 12 }; /* lvl 0-8, default 2 */
24 
25 static const int cycpwrThr1_table[] =
26 /* level: 0 1 2 3 4 5 6 7 8 */
27  { -6, -4, -2, 0, 2, 4, 6, 8 }; /* lvl 0-7, default 3 */
28 
29 /*
30  * register values to turn OFDM weak signal detection OFF
31  */
32 static const int m1ThreshLow_off = 127;
33 static const int m2ThreshLow_off = 127;
34 static const int m1Thresh_off = 127;
35 static const int m2Thresh_off = 127;
36 static const int m2CountThr_off = 31;
37 static const int m2CountThrLow_off = 63;
38 static const int m1ThreshLowExt_off = 127;
39 static const int m2ThreshLowExt_off = 127;
40 static const int m1ThreshExt_off = 127;
41 static const int m2ThreshExt_off = 127;
42 
68 static int ar9003_hw_set_channel(struct ath_hw *ah, struct ath9k_channel *chan)
69 {
70  u16 bMode, fracMode = 0, aModeRefSel = 0;
71  u32 freq, channelSel = 0, reg32 = 0;
72  struct chan_centers centers;
73  int loadSynthChannel;
74 
75  ath9k_hw_get_channel_centers(ah, chan, &centers);
76  freq = centers.synth_center;
77 
78  if (freq < 4800) { /* 2 GHz, fractional mode */
79  if (AR_SREV_9330(ah)) {
80  u32 chan_frac;
81  u32 div;
82 
83  if (ah->is_clk_25mhz)
84  div = 75;
85  else
86  div = 120;
87 
88  channelSel = (freq * 4) / div;
89  chan_frac = (((freq * 4) % div) * 0x20000) / div;
90  channelSel = (channelSel << 17) | chan_frac;
91  } else if (AR_SREV_9485(ah) || AR_SREV_9565(ah)) {
92  u32 chan_frac;
93 
94  /*
95  * freq_ref = 40 / (refdiva >> amoderefsel); where refdiva=1 and amoderefsel=0
96  * ndiv = ((chan_mhz * 4) / 3) / freq_ref;
97  * chansel = int(ndiv), chanfrac = (ndiv - chansel) * 0x20000
98  */
99  channelSel = (freq * 4) / 120;
100  chan_frac = (((freq * 4) % 120) * 0x20000) / 120;
101  channelSel = (channelSel << 17) | chan_frac;
102  } else if (AR_SREV_9340(ah) || AR_SREV_9550(ah)) {
103  if (ah->is_clk_25mhz) {
104  u32 chan_frac;
105 
106  channelSel = (freq * 2) / 75;
107  chan_frac = (((freq * 2) % 75) * 0x20000) / 75;
108  channelSel = (channelSel << 17) | chan_frac;
109  } else
110  channelSel = CHANSEL_2G(freq) >> 1;
111  } else
112  channelSel = CHANSEL_2G(freq);
113  /* Set to 2G mode */
114  bMode = 1;
115  } else {
116  if ((AR_SREV_9340(ah) || AR_SREV_9550(ah)) &&
117  ah->is_clk_25mhz) {
118  u32 chan_frac;
119 
120  channelSel = freq / 75;
121  chan_frac = ((freq % 75) * 0x20000) / 75;
122  channelSel = (channelSel << 17) | chan_frac;
123  } else {
124  channelSel = CHANSEL_5G(freq);
125  /* Doubler is ON, so, divide channelSel by 2. */
126  channelSel >>= 1;
127  }
128  /* Set to 5G mode */
129  bMode = 0;
130  }
131 
132  /* Enable fractional mode for all channels */
133  fracMode = 1;
134  aModeRefSel = 0;
135  loadSynthChannel = 0;
136 
137  reg32 = (bMode << 29);
138  REG_WRITE(ah, AR_PHY_SYNTH_CONTROL, reg32);
139 
140  /* Enable Long shift Select for Synthesizer */
143 
144  /* Program Synth. setting */
145  reg32 = (channelSel << 2) | (fracMode << 30) |
146  (aModeRefSel << 28) | (loadSynthChannel << 31);
147  REG_WRITE(ah, AR_PHY_65NM_CH0_SYNTH7, reg32);
148 
149  /* Toggle Load Synth channel bit */
150  loadSynthChannel = 1;
151  reg32 = (channelSel << 2) | (fracMode << 30) |
152  (aModeRefSel << 28) | (loadSynthChannel << 31);
153  REG_WRITE(ah, AR_PHY_65NM_CH0_SYNTH7, reg32);
154 
155  ah->curchan = chan;
156 
157  return 0;
158 }
159 
170 static void ar9003_hw_spur_mitigate_mrc_cck(struct ath_hw *ah,
171  struct ath9k_channel *chan)
172 {
173  static const u32 spur_freq[4] = { 2420, 2440, 2464, 2480 };
174  int cur_bb_spur, negative = 0, cck_spur_freq;
175  int i;
176  int range, max_spur_cnts, synth_freq;
177  u8 *spur_fbin_ptr = ar9003_get_spur_chan_ptr(ah, IS_CHAN_2GHZ(chan));
178 
179  /*
180  * Need to verify range +/- 10 MHz in control channel, otherwise spur
181  * is out-of-band and can be ignored.
182  */
183 
184  if (AR_SREV_9485(ah) || AR_SREV_9340(ah) || AR_SREV_9330(ah) ||
185  AR_SREV_9550(ah)) {
186  if (spur_fbin_ptr[0] == 0) /* No spur */
187  return;
188  max_spur_cnts = 5;
189  if (IS_CHAN_HT40(chan)) {
190  range = 19;
193  synth_freq = chan->channel + 10;
194  else
195  synth_freq = chan->channel - 10;
196  } else {
197  range = 10;
198  synth_freq = chan->channel;
199  }
200  } else {
201  range = AR_SREV_9462(ah) ? 5 : 10;
202  max_spur_cnts = 4;
203  synth_freq = chan->channel;
204  }
205 
206  for (i = 0; i < max_spur_cnts; i++) {
207  if (AR_SREV_9462(ah) && (i == 0 || i == 3))
208  continue;
209 
210  negative = 0;
211  if (AR_SREV_9485(ah) || AR_SREV_9340(ah) || AR_SREV_9330(ah) ||
212  AR_SREV_9550(ah))
213  cur_bb_spur = ath9k_hw_fbin2freq(spur_fbin_ptr[i],
214  IS_CHAN_2GHZ(chan));
215  else
216  cur_bb_spur = spur_freq[i];
217 
218  cur_bb_spur -= synth_freq;
219  if (cur_bb_spur < 0) {
220  negative = 1;
221  cur_bb_spur = -cur_bb_spur;
222  }
223  if (cur_bb_spur < range) {
224  cck_spur_freq = (int)((cur_bb_spur << 19) / 11);
225 
226  if (negative == 1)
227  cck_spur_freq = -cck_spur_freq;
228 
229  cck_spur_freq = cck_spur_freq & 0xfffff;
230 
237  0x2);
240  0x1);
243  cck_spur_freq);
244 
245  return;
246  }
247  }
248 
255 }
256 
257 /* Clean all spur register fields */
258 static void ar9003_hw_spur_ofdm_clear(struct ath_hw *ah)
259 {
278 
299 }
300 
301 static void ar9003_hw_spur_ofdm(struct ath_hw *ah,
302  int freq_offset,
303  int spur_freq_sd,
304  int spur_delta_phase,
305  int spur_subchannel_sd,
306  int range,
307  int synth_freq)
308 {
309  int mask_index = 0;
310 
311  /* OFDM Spur mitigation */
315  AR_PHY_TIMING11_SPUR_FREQ_SD, spur_freq_sd);
317  AR_PHY_TIMING11_SPUR_DELTA_PHASE, spur_delta_phase);
319  AR_PHY_SFCORR_EXT_SPUR_SUBCHANNEL_SD, spur_subchannel_sd);
322 
323  if (!(AR_SREV_9565(ah) && range == 10 && synth_freq == 2437))
326 
333 
334  if (REG_READ_FIELD(ah, AR_PHY_MODE,
335  AR_PHY_MODE_DYNAMIC) == 0x1)
338 
339  mask_index = (freq_offset << 4) / 5;
340  if (mask_index < 0)
341  mask_index = mask_index - 1;
342 
343  mask_index = mask_index & 0x7f;
344 
365 }
366 
367 static void ar9003_hw_spur_ofdm_9565(struct ath_hw *ah,
368  int freq_offset)
369 {
370  int mask_index = 0;
371 
372  mask_index = (freq_offset << 4) / 5;
373  if (mask_index < 0)
374  mask_index = mask_index - 1;
375 
376  mask_index = mask_index & 0x7f;
377 
380  mask_index);
381 
382  /* A == B */
385  mask_index);
386 
389  mask_index);
394 
395  /* A == B */
398 }
399 
400 static void ar9003_hw_spur_ofdm_work(struct ath_hw *ah,
401  struct ath9k_channel *chan,
402  int freq_offset,
403  int range,
404  int synth_freq)
405 {
406  int spur_freq_sd = 0;
407  int spur_subchannel_sd = 0;
408  int spur_delta_phase = 0;
409 
410  if (IS_CHAN_HT40(chan)) {
411  if (freq_offset < 0) {
413  AR_PHY_GC_DYN2040_PRI_CH) == 0x0)
414  spur_subchannel_sd = 1;
415  else
416  spur_subchannel_sd = 0;
417 
418  spur_freq_sd = ((freq_offset + 10) << 9) / 11;
419 
420  } else {
422  AR_PHY_GC_DYN2040_PRI_CH) == 0x0)
423  spur_subchannel_sd = 0;
424  else
425  spur_subchannel_sd = 1;
426 
427  spur_freq_sd = ((freq_offset - 10) << 9) / 11;
428 
429  }
430 
431  spur_delta_phase = (freq_offset << 17) / 5;
432 
433  } else {
434  spur_subchannel_sd = 0;
435  spur_freq_sd = (freq_offset << 9) /11;
436  spur_delta_phase = (freq_offset << 18) / 5;
437  }
438 
439  spur_freq_sd = spur_freq_sd & 0x3ff;
440  spur_delta_phase = spur_delta_phase & 0xfffff;
441 
442  ar9003_hw_spur_ofdm(ah,
443  freq_offset,
444  spur_freq_sd,
445  spur_delta_phase,
446  spur_subchannel_sd,
447  range, synth_freq);
448 }
449 
450 /* Spur mitigation for OFDM */
451 static void ar9003_hw_spur_mitigate_ofdm(struct ath_hw *ah,
452  struct ath9k_channel *chan)
453 {
454  int synth_freq;
455  int range = 10;
456  int freq_offset = 0;
457  int mode;
458  u8* spurChansPtr;
459  unsigned int i;
460  struct ar9300_eeprom *eep = &ah->eeprom.ar9300_eep;
461 
462  if (IS_CHAN_5GHZ(chan)) {
463  spurChansPtr = &(eep->modalHeader5G.spurChans[0]);
464  mode = 0;
465  }
466  else {
467  spurChansPtr = &(eep->modalHeader2G.spurChans[0]);
468  mode = 1;
469  }
470 
471  if (spurChansPtr[0] == 0)
472  return; /* No spur in the mode */
473 
474  if (IS_CHAN_HT40(chan)) {
475  range = 19;
477  AR_PHY_GC_DYN2040_PRI_CH) == 0x0)
478  synth_freq = chan->channel - 10;
479  else
480  synth_freq = chan->channel + 10;
481  } else {
482  range = 10;
483  synth_freq = chan->channel;
484  }
485 
486  ar9003_hw_spur_ofdm_clear(ah);
487 
488  for (i = 0; i < AR_EEPROM_MODAL_SPURS && spurChansPtr[i]; i++) {
489  freq_offset = ath9k_hw_fbin2freq(spurChansPtr[i], mode);
490  freq_offset -= synth_freq;
491  if (abs(freq_offset) < range) {
492  ar9003_hw_spur_ofdm_work(ah, chan, freq_offset,
493  range, synth_freq);
494 
495  if (AR_SREV_9565(ah) && (i < 4)) {
496  freq_offset = ath9k_hw_fbin2freq(spurChansPtr[i + 1],
497  mode);
498  freq_offset -= synth_freq;
499  if (abs(freq_offset) < range)
500  ar9003_hw_spur_ofdm_9565(ah, freq_offset);
501  }
502 
503  break;
504  }
505  }
506 }
507 
508 static void ar9003_hw_spur_mitigate(struct ath_hw *ah,
509  struct ath9k_channel *chan)
510 {
511  if (!AR_SREV_9565(ah))
512  ar9003_hw_spur_mitigate_mrc_cck(ah, chan);
513  ar9003_hw_spur_mitigate_ofdm(ah, chan);
514 }
515 
516 static u32 ar9003_hw_compute_pll_control(struct ath_hw *ah,
517  struct ath9k_channel *chan)
518 {
519  u32 pll;
520 
521  pll = SM(0x5, AR_RTC_9300_PLL_REFDIV);
522 
523  if (chan && IS_CHAN_HALF_RATE(chan))
524  pll |= SM(0x1, AR_RTC_9300_PLL_CLKSEL);
525  else if (chan && IS_CHAN_QUARTER_RATE(chan))
526  pll |= SM(0x2, AR_RTC_9300_PLL_CLKSEL);
527 
528  pll |= SM(0x2c, AR_RTC_9300_PLL_DIV);
529 
530  return pll;
531 }
532 
533 static void ar9003_hw_set_channel_regs(struct ath_hw *ah,
534  struct ath9k_channel *chan)
535 {
536  u32 phymode;
537  u32 enableDacFifo = 0;
538 
539  enableDacFifo =
541 
542  /* Enable 11n HT, 20 MHz */
544  AR_PHY_GC_SHORT_GI_40 | enableDacFifo;
545 
546  /* Configure baseband for dynamic 20/40 operation */
547  if (IS_CHAN_HT40(chan)) {
548  phymode |= AR_PHY_GC_DYN2040_EN;
549  /* Configure control (primary) channel at +-10MHz */
550  if ((chan->chanmode == CHANNEL_A_HT40PLUS) ||
551  (chan->chanmode == CHANNEL_G_HT40PLUS))
552  phymode |= AR_PHY_GC_DYN2040_PRI_CH;
553 
554  }
555 
556  /* make sure we preserve INI settings */
557  phymode |= REG_READ(ah, AR_PHY_GEN_CTRL);
558  /* turn off Green Field detection for STA for now */
559  phymode &= ~AR_PHY_GC_GF_DETECT_EN;
560 
561  REG_WRITE(ah, AR_PHY_GEN_CTRL, phymode);
562 
563  /* Configure MAC for 20/40 operation */
565 
566  /* global transmit timeout (25 TUs default)*/
568  /* carrier sense timeout */
570 }
571 
572 static void ar9003_hw_init_bb(struct ath_hw *ah,
573  struct ath9k_channel *chan)
574 {
575  u32 synthDelay;
576 
577  /*
578  * Wait for the frequency synth to settle (synth goes on
579  * via AR_PHY_ACTIVE_EN). Read the phy active delay register.
580  * Value is in 100ns increments.
581  */
582  synthDelay = REG_READ(ah, AR_PHY_RX_DELAY) & AR_PHY_RX_DELAY_DELAY;
583 
584  /* Activate the PHY (includes baseband activate + synthesizer on) */
586  ath9k_hw_synth_delay(ah, chan, synthDelay);
587 }
588 
589 static void ar9003_hw_set_chain_masks(struct ath_hw *ah, u8 rx, u8 tx)
590 {
591  switch (rx) {
592  case 0x5:
595  case 0x3:
596  case 0x1:
597  case 0x2:
598  case 0x7:
601  break;
602  default:
603  break;
604  }
605 
606  if ((ah->caps.hw_caps & ATH9K_HW_CAP_APM) && (tx == 0x7))
607  REG_WRITE(ah, AR_SELFGEN_MASK, 0x3);
608  else
609  REG_WRITE(ah, AR_SELFGEN_MASK, tx);
610 
611  if (tx == 0x5) {
614  }
615 }
616 
617 /*
618  * Override INI values with chip specific configuration.
619  */
620 static void ar9003_hw_override_ini(struct ath_hw *ah)
621 {
622  u32 val;
623 
624  /*
625  * Set the RX_ABORT and RX_DIS and clear it only after
626  * RXE is set for MAC. This prevents frames with
627  * corrupted descriptor status.
628  */
630 
631  /*
632  * For AR9280 and above, there is a new feature that allows
633  * Multicast search based on both MAC Address and Key ID. By default,
634  * this feature is enabled. But since the driver is not using this
635  * feature, we switch it off; otherwise multicast search based on
636  * MAC addr only will fail.
637  */
641 
644 }
645 
646 static void ar9003_hw_prog_ini(struct ath_hw *ah,
647  struct ar5416IniArray *iniArr,
648  int column)
649 {
650  unsigned int i, regWrites = 0;
651 
652  /* New INI format: Array may be undefined (pre, core, post arrays) */
653  if (!iniArr->ia_array)
654  return;
655 
656  /*
657  * New INI format: Pre, core, and post arrays for a given subsystem
658  * may be modal (> 2 columns) or non-modal (2 columns). Determine if
659  * the array is non-modal and force the column to 1.
660  */
661  if (column >= iniArr->ia_columns)
662  column = 1;
663 
664  for (i = 0; i < iniArr->ia_rows; i++) {
665  u32 reg = INI_RA(iniArr, i, 0);
666  u32 val = INI_RA(iniArr, i, column);
667 
668  REG_WRITE(ah, reg, val);
669 
670  DO_DELAY(regWrites);
671  }
672 }
673 
674 static int ar9550_hw_get_modes_txgain_index(struct ath_hw *ah,
675  struct ath9k_channel *chan)
676 {
677  int ret;
678 
679  switch (chan->chanmode) {
680  case CHANNEL_A:
681  case CHANNEL_A_HT20:
682  if (chan->channel <= 5350)
683  ret = 1;
684  else if ((chan->channel > 5350) && (chan->channel <= 5600))
685  ret = 3;
686  else
687  ret = 5;
688  break;
689 
690  case CHANNEL_A_HT40PLUS:
691  case CHANNEL_A_HT40MINUS:
692  if (chan->channel <= 5350)
693  ret = 2;
694  else if ((chan->channel > 5350) && (chan->channel <= 5600))
695  ret = 4;
696  else
697  ret = 6;
698  break;
699 
700  case CHANNEL_G:
701  case CHANNEL_G_HT20:
702  case CHANNEL_B:
703  ret = 8;
704  break;
705 
706  case CHANNEL_G_HT40PLUS:
707  case CHANNEL_G_HT40MINUS:
708  ret = 7;
709  break;
710 
711  default:
712  ret = -EINVAL;
713  }
714 
715  return ret;
716 }
717 
718 static int ar9003_hw_process_ini(struct ath_hw *ah,
719  struct ath9k_channel *chan)
720 {
721  unsigned int regWrites = 0, i;
722  u32 modesIndex;
723 
724  switch (chan->chanmode) {
725  case CHANNEL_A:
726  case CHANNEL_A_HT20:
727  modesIndex = 1;
728  break;
729  case CHANNEL_A_HT40PLUS:
730  case CHANNEL_A_HT40MINUS:
731  modesIndex = 2;
732  break;
733  case CHANNEL_G:
734  case CHANNEL_G_HT20:
735  case CHANNEL_B:
736  modesIndex = 4;
737  break;
738  case CHANNEL_G_HT40PLUS:
739  case CHANNEL_G_HT40MINUS:
740  modesIndex = 3;
741  break;
742 
743  default:
744  return -EINVAL;
745  }
746 
747  for (i = 0; i < ATH_INI_NUM_SPLIT; i++) {
748  ar9003_hw_prog_ini(ah, &ah->iniSOC[i], modesIndex);
749  ar9003_hw_prog_ini(ah, &ah->iniMac[i], modesIndex);
750  ar9003_hw_prog_ini(ah, &ah->iniBB[i], modesIndex);
751  ar9003_hw_prog_ini(ah, &ah->iniRadio[i], modesIndex);
752  if (i == ATH_INI_POST && AR_SREV_9462_20(ah))
753  ar9003_hw_prog_ini(ah,
755  modesIndex);
756  }
757 
758  REG_WRITE_ARRAY(&ah->iniModesRxGain, 1, regWrites);
759  if (AR_SREV_9550(ah))
760  REG_WRITE_ARRAY(&ah->ini_modes_rx_gain_bounds, modesIndex,
761  regWrites);
762 
763  if (AR_SREV_9550(ah)) {
764  int modes_txgain_index;
765 
766  modes_txgain_index = ar9550_hw_get_modes_txgain_index(ah, chan);
767  if (modes_txgain_index < 0)
768  return -EINVAL;
769 
770  REG_WRITE_ARRAY(&ah->iniModesTxGain, modes_txgain_index,
771  regWrites);
772  } else {
773  REG_WRITE_ARRAY(&ah->iniModesTxGain, modesIndex, regWrites);
774  }
775 
776  /*
777  * For 5GHz channels requiring Fast Clock, apply
778  * different modal values.
779  */
780  if (IS_CHAN_A_FAST_CLOCK(ah, chan))
782  modesIndex, regWrites);
783 
784  REG_WRITE_ARRAY(&ah->iniAdditional, 1, regWrites);
785 
786  if (chan->channel == 2484)
787  ar9003_hw_prog_ini(ah, &ah->ini_japan2484, 1);
788 
789  if (AR_SREV_9462(ah) || AR_SREV_9565(ah))
792 
793  ah->modes_index = modesIndex;
794  ar9003_hw_override_ini(ah);
795  ar9003_hw_set_channel_regs(ah, chan);
796  ar9003_hw_set_chain_masks(ah, ah->rxchainmask, ah->txchainmask);
797  ath9k_hw_apply_txpower(ah, chan, false);
798 
799  if (AR_SREV_9462(ah) || AR_SREV_9565(ah)) {
802  ah->enabled_cals |= TX_IQ_CAL;
803  else
804  ah->enabled_cals &= ~TX_IQ_CAL;
805 
807  ah->enabled_cals |= TX_CL_CAL;
808  else
809  ah->enabled_cals &= ~TX_CL_CAL;
810  }
811 
812  return 0;
813 }
814 
815 static void ar9003_hw_set_rfmode(struct ath_hw *ah,
816  struct ath9k_channel *chan)
817 {
818  u32 rfMode = 0;
819 
820  if (chan == NULL)
821  return;
822 
823  rfMode |= (IS_CHAN_B(chan) || IS_CHAN_G(chan))
825 
826  if (IS_CHAN_A_FAST_CLOCK(ah, chan))
828  if (IS_CHAN_QUARTER_RATE(chan))
829  rfMode |= AR_PHY_MODE_QUARTER;
830  if (IS_CHAN_HALF_RATE(chan))
831  rfMode |= AR_PHY_MODE_HALF;
832 
833  if (rfMode & (AR_PHY_MODE_QUARTER | AR_PHY_MODE_HALF))
836 
837  REG_WRITE(ah, AR_PHY_MODE, rfMode);
838 }
839 
840 static void ar9003_hw_mark_phy_inactive(struct ath_hw *ah)
841 {
843 }
844 
845 static void ar9003_hw_set_delta_slope(struct ath_hw *ah,
846  struct ath9k_channel *chan)
847 {
848  u32 coef_scaled, ds_coef_exp, ds_coef_man;
849  u32 clockMhzScaled = 0x64000000;
850  struct chan_centers centers;
851 
852  /*
853  * half and quarter rate can divide the scaled clock by 2 or 4
854  * scale for selected channel bandwidth
855  */
856  if (IS_CHAN_HALF_RATE(chan))
857  clockMhzScaled = clockMhzScaled >> 1;
858  else if (IS_CHAN_QUARTER_RATE(chan))
859  clockMhzScaled = clockMhzScaled >> 2;
860 
861  /*
862  * ALGO -> coef = 1e8/fcarrier*fclock/40;
863  * scaled coef to provide precision for this floating calculation
864  */
865  ath9k_hw_get_channel_centers(ah, chan, &centers);
866  coef_scaled = clockMhzScaled / centers.synth_center;
867 
868  ath9k_hw_get_delta_slope_vals(ah, coef_scaled, &ds_coef_man,
869  &ds_coef_exp);
870 
872  AR_PHY_TIMING3_DSC_MAN, ds_coef_man);
874  AR_PHY_TIMING3_DSC_EXP, ds_coef_exp);
875 
876  /*
877  * For Short GI,
878  * scaled coeff is 9/10 that of normal coeff
879  */
880  coef_scaled = (9 * coef_scaled) / 10;
881 
882  ath9k_hw_get_delta_slope_vals(ah, coef_scaled, &ds_coef_man,
883  &ds_coef_exp);
884 
885  /* for short gi */
887  AR_PHY_SGI_DSC_MAN, ds_coef_man);
889  AR_PHY_SGI_DSC_EXP, ds_coef_exp);
890 }
891 
892 static bool ar9003_hw_rfbus_req(struct ath_hw *ah)
893 {
897 }
898 
899 /*
900  * Wait for the frequency synth to settle (synth goes on via PHY_ACTIVE_EN).
901  * Read the phy active delay register. Value is in 100ns increments.
902  */
903 static void ar9003_hw_rfbus_done(struct ath_hw *ah)
904 {
906 
907  ath9k_hw_synth_delay(ah, ah->curchan, synthDelay);
908 
909  REG_WRITE(ah, AR_PHY_RFBUS_REQ, 0);
910 }
911 
912 static bool ar9003_hw_ani_control(struct ath_hw *ah,
913  enum ath9k_ani_cmd cmd, int param)
914 {
915  struct ath_common *common = ath9k_hw_common(ah);
916  struct ath9k_channel *chan = ah->curchan;
917  struct ar5416AniState *aniState = &chan->ani;
918  s32 value, value2;
919 
920  switch (cmd & ah->ani_function) {
922  /*
923  * on == 1 means ofdm weak signal detection is ON
924  * on == 1 is the default, for less noise immunity
925  *
926  * on == 0 means ofdm weak signal detection is OFF
927  * on == 0 means more noise imm
928  */
929  u32 on = param ? 1 : 0;
930 
931  if (on)
934  else
937 
938  if (on != aniState->ofdmWeakSigDetect) {
939  ath_dbg(common, ANI,
940  "** ch %d: ofdm weak signal: %s=>%s\n",
941  chan->channel,
942  aniState->ofdmWeakSigDetect ?
943  "on" : "off",
944  on ? "on" : "off");
945  if (on)
946  ah->stats.ast_ani_ofdmon++;
947  else
948  ah->stats.ast_ani_ofdmoff++;
949  aniState->ofdmWeakSigDetect = on;
950  }
951  break;
952  }
954  u32 level = param;
955 
956  if (level >= ARRAY_SIZE(firstep_table)) {
957  ath_dbg(common, ANI,
958  "ATH9K_ANI_FIRSTEP_LEVEL: level out of range (%u > %zu)\n",
959  level, ARRAY_SIZE(firstep_table));
960  return false;
961  }
962 
963  /*
964  * make register setting relative to default
965  * from INI file & cap value
966  */
967  value = firstep_table[level] -
968  firstep_table[ATH9K_ANI_FIRSTEP_LVL] +
969  aniState->iniDef.firstep;
970  if (value < ATH9K_SIG_FIRSTEP_SETTING_MIN)
972  if (value > ATH9K_SIG_FIRSTEP_SETTING_MAX)
976  value);
977  /*
978  * we need to set first step low register too
979  * make register setting relative to default
980  * from INI file & cap value
981  */
982  value2 = firstep_table[level] -
983  firstep_table[ATH9K_ANI_FIRSTEP_LVL] +
984  aniState->iniDef.firstepLow;
985  if (value2 < ATH9K_SIG_FIRSTEP_SETTING_MIN)
987  if (value2 > ATH9K_SIG_FIRSTEP_SETTING_MAX)
989 
992 
993  if (level != aniState->firstepLevel) {
994  ath_dbg(common, ANI,
995  "** ch %d: level %d=>%d[def:%d] firstep[level]=%d ini=%d\n",
996  chan->channel,
997  aniState->firstepLevel,
998  level,
1000  value,
1001  aniState->iniDef.firstep);
1002  ath_dbg(common, ANI,
1003  "** ch %d: level %d=>%d[def:%d] firstep_low[level]=%d ini=%d\n",
1004  chan->channel,
1005  aniState->firstepLevel,
1006  level,
1008  value2,
1009  aniState->iniDef.firstepLow);
1010  if (level > aniState->firstepLevel)
1011  ah->stats.ast_ani_stepup++;
1012  else if (level < aniState->firstepLevel)
1013  ah->stats.ast_ani_stepdown++;
1014  aniState->firstepLevel = level;
1015  }
1016  break;
1017  }
1019  u32 level = param;
1020 
1021  if (level >= ARRAY_SIZE(cycpwrThr1_table)) {
1022  ath_dbg(common, ANI,
1023  "ATH9K_ANI_SPUR_IMMUNITY_LEVEL: level out of range (%u > %zu)\n",
1024  level, ARRAY_SIZE(cycpwrThr1_table));
1025  return false;
1026  }
1027  /*
1028  * make register setting relative to default
1029  * from INI file & cap value
1030  */
1031  value = cycpwrThr1_table[level] -
1032  cycpwrThr1_table[ATH9K_ANI_SPUR_IMMUNE_LVL] +
1033  aniState->iniDef.cycpwrThr1;
1034  if (value < ATH9K_SIG_SPUR_IMM_SETTING_MIN)
1036  if (value > ATH9K_SIG_SPUR_IMM_SETTING_MAX)
1040  value);
1041 
1042  /*
1043  * set AR_PHY_EXT_CCA for extension channel
1044  * make register setting relative to default
1045  * from INI file & cap value
1046  */
1047  value2 = cycpwrThr1_table[level] -
1048  cycpwrThr1_table[ATH9K_ANI_SPUR_IMMUNE_LVL] +
1049  aniState->iniDef.cycpwrThr1Ext;
1050  if (value2 < ATH9K_SIG_SPUR_IMM_SETTING_MIN)
1052  if (value2 > ATH9K_SIG_SPUR_IMM_SETTING_MAX)
1055  AR_PHY_EXT_CYCPWR_THR1, value2);
1056 
1057  if (level != aniState->spurImmunityLevel) {
1058  ath_dbg(common, ANI,
1059  "** ch %d: level %d=>%d[def:%d] cycpwrThr1[level]=%d ini=%d\n",
1060  chan->channel,
1061  aniState->spurImmunityLevel,
1062  level,
1064  value,
1065  aniState->iniDef.cycpwrThr1);
1066  ath_dbg(common, ANI,
1067  "** ch %d: level %d=>%d[def:%d] cycpwrThr1Ext[level]=%d ini=%d\n",
1068  chan->channel,
1069  aniState->spurImmunityLevel,
1070  level,
1072  value2,
1073  aniState->iniDef.cycpwrThr1Ext);
1074  if (level > aniState->spurImmunityLevel)
1075  ah->stats.ast_ani_spurup++;
1076  else if (level < aniState->spurImmunityLevel)
1077  ah->stats.ast_ani_spurdown++;
1078  aniState->spurImmunityLevel = level;
1079  }
1080  break;
1081  }
1082  case ATH9K_ANI_MRC_CCK:{
1083  /*
1084  * is_on == 1 means MRC CCK ON (default, less noise imm)
1085  * is_on == 0 means MRC CCK is OFF (more noise imm)
1086  */
1087  bool is_on = param ? 1 : 0;
1089  AR_PHY_MRC_CCK_ENABLE, is_on);
1091  AR_PHY_MRC_CCK_MUX_REG, is_on);
1092  if (is_on != aniState->mrcCCK) {
1093  ath_dbg(common, ANI, "** ch %d: MRC CCK: %s=>%s\n",
1094  chan->channel,
1095  aniState->mrcCCK ? "on" : "off",
1096  is_on ? "on" : "off");
1097  if (is_on)
1098  ah->stats.ast_ani_ccklow++;
1099  else
1100  ah->stats.ast_ani_cckhigh++;
1101  aniState->mrcCCK = is_on;
1102  }
1103  break;
1104  }
1105  case ATH9K_ANI_PRESENT:
1106  break;
1107  default:
1108  ath_dbg(common, ANI, "invalid cmd %u\n", cmd);
1109  return false;
1110  }
1111 
1112  ath_dbg(common, ANI,
1113  "ANI parameters: SI=%d, ofdmWS=%s FS=%d MRCcck=%s listenTime=%d ofdmErrs=%d cckErrs=%d\n",
1114  aniState->spurImmunityLevel,
1115  aniState->ofdmWeakSigDetect ? "on" : "off",
1116  aniState->firstepLevel,
1117  aniState->mrcCCK ? "on" : "off",
1118  aniState->listenTime,
1119  aniState->ofdmPhyErrCount,
1120  aniState->cckPhyErrCount);
1121  return true;
1122 }
1123 
1124 static void ar9003_hw_do_getnf(struct ath_hw *ah,
1125  int16_t nfarray[NUM_NF_READINGS])
1126 {
1127 #define AR_PHY_CH_MINCCA_PWR 0x1FF00000
1128 #define AR_PHY_CH_MINCCA_PWR_S 20
1129 #define AR_PHY_CH_EXT_MINCCA_PWR 0x01FF0000
1130 #define AR_PHY_CH_EXT_MINCCA_PWR_S 16
1131 
1132  int16_t nf;
1133  int i;
1134 
1135  for (i = 0; i < AR9300_MAX_CHAINS; i++) {
1136  if (ah->rxchainmask & BIT(i)) {
1137  nf = MS(REG_READ(ah, ah->nf_regs[i]),
1138  AR_PHY_CH_MINCCA_PWR);
1139  nfarray[i] = sign_extend32(nf, 8);
1140 
1141  if (IS_CHAN_HT40(ah->curchan)) {
1142  u8 ext_idx = AR9300_MAX_CHAINS + i;
1143 
1144  nf = MS(REG_READ(ah, ah->nf_regs[ext_idx]),
1145  AR_PHY_CH_EXT_MINCCA_PWR);
1146  nfarray[ext_idx] = sign_extend32(nf, 8);
1147  }
1148  }
1149  }
1150 }
1151 
1152 static void ar9003_hw_set_nf_limits(struct ath_hw *ah)
1153 {
1156  ah->nf_2g.nominal = AR_PHY_CCA_NOM_VAL_9300_2GHZ;
1159  ah->nf_5g.nominal = AR_PHY_CCA_NOM_VAL_9300_5GHZ;
1160 
1161  if (AR_SREV_9330(ah))
1162  ah->nf_2g.nominal = AR_PHY_CCA_NOM_VAL_9330_2GHZ;
1163 
1164  if (AR_SREV_9462(ah) || AR_SREV_9565(ah)) {
1166  ah->nf_2g.nominal = AR_PHY_CCA_NOM_VAL_9462_2GHZ;
1168  ah->nf_5g.nominal = AR_PHY_CCA_NOM_VAL_9462_5GHZ;
1169  }
1170 }
1171 
1172 /*
1173  * Initialize the ANI register values with default (ini) values.
1174  * This routine is called during a (full) hardware reset after
1175  * all the registers are initialised from the INI.
1176  */
1177 static void ar9003_hw_ani_cache_ini_regs(struct ath_hw *ah)
1178 {
1179  struct ar5416AniState *aniState;
1180  struct ath_common *common = ath9k_hw_common(ah);
1181  struct ath9k_channel *chan = ah->curchan;
1182  struct ath9k_ani_default *iniDef;
1183  u32 val;
1184 
1185  aniState = &ah->curchan->ani;
1186  iniDef = &aniState->iniDef;
1187 
1188  ath_dbg(common, ANI, "ver %d.%d opmode %u chan %d Mhz/0x%x\n",
1189  ah->hw_version.macVersion,
1190  ah->hw_version.macRev,
1191  ah->opmode,
1192  chan->channel,
1193  chan->channelFlags);
1194 
1195  val = REG_READ(ah, AR_PHY_SFCORR);
1196  iniDef->m1Thresh = MS(val, AR_PHY_SFCORR_M1_THRESH);
1197  iniDef->m2Thresh = MS(val, AR_PHY_SFCORR_M2_THRESH);
1198  iniDef->m2CountThr = MS(val, AR_PHY_SFCORR_M2COUNT_THR);
1199 
1200  val = REG_READ(ah, AR_PHY_SFCORR_LOW);
1204 
1205  val = REG_READ(ah, AR_PHY_SFCORR_EXT);
1206  iniDef->m1ThreshExt = MS(val, AR_PHY_SFCORR_EXT_M1_THRESH);
1207  iniDef->m2ThreshExt = MS(val, AR_PHY_SFCORR_EXT_M2_THRESH);
1210  iniDef->firstep = REG_READ_FIELD(ah,
1213  iniDef->firstepLow = REG_READ_FIELD(ah,
1216  iniDef->cycpwrThr1 = REG_READ_FIELD(ah,
1219  iniDef->cycpwrThr1Ext = REG_READ_FIELD(ah,
1222 
1223  /* these levels just got reset to defaults by the INI */
1225  aniState->firstepLevel = ATH9K_ANI_FIRSTEP_LVL;
1227  aniState->mrcCCK = true;
1228 }
1229 
1230 static void ar9003_hw_set_radar_params(struct ath_hw *ah,
1231  struct ath_hw_radar_conf *conf)
1232 {
1233  u32 radar_0 = 0, radar_1 = 0;
1234 
1235  if (!conf) {
1237  return;
1238  }
1239 
1241  radar_0 |= SM(conf->fir_power, AR_PHY_RADAR_0_FIRPWR);
1242  radar_0 |= SM(conf->radar_rssi, AR_PHY_RADAR_0_RRSSI);
1243  radar_0 |= SM(conf->pulse_height, AR_PHY_RADAR_0_HEIGHT);
1244  radar_0 |= SM(conf->pulse_rssi, AR_PHY_RADAR_0_PRSSI);
1245  radar_0 |= SM(conf->pulse_inband, AR_PHY_RADAR_0_INBAND);
1246 
1247  radar_1 |= AR_PHY_RADAR_1_MAX_RRSSI;
1248  radar_1 |= AR_PHY_RADAR_1_BLOCK_CHECK;
1249  radar_1 |= SM(conf->pulse_maxlen, AR_PHY_RADAR_1_MAXLEN);
1251  radar_1 |= SM(conf->radar_inband, AR_PHY_RADAR_1_RELPWR_THRESH);
1252 
1253  REG_WRITE(ah, AR_PHY_RADAR_0, radar_0);
1254  REG_WRITE(ah, AR_PHY_RADAR_1, radar_1);
1255  if (conf->ext_channel)
1257  else
1259 }
1260 
1261 static void ar9003_hw_set_radar_conf(struct ath_hw *ah)
1262 {
1263  struct ath_hw_radar_conf *conf = &ah->radar_conf;
1264 
1265  conf->fir_power = -28;
1266  conf->radar_rssi = 0;
1267  conf->pulse_height = 10;
1268  conf->pulse_rssi = 24;
1269  conf->pulse_inband = 8;
1270  conf->pulse_maxlen = 255;
1271  conf->pulse_inband_step = 12;
1272  conf->radar_inband = 8;
1273 }
1274 
1275 static void ar9003_hw_antdiv_comb_conf_get(struct ath_hw *ah,
1276  struct ath_hw_antcomb_conf *antconf)
1277 {
1278  u32 regval;
1279 
1280  regval = REG_READ(ah, AR_PHY_MC_GAIN_CTRL);
1281  antconf->main_lna_conf = (regval & AR_PHY_ANT_DIV_MAIN_LNACONF) >>
1283  antconf->alt_lna_conf = (regval & AR_PHY_ANT_DIV_ALT_LNACONF) >>
1285  antconf->fast_div_bias = (regval & AR_PHY_ANT_FAST_DIV_BIAS) >>
1287 
1288  if (AR_SREV_9330_11(ah)) {
1289  antconf->lna1_lna2_delta = -9;
1290  antconf->div_group = 1;
1291  } else if (AR_SREV_9485(ah)) {
1292  antconf->lna1_lna2_delta = -9;
1293  antconf->div_group = 2;
1294  } else if (AR_SREV_9565(ah)) {
1295  antconf->lna1_lna2_delta = -3;
1296  antconf->div_group = 3;
1297  } else {
1298  antconf->lna1_lna2_delta = -3;
1299  antconf->div_group = 0;
1300  }
1301 }
1302 
1303 static void ar9003_hw_antdiv_comb_conf_set(struct ath_hw *ah,
1304  struct ath_hw_antcomb_conf *antconf)
1305 {
1306  u32 regval;
1307 
1308  regval = REG_READ(ah, AR_PHY_MC_GAIN_CTRL);
1309  regval &= ~(AR_PHY_ANT_DIV_MAIN_LNACONF |
1314  regval |= ((antconf->main_lna_conf << AR_PHY_ANT_DIV_MAIN_LNACONF_S)
1316  regval |= ((antconf->alt_lna_conf << AR_PHY_ANT_DIV_ALT_LNACONF_S)
1318  regval |= ((antconf->fast_div_bias << AR_PHY_ANT_FAST_DIV_BIAS_S)
1320  regval |= ((antconf->main_gaintb << AR_PHY_ANT_DIV_MAIN_GAINTB_S)
1322  regval |= ((antconf->alt_gaintb << AR_PHY_ANT_DIV_ALT_GAINTB_S)
1324 
1325  REG_WRITE(ah, AR_PHY_MC_GAIN_CTRL, regval);
1326 }
1327 
1328 static void ar9003_hw_antctrl_shared_chain_lnadiv(struct ath_hw *ah,
1329  bool enable)
1330 {
1331  u8 ant_div_ctl1;
1332  u32 regval;
1333 
1334  if (!AR_SREV_9565(ah))
1335  return;
1336 
1338  ant_div_ctl1 = ah->eep_ops->get_eeprom(ah, EEP_ANT_DIV_CTL1);
1339 
1340  regval = REG_READ(ah, AR_PHY_MC_GAIN_CTRL);
1341  regval &= (~AR_ANT_DIV_CTRL_ALL);
1342  regval |= (ant_div_ctl1 & 0x3f) << AR_ANT_DIV_CTRL_ALL_S;
1343  regval &= ~AR_PHY_ANT_DIV_LNADIV;
1344  regval |= ((ant_div_ctl1 >> 6) & 0x1) << AR_PHY_ANT_DIV_LNADIV_S;
1345 
1346  if (enable)
1347  regval |= AR_ANT_DIV_ENABLE;
1348 
1349  REG_WRITE(ah, AR_PHY_MC_GAIN_CTRL, regval);
1350 
1351  regval = REG_READ(ah, AR_PHY_CCK_DETECT);
1352  regval &= ~AR_FAST_DIV_ENABLE;
1353  regval |= ((ant_div_ctl1 >> 7) & 0x1) << AR_FAST_DIV_ENABLE_S;
1354 
1355  if (enable)
1356  regval |= AR_FAST_DIV_ENABLE;
1357 
1358  REG_WRITE(ah, AR_PHY_CCK_DETECT, regval);
1359 
1360  if (enable) {
1362  (1 << AR_PHY_ANT_SW_RX_PROT_S));
1363  if (ah->curchan && IS_CHAN_2GHZ(ah->curchan))
1368  } else {
1371  (1 << AR_PHY_ANT_SW_RX_PROT_S));
1375 
1376  regval = REG_READ(ah, AR_PHY_MC_GAIN_CTRL);
1377  regval &= ~(AR_PHY_ANT_DIV_MAIN_LNACONF |
1383  REG_WRITE(ah, AR_PHY_MC_GAIN_CTRL, regval);
1384  }
1385 }
1386 
1387 static int ar9003_hw_fast_chan_change(struct ath_hw *ah,
1388  struct ath9k_channel *chan,
1389  u8 *ini_reloaded)
1390 {
1391  unsigned int regWrites = 0;
1392  u32 modesIndex;
1393 
1394  switch (chan->chanmode) {
1395  case CHANNEL_A:
1396  case CHANNEL_A_HT20:
1397  modesIndex = 1;
1398  break;
1399  case CHANNEL_A_HT40PLUS:
1400  case CHANNEL_A_HT40MINUS:
1401  modesIndex = 2;
1402  break;
1403  case CHANNEL_G:
1404  case CHANNEL_G_HT20:
1405  case CHANNEL_B:
1406  modesIndex = 4;
1407  break;
1408  case CHANNEL_G_HT40PLUS:
1409  case CHANNEL_G_HT40MINUS:
1410  modesIndex = 3;
1411  break;
1412 
1413  default:
1414  return -EINVAL;
1415  }
1416 
1417  if (modesIndex == ah->modes_index) {
1418  *ini_reloaded = false;
1419  goto set_rfmode;
1420  }
1421 
1422  ar9003_hw_prog_ini(ah, &ah->iniSOC[ATH_INI_POST], modesIndex);
1423  ar9003_hw_prog_ini(ah, &ah->iniMac[ATH_INI_POST], modesIndex);
1424  ar9003_hw_prog_ini(ah, &ah->iniBB[ATH_INI_POST], modesIndex);
1425  ar9003_hw_prog_ini(ah, &ah->iniRadio[ATH_INI_POST], modesIndex);
1426 
1427  if (AR_SREV_9462_20(ah))
1428  ar9003_hw_prog_ini(ah, &ah->ini_radio_post_sys2ant,
1429  modesIndex);
1430 
1431  REG_WRITE_ARRAY(&ah->iniModesTxGain, modesIndex, regWrites);
1432 
1433  /*
1434  * For 5GHz channels requiring Fast Clock, apply
1435  * different modal values.
1436  */
1437  if (IS_CHAN_A_FAST_CLOCK(ah, chan))
1438  REG_WRITE_ARRAY(&ah->iniModesFastClock, modesIndex, regWrites);
1439 
1440  if (AR_SREV_9565(ah))
1441  REG_WRITE_ARRAY(&ah->iniModesFastClock, 1, regWrites);
1442 
1443  REG_WRITE_ARRAY(&ah->iniAdditional, 1, regWrites);
1444 
1445  ah->modes_index = modesIndex;
1446  *ini_reloaded = true;
1447 
1448 set_rfmode:
1449  ar9003_hw_set_rfmode(ah, chan);
1450  return 0;
1451 }
1452 
1454 {
1455  struct ath_hw_private_ops *priv_ops = ath9k_hw_private_ops(ah);
1456  struct ath_hw_ops *ops = ath9k_hw_ops(ah);
1457  static const u32 ar9300_cca_regs[6] = {
1458  AR_PHY_CCA_0,
1459  AR_PHY_CCA_1,
1460  AR_PHY_CCA_2,
1464  };
1465 
1466  priv_ops->rf_set_freq = ar9003_hw_set_channel;
1467  priv_ops->spur_mitigate_freq = ar9003_hw_spur_mitigate;
1468  priv_ops->compute_pll_control = ar9003_hw_compute_pll_control;
1469  priv_ops->set_channel_regs = ar9003_hw_set_channel_regs;
1470  priv_ops->init_bb = ar9003_hw_init_bb;
1471  priv_ops->process_ini = ar9003_hw_process_ini;
1472  priv_ops->set_rfmode = ar9003_hw_set_rfmode;
1473  priv_ops->mark_phy_inactive = ar9003_hw_mark_phy_inactive;
1474  priv_ops->set_delta_slope = ar9003_hw_set_delta_slope;
1475  priv_ops->rfbus_req = ar9003_hw_rfbus_req;
1476  priv_ops->rfbus_done = ar9003_hw_rfbus_done;
1477  priv_ops->ani_control = ar9003_hw_ani_control;
1478  priv_ops->do_getnf = ar9003_hw_do_getnf;
1479  priv_ops->ani_cache_ini_regs = ar9003_hw_ani_cache_ini_regs;
1480  priv_ops->set_radar_params = ar9003_hw_set_radar_params;
1481  priv_ops->fast_chan_change = ar9003_hw_fast_chan_change;
1482 
1483  ops->antdiv_comb_conf_get = ar9003_hw_antdiv_comb_conf_get;
1484  ops->antdiv_comb_conf_set = ar9003_hw_antdiv_comb_conf_set;
1485  ops->antctrl_shared_chain_lnadiv = ar9003_hw_antctrl_shared_chain_lnadiv;
1486 
1487  ar9003_hw_set_nf_limits(ah);
1488  ar9003_hw_set_radar_conf(ah);
1489  memcpy(ah->nf_regs, ar9300_cca_regs, sizeof(ah->nf_regs));
1490 }
1491 
1493 {
1494  struct ath_common *common = ath9k_hw_common(ah);
1495  u32 idle_tmo_ms = ah->bb_watchdog_timeout_ms;
1496  u32 val, idle_count;
1497 
1498  if (!idle_tmo_ms) {
1499  /* disable IRQ, disable chip-reset for BB panic */
1504 
1505  /* disable watchdog in non-IDLE mode, disable in IDLE mode */
1510 
1511  ath_dbg(common, RESET, "Disabled BB Watchdog\n");
1512  return;
1513  }
1514 
1515  /* enable IRQ, disable chip-reset for BB watchdog */
1518  (val | AR_PHY_WATCHDOG_IRQ_ENABLE) &
1520 
1521  /* bound limit to 10 secs */
1522  if (idle_tmo_ms > 10000)
1523  idle_tmo_ms = 10000;
1524 
1525  /*
1526  * The time unit for watchdog event is 2^15 44/88MHz cycles.
1527  *
1528  * For HT20 we have a time unit of 2^15/44 MHz = .74 ms per tick
1529  * For HT40 we have a time unit of 2^15/88 MHz = .37 ms per tick
1530  *
1531  * Given we use fast clock now in 5 GHz, these time units should
1532  * be common for both 2 GHz and 5 GHz.
1533  */
1534  idle_count = (100 * idle_tmo_ms) / 74;
1535  if (ah->curchan && IS_CHAN_HT40(ah->curchan))
1536  idle_count = (100 * idle_tmo_ms) / 37;
1537 
1538  /*
1539  * enable watchdog in non-IDLE mode, disable in IDLE mode,
1540  * set idle time-out.
1541  */
1545  (AR_PHY_WATCHDOG_NON_IDLE_MASK & (idle_count << 2)));
1546 
1547  ath_dbg(common, RESET, "Enabled BB Watchdog timeout (%u ms)\n",
1548  idle_tmo_ms);
1549 }
1550 
1552 {
1553  /*
1554  * we want to avoid printing in ISR context so we save the
1555  * watchdog status to be printed later in bottom half context.
1556  */
1558 
1559  /*
1560  * the watchdog timer should reset on status read but to be sure
1561  * sure we write 0 to the watchdog status bit.
1562  */
1565 }
1566 
1568 {
1569  struct ath_common *common = ath9k_hw_common(ah);
1570  u32 status;
1571 
1572  if (likely(!(common->debug_mask & ATH_DBG_RESET)))
1573  return;
1574 
1575  status = ah->bb_watchdog_last_status;
1576  ath_dbg(common, RESET,
1577  "\n==== BB update: BB status=0x%08x ====\n", status);
1578  ath_dbg(common, RESET,
1579  "** BB state: wd=%u det=%u rdar=%u rOFDM=%d rCCK=%u tOFDM=%u tCCK=%u agc=%u src=%u **\n",
1580  MS(status, AR_PHY_WATCHDOG_INFO),
1581  MS(status, AR_PHY_WATCHDOG_DET_HANG),
1582  MS(status, AR_PHY_WATCHDOG_RADAR_SM),
1583  MS(status, AR_PHY_WATCHDOG_RX_OFDM_SM),
1584  MS(status, AR_PHY_WATCHDOG_RX_CCK_SM),
1585  MS(status, AR_PHY_WATCHDOG_TX_OFDM_SM),
1586  MS(status, AR_PHY_WATCHDOG_TX_CCK_SM),
1587  MS(status, AR_PHY_WATCHDOG_AGC_SM),
1588  MS(status, AR_PHY_WATCHDOG_SRCH_SM));
1589 
1590  ath_dbg(common, RESET, "** BB WD cntl: cntl1=0x%08x cntl2=0x%08x **\n",
1593  ath_dbg(common, RESET, "** BB mode: BB_gen_controls=0x%08x **\n",
1594  REG_READ(ah, AR_PHY_GEN_CTRL));
1595 
1596 #define PCT(_field) (common->cc_survey._field * 100 / common->cc_survey.cycles)
1597  if (common->cc_survey.cycles)
1598  ath_dbg(common, RESET,
1599  "** BB busy times: rx_clear=%d%%, rx_frame=%d%%, tx_frame=%d%% **\n",
1600  PCT(rx_busy), PCT(rx_frame), PCT(tx_frame));
1601 
1602  ath_dbg(common, RESET, "==== BB update: done ====\n\n");
1603 }
1605 
1607 {
1608  u32 val;
1609 
1610  /* While receiving unsupported rate frame rx state machine
1611  * gets into a state 0xb and if phy_restart happens in that
1612  * state, BB would go hang. If RXSM is in 0xb state after
1613  * first bb panic, ensure to disable the phy_restart.
1614  */
1615  if (!((MS(ah->bb_watchdog_last_status,
1617  ah->bb_hang_rx_ofdm))
1618  return;
1619 
1620  ah->bb_hang_rx_ofdm = true;
1621  val = REG_READ(ah, AR_PHY_RESTART);
1622  val &= ~AR_PHY_RESTART_ENA;
1623 
1624  REG_WRITE(ah, AR_PHY_RESTART, val);
1625 }