2 * Copyright (c) 2010-2011 Atheros Communications Inc.
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.
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.
17 #include <asm/unaligned.h>
19 #include "ar9003_phy.h"
20 #include "ar9003_eeprom.h"
22 #define COMP_HDR_LEN 4
23 #define COMP_CKSUM_LEN 2
25 #define AR_CH0_TOP (AR_SREV_9300(ah) ? 0x16288 : \
26 ((AR_SREV_9480(ah) ? 0x1628c : 0x16280)))
27 #define AR_CH0_TOP_XPABIASLVL (0x300)
28 #define AR_CH0_TOP_XPABIASLVL_S (8)
30 #define AR_CH0_THERM (AR_SREV_9300(ah) ? 0x16290 : \
31 ((AR_SREV_9485(ah) ? 0x1628c : 0x16294)))
32 #define AR_CH0_THERM_XPABIASLVL_MSB 0x3
33 #define AR_CH0_THERM_XPABIASLVL_MSB_S 0
34 #define AR_CH0_THERM_XPASHORT2GND 0x4
35 #define AR_CH0_THERM_XPASHORT2GND_S 2
37 #define AR_SWITCH_TABLE_COM_ALL (0xffff)
38 #define AR_SWITCH_TABLE_COM_ALL_S (0)
39 #define AR_SWITCH_TABLE_COM_AR9480_ALL (0xffffff)
40 #define AR_SWITCH_TABLE_COM_AR9480_ALL_S (0)
41 #define AR_SWITCH_TABLE_COM_SPDT (0x00f00000)
42 #define AR_SWITCH_TABLE_COM_SPDT_ALL (0x0000fff0)
43 #define AR_SWITCH_TABLE_COM_SPDT_ALL_S (4)
45 #define AR_SWITCH_TABLE_COM2_ALL (0xffffff)
46 #define AR_SWITCH_TABLE_COM2_ALL_S (0)
48 #define AR_SWITCH_TABLE_ALL (0xfff)
49 #define AR_SWITCH_TABLE_ALL_S (0)
51 #define LE16(x) __constant_cpu_to_le16(x)
52 #define LE32(x) __constant_cpu_to_le32(x)
54 /* Local defines to distinguish between extension and control CTL's */
55 #define EXT_ADDITIVE (0x8000)
56 #define CTL_11A_EXT (CTL_11A | EXT_ADDITIVE)
57 #define CTL_11G_EXT (CTL_11G | EXT_ADDITIVE)
58 #define CTL_11B_EXT (CTL_11B | EXT_ADDITIVE)
59 #define REDUCE_SCALED_POWER_BY_TWO_CHAIN 6 /* 10*log10(2)*2 */
60 #define REDUCE_SCALED_POWER_BY_THREE_CHAIN 9 /* 10*log10(3)*2 */
61 #define PWRINCR_3_TO_1_CHAIN 9 /* 10*log(3)*2 */
62 #define PWRINCR_3_TO_2_CHAIN 3 /* floor(10*log(3/2)*2) */
63 #define PWRINCR_2_TO_1_CHAIN 6 /* 10*log(2)*2 */
65 #define SUB_NUM_CTL_MODES_AT_5G_40 2 /* excluding HT40, EXT-OFDM */
66 #define SUB_NUM_CTL_MODES_AT_2G_40 3 /* excluding HT40, EXT-OFDM, EXT-CCK */
68 #define CTL(_tpower, _flag) ((_tpower) | ((_flag) << 6))
70 #define EEPROM_DATA_LEN_9485 1088
72 static int ar9003_hw_power_interpolate(int32_t x,
73 int32_t *px, int32_t *py, u_int16_t np);
76 static const struct ar9300_eeprom ar9300_default = {
79 .macAddr = {1, 2, 3, 4, 5, 6},
80 .custData = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
81 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
83 .regDmn = { LE16(0), LE16(0x1f) },
84 .txrxMask = 0x77, /* 4 bits tx and 4 bits rx */
86 .opFlags = AR5416_OPFLAGS_11G | AR5416_OPFLAGS_11A,
90 .blueToothOptions = 0,
92 .deviceType = 5, /* takes lower byte in eeprom location */
93 .pwrTableOffset = AR9300_PWR_TABLE_OFFSET,
94 .params_for_tuning_caps = {0, 0},
95 .featureEnable = 0x0c,
97 * bit0 - enable tx temp comp - disabled
98 * bit1 - enable tx volt comp - disabled
99 * bit2 - enable fastClock - enabled
100 * bit3 - enable doubling - enabled
101 * bit4 - enable internal regulator - disabled
102 * bit5 - enable pa predistortion - disabled
104 .miscConfiguration = 0, /* bit0 - turn down drivestrength */
105 .eepromWriteEnableGpio = 3,
106 .wlanDisableGpio = 0,
108 .rxBandSelectGpio = 0xff,
113 /* ar9300_modal_eep_header 2g */
114 /* 4 idle,t1,t2,b(4 bits per setting) */
115 .antCtrlCommon = LE32(0x110),
116 /* 4 ra1l1, ra2l1, ra1l2, ra2l2, ra12 */
117 .antCtrlCommon2 = LE32(0x22222),
120 * antCtrlChain[AR9300_MAX_CHAINS]; 6 idle, t, r,
121 * rx1, rx12, b (2 bits each)
123 .antCtrlChain = { LE16(0x150), LE16(0x150), LE16(0x150) },
126 * xatten1DB[AR9300_MAX_CHAINS]; 3 xatten1_db
127 * for ar9280 (0xa20c/b20c 5:0)
129 .xatten1DB = {0, 0, 0},
132 * xatten1Margin[AR9300_MAX_CHAINS]; 3 xatten1_margin
133 * for ar9280 (0xa20c/b20c 16:12
135 .xatten1Margin = {0, 0, 0},
140 * spurChans[OSPREY_EEPROM_MODAL_SPURS]; spur
141 * channels in usual fbin coding format
143 .spurChans = {0, 0, 0, 0, 0},
146 * noiseFloorThreshCh[AR9300_MAX_CHAINS]; 3 Check
147 * if the register is per chain
149 .noiseFloorThreshCh = {-1, 0, 0},
150 .ob = {1, 1, 1},/* 3 chain */
151 .db_stage2 = {1, 1, 1}, /* 3 chain */
152 .db_stage3 = {0, 0, 0},
153 .db_stage4 = {0, 0, 0},
155 .txFrameToDataStart = 0x0e,
156 .txFrameToPaOn = 0x0e,
157 .txClip = 3, /* 4 bits tx_clip, 4 bits dac_scale_cck */
159 .switchSettling = 0x2c,
160 .adcDesiredSize = -30,
163 .txFrameToXpaOn = 0xe,
165 .papdRateMaskHt20 = LE32(0x0cf0e0e0),
166 .papdRateMaskHt40 = LE32(0x6cf0e0e0),
168 0, 0, 0, 0, 0, 0, 0, 0,
172 .ant_div_control = 0,
173 .future = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}
180 /* ar9300_cal_data_per_freq_op_loop 2g */
182 { {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0} },
183 { {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0} },
184 { {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0} },
186 .calTarget_freqbin_Cck = {
190 .calTarget_freqbin_2G = {
195 .calTarget_freqbin_2GHT20 = {
200 .calTarget_freqbin_2GHT40 = {
205 .calTargetPowerCck = {
206 /* 1L-5L,5S,11L,11S */
207 { {36, 36, 36, 36} },
208 { {36, 36, 36, 36} },
210 .calTargetPower2G = {
212 { {32, 32, 28, 24} },
213 { {32, 32, 28, 24} },
214 { {32, 32, 28, 24} },
216 .calTargetPower2GHT20 = {
217 { {32, 32, 32, 32, 28, 20, 32, 32, 28, 20, 32, 32, 28, 20} },
218 { {32, 32, 32, 32, 28, 20, 32, 32, 28, 20, 32, 32, 28, 20} },
219 { {32, 32, 32, 32, 28, 20, 32, 32, 28, 20, 32, 32, 28, 20} },
221 .calTargetPower2GHT40 = {
222 { {32, 32, 32, 32, 28, 20, 32, 32, 28, 20, 32, 32, 28, 20} },
223 { {32, 32, 32, 32, 28, 20, 32, 32, 28, 20, 32, 32, 28, 20} },
224 { {32, 32, 32, 32, 28, 20, 32, 32, 28, 20, 32, 32, 28, 20} },
227 0x11, 0x12, 0x15, 0x17, 0x41, 0x42,
228 0x45, 0x47, 0x31, 0x32, 0x35, 0x37,
258 /* Data[4].ctlEdges[0].bChannel */ FREQ2FBIN(2412, 1),
259 /* Data[4].ctlEdges[1].bChannel */ FREQ2FBIN(2417, 1),
260 /* Data[4].ctlEdges[2].bChannel */ FREQ2FBIN(2472, 1),
261 /* Data[4].ctlEdges[3].bChannel */ FREQ2FBIN(2484, 1),
265 /* Data[5].ctlEdges[0].bChannel */ FREQ2FBIN(2412, 1),
266 /* Data[5].ctlEdges[1].bChannel */ FREQ2FBIN(2417, 1),
267 /* Data[5].ctlEdges[2].bChannel */ FREQ2FBIN(2472, 1),
272 /* Data[6].ctlEdges[0].bChannel */ FREQ2FBIN(2412, 1),
273 /* Data[6].ctlEdges[1].bChannel */ FREQ2FBIN(2417, 1),
279 /* Data[7].ctlEdges[0].bChannel */ FREQ2FBIN(2422, 1),
280 /* Data[7].ctlEdges[1].bChannel */ FREQ2FBIN(2427, 1),
281 /* Data[7].ctlEdges[2].bChannel */ FREQ2FBIN(2447, 1),
282 /* Data[7].ctlEdges[3].bChannel */ FREQ2FBIN(2462, 1),
286 /* Data[8].ctlEdges[0].bChannel */ FREQ2FBIN(2412, 1),
287 /* Data[8].ctlEdges[1].bChannel */ FREQ2FBIN(2417, 1),
288 /* Data[8].ctlEdges[2].bChannel */ FREQ2FBIN(2472, 1),
292 /* Data[9].ctlEdges[0].bChannel */ FREQ2FBIN(2412, 1),
293 /* Data[9].ctlEdges[1].bChannel */ FREQ2FBIN(2417, 1),
294 /* Data[9].ctlEdges[2].bChannel */ FREQ2FBIN(2472, 1),
299 /* Data[10].ctlEdges[0].bChannel */ FREQ2FBIN(2412, 1),
300 /* Data[10].ctlEdges[1].bChannel */ FREQ2FBIN(2417, 1),
301 /* Data[10].ctlEdges[2].bChannel */ FREQ2FBIN(2472, 1),
306 /* Data[11].ctlEdges[0].bChannel */ FREQ2FBIN(2422, 1),
307 /* Data[11].ctlEdges[1].bChannel */ FREQ2FBIN(2427, 1),
308 /* Data[11].ctlEdges[2].bChannel */ FREQ2FBIN(2447, 1),
309 /* Data[11].ctlEdges[3].bChannel */ FREQ2FBIN(2462, 1),
313 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
314 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
315 { { CTL(60, 1), CTL(60, 0), CTL(60, 0), CTL(60, 1) } },
317 { { CTL(60, 1), CTL(60, 0), CTL(0, 0), CTL(0, 0) } },
318 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
319 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
321 { { CTL(60, 0), CTL(60, 1), CTL(60, 1), CTL(60, 0) } },
322 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
323 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
325 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
326 { { CTL(60, 0), CTL(60, 1), CTL(60, 1), CTL(60, 1) } },
327 { { CTL(60, 0), CTL(60, 1), CTL(60, 1), CTL(60, 1) } },
330 /* 4 idle,t1,t2,b (4 bits per setting) */
331 .antCtrlCommon = LE32(0x110),
332 /* 4 ra1l1, ra2l1, ra1l2,ra2l2,ra12 */
333 .antCtrlCommon2 = LE32(0x22222),
334 /* antCtrlChain 6 idle, t,r,rx1,rx12,b (2 bits each) */
336 LE16(0x000), LE16(0x000), LE16(0x000),
338 /* xatten1DB 3 xatten1_db for AR9280 (0xa20c/b20c 5:0) */
339 .xatten1DB = {0, 0, 0},
342 * xatten1Margin[AR9300_MAX_CHAINS]; 3 xatten1_margin
343 * for merlin (0xa20c/b20c 16:12
345 .xatten1Margin = {0, 0, 0},
348 /* spurChans spur channels in usual fbin coding format */
349 .spurChans = {0, 0, 0, 0, 0},
350 /* noiseFloorThreshCh Check if the register is per chain */
351 .noiseFloorThreshCh = {-1, 0, 0},
352 .ob = {3, 3, 3}, /* 3 chain */
353 .db_stage2 = {3, 3, 3}, /* 3 chain */
354 .db_stage3 = {3, 3, 3}, /* doesn't exist for 2G */
355 .db_stage4 = {3, 3, 3}, /* don't exist for 2G */
357 .txFrameToDataStart = 0x0e,
358 .txFrameToPaOn = 0x0e,
359 .txClip = 3, /* 4 bits tx_clip, 4 bits dac_scale_cck */
361 .switchSettling = 0x2d,
362 .adcDesiredSize = -30,
365 .txFrameToXpaOn = 0xe,
367 .papdRateMaskHt20 = LE32(0x0c80c080),
368 .papdRateMaskHt40 = LE32(0x0080c080),
370 0, 0, 0, 0, 0, 0, 0, 0,
376 .xatten1DBLow = {0, 0, 0},
377 .xatten1MarginLow = {0, 0, 0},
378 .xatten1DBHigh = {0, 0, 0},
379 .xatten1MarginHigh = {0, 0, 0}
424 .calTarget_freqbin_5G = {
434 .calTarget_freqbin_5GHT20 = {
444 .calTarget_freqbin_5GHT40 = {
454 .calTargetPower5G = {
456 { {20, 20, 20, 10} },
457 { {20, 20, 20, 10} },
458 { {20, 20, 20, 10} },
459 { {20, 20, 20, 10} },
460 { {20, 20, 20, 10} },
461 { {20, 20, 20, 10} },
462 { {20, 20, 20, 10} },
463 { {20, 20, 20, 10} },
465 .calTargetPower5GHT20 = {
467 * 0_8_16,1-3_9-11_17-19,
468 * 4,5,6,7,12,13,14,15,20,21,22,23
470 { {20, 20, 10, 10, 0, 0, 10, 10, 0, 0, 10, 10, 0, 0} },
471 { {20, 20, 10, 10, 0, 0, 10, 10, 0, 0, 10, 10, 0, 0} },
472 { {20, 20, 10, 10, 0, 0, 10, 10, 0, 0, 10, 10, 0, 0} },
473 { {20, 20, 10, 10, 0, 0, 10, 10, 0, 0, 10, 10, 0, 0} },
474 { {20, 20, 10, 10, 0, 0, 10, 10, 0, 0, 10, 10, 0, 0} },
475 { {20, 20, 10, 10, 0, 0, 10, 10, 0, 0, 10, 10, 0, 0} },
476 { {20, 20, 10, 10, 0, 0, 10, 10, 0, 0, 10, 10, 0, 0} },
477 { {20, 20, 10, 10, 0, 0, 10, 10, 0, 0, 10, 10, 0, 0} },
479 .calTargetPower5GHT40 = {
481 * 0_8_16,1-3_9-11_17-19,
482 * 4,5,6,7,12,13,14,15,20,21,22,23
484 { {20, 20, 10, 10, 0, 0, 10, 10, 0, 0, 10, 10, 0, 0} },
485 { {20, 20, 10, 10, 0, 0, 10, 10, 0, 0, 10, 10, 0, 0} },
486 { {20, 20, 10, 10, 0, 0, 10, 10, 0, 0, 10, 10, 0, 0} },
487 { {20, 20, 10, 10, 0, 0, 10, 10, 0, 0, 10, 10, 0, 0} },
488 { {20, 20, 10, 10, 0, 0, 10, 10, 0, 0, 10, 10, 0, 0} },
489 { {20, 20, 10, 10, 0, 0, 10, 10, 0, 0, 10, 10, 0, 0} },
490 { {20, 20, 10, 10, 0, 0, 10, 10, 0, 0, 10, 10, 0, 0} },
491 { {20, 20, 10, 10, 0, 0, 10, 10, 0, 0, 10, 10, 0, 0} },
494 0x10, 0x16, 0x18, 0x40, 0x46,
495 0x48, 0x30, 0x36, 0x38
499 /* Data[0].ctlEdges[0].bChannel */ FREQ2FBIN(5180, 0),
500 /* Data[0].ctlEdges[1].bChannel */ FREQ2FBIN(5260, 0),
501 /* Data[0].ctlEdges[2].bChannel */ FREQ2FBIN(5280, 0),
502 /* Data[0].ctlEdges[3].bChannel */ FREQ2FBIN(5500, 0),
503 /* Data[0].ctlEdges[4].bChannel */ FREQ2FBIN(5600, 0),
504 /* Data[0].ctlEdges[5].bChannel */ FREQ2FBIN(5700, 0),
505 /* Data[0].ctlEdges[6].bChannel */ FREQ2FBIN(5745, 0),
506 /* Data[0].ctlEdges[7].bChannel */ FREQ2FBIN(5825, 0)
509 /* Data[1].ctlEdges[0].bChannel */ FREQ2FBIN(5180, 0),
510 /* Data[1].ctlEdges[1].bChannel */ FREQ2FBIN(5260, 0),
511 /* Data[1].ctlEdges[2].bChannel */ FREQ2FBIN(5280, 0),
512 /* Data[1].ctlEdges[3].bChannel */ FREQ2FBIN(5500, 0),
513 /* Data[1].ctlEdges[4].bChannel */ FREQ2FBIN(5520, 0),
514 /* Data[1].ctlEdges[5].bChannel */ FREQ2FBIN(5700, 0),
515 /* Data[1].ctlEdges[6].bChannel */ FREQ2FBIN(5745, 0),
516 /* Data[1].ctlEdges[7].bChannel */ FREQ2FBIN(5825, 0)
520 /* Data[2].ctlEdges[0].bChannel */ FREQ2FBIN(5190, 0),
521 /* Data[2].ctlEdges[1].bChannel */ FREQ2FBIN(5230, 0),
522 /* Data[2].ctlEdges[2].bChannel */ FREQ2FBIN(5270, 0),
523 /* Data[2].ctlEdges[3].bChannel */ FREQ2FBIN(5310, 0),
524 /* Data[2].ctlEdges[4].bChannel */ FREQ2FBIN(5510, 0),
525 /* Data[2].ctlEdges[5].bChannel */ FREQ2FBIN(5550, 0),
526 /* Data[2].ctlEdges[6].bChannel */ FREQ2FBIN(5670, 0),
527 /* Data[2].ctlEdges[7].bChannel */ FREQ2FBIN(5755, 0)
531 /* Data[3].ctlEdges[0].bChannel */ FREQ2FBIN(5180, 0),
532 /* Data[3].ctlEdges[1].bChannel */ FREQ2FBIN(5200, 0),
533 /* Data[3].ctlEdges[2].bChannel */ FREQ2FBIN(5260, 0),
534 /* Data[3].ctlEdges[3].bChannel */ FREQ2FBIN(5320, 0),
535 /* Data[3].ctlEdges[4].bChannel */ FREQ2FBIN(5500, 0),
536 /* Data[3].ctlEdges[5].bChannel */ FREQ2FBIN(5700, 0),
537 /* Data[3].ctlEdges[6].bChannel */ 0xFF,
538 /* Data[3].ctlEdges[7].bChannel */ 0xFF,
542 /* Data[4].ctlEdges[0].bChannel */ FREQ2FBIN(5180, 0),
543 /* Data[4].ctlEdges[1].bChannel */ FREQ2FBIN(5260, 0),
544 /* Data[4].ctlEdges[2].bChannel */ FREQ2FBIN(5500, 0),
545 /* Data[4].ctlEdges[3].bChannel */ FREQ2FBIN(5700, 0),
546 /* Data[4].ctlEdges[4].bChannel */ 0xFF,
547 /* Data[4].ctlEdges[5].bChannel */ 0xFF,
548 /* Data[4].ctlEdges[6].bChannel */ 0xFF,
549 /* Data[4].ctlEdges[7].bChannel */ 0xFF,
553 /* Data[5].ctlEdges[0].bChannel */ FREQ2FBIN(5190, 0),
554 /* Data[5].ctlEdges[1].bChannel */ FREQ2FBIN(5270, 0),
555 /* Data[5].ctlEdges[2].bChannel */ FREQ2FBIN(5310, 0),
556 /* Data[5].ctlEdges[3].bChannel */ FREQ2FBIN(5510, 0),
557 /* Data[5].ctlEdges[4].bChannel */ FREQ2FBIN(5590, 0),
558 /* Data[5].ctlEdges[5].bChannel */ FREQ2FBIN(5670, 0),
559 /* Data[5].ctlEdges[6].bChannel */ 0xFF,
560 /* Data[5].ctlEdges[7].bChannel */ 0xFF
564 /* Data[6].ctlEdges[0].bChannel */ FREQ2FBIN(5180, 0),
565 /* Data[6].ctlEdges[1].bChannel */ FREQ2FBIN(5200, 0),
566 /* Data[6].ctlEdges[2].bChannel */ FREQ2FBIN(5220, 0),
567 /* Data[6].ctlEdges[3].bChannel */ FREQ2FBIN(5260, 0),
568 /* Data[6].ctlEdges[4].bChannel */ FREQ2FBIN(5500, 0),
569 /* Data[6].ctlEdges[5].bChannel */ FREQ2FBIN(5600, 0),
570 /* Data[6].ctlEdges[6].bChannel */ FREQ2FBIN(5700, 0),
571 /* Data[6].ctlEdges[7].bChannel */ FREQ2FBIN(5745, 0)
575 /* Data[7].ctlEdges[0].bChannel */ FREQ2FBIN(5180, 0),
576 /* Data[7].ctlEdges[1].bChannel */ FREQ2FBIN(5260, 0),
577 /* Data[7].ctlEdges[2].bChannel */ FREQ2FBIN(5320, 0),
578 /* Data[7].ctlEdges[3].bChannel */ FREQ2FBIN(5500, 0),
579 /* Data[7].ctlEdges[4].bChannel */ FREQ2FBIN(5560, 0),
580 /* Data[7].ctlEdges[5].bChannel */ FREQ2FBIN(5700, 0),
581 /* Data[7].ctlEdges[6].bChannel */ FREQ2FBIN(5745, 0),
582 /* Data[7].ctlEdges[7].bChannel */ FREQ2FBIN(5825, 0)
586 /* Data[8].ctlEdges[0].bChannel */ FREQ2FBIN(5190, 0),
587 /* Data[8].ctlEdges[1].bChannel */ FREQ2FBIN(5230, 0),
588 /* Data[8].ctlEdges[2].bChannel */ FREQ2FBIN(5270, 0),
589 /* Data[8].ctlEdges[3].bChannel */ FREQ2FBIN(5510, 0),
590 /* Data[8].ctlEdges[4].bChannel */ FREQ2FBIN(5550, 0),
591 /* Data[8].ctlEdges[5].bChannel */ FREQ2FBIN(5670, 0),
592 /* Data[8].ctlEdges[6].bChannel */ FREQ2FBIN(5755, 0),
593 /* Data[8].ctlEdges[7].bChannel */ FREQ2FBIN(5795, 0)
599 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
600 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 0),
605 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
606 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 0),
611 CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 1),
612 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
617 CTL(60, 0), CTL(60, 1), CTL(60, 1), CTL(60, 0),
618 CTL(60, 1), CTL(60, 0), CTL(60, 0), CTL(60, 0),
623 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 0),
624 CTL(60, 0), CTL(60, 0), CTL(60, 0), CTL(60, 0),
629 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
630 CTL(60, 1), CTL(60, 0), CTL(60, 0), CTL(60, 0),
635 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
636 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
641 CTL(60, 1), CTL(60, 1), CTL(60, 0), CTL(60, 1),
642 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 0),
647 CTL(60, 1), CTL(60, 0), CTL(60, 1), CTL(60, 1),
648 CTL(60, 1), CTL(60, 1), CTL(60, 0), CTL(60, 1),
654 static const struct ar9300_eeprom ar9300_x113 = {
656 .templateVersion = 6,
657 .macAddr = {0x00, 0x03, 0x7f, 0x0, 0x0, 0x0},
658 .custData = {"x113-023-f0000"},
660 .regDmn = { LE16(0), LE16(0x1f) },
661 .txrxMask = 0x77, /* 4 bits tx and 4 bits rx */
663 .opFlags = AR5416_OPFLAGS_11A,
667 .blueToothOptions = 0,
669 .deviceType = 5, /* takes lower byte in eeprom location */
670 .pwrTableOffset = AR9300_PWR_TABLE_OFFSET,
671 .params_for_tuning_caps = {0, 0},
672 .featureEnable = 0x0d,
674 * bit0 - enable tx temp comp - disabled
675 * bit1 - enable tx volt comp - disabled
676 * bit2 - enable fastClock - enabled
677 * bit3 - enable doubling - enabled
678 * bit4 - enable internal regulator - disabled
679 * bit5 - enable pa predistortion - disabled
681 .miscConfiguration = 0, /* bit0 - turn down drivestrength */
682 .eepromWriteEnableGpio = 6,
683 .wlanDisableGpio = 0,
685 .rxBandSelectGpio = 0xff,
690 /* ar9300_modal_eep_header 2g */
691 /* 4 idle,t1,t2,b(4 bits per setting) */
692 .antCtrlCommon = LE32(0x110),
693 /* 4 ra1l1, ra2l1, ra1l2, ra2l2, ra12 */
694 .antCtrlCommon2 = LE32(0x44444),
697 * antCtrlChain[AR9300_MAX_CHAINS]; 6 idle, t, r,
698 * rx1, rx12, b (2 bits each)
700 .antCtrlChain = { LE16(0x150), LE16(0x150), LE16(0x150) },
703 * xatten1DB[AR9300_MAX_CHAINS]; 3 xatten1_db
704 * for ar9280 (0xa20c/b20c 5:0)
706 .xatten1DB = {0, 0, 0},
709 * xatten1Margin[AR9300_MAX_CHAINS]; 3 xatten1_margin
710 * for ar9280 (0xa20c/b20c 16:12
712 .xatten1Margin = {0, 0, 0},
717 * spurChans[OSPREY_EEPROM_MODAL_SPURS]; spur
718 * channels in usual fbin coding format
720 .spurChans = {FREQ2FBIN(2464, 1), 0, 0, 0, 0},
723 * noiseFloorThreshCh[AR9300_MAX_CHAINS]; 3 Check
724 * if the register is per chain
726 .noiseFloorThreshCh = {-1, 0, 0},
727 .ob = {1, 1, 1},/* 3 chain */
728 .db_stage2 = {1, 1, 1}, /* 3 chain */
729 .db_stage3 = {0, 0, 0},
730 .db_stage4 = {0, 0, 0},
732 .txFrameToDataStart = 0x0e,
733 .txFrameToPaOn = 0x0e,
734 .txClip = 3, /* 4 bits tx_clip, 4 bits dac_scale_cck */
736 .switchSettling = 0x2c,
737 .adcDesiredSize = -30,
740 .txFrameToXpaOn = 0xe,
742 .papdRateMaskHt20 = LE32(0x0c80c080),
743 .papdRateMaskHt40 = LE32(0x0080c080),
745 0, 0, 0, 0, 0, 0, 0, 0,
749 .ant_div_control = 0,
750 .future = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}
757 /* ar9300_cal_data_per_freq_op_loop 2g */
759 { {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0} },
760 { {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0} },
761 { {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0} },
763 .calTarget_freqbin_Cck = {
767 .calTarget_freqbin_2G = {
772 .calTarget_freqbin_2GHT20 = {
777 .calTarget_freqbin_2GHT40 = {
782 .calTargetPowerCck = {
783 /* 1L-5L,5S,11L,11S */
784 { {34, 34, 34, 34} },
785 { {34, 34, 34, 34} },
787 .calTargetPower2G = {
789 { {34, 34, 32, 32} },
790 { {34, 34, 32, 32} },
791 { {34, 34, 32, 32} },
793 .calTargetPower2GHT20 = {
794 { {32, 32, 32, 32, 32, 28, 32, 32, 30, 28, 0, 0, 0, 0} },
795 { {32, 32, 32, 32, 32, 28, 32, 32, 30, 28, 0, 0, 0, 0} },
796 { {32, 32, 32, 32, 32, 28, 32, 32, 30, 28, 0, 0, 0, 0} },
798 .calTargetPower2GHT40 = {
799 { {30, 30, 30, 30, 30, 28, 30, 30, 28, 26, 0, 0, 0, 0} },
800 { {30, 30, 30, 30, 30, 28, 30, 30, 28, 26, 0, 0, 0, 0} },
801 { {30, 30, 30, 30, 30, 28, 30, 30, 28, 26, 0, 0, 0, 0} },
804 0x11, 0x12, 0x15, 0x17, 0x41, 0x42,
805 0x45, 0x47, 0x31, 0x32, 0x35, 0x37,
835 /* Data[4].ctlEdges[0].bChannel */ FREQ2FBIN(2412, 1),
836 /* Data[4].ctlEdges[1].bChannel */ FREQ2FBIN(2417, 1),
837 /* Data[4].ctlEdges[2].bChannel */ FREQ2FBIN(2472, 1),
838 /* Data[4].ctlEdges[3].bChannel */ FREQ2FBIN(2484, 1),
842 /* Data[5].ctlEdges[0].bChannel */ FREQ2FBIN(2412, 1),
843 /* Data[5].ctlEdges[1].bChannel */ FREQ2FBIN(2417, 1),
844 /* Data[5].ctlEdges[2].bChannel */ FREQ2FBIN(2472, 1),
849 /* Data[6].ctlEdges[0].bChannel */ FREQ2FBIN(2412, 1),
850 /* Data[6].ctlEdges[1].bChannel */ FREQ2FBIN(2417, 1),
856 /* Data[7].ctlEdges[0].bChannel */ FREQ2FBIN(2422, 1),
857 /* Data[7].ctlEdges[1].bChannel */ FREQ2FBIN(2427, 1),
858 /* Data[7].ctlEdges[2].bChannel */ FREQ2FBIN(2447, 1),
859 /* Data[7].ctlEdges[3].bChannel */ FREQ2FBIN(2462, 1),
863 /* Data[8].ctlEdges[0].bChannel */ FREQ2FBIN(2412, 1),
864 /* Data[8].ctlEdges[1].bChannel */ FREQ2FBIN(2417, 1),
865 /* Data[8].ctlEdges[2].bChannel */ FREQ2FBIN(2472, 1),
869 /* Data[9].ctlEdges[0].bChannel */ FREQ2FBIN(2412, 1),
870 /* Data[9].ctlEdges[1].bChannel */ FREQ2FBIN(2417, 1),
871 /* Data[9].ctlEdges[2].bChannel */ FREQ2FBIN(2472, 1),
876 /* Data[10].ctlEdges[0].bChannel */ FREQ2FBIN(2412, 1),
877 /* Data[10].ctlEdges[1].bChannel */ FREQ2FBIN(2417, 1),
878 /* Data[10].ctlEdges[2].bChannel */ FREQ2FBIN(2472, 1),
883 /* Data[11].ctlEdges[0].bChannel */ FREQ2FBIN(2422, 1),
884 /* Data[11].ctlEdges[1].bChannel */ FREQ2FBIN(2427, 1),
885 /* Data[11].ctlEdges[2].bChannel */ FREQ2FBIN(2447, 1),
886 /* Data[11].ctlEdges[3].bChannel */ FREQ2FBIN(2462, 1),
890 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
891 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
892 { { CTL(60, 1), CTL(60, 0), CTL(60, 0), CTL(60, 1) } },
894 { { CTL(60, 1), CTL(60, 0), CTL(0, 0), CTL(0, 0) } },
895 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
896 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
898 { { CTL(60, 0), CTL(60, 1), CTL(60, 1), CTL(60, 0) } },
899 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
900 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
902 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
903 { { CTL(60, 0), CTL(60, 1), CTL(60, 1), CTL(60, 1) } },
904 { { CTL(60, 0), CTL(60, 1), CTL(60, 1), CTL(60, 1) } },
907 /* 4 idle,t1,t2,b (4 bits per setting) */
908 .antCtrlCommon = LE32(0x220),
909 /* 4 ra1l1, ra2l1, ra1l2,ra2l2,ra12 */
910 .antCtrlCommon2 = LE32(0x11111),
911 /* antCtrlChain 6 idle, t,r,rx1,rx12,b (2 bits each) */
913 LE16(0x150), LE16(0x150), LE16(0x150),
915 /* xatten1DB 3 xatten1_db for AR9280 (0xa20c/b20c 5:0) */
916 .xatten1DB = {0, 0, 0},
919 * xatten1Margin[AR9300_MAX_CHAINS]; 3 xatten1_margin
920 * for merlin (0xa20c/b20c 16:12
922 .xatten1Margin = {0, 0, 0},
925 /* spurChans spur channels in usual fbin coding format */
926 .spurChans = {FREQ2FBIN(5500, 0), 0, 0, 0, 0},
927 /* noiseFloorThreshCh Check if the register is per chain */
928 .noiseFloorThreshCh = {-1, 0, 0},
929 .ob = {3, 3, 3}, /* 3 chain */
930 .db_stage2 = {3, 3, 3}, /* 3 chain */
931 .db_stage3 = {3, 3, 3}, /* doesn't exist for 2G */
932 .db_stage4 = {3, 3, 3}, /* don't exist for 2G */
934 .txFrameToDataStart = 0x0e,
935 .txFrameToPaOn = 0x0e,
936 .txClip = 3, /* 4 bits tx_clip, 4 bits dac_scale_cck */
938 .switchSettling = 0x2d,
939 .adcDesiredSize = -30,
942 .txFrameToXpaOn = 0xe,
944 .papdRateMaskHt20 = LE32(0x0cf0e0e0),
945 .papdRateMaskHt40 = LE32(0x6cf0e0e0),
947 0, 0, 0, 0, 0, 0, 0, 0,
952 .tempSlopeHigh = 105,
953 .xatten1DBLow = {0, 0, 0},
954 .xatten1MarginLow = {0, 0, 0},
955 .xatten1DBHigh = {0, 0, 0},
956 .xatten1MarginHigh = {0, 0, 0}
1001 .calTarget_freqbin_5G = {
1011 .calTarget_freqbin_5GHT20 = {
1021 .calTarget_freqbin_5GHT40 = {
1031 .calTargetPower5G = {
1033 { {42, 40, 40, 34} },
1034 { {42, 40, 40, 34} },
1035 { {42, 40, 40, 34} },
1036 { {42, 40, 40, 34} },
1037 { {42, 40, 40, 34} },
1038 { {42, 40, 40, 34} },
1039 { {42, 40, 40, 34} },
1040 { {42, 40, 40, 34} },
1042 .calTargetPower5GHT20 = {
1044 * 0_8_16,1-3_9-11_17-19,
1045 * 4,5,6,7,12,13,14,15,20,21,22,23
1047 { {40, 40, 40, 40, 32, 28, 40, 40, 32, 28, 40, 40, 32, 20} },
1048 { {40, 40, 40, 40, 32, 28, 40, 40, 32, 28, 40, 40, 32, 20} },
1049 { {40, 40, 40, 40, 32, 28, 40, 40, 32, 28, 40, 40, 32, 20} },
1050 { {40, 40, 40, 40, 32, 28, 40, 40, 32, 28, 40, 40, 32, 20} },
1051 { {40, 40, 40, 40, 32, 28, 40, 40, 32, 28, 40, 40, 32, 20} },
1052 { {40, 40, 40, 40, 32, 28, 40, 40, 32, 28, 40, 40, 32, 20} },
1053 { {38, 38, 38, 38, 32, 28, 38, 38, 32, 28, 38, 38, 32, 26} },
1054 { {36, 36, 36, 36, 32, 28, 36, 36, 32, 28, 36, 36, 32, 26} },
1056 .calTargetPower5GHT40 = {
1058 * 0_8_16,1-3_9-11_17-19,
1059 * 4,5,6,7,12,13,14,15,20,21,22,23
1061 { {40, 40, 40, 38, 30, 26, 40, 40, 30, 26, 40, 40, 30, 24} },
1062 { {40, 40, 40, 38, 30, 26, 40, 40, 30, 26, 40, 40, 30, 24} },
1063 { {40, 40, 40, 38, 30, 26, 40, 40, 30, 26, 40, 40, 30, 24} },
1064 { {40, 40, 40, 38, 30, 26, 40, 40, 30, 26, 40, 40, 30, 24} },
1065 { {40, 40, 40, 38, 30, 26, 40, 40, 30, 26, 40, 40, 30, 24} },
1066 { {40, 40, 40, 38, 30, 26, 40, 40, 30, 26, 40, 40, 30, 24} },
1067 { {36, 36, 36, 36, 30, 26, 36, 36, 30, 26, 36, 36, 30, 24} },
1068 { {34, 34, 34, 34, 30, 26, 34, 34, 30, 26, 34, 34, 30, 24} },
1071 0x10, 0x16, 0x18, 0x40, 0x46,
1072 0x48, 0x30, 0x36, 0x38
1076 /* Data[0].ctlEdges[0].bChannel */ FREQ2FBIN(5180, 0),
1077 /* Data[0].ctlEdges[1].bChannel */ FREQ2FBIN(5260, 0),
1078 /* Data[0].ctlEdges[2].bChannel */ FREQ2FBIN(5280, 0),
1079 /* Data[0].ctlEdges[3].bChannel */ FREQ2FBIN(5500, 0),
1080 /* Data[0].ctlEdges[4].bChannel */ FREQ2FBIN(5600, 0),
1081 /* Data[0].ctlEdges[5].bChannel */ FREQ2FBIN(5700, 0),
1082 /* Data[0].ctlEdges[6].bChannel */ FREQ2FBIN(5745, 0),
1083 /* Data[0].ctlEdges[7].bChannel */ FREQ2FBIN(5825, 0)
1086 /* Data[1].ctlEdges[0].bChannel */ FREQ2FBIN(5180, 0),
1087 /* Data[1].ctlEdges[1].bChannel */ FREQ2FBIN(5260, 0),
1088 /* Data[1].ctlEdges[2].bChannel */ FREQ2FBIN(5280, 0),
1089 /* Data[1].ctlEdges[3].bChannel */ FREQ2FBIN(5500, 0),
1090 /* Data[1].ctlEdges[4].bChannel */ FREQ2FBIN(5520, 0),
1091 /* Data[1].ctlEdges[5].bChannel */ FREQ2FBIN(5700, 0),
1092 /* Data[1].ctlEdges[6].bChannel */ FREQ2FBIN(5745, 0),
1093 /* Data[1].ctlEdges[7].bChannel */ FREQ2FBIN(5825, 0)
1097 /* Data[2].ctlEdges[0].bChannel */ FREQ2FBIN(5190, 0),
1098 /* Data[2].ctlEdges[1].bChannel */ FREQ2FBIN(5230, 0),
1099 /* Data[2].ctlEdges[2].bChannel */ FREQ2FBIN(5270, 0),
1100 /* Data[2].ctlEdges[3].bChannel */ FREQ2FBIN(5310, 0),
1101 /* Data[2].ctlEdges[4].bChannel */ FREQ2FBIN(5510, 0),
1102 /* Data[2].ctlEdges[5].bChannel */ FREQ2FBIN(5550, 0),
1103 /* Data[2].ctlEdges[6].bChannel */ FREQ2FBIN(5670, 0),
1104 /* Data[2].ctlEdges[7].bChannel */ FREQ2FBIN(5755, 0)
1108 /* Data[3].ctlEdges[0].bChannel */ FREQ2FBIN(5180, 0),
1109 /* Data[3].ctlEdges[1].bChannel */ FREQ2FBIN(5200, 0),
1110 /* Data[3].ctlEdges[2].bChannel */ FREQ2FBIN(5260, 0),
1111 /* Data[3].ctlEdges[3].bChannel */ FREQ2FBIN(5320, 0),
1112 /* Data[3].ctlEdges[4].bChannel */ FREQ2FBIN(5500, 0),
1113 /* Data[3].ctlEdges[5].bChannel */ FREQ2FBIN(5700, 0),
1114 /* Data[3].ctlEdges[6].bChannel */ 0xFF,
1115 /* Data[3].ctlEdges[7].bChannel */ 0xFF,
1119 /* Data[4].ctlEdges[0].bChannel */ FREQ2FBIN(5180, 0),
1120 /* Data[4].ctlEdges[1].bChannel */ FREQ2FBIN(5260, 0),
1121 /* Data[4].ctlEdges[2].bChannel */ FREQ2FBIN(5500, 0),
1122 /* Data[4].ctlEdges[3].bChannel */ FREQ2FBIN(5700, 0),
1123 /* Data[4].ctlEdges[4].bChannel */ 0xFF,
1124 /* Data[4].ctlEdges[5].bChannel */ 0xFF,
1125 /* Data[4].ctlEdges[6].bChannel */ 0xFF,
1126 /* Data[4].ctlEdges[7].bChannel */ 0xFF,
1130 /* Data[5].ctlEdges[0].bChannel */ FREQ2FBIN(5190, 0),
1131 /* Data[5].ctlEdges[1].bChannel */ FREQ2FBIN(5270, 0),
1132 /* Data[5].ctlEdges[2].bChannel */ FREQ2FBIN(5310, 0),
1133 /* Data[5].ctlEdges[3].bChannel */ FREQ2FBIN(5510, 0),
1134 /* Data[5].ctlEdges[4].bChannel */ FREQ2FBIN(5590, 0),
1135 /* Data[5].ctlEdges[5].bChannel */ FREQ2FBIN(5670, 0),
1136 /* Data[5].ctlEdges[6].bChannel */ 0xFF,
1137 /* Data[5].ctlEdges[7].bChannel */ 0xFF
1141 /* Data[6].ctlEdges[0].bChannel */ FREQ2FBIN(5180, 0),
1142 /* Data[6].ctlEdges[1].bChannel */ FREQ2FBIN(5200, 0),
1143 /* Data[6].ctlEdges[2].bChannel */ FREQ2FBIN(5220, 0),
1144 /* Data[6].ctlEdges[3].bChannel */ FREQ2FBIN(5260, 0),
1145 /* Data[6].ctlEdges[4].bChannel */ FREQ2FBIN(5500, 0),
1146 /* Data[6].ctlEdges[5].bChannel */ FREQ2FBIN(5600, 0),
1147 /* Data[6].ctlEdges[6].bChannel */ FREQ2FBIN(5700, 0),
1148 /* Data[6].ctlEdges[7].bChannel */ FREQ2FBIN(5745, 0)
1152 /* Data[7].ctlEdges[0].bChannel */ FREQ2FBIN(5180, 0),
1153 /* Data[7].ctlEdges[1].bChannel */ FREQ2FBIN(5260, 0),
1154 /* Data[7].ctlEdges[2].bChannel */ FREQ2FBIN(5320, 0),
1155 /* Data[7].ctlEdges[3].bChannel */ FREQ2FBIN(5500, 0),
1156 /* Data[7].ctlEdges[4].bChannel */ FREQ2FBIN(5560, 0),
1157 /* Data[7].ctlEdges[5].bChannel */ FREQ2FBIN(5700, 0),
1158 /* Data[7].ctlEdges[6].bChannel */ FREQ2FBIN(5745, 0),
1159 /* Data[7].ctlEdges[7].bChannel */ FREQ2FBIN(5825, 0)
1163 /* Data[8].ctlEdges[0].bChannel */ FREQ2FBIN(5190, 0),
1164 /* Data[8].ctlEdges[1].bChannel */ FREQ2FBIN(5230, 0),
1165 /* Data[8].ctlEdges[2].bChannel */ FREQ2FBIN(5270, 0),
1166 /* Data[8].ctlEdges[3].bChannel */ FREQ2FBIN(5510, 0),
1167 /* Data[8].ctlEdges[4].bChannel */ FREQ2FBIN(5550, 0),
1168 /* Data[8].ctlEdges[5].bChannel */ FREQ2FBIN(5670, 0),
1169 /* Data[8].ctlEdges[6].bChannel */ FREQ2FBIN(5755, 0),
1170 /* Data[8].ctlEdges[7].bChannel */ FREQ2FBIN(5795, 0)
1173 .ctlPowerData_5G = {
1176 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
1177 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 0),
1182 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
1183 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 0),
1188 CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 1),
1189 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
1194 CTL(60, 0), CTL(60, 1), CTL(60, 1), CTL(60, 0),
1195 CTL(60, 1), CTL(60, 0), CTL(60, 0), CTL(60, 0),
1200 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 0),
1201 CTL(60, 0), CTL(60, 0), CTL(60, 0), CTL(60, 0),
1206 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
1207 CTL(60, 1), CTL(60, 0), CTL(60, 0), CTL(60, 0),
1212 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
1213 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
1218 CTL(60, 1), CTL(60, 1), CTL(60, 0), CTL(60, 1),
1219 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 0),
1224 CTL(60, 1), CTL(60, 0), CTL(60, 1), CTL(60, 1),
1225 CTL(60, 1), CTL(60, 1), CTL(60, 0), CTL(60, 1),
1232 static const struct ar9300_eeprom ar9300_h112 = {
1234 .templateVersion = 3,
1235 .macAddr = {0x00, 0x03, 0x7f, 0x0, 0x0, 0x0},
1236 .custData = {"h112-241-f0000"},
1238 .regDmn = { LE16(0), LE16(0x1f) },
1239 .txrxMask = 0x77, /* 4 bits tx and 4 bits rx */
1241 .opFlags = AR5416_OPFLAGS_11G | AR5416_OPFLAGS_11A,
1245 .blueToothOptions = 0,
1247 .deviceType = 5, /* takes lower byte in eeprom location */
1248 .pwrTableOffset = AR9300_PWR_TABLE_OFFSET,
1249 .params_for_tuning_caps = {0, 0},
1250 .featureEnable = 0x0d,
1252 * bit0 - enable tx temp comp - disabled
1253 * bit1 - enable tx volt comp - disabled
1254 * bit2 - enable fastClock - enabled
1255 * bit3 - enable doubling - enabled
1256 * bit4 - enable internal regulator - disabled
1257 * bit5 - enable pa predistortion - disabled
1259 .miscConfiguration = 0, /* bit0 - turn down drivestrength */
1260 .eepromWriteEnableGpio = 6,
1261 .wlanDisableGpio = 0,
1263 .rxBandSelectGpio = 0xff,
1268 /* ar9300_modal_eep_header 2g */
1269 /* 4 idle,t1,t2,b(4 bits per setting) */
1270 .antCtrlCommon = LE32(0x110),
1271 /* 4 ra1l1, ra2l1, ra1l2, ra2l2, ra12 */
1272 .antCtrlCommon2 = LE32(0x44444),
1275 * antCtrlChain[AR9300_MAX_CHAINS]; 6 idle, t, r,
1276 * rx1, rx12, b (2 bits each)
1278 .antCtrlChain = { LE16(0x150), LE16(0x150), LE16(0x150) },
1281 * xatten1DB[AR9300_MAX_CHAINS]; 3 xatten1_db
1282 * for ar9280 (0xa20c/b20c 5:0)
1284 .xatten1DB = {0, 0, 0},
1287 * xatten1Margin[AR9300_MAX_CHAINS]; 3 xatten1_margin
1288 * for ar9280 (0xa20c/b20c 16:12
1290 .xatten1Margin = {0, 0, 0},
1295 * spurChans[OSPREY_EEPROM_MODAL_SPURS]; spur
1296 * channels in usual fbin coding format
1298 .spurChans = {FREQ2FBIN(2464, 1), 0, 0, 0, 0},
1301 * noiseFloorThreshCh[AR9300_MAX_CHAINS]; 3 Check
1302 * if the register is per chain
1304 .noiseFloorThreshCh = {-1, 0, 0},
1305 .ob = {1, 1, 1},/* 3 chain */
1306 .db_stage2 = {1, 1, 1}, /* 3 chain */
1307 .db_stage3 = {0, 0, 0},
1308 .db_stage4 = {0, 0, 0},
1310 .txFrameToDataStart = 0x0e,
1311 .txFrameToPaOn = 0x0e,
1312 .txClip = 3, /* 4 bits tx_clip, 4 bits dac_scale_cck */
1314 .switchSettling = 0x2c,
1315 .adcDesiredSize = -30,
1318 .txFrameToXpaOn = 0xe,
1320 .papdRateMaskHt20 = LE32(0x80c080),
1321 .papdRateMaskHt40 = LE32(0x80c080),
1323 0, 0, 0, 0, 0, 0, 0, 0,
1327 .ant_div_control = 0,
1328 .future = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}
1335 /* ar9300_cal_data_per_freq_op_loop 2g */
1337 { {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0} },
1338 { {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0} },
1339 { {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0} },
1341 .calTarget_freqbin_Cck = {
1345 .calTarget_freqbin_2G = {
1350 .calTarget_freqbin_2GHT20 = {
1355 .calTarget_freqbin_2GHT40 = {
1360 .calTargetPowerCck = {
1361 /* 1L-5L,5S,11L,11S */
1362 { {34, 34, 34, 34} },
1363 { {34, 34, 34, 34} },
1365 .calTargetPower2G = {
1367 { {34, 34, 32, 32} },
1368 { {34, 34, 32, 32} },
1369 { {34, 34, 32, 32} },
1371 .calTargetPower2GHT20 = {
1372 { {32, 32, 32, 32, 32, 30, 32, 32, 30, 28, 28, 28, 28, 24} },
1373 { {32, 32, 32, 32, 32, 30, 32, 32, 30, 28, 28, 28, 28, 24} },
1374 { {32, 32, 32, 32, 32, 30, 32, 32, 30, 28, 28, 28, 28, 24} },
1376 .calTargetPower2GHT40 = {
1377 { {30, 30, 30, 30, 30, 28, 30, 30, 28, 26, 26, 26, 26, 22} },
1378 { {30, 30, 30, 30, 30, 28, 30, 30, 28, 26, 26, 26, 26, 22} },
1379 { {30, 30, 30, 30, 30, 28, 30, 30, 28, 26, 26, 26, 26, 22} },
1382 0x11, 0x12, 0x15, 0x17, 0x41, 0x42,
1383 0x45, 0x47, 0x31, 0x32, 0x35, 0x37,
1413 /* Data[4].ctlEdges[0].bChannel */ FREQ2FBIN(2412, 1),
1414 /* Data[4].ctlEdges[1].bChannel */ FREQ2FBIN(2417, 1),
1415 /* Data[4].ctlEdges[2].bChannel */ FREQ2FBIN(2472, 1),
1416 /* Data[4].ctlEdges[3].bChannel */ FREQ2FBIN(2484, 1),
1420 /* Data[5].ctlEdges[0].bChannel */ FREQ2FBIN(2412, 1),
1421 /* Data[5].ctlEdges[1].bChannel */ FREQ2FBIN(2417, 1),
1422 /* Data[5].ctlEdges[2].bChannel */ FREQ2FBIN(2472, 1),
1427 /* Data[6].ctlEdges[0].bChannel */ FREQ2FBIN(2412, 1),
1428 /* Data[6].ctlEdges[1].bChannel */ FREQ2FBIN(2417, 1),
1434 /* Data[7].ctlEdges[0].bChannel */ FREQ2FBIN(2422, 1),
1435 /* Data[7].ctlEdges[1].bChannel */ FREQ2FBIN(2427, 1),
1436 /* Data[7].ctlEdges[2].bChannel */ FREQ2FBIN(2447, 1),
1437 /* Data[7].ctlEdges[3].bChannel */ FREQ2FBIN(2462, 1),
1441 /* Data[8].ctlEdges[0].bChannel */ FREQ2FBIN(2412, 1),
1442 /* Data[8].ctlEdges[1].bChannel */ FREQ2FBIN(2417, 1),
1443 /* Data[8].ctlEdges[2].bChannel */ FREQ2FBIN(2472, 1),
1447 /* Data[9].ctlEdges[0].bChannel */ FREQ2FBIN(2412, 1),
1448 /* Data[9].ctlEdges[1].bChannel */ FREQ2FBIN(2417, 1),
1449 /* Data[9].ctlEdges[2].bChannel */ FREQ2FBIN(2472, 1),
1454 /* Data[10].ctlEdges[0].bChannel */ FREQ2FBIN(2412, 1),
1455 /* Data[10].ctlEdges[1].bChannel */ FREQ2FBIN(2417, 1),
1456 /* Data[10].ctlEdges[2].bChannel */ FREQ2FBIN(2472, 1),
1461 /* Data[11].ctlEdges[0].bChannel */ FREQ2FBIN(2422, 1),
1462 /* Data[11].ctlEdges[1].bChannel */ FREQ2FBIN(2427, 1),
1463 /* Data[11].ctlEdges[2].bChannel */ FREQ2FBIN(2447, 1),
1464 /* Data[11].ctlEdges[3].bChannel */ FREQ2FBIN(2462, 1),
1467 .ctlPowerData_2G = {
1468 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
1469 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
1470 { { CTL(60, 1), CTL(60, 0), CTL(60, 0), CTL(60, 1) } },
1472 { { CTL(60, 1), CTL(60, 0), CTL(60, 0), CTL(60, 0) } },
1473 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
1474 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
1476 { { CTL(60, 0), CTL(60, 1), CTL(60, 1), CTL(60, 0) } },
1477 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
1478 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
1480 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
1481 { { CTL(60, 0), CTL(60, 1), CTL(60, 1), CTL(60, 1) } },
1482 { { CTL(60, 0), CTL(60, 1), CTL(60, 1), CTL(60, 1) } },
1485 /* 4 idle,t1,t2,b (4 bits per setting) */
1486 .antCtrlCommon = LE32(0x220),
1487 /* 4 ra1l1, ra2l1, ra1l2,ra2l2,ra12 */
1488 .antCtrlCommon2 = LE32(0x44444),
1489 /* antCtrlChain 6 idle, t,r,rx1,rx12,b (2 bits each) */
1491 LE16(0x150), LE16(0x150), LE16(0x150),
1493 /* xatten1DB 3 xatten1_db for AR9280 (0xa20c/b20c 5:0) */
1494 .xatten1DB = {0, 0, 0},
1497 * xatten1Margin[AR9300_MAX_CHAINS]; 3 xatten1_margin
1498 * for merlin (0xa20c/b20c 16:12
1500 .xatten1Margin = {0, 0, 0},
1503 /* spurChans spur channels in usual fbin coding format */
1504 .spurChans = {0, 0, 0, 0, 0},
1505 /* noiseFloorThreshCh Check if the register is per chain */
1506 .noiseFloorThreshCh = {-1, 0, 0},
1507 .ob = {3, 3, 3}, /* 3 chain */
1508 .db_stage2 = {3, 3, 3}, /* 3 chain */
1509 .db_stage3 = {3, 3, 3}, /* doesn't exist for 2G */
1510 .db_stage4 = {3, 3, 3}, /* don't exist for 2G */
1512 .txFrameToDataStart = 0x0e,
1513 .txFrameToPaOn = 0x0e,
1514 .txClip = 3, /* 4 bits tx_clip, 4 bits dac_scale_cck */
1516 .switchSettling = 0x2d,
1517 .adcDesiredSize = -30,
1520 .txFrameToXpaOn = 0xe,
1522 .papdRateMaskHt20 = LE32(0x0cf0e0e0),
1523 .papdRateMaskHt40 = LE32(0x6cf0e0e0),
1525 0, 0, 0, 0, 0, 0, 0, 0,
1530 .tempSlopeHigh = 50,
1531 .xatten1DBLow = {0, 0, 0},
1532 .xatten1MarginLow = {0, 0, 0},
1533 .xatten1DBHigh = {0, 0, 0},
1534 .xatten1MarginHigh = {0, 0, 0}
1579 .calTarget_freqbin_5G = {
1589 .calTarget_freqbin_5GHT20 = {
1599 .calTarget_freqbin_5GHT40 = {
1609 .calTargetPower5G = {
1611 { {30, 30, 28, 24} },
1612 { {30, 30, 28, 24} },
1613 { {30, 30, 28, 24} },
1614 { {30, 30, 28, 24} },
1615 { {30, 30, 28, 24} },
1616 { {30, 30, 28, 24} },
1617 { {30, 30, 28, 24} },
1618 { {30, 30, 28, 24} },
1620 .calTargetPower5GHT20 = {
1622 * 0_8_16,1-3_9-11_17-19,
1623 * 4,5,6,7,12,13,14,15,20,21,22,23
1625 { {30, 30, 30, 28, 24, 20, 30, 28, 24, 20, 20, 20, 20, 16} },
1626 { {30, 30, 30, 28, 24, 20, 30, 28, 24, 20, 20, 20, 20, 16} },
1627 { {30, 30, 30, 26, 22, 18, 30, 26, 22, 18, 18, 18, 18, 16} },
1628 { {30, 30, 30, 26, 22, 18, 30, 26, 22, 18, 18, 18, 18, 16} },
1629 { {30, 30, 30, 24, 20, 16, 30, 24, 20, 16, 16, 16, 16, 14} },
1630 { {30, 30, 30, 24, 20, 16, 30, 24, 20, 16, 16, 16, 16, 14} },
1631 { {30, 30, 30, 22, 18, 14, 30, 22, 18, 14, 14, 14, 14, 12} },
1632 { {30, 30, 30, 22, 18, 14, 30, 22, 18, 14, 14, 14, 14, 12} },
1634 .calTargetPower5GHT40 = {
1636 * 0_8_16,1-3_9-11_17-19,
1637 * 4,5,6,7,12,13,14,15,20,21,22,23
1639 { {28, 28, 28, 26, 22, 18, 28, 26, 22, 18, 18, 18, 18, 14} },
1640 { {28, 28, 28, 26, 22, 18, 28, 26, 22, 18, 18, 18, 18, 14} },
1641 { {28, 28, 28, 24, 20, 16, 28, 24, 20, 16, 16, 16, 16, 12} },
1642 { {28, 28, 28, 24, 20, 16, 28, 24, 20, 16, 16, 16, 16, 12} },
1643 { {28, 28, 28, 22, 18, 14, 28, 22, 18, 14, 14, 14, 14, 10} },
1644 { {28, 28, 28, 22, 18, 14, 28, 22, 18, 14, 14, 14, 14, 10} },
1645 { {28, 28, 28, 20, 16, 12, 28, 20, 16, 12, 12, 12, 12, 8} },
1646 { {28, 28, 28, 20, 16, 12, 28, 20, 16, 12, 12, 12, 12, 8} },
1649 0x10, 0x16, 0x18, 0x40, 0x46,
1650 0x48, 0x30, 0x36, 0x38
1654 /* Data[0].ctlEdges[0].bChannel */ FREQ2FBIN(5180, 0),
1655 /* Data[0].ctlEdges[1].bChannel */ FREQ2FBIN(5260, 0),
1656 /* Data[0].ctlEdges[2].bChannel */ FREQ2FBIN(5280, 0),
1657 /* Data[0].ctlEdges[3].bChannel */ FREQ2FBIN(5500, 0),
1658 /* Data[0].ctlEdges[4].bChannel */ FREQ2FBIN(5600, 0),
1659 /* Data[0].ctlEdges[5].bChannel */ FREQ2FBIN(5700, 0),
1660 /* Data[0].ctlEdges[6].bChannel */ FREQ2FBIN(5745, 0),
1661 /* Data[0].ctlEdges[7].bChannel */ FREQ2FBIN(5825, 0)
1664 /* Data[1].ctlEdges[0].bChannel */ FREQ2FBIN(5180, 0),
1665 /* Data[1].ctlEdges[1].bChannel */ FREQ2FBIN(5260, 0),
1666 /* Data[1].ctlEdges[2].bChannel */ FREQ2FBIN(5280, 0),
1667 /* Data[1].ctlEdges[3].bChannel */ FREQ2FBIN(5500, 0),
1668 /* Data[1].ctlEdges[4].bChannel */ FREQ2FBIN(5520, 0),
1669 /* Data[1].ctlEdges[5].bChannel */ FREQ2FBIN(5700, 0),
1670 /* Data[1].ctlEdges[6].bChannel */ FREQ2FBIN(5745, 0),
1671 /* Data[1].ctlEdges[7].bChannel */ FREQ2FBIN(5825, 0)
1675 /* Data[2].ctlEdges[0].bChannel */ FREQ2FBIN(5190, 0),
1676 /* Data[2].ctlEdges[1].bChannel */ FREQ2FBIN(5230, 0),
1677 /* Data[2].ctlEdges[2].bChannel */ FREQ2FBIN(5270, 0),
1678 /* Data[2].ctlEdges[3].bChannel */ FREQ2FBIN(5310, 0),
1679 /* Data[2].ctlEdges[4].bChannel */ FREQ2FBIN(5510, 0),
1680 /* Data[2].ctlEdges[5].bChannel */ FREQ2FBIN(5550, 0),
1681 /* Data[2].ctlEdges[6].bChannel */ FREQ2FBIN(5670, 0),
1682 /* Data[2].ctlEdges[7].bChannel */ FREQ2FBIN(5755, 0)
1686 /* Data[3].ctlEdges[0].bChannel */ FREQ2FBIN(5180, 0),
1687 /* Data[3].ctlEdges[1].bChannel */ FREQ2FBIN(5200, 0),
1688 /* Data[3].ctlEdges[2].bChannel */ FREQ2FBIN(5260, 0),
1689 /* Data[3].ctlEdges[3].bChannel */ FREQ2FBIN(5320, 0),
1690 /* Data[3].ctlEdges[4].bChannel */ FREQ2FBIN(5500, 0),
1691 /* Data[3].ctlEdges[5].bChannel */ FREQ2FBIN(5700, 0),
1692 /* Data[3].ctlEdges[6].bChannel */ 0xFF,
1693 /* Data[3].ctlEdges[7].bChannel */ 0xFF,
1697 /* Data[4].ctlEdges[0].bChannel */ FREQ2FBIN(5180, 0),
1698 /* Data[4].ctlEdges[1].bChannel */ FREQ2FBIN(5260, 0),
1699 /* Data[4].ctlEdges[2].bChannel */ FREQ2FBIN(5500, 0),
1700 /* Data[4].ctlEdges[3].bChannel */ FREQ2FBIN(5700, 0),
1701 /* Data[4].ctlEdges[4].bChannel */ 0xFF,
1702 /* Data[4].ctlEdges[5].bChannel */ 0xFF,
1703 /* Data[4].ctlEdges[6].bChannel */ 0xFF,
1704 /* Data[4].ctlEdges[7].bChannel */ 0xFF,
1708 /* Data[5].ctlEdges[0].bChannel */ FREQ2FBIN(5190, 0),
1709 /* Data[5].ctlEdges[1].bChannel */ FREQ2FBIN(5270, 0),
1710 /* Data[5].ctlEdges[2].bChannel */ FREQ2FBIN(5310, 0),
1711 /* Data[5].ctlEdges[3].bChannel */ FREQ2FBIN(5510, 0),
1712 /* Data[5].ctlEdges[4].bChannel */ FREQ2FBIN(5590, 0),
1713 /* Data[5].ctlEdges[5].bChannel */ FREQ2FBIN(5670, 0),
1714 /* Data[5].ctlEdges[6].bChannel */ 0xFF,
1715 /* Data[5].ctlEdges[7].bChannel */ 0xFF
1719 /* Data[6].ctlEdges[0].bChannel */ FREQ2FBIN(5180, 0),
1720 /* Data[6].ctlEdges[1].bChannel */ FREQ2FBIN(5200, 0),
1721 /* Data[6].ctlEdges[2].bChannel */ FREQ2FBIN(5220, 0),
1722 /* Data[6].ctlEdges[3].bChannel */ FREQ2FBIN(5260, 0),
1723 /* Data[6].ctlEdges[4].bChannel */ FREQ2FBIN(5500, 0),
1724 /* Data[6].ctlEdges[5].bChannel */ FREQ2FBIN(5600, 0),
1725 /* Data[6].ctlEdges[6].bChannel */ FREQ2FBIN(5700, 0),
1726 /* Data[6].ctlEdges[7].bChannel */ FREQ2FBIN(5745, 0)
1730 /* Data[7].ctlEdges[0].bChannel */ FREQ2FBIN(5180, 0),
1731 /* Data[7].ctlEdges[1].bChannel */ FREQ2FBIN(5260, 0),
1732 /* Data[7].ctlEdges[2].bChannel */ FREQ2FBIN(5320, 0),
1733 /* Data[7].ctlEdges[3].bChannel */ FREQ2FBIN(5500, 0),
1734 /* Data[7].ctlEdges[4].bChannel */ FREQ2FBIN(5560, 0),
1735 /* Data[7].ctlEdges[5].bChannel */ FREQ2FBIN(5700, 0),
1736 /* Data[7].ctlEdges[6].bChannel */ FREQ2FBIN(5745, 0),
1737 /* Data[7].ctlEdges[7].bChannel */ FREQ2FBIN(5825, 0)
1741 /* Data[8].ctlEdges[0].bChannel */ FREQ2FBIN(5190, 0),
1742 /* Data[8].ctlEdges[1].bChannel */ FREQ2FBIN(5230, 0),
1743 /* Data[8].ctlEdges[2].bChannel */ FREQ2FBIN(5270, 0),
1744 /* Data[8].ctlEdges[3].bChannel */ FREQ2FBIN(5510, 0),
1745 /* Data[8].ctlEdges[4].bChannel */ FREQ2FBIN(5550, 0),
1746 /* Data[8].ctlEdges[5].bChannel */ FREQ2FBIN(5670, 0),
1747 /* Data[8].ctlEdges[6].bChannel */ FREQ2FBIN(5755, 0),
1748 /* Data[8].ctlEdges[7].bChannel */ FREQ2FBIN(5795, 0)
1751 .ctlPowerData_5G = {
1754 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
1755 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 0),
1760 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
1761 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 0),
1766 CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 1),
1767 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
1772 CTL(60, 0), CTL(60, 1), CTL(60, 1), CTL(60, 0),
1773 CTL(60, 1), CTL(60, 0), CTL(60, 0), CTL(60, 0),
1778 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 0),
1779 CTL(60, 0), CTL(60, 0), CTL(60, 0), CTL(60, 0),
1784 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
1785 CTL(60, 1), CTL(60, 0), CTL(60, 0), CTL(60, 0),
1790 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
1791 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
1796 CTL(60, 1), CTL(60, 1), CTL(60, 0), CTL(60, 1),
1797 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 0),
1802 CTL(60, 1), CTL(60, 0), CTL(60, 1), CTL(60, 1),
1803 CTL(60, 1), CTL(60, 1), CTL(60, 0), CTL(60, 1),
1810 static const struct ar9300_eeprom ar9300_x112 = {
1812 .templateVersion = 5,
1813 .macAddr = {0x00, 0x03, 0x7f, 0x0, 0x0, 0x0},
1814 .custData = {"x112-041-f0000"},
1816 .regDmn = { LE16(0), LE16(0x1f) },
1817 .txrxMask = 0x77, /* 4 bits tx and 4 bits rx */
1819 .opFlags = AR5416_OPFLAGS_11G | AR5416_OPFLAGS_11A,
1823 .blueToothOptions = 0,
1825 .deviceType = 5, /* takes lower byte in eeprom location */
1826 .pwrTableOffset = AR9300_PWR_TABLE_OFFSET,
1827 .params_for_tuning_caps = {0, 0},
1828 .featureEnable = 0x0d,
1830 * bit0 - enable tx temp comp - disabled
1831 * bit1 - enable tx volt comp - disabled
1832 * bit2 - enable fastclock - enabled
1833 * bit3 - enable doubling - enabled
1834 * bit4 - enable internal regulator - disabled
1835 * bit5 - enable pa predistortion - disabled
1837 .miscConfiguration = 0, /* bit0 - turn down drivestrength */
1838 .eepromWriteEnableGpio = 6,
1839 .wlanDisableGpio = 0,
1841 .rxBandSelectGpio = 0xff,
1846 /* ar9300_modal_eep_header 2g */
1847 /* 4 idle,t1,t2,b(4 bits per setting) */
1848 .antCtrlCommon = LE32(0x110),
1849 /* 4 ra1l1, ra2l1, ra1l2, ra2l2, ra12 */
1850 .antCtrlCommon2 = LE32(0x22222),
1853 * antCtrlChain[ar9300_max_chains]; 6 idle, t, r,
1854 * rx1, rx12, b (2 bits each)
1856 .antCtrlChain = { LE16(0x10), LE16(0x10), LE16(0x10) },
1859 * xatten1DB[AR9300_max_chains]; 3 xatten1_db
1860 * for ar9280 (0xa20c/b20c 5:0)
1862 .xatten1DB = {0x1b, 0x1b, 0x1b},
1865 * xatten1Margin[ar9300_max_chains]; 3 xatten1_margin
1866 * for ar9280 (0xa20c/b20c 16:12
1868 .xatten1Margin = {0x15, 0x15, 0x15},
1873 * spurChans[OSPrey_eeprom_modal_sPURS]; spur
1874 * channels in usual fbin coding format
1876 .spurChans = {FREQ2FBIN(2464, 1), 0, 0, 0, 0},
1879 * noiseFloorThreshch[ar9300_max_cHAINS]; 3 Check
1880 * if the register is per chain
1882 .noiseFloorThreshCh = {-1, 0, 0},
1883 .ob = {1, 1, 1},/* 3 chain */
1884 .db_stage2 = {1, 1, 1}, /* 3 chain */
1885 .db_stage3 = {0, 0, 0},
1886 .db_stage4 = {0, 0, 0},
1888 .txFrameToDataStart = 0x0e,
1889 .txFrameToPaOn = 0x0e,
1890 .txClip = 3, /* 4 bits tx_clip, 4 bits dac_scale_cck */
1892 .switchSettling = 0x2c,
1893 .adcDesiredSize = -30,
1896 .txFrameToXpaOn = 0xe,
1898 .papdRateMaskHt20 = LE32(0x0c80c080),
1899 .papdRateMaskHt40 = LE32(0x0080c080),
1901 0, 0, 0, 0, 0, 0, 0, 0,
1905 .ant_div_control = 0,
1906 .future = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}
1913 /* ar9300_cal_data_per_freq_op_loop 2g */
1915 { {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0} },
1916 { {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0} },
1917 { {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0} },
1919 .calTarget_freqbin_Cck = {
1923 .calTarget_freqbin_2G = {
1928 .calTarget_freqbin_2GHT20 = {
1933 .calTarget_freqbin_2GHT40 = {
1938 .calTargetPowerCck = {
1939 /* 1L-5L,5S,11L,11s */
1940 { {38, 38, 38, 38} },
1941 { {38, 38, 38, 38} },
1943 .calTargetPower2G = {
1945 { {38, 38, 36, 34} },
1946 { {38, 38, 36, 34} },
1947 { {38, 38, 34, 32} },
1949 .calTargetPower2GHT20 = {
1950 { {36, 36, 36, 36, 36, 34, 34, 32, 30, 28, 28, 28, 28, 26} },
1951 { {36, 36, 36, 36, 36, 34, 36, 34, 32, 30, 30, 30, 28, 26} },
1952 { {36, 36, 36, 36, 36, 34, 34, 32, 30, 28, 28, 28, 28, 26} },
1954 .calTargetPower2GHT40 = {
1955 { {36, 36, 36, 36, 34, 32, 32, 30, 28, 26, 26, 26, 26, 24} },
1956 { {36, 36, 36, 36, 34, 32, 34, 32, 30, 28, 28, 28, 28, 24} },
1957 { {36, 36, 36, 36, 34, 32, 32, 30, 28, 26, 26, 26, 26, 24} },
1960 0x11, 0x12, 0x15, 0x17, 0x41, 0x42,
1961 0x45, 0x47, 0x31, 0x32, 0x35, 0x37,
1991 /* Data[4].ctledges[0].bchannel */ FREQ2FBIN(2412, 1),
1992 /* Data[4].ctledges[1].bchannel */ FREQ2FBIN(2417, 1),
1993 /* Data[4].ctledges[2].bchannel */ FREQ2FBIN(2472, 1),
1994 /* Data[4].ctledges[3].bchannel */ FREQ2FBIN(2484, 1),
1998 /* Data[5].ctledges[0].bchannel */ FREQ2FBIN(2412, 1),
1999 /* Data[5].ctledges[1].bchannel */ FREQ2FBIN(2417, 1),
2000 /* Data[5].ctledges[2].bchannel */ FREQ2FBIN(2472, 1),
2005 /* Data[6].ctledges[0].bchannel */ FREQ2FBIN(2412, 1),
2006 /* Data[6].ctledges[1].bchannel */ FREQ2FBIN(2417, 1),
2012 /* Data[7].ctledges[0].bchannel */ FREQ2FBIN(2422, 1),
2013 /* Data[7].ctledges[1].bchannel */ FREQ2FBIN(2427, 1),
2014 /* Data[7].ctledges[2].bchannel */ FREQ2FBIN(2447, 1),
2015 /* Data[7].ctledges[3].bchannel */ FREQ2FBIN(2462, 1),
2019 /* Data[8].ctledges[0].bchannel */ FREQ2FBIN(2412, 1),
2020 /* Data[8].ctledges[1].bchannel */ FREQ2FBIN(2417, 1),
2021 /* Data[8].ctledges[2].bchannel */ FREQ2FBIN(2472, 1),
2025 /* Data[9].ctledges[0].bchannel */ FREQ2FBIN(2412, 1),
2026 /* Data[9].ctledges[1].bchannel */ FREQ2FBIN(2417, 1),
2027 /* Data[9].ctledges[2].bchannel */ FREQ2FBIN(2472, 1),
2032 /* Data[10].ctledges[0].bchannel */ FREQ2FBIN(2412, 1),
2033 /* Data[10].ctledges[1].bchannel */ FREQ2FBIN(2417, 1),
2034 /* Data[10].ctledges[2].bchannel */ FREQ2FBIN(2472, 1),
2039 /* Data[11].ctledges[0].bchannel */ FREQ2FBIN(2422, 1),
2040 /* Data[11].ctledges[1].bchannel */ FREQ2FBIN(2427, 1),
2041 /* Data[11].ctledges[2].bchannel */ FREQ2FBIN(2447, 1),
2042 /* Data[11].ctledges[3].bchannel */ FREQ2FBIN(2462, 1),
2045 .ctlPowerData_2G = {
2046 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
2047 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
2048 { { CTL(60, 1), CTL(60, 0), CTL(60, 0), CTL(60, 1) } },
2050 { { CTL(60, 1), CTL(60, 0), CTL(0, 0), CTL(0, 0) } },
2051 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
2052 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
2054 { { CTL(60, 0), CTL(60, 1), CTL(60, 1), CTL(60, 0) } },
2055 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
2056 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
2058 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
2059 { { CTL(60, 0), CTL(60, 1), CTL(60, 1), CTL(60, 1) } },
2060 { { CTL(60, 0), CTL(60, 1), CTL(60, 1), CTL(60, 1) } },
2063 /* 4 idle,t1,t2,b (4 bits per setting) */
2064 .antCtrlCommon = LE32(0x110),
2065 /* 4 ra1l1, ra2l1, ra1l2,ra2l2,ra12 */
2066 .antCtrlCommon2 = LE32(0x22222),
2067 /* antCtrlChain 6 idle, t,r,rx1,rx12,b (2 bits each) */
2069 LE16(0x0), LE16(0x0), LE16(0x0),
2071 /* xatten1DB 3 xatten1_db for ar9280 (0xa20c/b20c 5:0) */
2072 .xatten1DB = {0x13, 0x19, 0x17},
2075 * xatten1Margin[ar9300_max_chains]; 3 xatten1_margin
2076 * for merlin (0xa20c/b20c 16:12
2078 .xatten1Margin = {0x19, 0x19, 0x19},
2081 /* spurChans spur channels in usual fbin coding format */
2082 .spurChans = {0, 0, 0, 0, 0},
2083 /* noiseFloorThreshch check if the register is per chain */
2084 .noiseFloorThreshCh = {-1, 0, 0},
2085 .ob = {3, 3, 3}, /* 3 chain */
2086 .db_stage2 = {3, 3, 3}, /* 3 chain */
2087 .db_stage3 = {3, 3, 3}, /* doesn't exist for 2G */
2088 .db_stage4 = {3, 3, 3}, /* don't exist for 2G */
2090 .txFrameToDataStart = 0x0e,
2091 .txFrameToPaOn = 0x0e,
2092 .txClip = 3, /* 4 bits tx_clip, 4 bits dac_scale_cck */
2094 .switchSettling = 0x2d,
2095 .adcDesiredSize = -30,
2098 .txFrameToXpaOn = 0xe,
2100 .papdRateMaskHt20 = LE32(0x0cf0e0e0),
2101 .papdRateMaskHt40 = LE32(0x6cf0e0e0),
2103 0, 0, 0, 0, 0, 0, 0, 0,
2108 .tempSlopeHigh = 105,
2109 .xatten1DBLow = {0x10, 0x14, 0x10},
2110 .xatten1MarginLow = {0x19, 0x19 , 0x19},
2111 .xatten1DBHigh = {0x1d, 0x20, 0x24},
2112 .xatten1MarginHigh = {0x10, 0x10, 0x10}
2157 .calTarget_freqbin_5G = {
2167 .calTarget_freqbin_5GHT20 = {
2177 .calTarget_freqbin_5GHT40 = {
2187 .calTargetPower5G = {
2189 { {32, 32, 28, 26} },
2190 { {32, 32, 28, 26} },
2191 { {32, 32, 28, 26} },
2192 { {32, 32, 26, 24} },
2193 { {32, 32, 26, 24} },
2194 { {32, 32, 24, 22} },
2195 { {30, 30, 24, 22} },
2196 { {30, 30, 24, 22} },
2198 .calTargetPower5GHT20 = {
2200 * 0_8_16,1-3_9-11_17-19,
2201 * 4,5,6,7,12,13,14,15,20,21,22,23
2203 { {32, 32, 32, 32, 28, 26, 32, 28, 26, 24, 24, 24, 22, 22} },
2204 { {32, 32, 32, 32, 28, 26, 32, 28, 26, 24, 24, 24, 22, 22} },
2205 { {32, 32, 32, 32, 28, 26, 32, 28, 26, 24, 24, 24, 22, 22} },
2206 { {32, 32, 32, 32, 28, 26, 32, 26, 24, 22, 22, 22, 20, 20} },
2207 { {32, 32, 32, 32, 28, 26, 32, 26, 24, 22, 20, 18, 16, 16} },
2208 { {32, 32, 32, 32, 28, 26, 32, 24, 20, 16, 18, 16, 14, 14} },
2209 { {30, 30, 30, 30, 28, 26, 30, 24, 20, 16, 18, 16, 14, 14} },
2210 { {30, 30, 30, 30, 28, 26, 30, 24, 20, 16, 18, 16, 14, 14} },
2212 .calTargetPower5GHT40 = {
2214 * 0_8_16,1-3_9-11_17-19,
2215 * 4,5,6,7,12,13,14,15,20,21,22,23
2217 { {32, 32, 32, 30, 28, 26, 30, 28, 26, 24, 24, 24, 22, 22} },
2218 { {32, 32, 32, 30, 28, 26, 30, 28, 26, 24, 24, 24, 22, 22} },
2219 { {32, 32, 32, 30, 28, 26, 30, 28, 26, 24, 24, 24, 22, 22} },
2220 { {32, 32, 32, 30, 28, 26, 30, 26, 24, 22, 22, 22, 20, 20} },
2221 { {32, 32, 32, 30, 28, 26, 30, 26, 24, 22, 20, 18, 16, 16} },
2222 { {32, 32, 32, 30, 28, 26, 30, 22, 20, 16, 18, 16, 14, 14} },
2223 { {30, 30, 30, 30, 28, 26, 30, 22, 20, 16, 18, 16, 14, 14} },
2224 { {30, 30, 30, 30, 28, 26, 30, 22, 20, 16, 18, 16, 14, 14} },
2227 0x10, 0x16, 0x18, 0x40, 0x46,
2228 0x48, 0x30, 0x36, 0x38
2232 /* Data[0].ctledges[0].bchannel */ FREQ2FBIN(5180, 0),
2233 /* Data[0].ctledges[1].bchannel */ FREQ2FBIN(5260, 0),
2234 /* Data[0].ctledges[2].bchannel */ FREQ2FBIN(5280, 0),
2235 /* Data[0].ctledges[3].bchannel */ FREQ2FBIN(5500, 0),
2236 /* Data[0].ctledges[4].bchannel */ FREQ2FBIN(5600, 0),
2237 /* Data[0].ctledges[5].bchannel */ FREQ2FBIN(5700, 0),
2238 /* Data[0].ctledges[6].bchannel */ FREQ2FBIN(5745, 0),
2239 /* Data[0].ctledges[7].bchannel */ FREQ2FBIN(5825, 0)
2242 /* Data[1].ctledges[0].bchannel */ FREQ2FBIN(5180, 0),
2243 /* Data[1].ctledges[1].bchannel */ FREQ2FBIN(5260, 0),
2244 /* Data[1].ctledges[2].bchannel */ FREQ2FBIN(5280, 0),
2245 /* Data[1].ctledges[3].bchannel */ FREQ2FBIN(5500, 0),
2246 /* Data[1].ctledges[4].bchannel */ FREQ2FBIN(5520, 0),
2247 /* Data[1].ctledges[5].bchannel */ FREQ2FBIN(5700, 0),
2248 /* Data[1].ctledges[6].bchannel */ FREQ2FBIN(5745, 0),
2249 /* Data[1].ctledges[7].bchannel */ FREQ2FBIN(5825, 0)
2253 /* Data[2].ctledges[0].bchannel */ FREQ2FBIN(5190, 0),
2254 /* Data[2].ctledges[1].bchannel */ FREQ2FBIN(5230, 0),
2255 /* Data[2].ctledges[2].bchannel */ FREQ2FBIN(5270, 0),
2256 /* Data[2].ctledges[3].bchannel */ FREQ2FBIN(5310, 0),
2257 /* Data[2].ctledges[4].bchannel */ FREQ2FBIN(5510, 0),
2258 /* Data[2].ctledges[5].bchannel */ FREQ2FBIN(5550, 0),
2259 /* Data[2].ctledges[6].bchannel */ FREQ2FBIN(5670, 0),
2260 /* Data[2].ctledges[7].bchannel */ FREQ2FBIN(5755, 0)
2264 /* Data[3].ctledges[0].bchannel */ FREQ2FBIN(5180, 0),
2265 /* Data[3].ctledges[1].bchannel */ FREQ2FBIN(5200, 0),
2266 /* Data[3].ctledges[2].bchannel */ FREQ2FBIN(5260, 0),
2267 /* Data[3].ctledges[3].bchannel */ FREQ2FBIN(5320, 0),
2268 /* Data[3].ctledges[4].bchannel */ FREQ2FBIN(5500, 0),
2269 /* Data[3].ctledges[5].bchannel */ FREQ2FBIN(5700, 0),
2270 /* Data[3].ctledges[6].bchannel */ 0xFF,
2271 /* Data[3].ctledges[7].bchannel */ 0xFF,
2275 /* Data[4].ctledges[0].bchannel */ FREQ2FBIN(5180, 0),
2276 /* Data[4].ctledges[1].bchannel */ FREQ2FBIN(5260, 0),
2277 /* Data[4].ctledges[2].bchannel */ FREQ2FBIN(5500, 0),
2278 /* Data[4].ctledges[3].bchannel */ FREQ2FBIN(5700, 0),
2279 /* Data[4].ctledges[4].bchannel */ 0xFF,
2280 /* Data[4].ctledges[5].bchannel */ 0xFF,
2281 /* Data[4].ctledges[6].bchannel */ 0xFF,
2282 /* Data[4].ctledges[7].bchannel */ 0xFF,
2286 /* Data[5].ctledges[0].bchannel */ FREQ2FBIN(5190, 0),
2287 /* Data[5].ctledges[1].bchannel */ FREQ2FBIN(5270, 0),
2288 /* Data[5].ctledges[2].bchannel */ FREQ2FBIN(5310, 0),
2289 /* Data[5].ctledges[3].bchannel */ FREQ2FBIN(5510, 0),
2290 /* Data[5].ctledges[4].bchannel */ FREQ2FBIN(5590, 0),
2291 /* Data[5].ctledges[5].bchannel */ FREQ2FBIN(5670, 0),
2292 /* Data[5].ctledges[6].bchannel */ 0xFF,
2293 /* Data[5].ctledges[7].bchannel */ 0xFF
2297 /* Data[6].ctledges[0].bchannel */ FREQ2FBIN(5180, 0),
2298 /* Data[6].ctledges[1].bchannel */ FREQ2FBIN(5200, 0),
2299 /* Data[6].ctledges[2].bchannel */ FREQ2FBIN(5220, 0),
2300 /* Data[6].ctledges[3].bchannel */ FREQ2FBIN(5260, 0),
2301 /* Data[6].ctledges[4].bchannel */ FREQ2FBIN(5500, 0),
2302 /* Data[6].ctledges[5].bchannel */ FREQ2FBIN(5600, 0),
2303 /* Data[6].ctledges[6].bchannel */ FREQ2FBIN(5700, 0),
2304 /* Data[6].ctledges[7].bchannel */ FREQ2FBIN(5745, 0)
2308 /* Data[7].ctledges[0].bchannel */ FREQ2FBIN(5180, 0),
2309 /* Data[7].ctledges[1].bchannel */ FREQ2FBIN(5260, 0),
2310 /* Data[7].ctledges[2].bchannel */ FREQ2FBIN(5320, 0),
2311 /* Data[7].ctledges[3].bchannel */ FREQ2FBIN(5500, 0),
2312 /* Data[7].ctledges[4].bchannel */ FREQ2FBIN(5560, 0),
2313 /* Data[7].ctledges[5].bchannel */ FREQ2FBIN(5700, 0),
2314 /* Data[7].ctledges[6].bchannel */ FREQ2FBIN(5745, 0),
2315 /* Data[7].ctledges[7].bchannel */ FREQ2FBIN(5825, 0)
2319 /* Data[8].ctledges[0].bchannel */ FREQ2FBIN(5190, 0),
2320 /* Data[8].ctledges[1].bchannel */ FREQ2FBIN(5230, 0),
2321 /* Data[8].ctledges[2].bchannel */ FREQ2FBIN(5270, 0),
2322 /* Data[8].ctledges[3].bchannel */ FREQ2FBIN(5510, 0),
2323 /* Data[8].ctledges[4].bchannel */ FREQ2FBIN(5550, 0),
2324 /* Data[8].ctledges[5].bchannel */ FREQ2FBIN(5670, 0),
2325 /* Data[8].ctledges[6].bchannel */ FREQ2FBIN(5755, 0),
2326 /* Data[8].ctledges[7].bchannel */ FREQ2FBIN(5795, 0)
2329 .ctlPowerData_5G = {
2332 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
2333 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 0),
2338 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
2339 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 0),
2344 CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 1),
2345 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
2350 CTL(60, 0), CTL(60, 1), CTL(60, 1), CTL(60, 0),
2351 CTL(60, 1), CTL(60, 0), CTL(60, 0), CTL(60, 0),
2356 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 0),
2357 CTL(60, 0), CTL(60, 0), CTL(60, 0), CTL(60, 0),
2362 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
2363 CTL(60, 1), CTL(60, 0), CTL(60, 0), CTL(60, 0),
2368 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
2369 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
2374 CTL(60, 1), CTL(60, 1), CTL(60, 0), CTL(60, 1),
2375 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 0),
2380 CTL(60, 1), CTL(60, 0), CTL(60, 1), CTL(60, 1),
2381 CTL(60, 1), CTL(60, 1), CTL(60, 0), CTL(60, 1),
2387 static const struct ar9300_eeprom ar9300_h116 = {
2389 .templateVersion = 4,
2390 .macAddr = {0x00, 0x03, 0x7f, 0x0, 0x0, 0x0},
2391 .custData = {"h116-041-f0000"},
2393 .regDmn = { LE16(0), LE16(0x1f) },
2394 .txrxMask = 0x33, /* 4 bits tx and 4 bits rx */
2396 .opFlags = AR5416_OPFLAGS_11G | AR5416_OPFLAGS_11A,
2400 .blueToothOptions = 0,
2402 .deviceType = 5, /* takes lower byte in eeprom location */
2403 .pwrTableOffset = AR9300_PWR_TABLE_OFFSET,
2404 .params_for_tuning_caps = {0, 0},
2405 .featureEnable = 0x0d,
2407 * bit0 - enable tx temp comp - disabled
2408 * bit1 - enable tx volt comp - disabled
2409 * bit2 - enable fastClock - enabled
2410 * bit3 - enable doubling - enabled
2411 * bit4 - enable internal regulator - disabled
2412 * bit5 - enable pa predistortion - disabled
2414 .miscConfiguration = 0, /* bit0 - turn down drivestrength */
2415 .eepromWriteEnableGpio = 6,
2416 .wlanDisableGpio = 0,
2418 .rxBandSelectGpio = 0xff,
2423 /* ar9300_modal_eep_header 2g */
2424 /* 4 idle,t1,t2,b(4 bits per setting) */
2425 .antCtrlCommon = LE32(0x110),
2426 /* 4 ra1l1, ra2l1, ra1l2, ra2l2, ra12 */
2427 .antCtrlCommon2 = LE32(0x44444),
2430 * antCtrlChain[AR9300_MAX_CHAINS]; 6 idle, t, r,
2431 * rx1, rx12, b (2 bits each)
2433 .antCtrlChain = { LE16(0x10), LE16(0x10), LE16(0x10) },
2436 * xatten1DB[AR9300_MAX_CHAINS]; 3 xatten1_db
2437 * for ar9280 (0xa20c/b20c 5:0)
2439 .xatten1DB = {0x1f, 0x1f, 0x1f},
2442 * xatten1Margin[AR9300_MAX_CHAINS]; 3 xatten1_margin
2443 * for ar9280 (0xa20c/b20c 16:12
2445 .xatten1Margin = {0x12, 0x12, 0x12},
2450 * spurChans[OSPREY_EEPROM_MODAL_SPURS]; spur
2451 * channels in usual fbin coding format
2453 .spurChans = {FREQ2FBIN(2464, 1), 0, 0, 0, 0},
2456 * noiseFloorThreshCh[AR9300_MAX_CHAINS]; 3 Check
2457 * if the register is per chain
2459 .noiseFloorThreshCh = {-1, 0, 0},
2460 .ob = {1, 1, 1},/* 3 chain */
2461 .db_stage2 = {1, 1, 1}, /* 3 chain */
2462 .db_stage3 = {0, 0, 0},
2463 .db_stage4 = {0, 0, 0},
2465 .txFrameToDataStart = 0x0e,
2466 .txFrameToPaOn = 0x0e,
2467 .txClip = 3, /* 4 bits tx_clip, 4 bits dac_scale_cck */
2469 .switchSettling = 0x2c,
2470 .adcDesiredSize = -30,
2473 .txFrameToXpaOn = 0xe,
2475 .papdRateMaskHt20 = LE32(0x0c80C080),
2476 .papdRateMaskHt40 = LE32(0x0080C080),
2478 0, 0, 0, 0, 0, 0, 0, 0,
2482 .ant_div_control = 0,
2483 .future = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}
2490 /* ar9300_cal_data_per_freq_op_loop 2g */
2492 { {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0} },
2493 { {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0} },
2494 { {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0} },
2496 .calTarget_freqbin_Cck = {
2500 .calTarget_freqbin_2G = {
2505 .calTarget_freqbin_2GHT20 = {
2510 .calTarget_freqbin_2GHT40 = {
2515 .calTargetPowerCck = {
2516 /* 1L-5L,5S,11L,11S */
2517 { {34, 34, 34, 34} },
2518 { {34, 34, 34, 34} },
2520 .calTargetPower2G = {
2522 { {34, 34, 32, 32} },
2523 { {34, 34, 32, 32} },
2524 { {34, 34, 32, 32} },
2526 .calTargetPower2GHT20 = {
2527 { {32, 32, 32, 32, 32, 30, 32, 32, 30, 28, 0, 0, 0, 0} },
2528 { {32, 32, 32, 32, 32, 30, 32, 32, 30, 28, 0, 0, 0, 0} },
2529 { {32, 32, 32, 32, 32, 30, 32, 32, 30, 28, 0, 0, 0, 0} },
2531 .calTargetPower2GHT40 = {
2532 { {30, 30, 30, 30, 30, 28, 30, 30, 28, 26, 0, 0, 0, 0} },
2533 { {30, 30, 30, 30, 30, 28, 30, 30, 28, 26, 0, 0, 0, 0} },
2534 { {30, 30, 30, 30, 30, 28, 30, 30, 28, 26, 0, 0, 0, 0} },
2537 0x11, 0x12, 0x15, 0x17, 0x41, 0x42,
2538 0x45, 0x47, 0x31, 0x32, 0x35, 0x37,
2568 /* Data[4].ctlEdges[0].bChannel */ FREQ2FBIN(2412, 1),
2569 /* Data[4].ctlEdges[1].bChannel */ FREQ2FBIN(2417, 1),
2570 /* Data[4].ctlEdges[2].bChannel */ FREQ2FBIN(2472, 1),
2571 /* Data[4].ctlEdges[3].bChannel */ FREQ2FBIN(2484, 1),
2575 /* Data[5].ctlEdges[0].bChannel */ FREQ2FBIN(2412, 1),
2576 /* Data[5].ctlEdges[1].bChannel */ FREQ2FBIN(2417, 1),
2577 /* Data[5].ctlEdges[2].bChannel */ FREQ2FBIN(2472, 1),
2582 /* Data[6].ctlEdges[0].bChannel */ FREQ2FBIN(2412, 1),
2583 /* Data[6].ctlEdges[1].bChannel */ FREQ2FBIN(2417, 1),
2589 /* Data[7].ctlEdges[0].bChannel */ FREQ2FBIN(2422, 1),
2590 /* Data[7].ctlEdges[1].bChannel */ FREQ2FBIN(2427, 1),
2591 /* Data[7].ctlEdges[2].bChannel */ FREQ2FBIN(2447, 1),
2592 /* Data[7].ctlEdges[3].bChannel */ FREQ2FBIN(2462, 1),
2596 /* Data[8].ctlEdges[0].bChannel */ FREQ2FBIN(2412, 1),
2597 /* Data[8].ctlEdges[1].bChannel */ FREQ2FBIN(2417, 1),
2598 /* Data[8].ctlEdges[2].bChannel */ FREQ2FBIN(2472, 1),
2602 /* Data[9].ctlEdges[0].bChannel */ FREQ2FBIN(2412, 1),
2603 /* Data[9].ctlEdges[1].bChannel */ FREQ2FBIN(2417, 1),
2604 /* Data[9].ctlEdges[2].bChannel */ FREQ2FBIN(2472, 1),
2609 /* Data[10].ctlEdges[0].bChannel */ FREQ2FBIN(2412, 1),
2610 /* Data[10].ctlEdges[1].bChannel */ FREQ2FBIN(2417, 1),
2611 /* Data[10].ctlEdges[2].bChannel */ FREQ2FBIN(2472, 1),
2616 /* Data[11].ctlEdges[0].bChannel */ FREQ2FBIN(2422, 1),
2617 /* Data[11].ctlEdges[1].bChannel */ FREQ2FBIN(2427, 1),
2618 /* Data[11].ctlEdges[2].bChannel */ FREQ2FBIN(2447, 1),
2619 /* Data[11].ctlEdges[3].bChannel */ FREQ2FBIN(2462, 1),
2622 .ctlPowerData_2G = {
2623 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
2624 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
2625 { { CTL(60, 1), CTL(60, 0), CTL(60, 0), CTL(60, 1) } },
2627 { { CTL(60, 1), CTL(60, 0), CTL(60, 0), CTL(60, 0) } },
2628 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
2629 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
2631 { { CTL(60, 0), CTL(60, 1), CTL(60, 1), CTL(60, 0) } },
2632 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
2633 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
2635 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
2636 { { CTL(60, 0), CTL(60, 1), CTL(60, 1), CTL(60, 1) } },
2637 { { CTL(60, 0), CTL(60, 1), CTL(60, 1), CTL(60, 1) } },
2640 /* 4 idle,t1,t2,b (4 bits per setting) */
2641 .antCtrlCommon = LE32(0x220),
2642 /* 4 ra1l1, ra2l1, ra1l2,ra2l2,ra12 */
2643 .antCtrlCommon2 = LE32(0x44444),
2644 /* antCtrlChain 6 idle, t,r,rx1,rx12,b (2 bits each) */
2646 LE16(0x150), LE16(0x150), LE16(0x150),
2648 /* xatten1DB 3 xatten1_db for AR9280 (0xa20c/b20c 5:0) */
2649 .xatten1DB = {0x19, 0x19, 0x19},
2652 * xatten1Margin[AR9300_MAX_CHAINS]; 3 xatten1_margin
2653 * for merlin (0xa20c/b20c 16:12
2655 .xatten1Margin = {0x14, 0x14, 0x14},
2658 /* spurChans spur channels in usual fbin coding format */
2659 .spurChans = {0, 0, 0, 0, 0},
2660 /* noiseFloorThreshCh Check if the register is per chain */
2661 .noiseFloorThreshCh = {-1, 0, 0},
2662 .ob = {3, 3, 3}, /* 3 chain */
2663 .db_stage2 = {3, 3, 3}, /* 3 chain */
2664 .db_stage3 = {3, 3, 3}, /* doesn't exist for 2G */
2665 .db_stage4 = {3, 3, 3}, /* don't exist for 2G */
2667 .txFrameToDataStart = 0x0e,
2668 .txFrameToPaOn = 0x0e,
2669 .txClip = 3, /* 4 bits tx_clip, 4 bits dac_scale_cck */
2671 .switchSettling = 0x2d,
2672 .adcDesiredSize = -30,
2675 .txFrameToXpaOn = 0xe,
2677 .papdRateMaskHt20 = LE32(0x0cf0e0e0),
2678 .papdRateMaskHt40 = LE32(0x6cf0e0e0),
2680 0, 0, 0, 0, 0, 0, 0, 0,
2685 .tempSlopeHigh = 50,
2686 .xatten1DBLow = {0, 0, 0},
2687 .xatten1MarginLow = {0, 0, 0},
2688 .xatten1DBHigh = {0, 0, 0},
2689 .xatten1MarginHigh = {0, 0, 0}
2734 .calTarget_freqbin_5G = {
2744 .calTarget_freqbin_5GHT20 = {
2754 .calTarget_freqbin_5GHT40 = {
2764 .calTargetPower5G = {
2766 { {30, 30, 28, 24} },
2767 { {30, 30, 28, 24} },
2768 { {30, 30, 28, 24} },
2769 { {30, 30, 28, 24} },
2770 { {30, 30, 28, 24} },
2771 { {30, 30, 28, 24} },
2772 { {30, 30, 28, 24} },
2773 { {30, 30, 28, 24} },
2775 .calTargetPower5GHT20 = {
2777 * 0_8_16,1-3_9-11_17-19,
2778 * 4,5,6,7,12,13,14,15,20,21,22,23
2780 { {30, 30, 30, 28, 24, 20, 30, 28, 24, 20, 0, 0, 0, 0} },
2781 { {30, 30, 30, 28, 24, 20, 30, 28, 24, 20, 0, 0, 0, 0} },
2782 { {30, 30, 30, 26, 22, 18, 30, 26, 22, 18, 0, 0, 0, 0} },
2783 { {30, 30, 30, 26, 22, 18, 30, 26, 22, 18, 0, 0, 0, 0} },
2784 { {30, 30, 30, 24, 20, 16, 30, 24, 20, 16, 0, 0, 0, 0} },
2785 { {30, 30, 30, 24, 20, 16, 30, 24, 20, 16, 0, 0, 0, 0} },
2786 { {30, 30, 30, 22, 18, 14, 30, 22, 18, 14, 0, 0, 0, 0} },
2787 { {30, 30, 30, 22, 18, 14, 30, 22, 18, 14, 0, 0, 0, 0} },
2789 .calTargetPower5GHT40 = {
2791 * 0_8_16,1-3_9-11_17-19,
2792 * 4,5,6,7,12,13,14,15,20,21,22,23
2794 { {28, 28, 28, 26, 22, 18, 28, 26, 22, 18, 0, 0, 0, 0} },
2795 { {28, 28, 28, 26, 22, 18, 28, 26, 22, 18, 0, 0, 0, 0} },
2796 { {28, 28, 28, 24, 20, 16, 28, 24, 20, 16, 0, 0, 0, 0} },
2797 { {28, 28, 28, 24, 20, 16, 28, 24, 20, 16, 0, 0, 0, 0} },
2798 { {28, 28, 28, 22, 18, 14, 28, 22, 18, 14, 0, 0, 0, 0} },
2799 { {28, 28, 28, 22, 18, 14, 28, 22, 18, 14, 0, 0, 0, 0} },
2800 { {28, 28, 28, 20, 16, 12, 28, 20, 16, 12, 0, 0, 0, 0} },
2801 { {28, 28, 28, 20, 16, 12, 28, 20, 16, 12, 0, 0, 0, 0} },
2804 0x10, 0x16, 0x18, 0x40, 0x46,
2805 0x48, 0x30, 0x36, 0x38
2809 /* Data[0].ctlEdges[0].bChannel */ FREQ2FBIN(5180, 0),
2810 /* Data[0].ctlEdges[1].bChannel */ FREQ2FBIN(5260, 0),
2811 /* Data[0].ctlEdges[2].bChannel */ FREQ2FBIN(5280, 0),
2812 /* Data[0].ctlEdges[3].bChannel */ FREQ2FBIN(5500, 0),
2813 /* Data[0].ctlEdges[4].bChannel */ FREQ2FBIN(5600, 0),
2814 /* Data[0].ctlEdges[5].bChannel */ FREQ2FBIN(5700, 0),
2815 /* Data[0].ctlEdges[6].bChannel */ FREQ2FBIN(5745, 0),
2816 /* Data[0].ctlEdges[7].bChannel */ FREQ2FBIN(5825, 0)
2819 /* Data[1].ctlEdges[0].bChannel */ FREQ2FBIN(5180, 0),
2820 /* Data[1].ctlEdges[1].bChannel */ FREQ2FBIN(5260, 0),
2821 /* Data[1].ctlEdges[2].bChannel */ FREQ2FBIN(5280, 0),
2822 /* Data[1].ctlEdges[3].bChannel */ FREQ2FBIN(5500, 0),
2823 /* Data[1].ctlEdges[4].bChannel */ FREQ2FBIN(5520, 0),
2824 /* Data[1].ctlEdges[5].bChannel */ FREQ2FBIN(5700, 0),
2825 /* Data[1].ctlEdges[6].bChannel */ FREQ2FBIN(5745, 0),
2826 /* Data[1].ctlEdges[7].bChannel */ FREQ2FBIN(5825, 0)
2830 /* Data[2].ctlEdges[0].bChannel */ FREQ2FBIN(5190, 0),
2831 /* Data[2].ctlEdges[1].bChannel */ FREQ2FBIN(5230, 0),
2832 /* Data[2].ctlEdges[2].bChannel */ FREQ2FBIN(5270, 0),
2833 /* Data[2].ctlEdges[3].bChannel */ FREQ2FBIN(5310, 0),
2834 /* Data[2].ctlEdges[4].bChannel */ FREQ2FBIN(5510, 0),
2835 /* Data[2].ctlEdges[5].bChannel */ FREQ2FBIN(5550, 0),
2836 /* Data[2].ctlEdges[6].bChannel */ FREQ2FBIN(5670, 0),
2837 /* Data[2].ctlEdges[7].bChannel */ FREQ2FBIN(5755, 0)
2841 /* Data[3].ctlEdges[0].bChannel */ FREQ2FBIN(5180, 0),
2842 /* Data[3].ctlEdges[1].bChannel */ FREQ2FBIN(5200, 0),
2843 /* Data[3].ctlEdges[2].bChannel */ FREQ2FBIN(5260, 0),
2844 /* Data[3].ctlEdges[3].bChannel */ FREQ2FBIN(5320, 0),
2845 /* Data[3].ctlEdges[4].bChannel */ FREQ2FBIN(5500, 0),
2846 /* Data[3].ctlEdges[5].bChannel */ FREQ2FBIN(5700, 0),
2847 /* Data[3].ctlEdges[6].bChannel */ 0xFF,
2848 /* Data[3].ctlEdges[7].bChannel */ 0xFF,
2852 /* Data[4].ctlEdges[0].bChannel */ FREQ2FBIN(5180, 0),
2853 /* Data[4].ctlEdges[1].bChannel */ FREQ2FBIN(5260, 0),
2854 /* Data[4].ctlEdges[2].bChannel */ FREQ2FBIN(5500, 0),
2855 /* Data[4].ctlEdges[3].bChannel */ FREQ2FBIN(5700, 0),
2856 /* Data[4].ctlEdges[4].bChannel */ 0xFF,
2857 /* Data[4].ctlEdges[5].bChannel */ 0xFF,
2858 /* Data[4].ctlEdges[6].bChannel */ 0xFF,
2859 /* Data[4].ctlEdges[7].bChannel */ 0xFF,
2863 /* Data[5].ctlEdges[0].bChannel */ FREQ2FBIN(5190, 0),
2864 /* Data[5].ctlEdges[1].bChannel */ FREQ2FBIN(5270, 0),
2865 /* Data[5].ctlEdges[2].bChannel */ FREQ2FBIN(5310, 0),
2866 /* Data[5].ctlEdges[3].bChannel */ FREQ2FBIN(5510, 0),
2867 /* Data[5].ctlEdges[4].bChannel */ FREQ2FBIN(5590, 0),
2868 /* Data[5].ctlEdges[5].bChannel */ FREQ2FBIN(5670, 0),
2869 /* Data[5].ctlEdges[6].bChannel */ 0xFF,
2870 /* Data[5].ctlEdges[7].bChannel */ 0xFF
2874 /* Data[6].ctlEdges[0].bChannel */ FREQ2FBIN(5180, 0),
2875 /* Data[6].ctlEdges[1].bChannel */ FREQ2FBIN(5200, 0),
2876 /* Data[6].ctlEdges[2].bChannel */ FREQ2FBIN(5220, 0),
2877 /* Data[6].ctlEdges[3].bChannel */ FREQ2FBIN(5260, 0),
2878 /* Data[6].ctlEdges[4].bChannel */ FREQ2FBIN(5500, 0),
2879 /* Data[6].ctlEdges[5].bChannel */ FREQ2FBIN(5600, 0),
2880 /* Data[6].ctlEdges[6].bChannel */ FREQ2FBIN(5700, 0),
2881 /* Data[6].ctlEdges[7].bChannel */ FREQ2FBIN(5745, 0)
2885 /* Data[7].ctlEdges[0].bChannel */ FREQ2FBIN(5180, 0),
2886 /* Data[7].ctlEdges[1].bChannel */ FREQ2FBIN(5260, 0),
2887 /* Data[7].ctlEdges[2].bChannel */ FREQ2FBIN(5320, 0),
2888 /* Data[7].ctlEdges[3].bChannel */ FREQ2FBIN(5500, 0),
2889 /* Data[7].ctlEdges[4].bChannel */ FREQ2FBIN(5560, 0),
2890 /* Data[7].ctlEdges[5].bChannel */ FREQ2FBIN(5700, 0),
2891 /* Data[7].ctlEdges[6].bChannel */ FREQ2FBIN(5745, 0),
2892 /* Data[7].ctlEdges[7].bChannel */ FREQ2FBIN(5825, 0)
2896 /* Data[8].ctlEdges[0].bChannel */ FREQ2FBIN(5190, 0),
2897 /* Data[8].ctlEdges[1].bChannel */ FREQ2FBIN(5230, 0),
2898 /* Data[8].ctlEdges[2].bChannel */ FREQ2FBIN(5270, 0),
2899 /* Data[8].ctlEdges[3].bChannel */ FREQ2FBIN(5510, 0),
2900 /* Data[8].ctlEdges[4].bChannel */ FREQ2FBIN(5550, 0),
2901 /* Data[8].ctlEdges[5].bChannel */ FREQ2FBIN(5670, 0),
2902 /* Data[8].ctlEdges[6].bChannel */ FREQ2FBIN(5755, 0),
2903 /* Data[8].ctlEdges[7].bChannel */ FREQ2FBIN(5795, 0)
2906 .ctlPowerData_5G = {
2909 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
2910 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 0),
2915 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
2916 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 0),
2921 CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 1),
2922 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
2927 CTL(60, 0), CTL(60, 1), CTL(60, 1), CTL(60, 0),
2928 CTL(60, 1), CTL(60, 0), CTL(60, 0), CTL(60, 0),
2933 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 0),
2934 CTL(60, 0), CTL(60, 0), CTL(60, 0), CTL(60, 0),
2939 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
2940 CTL(60, 1), CTL(60, 0), CTL(60, 0), CTL(60, 0),
2945 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
2946 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
2951 CTL(60, 1), CTL(60, 1), CTL(60, 0), CTL(60, 1),
2952 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 0),
2957 CTL(60, 1), CTL(60, 0), CTL(60, 1), CTL(60, 1),
2958 CTL(60, 1), CTL(60, 1), CTL(60, 0), CTL(60, 1),
2965 static const struct ar9300_eeprom *ar9300_eep_templates[] = {
2973 static const struct ar9300_eeprom *ar9003_eeprom_struct_find_by_id(int id)
2975 #define N_LOOP (sizeof(ar9300_eep_templates) / sizeof(ar9300_eep_templates[0]))
2978 for (it = 0; it < N_LOOP; it++)
2979 if (ar9300_eep_templates[it]->templateVersion == id)
2980 return ar9300_eep_templates[it];
2986 static u16 ath9k_hw_fbin2freq(u8 fbin, bool is2GHz)
2988 if (fbin == AR5416_BCHAN_UNUSED)
2991 return (u16) ((is2GHz) ? (2300 + fbin) : (4800 + 5 * fbin));
2994 static int ath9k_hw_ar9300_check_eeprom(struct ath_hw *ah)
2999 static int interpolate(int x, int xa, int xb, int ya, int yb)
3001 int bf, factor, plus;
3003 bf = 2 * (yb - ya) * (x - xa) / (xb - xa);
3006 return ya + factor + plus;
3009 static u32 ath9k_hw_ar9300_get_eeprom(struct ath_hw *ah,
3010 enum eeprom_param param)
3012 struct ar9300_eeprom *eep = &ah->eeprom.ar9300_eep;
3013 struct ar9300_base_eep_hdr *pBase = &eep->baseEepHeader;
3017 return get_unaligned_be16(eep->macAddr);
3019 return get_unaligned_be16(eep->macAddr + 2);
3021 return get_unaligned_be16(eep->macAddr + 4);
3023 return le16_to_cpu(pBase->regDmn[0]);
3025 return le16_to_cpu(pBase->regDmn[1]);
3027 return pBase->deviceCap;
3029 return pBase->opCapFlags.opFlags;
3031 return pBase->rfSilent;
3033 return (pBase->txrxMask >> 4) & 0xf;
3035 return pBase->txrxMask & 0xf;
3036 case EEP_DRIVE_STRENGTH:
3037 #define AR9300_EEP_BASE_DRIV_STRENGTH 0x1
3038 return pBase->miscConfiguration & AR9300_EEP_BASE_DRIV_STRENGTH;
3039 case EEP_INTERNAL_REGULATOR:
3040 /* Bit 4 is internal regulator flag */
3041 return (pBase->featureEnable & 0x10) >> 4;
3043 return le32_to_cpu(pBase->swreg);
3045 return !!(pBase->featureEnable & BIT(5));
3046 case EEP_CHAIN_MASK_REDUCE:
3047 return (pBase->miscConfiguration >> 0x3) & 0x1;
3048 case EEP_ANT_DIV_CTL1:
3049 return eep->base_ext1.ant_div_control;
3055 static bool ar9300_eeprom_read_byte(struct ath_common *common, int address,
3060 if (unlikely(!ath9k_hw_nvram_read(common, address / 2, &val)))
3063 *buffer = (val >> (8 * (address % 2))) & 0xff;
3067 static bool ar9300_eeprom_read_word(struct ath_common *common, int address,
3072 if (unlikely(!ath9k_hw_nvram_read(common, address / 2, &val)))
3075 buffer[0] = val >> 8;
3076 buffer[1] = val & 0xff;
3081 static bool ar9300_read_eeprom(struct ath_hw *ah, int address, u8 *buffer,
3084 struct ath_common *common = ath9k_hw_common(ah);
3087 if ((address < 0) || ((address + count) / 2 > AR9300_EEPROM_SIZE - 1)) {
3088 ath_dbg(common, ATH_DBG_EEPROM,
3089 "eeprom address not in range\n");
3094 * Since we're reading the bytes in reverse order from a little-endian
3095 * word stream, an even address means we only use the lower half of
3096 * the 16-bit word at that address
3098 if (address % 2 == 0) {
3099 if (!ar9300_eeprom_read_byte(common, address--, buffer++))
3105 for (i = 0; i < count / 2; i++) {
3106 if (!ar9300_eeprom_read_word(common, address, buffer))
3114 if (!ar9300_eeprom_read_byte(common, address, buffer))
3120 ath_dbg(common, ATH_DBG_EEPROM,
3121 "unable to read eeprom region at offset %d\n", address);
3125 static bool ar9300_otp_read_word(struct ath_hw *ah, int addr, u32 *data)
3127 REG_READ(ah, AR9300_OTP_BASE + (4 * addr));
3129 if (!ath9k_hw_wait(ah, AR9300_OTP_STATUS, AR9300_OTP_STATUS_TYPE,
3130 AR9300_OTP_STATUS_VALID, 1000))
3133 *data = REG_READ(ah, AR9300_OTP_READ_DATA);
3137 static bool ar9300_read_otp(struct ath_hw *ah, int address, u8 *buffer,
3143 for (i = 0; i < count; i++) {
3144 int offset = 8 * ((address - i) % 4);
3145 if (!ar9300_otp_read_word(ah, (address - i) / 4, &data))
3148 buffer[i] = (data >> offset) & 0xff;
3155 static void ar9300_comp_hdr_unpack(u8 *best, int *code, int *reference,
3156 int *length, int *major, int *minor)
3158 unsigned long value[4];
3164 *code = ((value[0] >> 5) & 0x0007);
3165 *reference = (value[0] & 0x001f) | ((value[1] >> 2) & 0x0020);
3166 *length = ((value[1] << 4) & 0x07f0) | ((value[2] >> 4) & 0x000f);
3167 *major = (value[2] & 0x000f);
3168 *minor = (value[3] & 0x00ff);
3171 static u16 ar9300_comp_cksum(u8 *data, int dsize)
3173 int it, checksum = 0;
3175 for (it = 0; it < dsize; it++) {
3176 checksum += data[it];
3183 static bool ar9300_uncompress_block(struct ath_hw *ah,
3193 struct ath_common *common = ath9k_hw_common(ah);
3197 for (it = 0; it < size; it += (length+2)) {
3201 length = block[it+1];
3204 if (length > 0 && spot >= 0 && spot+length <= mdataSize) {
3205 ath_dbg(common, ATH_DBG_EEPROM,
3206 "Restore at %d: spot=%d offset=%d length=%d\n",
3207 it, spot, offset, length);
3208 memcpy(&mptr[spot], &block[it+2], length);
3210 } else if (length > 0) {
3211 ath_dbg(common, ATH_DBG_EEPROM,
3212 "Bad restore at %d: spot=%d offset=%d length=%d\n",
3213 it, spot, offset, length);
3220 static int ar9300_compress_decision(struct ath_hw *ah,
3225 u8 *word, int length, int mdata_size)
3227 struct ath_common *common = ath9k_hw_common(ah);
3228 const struct ar9300_eeprom *eep = NULL;
3232 if (length != mdata_size) {
3233 ath_dbg(common, ATH_DBG_EEPROM,
3234 "EEPROM structure size mismatch memory=%d eeprom=%d\n",
3235 mdata_size, length);
3238 memcpy(mptr, (u8 *) (word + COMP_HDR_LEN), length);
3239 ath_dbg(common, ATH_DBG_EEPROM,
3240 "restored eeprom %d: uncompressed, length %d\n",
3243 case _CompressBlock:
3244 if (reference == 0) {
3246 eep = ar9003_eeprom_struct_find_by_id(reference);
3248 ath_dbg(common, ATH_DBG_EEPROM,
3249 "can't find reference eeprom struct %d\n",
3253 memcpy(mptr, eep, mdata_size);
3255 ath_dbg(common, ATH_DBG_EEPROM,
3256 "restore eeprom %d: block, reference %d, length %d\n",
3257 it, reference, length);
3258 ar9300_uncompress_block(ah, mptr, mdata_size,
3259 (u8 *) (word + COMP_HDR_LEN), length);
3262 ath_dbg(common, ATH_DBG_EEPROM,
3263 "unknown compression code %d\n", code);
3269 typedef bool (*eeprom_read_op)(struct ath_hw *ah, int address, u8 *buffer,
3272 static bool ar9300_check_header(void *data)
3275 return !(*word == 0 || *word == ~0);
3278 static bool ar9300_check_eeprom_header(struct ath_hw *ah, eeprom_read_op read,
3283 if (!read(ah, base_addr, header, 4))
3286 return ar9300_check_header(header);
3289 static int ar9300_eeprom_restore_flash(struct ath_hw *ah, u8 *mptr,
3292 struct ath_common *common = ath9k_hw_common(ah);
3293 u16 *data = (u16 *) mptr;
3296 for (i = 0; i < mdata_size / 2; i++, data++)
3297 ath9k_hw_nvram_read(common, i, data);
3302 * Read the configuration data from the eeprom.
3303 * The data can be put in any specified memory buffer.
3305 * Returns -1 on error.
3306 * Returns address of next memory location on success.
3308 static int ar9300_eeprom_restore_internal(struct ath_hw *ah,
3309 u8 *mptr, int mdata_size)
3316 int reference, length, major, minor;
3319 u16 checksum, mchecksum;
3320 struct ath_common *common = ath9k_hw_common(ah);
3321 eeprom_read_op read;
3323 if (ath9k_hw_use_flash(ah))
3324 return ar9300_eeprom_restore_flash(ah, mptr, mdata_size);
3326 word = kzalloc(2048, GFP_KERNEL);
3330 memcpy(mptr, &ar9300_default, mdata_size);
3332 read = ar9300_read_eeprom;
3333 if (AR_SREV_9485(ah))
3334 cptr = AR9300_BASE_ADDR_4K;
3335 else if (AR_SREV_9330(ah))
3336 cptr = AR9300_BASE_ADDR_512;
3338 cptr = AR9300_BASE_ADDR;
3339 ath_dbg(common, ATH_DBG_EEPROM,
3340 "Trying EEPROM access at Address 0x%04x\n", cptr);
3341 if (ar9300_check_eeprom_header(ah, read, cptr))
3344 cptr = AR9300_BASE_ADDR_512;
3345 ath_dbg(common, ATH_DBG_EEPROM,
3346 "Trying EEPROM access at Address 0x%04x\n", cptr);
3347 if (ar9300_check_eeprom_header(ah, read, cptr))
3350 read = ar9300_read_otp;
3351 cptr = AR9300_BASE_ADDR;
3352 ath_dbg(common, ATH_DBG_EEPROM,
3353 "Trying OTP access at Address 0x%04x\n", cptr);
3354 if (ar9300_check_eeprom_header(ah, read, cptr))
3357 cptr = AR9300_BASE_ADDR_512;
3358 ath_dbg(common, ATH_DBG_EEPROM,
3359 "Trying OTP access at Address 0x%04x\n", cptr);
3360 if (ar9300_check_eeprom_header(ah, read, cptr))
3366 ath_dbg(common, ATH_DBG_EEPROM, "Found valid EEPROM data\n");
3368 for (it = 0; it < MSTATE; it++) {
3369 if (!read(ah, cptr, word, COMP_HDR_LEN))
3372 if (!ar9300_check_header(word))
3375 ar9300_comp_hdr_unpack(word, &code, &reference,
3376 &length, &major, &minor);
3377 ath_dbg(common, ATH_DBG_EEPROM,
3378 "Found block at %x: code=%d ref=%d length=%d major=%d minor=%d\n",
3379 cptr, code, reference, length, major, minor);
3380 if ((!AR_SREV_9485(ah) && length >= 1024) ||
3381 (AR_SREV_9485(ah) && length > EEPROM_DATA_LEN_9485)) {
3382 ath_dbg(common, ATH_DBG_EEPROM,
3383 "Skipping bad header\n");
3384 cptr -= COMP_HDR_LEN;
3389 read(ah, cptr, word, COMP_HDR_LEN + osize + COMP_CKSUM_LEN);
3390 checksum = ar9300_comp_cksum(&word[COMP_HDR_LEN], length);
3391 mchecksum = get_unaligned_le16(&word[COMP_HDR_LEN + osize]);
3392 ath_dbg(common, ATH_DBG_EEPROM,
3393 "checksum %x %x\n", checksum, mchecksum);
3394 if (checksum == mchecksum) {
3395 ar9300_compress_decision(ah, it, code, reference, mptr,
3396 word, length, mdata_size);
3398 ath_dbg(common, ATH_DBG_EEPROM,
3399 "skipping block with bad checksum\n");
3401 cptr -= (COMP_HDR_LEN + osize + COMP_CKSUM_LEN);
3413 * Restore the configuration structure by reading the eeprom.
3414 * This function destroys any existing in-memory structure
3417 static bool ath9k_hw_ar9300_fill_eeprom(struct ath_hw *ah)
3419 u8 *mptr = (u8 *) &ah->eeprom.ar9300_eep;
3421 if (ar9300_eeprom_restore_internal(ah, mptr,
3422 sizeof(struct ar9300_eeprom)) < 0)
3428 #if defined(CONFIG_ATH9K_DEBUGFS) || defined(CONFIG_ATH9K_HTC_DEBUGFS)
3429 static u32 ar9003_dump_modal_eeprom(char *buf, u32 len, u32 size,
3430 struct ar9300_modal_eep_header *modal_hdr)
3432 PR_EEP("Chain0 Ant. Control", le16_to_cpu(modal_hdr->antCtrlChain[0]));
3433 PR_EEP("Chain1 Ant. Control", le16_to_cpu(modal_hdr->antCtrlChain[1]));
3434 PR_EEP("Chain2 Ant. Control", le16_to_cpu(modal_hdr->antCtrlChain[2]));
3435 PR_EEP("Ant. Common Control", le32_to_cpu(modal_hdr->antCtrlCommon));
3436 PR_EEP("Ant. Common Control2", le32_to_cpu(modal_hdr->antCtrlCommon2));
3437 PR_EEP("Ant. Gain", modal_hdr->antennaGain);
3438 PR_EEP("Switch Settle", modal_hdr->switchSettling);
3439 PR_EEP("Chain0 xatten1DB", modal_hdr->xatten1DB[0]);
3440 PR_EEP("Chain1 xatten1DB", modal_hdr->xatten1DB[1]);
3441 PR_EEP("Chain2 xatten1DB", modal_hdr->xatten1DB[2]);
3442 PR_EEP("Chain0 xatten1Margin", modal_hdr->xatten1Margin[0]);
3443 PR_EEP("Chain1 xatten1Margin", modal_hdr->xatten1Margin[1]);
3444 PR_EEP("Chain2 xatten1Margin", modal_hdr->xatten1Margin[2]);
3445 PR_EEP("Temp Slope", modal_hdr->tempSlope);
3446 PR_EEP("Volt Slope", modal_hdr->voltSlope);
3447 PR_EEP("spur Channels0", modal_hdr->spurChans[0]);
3448 PR_EEP("spur Channels1", modal_hdr->spurChans[1]);
3449 PR_EEP("spur Channels2", modal_hdr->spurChans[2]);
3450 PR_EEP("spur Channels3", modal_hdr->spurChans[3]);
3451 PR_EEP("spur Channels4", modal_hdr->spurChans[4]);
3452 PR_EEP("Chain0 NF Threshold", modal_hdr->noiseFloorThreshCh[0]);
3453 PR_EEP("Chain1 NF Threshold", modal_hdr->noiseFloorThreshCh[1]);
3454 PR_EEP("Chain2 NF Threshold", modal_hdr->noiseFloorThreshCh[2]);
3455 PR_EEP("xPA Bias Level", modal_hdr->xpaBiasLvl);
3456 PR_EEP("txFrameToDataStart", modal_hdr->txFrameToDataStart);
3457 PR_EEP("txFrameToPaOn", modal_hdr->txFrameToPaOn);
3458 PR_EEP("txFrameToXpaOn", modal_hdr->txFrameToXpaOn);
3459 PR_EEP("txClip", modal_hdr->txClip);
3460 PR_EEP("ADC Desired size", modal_hdr->adcDesiredSize);
3461 PR_EEP("Chain0 ob", modal_hdr->ob[0]);
3462 PR_EEP("Chain1 ob", modal_hdr->ob[1]);
3463 PR_EEP("Chain2 ob", modal_hdr->ob[2]);
3465 PR_EEP("Chain0 db_stage2", modal_hdr->db_stage2[0]);
3466 PR_EEP("Chain1 db_stage2", modal_hdr->db_stage2[1]);
3467 PR_EEP("Chain2 db_stage2", modal_hdr->db_stage2[2]);
3468 PR_EEP("Chain0 db_stage3", modal_hdr->db_stage3[0]);
3469 PR_EEP("Chain1 db_stage3", modal_hdr->db_stage3[1]);
3470 PR_EEP("Chain2 db_stage3", modal_hdr->db_stage3[2]);
3471 PR_EEP("Chain0 db_stage4", modal_hdr->db_stage4[0]);
3472 PR_EEP("Chain1 db_stage4", modal_hdr->db_stage4[1]);
3473 PR_EEP("Chain2 db_stage4", modal_hdr->db_stage4[2]);
3478 static u32 ath9k_hw_ar9003_dump_eeprom(struct ath_hw *ah, bool dump_base_hdr,
3479 u8 *buf, u32 len, u32 size)
3481 struct ar9300_eeprom *eep = &ah->eeprom.ar9300_eep;
3482 struct ar9300_base_eep_hdr *pBase;
3484 if (!dump_base_hdr) {
3485 len += snprintf(buf + len, size - len,
3486 "%20s :\n", "2GHz modal Header");
3487 len += ar9003_dump_modal_eeprom(buf, len, size,
3488 &eep->modalHeader2G);
3489 len += snprintf(buf + len, size - len,
3490 "%20s :\n", "5GHz modal Header");
3491 len += ar9003_dump_modal_eeprom(buf, len, size,
3492 &eep->modalHeader5G);
3496 pBase = &eep->baseEepHeader;
3498 PR_EEP("EEPROM Version", ah->eeprom.ar9300_eep.eepromVersion);
3499 PR_EEP("RegDomain1", le16_to_cpu(pBase->regDmn[0]));
3500 PR_EEP("RegDomain2", le16_to_cpu(pBase->regDmn[1]));
3501 PR_EEP("TX Mask", (pBase->txrxMask >> 4));
3502 PR_EEP("RX Mask", (pBase->txrxMask & 0x0f));
3503 PR_EEP("Allow 5GHz", !!(pBase->opCapFlags.opFlags &
3504 AR5416_OPFLAGS_11A));
3505 PR_EEP("Allow 2GHz", !!(pBase->opCapFlags.opFlags &
3506 AR5416_OPFLAGS_11G));
3507 PR_EEP("Disable 2GHz HT20", !!(pBase->opCapFlags.opFlags &
3508 AR5416_OPFLAGS_N_2G_HT20));
3509 PR_EEP("Disable 2GHz HT40", !!(pBase->opCapFlags.opFlags &
3510 AR5416_OPFLAGS_N_2G_HT40));
3511 PR_EEP("Disable 5Ghz HT20", !!(pBase->opCapFlags.opFlags &
3512 AR5416_OPFLAGS_N_5G_HT20));
3513 PR_EEP("Disable 5Ghz HT40", !!(pBase->opCapFlags.opFlags &
3514 AR5416_OPFLAGS_N_5G_HT40));
3515 PR_EEP("Big Endian", !!(pBase->opCapFlags.eepMisc & 0x01));
3516 PR_EEP("RF Silent", pBase->rfSilent);
3517 PR_EEP("BT option", pBase->blueToothOptions);
3518 PR_EEP("Device Cap", pBase->deviceCap);
3519 PR_EEP("Device Type", pBase->deviceType);
3520 PR_EEP("Power Table Offset", pBase->pwrTableOffset);
3521 PR_EEP("Tuning Caps1", pBase->params_for_tuning_caps[0]);
3522 PR_EEP("Tuning Caps2", pBase->params_for_tuning_caps[1]);
3523 PR_EEP("Enable Tx Temp Comp", !!(pBase->featureEnable & BIT(0)));
3524 PR_EEP("Enable Tx Volt Comp", !!(pBase->featureEnable & BIT(1)));
3525 PR_EEP("Enable fast clock", !!(pBase->featureEnable & BIT(2)));
3526 PR_EEP("Enable doubling", !!(pBase->featureEnable & BIT(3)));
3527 PR_EEP("Internal regulator", !!(pBase->featureEnable & BIT(4)));
3528 PR_EEP("Enable Paprd", !!(pBase->featureEnable & BIT(5)));
3529 PR_EEP("Driver Strength", !!(pBase->miscConfiguration & BIT(0)));
3530 PR_EEP("Chain mask Reduce", (pBase->miscConfiguration >> 0x3) & 0x1);
3531 PR_EEP("Write enable Gpio", pBase->eepromWriteEnableGpio);
3532 PR_EEP("WLAN Disable Gpio", pBase->wlanDisableGpio);
3533 PR_EEP("WLAN LED Gpio", pBase->wlanLedGpio);
3534 PR_EEP("Rx Band Select Gpio", pBase->rxBandSelectGpio);
3535 PR_EEP("Tx Gain", pBase->txrxgain >> 4);
3536 PR_EEP("Rx Gain", pBase->txrxgain & 0xf);
3537 PR_EEP("SW Reg", le32_to_cpu(pBase->swreg));
3539 len += snprintf(buf + len, size - len, "%20s : %pM\n", "MacAddress",
3540 ah->eeprom.ar9300_eep.macAddr);
3548 static u32 ath9k_hw_ar9003_dump_eeprom(struct ath_hw *ah, bool dump_base_hdr,
3549 u8 *buf, u32 len, u32 size)
3555 /* XXX: review hardware docs */
3556 static int ath9k_hw_ar9300_get_eeprom_ver(struct ath_hw *ah)
3558 return ah->eeprom.ar9300_eep.eepromVersion;
3561 /* XXX: could be read from the eepromVersion, not sure yet */
3562 static int ath9k_hw_ar9300_get_eeprom_rev(struct ath_hw *ah)
3567 static s32 ar9003_hw_xpa_bias_level_get(struct ath_hw *ah, bool is2ghz)
3569 struct ar9300_eeprom *eep = &ah->eeprom.ar9300_eep;
3572 return eep->modalHeader2G.xpaBiasLvl;
3574 return eep->modalHeader5G.xpaBiasLvl;
3577 static void ar9003_hw_xpa_bias_level_apply(struct ath_hw *ah, bool is2ghz)
3579 int bias = ar9003_hw_xpa_bias_level_get(ah, is2ghz);
3581 if (AR_SREV_9485(ah) || AR_SREV_9330(ah) || AR_SREV_9340(ah))
3582 REG_RMW_FIELD(ah, AR_CH0_TOP2, AR_CH0_TOP2_XPABIASLVL, bias);
3583 else if (AR_SREV_9480(ah))
3584 REG_RMW_FIELD(ah, AR_CH0_TOP, AR_CH0_TOP_XPABIASLVL, bias);
3586 REG_RMW_FIELD(ah, AR_CH0_TOP, AR_CH0_TOP_XPABIASLVL, bias);
3587 REG_RMW_FIELD(ah, AR_CH0_THERM,
3588 AR_CH0_THERM_XPABIASLVL_MSB,
3590 REG_RMW_FIELD(ah, AR_CH0_THERM,
3591 AR_CH0_THERM_XPASHORT2GND, 1);
3595 static u16 ar9003_switch_com_spdt_get(struct ath_hw *ah, bool is_2ghz)
3597 struct ar9300_eeprom *eep = &ah->eeprom.ar9300_eep;
3601 val = eep->modalHeader2G.switchcomspdt;
3603 val = eep->modalHeader5G.switchcomspdt;
3604 return le32_to_cpu(val);
3608 static u32 ar9003_hw_ant_ctrl_common_get(struct ath_hw *ah, bool is2ghz)
3610 struct ar9300_eeprom *eep = &ah->eeprom.ar9300_eep;
3614 val = eep->modalHeader2G.antCtrlCommon;
3616 val = eep->modalHeader5G.antCtrlCommon;
3617 return le32_to_cpu(val);
3620 static u32 ar9003_hw_ant_ctrl_common_2_get(struct ath_hw *ah, bool is2ghz)
3622 struct ar9300_eeprom *eep = &ah->eeprom.ar9300_eep;
3626 val = eep->modalHeader2G.antCtrlCommon2;
3628 val = eep->modalHeader5G.antCtrlCommon2;
3629 return le32_to_cpu(val);
3632 static u16 ar9003_hw_ant_ctrl_chain_get(struct ath_hw *ah,
3636 struct ar9300_eeprom *eep = &ah->eeprom.ar9300_eep;
3639 if (chain >= 0 && chain < AR9300_MAX_CHAINS) {
3641 val = eep->modalHeader2G.antCtrlChain[chain];
3643 val = eep->modalHeader5G.antCtrlChain[chain];
3646 return le16_to_cpu(val);
3649 static void ar9003_hw_ant_ctrl_apply(struct ath_hw *ah, bool is2ghz)
3654 static const u32 switch_chain_reg[AR9300_MAX_CHAINS] = {
3655 AR_PHY_SWITCH_CHAIN_0,
3656 AR_PHY_SWITCH_CHAIN_1,
3657 AR_PHY_SWITCH_CHAIN_2,
3660 u32 value = ar9003_hw_ant_ctrl_common_get(ah, is2ghz);
3662 if (AR_SREV_9480(ah)) {
3663 if (AR_SREV_9480_10(ah)) {
3664 value &= ~AR_SWITCH_TABLE_COM_SPDT;
3665 value |= 0x00100000;
3667 REG_RMW_FIELD(ah, AR_PHY_SWITCH_COM,
3668 AR_SWITCH_TABLE_COM_AR9480_ALL, value);
3670 REG_RMW_FIELD(ah, AR_PHY_SWITCH_COM,
3671 AR_SWITCH_TABLE_COM_ALL, value);
3675 * AR9480 defines new switch table for BT/WLAN,
3676 * here's new field name in XXX.ref for both 2G and 5G.
3677 * Register: [GLB_CONTROL] GLB_CONTROL (@0x20044)
3678 * 15:12 R/W SWITCH_TABLE_COM_SPDT_WLAN_RX
3679 * SWITCH_TABLE_COM_SPDT_WLAN_RX
3681 * 11:8 R/W SWITCH_TABLE_COM_SPDT_WLAN_TX
3682 * SWITCH_TABLE_COM_SPDT_WLAN_TX
3684 * 7:4 R/W SWITCH_TABLE_COM_SPDT_WLAN_IDLE
3685 * SWITCH_TABLE_COM_SPDT_WLAN_IDLE
3687 if (AR_SREV_9480_20_OR_LATER(ah)) {
3688 value = ar9003_switch_com_spdt_get(ah, is2ghz);
3689 REG_RMW_FIELD(ah, AR_PHY_GLB_CONTROL,
3690 AR_SWITCH_TABLE_COM_SPDT_ALL, value);
3693 value = ar9003_hw_ant_ctrl_common_2_get(ah, is2ghz);
3694 REG_RMW_FIELD(ah, AR_PHY_SWITCH_COM_2, AR_SWITCH_TABLE_COM2_ALL, value);
3696 for (chain = 0; chain < AR9300_MAX_CHAINS; chain++) {
3697 if ((ah->rxchainmask & BIT(chain)) ||
3698 (ah->txchainmask & BIT(chain))) {
3699 value = ar9003_hw_ant_ctrl_chain_get(ah, chain,
3701 REG_RMW_FIELD(ah, switch_chain_reg[chain],
3702 AR_SWITCH_TABLE_ALL, value);
3706 if (AR_SREV_9330(ah) || AR_SREV_9485(ah)) {
3707 value = ath9k_hw_ar9300_get_eeprom(ah, EEP_ANT_DIV_CTL1);
3709 * main_lnaconf, alt_lnaconf, main_tb, alt_tb
3710 * are the fields present
3712 regval = REG_READ(ah, AR_PHY_MC_GAIN_CTRL);
3713 regval &= (~AR_ANT_DIV_CTRL_ALL);
3714 regval |= (value & 0x3f) << AR_ANT_DIV_CTRL_ALL_S;
3716 regval &= (~AR_PHY_9485_ANT_DIV_LNADIV);
3717 regval |= ((value >> 6) & 0x1) <<
3718 AR_PHY_9485_ANT_DIV_LNADIV_S;
3719 REG_WRITE(ah, AR_PHY_MC_GAIN_CTRL, regval);
3721 /*enable fast_div */
3722 regval = REG_READ(ah, AR_PHY_CCK_DETECT);
3723 regval &= (~AR_FAST_DIV_ENABLE);
3724 regval |= ((value >> 7) & 0x1) <<
3725 AR_FAST_DIV_ENABLE_S;
3726 REG_WRITE(ah, AR_PHY_CCK_DETECT, regval);
3728 ah->eep_ops->get_eeprom(ah, EEP_ANT_DIV_CTL1);
3729 /* check whether antenna diversity is enabled */
3730 if ((ant_div_ctl1 >> 0x6) == 0x3) {
3731 regval = REG_READ(ah, AR_PHY_MC_GAIN_CTRL);
3733 * clear bits 25-30 main_lnaconf, alt_lnaconf,
3736 regval &= (~(AR_PHY_9485_ANT_DIV_MAIN_LNACONF |
3737 AR_PHY_9485_ANT_DIV_ALT_LNACONF |
3738 AR_PHY_9485_ANT_DIV_ALT_GAINTB |
3739 AR_PHY_9485_ANT_DIV_MAIN_GAINTB));
3740 /* by default use LNA1 for the main antenna */
3741 regval |= (AR_PHY_9485_ANT_DIV_LNA1 <<
3742 AR_PHY_9485_ANT_DIV_MAIN_LNACONF_S);
3743 regval |= (AR_PHY_9485_ANT_DIV_LNA2 <<
3744 AR_PHY_9485_ANT_DIV_ALT_LNACONF_S);
3745 REG_WRITE(ah, AR_PHY_MC_GAIN_CTRL, regval);
3753 static void ar9003_hw_drive_strength_apply(struct ath_hw *ah)
3758 drive_strength = ath9k_hw_ar9300_get_eeprom(ah, EEP_DRIVE_STRENGTH);
3760 if (!drive_strength)
3763 reg = REG_READ(ah, AR_PHY_65NM_CH0_BIAS1);
3771 REG_WRITE(ah, AR_PHY_65NM_CH0_BIAS1, reg);
3773 reg = REG_READ(ah, AR_PHY_65NM_CH0_BIAS2);
3784 REG_WRITE(ah, AR_PHY_65NM_CH0_BIAS2, reg);
3786 reg = REG_READ(ah, AR_PHY_65NM_CH0_BIAS4);
3791 REG_WRITE(ah, AR_PHY_65NM_CH0_BIAS4, reg);
3794 static u16 ar9003_hw_atten_chain_get(struct ath_hw *ah, int chain,
3795 struct ath9k_channel *chan)
3799 struct ar9300_eeprom *eep = &ah->eeprom.ar9300_eep;
3801 if (chain >= 0 && chain < 3) {
3802 if (IS_CHAN_2GHZ(chan))
3803 return eep->modalHeader2G.xatten1DB[chain];
3804 else if (eep->base_ext2.xatten1DBLow[chain] != 0) {
3805 t[0] = eep->base_ext2.xatten1DBLow[chain];
3807 t[1] = eep->modalHeader5G.xatten1DB[chain];
3809 t[2] = eep->base_ext2.xatten1DBHigh[chain];
3811 value = ar9003_hw_power_interpolate((s32) chan->channel,
3815 return eep->modalHeader5G.xatten1DB[chain];
3822 static u16 ar9003_hw_atten_chain_get_margin(struct ath_hw *ah, int chain,
3823 struct ath9k_channel *chan)
3827 struct ar9300_eeprom *eep = &ah->eeprom.ar9300_eep;
3829 if (chain >= 0 && chain < 3) {
3830 if (IS_CHAN_2GHZ(chan))
3831 return eep->modalHeader2G.xatten1Margin[chain];
3832 else if (eep->base_ext2.xatten1MarginLow[chain] != 0) {
3833 t[0] = eep->base_ext2.xatten1MarginLow[chain];
3835 t[1] = eep->modalHeader5G.xatten1Margin[chain];
3837 t[2] = eep->base_ext2.xatten1MarginHigh[chain];
3839 value = ar9003_hw_power_interpolate((s32) chan->channel,
3843 return eep->modalHeader5G.xatten1Margin[chain];
3849 static void ar9003_hw_atten_apply(struct ath_hw *ah, struct ath9k_channel *chan)
3853 unsigned long ext_atten_reg[3] = {AR_PHY_EXT_ATTEN_CTL_0,
3854 AR_PHY_EXT_ATTEN_CTL_1,
3855 AR_PHY_EXT_ATTEN_CTL_2,
3858 /* Test value. if 0 then attenuation is unused. Don't load anything. */
3859 for (i = 0; i < 3; i++) {
3860 if (ah->txchainmask & BIT(i)) {
3861 value = ar9003_hw_atten_chain_get(ah, i, chan);
3862 REG_RMW_FIELD(ah, ext_atten_reg[i],
3863 AR_PHY_EXT_ATTEN_CTL_XATTEN1_DB, value);
3865 value = ar9003_hw_atten_chain_get_margin(ah, i, chan);
3866 REG_RMW_FIELD(ah, ext_atten_reg[i],
3867 AR_PHY_EXT_ATTEN_CTL_XATTEN1_MARGIN,
3873 static bool is_pmu_set(struct ath_hw *ah, u32 pmu_reg, int pmu_set)
3877 while (pmu_set != REG_READ(ah, pmu_reg)) {
3880 REG_WRITE(ah, pmu_reg, pmu_set);
3887 static void ar9003_hw_internal_regulator_apply(struct ath_hw *ah)
3889 int internal_regulator =
3890 ath9k_hw_ar9300_get_eeprom(ah, EEP_INTERNAL_REGULATOR);
3893 if (internal_regulator) {
3894 if (AR_SREV_9330(ah) || AR_SREV_9485(ah)) {
3897 reg_pmu_set = REG_READ(ah, AR_PHY_PMU2) & ~AR_PHY_PMU2_PGM;
3898 REG_WRITE(ah, AR_PHY_PMU2, reg_pmu_set);
3899 if (!is_pmu_set(ah, AR_PHY_PMU2, reg_pmu_set))
3902 if (AR_SREV_9330(ah)) {
3903 if (ah->is_clk_25mhz) {
3904 reg_pmu_set = (3 << 1) | (8 << 4) |
3905 (3 << 8) | (1 << 14) |
3906 (6 << 17) | (1 << 20) |
3909 reg_pmu_set = (4 << 1) | (7 << 4) |
3910 (3 << 8) | (1 << 14) |
3911 (6 << 17) | (1 << 20) |
3915 reg_pmu_set = (5 << 1) | (7 << 4) |
3916 (1 << 8) | (2 << 14) |
3917 (6 << 17) | (1 << 20) |
3918 (3 << 24) | (1 << 28);
3921 REG_WRITE(ah, AR_PHY_PMU1, reg_pmu_set);
3922 if (!is_pmu_set(ah, AR_PHY_PMU1, reg_pmu_set))
3925 reg_pmu_set = (REG_READ(ah, AR_PHY_PMU2) & ~0xFFC00000)
3927 REG_WRITE(ah, AR_PHY_PMU2, reg_pmu_set);
3928 if (!is_pmu_set(ah, AR_PHY_PMU2, reg_pmu_set))
3931 reg_pmu_set = (REG_READ(ah, AR_PHY_PMU2) & ~0x00200000)
3933 REG_WRITE(ah, AR_PHY_PMU2, reg_pmu_set);
3934 if (!is_pmu_set(ah, AR_PHY_PMU2, reg_pmu_set))
3936 } else if (AR_SREV_9480(ah)) {
3937 reg_val = ath9k_hw_ar9300_get_eeprom(ah, EEP_SWREG);
3938 REG_WRITE(ah, AR_PHY_PMU1, reg_val);
3940 /* Internal regulator is ON. Write swreg register. */
3941 reg_val = ath9k_hw_ar9300_get_eeprom(ah, EEP_SWREG);
3942 REG_WRITE(ah, AR_RTC_REG_CONTROL1,
3943 REG_READ(ah, AR_RTC_REG_CONTROL1) &
3944 (~AR_RTC_REG_CONTROL1_SWREG_PROGRAM));
3945 REG_WRITE(ah, AR_RTC_REG_CONTROL0, reg_val);
3946 /* Set REG_CONTROL1.SWREG_PROGRAM */
3947 REG_WRITE(ah, AR_RTC_REG_CONTROL1,
3949 AR_RTC_REG_CONTROL1) |
3950 AR_RTC_REG_CONTROL1_SWREG_PROGRAM);
3953 if (AR_SREV_9330(ah) || AR_SREV_9485(ah)) {
3954 REG_RMW_FIELD(ah, AR_PHY_PMU2, AR_PHY_PMU2_PGM, 0);
3955 while (REG_READ_FIELD(ah, AR_PHY_PMU2,
3959 REG_RMW_FIELD(ah, AR_PHY_PMU1, AR_PHY_PMU1_PWD, 0x1);
3960 while (!REG_READ_FIELD(ah, AR_PHY_PMU1,
3963 REG_RMW_FIELD(ah, AR_PHY_PMU2, AR_PHY_PMU2_PGM, 0x1);
3964 while (!REG_READ_FIELD(ah, AR_PHY_PMU2,
3967 } else if (AR_SREV_9480(ah))
3968 REG_RMW_FIELD(ah, AR_PHY_PMU1, AR_PHY_PMU1_PWD, 0x1);
3970 reg_val = REG_READ(ah, AR_RTC_SLEEP_CLK) |
3971 AR_RTC_FORCE_SWREG_PRD;
3972 REG_WRITE(ah, AR_RTC_SLEEP_CLK, reg_val);
3978 static void ar9003_hw_apply_tuning_caps(struct ath_hw *ah)
3980 struct ar9300_eeprom *eep = &ah->eeprom.ar9300_eep;
3981 u8 tuning_caps_param = eep->baseEepHeader.params_for_tuning_caps[0];
3983 if (eep->baseEepHeader.featureEnable & 0x40) {
3984 tuning_caps_param &= 0x7f;
3985 REG_RMW_FIELD(ah, AR_CH0_XTAL, AR_CH0_XTAL_CAPINDAC,
3987 REG_RMW_FIELD(ah, AR_CH0_XTAL, AR_CH0_XTAL_CAPOUTDAC,
3992 static void ath9k_hw_ar9300_set_board_values(struct ath_hw *ah,
3993 struct ath9k_channel *chan)
3995 ar9003_hw_xpa_bias_level_apply(ah, IS_CHAN_2GHZ(chan));
3996 ar9003_hw_ant_ctrl_apply(ah, IS_CHAN_2GHZ(chan));
3997 ar9003_hw_drive_strength_apply(ah);
3998 ar9003_hw_atten_apply(ah, chan);
3999 if (!AR_SREV_9330(ah) && !AR_SREV_9340(ah))
4000 ar9003_hw_internal_regulator_apply(ah);
4001 if (AR_SREV_9485(ah) || AR_SREV_9330(ah) || AR_SREV_9340(ah))
4002 ar9003_hw_apply_tuning_caps(ah);
4005 static void ath9k_hw_ar9300_set_addac(struct ath_hw *ah,
4006 struct ath9k_channel *chan)
4011 * Returns the interpolated y value corresponding to the specified x value
4012 * from the np ordered pairs of data (px,py).
4013 * The pairs do not have to be in any order.
4014 * If the specified x value is less than any of the px,
4015 * the returned y value is equal to the py for the lowest px.
4016 * If the specified x value is greater than any of the px,
4017 * the returned y value is equal to the py for the highest px.
4019 static int ar9003_hw_power_interpolate(int32_t x,
4020 int32_t *px, int32_t *py, u_int16_t np)
4023 int lx = 0, ly = 0, lhave = 0;
4024 int hx = 0, hy = 0, hhave = 0;
4031 /* identify best lower and higher x calibration measurement */
4032 for (ip = 0; ip < np; ip++) {
4035 /* this measurement is higher than our desired x */
4037 if (!hhave || dx > (x - hx)) {
4038 /* new best higher x measurement */
4044 /* this measurement is lower than our desired x */
4046 if (!lhave || dx < (x - lx)) {
4047 /* new best lower x measurement */
4055 /* the low x is good */
4057 /* so is the high x */
4059 /* they're the same, so just pick one */
4062 else /* interpolate */
4063 y = interpolate(x, lx, hx, ly, hy);
4064 } else /* only low is good, use it */
4066 } else if (hhave) /* only high is good, use it */
4068 else /* nothing is good,this should never happen unless np=0, ???? */
4073 static u8 ar9003_hw_eeprom_get_tgt_pwr(struct ath_hw *ah,
4074 u16 rateIndex, u16 freq, bool is2GHz)
4077 s32 targetPowerArray[AR9300_NUM_5G_20_TARGET_POWERS];
4078 s32 freqArray[AR9300_NUM_5G_20_TARGET_POWERS];
4079 struct ar9300_eeprom *eep = &ah->eeprom.ar9300_eep;
4080 struct cal_tgt_pow_legacy *pEepromTargetPwr;
4084 numPiers = AR9300_NUM_2G_20_TARGET_POWERS;
4085 pEepromTargetPwr = eep->calTargetPower2G;
4086 pFreqBin = eep->calTarget_freqbin_2G;
4088 numPiers = AR9300_NUM_5G_20_TARGET_POWERS;
4089 pEepromTargetPwr = eep->calTargetPower5G;
4090 pFreqBin = eep->calTarget_freqbin_5G;
4094 * create array of channels and targetpower from
4095 * targetpower piers stored on eeprom
4097 for (i = 0; i < numPiers; i++) {
4098 freqArray[i] = FBIN2FREQ(pFreqBin[i], is2GHz);
4099 targetPowerArray[i] = pEepromTargetPwr[i].tPow2x[rateIndex];
4102 /* interpolate to get target power for given frequency */
4103 return (u8) ar9003_hw_power_interpolate((s32) freq,
4105 targetPowerArray, numPiers);
4108 static u8 ar9003_hw_eeprom_get_ht20_tgt_pwr(struct ath_hw *ah,
4110 u16 freq, bool is2GHz)
4113 s32 targetPowerArray[AR9300_NUM_5G_20_TARGET_POWERS];
4114 s32 freqArray[AR9300_NUM_5G_20_TARGET_POWERS];
4115 struct ar9300_eeprom *eep = &ah->eeprom.ar9300_eep;
4116 struct cal_tgt_pow_ht *pEepromTargetPwr;
4120 numPiers = AR9300_NUM_2G_20_TARGET_POWERS;
4121 pEepromTargetPwr = eep->calTargetPower2GHT20;
4122 pFreqBin = eep->calTarget_freqbin_2GHT20;
4124 numPiers = AR9300_NUM_5G_20_TARGET_POWERS;
4125 pEepromTargetPwr = eep->calTargetPower5GHT20;
4126 pFreqBin = eep->calTarget_freqbin_5GHT20;
4130 * create array of channels and targetpower
4131 * from targetpower piers stored on eeprom
4133 for (i = 0; i < numPiers; i++) {
4134 freqArray[i] = FBIN2FREQ(pFreqBin[i], is2GHz);
4135 targetPowerArray[i] = pEepromTargetPwr[i].tPow2x[rateIndex];
4138 /* interpolate to get target power for given frequency */
4139 return (u8) ar9003_hw_power_interpolate((s32) freq,
4141 targetPowerArray, numPiers);
4144 static u8 ar9003_hw_eeprom_get_ht40_tgt_pwr(struct ath_hw *ah,
4146 u16 freq, bool is2GHz)
4149 s32 targetPowerArray[AR9300_NUM_5G_40_TARGET_POWERS];
4150 s32 freqArray[AR9300_NUM_5G_40_TARGET_POWERS];
4151 struct ar9300_eeprom *eep = &ah->eeprom.ar9300_eep;
4152 struct cal_tgt_pow_ht *pEepromTargetPwr;
4156 numPiers = AR9300_NUM_2G_40_TARGET_POWERS;
4157 pEepromTargetPwr = eep->calTargetPower2GHT40;
4158 pFreqBin = eep->calTarget_freqbin_2GHT40;
4160 numPiers = AR9300_NUM_5G_40_TARGET_POWERS;
4161 pEepromTargetPwr = eep->calTargetPower5GHT40;
4162 pFreqBin = eep->calTarget_freqbin_5GHT40;
4166 * create array of channels and targetpower from
4167 * targetpower piers stored on eeprom
4169 for (i = 0; i < numPiers; i++) {
4170 freqArray[i] = FBIN2FREQ(pFreqBin[i], is2GHz);
4171 targetPowerArray[i] = pEepromTargetPwr[i].tPow2x[rateIndex];
4174 /* interpolate to get target power for given frequency */
4175 return (u8) ar9003_hw_power_interpolate((s32) freq,
4177 targetPowerArray, numPiers);
4180 static u8 ar9003_hw_eeprom_get_cck_tgt_pwr(struct ath_hw *ah,
4181 u16 rateIndex, u16 freq)
4183 u16 numPiers = AR9300_NUM_2G_CCK_TARGET_POWERS, i;
4184 s32 targetPowerArray[AR9300_NUM_2G_CCK_TARGET_POWERS];
4185 s32 freqArray[AR9300_NUM_2G_CCK_TARGET_POWERS];
4186 struct ar9300_eeprom *eep = &ah->eeprom.ar9300_eep;
4187 struct cal_tgt_pow_legacy *pEepromTargetPwr = eep->calTargetPowerCck;
4188 u8 *pFreqBin = eep->calTarget_freqbin_Cck;
4191 * create array of channels and targetpower from
4192 * targetpower piers stored on eeprom
4194 for (i = 0; i < numPiers; i++) {
4195 freqArray[i] = FBIN2FREQ(pFreqBin[i], 1);
4196 targetPowerArray[i] = pEepromTargetPwr[i].tPow2x[rateIndex];
4199 /* interpolate to get target power for given frequency */
4200 return (u8) ar9003_hw_power_interpolate((s32) freq,
4202 targetPowerArray, numPiers);
4205 /* Set tx power registers to array of values passed in */
4206 static int ar9003_hw_tx_power_regwrite(struct ath_hw *ah, u8 * pPwrArray)
4208 #define POW_SM(_r, _s) (((_r) & 0x3f) << (_s))
4209 /* make sure forced gain is not set */
4210 REG_WRITE(ah, AR_PHY_TX_FORCED_GAIN, 0);
4212 /* Write the OFDM power per rate set */
4214 /* 6 (LSB), 9, 12, 18 (MSB) */
4215 REG_WRITE(ah, AR_PHY_POWER_TX_RATE(0),
4216 POW_SM(pPwrArray[ALL_TARGET_LEGACY_6_24], 24) |
4217 POW_SM(pPwrArray[ALL_TARGET_LEGACY_6_24], 16) |
4218 POW_SM(pPwrArray[ALL_TARGET_LEGACY_6_24], 8) |
4219 POW_SM(pPwrArray[ALL_TARGET_LEGACY_6_24], 0));
4221 /* 24 (LSB), 36, 48, 54 (MSB) */
4222 REG_WRITE(ah, AR_PHY_POWER_TX_RATE(1),
4223 POW_SM(pPwrArray[ALL_TARGET_LEGACY_54], 24) |
4224 POW_SM(pPwrArray[ALL_TARGET_LEGACY_48], 16) |
4225 POW_SM(pPwrArray[ALL_TARGET_LEGACY_36], 8) |
4226 POW_SM(pPwrArray[ALL_TARGET_LEGACY_6_24], 0));
4228 /* Write the CCK power per rate set */
4230 /* 1L (LSB), reserved, 2L, 2S (MSB) */
4231 REG_WRITE(ah, AR_PHY_POWER_TX_RATE(2),
4232 POW_SM(pPwrArray[ALL_TARGET_LEGACY_1L_5L], 24) |
4233 POW_SM(pPwrArray[ALL_TARGET_LEGACY_1L_5L], 16) |
4234 /* POW_SM(txPowerTimes2, 8) | this is reserved for AR9003 */
4235 POW_SM(pPwrArray[ALL_TARGET_LEGACY_1L_5L], 0));
4237 /* 5.5L (LSB), 5.5S, 11L, 11S (MSB) */
4238 REG_WRITE(ah, AR_PHY_POWER_TX_RATE(3),
4239 POW_SM(pPwrArray[ALL_TARGET_LEGACY_11S], 24) |
4240 POW_SM(pPwrArray[ALL_TARGET_LEGACY_11L], 16) |
4241 POW_SM(pPwrArray[ALL_TARGET_LEGACY_5S], 8) |
4242 POW_SM(pPwrArray[ALL_TARGET_LEGACY_1L_5L], 0)
4245 /* Write the power for duplicated frames - HT40 */
4247 /* dup40_cck (LSB), dup40_ofdm, ext20_cck, ext20_ofdm (MSB) */
4248 REG_WRITE(ah, AR_PHY_POWER_TX_RATE(8),
4249 POW_SM(pPwrArray[ALL_TARGET_LEGACY_6_24], 24) |
4250 POW_SM(pPwrArray[ALL_TARGET_LEGACY_1L_5L], 16) |
4251 POW_SM(pPwrArray[ALL_TARGET_LEGACY_6_24], 8) |
4252 POW_SM(pPwrArray[ALL_TARGET_LEGACY_1L_5L], 0)
4255 /* Write the HT20 power per rate set */
4257 /* 0/8/16 (LSB), 1-3/9-11/17-19, 4, 5 (MSB) */
4258 REG_WRITE(ah, AR_PHY_POWER_TX_RATE(4),
4259 POW_SM(pPwrArray[ALL_TARGET_HT20_5], 24) |
4260 POW_SM(pPwrArray[ALL_TARGET_HT20_4], 16) |
4261 POW_SM(pPwrArray[ALL_TARGET_HT20_1_3_9_11_17_19], 8) |
4262 POW_SM(pPwrArray[ALL_TARGET_HT20_0_8_16], 0)
4265 /* 6 (LSB), 7, 12, 13 (MSB) */
4266 REG_WRITE(ah, AR_PHY_POWER_TX_RATE(5),
4267 POW_SM(pPwrArray[ALL_TARGET_HT20_13], 24) |
4268 POW_SM(pPwrArray[ALL_TARGET_HT20_12], 16) |
4269 POW_SM(pPwrArray[ALL_TARGET_HT20_7], 8) |
4270 POW_SM(pPwrArray[ALL_TARGET_HT20_6], 0)
4273 /* 14 (LSB), 15, 20, 21 */
4274 REG_WRITE(ah, AR_PHY_POWER_TX_RATE(9),
4275 POW_SM(pPwrArray[ALL_TARGET_HT20_21], 24) |
4276 POW_SM(pPwrArray[ALL_TARGET_HT20_20], 16) |
4277 POW_SM(pPwrArray[ALL_TARGET_HT20_15], 8) |
4278 POW_SM(pPwrArray[ALL_TARGET_HT20_14], 0)
4281 /* Mixed HT20 and HT40 rates */
4283 /* HT20 22 (LSB), HT20 23, HT40 22, HT40 23 (MSB) */
4284 REG_WRITE(ah, AR_PHY_POWER_TX_RATE(10),
4285 POW_SM(pPwrArray[ALL_TARGET_HT40_23], 24) |
4286 POW_SM(pPwrArray[ALL_TARGET_HT40_22], 16) |
4287 POW_SM(pPwrArray[ALL_TARGET_HT20_23], 8) |
4288 POW_SM(pPwrArray[ALL_TARGET_HT20_22], 0)
4292 * Write the HT40 power per rate set
4293 * correct PAR difference between HT40 and HT20/LEGACY
4294 * 0/8/16 (LSB), 1-3/9-11/17-19, 4, 5 (MSB)
4296 REG_WRITE(ah, AR_PHY_POWER_TX_RATE(6),
4297 POW_SM(pPwrArray[ALL_TARGET_HT40_5], 24) |
4298 POW_SM(pPwrArray[ALL_TARGET_HT40_4], 16) |
4299 POW_SM(pPwrArray[ALL_TARGET_HT40_1_3_9_11_17_19], 8) |
4300 POW_SM(pPwrArray[ALL_TARGET_HT40_0_8_16], 0)
4303 /* 6 (LSB), 7, 12, 13 (MSB) */
4304 REG_WRITE(ah, AR_PHY_POWER_TX_RATE(7),
4305 POW_SM(pPwrArray[ALL_TARGET_HT40_13], 24) |
4306 POW_SM(pPwrArray[ALL_TARGET_HT40_12], 16) |
4307 POW_SM(pPwrArray[ALL_TARGET_HT40_7], 8) |
4308 POW_SM(pPwrArray[ALL_TARGET_HT40_6], 0)
4311 /* 14 (LSB), 15, 20, 21 */
4312 REG_WRITE(ah, AR_PHY_POWER_TX_RATE(11),
4313 POW_SM(pPwrArray[ALL_TARGET_HT40_21], 24) |
4314 POW_SM(pPwrArray[ALL_TARGET_HT40_20], 16) |
4315 POW_SM(pPwrArray[ALL_TARGET_HT40_15], 8) |
4316 POW_SM(pPwrArray[ALL_TARGET_HT40_14], 0)
4323 static void ar9003_hw_set_target_power_eeprom(struct ath_hw *ah, u16 freq,
4324 u8 *targetPowerValT2)
4326 /* XXX: hard code for now, need to get from eeprom struct */
4327 u8 ht40PowerIncForPdadc = 0;
4328 bool is2GHz = false;
4330 struct ath_common *common = ath9k_hw_common(ah);
4335 targetPowerValT2[ALL_TARGET_LEGACY_6_24] =
4336 ar9003_hw_eeprom_get_tgt_pwr(ah, LEGACY_TARGET_RATE_6_24, freq,
4338 targetPowerValT2[ALL_TARGET_LEGACY_36] =
4339 ar9003_hw_eeprom_get_tgt_pwr(ah, LEGACY_TARGET_RATE_36, freq,
4341 targetPowerValT2[ALL_TARGET_LEGACY_48] =
4342 ar9003_hw_eeprom_get_tgt_pwr(ah, LEGACY_TARGET_RATE_48, freq,
4344 targetPowerValT2[ALL_TARGET_LEGACY_54] =
4345 ar9003_hw_eeprom_get_tgt_pwr(ah, LEGACY_TARGET_RATE_54, freq,
4347 targetPowerValT2[ALL_TARGET_LEGACY_1L_5L] =
4348 ar9003_hw_eeprom_get_cck_tgt_pwr(ah, LEGACY_TARGET_RATE_1L_5L,
4350 targetPowerValT2[ALL_TARGET_LEGACY_5S] =
4351 ar9003_hw_eeprom_get_cck_tgt_pwr(ah, LEGACY_TARGET_RATE_5S, freq);
4352 targetPowerValT2[ALL_TARGET_LEGACY_11L] =
4353 ar9003_hw_eeprom_get_cck_tgt_pwr(ah, LEGACY_TARGET_RATE_11L, freq);
4354 targetPowerValT2[ALL_TARGET_LEGACY_11S] =
4355 ar9003_hw_eeprom_get_cck_tgt_pwr(ah, LEGACY_TARGET_RATE_11S, freq);
4356 targetPowerValT2[ALL_TARGET_HT20_0_8_16] =
4357 ar9003_hw_eeprom_get_ht20_tgt_pwr(ah, HT_TARGET_RATE_0_8_16, freq,
4359 targetPowerValT2[ALL_TARGET_HT20_1_3_9_11_17_19] =
4360 ar9003_hw_eeprom_get_ht20_tgt_pwr(ah, HT_TARGET_RATE_1_3_9_11_17_19,
4362 targetPowerValT2[ALL_TARGET_HT20_4] =
4363 ar9003_hw_eeprom_get_ht20_tgt_pwr(ah, HT_TARGET_RATE_4, freq,
4365 targetPowerValT2[ALL_TARGET_HT20_5] =
4366 ar9003_hw_eeprom_get_ht20_tgt_pwr(ah, HT_TARGET_RATE_5, freq,
4368 targetPowerValT2[ALL_TARGET_HT20_6] =
4369 ar9003_hw_eeprom_get_ht20_tgt_pwr(ah, HT_TARGET_RATE_6, freq,
4371 targetPowerValT2[ALL_TARGET_HT20_7] =
4372 ar9003_hw_eeprom_get_ht20_tgt_pwr(ah, HT_TARGET_RATE_7, freq,
4374 targetPowerValT2[ALL_TARGET_HT20_12] =
4375 ar9003_hw_eeprom_get_ht20_tgt_pwr(ah, HT_TARGET_RATE_12, freq,
4377 targetPowerValT2[ALL_TARGET_HT20_13] =
4378 ar9003_hw_eeprom_get_ht20_tgt_pwr(ah, HT_TARGET_RATE_13, freq,
4380 targetPowerValT2[ALL_TARGET_HT20_14] =
4381 ar9003_hw_eeprom_get_ht20_tgt_pwr(ah, HT_TARGET_RATE_14, freq,
4383 targetPowerValT2[ALL_TARGET_HT20_15] =
4384 ar9003_hw_eeprom_get_ht20_tgt_pwr(ah, HT_TARGET_RATE_15, freq,
4386 targetPowerValT2[ALL_TARGET_HT20_20] =
4387 ar9003_hw_eeprom_get_ht20_tgt_pwr(ah, HT_TARGET_RATE_20, freq,
4389 targetPowerValT2[ALL_TARGET_HT20_21] =
4390 ar9003_hw_eeprom_get_ht20_tgt_pwr(ah, HT_TARGET_RATE_21, freq,
4392 targetPowerValT2[ALL_TARGET_HT20_22] =
4393 ar9003_hw_eeprom_get_ht20_tgt_pwr(ah, HT_TARGET_RATE_22, freq,
4395 targetPowerValT2[ALL_TARGET_HT20_23] =
4396 ar9003_hw_eeprom_get_ht20_tgt_pwr(ah, HT_TARGET_RATE_23, freq,
4398 targetPowerValT2[ALL_TARGET_HT40_0_8_16] =
4399 ar9003_hw_eeprom_get_ht40_tgt_pwr(ah, HT_TARGET_RATE_0_8_16, freq,
4400 is2GHz) + ht40PowerIncForPdadc;
4401 targetPowerValT2[ALL_TARGET_HT40_1_3_9_11_17_19] =
4402 ar9003_hw_eeprom_get_ht40_tgt_pwr(ah, HT_TARGET_RATE_1_3_9_11_17_19,
4404 is2GHz) + ht40PowerIncForPdadc;
4405 targetPowerValT2[ALL_TARGET_HT40_4] =
4406 ar9003_hw_eeprom_get_ht40_tgt_pwr(ah, HT_TARGET_RATE_4, freq,
4407 is2GHz) + ht40PowerIncForPdadc;
4408 targetPowerValT2[ALL_TARGET_HT40_5] =
4409 ar9003_hw_eeprom_get_ht40_tgt_pwr(ah, HT_TARGET_RATE_5, freq,
4410 is2GHz) + ht40PowerIncForPdadc;
4411 targetPowerValT2[ALL_TARGET_HT40_6] =
4412 ar9003_hw_eeprom_get_ht40_tgt_pwr(ah, HT_TARGET_RATE_6, freq,
4413 is2GHz) + ht40PowerIncForPdadc;
4414 targetPowerValT2[ALL_TARGET_HT40_7] =
4415 ar9003_hw_eeprom_get_ht40_tgt_pwr(ah, HT_TARGET_RATE_7, freq,
4416 is2GHz) + ht40PowerIncForPdadc;
4417 targetPowerValT2[ALL_TARGET_HT40_12] =
4418 ar9003_hw_eeprom_get_ht40_tgt_pwr(ah, HT_TARGET_RATE_12, freq,
4419 is2GHz) + ht40PowerIncForPdadc;
4420 targetPowerValT2[ALL_TARGET_HT40_13] =
4421 ar9003_hw_eeprom_get_ht40_tgt_pwr(ah, HT_TARGET_RATE_13, freq,
4422 is2GHz) + ht40PowerIncForPdadc;
4423 targetPowerValT2[ALL_TARGET_HT40_14] =
4424 ar9003_hw_eeprom_get_ht40_tgt_pwr(ah, HT_TARGET_RATE_14, freq,
4425 is2GHz) + ht40PowerIncForPdadc;
4426 targetPowerValT2[ALL_TARGET_HT40_15] =
4427 ar9003_hw_eeprom_get_ht40_tgt_pwr(ah, HT_TARGET_RATE_15, freq,
4428 is2GHz) + ht40PowerIncForPdadc;
4429 targetPowerValT2[ALL_TARGET_HT40_20] =
4430 ar9003_hw_eeprom_get_ht40_tgt_pwr(ah, HT_TARGET_RATE_20, freq,
4431 is2GHz) + ht40PowerIncForPdadc;
4432 targetPowerValT2[ALL_TARGET_HT40_21] =
4433 ar9003_hw_eeprom_get_ht40_tgt_pwr(ah, HT_TARGET_RATE_21, freq,
4434 is2GHz) + ht40PowerIncForPdadc;
4435 targetPowerValT2[ALL_TARGET_HT40_22] =
4436 ar9003_hw_eeprom_get_ht40_tgt_pwr(ah, HT_TARGET_RATE_22, freq,
4437 is2GHz) + ht40PowerIncForPdadc;
4438 targetPowerValT2[ALL_TARGET_HT40_23] =
4439 ar9003_hw_eeprom_get_ht40_tgt_pwr(ah, HT_TARGET_RATE_23, freq,
4440 is2GHz) + ht40PowerIncForPdadc;
4442 for (i = 0; i < ar9300RateSize; i++) {
4443 ath_dbg(common, ATH_DBG_EEPROM,
4444 "TPC[%02d] 0x%08x\n", i, targetPowerValT2[i]);
4448 static int ar9003_hw_cal_pier_get(struct ath_hw *ah,
4454 int *ptemperature, int *pvoltage)
4457 struct ar9300_cal_data_per_freq_op_loop *pCalPierStruct;
4459 struct ar9300_eeprom *eep = &ah->eeprom.ar9300_eep;
4460 struct ath_common *common = ath9k_hw_common(ah);
4462 if (ichain >= AR9300_MAX_CHAINS) {
4463 ath_dbg(common, ATH_DBG_EEPROM,
4464 "Invalid chain index, must be less than %d\n",
4469 if (mode) { /* 5GHz */
4470 if (ipier >= AR9300_NUM_5G_CAL_PIERS) {
4471 ath_dbg(common, ATH_DBG_EEPROM,
4472 "Invalid 5GHz cal pier index, must be less than %d\n",
4473 AR9300_NUM_5G_CAL_PIERS);
4476 pCalPier = &(eep->calFreqPier5G[ipier]);
4477 pCalPierStruct = &(eep->calPierData5G[ichain][ipier]);
4480 if (ipier >= AR9300_NUM_2G_CAL_PIERS) {
4481 ath_dbg(common, ATH_DBG_EEPROM,
4482 "Invalid 2GHz cal pier index, must be less than %d\n",
4483 AR9300_NUM_2G_CAL_PIERS);
4487 pCalPier = &(eep->calFreqPier2G[ipier]);
4488 pCalPierStruct = &(eep->calPierData2G[ichain][ipier]);
4492 *pfrequency = FBIN2FREQ(*pCalPier, is2GHz);
4493 *pcorrection = pCalPierStruct->refPower;
4494 *ptemperature = pCalPierStruct->tempMeas;
4495 *pvoltage = pCalPierStruct->voltMeas;
4500 static int ar9003_hw_power_control_override(struct ath_hw *ah,
4503 int *voltage, int *temperature)
4506 struct ar9300_eeprom *eep = &ah->eeprom.ar9300_eep;
4509 REG_RMW(ah, AR_PHY_TPC_11_B0,
4510 (correction[0] << AR_PHY_TPC_OLPC_GAIN_DELTA_S),
4511 AR_PHY_TPC_OLPC_GAIN_DELTA);
4512 if (ah->caps.tx_chainmask & BIT(1))
4513 REG_RMW(ah, AR_PHY_TPC_11_B1,
4514 (correction[1] << AR_PHY_TPC_OLPC_GAIN_DELTA_S),
4515 AR_PHY_TPC_OLPC_GAIN_DELTA);
4516 if (ah->caps.tx_chainmask & BIT(2))
4517 REG_RMW(ah, AR_PHY_TPC_11_B2,
4518 (correction[2] << AR_PHY_TPC_OLPC_GAIN_DELTA_S),
4519 AR_PHY_TPC_OLPC_GAIN_DELTA);
4521 /* enable open loop power control on chip */
4522 REG_RMW(ah, AR_PHY_TPC_6_B0,
4523 (3 << AR_PHY_TPC_6_ERROR_EST_MODE_S),
4524 AR_PHY_TPC_6_ERROR_EST_MODE);
4525 if (ah->caps.tx_chainmask & BIT(1))
4526 REG_RMW(ah, AR_PHY_TPC_6_B1,
4527 (3 << AR_PHY_TPC_6_ERROR_EST_MODE_S),
4528 AR_PHY_TPC_6_ERROR_EST_MODE);
4529 if (ah->caps.tx_chainmask & BIT(2))
4530 REG_RMW(ah, AR_PHY_TPC_6_B2,
4531 (3 << AR_PHY_TPC_6_ERROR_EST_MODE_S),
4532 AR_PHY_TPC_6_ERROR_EST_MODE);
4535 * enable temperature compensation
4536 * Need to use register names
4538 if (frequency < 4000)
4539 tempSlope = eep->modalHeader2G.tempSlope;
4540 else if (eep->base_ext2.tempSlopeLow != 0) {
4541 t[0] = eep->base_ext2.tempSlopeLow;
4543 t[1] = eep->modalHeader5G.tempSlope;
4545 t[2] = eep->base_ext2.tempSlopeHigh;
4547 tempSlope = ar9003_hw_power_interpolate((s32) frequency,
4550 tempSlope = eep->modalHeader5G.tempSlope;
4552 REG_RMW_FIELD(ah, AR_PHY_TPC_19, AR_PHY_TPC_19_ALPHA_THERM, tempSlope);
4554 if (AR_SREV_9480_20(ah))
4555 REG_RMW_FIELD(ah, AR_PHY_TPC_19_B1,
4556 AR_PHY_TPC_19_B1_ALPHA_THERM, tempSlope);
4559 REG_RMW_FIELD(ah, AR_PHY_TPC_18, AR_PHY_TPC_18_THERM_CAL_VALUE,
4565 /* Apply the recorded correction values. */
4566 static int ar9003_hw_calibration_apply(struct ath_hw *ah, int frequency)
4568 int ichain, ipier, npier;
4570 int lfrequency[AR9300_MAX_CHAINS],
4571 lcorrection[AR9300_MAX_CHAINS],
4572 ltemperature[AR9300_MAX_CHAINS], lvoltage[AR9300_MAX_CHAINS];
4573 int hfrequency[AR9300_MAX_CHAINS],
4574 hcorrection[AR9300_MAX_CHAINS],
4575 htemperature[AR9300_MAX_CHAINS], hvoltage[AR9300_MAX_CHAINS];
4577 int correction[AR9300_MAX_CHAINS],
4578 voltage[AR9300_MAX_CHAINS], temperature[AR9300_MAX_CHAINS];
4579 int pfrequency, pcorrection, ptemperature, pvoltage;
4580 struct ath_common *common = ath9k_hw_common(ah);
4582 mode = (frequency >= 4000);
4584 npier = AR9300_NUM_5G_CAL_PIERS;
4586 npier = AR9300_NUM_2G_CAL_PIERS;
4588 for (ichain = 0; ichain < AR9300_MAX_CHAINS; ichain++) {
4589 lfrequency[ichain] = 0;
4590 hfrequency[ichain] = 100000;
4592 /* identify best lower and higher frequency calibration measurement */
4593 for (ichain = 0; ichain < AR9300_MAX_CHAINS; ichain++) {
4594 for (ipier = 0; ipier < npier; ipier++) {
4595 if (!ar9003_hw_cal_pier_get(ah, mode, ipier, ichain,
4596 &pfrequency, &pcorrection,
4597 &ptemperature, &pvoltage)) {
4598 fdiff = frequency - pfrequency;
4601 * this measurement is higher than
4602 * our desired frequency
4605 if (hfrequency[ichain] <= 0 ||
4606 hfrequency[ichain] >= 100000 ||
4608 (frequency - hfrequency[ichain])) {
4611 * frequency measurement
4613 hfrequency[ichain] = pfrequency;
4614 hcorrection[ichain] =
4616 htemperature[ichain] =
4618 hvoltage[ichain] = pvoltage;
4622 if (lfrequency[ichain] <= 0
4624 (frequency - lfrequency[ichain])) {
4627 * frequency measurement
4629 lfrequency[ichain] = pfrequency;
4630 lcorrection[ichain] =
4632 ltemperature[ichain] =
4634 lvoltage[ichain] = pvoltage;
4642 for (ichain = 0; ichain < AR9300_MAX_CHAINS; ichain++) {
4643 ath_dbg(common, ATH_DBG_EEPROM,
4644 "ch=%d f=%d low=%d %d h=%d %d\n",
4645 ichain, frequency, lfrequency[ichain],
4646 lcorrection[ichain], hfrequency[ichain],
4647 hcorrection[ichain]);
4648 /* they're the same, so just pick one */
4649 if (hfrequency[ichain] == lfrequency[ichain]) {
4650 correction[ichain] = lcorrection[ichain];
4651 voltage[ichain] = lvoltage[ichain];
4652 temperature[ichain] = ltemperature[ichain];
4654 /* the low frequency is good */
4655 else if (frequency - lfrequency[ichain] < 1000) {
4656 /* so is the high frequency, interpolate */
4657 if (hfrequency[ichain] - frequency < 1000) {
4659 correction[ichain] = interpolate(frequency,
4662 lcorrection[ichain],
4663 hcorrection[ichain]);
4665 temperature[ichain] = interpolate(frequency,
4668 ltemperature[ichain],
4669 htemperature[ichain]);
4671 voltage[ichain] = interpolate(frequency,
4677 /* only low is good, use it */
4679 correction[ichain] = lcorrection[ichain];
4680 temperature[ichain] = ltemperature[ichain];
4681 voltage[ichain] = lvoltage[ichain];
4684 /* only high is good, use it */
4685 else if (hfrequency[ichain] - frequency < 1000) {
4686 correction[ichain] = hcorrection[ichain];
4687 temperature[ichain] = htemperature[ichain];
4688 voltage[ichain] = hvoltage[ichain];
4689 } else { /* nothing is good, presume 0???? */
4690 correction[ichain] = 0;
4691 temperature[ichain] = 0;
4692 voltage[ichain] = 0;
4696 ar9003_hw_power_control_override(ah, frequency, correction, voltage,
4699 ath_dbg(common, ATH_DBG_EEPROM,
4700 "for frequency=%d, calibration correction = %d %d %d\n",
4701 frequency, correction[0], correction[1], correction[2]);
4706 static u16 ar9003_hw_get_direct_edge_power(struct ar9300_eeprom *eep,
4711 struct cal_ctl_data_2g *ctl_2g = eep->ctlPowerData_2G;
4712 struct cal_ctl_data_5g *ctl_5g = eep->ctlPowerData_5G;
4715 return CTL_EDGE_TPOWER(ctl_2g[idx].ctlEdges[edge]);
4717 return CTL_EDGE_TPOWER(ctl_5g[idx].ctlEdges[edge]);
4720 static u16 ar9003_hw_get_indirect_edge_power(struct ar9300_eeprom *eep,
4726 struct cal_ctl_data_2g *ctl_2g = eep->ctlPowerData_2G;
4727 struct cal_ctl_data_5g *ctl_5g = eep->ctlPowerData_5G;
4729 u8 *ctl_freqbin = is2GHz ?
4730 &eep->ctl_freqbin_2G[idx][0] :
4731 &eep->ctl_freqbin_5G[idx][0];
4734 if (ath9k_hw_fbin2freq(ctl_freqbin[edge - 1], 1) < freq &&
4735 CTL_EDGE_FLAGS(ctl_2g[idx].ctlEdges[edge - 1]))
4736 return CTL_EDGE_TPOWER(ctl_2g[idx].ctlEdges[edge - 1]);
4738 if (ath9k_hw_fbin2freq(ctl_freqbin[edge - 1], 0) < freq &&
4739 CTL_EDGE_FLAGS(ctl_5g[idx].ctlEdges[edge - 1]))
4740 return CTL_EDGE_TPOWER(ctl_5g[idx].ctlEdges[edge - 1]);
4743 return MAX_RATE_POWER;
4747 * Find the maximum conformance test limit for the given channel and CTL info
4749 static u16 ar9003_hw_get_max_edge_power(struct ar9300_eeprom *eep,
4750 u16 freq, int idx, bool is2GHz)
4752 u16 twiceMaxEdgePower = MAX_RATE_POWER;
4753 u8 *ctl_freqbin = is2GHz ?
4754 &eep->ctl_freqbin_2G[idx][0] :
4755 &eep->ctl_freqbin_5G[idx][0];
4756 u16 num_edges = is2GHz ?
4757 AR9300_NUM_BAND_EDGES_2G : AR9300_NUM_BAND_EDGES_5G;
4760 /* Get the edge power */
4762 (edge < num_edges) && (ctl_freqbin[edge] != AR5416_BCHAN_UNUSED);
4765 * If there's an exact channel match or an inband flag set
4766 * on the lower channel use the given rdEdgePower
4768 if (freq == ath9k_hw_fbin2freq(ctl_freqbin[edge], is2GHz)) {
4770 ar9003_hw_get_direct_edge_power(eep, idx,
4773 } else if ((edge > 0) &&
4774 (freq < ath9k_hw_fbin2freq(ctl_freqbin[edge],
4777 ar9003_hw_get_indirect_edge_power(eep, idx,
4781 * Leave loop - no more affecting edges possible in
4782 * this monotonic increasing list
4787 return twiceMaxEdgePower;
4790 static void ar9003_hw_set_power_per_rate_table(struct ath_hw *ah,
4791 struct ath9k_channel *chan,
4792 u8 *pPwrArray, u16 cfgCtl,
4793 u8 twiceAntennaReduction,
4794 u8 twiceMaxRegulatoryPower,
4797 struct ath_regulatory *regulatory = ath9k_hw_regulatory(ah);
4798 struct ath_common *common = ath9k_hw_common(ah);
4799 struct ar9300_eeprom *pEepData = &ah->eeprom.ar9300_eep;
4800 u16 twiceMaxEdgePower = MAX_RATE_POWER;
4801 static const u16 tpScaleReductionTable[5] = {
4802 0, 3, 6, 9, MAX_RATE_POWER
4805 int16_t twiceLargestAntenna;
4806 u16 scaledPower = 0, minCtlPower, maxRegAllowedPower;
4807 static const u16 ctlModesFor11a[] = {
4808 CTL_11A, CTL_5GHT20, CTL_11A_EXT, CTL_5GHT40
4810 static const u16 ctlModesFor11g[] = {
4811 CTL_11B, CTL_11G, CTL_2GHT20, CTL_11B_EXT,
4812 CTL_11G_EXT, CTL_2GHT40
4815 const u16 *pCtlMode;
4817 struct chan_centers centers;
4820 u16 twiceMinEdgePower;
4821 bool is2ghz = IS_CHAN_2GHZ(chan);
4823 ath9k_hw_get_channel_centers(ah, chan, ¢ers);
4825 /* Compute TxPower reduction due to Antenna Gain */
4827 twiceLargestAntenna = pEepData->modalHeader2G.antennaGain;
4829 twiceLargestAntenna = pEepData->modalHeader5G.antennaGain;
4831 twiceLargestAntenna = (int16_t)min((twiceAntennaReduction) -
4832 twiceLargestAntenna, 0);
4835 * scaledPower is the minimum of the user input power level
4836 * and the regulatory allowed power level
4838 maxRegAllowedPower = twiceMaxRegulatoryPower + twiceLargestAntenna;
4840 if (regulatory->tp_scale != ATH9K_TP_SCALE_MAX) {
4841 maxRegAllowedPower -=
4842 (tpScaleReductionTable[(regulatory->tp_scale)] * 2);
4845 scaledPower = min(powerLimit, maxRegAllowedPower);
4848 * Reduce scaled Power by number of chains active to get
4849 * to per chain tx power level
4851 switch (ar5416_get_ntxchains(ah->txchainmask)) {
4855 if (scaledPower > REDUCE_SCALED_POWER_BY_TWO_CHAIN)
4856 scaledPower -= REDUCE_SCALED_POWER_BY_TWO_CHAIN;
4861 if (scaledPower > REDUCE_SCALED_POWER_BY_THREE_CHAIN)
4862 scaledPower -= REDUCE_SCALED_POWER_BY_THREE_CHAIN;
4868 scaledPower = max((u16)0, scaledPower);
4871 * Get target powers from EEPROM - our baseline for TX Power
4874 /* Setup for CTL modes */
4875 /* CTL_11B, CTL_11G, CTL_2GHT20 */
4877 ARRAY_SIZE(ctlModesFor11g) -
4878 SUB_NUM_CTL_MODES_AT_2G_40;
4879 pCtlMode = ctlModesFor11g;
4880 if (IS_CHAN_HT40(chan))
4882 numCtlModes = ARRAY_SIZE(ctlModesFor11g);
4884 /* Setup for CTL modes */
4885 /* CTL_11A, CTL_5GHT20 */
4886 numCtlModes = ARRAY_SIZE(ctlModesFor11a) -
4887 SUB_NUM_CTL_MODES_AT_5G_40;
4888 pCtlMode = ctlModesFor11a;
4889 if (IS_CHAN_HT40(chan))
4891 numCtlModes = ARRAY_SIZE(ctlModesFor11a);
4895 * For MIMO, need to apply regulatory caps individually across
4896 * dynamically running modes: CCK, OFDM, HT20, HT40
4898 * The outer loop walks through each possible applicable runtime mode.
4899 * The inner loop walks through each ctlIndex entry in EEPROM.
4900 * The ctl value is encoded as [7:4] == test group, [3:0] == test mode.
4902 for (ctlMode = 0; ctlMode < numCtlModes; ctlMode++) {
4903 bool isHt40CtlMode = (pCtlMode[ctlMode] == CTL_5GHT40) ||
4904 (pCtlMode[ctlMode] == CTL_2GHT40);
4906 freq = centers.synth_center;
4907 else if (pCtlMode[ctlMode] & EXT_ADDITIVE)
4908 freq = centers.ext_center;
4910 freq = centers.ctl_center;
4912 ath_dbg(common, ATH_DBG_REGULATORY,
4913 "LOOP-Mode ctlMode %d < %d, isHt40CtlMode %d, EXT_ADDITIVE %d\n",
4914 ctlMode, numCtlModes, isHt40CtlMode,
4915 (pCtlMode[ctlMode] & EXT_ADDITIVE));
4917 /* walk through each CTL index stored in EEPROM */
4919 ctlIndex = pEepData->ctlIndex_2G;
4920 ctlNum = AR9300_NUM_CTLS_2G;
4922 ctlIndex = pEepData->ctlIndex_5G;
4923 ctlNum = AR9300_NUM_CTLS_5G;
4926 for (i = 0; (i < ctlNum) && ctlIndex[i]; i++) {
4927 ath_dbg(common, ATH_DBG_REGULATORY,
4928 "LOOP-Ctlidx %d: cfgCtl 0x%2.2x pCtlMode 0x%2.2x ctlIndex 0x%2.2x chan %d\n",
4929 i, cfgCtl, pCtlMode[ctlMode], ctlIndex[i],
4933 * compare test group from regulatory
4934 * channel list with test mode from pCtlMode
4937 if ((((cfgCtl & ~CTL_MODE_M) |
4938 (pCtlMode[ctlMode] & CTL_MODE_M)) ==
4940 (((cfgCtl & ~CTL_MODE_M) |
4941 (pCtlMode[ctlMode] & CTL_MODE_M)) ==
4942 ((ctlIndex[i] & CTL_MODE_M) |
4945 ar9003_hw_get_max_edge_power(pEepData,
4949 if ((cfgCtl & ~CTL_MODE_M) == SD_NO_CTL)
4951 * Find the minimum of all CTL
4952 * edge powers that apply to
4956 min(twiceMaxEdgePower,
4967 minCtlPower = (u8)min(twiceMaxEdgePower, scaledPower);
4969 ath_dbg(common, ATH_DBG_REGULATORY,
4970 "SEL-Min ctlMode %d pCtlMode %d 2xMaxEdge %d sP %d minCtlPwr %d\n",
4971 ctlMode, pCtlMode[ctlMode], twiceMaxEdgePower,
4972 scaledPower, minCtlPower);
4974 /* Apply ctl mode to correct target power set */
4975 switch (pCtlMode[ctlMode]) {
4977 for (i = ALL_TARGET_LEGACY_1L_5L;
4978 i <= ALL_TARGET_LEGACY_11S; i++)
4980 (u8)min((u16)pPwrArray[i],
4985 for (i = ALL_TARGET_LEGACY_6_24;
4986 i <= ALL_TARGET_LEGACY_54; i++)
4988 (u8)min((u16)pPwrArray[i],
4993 for (i = ALL_TARGET_HT20_0_8_16;
4994 i <= ALL_TARGET_HT20_21; i++)
4996 (u8)min((u16)pPwrArray[i],
4998 pPwrArray[ALL_TARGET_HT20_22] =
4999 (u8)min((u16)pPwrArray[ALL_TARGET_HT20_22],
5001 pPwrArray[ALL_TARGET_HT20_23] =
5002 (u8)min((u16)pPwrArray[ALL_TARGET_HT20_23],
5007 for (i = ALL_TARGET_HT40_0_8_16;
5008 i <= ALL_TARGET_HT40_23; i++)
5010 (u8)min((u16)pPwrArray[i],
5016 } /* end ctl mode checking */
5019 static inline u8 mcsidx_to_tgtpwridx(unsigned int mcs_idx, u8 base_pwridx)
5021 u8 mod_idx = mcs_idx % 8;
5024 return mod_idx ? (base_pwridx + 1) : base_pwridx;
5026 return base_pwridx + 4 * (mcs_idx / 8) + mod_idx - 2;
5029 static void ath9k_hw_ar9300_set_txpower(struct ath_hw *ah,
5030 struct ath9k_channel *chan, u16 cfgCtl,
5031 u8 twiceAntennaReduction,
5032 u8 twiceMaxRegulatoryPower,
5033 u8 powerLimit, bool test)
5035 struct ath_regulatory *regulatory = ath9k_hw_regulatory(ah);
5036 struct ath_common *common = ath9k_hw_common(ah);
5037 struct ar9300_eeprom *eep = &ah->eeprom.ar9300_eep;
5038 struct ar9300_modal_eep_header *modal_hdr;
5039 u8 targetPowerValT2[ar9300RateSize];
5040 u8 target_power_val_t2_eep[ar9300RateSize];
5041 unsigned int i = 0, paprd_scale_factor = 0;
5042 u8 pwr_idx, min_pwridx = 0;
5044 ar9003_hw_set_target_power_eeprom(ah, chan->channel, targetPowerValT2);
5046 if (ah->eep_ops->get_eeprom(ah, EEP_PAPRD)) {
5047 if (IS_CHAN_2GHZ(chan))
5048 modal_hdr = &eep->modalHeader2G;
5050 modal_hdr = &eep->modalHeader5G;
5052 ah->paprd_ratemask =
5053 le32_to_cpu(modal_hdr->papdRateMaskHt20) &
5054 AR9300_PAPRD_RATE_MASK;
5056 ah->paprd_ratemask_ht40 =
5057 le32_to_cpu(modal_hdr->papdRateMaskHt40) &
5058 AR9300_PAPRD_RATE_MASK;
5060 paprd_scale_factor = ar9003_get_paprd_scale_factor(ah, chan);
5061 min_pwridx = IS_CHAN_HT40(chan) ? ALL_TARGET_HT40_0_8_16 :
5062 ALL_TARGET_HT20_0_8_16;
5064 if (!ah->paprd_table_write_done) {
5065 memcpy(target_power_val_t2_eep, targetPowerValT2,
5066 sizeof(targetPowerValT2));
5067 for (i = 0; i < 24; i++) {
5068 pwr_idx = mcsidx_to_tgtpwridx(i, min_pwridx);
5069 if (ah->paprd_ratemask & (1 << i)) {
5070 if (targetPowerValT2[pwr_idx] &&
5071 targetPowerValT2[pwr_idx] ==
5072 target_power_val_t2_eep[pwr_idx])
5073 targetPowerValT2[pwr_idx] -=
5078 memcpy(target_power_val_t2_eep, targetPowerValT2,
5079 sizeof(targetPowerValT2));
5082 ar9003_hw_set_power_per_rate_table(ah, chan,
5083 targetPowerValT2, cfgCtl,
5084 twiceAntennaReduction,
5085 twiceMaxRegulatoryPower,
5088 if (ah->eep_ops->get_eeprom(ah, EEP_PAPRD)) {
5089 for (i = 0; i < ar9300RateSize; i++) {
5090 if ((ah->paprd_ratemask & (1 << i)) &&
5091 (abs(targetPowerValT2[i] -
5092 target_power_val_t2_eep[i]) >
5093 paprd_scale_factor)) {
5094 ah->paprd_ratemask &= ~(1 << i);
5095 ath_dbg(common, ATH_DBG_EEPROM,
5096 "paprd disabled for mcs %d\n", i);
5101 regulatory->max_power_level = 0;
5102 for (i = 0; i < ar9300RateSize; i++) {
5103 if (targetPowerValT2[i] > regulatory->max_power_level)
5104 regulatory->max_power_level = targetPowerValT2[i];
5110 for (i = 0; i < ar9300RateSize; i++) {
5111 ath_dbg(common, ATH_DBG_EEPROM,
5112 "TPC[%02d] 0x%08x\n", i, targetPowerValT2[i]);
5115 ah->txpower_limit = regulatory->max_power_level;
5117 /* Write target power array to registers */
5118 ar9003_hw_tx_power_regwrite(ah, targetPowerValT2);
5119 ar9003_hw_calibration_apply(ah, chan->channel);
5121 if (IS_CHAN_2GHZ(chan)) {
5122 if (IS_CHAN_HT40(chan))
5123 i = ALL_TARGET_HT40_0_8_16;
5125 i = ALL_TARGET_HT20_0_8_16;
5127 if (IS_CHAN_HT40(chan))
5128 i = ALL_TARGET_HT40_7;
5130 i = ALL_TARGET_HT20_7;
5132 ah->paprd_target_power = targetPowerValT2[i];
5135 static u16 ath9k_hw_ar9300_get_spur_channel(struct ath_hw *ah,
5141 s32 ar9003_hw_get_tx_gain_idx(struct ath_hw *ah)
5143 struct ar9300_eeprom *eep = &ah->eeprom.ar9300_eep;
5145 return (eep->baseEepHeader.txrxgain >> 4) & 0xf; /* bits 7:4 */
5148 s32 ar9003_hw_get_rx_gain_idx(struct ath_hw *ah)
5150 struct ar9300_eeprom *eep = &ah->eeprom.ar9300_eep;
5152 return (eep->baseEepHeader.txrxgain) & 0xf; /* bits 3:0 */
5155 u8 *ar9003_get_spur_chan_ptr(struct ath_hw *ah, bool is_2ghz)
5157 struct ar9300_eeprom *eep = &ah->eeprom.ar9300_eep;
5160 return eep->modalHeader2G.spurChans;
5162 return eep->modalHeader5G.spurChans;
5165 unsigned int ar9003_get_paprd_scale_factor(struct ath_hw *ah,
5166 struct ath9k_channel *chan)
5168 struct ar9300_eeprom *eep = &ah->eeprom.ar9300_eep;
5170 if (IS_CHAN_2GHZ(chan))
5171 return MS(le32_to_cpu(eep->modalHeader2G.papdRateMaskHt20),
5172 AR9300_PAPRD_SCALE_1);
5174 if (chan->channel >= 5700)
5175 return MS(le32_to_cpu(eep->modalHeader5G.papdRateMaskHt20),
5176 AR9300_PAPRD_SCALE_1);
5177 else if (chan->channel >= 5400)
5178 return MS(le32_to_cpu(eep->modalHeader5G.papdRateMaskHt40),
5179 AR9300_PAPRD_SCALE_2);
5181 return MS(le32_to_cpu(eep->modalHeader5G.papdRateMaskHt40),
5182 AR9300_PAPRD_SCALE_1);
5186 const struct eeprom_ops eep_ar9300_ops = {
5187 .check_eeprom = ath9k_hw_ar9300_check_eeprom,
5188 .get_eeprom = ath9k_hw_ar9300_get_eeprom,
5189 .fill_eeprom = ath9k_hw_ar9300_fill_eeprom,
5190 .dump_eeprom = ath9k_hw_ar9003_dump_eeprom,
5191 .get_eeprom_ver = ath9k_hw_ar9300_get_eeprom_ver,
5192 .get_eeprom_rev = ath9k_hw_ar9300_get_eeprom_rev,
5193 .set_board_values = ath9k_hw_ar9300_set_board_values,
5194 .set_addac = ath9k_hw_ar9300_set_addac,
5195 .set_txpower = ath9k_hw_ar9300_set_txpower,
5196 .get_spur_channel = ath9k_hw_ar9300_get_spur_channel