2 * Copyright (c) 2010 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.
18 #include "ar9003_phy.h"
19 #include "ar9003_eeprom.h"
21 #define COMP_HDR_LEN 4
22 #define COMP_CKSUM_LEN 2
24 #define AR_CH0_TOP (0x00016288)
25 #define AR_CH0_TOP_XPABIASLVL (0x300)
26 #define AR_CH0_TOP_XPABIASLVL_S (8)
28 #define AR_CH0_THERM (0x00016290)
29 #define AR_CH0_THERM_XPABIASLVL_MSB 0x3
30 #define AR_CH0_THERM_XPABIASLVL_MSB_S 0
31 #define AR_CH0_THERM_XPASHORT2GND 0x4
32 #define AR_CH0_THERM_XPASHORT2GND_S 2
34 #define AR_SWITCH_TABLE_COM_ALL (0xffff)
35 #define AR_SWITCH_TABLE_COM_ALL_S (0)
37 #define AR_SWITCH_TABLE_COM2_ALL (0xffffff)
38 #define AR_SWITCH_TABLE_COM2_ALL_S (0)
40 #define AR_SWITCH_TABLE_ALL (0xfff)
41 #define AR_SWITCH_TABLE_ALL_S (0)
43 #define LE16(x) __constant_cpu_to_le16(x)
44 #define LE32(x) __constant_cpu_to_le32(x)
46 /* Local defines to distinguish between extension and control CTL's */
47 #define EXT_ADDITIVE (0x8000)
48 #define CTL_11A_EXT (CTL_11A | EXT_ADDITIVE)
49 #define CTL_11G_EXT (CTL_11G | EXT_ADDITIVE)
50 #define CTL_11B_EXT (CTL_11B | EXT_ADDITIVE)
51 #define REDUCE_SCALED_POWER_BY_TWO_CHAIN 6 /* 10*log10(2)*2 */
52 #define REDUCE_SCALED_POWER_BY_THREE_CHAIN 9 /* 10*log10(3)*2 */
53 #define PWRINCR_3_TO_1_CHAIN 9 /* 10*log(3)*2 */
54 #define PWRINCR_3_TO_2_CHAIN 3 /* floor(10*log(3/2)*2) */
55 #define PWRINCR_2_TO_1_CHAIN 6 /* 10*log(2)*2 */
57 #define SUB_NUM_CTL_MODES_AT_5G_40 2 /* excluding HT40, EXT-OFDM */
58 #define SUB_NUM_CTL_MODES_AT_2G_40 3 /* excluding HT40, EXT-OFDM, EXT-CCK */
60 #define CTL(_tpower, _flag) ((_tpower) | ((_flag) << 6))
62 static int ar9003_hw_power_interpolate(int32_t x,
63 int32_t *px, int32_t *py, u_int16_t np);
65 static const struct ar9300_eeprom ar9300_default = {
68 .macAddr = {1, 2, 3, 4, 5, 6},
69 .custData = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
70 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
72 .regDmn = { LE16(0), LE16(0x1f) },
73 .txrxMask = 0x77, /* 4 bits tx and 4 bits rx */
75 .opFlags = AR5416_OPFLAGS_11G | AR5416_OPFLAGS_11A,
79 .blueToothOptions = 0,
81 .deviceType = 5, /* takes lower byte in eeprom location */
82 .pwrTableOffset = AR9300_PWR_TABLE_OFFSET,
83 .params_for_tuning_caps = {0, 0},
84 .featureEnable = 0x0c,
86 * bit0 - enable tx temp comp - disabled
87 * bit1 - enable tx volt comp - disabled
88 * bit2 - enable fastClock - enabled
89 * bit3 - enable doubling - enabled
90 * bit4 - enable internal regulator - disabled
91 * bit5 - enable pa predistortion - disabled
93 .miscConfiguration = 0, /* bit0 - turn down drivestrength */
94 .eepromWriteEnableGpio = 3,
97 .rxBandSelectGpio = 0xff,
102 /* ar9300_modal_eep_header 2g */
103 /* 4 idle,t1,t2,b(4 bits per setting) */
104 .antCtrlCommon = LE32(0x110),
105 /* 4 ra1l1, ra2l1, ra1l2, ra2l2, ra12 */
106 .antCtrlCommon2 = LE32(0x22222),
109 * antCtrlChain[AR9300_MAX_CHAINS]; 6 idle, t, r,
110 * rx1, rx12, b (2 bits each)
112 .antCtrlChain = { LE16(0x150), LE16(0x150), LE16(0x150) },
115 * xatten1DB[AR9300_MAX_CHAINS]; 3 xatten1_db
116 * for ar9280 (0xa20c/b20c 5:0)
118 .xatten1DB = {0, 0, 0},
121 * xatten1Margin[AR9300_MAX_CHAINS]; 3 xatten1_margin
122 * for ar9280 (0xa20c/b20c 16:12
124 .xatten1Margin = {0, 0, 0},
129 * spurChans[OSPREY_EEPROM_MODAL_SPURS]; spur
130 * channels in usual fbin coding format
132 .spurChans = {0, 0, 0, 0, 0},
135 * noiseFloorThreshCh[AR9300_MAX_CHAINS]; 3 Check
136 * if the register is per chain
138 .noiseFloorThreshCh = {-1, 0, 0},
139 .ob = {1, 1, 1},/* 3 chain */
140 .db_stage2 = {1, 1, 1}, /* 3 chain */
141 .db_stage3 = {0, 0, 0},
142 .db_stage4 = {0, 0, 0},
144 .txFrameToDataStart = 0x0e,
145 .txFrameToPaOn = 0x0e,
146 .txClip = 3, /* 4 bits tx_clip, 4 bits dac_scale_cck */
148 .switchSettling = 0x2c,
149 .adcDesiredSize = -30,
152 .txFrameToXpaOn = 0xe,
154 .papdRateMaskHt20 = LE32(0x0cf0e0e0),
155 .papdRateMaskHt40 = LE32(0x6cf0e0e0),
157 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
161 .ant_div_control = 0,
162 .future = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}
169 /* ar9300_cal_data_per_freq_op_loop 2g */
171 { {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0} },
172 { {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0} },
173 { {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0} },
175 .calTarget_freqbin_Cck = {
179 .calTarget_freqbin_2G = {
184 .calTarget_freqbin_2GHT20 = {
189 .calTarget_freqbin_2GHT40 = {
194 .calTargetPowerCck = {
195 /* 1L-5L,5S,11L,11S */
196 { {36, 36, 36, 36} },
197 { {36, 36, 36, 36} },
199 .calTargetPower2G = {
201 { {32, 32, 28, 24} },
202 { {32, 32, 28, 24} },
203 { {32, 32, 28, 24} },
205 .calTargetPower2GHT20 = {
206 { {32, 32, 32, 32, 28, 20, 32, 32, 28, 20, 32, 32, 28, 20} },
207 { {32, 32, 32, 32, 28, 20, 32, 32, 28, 20, 32, 32, 28, 20} },
208 { {32, 32, 32, 32, 28, 20, 32, 32, 28, 20, 32, 32, 28, 20} },
210 .calTargetPower2GHT40 = {
211 { {32, 32, 32, 32, 28, 20, 32, 32, 28, 20, 32, 32, 28, 20} },
212 { {32, 32, 32, 32, 28, 20, 32, 32, 28, 20, 32, 32, 28, 20} },
213 { {32, 32, 32, 32, 28, 20, 32, 32, 28, 20, 32, 32, 28, 20} },
216 0x11, 0x12, 0x15, 0x17, 0x41, 0x42,
217 0x45, 0x47, 0x31, 0x32, 0x35, 0x37,
247 /* Data[4].ctlEdges[0].bChannel */ FREQ2FBIN(2412, 1),
248 /* Data[4].ctlEdges[1].bChannel */ FREQ2FBIN(2417, 1),
249 /* Data[4].ctlEdges[2].bChannel */ FREQ2FBIN(2472, 1),
250 /* Data[4].ctlEdges[3].bChannel */ FREQ2FBIN(2484, 1),
254 /* Data[5].ctlEdges[0].bChannel */ FREQ2FBIN(2412, 1),
255 /* Data[5].ctlEdges[1].bChannel */ FREQ2FBIN(2417, 1),
256 /* Data[5].ctlEdges[2].bChannel */ FREQ2FBIN(2472, 1),
261 /* Data[6].ctlEdges[0].bChannel */ FREQ2FBIN(2412, 1),
262 /* Data[6].ctlEdges[1].bChannel */ FREQ2FBIN(2417, 1),
268 /* Data[7].ctlEdges[0].bChannel */ FREQ2FBIN(2422, 1),
269 /* Data[7].ctlEdges[1].bChannel */ FREQ2FBIN(2427, 1),
270 /* Data[7].ctlEdges[2].bChannel */ FREQ2FBIN(2447, 1),
271 /* Data[7].ctlEdges[3].bChannel */ FREQ2FBIN(2462, 1),
275 /* Data[8].ctlEdges[0].bChannel */ FREQ2FBIN(2412, 1),
276 /* Data[8].ctlEdges[1].bChannel */ FREQ2FBIN(2417, 1),
277 /* Data[8].ctlEdges[2].bChannel */ FREQ2FBIN(2472, 1),
281 /* Data[9].ctlEdges[0].bChannel */ FREQ2FBIN(2412, 1),
282 /* Data[9].ctlEdges[1].bChannel */ FREQ2FBIN(2417, 1),
283 /* Data[9].ctlEdges[2].bChannel */ FREQ2FBIN(2472, 1),
288 /* Data[10].ctlEdges[0].bChannel */ FREQ2FBIN(2412, 1),
289 /* Data[10].ctlEdges[1].bChannel */ FREQ2FBIN(2417, 1),
290 /* Data[10].ctlEdges[2].bChannel */ FREQ2FBIN(2472, 1),
295 /* Data[11].ctlEdges[0].bChannel */ FREQ2FBIN(2422, 1),
296 /* Data[11].ctlEdges[1].bChannel */ FREQ2FBIN(2427, 1),
297 /* Data[11].ctlEdges[2].bChannel */ FREQ2FBIN(2447, 1),
298 /* Data[11].ctlEdges[3].bChannel */ FREQ2FBIN(2462, 1),
302 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
303 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
304 { { CTL(60, 1), CTL(60, 0), CTL(60, 0), CTL(60, 1) } },
306 { { CTL(60, 1), CTL(60, 0), CTL(0, 0), CTL(0, 0) } },
307 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
308 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
310 { { CTL(60, 0), CTL(60, 1), CTL(60, 1), CTL(60, 0) } },
311 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
312 { { 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, 0), CTL(60, 1), CTL(60, 1), CTL(60, 1) } },
316 { { CTL(60, 0), CTL(60, 1), CTL(60, 1), CTL(60, 1) } },
319 /* 4 idle,t1,t2,b (4 bits per setting) */
320 .antCtrlCommon = LE32(0x110),
321 /* 4 ra1l1, ra2l1, ra1l2,ra2l2,ra12 */
322 .antCtrlCommon2 = LE32(0x22222),
323 /* antCtrlChain 6 idle, t,r,rx1,rx12,b (2 bits each) */
325 LE16(0x000), LE16(0x000), LE16(0x000),
327 /* xatten1DB 3 xatten1_db for AR9280 (0xa20c/b20c 5:0) */
328 .xatten1DB = {0, 0, 0},
331 * xatten1Margin[AR9300_MAX_CHAINS]; 3 xatten1_margin
332 * for merlin (0xa20c/b20c 16:12
334 .xatten1Margin = {0, 0, 0},
337 /* spurChans spur channels in usual fbin coding format */
338 .spurChans = {0, 0, 0, 0, 0},
339 /* noiseFloorThreshCh Check if the register is per chain */
340 .noiseFloorThreshCh = {-1, 0, 0},
341 .ob = {3, 3, 3}, /* 3 chain */
342 .db_stage2 = {3, 3, 3}, /* 3 chain */
343 .db_stage3 = {3, 3, 3}, /* doesn't exist for 2G */
344 .db_stage4 = {3, 3, 3}, /* don't exist for 2G */
346 .txFrameToDataStart = 0x0e,
347 .txFrameToPaOn = 0x0e,
348 .txClip = 3, /* 4 bits tx_clip, 4 bits dac_scale_cck */
350 .switchSettling = 0x2d,
351 .adcDesiredSize = -30,
354 .txFrameToXpaOn = 0xe,
356 .papdRateMaskHt20 = LE32(0x0c80c080),
357 .papdRateMaskHt40 = LE32(0x0080c080),
359 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
365 .xatten1DBLow = {0, 0, 0},
366 .xatten1MarginLow = {0, 0, 0},
367 .xatten1DBHigh = {0, 0, 0},
368 .xatten1MarginHigh = {0, 0, 0}
413 .calTarget_freqbin_5G = {
423 .calTarget_freqbin_5GHT20 = {
433 .calTarget_freqbin_5GHT40 = {
443 .calTargetPower5G = {
445 { {20, 20, 20, 10} },
446 { {20, 20, 20, 10} },
447 { {20, 20, 20, 10} },
448 { {20, 20, 20, 10} },
449 { {20, 20, 20, 10} },
450 { {20, 20, 20, 10} },
451 { {20, 20, 20, 10} },
452 { {20, 20, 20, 10} },
454 .calTargetPower5GHT20 = {
456 * 0_8_16,1-3_9-11_17-19,
457 * 4,5,6,7,12,13,14,15,20,21,22,23
459 { {20, 20, 10, 10, 0, 0, 10, 10, 0, 0, 10, 10, 0, 0} },
460 { {20, 20, 10, 10, 0, 0, 10, 10, 0, 0, 10, 10, 0, 0} },
461 { {20, 20, 10, 10, 0, 0, 10, 10, 0, 0, 10, 10, 0, 0} },
462 { {20, 20, 10, 10, 0, 0, 10, 10, 0, 0, 10, 10, 0, 0} },
463 { {20, 20, 10, 10, 0, 0, 10, 10, 0, 0, 10, 10, 0, 0} },
464 { {20, 20, 10, 10, 0, 0, 10, 10, 0, 0, 10, 10, 0, 0} },
465 { {20, 20, 10, 10, 0, 0, 10, 10, 0, 0, 10, 10, 0, 0} },
466 { {20, 20, 10, 10, 0, 0, 10, 10, 0, 0, 10, 10, 0, 0} },
468 .calTargetPower5GHT40 = {
470 * 0_8_16,1-3_9-11_17-19,
471 * 4,5,6,7,12,13,14,15,20,21,22,23
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} },
478 { {20, 20, 10, 10, 0, 0, 10, 10, 0, 0, 10, 10, 0, 0} },
479 { {20, 20, 10, 10, 0, 0, 10, 10, 0, 0, 10, 10, 0, 0} },
480 { {20, 20, 10, 10, 0, 0, 10, 10, 0, 0, 10, 10, 0, 0} },
483 0x10, 0x16, 0x18, 0x40, 0x46,
484 0x48, 0x30, 0x36, 0x38
488 /* Data[0].ctlEdges[0].bChannel */ FREQ2FBIN(5180, 0),
489 /* Data[0].ctlEdges[1].bChannel */ FREQ2FBIN(5260, 0),
490 /* Data[0].ctlEdges[2].bChannel */ FREQ2FBIN(5280, 0),
491 /* Data[0].ctlEdges[3].bChannel */ FREQ2FBIN(5500, 0),
492 /* Data[0].ctlEdges[4].bChannel */ FREQ2FBIN(5600, 0),
493 /* Data[0].ctlEdges[5].bChannel */ FREQ2FBIN(5700, 0),
494 /* Data[0].ctlEdges[6].bChannel */ FREQ2FBIN(5745, 0),
495 /* Data[0].ctlEdges[7].bChannel */ FREQ2FBIN(5825, 0)
498 /* Data[1].ctlEdges[0].bChannel */ FREQ2FBIN(5180, 0),
499 /* Data[1].ctlEdges[1].bChannel */ FREQ2FBIN(5260, 0),
500 /* Data[1].ctlEdges[2].bChannel */ FREQ2FBIN(5280, 0),
501 /* Data[1].ctlEdges[3].bChannel */ FREQ2FBIN(5500, 0),
502 /* Data[1].ctlEdges[4].bChannel */ FREQ2FBIN(5520, 0),
503 /* Data[1].ctlEdges[5].bChannel */ FREQ2FBIN(5700, 0),
504 /* Data[1].ctlEdges[6].bChannel */ FREQ2FBIN(5745, 0),
505 /* Data[1].ctlEdges[7].bChannel */ FREQ2FBIN(5825, 0)
509 /* Data[2].ctlEdges[0].bChannel */ FREQ2FBIN(5190, 0),
510 /* Data[2].ctlEdges[1].bChannel */ FREQ2FBIN(5230, 0),
511 /* Data[2].ctlEdges[2].bChannel */ FREQ2FBIN(5270, 0),
512 /* Data[2].ctlEdges[3].bChannel */ FREQ2FBIN(5310, 0),
513 /* Data[2].ctlEdges[4].bChannel */ FREQ2FBIN(5510, 0),
514 /* Data[2].ctlEdges[5].bChannel */ FREQ2FBIN(5550, 0),
515 /* Data[2].ctlEdges[6].bChannel */ FREQ2FBIN(5670, 0),
516 /* Data[2].ctlEdges[7].bChannel */ FREQ2FBIN(5755, 0)
520 /* Data[3].ctlEdges[0].bChannel */ FREQ2FBIN(5180, 0),
521 /* Data[3].ctlEdges[1].bChannel */ FREQ2FBIN(5200, 0),
522 /* Data[3].ctlEdges[2].bChannel */ FREQ2FBIN(5260, 0),
523 /* Data[3].ctlEdges[3].bChannel */ FREQ2FBIN(5320, 0),
524 /* Data[3].ctlEdges[4].bChannel */ FREQ2FBIN(5500, 0),
525 /* Data[3].ctlEdges[5].bChannel */ FREQ2FBIN(5700, 0),
526 /* Data[3].ctlEdges[6].bChannel */ 0xFF,
527 /* Data[3].ctlEdges[7].bChannel */ 0xFF,
531 /* Data[4].ctlEdges[0].bChannel */ FREQ2FBIN(5180, 0),
532 /* Data[4].ctlEdges[1].bChannel */ FREQ2FBIN(5260, 0),
533 /* Data[4].ctlEdges[2].bChannel */ FREQ2FBIN(5500, 0),
534 /* Data[4].ctlEdges[3].bChannel */ FREQ2FBIN(5700, 0),
535 /* Data[4].ctlEdges[4].bChannel */ 0xFF,
536 /* Data[4].ctlEdges[5].bChannel */ 0xFF,
537 /* Data[4].ctlEdges[6].bChannel */ 0xFF,
538 /* Data[4].ctlEdges[7].bChannel */ 0xFF,
542 /* Data[5].ctlEdges[0].bChannel */ FREQ2FBIN(5190, 0),
543 /* Data[5].ctlEdges[1].bChannel */ FREQ2FBIN(5270, 0),
544 /* Data[5].ctlEdges[2].bChannel */ FREQ2FBIN(5310, 0),
545 /* Data[5].ctlEdges[3].bChannel */ FREQ2FBIN(5510, 0),
546 /* Data[5].ctlEdges[4].bChannel */ FREQ2FBIN(5590, 0),
547 /* Data[5].ctlEdges[5].bChannel */ FREQ2FBIN(5670, 0),
548 /* Data[5].ctlEdges[6].bChannel */ 0xFF,
549 /* Data[5].ctlEdges[7].bChannel */ 0xFF
553 /* Data[6].ctlEdges[0].bChannel */ FREQ2FBIN(5180, 0),
554 /* Data[6].ctlEdges[1].bChannel */ FREQ2FBIN(5200, 0),
555 /* Data[6].ctlEdges[2].bChannel */ FREQ2FBIN(5220, 0),
556 /* Data[6].ctlEdges[3].bChannel */ FREQ2FBIN(5260, 0),
557 /* Data[6].ctlEdges[4].bChannel */ FREQ2FBIN(5500, 0),
558 /* Data[6].ctlEdges[5].bChannel */ FREQ2FBIN(5600, 0),
559 /* Data[6].ctlEdges[6].bChannel */ FREQ2FBIN(5700, 0),
560 /* Data[6].ctlEdges[7].bChannel */ FREQ2FBIN(5745, 0)
564 /* Data[7].ctlEdges[0].bChannel */ FREQ2FBIN(5180, 0),
565 /* Data[7].ctlEdges[1].bChannel */ FREQ2FBIN(5260, 0),
566 /* Data[7].ctlEdges[2].bChannel */ FREQ2FBIN(5320, 0),
567 /* Data[7].ctlEdges[3].bChannel */ FREQ2FBIN(5500, 0),
568 /* Data[7].ctlEdges[4].bChannel */ FREQ2FBIN(5560, 0),
569 /* Data[7].ctlEdges[5].bChannel */ FREQ2FBIN(5700, 0),
570 /* Data[7].ctlEdges[6].bChannel */ FREQ2FBIN(5745, 0),
571 /* Data[7].ctlEdges[7].bChannel */ FREQ2FBIN(5825, 0)
575 /* Data[8].ctlEdges[0].bChannel */ FREQ2FBIN(5190, 0),
576 /* Data[8].ctlEdges[1].bChannel */ FREQ2FBIN(5230, 0),
577 /* Data[8].ctlEdges[2].bChannel */ FREQ2FBIN(5270, 0),
578 /* Data[8].ctlEdges[3].bChannel */ FREQ2FBIN(5510, 0),
579 /* Data[8].ctlEdges[4].bChannel */ FREQ2FBIN(5550, 0),
580 /* Data[8].ctlEdges[5].bChannel */ FREQ2FBIN(5670, 0),
581 /* Data[8].ctlEdges[6].bChannel */ FREQ2FBIN(5755, 0),
582 /* Data[8].ctlEdges[7].bChannel */ FREQ2FBIN(5795, 0)
588 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
589 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 0),
594 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
595 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 0),
600 CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 1),
601 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
606 CTL(60, 0), CTL(60, 1), CTL(60, 1), CTL(60, 0),
607 CTL(60, 1), CTL(60, 0), CTL(60, 0), CTL(60, 0),
612 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 0),
613 CTL(60, 0), CTL(60, 0), CTL(60, 0), CTL(60, 0),
618 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
619 CTL(60, 1), CTL(60, 0), CTL(60, 0), CTL(60, 0),
624 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
625 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
630 CTL(60, 1), CTL(60, 1), CTL(60, 0), CTL(60, 1),
631 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 0),
636 CTL(60, 1), CTL(60, 0), CTL(60, 1), CTL(60, 1),
637 CTL(60, 1), CTL(60, 1), CTL(60, 0), CTL(60, 1),
643 static const struct ar9300_eeprom ar9300_x113 = {
645 .templateVersion = 6,
646 .macAddr = {0x00, 0x03, 0x7f, 0x0, 0x0, 0x0},
647 .custData = {"x113-023-f0000"},
649 .regDmn = { LE16(0), LE16(0x1f) },
650 .txrxMask = 0x77, /* 4 bits tx and 4 bits rx */
652 .opFlags = AR5416_OPFLAGS_11G | AR5416_OPFLAGS_11A,
656 .blueToothOptions = 0,
658 .deviceType = 5, /* takes lower byte in eeprom location */
659 .pwrTableOffset = AR9300_PWR_TABLE_OFFSET,
660 .params_for_tuning_caps = {0, 0},
661 .featureEnable = 0x0d,
663 * bit0 - enable tx temp comp - disabled
664 * bit1 - enable tx volt comp - disabled
665 * bit2 - enable fastClock - enabled
666 * bit3 - enable doubling - enabled
667 * bit4 - enable internal regulator - disabled
668 * bit5 - enable pa predistortion - disabled
670 .miscConfiguration = 0, /* bit0 - turn down drivestrength */
671 .eepromWriteEnableGpio = 6,
672 .wlanDisableGpio = 0,
674 .rxBandSelectGpio = 0xff,
679 /* ar9300_modal_eep_header 2g */
680 /* 4 idle,t1,t2,b(4 bits per setting) */
681 .antCtrlCommon = LE32(0x110),
682 /* 4 ra1l1, ra2l1, ra1l2, ra2l2, ra12 */
683 .antCtrlCommon2 = LE32(0x44444),
686 * antCtrlChain[AR9300_MAX_CHAINS]; 6 idle, t, r,
687 * rx1, rx12, b (2 bits each)
689 .antCtrlChain = { LE16(0x150), LE16(0x150), LE16(0x150) },
692 * xatten1DB[AR9300_MAX_CHAINS]; 3 xatten1_db
693 * for ar9280 (0xa20c/b20c 5:0)
695 .xatten1DB = {0, 0, 0},
698 * xatten1Margin[AR9300_MAX_CHAINS]; 3 xatten1_margin
699 * for ar9280 (0xa20c/b20c 16:12
701 .xatten1Margin = {0, 0, 0},
706 * spurChans[OSPREY_EEPROM_MODAL_SPURS]; spur
707 * channels in usual fbin coding format
709 .spurChans = {FREQ2FBIN(2464, 1), 0, 0, 0, 0},
712 * noiseFloorThreshCh[AR9300_MAX_CHAINS]; 3 Check
713 * if the register is per chain
715 .noiseFloorThreshCh = {-1, 0, 0},
716 .ob = {1, 1, 1},/* 3 chain */
717 .db_stage2 = {1, 1, 1}, /* 3 chain */
718 .db_stage3 = {0, 0, 0},
719 .db_stage4 = {0, 0, 0},
721 .txFrameToDataStart = 0x0e,
722 .txFrameToPaOn = 0x0e,
723 .txClip = 3, /* 4 bits tx_clip, 4 bits dac_scale_cck */
725 .switchSettling = 0x2c,
726 .adcDesiredSize = -30,
729 .txFrameToXpaOn = 0xe,
731 .papdRateMaskHt20 = LE32(0x0c80c080),
732 .papdRateMaskHt40 = LE32(0x0080c080),
734 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
738 .ant_div_control = 0,
739 .future = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}
746 /* ar9300_cal_data_per_freq_op_loop 2g */
748 { {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0} },
749 { {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0} },
750 { {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0} },
752 .calTarget_freqbin_Cck = {
756 .calTarget_freqbin_2G = {
761 .calTarget_freqbin_2GHT20 = {
766 .calTarget_freqbin_2GHT40 = {
771 .calTargetPowerCck = {
772 /* 1L-5L,5S,11L,11S */
773 { {34, 34, 34, 34} },
774 { {34, 34, 34, 34} },
776 .calTargetPower2G = {
778 { {34, 34, 32, 32} },
779 { {34, 34, 32, 32} },
780 { {34, 34, 32, 32} },
782 .calTargetPower2GHT20 = {
783 { {32, 32, 32, 32, 32, 28, 32, 32, 30, 28, 0, 0, 0, 0} },
784 { {32, 32, 32, 32, 32, 28, 32, 32, 30, 28, 0, 0, 0, 0} },
785 { {32, 32, 32, 32, 32, 28, 32, 32, 30, 28, 0, 0, 0, 0} },
787 .calTargetPower2GHT40 = {
788 { {30, 30, 30, 30, 30, 28, 30, 30, 28, 26, 0, 0, 0, 0} },
789 { {30, 30, 30, 30, 30, 28, 30, 30, 28, 26, 0, 0, 0, 0} },
790 { {30, 30, 30, 30, 30, 28, 30, 30, 28, 26, 0, 0, 0, 0} },
793 0x11, 0x12, 0x15, 0x17, 0x41, 0x42,
794 0x45, 0x47, 0x31, 0x32, 0x35, 0x37,
824 /* Data[4].ctlEdges[0].bChannel */ FREQ2FBIN(2412, 1),
825 /* Data[4].ctlEdges[1].bChannel */ FREQ2FBIN(2417, 1),
826 /* Data[4].ctlEdges[2].bChannel */ FREQ2FBIN(2472, 1),
827 /* Data[4].ctlEdges[3].bChannel */ FREQ2FBIN(2484, 1),
831 /* Data[5].ctlEdges[0].bChannel */ FREQ2FBIN(2412, 1),
832 /* Data[5].ctlEdges[1].bChannel */ FREQ2FBIN(2417, 1),
833 /* Data[5].ctlEdges[2].bChannel */ FREQ2FBIN(2472, 1),
838 /* Data[6].ctlEdges[0].bChannel */ FREQ2FBIN(2412, 1),
839 /* Data[6].ctlEdges[1].bChannel */ FREQ2FBIN(2417, 1),
845 /* Data[7].ctlEdges[0].bChannel */ FREQ2FBIN(2422, 1),
846 /* Data[7].ctlEdges[1].bChannel */ FREQ2FBIN(2427, 1),
847 /* Data[7].ctlEdges[2].bChannel */ FREQ2FBIN(2447, 1),
848 /* Data[7].ctlEdges[3].bChannel */ FREQ2FBIN(2462, 1),
852 /* Data[8].ctlEdges[0].bChannel */ FREQ2FBIN(2412, 1),
853 /* Data[8].ctlEdges[1].bChannel */ FREQ2FBIN(2417, 1),
854 /* Data[8].ctlEdges[2].bChannel */ FREQ2FBIN(2472, 1),
858 /* Data[9].ctlEdges[0].bChannel */ FREQ2FBIN(2412, 1),
859 /* Data[9].ctlEdges[1].bChannel */ FREQ2FBIN(2417, 1),
860 /* Data[9].ctlEdges[2].bChannel */ FREQ2FBIN(2472, 1),
865 /* Data[10].ctlEdges[0].bChannel */ FREQ2FBIN(2412, 1),
866 /* Data[10].ctlEdges[1].bChannel */ FREQ2FBIN(2417, 1),
867 /* Data[10].ctlEdges[2].bChannel */ FREQ2FBIN(2472, 1),
872 /* Data[11].ctlEdges[0].bChannel */ FREQ2FBIN(2422, 1),
873 /* Data[11].ctlEdges[1].bChannel */ FREQ2FBIN(2427, 1),
874 /* Data[11].ctlEdges[2].bChannel */ FREQ2FBIN(2447, 1),
875 /* Data[11].ctlEdges[3].bChannel */ FREQ2FBIN(2462, 1),
879 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
880 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
881 { { CTL(60, 1), CTL(60, 0), CTL(60, 0), CTL(60, 1) } },
883 { { CTL(60, 1), CTL(60, 0), CTL(0, 0), CTL(0, 0) } },
884 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
885 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
887 { { CTL(60, 0), CTL(60, 1), CTL(60, 1), CTL(60, 0) } },
888 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
889 { { 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, 0), CTL(60, 1), CTL(60, 1), CTL(60, 1) } },
893 { { CTL(60, 0), CTL(60, 1), CTL(60, 1), CTL(60, 1) } },
896 /* 4 idle,t1,t2,b (4 bits per setting) */
897 .antCtrlCommon = LE32(0x220),
898 /* 4 ra1l1, ra2l1, ra1l2,ra2l2,ra12 */
899 .antCtrlCommon2 = LE32(0x11111),
900 /* antCtrlChain 6 idle, t,r,rx1,rx12,b (2 bits each) */
902 LE16(0x150), LE16(0x150), LE16(0x150),
904 /* xatten1DB 3 xatten1_db for AR9280 (0xa20c/b20c 5:0) */
905 .xatten1DB = {0, 0, 0},
908 * xatten1Margin[AR9300_MAX_CHAINS]; 3 xatten1_margin
909 * for merlin (0xa20c/b20c 16:12
911 .xatten1Margin = {0, 0, 0},
914 /* spurChans spur channels in usual fbin coding format */
915 .spurChans = {FREQ2FBIN(5500, 0), 0, 0, 0, 0},
916 /* noiseFloorThreshCh Check if the register is per chain */
917 .noiseFloorThreshCh = {-1, 0, 0},
918 .ob = {3, 3, 3}, /* 3 chain */
919 .db_stage2 = {3, 3, 3}, /* 3 chain */
920 .db_stage3 = {3, 3, 3}, /* doesn't exist for 2G */
921 .db_stage4 = {3, 3, 3}, /* don't exist for 2G */
923 .txFrameToDataStart = 0x0e,
924 .txFrameToPaOn = 0x0e,
925 .txClip = 3, /* 4 bits tx_clip, 4 bits dac_scale_cck */
927 .switchSettling = 0x2d,
928 .adcDesiredSize = -30,
931 .txFrameToXpaOn = 0xe,
933 .papdRateMaskHt20 = LE32(0x0cf0e0e0),
934 .papdRateMaskHt40 = LE32(0x6cf0e0e0),
936 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
941 .tempSlopeHigh = 105,
942 .xatten1DBLow = {0, 0, 0},
943 .xatten1MarginLow = {0, 0, 0},
944 .xatten1DBHigh = {0, 0, 0},
945 .xatten1MarginHigh = {0, 0, 0}
990 .calTarget_freqbin_5G = {
1000 .calTarget_freqbin_5GHT20 = {
1010 .calTarget_freqbin_5GHT40 = {
1020 .calTargetPower5G = {
1022 { {42, 40, 40, 34} },
1023 { {42, 40, 40, 34} },
1024 { {42, 40, 40, 34} },
1025 { {42, 40, 40, 34} },
1026 { {42, 40, 40, 34} },
1027 { {42, 40, 40, 34} },
1028 { {42, 40, 40, 34} },
1029 { {42, 40, 40, 34} },
1031 .calTargetPower5GHT20 = {
1033 * 0_8_16,1-3_9-11_17-19,
1034 * 4,5,6,7,12,13,14,15,20,21,22,23
1036 { {40, 40, 40, 40, 32, 28, 40, 40, 32, 28, 40, 40, 32, 20} },
1037 { {40, 40, 40, 40, 32, 28, 40, 40, 32, 28, 40, 40, 32, 20} },
1038 { {40, 40, 40, 40, 32, 28, 40, 40, 32, 28, 40, 40, 32, 20} },
1039 { {40, 40, 40, 40, 32, 28, 40, 40, 32, 28, 40, 40, 32, 20} },
1040 { {40, 40, 40, 40, 32, 28, 40, 40, 32, 28, 40, 40, 32, 20} },
1041 { {40, 40, 40, 40, 32, 28, 40, 40, 32, 28, 40, 40, 32, 20} },
1042 { {38, 38, 38, 38, 32, 28, 38, 38, 32, 28, 38, 38, 32, 26} },
1043 { {36, 36, 36, 36, 32, 28, 36, 36, 32, 28, 36, 36, 32, 26} },
1045 .calTargetPower5GHT40 = {
1047 * 0_8_16,1-3_9-11_17-19,
1048 * 4,5,6,7,12,13,14,15,20,21,22,23
1050 { {40, 40, 40, 38, 30, 26, 40, 40, 30, 26, 40, 40, 30, 24} },
1051 { {40, 40, 40, 38, 30, 26, 40, 40, 30, 26, 40, 40, 30, 24} },
1052 { {40, 40, 40, 38, 30, 26, 40, 40, 30, 26, 40, 40, 30, 24} },
1053 { {40, 40, 40, 38, 30, 26, 40, 40, 30, 26, 40, 40, 30, 24} },
1054 { {40, 40, 40, 38, 30, 26, 40, 40, 30, 26, 40, 40, 30, 24} },
1055 { {40, 40, 40, 38, 30, 26, 40, 40, 30, 26, 40, 40, 30, 24} },
1056 { {36, 36, 36, 36, 30, 26, 36, 36, 30, 26, 36, 36, 30, 24} },
1057 { {34, 34, 34, 34, 30, 26, 34, 34, 30, 26, 34, 34, 30, 24} },
1060 0x10, 0x16, 0x18, 0x40, 0x46,
1061 0x48, 0x30, 0x36, 0x38
1065 /* Data[0].ctlEdges[0].bChannel */ FREQ2FBIN(5180, 0),
1066 /* Data[0].ctlEdges[1].bChannel */ FREQ2FBIN(5260, 0),
1067 /* Data[0].ctlEdges[2].bChannel */ FREQ2FBIN(5280, 0),
1068 /* Data[0].ctlEdges[3].bChannel */ FREQ2FBIN(5500, 0),
1069 /* Data[0].ctlEdges[4].bChannel */ FREQ2FBIN(5600, 0),
1070 /* Data[0].ctlEdges[5].bChannel */ FREQ2FBIN(5700, 0),
1071 /* Data[0].ctlEdges[6].bChannel */ FREQ2FBIN(5745, 0),
1072 /* Data[0].ctlEdges[7].bChannel */ FREQ2FBIN(5825, 0)
1075 /* Data[1].ctlEdges[0].bChannel */ FREQ2FBIN(5180, 0),
1076 /* Data[1].ctlEdges[1].bChannel */ FREQ2FBIN(5260, 0),
1077 /* Data[1].ctlEdges[2].bChannel */ FREQ2FBIN(5280, 0),
1078 /* Data[1].ctlEdges[3].bChannel */ FREQ2FBIN(5500, 0),
1079 /* Data[1].ctlEdges[4].bChannel */ FREQ2FBIN(5520, 0),
1080 /* Data[1].ctlEdges[5].bChannel */ FREQ2FBIN(5700, 0),
1081 /* Data[1].ctlEdges[6].bChannel */ FREQ2FBIN(5745, 0),
1082 /* Data[1].ctlEdges[7].bChannel */ FREQ2FBIN(5825, 0)
1086 /* Data[2].ctlEdges[0].bChannel */ FREQ2FBIN(5190, 0),
1087 /* Data[2].ctlEdges[1].bChannel */ FREQ2FBIN(5230, 0),
1088 /* Data[2].ctlEdges[2].bChannel */ FREQ2FBIN(5270, 0),
1089 /* Data[2].ctlEdges[3].bChannel */ FREQ2FBIN(5310, 0),
1090 /* Data[2].ctlEdges[4].bChannel */ FREQ2FBIN(5510, 0),
1091 /* Data[2].ctlEdges[5].bChannel */ FREQ2FBIN(5550, 0),
1092 /* Data[2].ctlEdges[6].bChannel */ FREQ2FBIN(5670, 0),
1093 /* Data[2].ctlEdges[7].bChannel */ FREQ2FBIN(5755, 0)
1097 /* Data[3].ctlEdges[0].bChannel */ FREQ2FBIN(5180, 0),
1098 /* Data[3].ctlEdges[1].bChannel */ FREQ2FBIN(5200, 0),
1099 /* Data[3].ctlEdges[2].bChannel */ FREQ2FBIN(5260, 0),
1100 /* Data[3].ctlEdges[3].bChannel */ FREQ2FBIN(5320, 0),
1101 /* Data[3].ctlEdges[4].bChannel */ FREQ2FBIN(5500, 0),
1102 /* Data[3].ctlEdges[5].bChannel */ FREQ2FBIN(5700, 0),
1103 /* Data[3].ctlEdges[6].bChannel */ 0xFF,
1104 /* Data[3].ctlEdges[7].bChannel */ 0xFF,
1108 /* Data[4].ctlEdges[0].bChannel */ FREQ2FBIN(5180, 0),
1109 /* Data[4].ctlEdges[1].bChannel */ FREQ2FBIN(5260, 0),
1110 /* Data[4].ctlEdges[2].bChannel */ FREQ2FBIN(5500, 0),
1111 /* Data[4].ctlEdges[3].bChannel */ FREQ2FBIN(5700, 0),
1112 /* Data[4].ctlEdges[4].bChannel */ 0xFF,
1113 /* Data[4].ctlEdges[5].bChannel */ 0xFF,
1114 /* Data[4].ctlEdges[6].bChannel */ 0xFF,
1115 /* Data[4].ctlEdges[7].bChannel */ 0xFF,
1119 /* Data[5].ctlEdges[0].bChannel */ FREQ2FBIN(5190, 0),
1120 /* Data[5].ctlEdges[1].bChannel */ FREQ2FBIN(5270, 0),
1121 /* Data[5].ctlEdges[2].bChannel */ FREQ2FBIN(5310, 0),
1122 /* Data[5].ctlEdges[3].bChannel */ FREQ2FBIN(5510, 0),
1123 /* Data[5].ctlEdges[4].bChannel */ FREQ2FBIN(5590, 0),
1124 /* Data[5].ctlEdges[5].bChannel */ FREQ2FBIN(5670, 0),
1125 /* Data[5].ctlEdges[6].bChannel */ 0xFF,
1126 /* Data[5].ctlEdges[7].bChannel */ 0xFF
1130 /* Data[6].ctlEdges[0].bChannel */ FREQ2FBIN(5180, 0),
1131 /* Data[6].ctlEdges[1].bChannel */ FREQ2FBIN(5200, 0),
1132 /* Data[6].ctlEdges[2].bChannel */ FREQ2FBIN(5220, 0),
1133 /* Data[6].ctlEdges[3].bChannel */ FREQ2FBIN(5260, 0),
1134 /* Data[6].ctlEdges[4].bChannel */ FREQ2FBIN(5500, 0),
1135 /* Data[6].ctlEdges[5].bChannel */ FREQ2FBIN(5600, 0),
1136 /* Data[6].ctlEdges[6].bChannel */ FREQ2FBIN(5700, 0),
1137 /* Data[6].ctlEdges[7].bChannel */ FREQ2FBIN(5745, 0)
1141 /* Data[7].ctlEdges[0].bChannel */ FREQ2FBIN(5180, 0),
1142 /* Data[7].ctlEdges[1].bChannel */ FREQ2FBIN(5260, 0),
1143 /* Data[7].ctlEdges[2].bChannel */ FREQ2FBIN(5320, 0),
1144 /* Data[7].ctlEdges[3].bChannel */ FREQ2FBIN(5500, 0),
1145 /* Data[7].ctlEdges[4].bChannel */ FREQ2FBIN(5560, 0),
1146 /* Data[7].ctlEdges[5].bChannel */ FREQ2FBIN(5700, 0),
1147 /* Data[7].ctlEdges[6].bChannel */ FREQ2FBIN(5745, 0),
1148 /* Data[7].ctlEdges[7].bChannel */ FREQ2FBIN(5825, 0)
1152 /* Data[8].ctlEdges[0].bChannel */ FREQ2FBIN(5190, 0),
1153 /* Data[8].ctlEdges[1].bChannel */ FREQ2FBIN(5230, 0),
1154 /* Data[8].ctlEdges[2].bChannel */ FREQ2FBIN(5270, 0),
1155 /* Data[8].ctlEdges[3].bChannel */ FREQ2FBIN(5510, 0),
1156 /* Data[8].ctlEdges[4].bChannel */ FREQ2FBIN(5550, 0),
1157 /* Data[8].ctlEdges[5].bChannel */ FREQ2FBIN(5670, 0),
1158 /* Data[8].ctlEdges[6].bChannel */ FREQ2FBIN(5755, 0),
1159 /* Data[8].ctlEdges[7].bChannel */ FREQ2FBIN(5795, 0)
1162 .ctlPowerData_5G = {
1165 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
1166 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 0),
1171 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
1172 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 0),
1177 CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 1),
1178 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
1183 CTL(60, 0), CTL(60, 1), CTL(60, 1), CTL(60, 0),
1184 CTL(60, 1), CTL(60, 0), CTL(60, 0), CTL(60, 0),
1189 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 0),
1190 CTL(60, 0), CTL(60, 0), CTL(60, 0), CTL(60, 0),
1195 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
1196 CTL(60, 1), CTL(60, 0), CTL(60, 0), CTL(60, 0),
1201 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
1202 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
1207 CTL(60, 1), CTL(60, 1), CTL(60, 0), CTL(60, 1),
1208 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 0),
1213 CTL(60, 1), CTL(60, 0), CTL(60, 1), CTL(60, 1),
1214 CTL(60, 1), CTL(60, 1), CTL(60, 0), CTL(60, 1),
1221 static const struct ar9300_eeprom ar9300_h112 = {
1223 .templateVersion = 3,
1224 .macAddr = {0x00, 0x03, 0x7f, 0x0, 0x0, 0x0},
1225 .custData = {"h112-241-f0000"},
1227 .regDmn = { LE16(0), LE16(0x1f) },
1228 .txrxMask = 0x77, /* 4 bits tx and 4 bits rx */
1230 .opFlags = AR5416_OPFLAGS_11G | AR5416_OPFLAGS_11A,
1234 .blueToothOptions = 0,
1236 .deviceType = 5, /* takes lower byte in eeprom location */
1237 .pwrTableOffset = AR9300_PWR_TABLE_OFFSET,
1238 .params_for_tuning_caps = {0, 0},
1239 .featureEnable = 0x0d,
1241 * bit0 - enable tx temp comp - disabled
1242 * bit1 - enable tx volt comp - disabled
1243 * bit2 - enable fastClock - enabled
1244 * bit3 - enable doubling - enabled
1245 * bit4 - enable internal regulator - disabled
1246 * bit5 - enable pa predistortion - disabled
1248 .miscConfiguration = 0, /* bit0 - turn down drivestrength */
1249 .eepromWriteEnableGpio = 6,
1250 .wlanDisableGpio = 0,
1252 .rxBandSelectGpio = 0xff,
1257 /* ar9300_modal_eep_header 2g */
1258 /* 4 idle,t1,t2,b(4 bits per setting) */
1259 .antCtrlCommon = LE32(0x110),
1260 /* 4 ra1l1, ra2l1, ra1l2, ra2l2, ra12 */
1261 .antCtrlCommon2 = LE32(0x44444),
1264 * antCtrlChain[AR9300_MAX_CHAINS]; 6 idle, t, r,
1265 * rx1, rx12, b (2 bits each)
1267 .antCtrlChain = { LE16(0x150), LE16(0x150), LE16(0x150) },
1270 * xatten1DB[AR9300_MAX_CHAINS]; 3 xatten1_db
1271 * for ar9280 (0xa20c/b20c 5:0)
1273 .xatten1DB = {0, 0, 0},
1276 * xatten1Margin[AR9300_MAX_CHAINS]; 3 xatten1_margin
1277 * for ar9280 (0xa20c/b20c 16:12
1279 .xatten1Margin = {0, 0, 0},
1284 * spurChans[OSPREY_EEPROM_MODAL_SPURS]; spur
1285 * channels in usual fbin coding format
1287 .spurChans = {FREQ2FBIN(2464, 1), 0, 0, 0, 0},
1290 * noiseFloorThreshCh[AR9300_MAX_CHAINS]; 3 Check
1291 * if the register is per chain
1293 .noiseFloorThreshCh = {-1, 0, 0},
1294 .ob = {1, 1, 1},/* 3 chain */
1295 .db_stage2 = {1, 1, 1}, /* 3 chain */
1296 .db_stage3 = {0, 0, 0},
1297 .db_stage4 = {0, 0, 0},
1299 .txFrameToDataStart = 0x0e,
1300 .txFrameToPaOn = 0x0e,
1301 .txClip = 3, /* 4 bits tx_clip, 4 bits dac_scale_cck */
1303 .switchSettling = 0x2c,
1304 .adcDesiredSize = -30,
1307 .txFrameToXpaOn = 0xe,
1309 .papdRateMaskHt20 = LE32(0x80c080),
1310 .papdRateMaskHt40 = LE32(0x80c080),
1312 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
1316 .ant_div_control = 0,
1317 .future = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}
1324 /* ar9300_cal_data_per_freq_op_loop 2g */
1326 { {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0} },
1327 { {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0} },
1328 { {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0} },
1330 .calTarget_freqbin_Cck = {
1334 .calTarget_freqbin_2G = {
1339 .calTarget_freqbin_2GHT20 = {
1344 .calTarget_freqbin_2GHT40 = {
1349 .calTargetPowerCck = {
1350 /* 1L-5L,5S,11L,11S */
1351 { {34, 34, 34, 34} },
1352 { {34, 34, 34, 34} },
1354 .calTargetPower2G = {
1356 { {34, 34, 32, 32} },
1357 { {34, 34, 32, 32} },
1358 { {34, 34, 32, 32} },
1360 .calTargetPower2GHT20 = {
1361 { {32, 32, 32, 32, 32, 30, 32, 32, 30, 28, 28, 28, 28, 24} },
1362 { {32, 32, 32, 32, 32, 30, 32, 32, 30, 28, 28, 28, 28, 24} },
1363 { {32, 32, 32, 32, 32, 30, 32, 32, 30, 28, 28, 28, 28, 24} },
1365 .calTargetPower2GHT40 = {
1366 { {30, 30, 30, 30, 30, 28, 30, 30, 28, 26, 26, 26, 26, 22} },
1367 { {30, 30, 30, 30, 30, 28, 30, 30, 28, 26, 26, 26, 26, 22} },
1368 { {30, 30, 30, 30, 30, 28, 30, 30, 28, 26, 26, 26, 26, 22} },
1371 0x11, 0x12, 0x15, 0x17, 0x41, 0x42,
1372 0x45, 0x47, 0x31, 0x32, 0x35, 0x37,
1402 /* Data[4].ctlEdges[0].bChannel */ FREQ2FBIN(2412, 1),
1403 /* Data[4].ctlEdges[1].bChannel */ FREQ2FBIN(2417, 1),
1404 /* Data[4].ctlEdges[2].bChannel */ FREQ2FBIN(2472, 1),
1405 /* Data[4].ctlEdges[3].bChannel */ FREQ2FBIN(2484, 1),
1409 /* Data[5].ctlEdges[0].bChannel */ FREQ2FBIN(2412, 1),
1410 /* Data[5].ctlEdges[1].bChannel */ FREQ2FBIN(2417, 1),
1411 /* Data[5].ctlEdges[2].bChannel */ FREQ2FBIN(2472, 1),
1416 /* Data[6].ctlEdges[0].bChannel */ FREQ2FBIN(2412, 1),
1417 /* Data[6].ctlEdges[1].bChannel */ FREQ2FBIN(2417, 1),
1423 /* Data[7].ctlEdges[0].bChannel */ FREQ2FBIN(2422, 1),
1424 /* Data[7].ctlEdges[1].bChannel */ FREQ2FBIN(2427, 1),
1425 /* Data[7].ctlEdges[2].bChannel */ FREQ2FBIN(2447, 1),
1426 /* Data[7].ctlEdges[3].bChannel */ FREQ2FBIN(2462, 1),
1430 /* Data[8].ctlEdges[0].bChannel */ FREQ2FBIN(2412, 1),
1431 /* Data[8].ctlEdges[1].bChannel */ FREQ2FBIN(2417, 1),
1432 /* Data[8].ctlEdges[2].bChannel */ FREQ2FBIN(2472, 1),
1436 /* Data[9].ctlEdges[0].bChannel */ FREQ2FBIN(2412, 1),
1437 /* Data[9].ctlEdges[1].bChannel */ FREQ2FBIN(2417, 1),
1438 /* Data[9].ctlEdges[2].bChannel */ FREQ2FBIN(2472, 1),
1443 /* Data[10].ctlEdges[0].bChannel */ FREQ2FBIN(2412, 1),
1444 /* Data[10].ctlEdges[1].bChannel */ FREQ2FBIN(2417, 1),
1445 /* Data[10].ctlEdges[2].bChannel */ FREQ2FBIN(2472, 1),
1450 /* Data[11].ctlEdges[0].bChannel */ FREQ2FBIN(2422, 1),
1451 /* Data[11].ctlEdges[1].bChannel */ FREQ2FBIN(2427, 1),
1452 /* Data[11].ctlEdges[2].bChannel */ FREQ2FBIN(2447, 1),
1453 /* Data[11].ctlEdges[3].bChannel */ FREQ2FBIN(2462, 1),
1456 .ctlPowerData_2G = {
1457 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
1458 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
1459 { { CTL(60, 1), CTL(60, 0), CTL(60, 0), CTL(60, 1) } },
1461 { { CTL(60, 1), CTL(60, 0), CTL(0, 0), CTL(0, 0) } },
1462 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
1463 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
1465 { { CTL(60, 0), CTL(60, 1), CTL(60, 1), CTL(60, 0) } },
1466 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
1467 { { 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, 0), CTL(60, 1), CTL(60, 1), CTL(60, 1) } },
1471 { { CTL(60, 0), CTL(60, 1), CTL(60, 1), CTL(60, 1) } },
1474 /* 4 idle,t1,t2,b (4 bits per setting) */
1475 .antCtrlCommon = LE32(0x220),
1476 /* 4 ra1l1, ra2l1, ra1l2,ra2l2,ra12 */
1477 .antCtrlCommon2 = LE32(0x44444),
1478 /* antCtrlChain 6 idle, t,r,rx1,rx12,b (2 bits each) */
1480 LE16(0x150), LE16(0x150), LE16(0x150),
1482 /* xatten1DB 3 xatten1_db for AR9280 (0xa20c/b20c 5:0) */
1483 .xatten1DB = {0, 0, 0},
1486 * xatten1Margin[AR9300_MAX_CHAINS]; 3 xatten1_margin
1487 * for merlin (0xa20c/b20c 16:12
1489 .xatten1Margin = {0, 0, 0},
1492 /* spurChans spur channels in usual fbin coding format */
1493 .spurChans = {0, 0, 0, 0, 0},
1494 /* noiseFloorThreshCh Check if the register is per chain */
1495 .noiseFloorThreshCh = {-1, 0, 0},
1496 .ob = {3, 3, 3}, /* 3 chain */
1497 .db_stage2 = {3, 3, 3}, /* 3 chain */
1498 .db_stage3 = {3, 3, 3}, /* doesn't exist for 2G */
1499 .db_stage4 = {3, 3, 3}, /* don't exist for 2G */
1501 .txFrameToDataStart = 0x0e,
1502 .txFrameToPaOn = 0x0e,
1503 .txClip = 3, /* 4 bits tx_clip, 4 bits dac_scale_cck */
1505 .switchSettling = 0x2d,
1506 .adcDesiredSize = -30,
1509 .txFrameToXpaOn = 0xe,
1511 .papdRateMaskHt20 = LE32(0x0cf0e0e0),
1512 .papdRateMaskHt40 = LE32(0x6cf0e0e0),
1514 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
1519 .tempSlopeHigh = 50,
1520 .xatten1DBLow = {0, 0, 0},
1521 .xatten1MarginLow = {0, 0, 0},
1522 .xatten1DBHigh = {0, 0, 0},
1523 .xatten1MarginHigh = {0, 0, 0}
1568 .calTarget_freqbin_5G = {
1578 .calTarget_freqbin_5GHT20 = {
1588 .calTarget_freqbin_5GHT40 = {
1598 .calTargetPower5G = {
1600 { {30, 30, 28, 24} },
1601 { {30, 30, 28, 24} },
1602 { {30, 30, 28, 24} },
1603 { {30, 30, 28, 24} },
1604 { {30, 30, 28, 24} },
1605 { {30, 30, 28, 24} },
1606 { {30, 30, 28, 24} },
1607 { {30, 30, 28, 24} },
1609 .calTargetPower5GHT20 = {
1611 * 0_8_16,1-3_9-11_17-19,
1612 * 4,5,6,7,12,13,14,15,20,21,22,23
1614 { {30, 30, 30, 28, 24, 20, 30, 28, 24, 20, 20, 20, 20, 16} },
1615 { {30, 30, 30, 28, 24, 20, 30, 28, 24, 20, 20, 20, 20, 16} },
1616 { {30, 30, 30, 26, 22, 18, 30, 26, 22, 18, 18, 18, 18, 16} },
1617 { {30, 30, 30, 26, 22, 18, 30, 26, 22, 18, 18, 18, 18, 16} },
1618 { {30, 30, 30, 24, 20, 16, 30, 24, 20, 16, 16, 16, 16, 14} },
1619 { {30, 30, 30, 24, 20, 16, 30, 24, 20, 16, 16, 16, 16, 14} },
1620 { {30, 30, 30, 22, 18, 14, 30, 22, 18, 14, 14, 14, 14, 12} },
1621 { {30, 30, 30, 22, 18, 14, 30, 22, 18, 14, 14, 14, 14, 12} },
1623 .calTargetPower5GHT40 = {
1625 * 0_8_16,1-3_9-11_17-19,
1626 * 4,5,6,7,12,13,14,15,20,21,22,23
1628 { {28, 28, 28, 26, 22, 18, 28, 26, 22, 18, 18, 18, 18, 14} },
1629 { {28, 28, 28, 26, 22, 18, 28, 26, 22, 18, 18, 18, 18, 14} },
1630 { {28, 28, 28, 24, 20, 16, 28, 24, 20, 16, 16, 16, 16, 12} },
1631 { {28, 28, 28, 24, 20, 16, 28, 24, 20, 16, 16, 16, 16, 12} },
1632 { {28, 28, 28, 22, 18, 14, 28, 22, 18, 14, 14, 14, 14, 10} },
1633 { {28, 28, 28, 22, 18, 14, 28, 22, 18, 14, 14, 14, 14, 10} },
1634 { {28, 28, 28, 20, 16, 12, 28, 20, 16, 12, 12, 12, 12, 8} },
1635 { {28, 28, 28, 20, 16, 12, 28, 20, 16, 12, 12, 12, 12, 8} },
1638 0x10, 0x16, 0x18, 0x40, 0x46,
1639 0x48, 0x30, 0x36, 0x38
1643 /* Data[0].ctlEdges[0].bChannel */ FREQ2FBIN(5180, 0),
1644 /* Data[0].ctlEdges[1].bChannel */ FREQ2FBIN(5260, 0),
1645 /* Data[0].ctlEdges[2].bChannel */ FREQ2FBIN(5280, 0),
1646 /* Data[0].ctlEdges[3].bChannel */ FREQ2FBIN(5500, 0),
1647 /* Data[0].ctlEdges[4].bChannel */ FREQ2FBIN(5600, 0),
1648 /* Data[0].ctlEdges[5].bChannel */ FREQ2FBIN(5700, 0),
1649 /* Data[0].ctlEdges[6].bChannel */ FREQ2FBIN(5745, 0),
1650 /* Data[0].ctlEdges[7].bChannel */ FREQ2FBIN(5825, 0)
1653 /* Data[1].ctlEdges[0].bChannel */ FREQ2FBIN(5180, 0),
1654 /* Data[1].ctlEdges[1].bChannel */ FREQ2FBIN(5260, 0),
1655 /* Data[1].ctlEdges[2].bChannel */ FREQ2FBIN(5280, 0),
1656 /* Data[1].ctlEdges[3].bChannel */ FREQ2FBIN(5500, 0),
1657 /* Data[1].ctlEdges[4].bChannel */ FREQ2FBIN(5520, 0),
1658 /* Data[1].ctlEdges[5].bChannel */ FREQ2FBIN(5700, 0),
1659 /* Data[1].ctlEdges[6].bChannel */ FREQ2FBIN(5745, 0),
1660 /* Data[1].ctlEdges[7].bChannel */ FREQ2FBIN(5825, 0)
1664 /* Data[2].ctlEdges[0].bChannel */ FREQ2FBIN(5190, 0),
1665 /* Data[2].ctlEdges[1].bChannel */ FREQ2FBIN(5230, 0),
1666 /* Data[2].ctlEdges[2].bChannel */ FREQ2FBIN(5270, 0),
1667 /* Data[2].ctlEdges[3].bChannel */ FREQ2FBIN(5310, 0),
1668 /* Data[2].ctlEdges[4].bChannel */ FREQ2FBIN(5510, 0),
1669 /* Data[2].ctlEdges[5].bChannel */ FREQ2FBIN(5550, 0),
1670 /* Data[2].ctlEdges[6].bChannel */ FREQ2FBIN(5670, 0),
1671 /* Data[2].ctlEdges[7].bChannel */ FREQ2FBIN(5755, 0)
1675 /* Data[3].ctlEdges[0].bChannel */ FREQ2FBIN(5180, 0),
1676 /* Data[3].ctlEdges[1].bChannel */ FREQ2FBIN(5200, 0),
1677 /* Data[3].ctlEdges[2].bChannel */ FREQ2FBIN(5260, 0),
1678 /* Data[3].ctlEdges[3].bChannel */ FREQ2FBIN(5320, 0),
1679 /* Data[3].ctlEdges[4].bChannel */ FREQ2FBIN(5500, 0),
1680 /* Data[3].ctlEdges[5].bChannel */ FREQ2FBIN(5700, 0),
1681 /* Data[3].ctlEdges[6].bChannel */ 0xFF,
1682 /* Data[3].ctlEdges[7].bChannel */ 0xFF,
1686 /* Data[4].ctlEdges[0].bChannel */ FREQ2FBIN(5180, 0),
1687 /* Data[4].ctlEdges[1].bChannel */ FREQ2FBIN(5260, 0),
1688 /* Data[4].ctlEdges[2].bChannel */ FREQ2FBIN(5500, 0),
1689 /* Data[4].ctlEdges[3].bChannel */ FREQ2FBIN(5700, 0),
1690 /* Data[4].ctlEdges[4].bChannel */ 0xFF,
1691 /* Data[4].ctlEdges[5].bChannel */ 0xFF,
1692 /* Data[4].ctlEdges[6].bChannel */ 0xFF,
1693 /* Data[4].ctlEdges[7].bChannel */ 0xFF,
1697 /* Data[5].ctlEdges[0].bChannel */ FREQ2FBIN(5190, 0),
1698 /* Data[5].ctlEdges[1].bChannel */ FREQ2FBIN(5270, 0),
1699 /* Data[5].ctlEdges[2].bChannel */ FREQ2FBIN(5310, 0),
1700 /* Data[5].ctlEdges[3].bChannel */ FREQ2FBIN(5510, 0),
1701 /* Data[5].ctlEdges[4].bChannel */ FREQ2FBIN(5590, 0),
1702 /* Data[5].ctlEdges[5].bChannel */ FREQ2FBIN(5670, 0),
1703 /* Data[5].ctlEdges[6].bChannel */ 0xFF,
1704 /* Data[5].ctlEdges[7].bChannel */ 0xFF
1708 /* Data[6].ctlEdges[0].bChannel */ FREQ2FBIN(5180, 0),
1709 /* Data[6].ctlEdges[1].bChannel */ FREQ2FBIN(5200, 0),
1710 /* Data[6].ctlEdges[2].bChannel */ FREQ2FBIN(5220, 0),
1711 /* Data[6].ctlEdges[3].bChannel */ FREQ2FBIN(5260, 0),
1712 /* Data[6].ctlEdges[4].bChannel */ FREQ2FBIN(5500, 0),
1713 /* Data[6].ctlEdges[5].bChannel */ FREQ2FBIN(5600, 0),
1714 /* Data[6].ctlEdges[6].bChannel */ FREQ2FBIN(5700, 0),
1715 /* Data[6].ctlEdges[7].bChannel */ FREQ2FBIN(5745, 0)
1719 /* Data[7].ctlEdges[0].bChannel */ FREQ2FBIN(5180, 0),
1720 /* Data[7].ctlEdges[1].bChannel */ FREQ2FBIN(5260, 0),
1721 /* Data[7].ctlEdges[2].bChannel */ FREQ2FBIN(5320, 0),
1722 /* Data[7].ctlEdges[3].bChannel */ FREQ2FBIN(5500, 0),
1723 /* Data[7].ctlEdges[4].bChannel */ FREQ2FBIN(5560, 0),
1724 /* Data[7].ctlEdges[5].bChannel */ FREQ2FBIN(5700, 0),
1725 /* Data[7].ctlEdges[6].bChannel */ FREQ2FBIN(5745, 0),
1726 /* Data[7].ctlEdges[7].bChannel */ FREQ2FBIN(5825, 0)
1730 /* Data[8].ctlEdges[0].bChannel */ FREQ2FBIN(5190, 0),
1731 /* Data[8].ctlEdges[1].bChannel */ FREQ2FBIN(5230, 0),
1732 /* Data[8].ctlEdges[2].bChannel */ FREQ2FBIN(5270, 0),
1733 /* Data[8].ctlEdges[3].bChannel */ FREQ2FBIN(5510, 0),
1734 /* Data[8].ctlEdges[4].bChannel */ FREQ2FBIN(5550, 0),
1735 /* Data[8].ctlEdges[5].bChannel */ FREQ2FBIN(5670, 0),
1736 /* Data[8].ctlEdges[6].bChannel */ FREQ2FBIN(5755, 0),
1737 /* Data[8].ctlEdges[7].bChannel */ FREQ2FBIN(5795, 0)
1740 .ctlPowerData_5G = {
1743 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
1744 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 0),
1749 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
1750 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 0),
1755 CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 1),
1756 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
1761 CTL(60, 0), CTL(60, 1), CTL(60, 1), CTL(60, 0),
1762 CTL(60, 1), CTL(60, 0), CTL(60, 0), CTL(60, 0),
1767 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 0),
1768 CTL(60, 0), CTL(60, 0), CTL(60, 0), CTL(60, 0),
1773 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
1774 CTL(60, 1), CTL(60, 0), CTL(60, 0), CTL(60, 0),
1779 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
1780 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
1785 CTL(60, 1), CTL(60, 1), CTL(60, 0), CTL(60, 1),
1786 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 0),
1791 CTL(60, 1), CTL(60, 0), CTL(60, 1), CTL(60, 1),
1792 CTL(60, 1), CTL(60, 1), CTL(60, 0), CTL(60, 1),
1799 static const struct ar9300_eeprom ar9300_x112 = {
1801 .templateVersion = 5,
1802 .macAddr = {0x00, 0x03, 0x7f, 0x0, 0x0, 0x0},
1803 .custData = {"x112-041-f0000"},
1805 .regDmn = { LE16(0), LE16(0x1f) },
1806 .txrxMask = 0x77, /* 4 bits tx and 4 bits rx */
1808 .opFlags = AR5416_OPFLAGS_11G | AR5416_OPFLAGS_11A,
1812 .blueToothOptions = 0,
1814 .deviceType = 5, /* takes lower byte in eeprom location */
1815 .pwrTableOffset = AR9300_PWR_TABLE_OFFSET,
1816 .params_for_tuning_caps = {0, 0},
1817 .featureEnable = 0x0d,
1819 * bit0 - enable tx temp comp - disabled
1820 * bit1 - enable tx volt comp - disabled
1821 * bit2 - enable fastclock - enabled
1822 * bit3 - enable doubling - enabled
1823 * bit4 - enable internal regulator - disabled
1824 * bit5 - enable pa predistortion - disabled
1826 .miscConfiguration = 0, /* bit0 - turn down drivestrength */
1827 .eepromWriteEnableGpio = 6,
1828 .wlanDisableGpio = 0,
1830 .rxBandSelectGpio = 0xff,
1835 /* ar9300_modal_eep_header 2g */
1836 /* 4 idle,t1,t2,b(4 bits per setting) */
1837 .antCtrlCommon = LE32(0x110),
1838 /* 4 ra1l1, ra2l1, ra1l2, ra2l2, ra12 */
1839 .antCtrlCommon2 = LE32(0x22222),
1842 * antCtrlChain[ar9300_max_chains]; 6 idle, t, r,
1843 * rx1, rx12, b (2 bits each)
1845 .antCtrlChain = { LE16(0x10), LE16(0x10), LE16(0x10) },
1848 * xatten1DB[AR9300_max_chains]; 3 xatten1_db
1849 * for ar9280 (0xa20c/b20c 5:0)
1851 .xatten1DB = {0x1b, 0x1b, 0x1b},
1854 * xatten1Margin[ar9300_max_chains]; 3 xatten1_margin
1855 * for ar9280 (0xa20c/b20c 16:12
1857 .xatten1Margin = {0x15, 0x15, 0x15},
1862 * spurChans[OSPrey_eeprom_modal_sPURS]; spur
1863 * channels in usual fbin coding format
1865 .spurChans = {FREQ2FBIN(2464, 1), 0, 0, 0, 0},
1868 * noiseFloorThreshch[ar9300_max_cHAINS]; 3 Check
1869 * if the register is per chain
1871 .noiseFloorThreshCh = {-1, 0, 0},
1872 .ob = {1, 1, 1},/* 3 chain */
1873 .db_stage2 = {1, 1, 1}, /* 3 chain */
1874 .db_stage3 = {0, 0, 0},
1875 .db_stage4 = {0, 0, 0},
1877 .txFrameToDataStart = 0x0e,
1878 .txFrameToPaOn = 0x0e,
1879 .txClip = 3, /* 4 bits tx_clip, 4 bits dac_scale_cck */
1881 .switchSettling = 0x2c,
1882 .adcDesiredSize = -30,
1885 .txFrameToXpaOn = 0xe,
1887 .papdRateMaskHt20 = LE32(0x0c80c080),
1888 .papdRateMaskHt40 = LE32(0x0080c080),
1890 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
1894 .ant_div_control = 0,
1895 .future = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}
1902 /* ar9300_cal_data_per_freq_op_loop 2g */
1904 { {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0} },
1905 { {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0} },
1906 { {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0} },
1908 .calTarget_freqbin_Cck = {
1912 .calTarget_freqbin_2G = {
1917 .calTarget_freqbin_2GHT20 = {
1922 .calTarget_freqbin_2GHT40 = {
1927 .calTargetPowerCck = {
1928 /* 1L-5L,5S,11L,11s */
1929 { {38, 38, 38, 38} },
1930 { {38, 38, 38, 38} },
1932 .calTargetPower2G = {
1934 { {38, 38, 36, 34} },
1935 { {38, 38, 36, 34} },
1936 { {38, 38, 34, 32} },
1938 .calTargetPower2GHT20 = {
1939 { {36, 36, 36, 36, 36, 34, 34, 32, 30, 28, 28, 28, 28, 26} },
1940 { {36, 36, 36, 36, 36, 34, 36, 34, 32, 30, 30, 30, 28, 26} },
1941 { {36, 36, 36, 36, 36, 34, 34, 32, 30, 28, 28, 28, 28, 26} },
1943 .calTargetPower2GHT40 = {
1944 { {36, 36, 36, 36, 34, 32, 32, 30, 28, 26, 26, 26, 26, 24} },
1945 { {36, 36, 36, 36, 34, 32, 34, 32, 30, 28, 28, 28, 28, 24} },
1946 { {36, 36, 36, 36, 34, 32, 32, 30, 28, 26, 26, 26, 26, 24} },
1949 0x11, 0x12, 0x15, 0x17, 0x41, 0x42,
1950 0x45, 0x47, 0x31, 0x32, 0x35, 0x37,
1980 /* Data[4].ctledges[0].bchannel */ FREQ2FBIN(2412, 1),
1981 /* Data[4].ctledges[1].bchannel */ FREQ2FBIN(2417, 1),
1982 /* Data[4].ctledges[2].bchannel */ FREQ2FBIN(2472, 1),
1983 /* Data[4].ctledges[3].bchannel */ FREQ2FBIN(2484, 1),
1987 /* Data[5].ctledges[0].bchannel */ FREQ2FBIN(2412, 1),
1988 /* Data[5].ctledges[1].bchannel */ FREQ2FBIN(2417, 1),
1989 /* Data[5].ctledges[2].bchannel */ FREQ2FBIN(2472, 1),
1994 /* Data[6].ctledges[0].bchannel */ FREQ2FBIN(2412, 1),
1995 /* Data[6].ctledges[1].bchannel */ FREQ2FBIN(2417, 1),
2001 /* Data[7].ctledges[0].bchannel */ FREQ2FBIN(2422, 1),
2002 /* Data[7].ctledges[1].bchannel */ FREQ2FBIN(2427, 1),
2003 /* Data[7].ctledges[2].bchannel */ FREQ2FBIN(2447, 1),
2004 /* Data[7].ctledges[3].bchannel */ FREQ2FBIN(2462, 1),
2008 /* Data[8].ctledges[0].bchannel */ FREQ2FBIN(2412, 1),
2009 /* Data[8].ctledges[1].bchannel */ FREQ2FBIN(2417, 1),
2010 /* Data[8].ctledges[2].bchannel */ FREQ2FBIN(2472, 1),
2014 /* Data[9].ctledges[0].bchannel */ FREQ2FBIN(2412, 1),
2015 /* Data[9].ctledges[1].bchannel */ FREQ2FBIN(2417, 1),
2016 /* Data[9].ctledges[2].bchannel */ FREQ2FBIN(2472, 1),
2021 /* Data[10].ctledges[0].bchannel */ FREQ2FBIN(2412, 1),
2022 /* Data[10].ctledges[1].bchannel */ FREQ2FBIN(2417, 1),
2023 /* Data[10].ctledges[2].bchannel */ FREQ2FBIN(2472, 1),
2028 /* Data[11].ctledges[0].bchannel */ FREQ2FBIN(2422, 1),
2029 /* Data[11].ctledges[1].bchannel */ FREQ2FBIN(2427, 1),
2030 /* Data[11].ctledges[2].bchannel */ FREQ2FBIN(2447, 1),
2031 /* Data[11].ctledges[3].bchannel */ FREQ2FBIN(2462, 1),
2034 .ctlPowerData_2G = {
2035 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
2036 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
2037 { { CTL(60, 1), CTL(60, 0), CTL(60, 0), CTL(60, 1) } },
2039 { { CTL(60, 1), CTL(60, 0), CTL(0, 0), CTL(0, 0) } },
2040 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
2041 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
2043 { { CTL(60, 0), CTL(60, 1), CTL(60, 1), CTL(60, 0) } },
2044 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
2045 { { 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, 0), CTL(60, 1), CTL(60, 1), CTL(60, 1) } },
2049 { { CTL(60, 0), CTL(60, 1), CTL(60, 1), CTL(60, 1) } },
2052 /* 4 idle,t1,t2,b (4 bits per setting) */
2053 .antCtrlCommon = LE32(0x110),
2054 /* 4 ra1l1, ra2l1, ra1l2,ra2l2,ra12 */
2055 .antCtrlCommon2 = LE32(0x22222),
2056 /* antCtrlChain 6 idle, t,r,rx1,rx12,b (2 bits each) */
2058 LE16(0x0), LE16(0x0), LE16(0x0),
2060 /* xatten1DB 3 xatten1_db for ar9280 (0xa20c/b20c 5:0) */
2061 .xatten1DB = {0x13, 0x19, 0x17},
2064 * xatten1Margin[ar9300_max_chains]; 3 xatten1_margin
2065 * for merlin (0xa20c/b20c 16:12
2067 .xatten1Margin = {0x19, 0x19, 0x19},
2070 /* spurChans spur channels in usual fbin coding format */
2071 .spurChans = {0, 0, 0, 0, 0},
2072 /* noiseFloorThreshch check if the register is per chain */
2073 .noiseFloorThreshCh = {-1, 0, 0},
2074 .ob = {3, 3, 3}, /* 3 chain */
2075 .db_stage2 = {3, 3, 3}, /* 3 chain */
2076 .db_stage3 = {3, 3, 3}, /* doesn't exist for 2G */
2077 .db_stage4 = {3, 3, 3}, /* don't exist for 2G */
2079 .txFrameToDataStart = 0x0e,
2080 .txFrameToPaOn = 0x0e,
2081 .txClip = 3, /* 4 bits tx_clip, 4 bits dac_scale_cck */
2083 .switchSettling = 0x2d,
2084 .adcDesiredSize = -30,
2087 .txFrameToXpaOn = 0xe,
2089 .papdRateMaskHt20 = LE32(0x0cf0e0e0),
2090 .papdRateMaskHt40 = LE32(0x6cf0e0e0),
2092 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
2097 .tempSlopeHigh = 105,
2098 .xatten1DBLow = {0x10, 0x14, 0x10},
2099 .xatten1MarginLow = {0x19, 0x19 , 0x19},
2100 .xatten1DBHigh = {0x1d, 0x20, 0x24},
2101 .xatten1MarginHigh = {0x10, 0x10, 0x10}
2146 .calTarget_freqbin_5G = {
2156 .calTarget_freqbin_5GHT20 = {
2166 .calTarget_freqbin_5GHT40 = {
2176 .calTargetPower5G = {
2178 { {32, 32, 28, 26} },
2179 { {32, 32, 28, 26} },
2180 { {32, 32, 28, 26} },
2181 { {32, 32, 26, 24} },
2182 { {32, 32, 26, 24} },
2183 { {32, 32, 24, 22} },
2184 { {30, 30, 24, 22} },
2185 { {30, 30, 24, 22} },
2187 .calTargetPower5GHT20 = {
2189 * 0_8_16,1-3_9-11_17-19,
2190 * 4,5,6,7,12,13,14,15,20,21,22,23
2192 { {32, 32, 32, 32, 28, 26, 32, 28, 26, 24, 24, 24, 22, 22} },
2193 { {32, 32, 32, 32, 28, 26, 32, 28, 26, 24, 24, 24, 22, 22} },
2194 { {32, 32, 32, 32, 28, 26, 32, 28, 26, 24, 24, 24, 22, 22} },
2195 { {32, 32, 32, 32, 28, 26, 32, 26, 24, 22, 22, 22, 20, 20} },
2196 { {32, 32, 32, 32, 28, 26, 32, 26, 24, 22, 20, 18, 16, 16} },
2197 { {32, 32, 32, 32, 28, 26, 32, 24, 20, 16, 18, 16, 14, 14} },
2198 { {30, 30, 30, 30, 28, 26, 30, 24, 20, 16, 18, 16, 14, 14} },
2199 { {30, 30, 30, 30, 28, 26, 30, 24, 20, 16, 18, 16, 14, 14} },
2201 .calTargetPower5GHT40 = {
2203 * 0_8_16,1-3_9-11_17-19,
2204 * 4,5,6,7,12,13,14,15,20,21,22,23
2206 { {32, 32, 32, 30, 28, 26, 30, 28, 26, 24, 24, 24, 22, 22} },
2207 { {32, 32, 32, 30, 28, 26, 30, 28, 26, 24, 24, 24, 22, 22} },
2208 { {32, 32, 32, 30, 28, 26, 30, 28, 26, 24, 24, 24, 22, 22} },
2209 { {32, 32, 32, 30, 28, 26, 30, 26, 24, 22, 22, 22, 20, 20} },
2210 { {32, 32, 32, 30, 28, 26, 30, 26, 24, 22, 20, 18, 16, 16} },
2211 { {32, 32, 32, 30, 28, 26, 30, 22, 20, 16, 18, 16, 14, 14} },
2212 { {30, 30, 30, 30, 28, 26, 30, 22, 20, 16, 18, 16, 14, 14} },
2213 { {30, 30, 30, 30, 28, 26, 30, 22, 20, 16, 18, 16, 14, 14} },
2216 0x10, 0x16, 0x18, 0x40, 0x46,
2217 0x48, 0x30, 0x36, 0x38
2221 /* Data[0].ctledges[0].bchannel */ FREQ2FBIN(5180, 0),
2222 /* Data[0].ctledges[1].bchannel */ FREQ2FBIN(5260, 0),
2223 /* Data[0].ctledges[2].bchannel */ FREQ2FBIN(5280, 0),
2224 /* Data[0].ctledges[3].bchannel */ FREQ2FBIN(5500, 0),
2225 /* Data[0].ctledges[4].bchannel */ FREQ2FBIN(5600, 0),
2226 /* Data[0].ctledges[5].bchannel */ FREQ2FBIN(5700, 0),
2227 /* Data[0].ctledges[6].bchannel */ FREQ2FBIN(5745, 0),
2228 /* Data[0].ctledges[7].bchannel */ FREQ2FBIN(5825, 0)
2231 /* Data[1].ctledges[0].bchannel */ FREQ2FBIN(5180, 0),
2232 /* Data[1].ctledges[1].bchannel */ FREQ2FBIN(5260, 0),
2233 /* Data[1].ctledges[2].bchannel */ FREQ2FBIN(5280, 0),
2234 /* Data[1].ctledges[3].bchannel */ FREQ2FBIN(5500, 0),
2235 /* Data[1].ctledges[4].bchannel */ FREQ2FBIN(5520, 0),
2236 /* Data[1].ctledges[5].bchannel */ FREQ2FBIN(5700, 0),
2237 /* Data[1].ctledges[6].bchannel */ FREQ2FBIN(5745, 0),
2238 /* Data[1].ctledges[7].bchannel */ FREQ2FBIN(5825, 0)
2242 /* Data[2].ctledges[0].bchannel */ FREQ2FBIN(5190, 0),
2243 /* Data[2].ctledges[1].bchannel */ FREQ2FBIN(5230, 0),
2244 /* Data[2].ctledges[2].bchannel */ FREQ2FBIN(5270, 0),
2245 /* Data[2].ctledges[3].bchannel */ FREQ2FBIN(5310, 0),
2246 /* Data[2].ctledges[4].bchannel */ FREQ2FBIN(5510, 0),
2247 /* Data[2].ctledges[5].bchannel */ FREQ2FBIN(5550, 0),
2248 /* Data[2].ctledges[6].bchannel */ FREQ2FBIN(5670, 0),
2249 /* Data[2].ctledges[7].bchannel */ FREQ2FBIN(5755, 0)
2253 /* Data[3].ctledges[0].bchannel */ FREQ2FBIN(5180, 0),
2254 /* Data[3].ctledges[1].bchannel */ FREQ2FBIN(5200, 0),
2255 /* Data[3].ctledges[2].bchannel */ FREQ2FBIN(5260, 0),
2256 /* Data[3].ctledges[3].bchannel */ FREQ2FBIN(5320, 0),
2257 /* Data[3].ctledges[4].bchannel */ FREQ2FBIN(5500, 0),
2258 /* Data[3].ctledges[5].bchannel */ FREQ2FBIN(5700, 0),
2259 /* Data[3].ctledges[6].bchannel */ 0xFF,
2260 /* Data[3].ctledges[7].bchannel */ 0xFF,
2264 /* Data[4].ctledges[0].bchannel */ FREQ2FBIN(5180, 0),
2265 /* Data[4].ctledges[1].bchannel */ FREQ2FBIN(5260, 0),
2266 /* Data[4].ctledges[2].bchannel */ FREQ2FBIN(5500, 0),
2267 /* Data[4].ctledges[3].bchannel */ FREQ2FBIN(5700, 0),
2268 /* Data[4].ctledges[4].bchannel */ 0xFF,
2269 /* Data[4].ctledges[5].bchannel */ 0xFF,
2270 /* Data[4].ctledges[6].bchannel */ 0xFF,
2271 /* Data[4].ctledges[7].bchannel */ 0xFF,
2275 /* Data[5].ctledges[0].bchannel */ FREQ2FBIN(5190, 0),
2276 /* Data[5].ctledges[1].bchannel */ FREQ2FBIN(5270, 0),
2277 /* Data[5].ctledges[2].bchannel */ FREQ2FBIN(5310, 0),
2278 /* Data[5].ctledges[3].bchannel */ FREQ2FBIN(5510, 0),
2279 /* Data[5].ctledges[4].bchannel */ FREQ2FBIN(5590, 0),
2280 /* Data[5].ctledges[5].bchannel */ FREQ2FBIN(5670, 0),
2281 /* Data[5].ctledges[6].bchannel */ 0xFF,
2282 /* Data[5].ctledges[7].bchannel */ 0xFF
2286 /* Data[6].ctledges[0].bchannel */ FREQ2FBIN(5180, 0),
2287 /* Data[6].ctledges[1].bchannel */ FREQ2FBIN(5200, 0),
2288 /* Data[6].ctledges[2].bchannel */ FREQ2FBIN(5220, 0),
2289 /* Data[6].ctledges[3].bchannel */ FREQ2FBIN(5260, 0),
2290 /* Data[6].ctledges[4].bchannel */ FREQ2FBIN(5500, 0),
2291 /* Data[6].ctledges[5].bchannel */ FREQ2FBIN(5600, 0),
2292 /* Data[6].ctledges[6].bchannel */ FREQ2FBIN(5700, 0),
2293 /* Data[6].ctledges[7].bchannel */ FREQ2FBIN(5745, 0)
2297 /* Data[7].ctledges[0].bchannel */ FREQ2FBIN(5180, 0),
2298 /* Data[7].ctledges[1].bchannel */ FREQ2FBIN(5260, 0),
2299 /* Data[7].ctledges[2].bchannel */ FREQ2FBIN(5320, 0),
2300 /* Data[7].ctledges[3].bchannel */ FREQ2FBIN(5500, 0),
2301 /* Data[7].ctledges[4].bchannel */ FREQ2FBIN(5560, 0),
2302 /* Data[7].ctledges[5].bchannel */ FREQ2FBIN(5700, 0),
2303 /* Data[7].ctledges[6].bchannel */ FREQ2FBIN(5745, 0),
2304 /* Data[7].ctledges[7].bchannel */ FREQ2FBIN(5825, 0)
2308 /* Data[8].ctledges[0].bchannel */ FREQ2FBIN(5190, 0),
2309 /* Data[8].ctledges[1].bchannel */ FREQ2FBIN(5230, 0),
2310 /* Data[8].ctledges[2].bchannel */ FREQ2FBIN(5270, 0),
2311 /* Data[8].ctledges[3].bchannel */ FREQ2FBIN(5510, 0),
2312 /* Data[8].ctledges[4].bchannel */ FREQ2FBIN(5550, 0),
2313 /* Data[8].ctledges[5].bchannel */ FREQ2FBIN(5670, 0),
2314 /* Data[8].ctledges[6].bchannel */ FREQ2FBIN(5755, 0),
2315 /* Data[8].ctledges[7].bchannel */ FREQ2FBIN(5795, 0)
2318 .ctlPowerData_5G = {
2321 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
2322 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 0),
2327 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
2328 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 0),
2333 CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 1),
2334 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
2339 CTL(60, 0), CTL(60, 1), CTL(60, 1), CTL(60, 0),
2340 CTL(60, 1), CTL(60, 0), CTL(60, 0), CTL(60, 0),
2345 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 0),
2346 CTL(60, 0), CTL(60, 0), CTL(60, 0), CTL(60, 0),
2351 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
2352 CTL(60, 1), CTL(60, 0), CTL(60, 0), CTL(60, 0),
2357 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
2358 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
2363 CTL(60, 1), CTL(60, 1), CTL(60, 0), CTL(60, 1),
2364 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 0),
2369 CTL(60, 1), CTL(60, 0), CTL(60, 1), CTL(60, 1),
2370 CTL(60, 1), CTL(60, 1), CTL(60, 0), CTL(60, 1),
2376 static const struct ar9300_eeprom ar9300_h116 = {
2378 .templateVersion = 4,
2379 .macAddr = {0x00, 0x03, 0x7f, 0x0, 0x0, 0x0},
2380 .custData = {"h116-041-f0000"},
2382 .regDmn = { LE16(0), LE16(0x1f) },
2383 .txrxMask = 0x33, /* 4 bits tx and 4 bits rx */
2385 .opFlags = AR5416_OPFLAGS_11G | AR5416_OPFLAGS_11A,
2389 .blueToothOptions = 0,
2391 .deviceType = 5, /* takes lower byte in eeprom location */
2392 .pwrTableOffset = AR9300_PWR_TABLE_OFFSET,
2393 .params_for_tuning_caps = {0, 0},
2394 .featureEnable = 0x0d,
2396 * bit0 - enable tx temp comp - disabled
2397 * bit1 - enable tx volt comp - disabled
2398 * bit2 - enable fastClock - enabled
2399 * bit3 - enable doubling - enabled
2400 * bit4 - enable internal regulator - disabled
2401 * bit5 - enable pa predistortion - disabled
2403 .miscConfiguration = 0, /* bit0 - turn down drivestrength */
2404 .eepromWriteEnableGpio = 6,
2405 .wlanDisableGpio = 0,
2407 .rxBandSelectGpio = 0xff,
2412 /* ar9300_modal_eep_header 2g */
2413 /* 4 idle,t1,t2,b(4 bits per setting) */
2414 .antCtrlCommon = LE32(0x110),
2415 /* 4 ra1l1, ra2l1, ra1l2, ra2l2, ra12 */
2416 .antCtrlCommon2 = LE32(0x44444),
2419 * antCtrlChain[AR9300_MAX_CHAINS]; 6 idle, t, r,
2420 * rx1, rx12, b (2 bits each)
2422 .antCtrlChain = { LE16(0x10), LE16(0x10), LE16(0x10) },
2425 * xatten1DB[AR9300_MAX_CHAINS]; 3 xatten1_db
2426 * for ar9280 (0xa20c/b20c 5:0)
2428 .xatten1DB = {0x1f, 0x1f, 0x1f},
2431 * xatten1Margin[AR9300_MAX_CHAINS]; 3 xatten1_margin
2432 * for ar9280 (0xa20c/b20c 16:12
2434 .xatten1Margin = {0x12, 0x12, 0x12},
2439 * spurChans[OSPREY_EEPROM_MODAL_SPURS]; spur
2440 * channels in usual fbin coding format
2442 .spurChans = {FREQ2FBIN(2464, 1), 0, 0, 0, 0},
2445 * noiseFloorThreshCh[AR9300_MAX_CHAINS]; 3 Check
2446 * if the register is per chain
2448 .noiseFloorThreshCh = {-1, 0, 0},
2449 .ob = {1, 1, 1},/* 3 chain */
2450 .db_stage2 = {1, 1, 1}, /* 3 chain */
2451 .db_stage3 = {0, 0, 0},
2452 .db_stage4 = {0, 0, 0},
2454 .txFrameToDataStart = 0x0e,
2455 .txFrameToPaOn = 0x0e,
2456 .txClip = 3, /* 4 bits tx_clip, 4 bits dac_scale_cck */
2458 .switchSettling = 0x2c,
2459 .adcDesiredSize = -30,
2462 .txFrameToXpaOn = 0xe,
2464 .papdRateMaskHt20 = LE32(0x0c80C080),
2465 .papdRateMaskHt40 = LE32(0x0080C080),
2467 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
2471 .ant_div_control = 0,
2472 .future = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}
2479 /* ar9300_cal_data_per_freq_op_loop 2g */
2481 { {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0} },
2482 { {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0} },
2483 { {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0}, {0, 0, 0, 0, 0, 0} },
2485 .calTarget_freqbin_Cck = {
2489 .calTarget_freqbin_2G = {
2494 .calTarget_freqbin_2GHT20 = {
2499 .calTarget_freqbin_2GHT40 = {
2504 .calTargetPowerCck = {
2505 /* 1L-5L,5S,11L,11S */
2506 { {34, 34, 34, 34} },
2507 { {34, 34, 34, 34} },
2509 .calTargetPower2G = {
2511 { {34, 34, 32, 32} },
2512 { {34, 34, 32, 32} },
2513 { {34, 34, 32, 32} },
2515 .calTargetPower2GHT20 = {
2516 { {32, 32, 32, 32, 32, 30, 32, 32, 30, 28, 0, 0, 0, 0} },
2517 { {32, 32, 32, 32, 32, 30, 32, 32, 30, 28, 0, 0, 0, 0} },
2518 { {32, 32, 32, 32, 32, 30, 32, 32, 30, 28, 0, 0, 0, 0} },
2520 .calTargetPower2GHT40 = {
2521 { {30, 30, 30, 30, 30, 28, 30, 30, 28, 26, 0, 0, 0, 0} },
2522 { {30, 30, 30, 30, 30, 28, 30, 30, 28, 26, 0, 0, 0, 0} },
2523 { {30, 30, 30, 30, 30, 28, 30, 30, 28, 26, 0, 0, 0, 0} },
2526 0x11, 0x12, 0x15, 0x17, 0x41, 0x42,
2527 0x45, 0x47, 0x31, 0x32, 0x35, 0x37,
2557 /* Data[4].ctlEdges[0].bChannel */ FREQ2FBIN(2412, 1),
2558 /* Data[4].ctlEdges[1].bChannel */ FREQ2FBIN(2417, 1),
2559 /* Data[4].ctlEdges[2].bChannel */ FREQ2FBIN(2472, 1),
2560 /* Data[4].ctlEdges[3].bChannel */ FREQ2FBIN(2484, 1),
2564 /* Data[5].ctlEdges[0].bChannel */ FREQ2FBIN(2412, 1),
2565 /* Data[5].ctlEdges[1].bChannel */ FREQ2FBIN(2417, 1),
2566 /* Data[5].ctlEdges[2].bChannel */ FREQ2FBIN(2472, 1),
2571 /* Data[6].ctlEdges[0].bChannel */ FREQ2FBIN(2412, 1),
2572 /* Data[6].ctlEdges[1].bChannel */ FREQ2FBIN(2417, 1),
2578 /* Data[7].ctlEdges[0].bChannel */ FREQ2FBIN(2422, 1),
2579 /* Data[7].ctlEdges[1].bChannel */ FREQ2FBIN(2427, 1),
2580 /* Data[7].ctlEdges[2].bChannel */ FREQ2FBIN(2447, 1),
2581 /* Data[7].ctlEdges[3].bChannel */ FREQ2FBIN(2462, 1),
2585 /* Data[8].ctlEdges[0].bChannel */ FREQ2FBIN(2412, 1),
2586 /* Data[8].ctlEdges[1].bChannel */ FREQ2FBIN(2417, 1),
2587 /* Data[8].ctlEdges[2].bChannel */ FREQ2FBIN(2472, 1),
2591 /* Data[9].ctlEdges[0].bChannel */ FREQ2FBIN(2412, 1),
2592 /* Data[9].ctlEdges[1].bChannel */ FREQ2FBIN(2417, 1),
2593 /* Data[9].ctlEdges[2].bChannel */ FREQ2FBIN(2472, 1),
2598 /* Data[10].ctlEdges[0].bChannel */ FREQ2FBIN(2412, 1),
2599 /* Data[10].ctlEdges[1].bChannel */ FREQ2FBIN(2417, 1),
2600 /* Data[10].ctlEdges[2].bChannel */ FREQ2FBIN(2472, 1),
2605 /* Data[11].ctlEdges[0].bChannel */ FREQ2FBIN(2422, 1),
2606 /* Data[11].ctlEdges[1].bChannel */ FREQ2FBIN(2427, 1),
2607 /* Data[11].ctlEdges[2].bChannel */ FREQ2FBIN(2447, 1),
2608 /* Data[11].ctlEdges[3].bChannel */ FREQ2FBIN(2462, 1),
2611 .ctlPowerData_2G = {
2612 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
2613 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
2614 { { CTL(60, 1), CTL(60, 0), CTL(60, 0), CTL(60, 1) } },
2616 { { CTL(60, 1), CTL(60, 0), CTL(0, 0), CTL(0, 0) } },
2617 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
2618 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
2620 { { CTL(60, 0), CTL(60, 1), CTL(60, 1), CTL(60, 0) } },
2621 { { CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 0) } },
2622 { { 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, 0), CTL(60, 1), CTL(60, 1), CTL(60, 1) } },
2626 { { CTL(60, 0), CTL(60, 1), CTL(60, 1), CTL(60, 1) } },
2629 /* 4 idle,t1,t2,b (4 bits per setting) */
2630 .antCtrlCommon = LE32(0x220),
2631 /* 4 ra1l1, ra2l1, ra1l2,ra2l2,ra12 */
2632 .antCtrlCommon2 = LE32(0x44444),
2633 /* antCtrlChain 6 idle, t,r,rx1,rx12,b (2 bits each) */
2635 LE16(0x150), LE16(0x150), LE16(0x150),
2637 /* xatten1DB 3 xatten1_db for AR9280 (0xa20c/b20c 5:0) */
2638 .xatten1DB = {0x19, 0x19, 0x19},
2641 * xatten1Margin[AR9300_MAX_CHAINS]; 3 xatten1_margin
2642 * for merlin (0xa20c/b20c 16:12
2644 .xatten1Margin = {0x14, 0x14, 0x14},
2647 /* spurChans spur channels in usual fbin coding format */
2648 .spurChans = {0, 0, 0, 0, 0},
2649 /* noiseFloorThreshCh Check if the register is per chain */
2650 .noiseFloorThreshCh = {-1, 0, 0},
2651 .ob = {3, 3, 3}, /* 3 chain */
2652 .db_stage2 = {3, 3, 3}, /* 3 chain */
2653 .db_stage3 = {3, 3, 3}, /* doesn't exist for 2G */
2654 .db_stage4 = {3, 3, 3}, /* don't exist for 2G */
2656 .txFrameToDataStart = 0x0e,
2657 .txFrameToPaOn = 0x0e,
2658 .txClip = 3, /* 4 bits tx_clip, 4 bits dac_scale_cck */
2660 .switchSettling = 0x2d,
2661 .adcDesiredSize = -30,
2664 .txFrameToXpaOn = 0xe,
2666 .papdRateMaskHt20 = LE32(0x0cf0e0e0),
2667 .papdRateMaskHt40 = LE32(0x6cf0e0e0),
2669 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
2674 .tempSlopeHigh = 50,
2675 .xatten1DBLow = {0, 0, 0},
2676 .xatten1MarginLow = {0, 0, 0},
2677 .xatten1DBHigh = {0, 0, 0},
2678 .xatten1MarginHigh = {0, 0, 0}
2723 .calTarget_freqbin_5G = {
2733 .calTarget_freqbin_5GHT20 = {
2743 .calTarget_freqbin_5GHT40 = {
2753 .calTargetPower5G = {
2755 { {30, 30, 28, 24} },
2756 { {30, 30, 28, 24} },
2757 { {30, 30, 28, 24} },
2758 { {30, 30, 28, 24} },
2759 { {30, 30, 28, 24} },
2760 { {30, 30, 28, 24} },
2761 { {30, 30, 28, 24} },
2762 { {30, 30, 28, 24} },
2764 .calTargetPower5GHT20 = {
2766 * 0_8_16,1-3_9-11_17-19,
2767 * 4,5,6,7,12,13,14,15,20,21,22,23
2769 { {30, 30, 30, 28, 24, 20, 30, 28, 24, 20, 0, 0, 0, 0} },
2770 { {30, 30, 30, 28, 24, 20, 30, 28, 24, 20, 0, 0, 0, 0} },
2771 { {30, 30, 30, 26, 22, 18, 30, 26, 22, 18, 0, 0, 0, 0} },
2772 { {30, 30, 30, 26, 22, 18, 30, 26, 22, 18, 0, 0, 0, 0} },
2773 { {30, 30, 30, 24, 20, 16, 30, 24, 20, 16, 0, 0, 0, 0} },
2774 { {30, 30, 30, 24, 20, 16, 30, 24, 20, 16, 0, 0, 0, 0} },
2775 { {30, 30, 30, 22, 18, 14, 30, 22, 18, 14, 0, 0, 0, 0} },
2776 { {30, 30, 30, 22, 18, 14, 30, 22, 18, 14, 0, 0, 0, 0} },
2778 .calTargetPower5GHT40 = {
2780 * 0_8_16,1-3_9-11_17-19,
2781 * 4,5,6,7,12,13,14,15,20,21,22,23
2783 { {28, 28, 28, 26, 22, 18, 28, 26, 22, 18, 0, 0, 0, 0} },
2784 { {28, 28, 28, 26, 22, 18, 28, 26, 22, 18, 0, 0, 0, 0} },
2785 { {28, 28, 28, 24, 20, 16, 28, 24, 20, 16, 0, 0, 0, 0} },
2786 { {28, 28, 28, 24, 20, 16, 28, 24, 20, 16, 0, 0, 0, 0} },
2787 { {28, 28, 28, 22, 18, 14, 28, 22, 18, 14, 0, 0, 0, 0} },
2788 { {28, 28, 28, 22, 18, 14, 28, 22, 18, 14, 0, 0, 0, 0} },
2789 { {28, 28, 28, 20, 16, 12, 28, 20, 16, 12, 0, 0, 0, 0} },
2790 { {28, 28, 28, 20, 16, 12, 28, 20, 16, 12, 0, 0, 0, 0} },
2793 0x10, 0x16, 0x18, 0x40, 0x46,
2794 0x48, 0x30, 0x36, 0x38
2798 /* Data[0].ctlEdges[0].bChannel */ FREQ2FBIN(5180, 0),
2799 /* Data[0].ctlEdges[1].bChannel */ FREQ2FBIN(5260, 0),
2800 /* Data[0].ctlEdges[2].bChannel */ FREQ2FBIN(5280, 0),
2801 /* Data[0].ctlEdges[3].bChannel */ FREQ2FBIN(5500, 0),
2802 /* Data[0].ctlEdges[4].bChannel */ FREQ2FBIN(5600, 0),
2803 /* Data[0].ctlEdges[5].bChannel */ FREQ2FBIN(5700, 0),
2804 /* Data[0].ctlEdges[6].bChannel */ FREQ2FBIN(5745, 0),
2805 /* Data[0].ctlEdges[7].bChannel */ FREQ2FBIN(5825, 0)
2808 /* Data[1].ctlEdges[0].bChannel */ FREQ2FBIN(5180, 0),
2809 /* Data[1].ctlEdges[1].bChannel */ FREQ2FBIN(5260, 0),
2810 /* Data[1].ctlEdges[2].bChannel */ FREQ2FBIN(5280, 0),
2811 /* Data[1].ctlEdges[3].bChannel */ FREQ2FBIN(5500, 0),
2812 /* Data[1].ctlEdges[4].bChannel */ FREQ2FBIN(5520, 0),
2813 /* Data[1].ctlEdges[5].bChannel */ FREQ2FBIN(5700, 0),
2814 /* Data[1].ctlEdges[6].bChannel */ FREQ2FBIN(5745, 0),
2815 /* Data[1].ctlEdges[7].bChannel */ FREQ2FBIN(5825, 0)
2819 /* Data[2].ctlEdges[0].bChannel */ FREQ2FBIN(5190, 0),
2820 /* Data[2].ctlEdges[1].bChannel */ FREQ2FBIN(5230, 0),
2821 /* Data[2].ctlEdges[2].bChannel */ FREQ2FBIN(5270, 0),
2822 /* Data[2].ctlEdges[3].bChannel */ FREQ2FBIN(5310, 0),
2823 /* Data[2].ctlEdges[4].bChannel */ FREQ2FBIN(5510, 0),
2824 /* Data[2].ctlEdges[5].bChannel */ FREQ2FBIN(5550, 0),
2825 /* Data[2].ctlEdges[6].bChannel */ FREQ2FBIN(5670, 0),
2826 /* Data[2].ctlEdges[7].bChannel */ FREQ2FBIN(5755, 0)
2830 /* Data[3].ctlEdges[0].bChannel */ FREQ2FBIN(5180, 0),
2831 /* Data[3].ctlEdges[1].bChannel */ FREQ2FBIN(5200, 0),
2832 /* Data[3].ctlEdges[2].bChannel */ FREQ2FBIN(5260, 0),
2833 /* Data[3].ctlEdges[3].bChannel */ FREQ2FBIN(5320, 0),
2834 /* Data[3].ctlEdges[4].bChannel */ FREQ2FBIN(5500, 0),
2835 /* Data[3].ctlEdges[5].bChannel */ FREQ2FBIN(5700, 0),
2836 /* Data[3].ctlEdges[6].bChannel */ 0xFF,
2837 /* Data[3].ctlEdges[7].bChannel */ 0xFF,
2841 /* Data[4].ctlEdges[0].bChannel */ FREQ2FBIN(5180, 0),
2842 /* Data[4].ctlEdges[1].bChannel */ FREQ2FBIN(5260, 0),
2843 /* Data[4].ctlEdges[2].bChannel */ FREQ2FBIN(5500, 0),
2844 /* Data[4].ctlEdges[3].bChannel */ FREQ2FBIN(5700, 0),
2845 /* Data[4].ctlEdges[4].bChannel */ 0xFF,
2846 /* Data[4].ctlEdges[5].bChannel */ 0xFF,
2847 /* Data[4].ctlEdges[6].bChannel */ 0xFF,
2848 /* Data[4].ctlEdges[7].bChannel */ 0xFF,
2852 /* Data[5].ctlEdges[0].bChannel */ FREQ2FBIN(5190, 0),
2853 /* Data[5].ctlEdges[1].bChannel */ FREQ2FBIN(5270, 0),
2854 /* Data[5].ctlEdges[2].bChannel */ FREQ2FBIN(5310, 0),
2855 /* Data[5].ctlEdges[3].bChannel */ FREQ2FBIN(5510, 0),
2856 /* Data[5].ctlEdges[4].bChannel */ FREQ2FBIN(5590, 0),
2857 /* Data[5].ctlEdges[5].bChannel */ FREQ2FBIN(5670, 0),
2858 /* Data[5].ctlEdges[6].bChannel */ 0xFF,
2859 /* Data[5].ctlEdges[7].bChannel */ 0xFF
2863 /* Data[6].ctlEdges[0].bChannel */ FREQ2FBIN(5180, 0),
2864 /* Data[6].ctlEdges[1].bChannel */ FREQ2FBIN(5200, 0),
2865 /* Data[6].ctlEdges[2].bChannel */ FREQ2FBIN(5220, 0),
2866 /* Data[6].ctlEdges[3].bChannel */ FREQ2FBIN(5260, 0),
2867 /* Data[6].ctlEdges[4].bChannel */ FREQ2FBIN(5500, 0),
2868 /* Data[6].ctlEdges[5].bChannel */ FREQ2FBIN(5600, 0),
2869 /* Data[6].ctlEdges[6].bChannel */ FREQ2FBIN(5700, 0),
2870 /* Data[6].ctlEdges[7].bChannel */ FREQ2FBIN(5745, 0)
2874 /* Data[7].ctlEdges[0].bChannel */ FREQ2FBIN(5180, 0),
2875 /* Data[7].ctlEdges[1].bChannel */ FREQ2FBIN(5260, 0),
2876 /* Data[7].ctlEdges[2].bChannel */ FREQ2FBIN(5320, 0),
2877 /* Data[7].ctlEdges[3].bChannel */ FREQ2FBIN(5500, 0),
2878 /* Data[7].ctlEdges[4].bChannel */ FREQ2FBIN(5560, 0),
2879 /* Data[7].ctlEdges[5].bChannel */ FREQ2FBIN(5700, 0),
2880 /* Data[7].ctlEdges[6].bChannel */ FREQ2FBIN(5745, 0),
2881 /* Data[7].ctlEdges[7].bChannel */ FREQ2FBIN(5825, 0)
2885 /* Data[8].ctlEdges[0].bChannel */ FREQ2FBIN(5190, 0),
2886 /* Data[8].ctlEdges[1].bChannel */ FREQ2FBIN(5230, 0),
2887 /* Data[8].ctlEdges[2].bChannel */ FREQ2FBIN(5270, 0),
2888 /* Data[8].ctlEdges[3].bChannel */ FREQ2FBIN(5510, 0),
2889 /* Data[8].ctlEdges[4].bChannel */ FREQ2FBIN(5550, 0),
2890 /* Data[8].ctlEdges[5].bChannel */ FREQ2FBIN(5670, 0),
2891 /* Data[8].ctlEdges[6].bChannel */ FREQ2FBIN(5755, 0),
2892 /* Data[8].ctlEdges[7].bChannel */ FREQ2FBIN(5795, 0)
2895 .ctlPowerData_5G = {
2898 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
2899 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 0),
2904 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
2905 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 0),
2910 CTL(60, 0), CTL(60, 1), CTL(60, 0), CTL(60, 1),
2911 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
2916 CTL(60, 0), CTL(60, 1), CTL(60, 1), CTL(60, 0),
2917 CTL(60, 1), CTL(60, 0), CTL(60, 0), CTL(60, 0),
2922 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 0),
2923 CTL(60, 0), CTL(60, 0), CTL(60, 0), CTL(60, 0),
2928 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
2929 CTL(60, 1), CTL(60, 0), CTL(60, 0), CTL(60, 0),
2934 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
2935 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 1),
2940 CTL(60, 1), CTL(60, 1), CTL(60, 0), CTL(60, 1),
2941 CTL(60, 1), CTL(60, 1), CTL(60, 1), CTL(60, 0),
2946 CTL(60, 1), CTL(60, 0), CTL(60, 1), CTL(60, 1),
2947 CTL(60, 1), CTL(60, 1), CTL(60, 0), CTL(60, 1),
2954 static const struct ar9300_eeprom *ar9300_eep_templates[] = {
2962 static const struct ar9300_eeprom *ar9003_eeprom_struct_find_by_id(int id)
2964 #define N_LOOP (sizeof(ar9300_eep_templates) / sizeof(ar9300_eep_templates[0]))
2967 for (it = 0; it < N_LOOP; it++)
2968 if (ar9300_eep_templates[it]->templateVersion == id)
2969 return ar9300_eep_templates[it];
2975 static u16 ath9k_hw_fbin2freq(u8 fbin, bool is2GHz)
2977 if (fbin == AR5416_BCHAN_UNUSED)
2980 return (u16) ((is2GHz) ? (2300 + fbin) : (4800 + 5 * fbin));
2983 static int ath9k_hw_ar9300_check_eeprom(struct ath_hw *ah)
2988 static int interpolate(int x, int xa, int xb, int ya, int yb)
2990 int bf, factor, plus;
2992 bf = 2 * (yb - ya) * (x - xa) / (xb - xa);
2995 return ya + factor + plus;
2998 static u32 ath9k_hw_ar9300_get_eeprom(struct ath_hw *ah,
2999 enum eeprom_param param)
3001 struct ar9300_eeprom *eep = &ah->eeprom.ar9300_eep;
3002 struct ar9300_base_eep_hdr *pBase = &eep->baseEepHeader;
3006 return eep->macAddr[0] << 8 | eep->macAddr[1];
3008 return eep->macAddr[2] << 8 | eep->macAddr[3];
3010 return eep->macAddr[4] << 8 | eep->macAddr[5];
3012 return le16_to_cpu(pBase->regDmn[0]);
3014 return le16_to_cpu(pBase->regDmn[1]);
3016 return pBase->deviceCap;
3018 return pBase->opCapFlags.opFlags;
3020 return pBase->rfSilent;
3022 return (pBase->txrxMask >> 4) & 0xf;
3024 return pBase->txrxMask & 0xf;
3025 case EEP_DRIVE_STRENGTH:
3026 #define AR9300_EEP_BASE_DRIV_STRENGTH 0x1
3027 return pBase->miscConfiguration & AR9300_EEP_BASE_DRIV_STRENGTH;
3028 case EEP_INTERNAL_REGULATOR:
3029 /* Bit 4 is internal regulator flag */
3030 return (pBase->featureEnable & 0x10) >> 4;
3032 return le32_to_cpu(pBase->swreg);
3034 return !!(pBase->featureEnable & BIT(5));
3035 case EEP_CHAIN_MASK_REDUCE:
3036 return (pBase->miscConfiguration >> 0x3) & 0x1;
3037 case EEP_ANT_DIV_CTL1:
3038 return le32_to_cpu(eep->base_ext1.ant_div_control);
3044 static bool ar9300_eeprom_read_byte(struct ath_common *common, int address,
3049 if (unlikely(!ath9k_hw_nvram_read(common, address / 2, &val)))
3052 *buffer = (val >> (8 * (address % 2))) & 0xff;
3056 static bool ar9300_eeprom_read_word(struct ath_common *common, int address,
3061 if (unlikely(!ath9k_hw_nvram_read(common, address / 2, &val)))
3064 buffer[0] = val >> 8;
3065 buffer[1] = val & 0xff;
3070 static bool ar9300_read_eeprom(struct ath_hw *ah, int address, u8 *buffer,
3073 struct ath_common *common = ath9k_hw_common(ah);
3076 if ((address < 0) || ((address + count) / 2 > AR9300_EEPROM_SIZE - 1)) {
3077 ath_dbg(common, ATH_DBG_EEPROM,
3078 "eeprom address not in range\n");
3083 * Since we're reading the bytes in reverse order from a little-endian
3084 * word stream, an even address means we only use the lower half of
3085 * the 16-bit word at that address
3087 if (address % 2 == 0) {
3088 if (!ar9300_eeprom_read_byte(common, address--, buffer++))
3094 for (i = 0; i < count / 2; i++) {
3095 if (!ar9300_eeprom_read_word(common, address, buffer))
3103 if (!ar9300_eeprom_read_byte(common, address, buffer))
3109 ath_dbg(common, ATH_DBG_EEPROM,
3110 "unable to read eeprom region at offset %d\n", address);
3114 static bool ar9300_otp_read_word(struct ath_hw *ah, int addr, u32 *data)
3116 REG_READ(ah, AR9300_OTP_BASE + (4 * addr));
3118 if (!ath9k_hw_wait(ah, AR9300_OTP_STATUS, AR9300_OTP_STATUS_TYPE,
3119 AR9300_OTP_STATUS_VALID, 1000))
3122 *data = REG_READ(ah, AR9300_OTP_READ_DATA);
3126 static bool ar9300_read_otp(struct ath_hw *ah, int address, u8 *buffer,
3132 for (i = 0; i < count; i++) {
3133 int offset = 8 * ((address - i) % 4);
3134 if (!ar9300_otp_read_word(ah, (address - i) / 4, &data))
3137 buffer[i] = (data >> offset) & 0xff;
3144 static void ar9300_comp_hdr_unpack(u8 *best, int *code, int *reference,
3145 int *length, int *major, int *minor)
3147 unsigned long value[4];
3153 *code = ((value[0] >> 5) & 0x0007);
3154 *reference = (value[0] & 0x001f) | ((value[1] >> 2) & 0x0020);
3155 *length = ((value[1] << 4) & 0x07f0) | ((value[2] >> 4) & 0x000f);
3156 *major = (value[2] & 0x000f);
3157 *minor = (value[3] & 0x00ff);
3160 static u16 ar9300_comp_cksum(u8 *data, int dsize)
3162 int it, checksum = 0;
3164 for (it = 0; it < dsize; it++) {
3165 checksum += data[it];
3172 static bool ar9300_uncompress_block(struct ath_hw *ah,
3182 struct ath_common *common = ath9k_hw_common(ah);
3186 for (it = 0; it < size; it += (length+2)) {
3190 length = block[it+1];
3193 if (length > 0 && spot >= 0 && spot+length <= mdataSize) {
3194 ath_dbg(common, ATH_DBG_EEPROM,
3195 "Restore at %d: spot=%d offset=%d length=%d\n",
3196 it, spot, offset, length);
3197 memcpy(&mptr[spot], &block[it+2], length);
3199 } else if (length > 0) {
3200 ath_dbg(common, ATH_DBG_EEPROM,
3201 "Bad restore at %d: spot=%d offset=%d length=%d\n",
3202 it, spot, offset, length);
3209 static int ar9300_compress_decision(struct ath_hw *ah,
3214 u8 *word, int length, int mdata_size)
3216 struct ath_common *common = ath9k_hw_common(ah);
3218 const struct ar9300_eeprom *eep = NULL;
3222 if (length != mdata_size) {
3223 ath_dbg(common, ATH_DBG_EEPROM,
3224 "EEPROM structure size mismatch memory=%d eeprom=%d\n",
3225 mdata_size, length);
3228 memcpy(mptr, (u8 *) (word + COMP_HDR_LEN), length);
3229 ath_dbg(common, ATH_DBG_EEPROM,
3230 "restored eeprom %d: uncompressed, length %d\n",
3233 case _CompressBlock:
3234 if (reference == 0) {
3237 eep = ar9003_eeprom_struct_find_by_id(reference);
3239 ath_dbg(common, ATH_DBG_EEPROM,
3240 "cant find reference eeprom struct %d\n",
3244 memcpy(mptr, eep, mdata_size);
3246 ath_dbg(common, ATH_DBG_EEPROM,
3247 "restore eeprom %d: block, reference %d, length %d\n",
3248 it, reference, length);
3249 ar9300_uncompress_block(ah, mptr, mdata_size,
3250 (u8 *) (word + COMP_HDR_LEN), length);
3253 ath_dbg(common, ATH_DBG_EEPROM,
3254 "unknown compression code %d\n", code);
3260 typedef bool (*eeprom_read_op)(struct ath_hw *ah, int address, u8 *buffer,
3263 static bool ar9300_check_header(void *data)
3266 return !(*word == 0 || *word == ~0);
3269 static bool ar9300_check_eeprom_header(struct ath_hw *ah, eeprom_read_op read,
3274 if (!read(ah, base_addr, header, 4))
3277 return ar9300_check_header(header);
3280 static int ar9300_eeprom_restore_flash(struct ath_hw *ah, u8 *mptr,
3283 struct ath_common *common = ath9k_hw_common(ah);
3284 u16 *data = (u16 *) mptr;
3287 for (i = 0; i < mdata_size / 2; i++, data++)
3288 ath9k_hw_nvram_read(common, i, data);
3293 * Read the configuration data from the eeprom.
3294 * The data can be put in any specified memory buffer.
3296 * Returns -1 on error.
3297 * Returns address of next memory location on success.
3299 static int ar9300_eeprom_restore_internal(struct ath_hw *ah,
3300 u8 *mptr, int mdata_size)
3307 int reference, length, major, minor;
3310 u16 checksum, mchecksum;
3311 struct ath_common *common = ath9k_hw_common(ah);
3312 eeprom_read_op read;
3314 if (ath9k_hw_use_flash(ah))
3315 return ar9300_eeprom_restore_flash(ah, mptr, mdata_size);
3317 word = kzalloc(2048, GFP_KERNEL);
3321 memcpy(mptr, &ar9300_default, mdata_size);
3323 read = ar9300_read_eeprom;
3324 if (AR_SREV_9485(ah))
3325 cptr = AR9300_BASE_ADDR_4K;
3327 cptr = AR9300_BASE_ADDR;
3328 ath_dbg(common, ATH_DBG_EEPROM,
3329 "Trying EEPROM accesss at Address 0x%04x\n", cptr);
3330 if (ar9300_check_eeprom_header(ah, read, cptr))
3333 cptr = AR9300_BASE_ADDR_512;
3334 ath_dbg(common, ATH_DBG_EEPROM,
3335 "Trying EEPROM accesss at Address 0x%04x\n", cptr);
3336 if (ar9300_check_eeprom_header(ah, read, cptr))
3339 read = ar9300_read_otp;
3340 cptr = AR9300_BASE_ADDR;
3341 ath_dbg(common, ATH_DBG_EEPROM,
3342 "Trying OTP accesss at Address 0x%04x\n", cptr);
3343 if (ar9300_check_eeprom_header(ah, read, cptr))
3346 cptr = AR9300_BASE_ADDR_512;
3347 ath_dbg(common, ATH_DBG_EEPROM,
3348 "Trying OTP accesss at Address 0x%04x\n", cptr);
3349 if (ar9300_check_eeprom_header(ah, read, cptr))
3355 ath_dbg(common, ATH_DBG_EEPROM, "Found valid EEPROM data\n");
3357 for (it = 0; it < MSTATE; it++) {
3358 if (!read(ah, cptr, word, COMP_HDR_LEN))
3361 if (!ar9300_check_header(word))
3364 ar9300_comp_hdr_unpack(word, &code, &reference,
3365 &length, &major, &minor);
3366 ath_dbg(common, ATH_DBG_EEPROM,
3367 "Found block at %x: code=%d ref=%d length=%d major=%d minor=%d\n",
3368 cptr, code, reference, length, major, minor);
3369 if ((!AR_SREV_9485(ah) && length >= 1024) ||
3370 (AR_SREV_9485(ah) && length >= (4 * 1024))) {
3371 ath_dbg(common, ATH_DBG_EEPROM,
3372 "Skipping bad header\n");
3373 cptr -= COMP_HDR_LEN;
3378 read(ah, cptr, word, COMP_HDR_LEN + osize + COMP_CKSUM_LEN);
3379 checksum = ar9300_comp_cksum(&word[COMP_HDR_LEN], length);
3380 mchecksum = word[COMP_HDR_LEN + osize] |
3381 (word[COMP_HDR_LEN + osize + 1] << 8);
3382 ath_dbg(common, ATH_DBG_EEPROM,
3383 "checksum %x %x\n", checksum, mchecksum);
3384 if (checksum == mchecksum) {
3385 ar9300_compress_decision(ah, it, code, reference, mptr,
3386 word, length, mdata_size);
3388 ath_dbg(common, ATH_DBG_EEPROM,
3389 "skipping block with bad checksum\n");
3391 cptr -= (COMP_HDR_LEN + osize + COMP_CKSUM_LEN);
3403 * Restore the configuration structure by reading the eeprom.
3404 * This function destroys any existing in-memory structure
3407 static bool ath9k_hw_ar9300_fill_eeprom(struct ath_hw *ah)
3409 u8 *mptr = (u8 *) &ah->eeprom.ar9300_eep;
3411 if (ar9300_eeprom_restore_internal(ah, mptr,
3412 sizeof(struct ar9300_eeprom)) < 0)
3418 /* XXX: review hardware docs */
3419 static int ath9k_hw_ar9300_get_eeprom_ver(struct ath_hw *ah)
3421 return ah->eeprom.ar9300_eep.eepromVersion;
3424 /* XXX: could be read from the eepromVersion, not sure yet */
3425 static int ath9k_hw_ar9300_get_eeprom_rev(struct ath_hw *ah)
3430 static s32 ar9003_hw_xpa_bias_level_get(struct ath_hw *ah, bool is2ghz)
3432 struct ar9300_eeprom *eep = &ah->eeprom.ar9300_eep;
3435 return eep->modalHeader2G.xpaBiasLvl;
3437 return eep->modalHeader5G.xpaBiasLvl;
3440 static void ar9003_hw_xpa_bias_level_apply(struct ath_hw *ah, bool is2ghz)
3442 int bias = ar9003_hw_xpa_bias_level_get(ah, is2ghz);
3444 if (AR_SREV_9485(ah))
3445 REG_RMW_FIELD(ah, AR_CH0_TOP2, AR_CH0_TOP2_XPABIASLVL, bias);
3447 REG_RMW_FIELD(ah, AR_CH0_TOP, AR_CH0_TOP_XPABIASLVL, bias);
3448 REG_RMW_FIELD(ah, AR_CH0_THERM, AR_CH0_THERM_XPABIASLVL_MSB,
3450 REG_RMW_FIELD(ah, AR_CH0_THERM, AR_CH0_THERM_XPASHORT2GND, 1);
3454 static u32 ar9003_hw_ant_ctrl_common_get(struct ath_hw *ah, bool is2ghz)
3456 struct ar9300_eeprom *eep = &ah->eeprom.ar9300_eep;
3460 val = eep->modalHeader2G.antCtrlCommon;
3462 val = eep->modalHeader5G.antCtrlCommon;
3463 return le32_to_cpu(val);
3466 static u32 ar9003_hw_ant_ctrl_common_2_get(struct ath_hw *ah, bool is2ghz)
3468 struct ar9300_eeprom *eep = &ah->eeprom.ar9300_eep;
3472 val = eep->modalHeader2G.antCtrlCommon2;
3474 val = eep->modalHeader5G.antCtrlCommon2;
3475 return le32_to_cpu(val);
3478 static u16 ar9003_hw_ant_ctrl_chain_get(struct ath_hw *ah,
3482 struct ar9300_eeprom *eep = &ah->eeprom.ar9300_eep;
3485 if (chain >= 0 && chain < AR9300_MAX_CHAINS) {
3487 val = eep->modalHeader2G.antCtrlChain[chain];
3489 val = eep->modalHeader5G.antCtrlChain[chain];
3492 return le16_to_cpu(val);
3495 static void ar9003_hw_ant_ctrl_apply(struct ath_hw *ah, bool is2ghz)
3497 u32 value = ar9003_hw_ant_ctrl_common_get(ah, is2ghz);
3498 REG_RMW_FIELD(ah, AR_PHY_SWITCH_COM, AR_SWITCH_TABLE_COM_ALL, value);
3500 value = ar9003_hw_ant_ctrl_common_2_get(ah, is2ghz);
3501 REG_RMW_FIELD(ah, AR_PHY_SWITCH_COM_2, AR_SWITCH_TABLE_COM2_ALL, value);
3503 value = ar9003_hw_ant_ctrl_chain_get(ah, 0, is2ghz);
3504 REG_RMW_FIELD(ah, AR_PHY_SWITCH_CHAIN_0, AR_SWITCH_TABLE_ALL, value);
3506 if (!AR_SREV_9485(ah)) {
3507 value = ar9003_hw_ant_ctrl_chain_get(ah, 1, is2ghz);
3508 REG_RMW_FIELD(ah, AR_PHY_SWITCH_CHAIN_1, AR_SWITCH_TABLE_ALL,
3511 value = ar9003_hw_ant_ctrl_chain_get(ah, 2, is2ghz);
3512 REG_RMW_FIELD(ah, AR_PHY_SWITCH_CHAIN_2, AR_SWITCH_TABLE_ALL,
3516 if (AR_SREV_9485(ah)) {
3517 value = ath9k_hw_ar9300_get_eeprom(ah, EEP_ANT_DIV_CTL1);
3518 REG_RMW_FIELD(ah, AR_PHY_MC_GAIN_CTRL, AR_ANT_DIV_CTRL_ALL,
3520 REG_RMW_FIELD(ah, AR_PHY_MC_GAIN_CTRL, AR_ANT_DIV_ENABLE,
3522 REG_RMW_FIELD(ah, AR_PHY_CCK_DETECT, AR_FAST_DIV_ENABLE,
3527 static void ar9003_hw_drive_strength_apply(struct ath_hw *ah)
3532 drive_strength = ath9k_hw_ar9300_get_eeprom(ah, EEP_DRIVE_STRENGTH);
3534 if (!drive_strength)
3537 reg = REG_READ(ah, AR_PHY_65NM_CH0_BIAS1);
3545 REG_WRITE(ah, AR_PHY_65NM_CH0_BIAS1, reg);
3547 reg = REG_READ(ah, AR_PHY_65NM_CH0_BIAS2);
3558 REG_WRITE(ah, AR_PHY_65NM_CH0_BIAS2, reg);
3560 reg = REG_READ(ah, AR_PHY_65NM_CH0_BIAS4);
3565 REG_WRITE(ah, AR_PHY_65NM_CH0_BIAS4, reg);
3568 static u16 ar9003_hw_atten_chain_get(struct ath_hw *ah, int chain,
3569 struct ath9k_channel *chan)
3573 struct ar9300_eeprom *eep = &ah->eeprom.ar9300_eep;
3575 if (chain >= 0 && chain < 3) {
3576 if (IS_CHAN_2GHZ(chan))
3577 return eep->modalHeader2G.xatten1DB[chain];
3578 else if (eep->base_ext2.xatten1DBLow[chain] != 0) {
3579 t[0] = eep->base_ext2.xatten1DBLow[chain];
3581 t[1] = eep->modalHeader5G.xatten1DB[chain];
3583 t[2] = eep->base_ext2.xatten1DBHigh[chain];
3585 value = ar9003_hw_power_interpolate((s32) chan->channel,
3589 return eep->modalHeader5G.xatten1DB[chain];
3596 static u16 ar9003_hw_atten_chain_get_margin(struct ath_hw *ah, int chain,
3597 struct ath9k_channel *chan)
3601 struct ar9300_eeprom *eep = &ah->eeprom.ar9300_eep;
3603 if (chain >= 0 && chain < 3) {
3604 if (IS_CHAN_2GHZ(chan))
3605 return eep->modalHeader2G.xatten1Margin[chain];
3606 else if (eep->base_ext2.xatten1MarginLow[chain] != 0) {
3607 t[0] = eep->base_ext2.xatten1MarginLow[chain];
3609 t[1] = eep->modalHeader5G.xatten1Margin[chain];
3611 t[2] = eep->base_ext2.xatten1MarginHigh[chain];
3613 value = ar9003_hw_power_interpolate((s32) chan->channel,
3617 return eep->modalHeader5G.xatten1Margin[chain];
3623 static void ar9003_hw_atten_apply(struct ath_hw *ah, struct ath9k_channel *chan)
3627 unsigned long ext_atten_reg[3] = {AR_PHY_EXT_ATTEN_CTL_0,
3628 AR_PHY_EXT_ATTEN_CTL_1,
3629 AR_PHY_EXT_ATTEN_CTL_2,
3632 /* Test value. if 0 then attenuation is unused. Don't load anything. */
3633 for (i = 0; i < 3; i++) {
3634 value = ar9003_hw_atten_chain_get(ah, i, chan);
3635 REG_RMW_FIELD(ah, ext_atten_reg[i],
3636 AR_PHY_EXT_ATTEN_CTL_XATTEN1_DB, value);
3638 value = ar9003_hw_atten_chain_get_margin(ah, i, chan);
3639 REG_RMW_FIELD(ah, ext_atten_reg[i],
3640 AR_PHY_EXT_ATTEN_CTL_XATTEN1_MARGIN, value);
3644 static bool is_pmu_set(struct ath_hw *ah, u32 pmu_reg, int pmu_set)
3648 while (pmu_set != REG_READ(ah, pmu_reg)) {
3651 REG_WRITE(ah, pmu_reg, pmu_set);
3658 static void ar9003_hw_internal_regulator_apply(struct ath_hw *ah)
3660 int internal_regulator =
3661 ath9k_hw_ar9300_get_eeprom(ah, EEP_INTERNAL_REGULATOR);
3663 if (internal_regulator) {
3664 if (AR_SREV_9485(ah)) {
3667 reg_pmu_set = REG_READ(ah, AR_PHY_PMU2) & ~AR_PHY_PMU2_PGM;
3668 REG_WRITE(ah, AR_PHY_PMU2, reg_pmu_set);
3669 if (!is_pmu_set(ah, AR_PHY_PMU2, reg_pmu_set))
3672 reg_pmu_set = (5 << 1) | (7 << 4) | (1 << 8) |
3673 (7 << 14) | (6 << 17) | (1 << 20) |
3674 (3 << 24) | (1 << 28);
3676 REG_WRITE(ah, AR_PHY_PMU1, reg_pmu_set);
3677 if (!is_pmu_set(ah, AR_PHY_PMU1, reg_pmu_set))
3680 reg_pmu_set = (REG_READ(ah, AR_PHY_PMU2) & ~0xFFC00000)
3682 REG_WRITE(ah, AR_PHY_PMU2, reg_pmu_set);
3683 if (!is_pmu_set(ah, AR_PHY_PMU2, reg_pmu_set))
3686 reg_pmu_set = (REG_READ(ah, AR_PHY_PMU2) & ~0x00200000)
3688 REG_WRITE(ah, AR_PHY_PMU2, reg_pmu_set);
3689 if (!is_pmu_set(ah, AR_PHY_PMU2, reg_pmu_set))
3692 /* Internal regulator is ON. Write swreg register. */
3693 int swreg = ath9k_hw_ar9300_get_eeprom(ah, EEP_SWREG);
3694 REG_WRITE(ah, AR_RTC_REG_CONTROL1,
3695 REG_READ(ah, AR_RTC_REG_CONTROL1) &
3696 (~AR_RTC_REG_CONTROL1_SWREG_PROGRAM));
3697 REG_WRITE(ah, AR_RTC_REG_CONTROL0, swreg);
3698 /* Set REG_CONTROL1.SWREG_PROGRAM */
3699 REG_WRITE(ah, AR_RTC_REG_CONTROL1,
3701 AR_RTC_REG_CONTROL1) |
3702 AR_RTC_REG_CONTROL1_SWREG_PROGRAM);
3705 if (AR_SREV_9485(ah)) {
3706 REG_RMW_FIELD(ah, AR_PHY_PMU2, AR_PHY_PMU2_PGM, 0);
3707 while (REG_READ_FIELD(ah, AR_PHY_PMU2,
3711 REG_RMW_FIELD(ah, AR_PHY_PMU1, AR_PHY_PMU1_PWD, 0x1);
3712 while (!REG_READ_FIELD(ah, AR_PHY_PMU1,
3715 REG_RMW_FIELD(ah, AR_PHY_PMU2, AR_PHY_PMU2_PGM, 0x1);
3716 while (!REG_READ_FIELD(ah, AR_PHY_PMU2,
3720 REG_WRITE(ah, AR_RTC_SLEEP_CLK,
3723 AR_RTC_FORCE_SWREG_PRD));
3728 static void ar9003_hw_apply_tuning_caps(struct ath_hw *ah)
3730 struct ar9300_eeprom *eep = &ah->eeprom.ar9300_eep;
3731 u8 tuning_caps_param = eep->baseEepHeader.params_for_tuning_caps[0];
3733 if (eep->baseEepHeader.featureEnable & 0x40) {
3734 tuning_caps_param &= 0x7f;
3735 REG_RMW_FIELD(ah, AR_CH0_XTAL, AR_CH0_XTAL_CAPINDAC,
3737 REG_RMW_FIELD(ah, AR_CH0_XTAL, AR_CH0_XTAL_CAPOUTDAC,
3742 static void ath9k_hw_ar9300_set_board_values(struct ath_hw *ah,
3743 struct ath9k_channel *chan)
3745 ar9003_hw_xpa_bias_level_apply(ah, IS_CHAN_2GHZ(chan));
3746 ar9003_hw_ant_ctrl_apply(ah, IS_CHAN_2GHZ(chan));
3747 ar9003_hw_drive_strength_apply(ah);
3748 ar9003_hw_atten_apply(ah, chan);
3749 ar9003_hw_internal_regulator_apply(ah);
3750 if (AR_SREV_9485(ah))
3751 ar9003_hw_apply_tuning_caps(ah);
3754 static void ath9k_hw_ar9300_set_addac(struct ath_hw *ah,
3755 struct ath9k_channel *chan)
3760 * Returns the interpolated y value corresponding to the specified x value
3761 * from the np ordered pairs of data (px,py).
3762 * The pairs do not have to be in any order.
3763 * If the specified x value is less than any of the px,
3764 * the returned y value is equal to the py for the lowest px.
3765 * If the specified x value is greater than any of the px,
3766 * the returned y value is equal to the py for the highest px.
3768 static int ar9003_hw_power_interpolate(int32_t x,
3769 int32_t *px, int32_t *py, u_int16_t np)
3772 int lx = 0, ly = 0, lhave = 0;
3773 int hx = 0, hy = 0, hhave = 0;
3780 /* identify best lower and higher x calibration measurement */
3781 for (ip = 0; ip < np; ip++) {
3784 /* this measurement is higher than our desired x */
3786 if (!hhave || dx > (x - hx)) {
3787 /* new best higher x measurement */
3793 /* this measurement is lower than our desired x */
3795 if (!lhave || dx < (x - lx)) {
3796 /* new best lower x measurement */
3804 /* the low x is good */
3806 /* so is the high x */
3808 /* they're the same, so just pick one */
3811 else /* interpolate */
3812 y = interpolate(x, lx, hx, ly, hy);
3813 } else /* only low is good, use it */
3815 } else if (hhave) /* only high is good, use it */
3817 else /* nothing is good,this should never happen unless np=0, ???? */
3822 static u8 ar9003_hw_eeprom_get_tgt_pwr(struct ath_hw *ah,
3823 u16 rateIndex, u16 freq, bool is2GHz)
3826 s32 targetPowerArray[AR9300_NUM_5G_20_TARGET_POWERS];
3827 s32 freqArray[AR9300_NUM_5G_20_TARGET_POWERS];
3828 struct ar9300_eeprom *eep = &ah->eeprom.ar9300_eep;
3829 struct cal_tgt_pow_legacy *pEepromTargetPwr;
3833 numPiers = AR9300_NUM_2G_20_TARGET_POWERS;
3834 pEepromTargetPwr = eep->calTargetPower2G;
3835 pFreqBin = eep->calTarget_freqbin_2G;
3837 numPiers = AR9300_NUM_5G_20_TARGET_POWERS;
3838 pEepromTargetPwr = eep->calTargetPower5G;
3839 pFreqBin = eep->calTarget_freqbin_5G;
3843 * create array of channels and targetpower from
3844 * targetpower piers stored on eeprom
3846 for (i = 0; i < numPiers; i++) {
3847 freqArray[i] = FBIN2FREQ(pFreqBin[i], is2GHz);
3848 targetPowerArray[i] = pEepromTargetPwr[i].tPow2x[rateIndex];
3851 /* interpolate to get target power for given frequency */
3852 return (u8) ar9003_hw_power_interpolate((s32) freq,
3854 targetPowerArray, numPiers);
3857 static u8 ar9003_hw_eeprom_get_ht20_tgt_pwr(struct ath_hw *ah,
3859 u16 freq, bool is2GHz)
3862 s32 targetPowerArray[AR9300_NUM_5G_20_TARGET_POWERS];
3863 s32 freqArray[AR9300_NUM_5G_20_TARGET_POWERS];
3864 struct ar9300_eeprom *eep = &ah->eeprom.ar9300_eep;
3865 struct cal_tgt_pow_ht *pEepromTargetPwr;
3869 numPiers = AR9300_NUM_2G_20_TARGET_POWERS;
3870 pEepromTargetPwr = eep->calTargetPower2GHT20;
3871 pFreqBin = eep->calTarget_freqbin_2GHT20;
3873 numPiers = AR9300_NUM_5G_20_TARGET_POWERS;
3874 pEepromTargetPwr = eep->calTargetPower5GHT20;
3875 pFreqBin = eep->calTarget_freqbin_5GHT20;
3879 * create array of channels and targetpower
3880 * from targetpower piers stored on eeprom
3882 for (i = 0; i < numPiers; i++) {
3883 freqArray[i] = FBIN2FREQ(pFreqBin[i], is2GHz);
3884 targetPowerArray[i] = pEepromTargetPwr[i].tPow2x[rateIndex];
3887 /* interpolate to get target power for given frequency */
3888 return (u8) ar9003_hw_power_interpolate((s32) freq,
3890 targetPowerArray, numPiers);
3893 static u8 ar9003_hw_eeprom_get_ht40_tgt_pwr(struct ath_hw *ah,
3895 u16 freq, bool is2GHz)
3898 s32 targetPowerArray[AR9300_NUM_5G_40_TARGET_POWERS];
3899 s32 freqArray[AR9300_NUM_5G_40_TARGET_POWERS];
3900 struct ar9300_eeprom *eep = &ah->eeprom.ar9300_eep;
3901 struct cal_tgt_pow_ht *pEepromTargetPwr;
3905 numPiers = AR9300_NUM_2G_40_TARGET_POWERS;
3906 pEepromTargetPwr = eep->calTargetPower2GHT40;
3907 pFreqBin = eep->calTarget_freqbin_2GHT40;
3909 numPiers = AR9300_NUM_5G_40_TARGET_POWERS;
3910 pEepromTargetPwr = eep->calTargetPower5GHT40;
3911 pFreqBin = eep->calTarget_freqbin_5GHT40;
3915 * create array of channels and targetpower from
3916 * targetpower piers stored on eeprom
3918 for (i = 0; i < numPiers; i++) {
3919 freqArray[i] = FBIN2FREQ(pFreqBin[i], is2GHz);
3920 targetPowerArray[i] = pEepromTargetPwr[i].tPow2x[rateIndex];
3923 /* interpolate to get target power for given frequency */
3924 return (u8) ar9003_hw_power_interpolate((s32) freq,
3926 targetPowerArray, numPiers);
3929 static u8 ar9003_hw_eeprom_get_cck_tgt_pwr(struct ath_hw *ah,
3930 u16 rateIndex, u16 freq)
3932 u16 numPiers = AR9300_NUM_2G_CCK_TARGET_POWERS, i;
3933 s32 targetPowerArray[AR9300_NUM_2G_CCK_TARGET_POWERS];
3934 s32 freqArray[AR9300_NUM_2G_CCK_TARGET_POWERS];
3935 struct ar9300_eeprom *eep = &ah->eeprom.ar9300_eep;
3936 struct cal_tgt_pow_legacy *pEepromTargetPwr = eep->calTargetPowerCck;
3937 u8 *pFreqBin = eep->calTarget_freqbin_Cck;
3940 * create array of channels and targetpower from
3941 * targetpower piers stored on eeprom
3943 for (i = 0; i < numPiers; i++) {
3944 freqArray[i] = FBIN2FREQ(pFreqBin[i], 1);
3945 targetPowerArray[i] = pEepromTargetPwr[i].tPow2x[rateIndex];
3948 /* interpolate to get target power for given frequency */
3949 return (u8) ar9003_hw_power_interpolate((s32) freq,
3951 targetPowerArray, numPiers);
3954 /* Set tx power registers to array of values passed in */
3955 static int ar9003_hw_tx_power_regwrite(struct ath_hw *ah, u8 * pPwrArray)
3957 #define POW_SM(_r, _s) (((_r) & 0x3f) << (_s))
3958 /* make sure forced gain is not set */
3959 REG_WRITE(ah, 0xa458, 0);
3961 /* Write the OFDM power per rate set */
3963 /* 6 (LSB), 9, 12, 18 (MSB) */
3964 REG_WRITE(ah, 0xa3c0,
3965 POW_SM(pPwrArray[ALL_TARGET_LEGACY_6_24], 24) |
3966 POW_SM(pPwrArray[ALL_TARGET_LEGACY_6_24], 16) |
3967 POW_SM(pPwrArray[ALL_TARGET_LEGACY_6_24], 8) |
3968 POW_SM(pPwrArray[ALL_TARGET_LEGACY_6_24], 0));
3970 /* 24 (LSB), 36, 48, 54 (MSB) */
3971 REG_WRITE(ah, 0xa3c4,
3972 POW_SM(pPwrArray[ALL_TARGET_LEGACY_54], 24) |
3973 POW_SM(pPwrArray[ALL_TARGET_LEGACY_48], 16) |
3974 POW_SM(pPwrArray[ALL_TARGET_LEGACY_36], 8) |
3975 POW_SM(pPwrArray[ALL_TARGET_LEGACY_6_24], 0));
3977 /* Write the CCK power per rate set */
3979 /* 1L (LSB), reserved, 2L, 2S (MSB) */
3980 REG_WRITE(ah, 0xa3c8,
3981 POW_SM(pPwrArray[ALL_TARGET_LEGACY_1L_5L], 24) |
3982 POW_SM(pPwrArray[ALL_TARGET_LEGACY_1L_5L], 16) |
3983 /* POW_SM(txPowerTimes2, 8) | this is reserved for AR9003 */
3984 POW_SM(pPwrArray[ALL_TARGET_LEGACY_1L_5L], 0));
3986 /* 5.5L (LSB), 5.5S, 11L, 11S (MSB) */
3987 REG_WRITE(ah, 0xa3cc,
3988 POW_SM(pPwrArray[ALL_TARGET_LEGACY_11S], 24) |
3989 POW_SM(pPwrArray[ALL_TARGET_LEGACY_11L], 16) |
3990 POW_SM(pPwrArray[ALL_TARGET_LEGACY_5S], 8) |
3991 POW_SM(pPwrArray[ALL_TARGET_LEGACY_1L_5L], 0)
3994 /* Write the HT20 power per rate set */
3996 /* 0/8/16 (LSB), 1-3/9-11/17-19, 4, 5 (MSB) */
3997 REG_WRITE(ah, 0xa3d0,
3998 POW_SM(pPwrArray[ALL_TARGET_HT20_5], 24) |
3999 POW_SM(pPwrArray[ALL_TARGET_HT20_4], 16) |
4000 POW_SM(pPwrArray[ALL_TARGET_HT20_1_3_9_11_17_19], 8) |
4001 POW_SM(pPwrArray[ALL_TARGET_HT20_0_8_16], 0)
4004 /* 6 (LSB), 7, 12, 13 (MSB) */
4005 REG_WRITE(ah, 0xa3d4,
4006 POW_SM(pPwrArray[ALL_TARGET_HT20_13], 24) |
4007 POW_SM(pPwrArray[ALL_TARGET_HT20_12], 16) |
4008 POW_SM(pPwrArray[ALL_TARGET_HT20_7], 8) |
4009 POW_SM(pPwrArray[ALL_TARGET_HT20_6], 0)
4012 /* 14 (LSB), 15, 20, 21 */
4013 REG_WRITE(ah, 0xa3e4,
4014 POW_SM(pPwrArray[ALL_TARGET_HT20_21], 24) |
4015 POW_SM(pPwrArray[ALL_TARGET_HT20_20], 16) |
4016 POW_SM(pPwrArray[ALL_TARGET_HT20_15], 8) |
4017 POW_SM(pPwrArray[ALL_TARGET_HT20_14], 0)
4020 /* Mixed HT20 and HT40 rates */
4022 /* HT20 22 (LSB), HT20 23, HT40 22, HT40 23 (MSB) */
4023 REG_WRITE(ah, 0xa3e8,
4024 POW_SM(pPwrArray[ALL_TARGET_HT40_23], 24) |
4025 POW_SM(pPwrArray[ALL_TARGET_HT40_22], 16) |
4026 POW_SM(pPwrArray[ALL_TARGET_HT20_23], 8) |
4027 POW_SM(pPwrArray[ALL_TARGET_HT20_22], 0)
4031 * Write the HT40 power per rate set
4032 * correct PAR difference between HT40 and HT20/LEGACY
4033 * 0/8/16 (LSB), 1-3/9-11/17-19, 4, 5 (MSB)
4035 REG_WRITE(ah, 0xa3d8,
4036 POW_SM(pPwrArray[ALL_TARGET_HT40_5], 24) |
4037 POW_SM(pPwrArray[ALL_TARGET_HT40_4], 16) |
4038 POW_SM(pPwrArray[ALL_TARGET_HT40_1_3_9_11_17_19], 8) |
4039 POW_SM(pPwrArray[ALL_TARGET_HT40_0_8_16], 0)
4042 /* 6 (LSB), 7, 12, 13 (MSB) */
4043 REG_WRITE(ah, 0xa3dc,
4044 POW_SM(pPwrArray[ALL_TARGET_HT40_13], 24) |
4045 POW_SM(pPwrArray[ALL_TARGET_HT40_12], 16) |
4046 POW_SM(pPwrArray[ALL_TARGET_HT40_7], 8) |
4047 POW_SM(pPwrArray[ALL_TARGET_HT40_6], 0)
4050 /* 14 (LSB), 15, 20, 21 */
4051 REG_WRITE(ah, 0xa3ec,
4052 POW_SM(pPwrArray[ALL_TARGET_HT40_21], 24) |
4053 POW_SM(pPwrArray[ALL_TARGET_HT40_20], 16) |
4054 POW_SM(pPwrArray[ALL_TARGET_HT40_15], 8) |
4055 POW_SM(pPwrArray[ALL_TARGET_HT40_14], 0)
4062 static void ar9003_hw_set_target_power_eeprom(struct ath_hw *ah, u16 freq,
4063 u8 *targetPowerValT2)
4065 /* XXX: hard code for now, need to get from eeprom struct */
4066 u8 ht40PowerIncForPdadc = 0;
4067 bool is2GHz = false;
4069 struct ath_common *common = ath9k_hw_common(ah);
4074 targetPowerValT2[ALL_TARGET_LEGACY_6_24] =
4075 ar9003_hw_eeprom_get_tgt_pwr(ah, LEGACY_TARGET_RATE_6_24, freq,
4077 targetPowerValT2[ALL_TARGET_LEGACY_36] =
4078 ar9003_hw_eeprom_get_tgt_pwr(ah, LEGACY_TARGET_RATE_36, freq,
4080 targetPowerValT2[ALL_TARGET_LEGACY_48] =
4081 ar9003_hw_eeprom_get_tgt_pwr(ah, LEGACY_TARGET_RATE_48, freq,
4083 targetPowerValT2[ALL_TARGET_LEGACY_54] =
4084 ar9003_hw_eeprom_get_tgt_pwr(ah, LEGACY_TARGET_RATE_54, freq,
4086 targetPowerValT2[ALL_TARGET_LEGACY_1L_5L] =
4087 ar9003_hw_eeprom_get_cck_tgt_pwr(ah, LEGACY_TARGET_RATE_1L_5L,
4089 targetPowerValT2[ALL_TARGET_LEGACY_5S] =
4090 ar9003_hw_eeprom_get_cck_tgt_pwr(ah, LEGACY_TARGET_RATE_5S, freq);
4091 targetPowerValT2[ALL_TARGET_LEGACY_11L] =
4092 ar9003_hw_eeprom_get_cck_tgt_pwr(ah, LEGACY_TARGET_RATE_11L, freq);
4093 targetPowerValT2[ALL_TARGET_LEGACY_11S] =
4094 ar9003_hw_eeprom_get_cck_tgt_pwr(ah, LEGACY_TARGET_RATE_11S, freq);
4095 targetPowerValT2[ALL_TARGET_HT20_0_8_16] =
4096 ar9003_hw_eeprom_get_ht20_tgt_pwr(ah, HT_TARGET_RATE_0_8_16, freq,
4098 targetPowerValT2[ALL_TARGET_HT20_1_3_9_11_17_19] =
4099 ar9003_hw_eeprom_get_ht20_tgt_pwr(ah, HT_TARGET_RATE_1_3_9_11_17_19,
4101 targetPowerValT2[ALL_TARGET_HT20_4] =
4102 ar9003_hw_eeprom_get_ht20_tgt_pwr(ah, HT_TARGET_RATE_4, freq,
4104 targetPowerValT2[ALL_TARGET_HT20_5] =
4105 ar9003_hw_eeprom_get_ht20_tgt_pwr(ah, HT_TARGET_RATE_5, freq,
4107 targetPowerValT2[ALL_TARGET_HT20_6] =
4108 ar9003_hw_eeprom_get_ht20_tgt_pwr(ah, HT_TARGET_RATE_6, freq,
4110 targetPowerValT2[ALL_TARGET_HT20_7] =
4111 ar9003_hw_eeprom_get_ht20_tgt_pwr(ah, HT_TARGET_RATE_7, freq,
4113 targetPowerValT2[ALL_TARGET_HT20_12] =
4114 ar9003_hw_eeprom_get_ht20_tgt_pwr(ah, HT_TARGET_RATE_12, freq,
4116 targetPowerValT2[ALL_TARGET_HT20_13] =
4117 ar9003_hw_eeprom_get_ht20_tgt_pwr(ah, HT_TARGET_RATE_13, freq,
4119 targetPowerValT2[ALL_TARGET_HT20_14] =
4120 ar9003_hw_eeprom_get_ht20_tgt_pwr(ah, HT_TARGET_RATE_14, freq,
4122 targetPowerValT2[ALL_TARGET_HT20_15] =
4123 ar9003_hw_eeprom_get_ht20_tgt_pwr(ah, HT_TARGET_RATE_15, freq,
4125 targetPowerValT2[ALL_TARGET_HT20_20] =
4126 ar9003_hw_eeprom_get_ht20_tgt_pwr(ah, HT_TARGET_RATE_20, freq,
4128 targetPowerValT2[ALL_TARGET_HT20_21] =
4129 ar9003_hw_eeprom_get_ht20_tgt_pwr(ah, HT_TARGET_RATE_21, freq,
4131 targetPowerValT2[ALL_TARGET_HT20_22] =
4132 ar9003_hw_eeprom_get_ht20_tgt_pwr(ah, HT_TARGET_RATE_22, freq,
4134 targetPowerValT2[ALL_TARGET_HT20_23] =
4135 ar9003_hw_eeprom_get_ht20_tgt_pwr(ah, HT_TARGET_RATE_23, freq,
4137 targetPowerValT2[ALL_TARGET_HT40_0_8_16] =
4138 ar9003_hw_eeprom_get_ht40_tgt_pwr(ah, HT_TARGET_RATE_0_8_16, freq,
4139 is2GHz) + ht40PowerIncForPdadc;
4140 targetPowerValT2[ALL_TARGET_HT40_1_3_9_11_17_19] =
4141 ar9003_hw_eeprom_get_ht40_tgt_pwr(ah, HT_TARGET_RATE_1_3_9_11_17_19,
4143 is2GHz) + ht40PowerIncForPdadc;
4144 targetPowerValT2[ALL_TARGET_HT40_4] =
4145 ar9003_hw_eeprom_get_ht40_tgt_pwr(ah, HT_TARGET_RATE_4, freq,
4146 is2GHz) + ht40PowerIncForPdadc;
4147 targetPowerValT2[ALL_TARGET_HT40_5] =
4148 ar9003_hw_eeprom_get_ht40_tgt_pwr(ah, HT_TARGET_RATE_5, freq,
4149 is2GHz) + ht40PowerIncForPdadc;
4150 targetPowerValT2[ALL_TARGET_HT40_6] =
4151 ar9003_hw_eeprom_get_ht40_tgt_pwr(ah, HT_TARGET_RATE_6, freq,
4152 is2GHz) + ht40PowerIncForPdadc;
4153 targetPowerValT2[ALL_TARGET_HT40_7] =
4154 ar9003_hw_eeprom_get_ht40_tgt_pwr(ah, HT_TARGET_RATE_7, freq,
4155 is2GHz) + ht40PowerIncForPdadc;
4156 targetPowerValT2[ALL_TARGET_HT40_12] =
4157 ar9003_hw_eeprom_get_ht40_tgt_pwr(ah, HT_TARGET_RATE_12, freq,
4158 is2GHz) + ht40PowerIncForPdadc;
4159 targetPowerValT2[ALL_TARGET_HT40_13] =
4160 ar9003_hw_eeprom_get_ht40_tgt_pwr(ah, HT_TARGET_RATE_13, freq,
4161 is2GHz) + ht40PowerIncForPdadc;
4162 targetPowerValT2[ALL_TARGET_HT40_14] =
4163 ar9003_hw_eeprom_get_ht40_tgt_pwr(ah, HT_TARGET_RATE_14, freq,
4164 is2GHz) + ht40PowerIncForPdadc;
4165 targetPowerValT2[ALL_TARGET_HT40_15] =
4166 ar9003_hw_eeprom_get_ht40_tgt_pwr(ah, HT_TARGET_RATE_15, freq,
4167 is2GHz) + ht40PowerIncForPdadc;
4168 targetPowerValT2[ALL_TARGET_HT40_20] =
4169 ar9003_hw_eeprom_get_ht40_tgt_pwr(ah, HT_TARGET_RATE_20, freq,
4170 is2GHz) + ht40PowerIncForPdadc;
4171 targetPowerValT2[ALL_TARGET_HT40_21] =
4172 ar9003_hw_eeprom_get_ht40_tgt_pwr(ah, HT_TARGET_RATE_21, freq,
4173 is2GHz) + ht40PowerIncForPdadc;
4174 targetPowerValT2[ALL_TARGET_HT40_22] =
4175 ar9003_hw_eeprom_get_ht40_tgt_pwr(ah, HT_TARGET_RATE_22, freq,
4176 is2GHz) + ht40PowerIncForPdadc;
4177 targetPowerValT2[ALL_TARGET_HT40_23] =
4178 ar9003_hw_eeprom_get_ht40_tgt_pwr(ah, HT_TARGET_RATE_23, freq,
4179 is2GHz) + ht40PowerIncForPdadc;
4181 for (i = 0; i < ar9300RateSize; i++) {
4182 ath_dbg(common, ATH_DBG_EEPROM,
4183 "TPC[%02d] 0x%08x\n", i, targetPowerValT2[i]);
4187 static int ar9003_hw_cal_pier_get(struct ath_hw *ah,
4193 int *ptemperature, int *pvoltage)
4196 struct ar9300_cal_data_per_freq_op_loop *pCalPierStruct;
4198 struct ar9300_eeprom *eep = &ah->eeprom.ar9300_eep;
4199 struct ath_common *common = ath9k_hw_common(ah);
4201 if (ichain >= AR9300_MAX_CHAINS) {
4202 ath_dbg(common, ATH_DBG_EEPROM,
4203 "Invalid chain index, must be less than %d\n",
4208 if (mode) { /* 5GHz */
4209 if (ipier >= AR9300_NUM_5G_CAL_PIERS) {
4210 ath_dbg(common, ATH_DBG_EEPROM,
4211 "Invalid 5GHz cal pier index, must be less than %d\n",
4212 AR9300_NUM_5G_CAL_PIERS);
4215 pCalPier = &(eep->calFreqPier5G[ipier]);
4216 pCalPierStruct = &(eep->calPierData5G[ichain][ipier]);
4219 if (ipier >= AR9300_NUM_2G_CAL_PIERS) {
4220 ath_dbg(common, ATH_DBG_EEPROM,
4221 "Invalid 2GHz cal pier index, must be less than %d\n",
4222 AR9300_NUM_2G_CAL_PIERS);
4226 pCalPier = &(eep->calFreqPier2G[ipier]);
4227 pCalPierStruct = &(eep->calPierData2G[ichain][ipier]);
4231 *pfrequency = FBIN2FREQ(*pCalPier, is2GHz);
4232 *pcorrection = pCalPierStruct->refPower;
4233 *ptemperature = pCalPierStruct->tempMeas;
4234 *pvoltage = pCalPierStruct->voltMeas;
4239 static int ar9003_hw_power_control_override(struct ath_hw *ah,
4242 int *voltage, int *temperature)
4245 struct ar9300_eeprom *eep = &ah->eeprom.ar9300_eep;
4248 REG_RMW(ah, AR_PHY_TPC_11_B0,
4249 (correction[0] << AR_PHY_TPC_OLPC_GAIN_DELTA_S),
4250 AR_PHY_TPC_OLPC_GAIN_DELTA);
4251 if (ah->caps.tx_chainmask & BIT(1))
4252 REG_RMW(ah, AR_PHY_TPC_11_B1,
4253 (correction[1] << AR_PHY_TPC_OLPC_GAIN_DELTA_S),
4254 AR_PHY_TPC_OLPC_GAIN_DELTA);
4255 if (ah->caps.tx_chainmask & BIT(2))
4256 REG_RMW(ah, AR_PHY_TPC_11_B2,
4257 (correction[2] << AR_PHY_TPC_OLPC_GAIN_DELTA_S),
4258 AR_PHY_TPC_OLPC_GAIN_DELTA);
4260 /* enable open loop power control on chip */
4261 REG_RMW(ah, AR_PHY_TPC_6_B0,
4262 (3 << AR_PHY_TPC_6_ERROR_EST_MODE_S),
4263 AR_PHY_TPC_6_ERROR_EST_MODE);
4264 if (ah->caps.tx_chainmask & BIT(1))
4265 REG_RMW(ah, AR_PHY_TPC_6_B1,
4266 (3 << AR_PHY_TPC_6_ERROR_EST_MODE_S),
4267 AR_PHY_TPC_6_ERROR_EST_MODE);
4268 if (ah->caps.tx_chainmask & BIT(2))
4269 REG_RMW(ah, AR_PHY_TPC_6_B2,
4270 (3 << AR_PHY_TPC_6_ERROR_EST_MODE_S),
4271 AR_PHY_TPC_6_ERROR_EST_MODE);
4274 * enable temperature compensation
4275 * Need to use register names
4277 if (frequency < 4000)
4278 tempSlope = eep->modalHeader2G.tempSlope;
4279 else if (eep->base_ext2.tempSlopeLow != 0) {
4280 t[0] = eep->base_ext2.tempSlopeLow;
4282 t[1] = eep->modalHeader5G.tempSlope;
4284 t[2] = eep->base_ext2.tempSlopeHigh;
4286 tempSlope = ar9003_hw_power_interpolate((s32) frequency,
4289 tempSlope = eep->modalHeader5G.tempSlope;
4291 REG_RMW_FIELD(ah, AR_PHY_TPC_19, AR_PHY_TPC_19_ALPHA_THERM, tempSlope);
4292 REG_RMW_FIELD(ah, AR_PHY_TPC_18, AR_PHY_TPC_18_THERM_CAL_VALUE,
4298 /* Apply the recorded correction values. */
4299 static int ar9003_hw_calibration_apply(struct ath_hw *ah, int frequency)
4301 int ichain, ipier, npier;
4303 int lfrequency[AR9300_MAX_CHAINS],
4304 lcorrection[AR9300_MAX_CHAINS],
4305 ltemperature[AR9300_MAX_CHAINS], lvoltage[AR9300_MAX_CHAINS];
4306 int hfrequency[AR9300_MAX_CHAINS],
4307 hcorrection[AR9300_MAX_CHAINS],
4308 htemperature[AR9300_MAX_CHAINS], hvoltage[AR9300_MAX_CHAINS];
4310 int correction[AR9300_MAX_CHAINS],
4311 voltage[AR9300_MAX_CHAINS], temperature[AR9300_MAX_CHAINS];
4312 int pfrequency, pcorrection, ptemperature, pvoltage;
4313 struct ath_common *common = ath9k_hw_common(ah);
4315 mode = (frequency >= 4000);
4317 npier = AR9300_NUM_5G_CAL_PIERS;
4319 npier = AR9300_NUM_2G_CAL_PIERS;
4321 for (ichain = 0; ichain < AR9300_MAX_CHAINS; ichain++) {
4322 lfrequency[ichain] = 0;
4323 hfrequency[ichain] = 100000;
4325 /* identify best lower and higher frequency calibration measurement */
4326 for (ichain = 0; ichain < AR9300_MAX_CHAINS; ichain++) {
4327 for (ipier = 0; ipier < npier; ipier++) {
4328 if (!ar9003_hw_cal_pier_get(ah, mode, ipier, ichain,
4329 &pfrequency, &pcorrection,
4330 &ptemperature, &pvoltage)) {
4331 fdiff = frequency - pfrequency;
4334 * this measurement is higher than
4335 * our desired frequency
4338 if (hfrequency[ichain] <= 0 ||
4339 hfrequency[ichain] >= 100000 ||
4341 (frequency - hfrequency[ichain])) {
4344 * frequency measurement
4346 hfrequency[ichain] = pfrequency;
4347 hcorrection[ichain] =
4349 htemperature[ichain] =
4351 hvoltage[ichain] = pvoltage;
4355 if (lfrequency[ichain] <= 0
4357 (frequency - lfrequency[ichain])) {
4360 * frequency measurement
4362 lfrequency[ichain] = pfrequency;
4363 lcorrection[ichain] =
4365 ltemperature[ichain] =
4367 lvoltage[ichain] = pvoltage;
4375 for (ichain = 0; ichain < AR9300_MAX_CHAINS; ichain++) {
4376 ath_dbg(common, ATH_DBG_EEPROM,
4377 "ch=%d f=%d low=%d %d h=%d %d\n",
4378 ichain, frequency, lfrequency[ichain],
4379 lcorrection[ichain], hfrequency[ichain],
4380 hcorrection[ichain]);
4381 /* they're the same, so just pick one */
4382 if (hfrequency[ichain] == lfrequency[ichain]) {
4383 correction[ichain] = lcorrection[ichain];
4384 voltage[ichain] = lvoltage[ichain];
4385 temperature[ichain] = ltemperature[ichain];
4387 /* the low frequency is good */
4388 else if (frequency - lfrequency[ichain] < 1000) {
4389 /* so is the high frequency, interpolate */
4390 if (hfrequency[ichain] - frequency < 1000) {
4392 correction[ichain] = interpolate(frequency,
4395 lcorrection[ichain],
4396 hcorrection[ichain]);
4398 temperature[ichain] = interpolate(frequency,
4401 ltemperature[ichain],
4402 htemperature[ichain]);
4404 voltage[ichain] = interpolate(frequency,
4410 /* only low is good, use it */
4412 correction[ichain] = lcorrection[ichain];
4413 temperature[ichain] = ltemperature[ichain];
4414 voltage[ichain] = lvoltage[ichain];
4417 /* only high is good, use it */
4418 else if (hfrequency[ichain] - frequency < 1000) {
4419 correction[ichain] = hcorrection[ichain];
4420 temperature[ichain] = htemperature[ichain];
4421 voltage[ichain] = hvoltage[ichain];
4422 } else { /* nothing is good, presume 0???? */
4423 correction[ichain] = 0;
4424 temperature[ichain] = 0;
4425 voltage[ichain] = 0;
4429 ar9003_hw_power_control_override(ah, frequency, correction, voltage,
4432 ath_dbg(common, ATH_DBG_EEPROM,
4433 "for frequency=%d, calibration correction = %d %d %d\n",
4434 frequency, correction[0], correction[1], correction[2]);
4439 static u16 ar9003_hw_get_direct_edge_power(struct ar9300_eeprom *eep,
4444 struct cal_ctl_data_2g *ctl_2g = eep->ctlPowerData_2G;
4445 struct cal_ctl_data_5g *ctl_5g = eep->ctlPowerData_5G;
4448 return CTL_EDGE_TPOWER(ctl_2g[idx].ctlEdges[edge]);
4450 return CTL_EDGE_TPOWER(ctl_5g[idx].ctlEdges[edge]);
4453 static u16 ar9003_hw_get_indirect_edge_power(struct ar9300_eeprom *eep,
4459 struct cal_ctl_data_2g *ctl_2g = eep->ctlPowerData_2G;
4460 struct cal_ctl_data_5g *ctl_5g = eep->ctlPowerData_5G;
4462 u8 *ctl_freqbin = is2GHz ?
4463 &eep->ctl_freqbin_2G[idx][0] :
4464 &eep->ctl_freqbin_5G[idx][0];
4467 if (ath9k_hw_fbin2freq(ctl_freqbin[edge - 1], 1) < freq &&
4468 CTL_EDGE_FLAGS(ctl_2g[idx].ctlEdges[edge - 1]))
4469 return CTL_EDGE_TPOWER(ctl_2g[idx].ctlEdges[edge - 1]);
4471 if (ath9k_hw_fbin2freq(ctl_freqbin[edge - 1], 0) < freq &&
4472 CTL_EDGE_FLAGS(ctl_5g[idx].ctlEdges[edge - 1]))
4473 return CTL_EDGE_TPOWER(ctl_5g[idx].ctlEdges[edge - 1]);
4476 return MAX_RATE_POWER;
4480 * Find the maximum conformance test limit for the given channel and CTL info
4482 static u16 ar9003_hw_get_max_edge_power(struct ar9300_eeprom *eep,
4483 u16 freq, int idx, bool is2GHz)
4485 u16 twiceMaxEdgePower = MAX_RATE_POWER;
4486 u8 *ctl_freqbin = is2GHz ?
4487 &eep->ctl_freqbin_2G[idx][0] :
4488 &eep->ctl_freqbin_5G[idx][0];
4489 u16 num_edges = is2GHz ?
4490 AR9300_NUM_BAND_EDGES_2G : AR9300_NUM_BAND_EDGES_5G;
4493 /* Get the edge power */
4495 (edge < num_edges) && (ctl_freqbin[edge] != AR5416_BCHAN_UNUSED);
4498 * If there's an exact channel match or an inband flag set
4499 * on the lower channel use the given rdEdgePower
4501 if (freq == ath9k_hw_fbin2freq(ctl_freqbin[edge], is2GHz)) {
4503 ar9003_hw_get_direct_edge_power(eep, idx,
4506 } else if ((edge > 0) &&
4507 (freq < ath9k_hw_fbin2freq(ctl_freqbin[edge],
4510 ar9003_hw_get_indirect_edge_power(eep, idx,
4514 * Leave loop - no more affecting edges possible in
4515 * this monotonic increasing list
4520 return twiceMaxEdgePower;
4523 static void ar9003_hw_set_power_per_rate_table(struct ath_hw *ah,
4524 struct ath9k_channel *chan,
4525 u8 *pPwrArray, u16 cfgCtl,
4526 u8 twiceAntennaReduction,
4527 u8 twiceMaxRegulatoryPower,
4530 struct ath_regulatory *regulatory = ath9k_hw_regulatory(ah);
4531 struct ath_common *common = ath9k_hw_common(ah);
4532 struct ar9300_eeprom *pEepData = &ah->eeprom.ar9300_eep;
4533 u16 twiceMaxEdgePower = MAX_RATE_POWER;
4534 static const u16 tpScaleReductionTable[5] = {
4535 0, 3, 6, 9, MAX_RATE_POWER
4538 int16_t twiceLargestAntenna;
4539 u16 scaledPower = 0, minCtlPower, maxRegAllowedPower;
4540 static const u16 ctlModesFor11a[] = {
4541 CTL_11A, CTL_5GHT20, CTL_11A_EXT, CTL_5GHT40
4543 static const u16 ctlModesFor11g[] = {
4544 CTL_11B, CTL_11G, CTL_2GHT20, CTL_11B_EXT,
4545 CTL_11G_EXT, CTL_2GHT40
4548 const u16 *pCtlMode;
4550 struct chan_centers centers;
4553 u16 twiceMinEdgePower;
4554 bool is2ghz = IS_CHAN_2GHZ(chan);
4556 ath9k_hw_get_channel_centers(ah, chan, ¢ers);
4558 /* Compute TxPower reduction due to Antenna Gain */
4560 twiceLargestAntenna = pEepData->modalHeader2G.antennaGain;
4562 twiceLargestAntenna = pEepData->modalHeader5G.antennaGain;
4564 twiceLargestAntenna = (int16_t)min((twiceAntennaReduction) -
4565 twiceLargestAntenna, 0);
4568 * scaledPower is the minimum of the user input power level
4569 * and the regulatory allowed power level
4571 maxRegAllowedPower = twiceMaxRegulatoryPower + twiceLargestAntenna;
4573 if (regulatory->tp_scale != ATH9K_TP_SCALE_MAX) {
4574 maxRegAllowedPower -=
4575 (tpScaleReductionTable[(regulatory->tp_scale)] * 2);
4578 scaledPower = min(powerLimit, maxRegAllowedPower);
4581 * Reduce scaled Power by number of chains active to get
4582 * to per chain tx power level
4584 switch (ar5416_get_ntxchains(ah->txchainmask)) {
4588 scaledPower -= REDUCE_SCALED_POWER_BY_TWO_CHAIN;
4591 scaledPower -= REDUCE_SCALED_POWER_BY_THREE_CHAIN;
4595 scaledPower = max((u16)0, scaledPower);
4598 * Get target powers from EEPROM - our baseline for TX Power
4601 /* Setup for CTL modes */
4602 /* CTL_11B, CTL_11G, CTL_2GHT20 */
4604 ARRAY_SIZE(ctlModesFor11g) -
4605 SUB_NUM_CTL_MODES_AT_2G_40;
4606 pCtlMode = ctlModesFor11g;
4607 if (IS_CHAN_HT40(chan))
4609 numCtlModes = ARRAY_SIZE(ctlModesFor11g);
4611 /* Setup for CTL modes */
4612 /* CTL_11A, CTL_5GHT20 */
4613 numCtlModes = ARRAY_SIZE(ctlModesFor11a) -
4614 SUB_NUM_CTL_MODES_AT_5G_40;
4615 pCtlMode = ctlModesFor11a;
4616 if (IS_CHAN_HT40(chan))
4618 numCtlModes = ARRAY_SIZE(ctlModesFor11a);
4622 * For MIMO, need to apply regulatory caps individually across
4623 * dynamically running modes: CCK, OFDM, HT20, HT40
4625 * The outer loop walks through each possible applicable runtime mode.
4626 * The inner loop walks through each ctlIndex entry in EEPROM.
4627 * The ctl value is encoded as [7:4] == test group, [3:0] == test mode.
4629 for (ctlMode = 0; ctlMode < numCtlModes; ctlMode++) {
4630 bool isHt40CtlMode = (pCtlMode[ctlMode] == CTL_5GHT40) ||
4631 (pCtlMode[ctlMode] == CTL_2GHT40);
4633 freq = centers.synth_center;
4634 else if (pCtlMode[ctlMode] & EXT_ADDITIVE)
4635 freq = centers.ext_center;
4637 freq = centers.ctl_center;
4639 ath_dbg(common, ATH_DBG_REGULATORY,
4640 "LOOP-Mode ctlMode %d < %d, isHt40CtlMode %d, EXT_ADDITIVE %d\n",
4641 ctlMode, numCtlModes, isHt40CtlMode,
4642 (pCtlMode[ctlMode] & EXT_ADDITIVE));
4644 /* walk through each CTL index stored in EEPROM */
4646 ctlIndex = pEepData->ctlIndex_2G;
4647 ctlNum = AR9300_NUM_CTLS_2G;
4649 ctlIndex = pEepData->ctlIndex_5G;
4650 ctlNum = AR9300_NUM_CTLS_5G;
4653 for (i = 0; (i < ctlNum) && ctlIndex[i]; i++) {
4654 ath_dbg(common, ATH_DBG_REGULATORY,
4655 "LOOP-Ctlidx %d: cfgCtl 0x%2.2x pCtlMode 0x%2.2x ctlIndex 0x%2.2x chan %d\n",
4656 i, cfgCtl, pCtlMode[ctlMode], ctlIndex[i],
4660 * compare test group from regulatory
4661 * channel list with test mode from pCtlMode
4664 if ((((cfgCtl & ~CTL_MODE_M) |
4665 (pCtlMode[ctlMode] & CTL_MODE_M)) ==
4667 (((cfgCtl & ~CTL_MODE_M) |
4668 (pCtlMode[ctlMode] & CTL_MODE_M)) ==
4669 ((ctlIndex[i] & CTL_MODE_M) |
4672 ar9003_hw_get_max_edge_power(pEepData,
4676 if ((cfgCtl & ~CTL_MODE_M) == SD_NO_CTL)
4678 * Find the minimum of all CTL
4679 * edge powers that apply to
4683 min(twiceMaxEdgePower,
4694 minCtlPower = (u8)min(twiceMaxEdgePower, scaledPower);
4696 ath_dbg(common, ATH_DBG_REGULATORY,
4697 "SEL-Min ctlMode %d pCtlMode %d 2xMaxEdge %d sP %d minCtlPwr %d\n",
4698 ctlMode, pCtlMode[ctlMode], twiceMaxEdgePower,
4699 scaledPower, minCtlPower);
4701 /* Apply ctl mode to correct target power set */
4702 switch (pCtlMode[ctlMode]) {
4704 for (i = ALL_TARGET_LEGACY_1L_5L;
4705 i <= ALL_TARGET_LEGACY_11S; i++)
4707 (u8)min((u16)pPwrArray[i],
4712 for (i = ALL_TARGET_LEGACY_6_24;
4713 i <= ALL_TARGET_LEGACY_54; i++)
4715 (u8)min((u16)pPwrArray[i],
4720 for (i = ALL_TARGET_HT20_0_8_16;
4721 i <= ALL_TARGET_HT20_21; i++)
4723 (u8)min((u16)pPwrArray[i],
4725 pPwrArray[ALL_TARGET_HT20_22] =
4726 (u8)min((u16)pPwrArray[ALL_TARGET_HT20_22],
4728 pPwrArray[ALL_TARGET_HT20_23] =
4729 (u8)min((u16)pPwrArray[ALL_TARGET_HT20_23],
4734 for (i = ALL_TARGET_HT40_0_8_16;
4735 i <= ALL_TARGET_HT40_23; i++)
4737 (u8)min((u16)pPwrArray[i],
4743 } /* end ctl mode checking */
4746 static void ath9k_hw_ar9300_set_txpower(struct ath_hw *ah,
4747 struct ath9k_channel *chan, u16 cfgCtl,
4748 u8 twiceAntennaReduction,
4749 u8 twiceMaxRegulatoryPower,
4750 u8 powerLimit, bool test)
4752 struct ath_regulatory *regulatory = ath9k_hw_regulatory(ah);
4753 struct ath_common *common = ath9k_hw_common(ah);
4754 u8 targetPowerValT2[ar9300RateSize];
4757 ar9003_hw_set_target_power_eeprom(ah, chan->channel, targetPowerValT2);
4758 ar9003_hw_set_power_per_rate_table(ah, chan,
4759 targetPowerValT2, cfgCtl,
4760 twiceAntennaReduction,
4761 twiceMaxRegulatoryPower,
4764 regulatory->max_power_level = 0;
4765 for (i = 0; i < ar9300RateSize; i++) {
4766 if (targetPowerValT2[i] > regulatory->max_power_level)
4767 regulatory->max_power_level = targetPowerValT2[i];
4773 for (i = 0; i < ar9300RateSize; i++) {
4774 ath_dbg(common, ATH_DBG_EEPROM,
4775 "TPC[%02d] 0x%08x\n", i, targetPowerValT2[i]);
4779 * This is the TX power we send back to driver core,
4780 * and it can use to pass to userspace to display our
4781 * currently configured TX power setting.
4783 * Since power is rate dependent, use one of the indices
4784 * from the AR9300_Rates enum to select an entry from
4785 * targetPowerValT2[] to report. Currently returns the
4786 * power for HT40 MCS 0, HT20 MCS 0, or OFDM 6 Mbps
4787 * as CCK power is less interesting (?).
4789 i = ALL_TARGET_LEGACY_6_24; /* legacy */
4790 if (IS_CHAN_HT40(chan))
4791 i = ALL_TARGET_HT40_0_8_16; /* ht40 */
4792 else if (IS_CHAN_HT20(chan))
4793 i = ALL_TARGET_HT20_0_8_16; /* ht20 */
4795 ah->txpower_limit = targetPowerValT2[i];
4796 regulatory->max_power_level = targetPowerValT2[i];
4798 /* Write target power array to registers */
4799 ar9003_hw_tx_power_regwrite(ah, targetPowerValT2);
4800 ar9003_hw_calibration_apply(ah, chan->channel);
4803 static u16 ath9k_hw_ar9300_get_spur_channel(struct ath_hw *ah,
4809 s32 ar9003_hw_get_tx_gain_idx(struct ath_hw *ah)
4811 struct ar9300_eeprom *eep = &ah->eeprom.ar9300_eep;
4813 return (eep->baseEepHeader.txrxgain >> 4) & 0xf; /* bits 7:4 */
4816 s32 ar9003_hw_get_rx_gain_idx(struct ath_hw *ah)
4818 struct ar9300_eeprom *eep = &ah->eeprom.ar9300_eep;
4820 return (eep->baseEepHeader.txrxgain) & 0xf; /* bits 3:0 */
4823 u8 *ar9003_get_spur_chan_ptr(struct ath_hw *ah, bool is_2ghz)
4825 struct ar9300_eeprom *eep = &ah->eeprom.ar9300_eep;
4828 return eep->modalHeader2G.spurChans;
4830 return eep->modalHeader5G.spurChans;
4833 const struct eeprom_ops eep_ar9300_ops = {
4834 .check_eeprom = ath9k_hw_ar9300_check_eeprom,
4835 .get_eeprom = ath9k_hw_ar9300_get_eeprom,
4836 .fill_eeprom = ath9k_hw_ar9300_fill_eeprom,
4837 .get_eeprom_ver = ath9k_hw_ar9300_get_eeprom_ver,
4838 .get_eeprom_rev = ath9k_hw_ar9300_get_eeprom_rev,
4839 .set_board_values = ath9k_hw_ar9300_set_board_values,
4840 .set_addac = ath9k_hw_ar9300_set_addac,
4841 .set_txpower = ath9k_hw_ar9300_set_txpower,
4842 .get_spur_channel = ath9k_hw_ar9300_get_spur_channel