Merge branch 'master' of /home/davem/src/GIT/linux-2.6/
[sfrench/cifs-2.6.git] / drivers / net / wireless / ath / ath5k / eeprom.c
1 /*
2  * Copyright (c) 2004-2008 Reyk Floeter <reyk@openbsd.org>
3  * Copyright (c) 2006-2009 Nick Kossifidis <mickflemm@gmail.com>
4  * Copyright (c) 2008-2009 Felix Fietkau <nbd@openwrt.org>
5  *
6  * Permission to use, copy, modify, and distribute this software for any
7  * purpose with or without fee is hereby granted, provided that the above
8  * copyright notice and this permission notice appear in all copies.
9  *
10  * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
11  * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
12  * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
13  * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
14  * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
15  * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
16  * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
17  *
18  */
19
20 /*************************************\
21 * EEPROM access functions and helpers *
22 \*************************************/
23
24 #include "ath5k.h"
25 #include "reg.h"
26 #include "debug.h"
27 #include "base.h"
28
29 /*
30  * Read from eeprom
31  */
32 static int ath5k_hw_eeprom_read(struct ath5k_hw *ah, u32 offset, u16 *data)
33 {
34         u32 status, timeout;
35
36         ATH5K_TRACE(ah->ah_sc);
37         /*
38          * Initialize EEPROM access
39          */
40         if (ah->ah_version == AR5K_AR5210) {
41                 AR5K_REG_ENABLE_BITS(ah, AR5K_PCICFG, AR5K_PCICFG_EEAE);
42                 (void)ath5k_hw_reg_read(ah, AR5K_EEPROM_BASE + (4 * offset));
43         } else {
44                 ath5k_hw_reg_write(ah, offset, AR5K_EEPROM_BASE);
45                 AR5K_REG_ENABLE_BITS(ah, AR5K_EEPROM_CMD,
46                                 AR5K_EEPROM_CMD_READ);
47         }
48
49         for (timeout = AR5K_TUNE_REGISTER_TIMEOUT; timeout > 0; timeout--) {
50                 status = ath5k_hw_reg_read(ah, AR5K_EEPROM_STATUS);
51                 if (status & AR5K_EEPROM_STAT_RDDONE) {
52                         if (status & AR5K_EEPROM_STAT_RDERR)
53                                 return -EIO;
54                         *data = (u16)(ath5k_hw_reg_read(ah, AR5K_EEPROM_DATA) &
55                                         0xffff);
56                         return 0;
57                 }
58                 udelay(15);
59         }
60
61         return -ETIMEDOUT;
62 }
63
64 /*
65  * Translate binary channel representation in EEPROM to frequency
66  */
67 static u16 ath5k_eeprom_bin2freq(struct ath5k_eeprom_info *ee, u16 bin,
68                                  unsigned int mode)
69 {
70         u16 val;
71
72         if (bin == AR5K_EEPROM_CHANNEL_DIS)
73                 return bin;
74
75         if (mode == AR5K_EEPROM_MODE_11A) {
76                 if (ee->ee_version > AR5K_EEPROM_VERSION_3_2)
77                         val = (5 * bin) + 4800;
78                 else
79                         val = bin > 62 ? (10 * 62) + (5 * (bin - 62)) + 5100 :
80                                 (bin * 10) + 5100;
81         } else {
82                 if (ee->ee_version > AR5K_EEPROM_VERSION_3_2)
83                         val = bin + 2300;
84                 else
85                         val = bin + 2400;
86         }
87
88         return val;
89 }
90
91 /*
92  * Initialize eeprom & capabilities structs
93  */
94 static int
95 ath5k_eeprom_init_header(struct ath5k_hw *ah)
96 {
97         struct ath5k_eeprom_info *ee = &ah->ah_capabilities.cap_eeprom;
98         int ret;
99         u16 val;
100         u32 cksum, offset;
101
102         /*
103          * Read values from EEPROM and store them in the capability structure
104          */
105         AR5K_EEPROM_READ_HDR(AR5K_EEPROM_MAGIC, ee_magic);
106         AR5K_EEPROM_READ_HDR(AR5K_EEPROM_PROTECT, ee_protect);
107         AR5K_EEPROM_READ_HDR(AR5K_EEPROM_REG_DOMAIN, ee_regdomain);
108         AR5K_EEPROM_READ_HDR(AR5K_EEPROM_VERSION, ee_version);
109         AR5K_EEPROM_READ_HDR(AR5K_EEPROM_HDR, ee_header);
110
111         /* Return if we have an old EEPROM */
112         if (ah->ah_ee_version < AR5K_EEPROM_VERSION_3_0)
113                 return 0;
114
115         /*
116          * Validate the checksum of the EEPROM date. There are some
117          * devices with invalid EEPROMs.
118          */
119         for (cksum = 0, offset = 0; offset < AR5K_EEPROM_INFO_MAX; offset++) {
120                 AR5K_EEPROM_READ(AR5K_EEPROM_INFO(offset), val);
121                 cksum ^= val;
122         }
123         if (cksum != AR5K_EEPROM_INFO_CKSUM) {
124                 ATH5K_ERR(ah->ah_sc, "Invalid EEPROM checksum 0x%04x\n", cksum);
125                 return -EIO;
126         }
127
128         AR5K_EEPROM_READ_HDR(AR5K_EEPROM_ANT_GAIN(ah->ah_ee_version),
129             ee_ant_gain);
130
131         if (ah->ah_ee_version >= AR5K_EEPROM_VERSION_4_0) {
132                 AR5K_EEPROM_READ_HDR(AR5K_EEPROM_MISC0, ee_misc0);
133                 AR5K_EEPROM_READ_HDR(AR5K_EEPROM_MISC1, ee_misc1);
134
135                 /* XXX: Don't know which versions include these two */
136                 AR5K_EEPROM_READ_HDR(AR5K_EEPROM_MISC2, ee_misc2);
137
138                 if (ee->ee_version >= AR5K_EEPROM_VERSION_4_3)
139                         AR5K_EEPROM_READ_HDR(AR5K_EEPROM_MISC3, ee_misc3);
140
141                 if (ee->ee_version >= AR5K_EEPROM_VERSION_5_0) {
142                         AR5K_EEPROM_READ_HDR(AR5K_EEPROM_MISC4, ee_misc4);
143                         AR5K_EEPROM_READ_HDR(AR5K_EEPROM_MISC5, ee_misc5);
144                         AR5K_EEPROM_READ_HDR(AR5K_EEPROM_MISC6, ee_misc6);
145                 }
146         }
147
148         if (ah->ah_ee_version < AR5K_EEPROM_VERSION_3_3) {
149                 AR5K_EEPROM_READ(AR5K_EEPROM_OBDB0_2GHZ, val);
150                 ee->ee_ob[AR5K_EEPROM_MODE_11B][0] = val & 0x7;
151                 ee->ee_db[AR5K_EEPROM_MODE_11B][0] = (val >> 3) & 0x7;
152
153                 AR5K_EEPROM_READ(AR5K_EEPROM_OBDB1_2GHZ, val);
154                 ee->ee_ob[AR5K_EEPROM_MODE_11G][0] = val & 0x7;
155                 ee->ee_db[AR5K_EEPROM_MODE_11G][0] = (val >> 3) & 0x7;
156         }
157
158         AR5K_EEPROM_READ(AR5K_EEPROM_IS_HB63, val);
159
160         if ((ah->ah_mac_version == (AR5K_SREV_AR2425 >> 4)) && val)
161                 ee->ee_is_hb63 = true;
162         else
163                 ee->ee_is_hb63 = false;
164
165         AR5K_EEPROM_READ(AR5K_EEPROM_RFKILL, val);
166         ee->ee_rfkill_pin = (u8) AR5K_REG_MS(val, AR5K_EEPROM_RFKILL_GPIO_SEL);
167         ee->ee_rfkill_pol = val & AR5K_EEPROM_RFKILL_POLARITY ? true : false;
168
169         /* Check if PCIE_OFFSET points to PCIE_SERDES_SECTION
170          * and enable serdes programming if needed.
171          *
172          * XXX: Serdes values seem to be fixed so
173          * no need to read them here, we write them
174          * during ath5k_hw_attach */
175         AR5K_EEPROM_READ(AR5K_EEPROM_PCIE_OFFSET, val);
176         ee->ee_serdes = (val == AR5K_EEPROM_PCIE_SERDES_SECTION) ?
177                                                         true : false;
178
179         return 0;
180 }
181
182
183 /*
184  * Read antenna infos from eeprom
185  */
186 static int ath5k_eeprom_read_ants(struct ath5k_hw *ah, u32 *offset,
187                 unsigned int mode)
188 {
189         struct ath5k_eeprom_info *ee = &ah->ah_capabilities.cap_eeprom;
190         u32 o = *offset;
191         u16 val;
192         int ret, i = 0;
193
194         AR5K_EEPROM_READ(o++, val);
195         ee->ee_switch_settling[mode]    = (val >> 8) & 0x7f;
196         ee->ee_atn_tx_rx[mode]          = (val >> 2) & 0x3f;
197         ee->ee_ant_control[mode][i]     = (val << 4) & 0x3f;
198
199         AR5K_EEPROM_READ(o++, val);
200         ee->ee_ant_control[mode][i++]   |= (val >> 12) & 0xf;
201         ee->ee_ant_control[mode][i++]   = (val >> 6) & 0x3f;
202         ee->ee_ant_control[mode][i++]   = val & 0x3f;
203
204         AR5K_EEPROM_READ(o++, val);
205         ee->ee_ant_control[mode][i++]   = (val >> 10) & 0x3f;
206         ee->ee_ant_control[mode][i++]   = (val >> 4) & 0x3f;
207         ee->ee_ant_control[mode][i]     = (val << 2) & 0x3f;
208
209         AR5K_EEPROM_READ(o++, val);
210         ee->ee_ant_control[mode][i++]   |= (val >> 14) & 0x3;
211         ee->ee_ant_control[mode][i++]   = (val >> 8) & 0x3f;
212         ee->ee_ant_control[mode][i++]   = (val >> 2) & 0x3f;
213         ee->ee_ant_control[mode][i]     = (val << 4) & 0x3f;
214
215         AR5K_EEPROM_READ(o++, val);
216         ee->ee_ant_control[mode][i++]   |= (val >> 12) & 0xf;
217         ee->ee_ant_control[mode][i++]   = (val >> 6) & 0x3f;
218         ee->ee_ant_control[mode][i++]   = val & 0x3f;
219
220         /* Get antenna switch tables */
221         ah->ah_ant_ctl[mode][AR5K_ANT_CTL] =
222             (ee->ee_ant_control[mode][0] << 4);
223         ah->ah_ant_ctl[mode][AR5K_ANT_SWTABLE_A] =
224              ee->ee_ant_control[mode][1]        |
225             (ee->ee_ant_control[mode][2] << 6)  |
226             (ee->ee_ant_control[mode][3] << 12) |
227             (ee->ee_ant_control[mode][4] << 18) |
228             (ee->ee_ant_control[mode][5] << 24);
229         ah->ah_ant_ctl[mode][AR5K_ANT_SWTABLE_B] =
230              ee->ee_ant_control[mode][6]        |
231             (ee->ee_ant_control[mode][7] << 6)  |
232             (ee->ee_ant_control[mode][8] << 12) |
233             (ee->ee_ant_control[mode][9] << 18) |
234             (ee->ee_ant_control[mode][10] << 24);
235
236         /* return new offset */
237         *offset = o;
238
239         return 0;
240 }
241
242 /*
243  * Read supported modes and some mode-specific calibration data
244  * from eeprom
245  */
246 static int ath5k_eeprom_read_modes(struct ath5k_hw *ah, u32 *offset,
247                 unsigned int mode)
248 {
249         struct ath5k_eeprom_info *ee = &ah->ah_capabilities.cap_eeprom;
250         u32 o = *offset;
251         u16 val;
252         int ret;
253
254         ee->ee_n_piers[mode] = 0;
255         AR5K_EEPROM_READ(o++, val);
256         ee->ee_adc_desired_size[mode]   = (s8)((val >> 8) & 0xff);
257         switch(mode) {
258         case AR5K_EEPROM_MODE_11A:
259                 ee->ee_ob[mode][3]      = (val >> 5) & 0x7;
260                 ee->ee_db[mode][3]      = (val >> 2) & 0x7;
261                 ee->ee_ob[mode][2]      = (val << 1) & 0x7;
262
263                 AR5K_EEPROM_READ(o++, val);
264                 ee->ee_ob[mode][2]      |= (val >> 15) & 0x1;
265                 ee->ee_db[mode][2]      = (val >> 12) & 0x7;
266                 ee->ee_ob[mode][1]      = (val >> 9) & 0x7;
267                 ee->ee_db[mode][1]      = (val >> 6) & 0x7;
268                 ee->ee_ob[mode][0]      = (val >> 3) & 0x7;
269                 ee->ee_db[mode][0]      = val & 0x7;
270                 break;
271         case AR5K_EEPROM_MODE_11G:
272         case AR5K_EEPROM_MODE_11B:
273                 ee->ee_ob[mode][1]      = (val >> 4) & 0x7;
274                 ee->ee_db[mode][1]      = val & 0x7;
275                 break;
276         }
277
278         AR5K_EEPROM_READ(o++, val);
279         ee->ee_tx_end2xlna_enable[mode] = (val >> 8) & 0xff;
280         ee->ee_thr_62[mode]             = val & 0xff;
281
282         if (ah->ah_ee_version <= AR5K_EEPROM_VERSION_3_2)
283                 ee->ee_thr_62[mode] = mode == AR5K_EEPROM_MODE_11A ? 15 : 28;
284
285         AR5K_EEPROM_READ(o++, val);
286         ee->ee_tx_end2xpa_disable[mode] = (val >> 8) & 0xff;
287         ee->ee_tx_frm2xpa_enable[mode]  = val & 0xff;
288
289         AR5K_EEPROM_READ(o++, val);
290         ee->ee_pga_desired_size[mode]   = (val >> 8) & 0xff;
291
292         if ((val & 0xff) & 0x80)
293                 ee->ee_noise_floor_thr[mode] = -((((val & 0xff) ^ 0xff)) + 1);
294         else
295                 ee->ee_noise_floor_thr[mode] = val & 0xff;
296
297         if (ah->ah_ee_version <= AR5K_EEPROM_VERSION_3_2)
298                 ee->ee_noise_floor_thr[mode] =
299                     mode == AR5K_EEPROM_MODE_11A ? -54 : -1;
300
301         AR5K_EEPROM_READ(o++, val);
302         ee->ee_xlna_gain[mode]          = (val >> 5) & 0xff;
303         ee->ee_x_gain[mode]             = (val >> 1) & 0xf;
304         ee->ee_xpd[mode]                = val & 0x1;
305
306         if (ah->ah_ee_version >= AR5K_EEPROM_VERSION_4_0)
307                 ee->ee_fixed_bias[mode] = (val >> 13) & 0x1;
308
309         if (ah->ah_ee_version >= AR5K_EEPROM_VERSION_3_3) {
310                 AR5K_EEPROM_READ(o++, val);
311                 ee->ee_false_detect[mode] = (val >> 6) & 0x7f;
312
313                 if (mode == AR5K_EEPROM_MODE_11A)
314                         ee->ee_xr_power[mode] = val & 0x3f;
315                 else {
316                         ee->ee_ob[mode][0] = val & 0x7;
317                         ee->ee_db[mode][0] = (val >> 3) & 0x7;
318                 }
319         }
320
321         if (ah->ah_ee_version < AR5K_EEPROM_VERSION_3_4) {
322                 ee->ee_i_gain[mode] = AR5K_EEPROM_I_GAIN;
323                 ee->ee_cck_ofdm_power_delta = AR5K_EEPROM_CCK_OFDM_DELTA;
324         } else {
325                 ee->ee_i_gain[mode] = (val >> 13) & 0x7;
326
327                 AR5K_EEPROM_READ(o++, val);
328                 ee->ee_i_gain[mode] |= (val << 3) & 0x38;
329
330                 if (mode == AR5K_EEPROM_MODE_11G) {
331                         ee->ee_cck_ofdm_power_delta = (val >> 3) & 0xff;
332                         if (ah->ah_ee_version >= AR5K_EEPROM_VERSION_4_6)
333                                 ee->ee_scaled_cck_delta = (val >> 11) & 0x1f;
334                 }
335         }
336
337         if (ah->ah_ee_version >= AR5K_EEPROM_VERSION_4_0 &&
338                         mode == AR5K_EEPROM_MODE_11A) {
339                 ee->ee_i_cal[mode] = (val >> 8) & 0x3f;
340                 ee->ee_q_cal[mode] = (val >> 3) & 0x1f;
341         }
342
343         if (ah->ah_ee_version < AR5K_EEPROM_VERSION_4_0)
344                 goto done;
345
346         /* Note: >= v5 have bg freq piers on another location
347          * so these freq piers are ignored for >= v5 (should be 0xff
348          * anyway) */
349         switch(mode) {
350         case AR5K_EEPROM_MODE_11A:
351                 if (ah->ah_ee_version < AR5K_EEPROM_VERSION_4_1)
352                         break;
353
354                 AR5K_EEPROM_READ(o++, val);
355                 ee->ee_margin_tx_rx[mode] = val & 0x3f;
356                 break;
357         case AR5K_EEPROM_MODE_11B:
358                 AR5K_EEPROM_READ(o++, val);
359
360                 ee->ee_pwr_cal_b[0].freq =
361                         ath5k_eeprom_bin2freq(ee, val & 0xff, mode);
362                 if (ee->ee_pwr_cal_b[0].freq != AR5K_EEPROM_CHANNEL_DIS)
363                         ee->ee_n_piers[mode]++;
364
365                 ee->ee_pwr_cal_b[1].freq =
366                         ath5k_eeprom_bin2freq(ee, (val >> 8) & 0xff, mode);
367                 if (ee->ee_pwr_cal_b[1].freq != AR5K_EEPROM_CHANNEL_DIS)
368                         ee->ee_n_piers[mode]++;
369
370                 AR5K_EEPROM_READ(o++, val);
371                 ee->ee_pwr_cal_b[2].freq =
372                         ath5k_eeprom_bin2freq(ee, val & 0xff, mode);
373                 if (ee->ee_pwr_cal_b[2].freq != AR5K_EEPROM_CHANNEL_DIS)
374                         ee->ee_n_piers[mode]++;
375
376                 if (ah->ah_ee_version >= AR5K_EEPROM_VERSION_4_1)
377                         ee->ee_margin_tx_rx[mode] = (val >> 8) & 0x3f;
378                 break;
379         case AR5K_EEPROM_MODE_11G:
380                 AR5K_EEPROM_READ(o++, val);
381
382                 ee->ee_pwr_cal_g[0].freq =
383                         ath5k_eeprom_bin2freq(ee, val & 0xff, mode);
384                 if (ee->ee_pwr_cal_g[0].freq != AR5K_EEPROM_CHANNEL_DIS)
385                         ee->ee_n_piers[mode]++;
386
387                 ee->ee_pwr_cal_g[1].freq =
388                         ath5k_eeprom_bin2freq(ee, (val >> 8) & 0xff, mode);
389                 if (ee->ee_pwr_cal_g[1].freq != AR5K_EEPROM_CHANNEL_DIS)
390                         ee->ee_n_piers[mode]++;
391
392                 AR5K_EEPROM_READ(o++, val);
393                 ee->ee_turbo_max_power[mode] = val & 0x7f;
394                 ee->ee_xr_power[mode] = (val >> 7) & 0x3f;
395
396                 AR5K_EEPROM_READ(o++, val);
397                 ee->ee_pwr_cal_g[2].freq =
398                         ath5k_eeprom_bin2freq(ee, val & 0xff, mode);
399                 if (ee->ee_pwr_cal_g[2].freq != AR5K_EEPROM_CHANNEL_DIS)
400                         ee->ee_n_piers[mode]++;
401
402                 if (ah->ah_ee_version >= AR5K_EEPROM_VERSION_4_1)
403                         ee->ee_margin_tx_rx[mode] = (val >> 8) & 0x3f;
404
405                 AR5K_EEPROM_READ(o++, val);
406                 ee->ee_i_cal[mode] = (val >> 8) & 0x3f;
407                 ee->ee_q_cal[mode] = (val >> 3) & 0x1f;
408
409                 if (ah->ah_ee_version >= AR5K_EEPROM_VERSION_4_2) {
410                         AR5K_EEPROM_READ(o++, val);
411                         ee->ee_cck_ofdm_gain_delta = val & 0xff;
412                 }
413                 break;
414         }
415
416         /*
417          * Read turbo mode information on newer EEPROM versions
418          */
419         if (ee->ee_version < AR5K_EEPROM_VERSION_5_0)
420                 goto done;
421
422         switch (mode){
423         case AR5K_EEPROM_MODE_11A:
424                 ee->ee_switch_settling_turbo[mode] = (val >> 6) & 0x7f;
425
426                 ee->ee_atn_tx_rx_turbo[mode] = (val >> 13) & 0x7;
427                 AR5K_EEPROM_READ(o++, val);
428                 ee->ee_atn_tx_rx_turbo[mode] |= (val & 0x7) << 3;
429                 ee->ee_margin_tx_rx_turbo[mode] = (val >> 3) & 0x3f;
430
431                 ee->ee_adc_desired_size_turbo[mode] = (val >> 9) & 0x7f;
432                 AR5K_EEPROM_READ(o++, val);
433                 ee->ee_adc_desired_size_turbo[mode] |= (val & 0x1) << 7;
434                 ee->ee_pga_desired_size_turbo[mode] = (val >> 1) & 0xff;
435
436                 if (AR5K_EEPROM_EEMAP(ee->ee_misc0) >=2)
437                         ee->ee_pd_gain_overlap = (val >> 9) & 0xf;
438                 break;
439         case AR5K_EEPROM_MODE_11G:
440                 ee->ee_switch_settling_turbo[mode] = (val >> 8) & 0x7f;
441
442                 ee->ee_atn_tx_rx_turbo[mode] = (val >> 15) & 0x7;
443                 AR5K_EEPROM_READ(o++, val);
444                 ee->ee_atn_tx_rx_turbo[mode] |= (val & 0x1f) << 1;
445                 ee->ee_margin_tx_rx_turbo[mode] = (val >> 5) & 0x3f;
446
447                 ee->ee_adc_desired_size_turbo[mode] = (val >> 11) & 0x7f;
448                 AR5K_EEPROM_READ(o++, val);
449                 ee->ee_adc_desired_size_turbo[mode] |= (val & 0x7) << 5;
450                 ee->ee_pga_desired_size_turbo[mode] = (val >> 3) & 0xff;
451                 break;
452         }
453
454 done:
455         /* return new offset */
456         *offset = o;
457
458         return 0;
459 }
460
461 /* Read mode-specific data (except power calibration data) */
462 static int
463 ath5k_eeprom_init_modes(struct ath5k_hw *ah)
464 {
465         struct ath5k_eeprom_info *ee = &ah->ah_capabilities.cap_eeprom;
466         u32 mode_offset[3];
467         unsigned int mode;
468         u32 offset;
469         int ret;
470
471         /*
472          * Get values for all modes
473          */
474         mode_offset[AR5K_EEPROM_MODE_11A] = AR5K_EEPROM_MODES_11A(ah->ah_ee_version);
475         mode_offset[AR5K_EEPROM_MODE_11B] = AR5K_EEPROM_MODES_11B(ah->ah_ee_version);
476         mode_offset[AR5K_EEPROM_MODE_11G] = AR5K_EEPROM_MODES_11G(ah->ah_ee_version);
477
478         ee->ee_turbo_max_power[AR5K_EEPROM_MODE_11A] =
479                 AR5K_EEPROM_HDR_T_5GHZ_DBM(ee->ee_header);
480
481         for (mode = AR5K_EEPROM_MODE_11A; mode <= AR5K_EEPROM_MODE_11G; mode++) {
482                 offset = mode_offset[mode];
483
484                 ret = ath5k_eeprom_read_ants(ah, &offset, mode);
485                 if (ret)
486                         return ret;
487
488                 ret = ath5k_eeprom_read_modes(ah, &offset, mode);
489                 if (ret)
490                         return ret;
491         }
492
493         /* override for older eeprom versions for better performance */
494         if (ah->ah_ee_version <= AR5K_EEPROM_VERSION_3_2) {
495                 ee->ee_thr_62[AR5K_EEPROM_MODE_11A] = 15;
496                 ee->ee_thr_62[AR5K_EEPROM_MODE_11B] = 28;
497                 ee->ee_thr_62[AR5K_EEPROM_MODE_11G] = 28;
498         }
499
500         return 0;
501 }
502
503 /* Read the frequency piers for each mode (mostly used on newer eeproms with 0xff
504  * frequency mask) */
505 static inline int
506 ath5k_eeprom_read_freq_list(struct ath5k_hw *ah, int *offset, int max,
507                         struct ath5k_chan_pcal_info *pc, unsigned int mode)
508 {
509         struct ath5k_eeprom_info *ee = &ah->ah_capabilities.cap_eeprom;
510         int o = *offset;
511         int i = 0;
512         u8 freq1, freq2;
513         int ret;
514         u16 val;
515
516         ee->ee_n_piers[mode] = 0;
517         while(i < max) {
518                 AR5K_EEPROM_READ(o++, val);
519
520                 freq1 = val & 0xff;
521                 if (!freq1)
522                         break;
523
524                 pc[i++].freq = ath5k_eeprom_bin2freq(ee,
525                                 freq1, mode);
526                 ee->ee_n_piers[mode]++;
527
528                 freq2 = (val >> 8) & 0xff;
529                 if (!freq2)
530                         break;
531
532                 pc[i++].freq = ath5k_eeprom_bin2freq(ee,
533                                 freq2, mode);
534                 ee->ee_n_piers[mode]++;
535         }
536
537         /* return new offset */
538         *offset = o;
539
540         return 0;
541 }
542
543 /* Read frequency piers for 802.11a */
544 static int
545 ath5k_eeprom_init_11a_pcal_freq(struct ath5k_hw *ah, int offset)
546 {
547         struct ath5k_eeprom_info *ee = &ah->ah_capabilities.cap_eeprom;
548         struct ath5k_chan_pcal_info *pcal = ee->ee_pwr_cal_a;
549         int i, ret;
550         u16 val;
551         u8 mask;
552
553         if (ee->ee_version >= AR5K_EEPROM_VERSION_3_3) {
554                 ath5k_eeprom_read_freq_list(ah, &offset,
555                         AR5K_EEPROM_N_5GHZ_CHAN, pcal,
556                         AR5K_EEPROM_MODE_11A);
557         } else {
558                 mask = AR5K_EEPROM_FREQ_M(ah->ah_ee_version);
559
560                 AR5K_EEPROM_READ(offset++, val);
561                 pcal[0].freq  = (val >> 9) & mask;
562                 pcal[1].freq  = (val >> 2) & mask;
563                 pcal[2].freq  = (val << 5) & mask;
564
565                 AR5K_EEPROM_READ(offset++, val);
566                 pcal[2].freq |= (val >> 11) & 0x1f;
567                 pcal[3].freq  = (val >> 4) & mask;
568                 pcal[4].freq  = (val << 3) & mask;
569
570                 AR5K_EEPROM_READ(offset++, val);
571                 pcal[4].freq |= (val >> 13) & 0x7;
572                 pcal[5].freq  = (val >> 6) & mask;
573                 pcal[6].freq  = (val << 1) & mask;
574
575                 AR5K_EEPROM_READ(offset++, val);
576                 pcal[6].freq |= (val >> 15) & 0x1;
577                 pcal[7].freq  = (val >> 8) & mask;
578                 pcal[8].freq  = (val >> 1) & mask;
579                 pcal[9].freq  = (val << 6) & mask;
580
581                 AR5K_EEPROM_READ(offset++, val);
582                 pcal[9].freq |= (val >> 10) & 0x3f;
583
584                 /* Fixed number of piers */
585                 ee->ee_n_piers[AR5K_EEPROM_MODE_11A] = 10;
586
587                 for (i = 0; i < AR5K_EEPROM_N_5GHZ_CHAN; i++) {
588                         pcal[i].freq = ath5k_eeprom_bin2freq(ee,
589                                 pcal[i].freq, AR5K_EEPROM_MODE_11A);
590                 }
591         }
592
593         return 0;
594 }
595
596 /* Read frequency piers for 802.11bg on eeprom versions >= 5 and eemap >= 2 */
597 static inline int
598 ath5k_eeprom_init_11bg_2413(struct ath5k_hw *ah, unsigned int mode, int offset)
599 {
600         struct ath5k_eeprom_info *ee = &ah->ah_capabilities.cap_eeprom;
601         struct ath5k_chan_pcal_info *pcal;
602
603         switch(mode) {
604         case AR5K_EEPROM_MODE_11B:
605                 pcal = ee->ee_pwr_cal_b;
606                 break;
607         case AR5K_EEPROM_MODE_11G:
608                 pcal = ee->ee_pwr_cal_g;
609                 break;
610         default:
611                 return -EINVAL;
612         }
613
614         ath5k_eeprom_read_freq_list(ah, &offset,
615                 AR5K_EEPROM_N_2GHZ_CHAN_2413, pcal,
616                 mode);
617
618         return 0;
619 }
620
621 /*
622  * Read power calibration for RF5111 chips
623  *
624  * For RF5111 we have an XPD -eXternal Power Detector- curve
625  * for each calibrated channel. Each curve has 0,5dB Power steps
626  * on x axis and PCDAC steps (offsets) on y axis and looks like an
627  * exponential function. To recreate the curve we read 11 points
628  * here and interpolate later.
629  */
630
631 /* Used to match PCDAC steps with power values on RF5111 chips
632  * (eeprom versions < 4). For RF5111 we have 11 pre-defined PCDAC
633  * steps that match with the power values we read from eeprom. On
634  * older eeprom versions (< 3.2) these steps are equaly spaced at
635  * 10% of the pcdac curve -until the curve reaches it's maximum-
636  * (11 steps from 0 to 100%) but on newer eeprom versions (>= 3.2)
637  * these 11 steps are spaced in a different way. This function returns
638  * the pcdac steps based on eeprom version and curve min/max so that we
639  * can have pcdac/pwr points.
640  */
641 static inline void
642 ath5k_get_pcdac_intercepts(struct ath5k_hw *ah, u8 min, u8 max, u8 *vp)
643 {
644         static const u16 intercepts3[] =
645                 { 0, 5, 10, 20, 30, 50, 70, 85, 90, 95, 100 };
646         static const u16 intercepts3_2[] =
647                 { 0, 10, 20, 30, 40, 50, 60, 70, 80, 90, 100 };
648         const u16 *ip;
649         int i;
650
651         if (ah->ah_ee_version >= AR5K_EEPROM_VERSION_3_2)
652                 ip = intercepts3_2;
653         else
654                 ip = intercepts3;
655
656         for (i = 0; i < ARRAY_SIZE(intercepts3); i++)
657                 vp[i] = (ip[i] * max + (100 - ip[i]) * min) / 100;
658 }
659
660 /* Convert RF5111 specific data to generic raw data
661  * used by interpolation code */
662 static int
663 ath5k_eeprom_convert_pcal_info_5111(struct ath5k_hw *ah, int mode,
664                                 struct ath5k_chan_pcal_info *chinfo)
665 {
666         struct ath5k_eeprom_info *ee = &ah->ah_capabilities.cap_eeprom;
667         struct ath5k_chan_pcal_info_rf5111 *pcinfo;
668         struct ath5k_pdgain_info *pd;
669         u8 pier, point, idx;
670         u8 *pdgain_idx = ee->ee_pdc_to_idx[mode];
671
672         /* Fill raw data for each calibration pier */
673         for (pier = 0; pier < ee->ee_n_piers[mode]; pier++) {
674
675                 pcinfo = &chinfo[pier].rf5111_info;
676
677                 /* Allocate pd_curves for this cal pier */
678                 chinfo[pier].pd_curves =
679                         kcalloc(AR5K_EEPROM_N_PD_CURVES,
680                                 sizeof(struct ath5k_pdgain_info),
681                                 GFP_KERNEL);
682
683                 if (!chinfo[pier].pd_curves)
684                         return -ENOMEM;
685
686                 /* Only one curve for RF5111
687                  * find out which one and place
688                  * in in pd_curves.
689                  * Note: ee_x_gain is reversed here */
690                 for (idx = 0; idx < AR5K_EEPROM_N_PD_CURVES; idx++) {
691
692                         if (!((ee->ee_x_gain[mode] >> idx) & 0x1)) {
693                                 pdgain_idx[0] = idx;
694                                 break;
695                         }
696                 }
697
698                 ee->ee_pd_gains[mode] = 1;
699
700                 pd = &chinfo[pier].pd_curves[idx];
701
702                 pd->pd_points = AR5K_EEPROM_N_PWR_POINTS_5111;
703
704                 /* Allocate pd points for this curve */
705                 pd->pd_step = kcalloc(AR5K_EEPROM_N_PWR_POINTS_5111,
706                                         sizeof(u8), GFP_KERNEL);
707                 if (!pd->pd_step)
708                         return -ENOMEM;
709
710                 pd->pd_pwr = kcalloc(AR5K_EEPROM_N_PWR_POINTS_5111,
711                                         sizeof(s16), GFP_KERNEL);
712                 if (!pd->pd_pwr)
713                         return -ENOMEM;
714
715                 /* Fill raw dataset
716                  * (convert power to 0.25dB units
717                  * for RF5112 combatibility) */
718                 for (point = 0; point < pd->pd_points; point++) {
719
720                         /* Absolute values */
721                         pd->pd_pwr[point] = 2 * pcinfo->pwr[point];
722
723                         /* Already sorted */
724                         pd->pd_step[point] = pcinfo->pcdac[point];
725                 }
726
727                 /* Set min/max pwr */
728                 chinfo[pier].min_pwr = pd->pd_pwr[0];
729                 chinfo[pier].max_pwr = pd->pd_pwr[10];
730
731         }
732
733         return 0;
734 }
735
736 /* Parse EEPROM data */
737 static int
738 ath5k_eeprom_read_pcal_info_5111(struct ath5k_hw *ah, int mode)
739 {
740         struct ath5k_eeprom_info *ee = &ah->ah_capabilities.cap_eeprom;
741         struct ath5k_chan_pcal_info *pcal;
742         int offset, ret;
743         int i;
744         u16 val;
745
746         offset = AR5K_EEPROM_GROUPS_START(ee->ee_version);
747         switch(mode) {
748         case AR5K_EEPROM_MODE_11A:
749                 if (!AR5K_EEPROM_HDR_11A(ee->ee_header))
750                         return 0;
751
752                 ret = ath5k_eeprom_init_11a_pcal_freq(ah,
753                         offset + AR5K_EEPROM_GROUP1_OFFSET);
754                 if (ret < 0)
755                         return ret;
756
757                 offset += AR5K_EEPROM_GROUP2_OFFSET;
758                 pcal = ee->ee_pwr_cal_a;
759                 break;
760         case AR5K_EEPROM_MODE_11B:
761                 if (!AR5K_EEPROM_HDR_11B(ee->ee_header) &&
762                     !AR5K_EEPROM_HDR_11G(ee->ee_header))
763                         return 0;
764
765                 pcal = ee->ee_pwr_cal_b;
766                 offset += AR5K_EEPROM_GROUP3_OFFSET;
767
768                 /* fixed piers */
769                 pcal[0].freq = 2412;
770                 pcal[1].freq = 2447;
771                 pcal[2].freq = 2484;
772                 ee->ee_n_piers[mode] = 3;
773                 break;
774         case AR5K_EEPROM_MODE_11G:
775                 if (!AR5K_EEPROM_HDR_11G(ee->ee_header))
776                         return 0;
777
778                 pcal = ee->ee_pwr_cal_g;
779                 offset += AR5K_EEPROM_GROUP4_OFFSET;
780
781                 /* fixed piers */
782                 pcal[0].freq = 2312;
783                 pcal[1].freq = 2412;
784                 pcal[2].freq = 2484;
785                 ee->ee_n_piers[mode] = 3;
786                 break;
787         default:
788                 return -EINVAL;
789         }
790
791         for (i = 0; i < ee->ee_n_piers[mode]; i++) {
792                 struct ath5k_chan_pcal_info_rf5111 *cdata =
793                         &pcal[i].rf5111_info;
794
795                 AR5K_EEPROM_READ(offset++, val);
796                 cdata->pcdac_max = ((val >> 10) & AR5K_EEPROM_PCDAC_M);
797                 cdata->pcdac_min = ((val >> 4) & AR5K_EEPROM_PCDAC_M);
798                 cdata->pwr[0] = ((val << 2) & AR5K_EEPROM_POWER_M);
799
800                 AR5K_EEPROM_READ(offset++, val);
801                 cdata->pwr[0] |= ((val >> 14) & 0x3);
802                 cdata->pwr[1] = ((val >> 8) & AR5K_EEPROM_POWER_M);
803                 cdata->pwr[2] = ((val >> 2) & AR5K_EEPROM_POWER_M);
804                 cdata->pwr[3] = ((val << 4) & AR5K_EEPROM_POWER_M);
805
806                 AR5K_EEPROM_READ(offset++, val);
807                 cdata->pwr[3] |= ((val >> 12) & 0xf);
808                 cdata->pwr[4] = ((val >> 6) & AR5K_EEPROM_POWER_M);
809                 cdata->pwr[5] = (val  & AR5K_EEPROM_POWER_M);
810
811                 AR5K_EEPROM_READ(offset++, val);
812                 cdata->pwr[6] = ((val >> 10) & AR5K_EEPROM_POWER_M);
813                 cdata->pwr[7] = ((val >> 4) & AR5K_EEPROM_POWER_M);
814                 cdata->pwr[8] = ((val << 2) & AR5K_EEPROM_POWER_M);
815
816                 AR5K_EEPROM_READ(offset++, val);
817                 cdata->pwr[8] |= ((val >> 14) & 0x3);
818                 cdata->pwr[9] = ((val >> 8) & AR5K_EEPROM_POWER_M);
819                 cdata->pwr[10] = ((val >> 2) & AR5K_EEPROM_POWER_M);
820
821                 ath5k_get_pcdac_intercepts(ah, cdata->pcdac_min,
822                         cdata->pcdac_max, cdata->pcdac);
823         }
824
825         return ath5k_eeprom_convert_pcal_info_5111(ah, mode, pcal);
826 }
827
828
829 /*
830  * Read power calibration for RF5112 chips
831  *
832  * For RF5112 we have 4 XPD -eXternal Power Detector- curves
833  * for each calibrated channel on 0, -6, -12 and -18dbm but we only
834  * use the higher (3) and the lower (0) curves. Each curve has 0.5dB
835  * power steps on x axis and PCDAC steps on y axis and looks like a
836  * linear function. To recreate the curve and pass the power values
837  * on hw, we read 4 points for xpd 0 (lower gain -> max power)
838  * and 3 points for xpd 3 (higher gain -> lower power) here and
839  * interpolate later.
840  *
841  * Note: Many vendors just use xpd 0 so xpd 3 is zeroed.
842  */
843
844 /* Convert RF5112 specific data to generic raw data
845  * used by interpolation code */
846 static int
847 ath5k_eeprom_convert_pcal_info_5112(struct ath5k_hw *ah, int mode,
848                                 struct ath5k_chan_pcal_info *chinfo)
849 {
850         struct ath5k_eeprom_info *ee = &ah->ah_capabilities.cap_eeprom;
851         struct ath5k_chan_pcal_info_rf5112 *pcinfo;
852         u8 *pdgain_idx = ee->ee_pdc_to_idx[mode];
853         unsigned int pier, pdg, point;
854
855         /* Fill raw data for each calibration pier */
856         for (pier = 0; pier < ee->ee_n_piers[mode]; pier++) {
857
858                 pcinfo = &chinfo[pier].rf5112_info;
859
860                 /* Allocate pd_curves for this cal pier */
861                 chinfo[pier].pd_curves =
862                                 kcalloc(AR5K_EEPROM_N_PD_CURVES,
863                                         sizeof(struct ath5k_pdgain_info),
864                                         GFP_KERNEL);
865
866                 if (!chinfo[pier].pd_curves)
867                         return -ENOMEM;
868
869                 /* Fill pd_curves */
870                 for (pdg = 0; pdg < ee->ee_pd_gains[mode]; pdg++) {
871
872                         u8 idx = pdgain_idx[pdg];
873                         struct ath5k_pdgain_info *pd =
874                                         &chinfo[pier].pd_curves[idx];
875
876                         /* Lowest gain curve (max power) */
877                         if (pdg == 0) {
878                                 /* One more point for better accuracy */
879                                 pd->pd_points = AR5K_EEPROM_N_XPD0_POINTS;
880
881                                 /* Allocate pd points for this curve */
882                                 pd->pd_step = kcalloc(pd->pd_points,
883                                                 sizeof(u8), GFP_KERNEL);
884
885                                 if (!pd->pd_step)
886                                         return -ENOMEM;
887
888                                 pd->pd_pwr = kcalloc(pd->pd_points,
889                                                 sizeof(s16), GFP_KERNEL);
890
891                                 if (!pd->pd_pwr)
892                                         return -ENOMEM;
893
894
895                                 /* Fill raw dataset
896                                  * (all power levels are in 0.25dB units) */
897                                 pd->pd_step[0] = pcinfo->pcdac_x0[0];
898                                 pd->pd_pwr[0] = pcinfo->pwr_x0[0];
899
900                                 for (point = 1; point < pd->pd_points;
901                                 point++) {
902                                         /* Absolute values */
903                                         pd->pd_pwr[point] =
904                                                 pcinfo->pwr_x0[point];
905
906                                         /* Deltas */
907                                         pd->pd_step[point] =
908                                                 pd->pd_step[point - 1] +
909                                                 pcinfo->pcdac_x0[point];
910                                 }
911
912                                 /* Set min power for this frequency */
913                                 chinfo[pier].min_pwr = pd->pd_pwr[0];
914
915                         /* Highest gain curve (min power) */
916                         } else if (pdg == 1) {
917
918                                 pd->pd_points = AR5K_EEPROM_N_XPD3_POINTS;
919
920                                 /* Allocate pd points for this curve */
921                                 pd->pd_step = kcalloc(pd->pd_points,
922                                                 sizeof(u8), GFP_KERNEL);
923
924                                 if (!pd->pd_step)
925                                         return -ENOMEM;
926
927                                 pd->pd_pwr = kcalloc(pd->pd_points,
928                                                 sizeof(s16), GFP_KERNEL);
929
930                                 if (!pd->pd_pwr)
931                                         return -ENOMEM;
932
933                                 /* Fill raw dataset
934                                  * (all power levels are in 0.25dB units) */
935                                 for (point = 0; point < pd->pd_points;
936                                 point++) {
937                                         /* Absolute values */
938                                         pd->pd_pwr[point] =
939                                                 pcinfo->pwr_x3[point];
940
941                                         /* Fixed points */
942                                         pd->pd_step[point] =
943                                                 pcinfo->pcdac_x3[point];
944                                 }
945
946                                 /* Since we have a higher gain curve
947                                  * override min power */
948                                 chinfo[pier].min_pwr = pd->pd_pwr[0];
949                         }
950                 }
951         }
952
953         return 0;
954 }
955
956 /* Parse EEPROM data */
957 static int
958 ath5k_eeprom_read_pcal_info_5112(struct ath5k_hw *ah, int mode)
959 {
960         struct ath5k_eeprom_info *ee = &ah->ah_capabilities.cap_eeprom;
961         struct ath5k_chan_pcal_info_rf5112 *chan_pcal_info;
962         struct ath5k_chan_pcal_info *gen_chan_info;
963         u8 *pdgain_idx = ee->ee_pdc_to_idx[mode];
964         u32 offset;
965         u8 i, c;
966         u16 val;
967         int ret;
968         u8 pd_gains = 0;
969
970         /* Count how many curves we have and
971          * identify them (which one of the 4
972          * available curves we have on each count).
973          * Curves are stored from lower (x0) to
974          * higher (x3) gain */
975         for (i = 0; i < AR5K_EEPROM_N_PD_CURVES; i++) {
976                 /* ee_x_gain[mode] is x gain mask */
977                 if ((ee->ee_x_gain[mode] >> i) & 0x1)
978                         pdgain_idx[pd_gains++] = i;
979         }
980         ee->ee_pd_gains[mode] = pd_gains;
981
982         if (pd_gains == 0 || pd_gains > 2)
983                 return -EINVAL;
984
985         switch (mode) {
986         case AR5K_EEPROM_MODE_11A:
987                 /*
988                  * Read 5GHz EEPROM channels
989                  */
990                 offset = AR5K_EEPROM_GROUPS_START(ee->ee_version);
991                 ath5k_eeprom_init_11a_pcal_freq(ah, offset);
992
993                 offset += AR5K_EEPROM_GROUP2_OFFSET;
994                 gen_chan_info = ee->ee_pwr_cal_a;
995                 break;
996         case AR5K_EEPROM_MODE_11B:
997                 offset = AR5K_EEPROM_GROUPS_START(ee->ee_version);
998                 if (AR5K_EEPROM_HDR_11A(ee->ee_header))
999                         offset += AR5K_EEPROM_GROUP3_OFFSET;
1000
1001                 /* NB: frequency piers parsed during mode init */
1002                 gen_chan_info = ee->ee_pwr_cal_b;
1003                 break;
1004         case AR5K_EEPROM_MODE_11G:
1005                 offset = AR5K_EEPROM_GROUPS_START(ee->ee_version);
1006                 if (AR5K_EEPROM_HDR_11A(ee->ee_header))
1007                         offset += AR5K_EEPROM_GROUP4_OFFSET;
1008                 else if (AR5K_EEPROM_HDR_11B(ee->ee_header))
1009                         offset += AR5K_EEPROM_GROUP2_OFFSET;
1010
1011                 /* NB: frequency piers parsed during mode init */
1012                 gen_chan_info = ee->ee_pwr_cal_g;
1013                 break;
1014         default:
1015                 return -EINVAL;
1016         }
1017
1018         for (i = 0; i < ee->ee_n_piers[mode]; i++) {
1019                 chan_pcal_info = &gen_chan_info[i].rf5112_info;
1020
1021                 /* Power values in quarter dB
1022                  * for the lower xpd gain curve
1023                  * (0 dBm -> higher output power) */
1024                 for (c = 0; c < AR5K_EEPROM_N_XPD0_POINTS; c++) {
1025                         AR5K_EEPROM_READ(offset++, val);
1026                         chan_pcal_info->pwr_x0[c] = (s8) (val & 0xff);
1027                         chan_pcal_info->pwr_x0[++c] = (s8) ((val >> 8) & 0xff);
1028                 }
1029
1030                 /* PCDAC steps
1031                  * corresponding to the above power
1032                  * measurements */
1033                 AR5K_EEPROM_READ(offset++, val);
1034                 chan_pcal_info->pcdac_x0[1] = (val & 0x1f);
1035                 chan_pcal_info->pcdac_x0[2] = ((val >> 5) & 0x1f);
1036                 chan_pcal_info->pcdac_x0[3] = ((val >> 10) & 0x1f);
1037
1038                 /* Power values in quarter dB
1039                  * for the higher xpd gain curve
1040                  * (18 dBm -> lower output power) */
1041                 AR5K_EEPROM_READ(offset++, val);
1042                 chan_pcal_info->pwr_x3[0] = (s8) (val & 0xff);
1043                 chan_pcal_info->pwr_x3[1] = (s8) ((val >> 8) & 0xff);
1044
1045                 AR5K_EEPROM_READ(offset++, val);
1046                 chan_pcal_info->pwr_x3[2] = (val & 0xff);
1047
1048                 /* PCDAC steps
1049                  * corresponding to the above power
1050                  * measurements (fixed) */
1051                 chan_pcal_info->pcdac_x3[0] = 20;
1052                 chan_pcal_info->pcdac_x3[1] = 35;
1053                 chan_pcal_info->pcdac_x3[2] = 63;
1054
1055                 if (ee->ee_version >= AR5K_EEPROM_VERSION_4_3) {
1056                         chan_pcal_info->pcdac_x0[0] = ((val >> 8) & 0x3f);
1057
1058                         /* Last xpd0 power level is also channel maximum */
1059                         gen_chan_info[i].max_pwr = chan_pcal_info->pwr_x0[3];
1060                 } else {
1061                         chan_pcal_info->pcdac_x0[0] = 1;
1062                         gen_chan_info[i].max_pwr = (s8) ((val >> 8) & 0xff);
1063                 }
1064
1065         }
1066
1067         return ath5k_eeprom_convert_pcal_info_5112(ah, mode, gen_chan_info);
1068 }
1069
1070
1071 /*
1072  * Read power calibration for RF2413 chips
1073  *
1074  * For RF2413 we have a Power to PDDAC table (Power Detector)
1075  * instead of a PCDAC and 4 pd gain curves for each calibrated channel.
1076  * Each curve has power on x axis in 0.5 db steps and PDDADC steps on y
1077  * axis and looks like an exponential function like the RF5111 curve.
1078  *
1079  * To recreate the curves we read here the points and interpolate
1080  * later. Note that in most cases only 2 (higher and lower) curves are
1081  * used (like RF5112) but vendors have the oportunity to include all
1082  * 4 curves on eeprom. The final curve (higher power) has an extra
1083  * point for better accuracy like RF5112.
1084  */
1085
1086 /* For RF2413 power calibration data doesn't start on a fixed location and
1087  * if a mode is not supported, it's section is missing -not zeroed-.
1088  * So we need to calculate the starting offset for each section by using
1089  * these two functions */
1090
1091 /* Return the size of each section based on the mode and the number of pd
1092  * gains available (maximum 4). */
1093 static inline unsigned int
1094 ath5k_pdgains_size_2413(struct ath5k_eeprom_info *ee, unsigned int mode)
1095 {
1096         static const unsigned int pdgains_size[] = { 4, 6, 9, 12 };
1097         unsigned int sz;
1098
1099         sz = pdgains_size[ee->ee_pd_gains[mode] - 1];
1100         sz *= ee->ee_n_piers[mode];
1101
1102         return sz;
1103 }
1104
1105 /* Return the starting offset for a section based on the modes supported
1106  * and each section's size. */
1107 static unsigned int
1108 ath5k_cal_data_offset_2413(struct ath5k_eeprom_info *ee, int mode)
1109 {
1110         u32 offset = AR5K_EEPROM_CAL_DATA_START(ee->ee_misc4);
1111
1112         switch(mode) {
1113         case AR5K_EEPROM_MODE_11G:
1114                 if (AR5K_EEPROM_HDR_11B(ee->ee_header))
1115                         offset += ath5k_pdgains_size_2413(ee,
1116                                         AR5K_EEPROM_MODE_11B) +
1117                                         AR5K_EEPROM_N_2GHZ_CHAN_2413 / 2;
1118                 /* fall through */
1119         case AR5K_EEPROM_MODE_11B:
1120                 if (AR5K_EEPROM_HDR_11A(ee->ee_header))
1121                         offset += ath5k_pdgains_size_2413(ee,
1122                                         AR5K_EEPROM_MODE_11A) +
1123                                         AR5K_EEPROM_N_5GHZ_CHAN / 2;
1124                 /* fall through */
1125         case AR5K_EEPROM_MODE_11A:
1126                 break;
1127         default:
1128                 break;
1129         }
1130
1131         return offset;
1132 }
1133
1134 /* Convert RF2413 specific data to generic raw data
1135  * used by interpolation code */
1136 static int
1137 ath5k_eeprom_convert_pcal_info_2413(struct ath5k_hw *ah, int mode,
1138                                 struct ath5k_chan_pcal_info *chinfo)
1139 {
1140         struct ath5k_eeprom_info *ee = &ah->ah_capabilities.cap_eeprom;
1141         struct ath5k_chan_pcal_info_rf2413 *pcinfo;
1142         u8 *pdgain_idx = ee->ee_pdc_to_idx[mode];
1143         unsigned int pier, pdg, point;
1144
1145         /* Fill raw data for each calibration pier */
1146         for (pier = 0; pier < ee->ee_n_piers[mode]; pier++) {
1147
1148                 pcinfo = &chinfo[pier].rf2413_info;
1149
1150                 /* Allocate pd_curves for this cal pier */
1151                 chinfo[pier].pd_curves =
1152                                 kcalloc(AR5K_EEPROM_N_PD_CURVES,
1153                                         sizeof(struct ath5k_pdgain_info),
1154                                         GFP_KERNEL);
1155
1156                 if (!chinfo[pier].pd_curves)
1157                         return -ENOMEM;
1158
1159                 /* Fill pd_curves */
1160                 for (pdg = 0; pdg < ee->ee_pd_gains[mode]; pdg++) {
1161
1162                         u8 idx = pdgain_idx[pdg];
1163                         struct ath5k_pdgain_info *pd =
1164                                         &chinfo[pier].pd_curves[idx];
1165
1166                         /* One more point for the highest power
1167                          * curve (lowest gain) */
1168                         if (pdg == ee->ee_pd_gains[mode] - 1)
1169                                 pd->pd_points = AR5K_EEPROM_N_PD_POINTS;
1170                         else
1171                                 pd->pd_points = AR5K_EEPROM_N_PD_POINTS - 1;
1172
1173                         /* Allocate pd points for this curve */
1174                         pd->pd_step = kcalloc(pd->pd_points,
1175                                         sizeof(u8), GFP_KERNEL);
1176
1177                         if (!pd->pd_step)
1178                                 return -ENOMEM;
1179
1180                         pd->pd_pwr = kcalloc(pd->pd_points,
1181                                         sizeof(s16), GFP_KERNEL);
1182
1183                         if (!pd->pd_pwr)
1184                                 return -ENOMEM;
1185
1186                         /* Fill raw dataset
1187                          * convert all pwr levels to
1188                          * quarter dB for RF5112 combatibility */
1189                         pd->pd_step[0] = pcinfo->pddac_i[pdg];
1190                         pd->pd_pwr[0] = 4 * pcinfo->pwr_i[pdg];
1191
1192                         for (point = 1; point < pd->pd_points; point++) {
1193
1194                                 pd->pd_pwr[point] = pd->pd_pwr[point - 1] +
1195                                         2 * pcinfo->pwr[pdg][point - 1];
1196
1197                                 pd->pd_step[point] = pd->pd_step[point - 1] +
1198                                                 pcinfo->pddac[pdg][point - 1];
1199
1200                         }
1201
1202                         /* Highest gain curve -> min power */
1203                         if (pdg == 0)
1204                                 chinfo[pier].min_pwr = pd->pd_pwr[0];
1205
1206                         /* Lowest gain curve -> max power */
1207                         if (pdg == ee->ee_pd_gains[mode] - 1)
1208                                 chinfo[pier].max_pwr =
1209                                         pd->pd_pwr[pd->pd_points - 1];
1210                 }
1211         }
1212
1213         return 0;
1214 }
1215
1216 /* Parse EEPROM data */
1217 static int
1218 ath5k_eeprom_read_pcal_info_2413(struct ath5k_hw *ah, int mode)
1219 {
1220         struct ath5k_eeprom_info *ee = &ah->ah_capabilities.cap_eeprom;
1221         struct ath5k_chan_pcal_info_rf2413 *pcinfo;
1222         struct ath5k_chan_pcal_info *chinfo;
1223         u8 *pdgain_idx = ee->ee_pdc_to_idx[mode];
1224         u32 offset;
1225         int idx, i, ret;
1226         u16 val;
1227         u8 pd_gains = 0;
1228
1229         /* Count how many curves we have and
1230          * identify them (which one of the 4
1231          * available curves we have on each count).
1232          * Curves are stored from higher to
1233          * lower gain so we go backwards */
1234         for (idx = AR5K_EEPROM_N_PD_CURVES - 1; idx >= 0; idx--) {
1235                 /* ee_x_gain[mode] is x gain mask */
1236                 if ((ee->ee_x_gain[mode] >> idx) & 0x1)
1237                         pdgain_idx[pd_gains++] = idx;
1238
1239         }
1240         ee->ee_pd_gains[mode] = pd_gains;
1241
1242         if (pd_gains == 0)
1243                 return -EINVAL;
1244
1245         offset = ath5k_cal_data_offset_2413(ee, mode);
1246         switch (mode) {
1247         case AR5K_EEPROM_MODE_11A:
1248                 if (!AR5K_EEPROM_HDR_11A(ee->ee_header))
1249                         return 0;
1250
1251                 ath5k_eeprom_init_11a_pcal_freq(ah, offset);
1252                 offset += AR5K_EEPROM_N_5GHZ_CHAN / 2;
1253                 chinfo = ee->ee_pwr_cal_a;
1254                 break;
1255         case AR5K_EEPROM_MODE_11B:
1256                 if (!AR5K_EEPROM_HDR_11B(ee->ee_header))
1257                         return 0;
1258
1259                 ath5k_eeprom_init_11bg_2413(ah, mode, offset);
1260                 offset += AR5K_EEPROM_N_2GHZ_CHAN_2413 / 2;
1261                 chinfo = ee->ee_pwr_cal_b;
1262                 break;
1263         case AR5K_EEPROM_MODE_11G:
1264                 if (!AR5K_EEPROM_HDR_11G(ee->ee_header))
1265                         return 0;
1266
1267                 ath5k_eeprom_init_11bg_2413(ah, mode, offset);
1268                 offset += AR5K_EEPROM_N_2GHZ_CHAN_2413 / 2;
1269                 chinfo = ee->ee_pwr_cal_g;
1270                 break;
1271         default:
1272                 return -EINVAL;
1273         }
1274
1275         for (i = 0; i < ee->ee_n_piers[mode]; i++) {
1276                 pcinfo = &chinfo[i].rf2413_info;
1277
1278                 /*
1279                  * Read pwr_i, pddac_i and the first
1280                  * 2 pd points (pwr, pddac)
1281                  */
1282                 AR5K_EEPROM_READ(offset++, val);
1283                 pcinfo->pwr_i[0] = val & 0x1f;
1284                 pcinfo->pddac_i[0] = (val >> 5) & 0x7f;
1285                 pcinfo->pwr[0][0] = (val >> 12) & 0xf;
1286
1287                 AR5K_EEPROM_READ(offset++, val);
1288                 pcinfo->pddac[0][0] = val & 0x3f;
1289                 pcinfo->pwr[0][1] = (val >> 6) & 0xf;
1290                 pcinfo->pddac[0][1] = (val >> 10) & 0x3f;
1291
1292                 AR5K_EEPROM_READ(offset++, val);
1293                 pcinfo->pwr[0][2] = val & 0xf;
1294                 pcinfo->pddac[0][2] = (val >> 4) & 0x3f;
1295
1296                 pcinfo->pwr[0][3] = 0;
1297                 pcinfo->pddac[0][3] = 0;
1298
1299                 if (pd_gains > 1) {
1300                         /*
1301                          * Pd gain 0 is not the last pd gain
1302                          * so it only has 2 pd points.
1303                          * Continue wih pd gain 1.
1304                          */
1305                         pcinfo->pwr_i[1] = (val >> 10) & 0x1f;
1306
1307                         pcinfo->pddac_i[1] = (val >> 15) & 0x1;
1308                         AR5K_EEPROM_READ(offset++, val);
1309                         pcinfo->pddac_i[1] |= (val & 0x3F) << 1;
1310
1311                         pcinfo->pwr[1][0] = (val >> 6) & 0xf;
1312                         pcinfo->pddac[1][0] = (val >> 10) & 0x3f;
1313
1314                         AR5K_EEPROM_READ(offset++, val);
1315                         pcinfo->pwr[1][1] = val & 0xf;
1316                         pcinfo->pddac[1][1] = (val >> 4) & 0x3f;
1317                         pcinfo->pwr[1][2] = (val >> 10) & 0xf;
1318
1319                         pcinfo->pddac[1][2] = (val >> 14) & 0x3;
1320                         AR5K_EEPROM_READ(offset++, val);
1321                         pcinfo->pddac[1][2] |= (val & 0xF) << 2;
1322
1323                         pcinfo->pwr[1][3] = 0;
1324                         pcinfo->pddac[1][3] = 0;
1325                 } else if (pd_gains == 1) {
1326                         /*
1327                          * Pd gain 0 is the last one so
1328                          * read the extra point.
1329                          */
1330                         pcinfo->pwr[0][3] = (val >> 10) & 0xf;
1331
1332                         pcinfo->pddac[0][3] = (val >> 14) & 0x3;
1333                         AR5K_EEPROM_READ(offset++, val);
1334                         pcinfo->pddac[0][3] |= (val & 0xF) << 2;
1335                 }
1336
1337                 /*
1338                  * Proceed with the other pd_gains
1339                  * as above.
1340                  */
1341                 if (pd_gains > 2) {
1342                         pcinfo->pwr_i[2] = (val >> 4) & 0x1f;
1343                         pcinfo->pddac_i[2] = (val >> 9) & 0x7f;
1344
1345                         AR5K_EEPROM_READ(offset++, val);
1346                         pcinfo->pwr[2][0] = (val >> 0) & 0xf;
1347                         pcinfo->pddac[2][0] = (val >> 4) & 0x3f;
1348                         pcinfo->pwr[2][1] = (val >> 10) & 0xf;
1349
1350                         pcinfo->pddac[2][1] = (val >> 14) & 0x3;
1351                         AR5K_EEPROM_READ(offset++, val);
1352                         pcinfo->pddac[2][1] |= (val & 0xF) << 2;
1353
1354                         pcinfo->pwr[2][2] = (val >> 4) & 0xf;
1355                         pcinfo->pddac[2][2] = (val >> 8) & 0x3f;
1356
1357                         pcinfo->pwr[2][3] = 0;
1358                         pcinfo->pddac[2][3] = 0;
1359                 } else if (pd_gains == 2) {
1360                         pcinfo->pwr[1][3] = (val >> 4) & 0xf;
1361                         pcinfo->pddac[1][3] = (val >> 8) & 0x3f;
1362                 }
1363
1364                 if (pd_gains > 3) {
1365                         pcinfo->pwr_i[3] = (val >> 14) & 0x3;
1366                         AR5K_EEPROM_READ(offset++, val);
1367                         pcinfo->pwr_i[3] |= ((val >> 0) & 0x7) << 2;
1368
1369                         pcinfo->pddac_i[3] = (val >> 3) & 0x7f;
1370                         pcinfo->pwr[3][0] = (val >> 10) & 0xf;
1371                         pcinfo->pddac[3][0] = (val >> 14) & 0x3;
1372
1373                         AR5K_EEPROM_READ(offset++, val);
1374                         pcinfo->pddac[3][0] |= (val & 0xF) << 2;
1375                         pcinfo->pwr[3][1] = (val >> 4) & 0xf;
1376                         pcinfo->pddac[3][1] = (val >> 8) & 0x3f;
1377
1378                         pcinfo->pwr[3][2] = (val >> 14) & 0x3;
1379                         AR5K_EEPROM_READ(offset++, val);
1380                         pcinfo->pwr[3][2] |= ((val >> 0) & 0x3) << 2;
1381
1382                         pcinfo->pddac[3][2] = (val >> 2) & 0x3f;
1383                         pcinfo->pwr[3][3] = (val >> 8) & 0xf;
1384
1385                         pcinfo->pddac[3][3] = (val >> 12) & 0xF;
1386                         AR5K_EEPROM_READ(offset++, val);
1387                         pcinfo->pddac[3][3] |= ((val >> 0) & 0x3) << 4;
1388                 } else if (pd_gains == 3) {
1389                         pcinfo->pwr[2][3] = (val >> 14) & 0x3;
1390                         AR5K_EEPROM_READ(offset++, val);
1391                         pcinfo->pwr[2][3] |= ((val >> 0) & 0x3) << 2;
1392
1393                         pcinfo->pddac[2][3] = (val >> 2) & 0x3f;
1394                 }
1395         }
1396
1397         return ath5k_eeprom_convert_pcal_info_2413(ah, mode, chinfo);
1398 }
1399
1400
1401 /*
1402  * Read per rate target power (this is the maximum tx power
1403  * supported by the card). This info is used when setting
1404  * tx power, no matter the channel.
1405  *
1406  * This also works for v5 EEPROMs.
1407  */
1408 static int
1409 ath5k_eeprom_read_target_rate_pwr_info(struct ath5k_hw *ah, unsigned int mode)
1410 {
1411         struct ath5k_eeprom_info *ee = &ah->ah_capabilities.cap_eeprom;
1412         struct ath5k_rate_pcal_info *rate_pcal_info;
1413         u8 *rate_target_pwr_num;
1414         u32 offset;
1415         u16 val;
1416         int ret, i;
1417
1418         offset = AR5K_EEPROM_TARGET_PWRSTART(ee->ee_misc1);
1419         rate_target_pwr_num = &ee->ee_rate_target_pwr_num[mode];
1420         switch (mode) {
1421         case AR5K_EEPROM_MODE_11A:
1422                 offset += AR5K_EEPROM_TARGET_PWR_OFF_11A(ee->ee_version);
1423                 rate_pcal_info = ee->ee_rate_tpwr_a;
1424                 ee->ee_rate_target_pwr_num[mode] = AR5K_EEPROM_N_5GHZ_CHAN;
1425                 break;
1426         case AR5K_EEPROM_MODE_11B:
1427                 offset += AR5K_EEPROM_TARGET_PWR_OFF_11B(ee->ee_version);
1428                 rate_pcal_info = ee->ee_rate_tpwr_b;
1429                 ee->ee_rate_target_pwr_num[mode] = 2; /* 3rd is g mode's 1st */
1430                 break;
1431         case AR5K_EEPROM_MODE_11G:
1432                 offset += AR5K_EEPROM_TARGET_PWR_OFF_11G(ee->ee_version);
1433                 rate_pcal_info = ee->ee_rate_tpwr_g;
1434                 ee->ee_rate_target_pwr_num[mode] = AR5K_EEPROM_N_2GHZ_CHAN;
1435                 break;
1436         default:
1437                 return -EINVAL;
1438         }
1439
1440         /* Different freq mask for older eeproms (<= v3.2) */
1441         if (ee->ee_version <= AR5K_EEPROM_VERSION_3_2) {
1442                 for (i = 0; i < (*rate_target_pwr_num); i++) {
1443                         AR5K_EEPROM_READ(offset++, val);
1444                         rate_pcal_info[i].freq =
1445                             ath5k_eeprom_bin2freq(ee, (val >> 9) & 0x7f, mode);
1446
1447                         rate_pcal_info[i].target_power_6to24 = ((val >> 3) & 0x3f);
1448                         rate_pcal_info[i].target_power_36 = (val << 3) & 0x3f;
1449
1450                         AR5K_EEPROM_READ(offset++, val);
1451
1452                         if (rate_pcal_info[i].freq == AR5K_EEPROM_CHANNEL_DIS ||
1453                             val == 0) {
1454                                 (*rate_target_pwr_num) = i;
1455                                 break;
1456                         }
1457
1458                         rate_pcal_info[i].target_power_36 |= ((val >> 13) & 0x7);
1459                         rate_pcal_info[i].target_power_48 = ((val >> 7) & 0x3f);
1460                         rate_pcal_info[i].target_power_54 = ((val >> 1) & 0x3f);
1461                 }
1462         } else {
1463                 for (i = 0; i < (*rate_target_pwr_num); i++) {
1464                         AR5K_EEPROM_READ(offset++, val);
1465                         rate_pcal_info[i].freq =
1466                             ath5k_eeprom_bin2freq(ee, (val >> 8) & 0xff, mode);
1467
1468                         rate_pcal_info[i].target_power_6to24 = ((val >> 2) & 0x3f);
1469                         rate_pcal_info[i].target_power_36 = (val << 4) & 0x3f;
1470
1471                         AR5K_EEPROM_READ(offset++, val);
1472
1473                         if (rate_pcal_info[i].freq == AR5K_EEPROM_CHANNEL_DIS ||
1474                             val == 0) {
1475                                 (*rate_target_pwr_num) = i;
1476                                 break;
1477                         }
1478
1479                         rate_pcal_info[i].target_power_36 |= (val >> 12) & 0xf;
1480                         rate_pcal_info[i].target_power_48 = ((val >> 6) & 0x3f);
1481                         rate_pcal_info[i].target_power_54 = (val & 0x3f);
1482                 }
1483         }
1484
1485         return 0;
1486 }
1487
1488 /*
1489  * Read per channel calibration info from EEPROM
1490  *
1491  * This info is used to calibrate the baseband power table. Imagine
1492  * that for each channel there is a power curve that's hw specific
1493  * (depends on amplifier etc) and we try to "correct" this curve using
1494  * offsets we pass on to phy chip (baseband -> before amplifier) so that
1495  * it can use accurate power values when setting tx power (takes amplifier's
1496  * performance on each channel into account).
1497  *
1498  * EEPROM provides us with the offsets for some pre-calibrated channels
1499  * and we have to interpolate to create the full table for these channels and
1500  * also the table for any channel.
1501  */
1502 static int
1503 ath5k_eeprom_read_pcal_info(struct ath5k_hw *ah)
1504 {
1505         struct ath5k_eeprom_info *ee = &ah->ah_capabilities.cap_eeprom;
1506         int (*read_pcal)(struct ath5k_hw *hw, int mode);
1507         int mode;
1508         int err;
1509
1510         if ((ah->ah_ee_version >= AR5K_EEPROM_VERSION_4_0) &&
1511                         (AR5K_EEPROM_EEMAP(ee->ee_misc0) == 1))
1512                 read_pcal = ath5k_eeprom_read_pcal_info_5112;
1513         else if ((ah->ah_ee_version >= AR5K_EEPROM_VERSION_5_0) &&
1514                         (AR5K_EEPROM_EEMAP(ee->ee_misc0) == 2))
1515                 read_pcal = ath5k_eeprom_read_pcal_info_2413;
1516         else
1517                 read_pcal = ath5k_eeprom_read_pcal_info_5111;
1518
1519
1520         for (mode = AR5K_EEPROM_MODE_11A; mode <= AR5K_EEPROM_MODE_11G;
1521         mode++) {
1522                 err = read_pcal(ah, mode);
1523                 if (err)
1524                         return err;
1525
1526                 err = ath5k_eeprom_read_target_rate_pwr_info(ah, mode);
1527                 if (err < 0)
1528                         return err;
1529         }
1530
1531         return 0;
1532 }
1533
1534 static int
1535 ath5k_eeprom_free_pcal_info(struct ath5k_hw *ah, int mode)
1536 {
1537         struct ath5k_eeprom_info *ee = &ah->ah_capabilities.cap_eeprom;
1538         struct ath5k_chan_pcal_info *chinfo;
1539         u8 pier, pdg;
1540
1541         switch (mode) {
1542         case AR5K_EEPROM_MODE_11A:
1543                 if (!AR5K_EEPROM_HDR_11A(ee->ee_header))
1544                         return 0;
1545                 chinfo = ee->ee_pwr_cal_a;
1546                 break;
1547         case AR5K_EEPROM_MODE_11B:
1548                 if (!AR5K_EEPROM_HDR_11B(ee->ee_header))
1549                         return 0;
1550                 chinfo = ee->ee_pwr_cal_b;
1551                 break;
1552         case AR5K_EEPROM_MODE_11G:
1553                 if (!AR5K_EEPROM_HDR_11G(ee->ee_header))
1554                         return 0;
1555                 chinfo = ee->ee_pwr_cal_g;
1556                 break;
1557         default:
1558                 return -EINVAL;
1559         }
1560
1561         for (pier = 0; pier < ee->ee_n_piers[mode]; pier++) {
1562                 if (!chinfo[pier].pd_curves)
1563                         continue;
1564
1565                 for (pdg = 0; pdg < ee->ee_pd_gains[mode]; pdg++) {
1566                         struct ath5k_pdgain_info *pd =
1567                                         &chinfo[pier].pd_curves[pdg];
1568
1569                         if (pd != NULL) {
1570                                 kfree(pd->pd_step);
1571                                 kfree(pd->pd_pwr);
1572                         }
1573                 }
1574
1575                 kfree(chinfo[pier].pd_curves);
1576         }
1577
1578         return 0;
1579 }
1580
1581 void
1582 ath5k_eeprom_detach(struct ath5k_hw *ah)
1583 {
1584         u8 mode;
1585
1586         for (mode = AR5K_EEPROM_MODE_11A; mode <= AR5K_EEPROM_MODE_11G; mode++)
1587                 ath5k_eeprom_free_pcal_info(ah, mode);
1588 }
1589
1590 /* Read conformance test limits used for regulatory control */
1591 static int
1592 ath5k_eeprom_read_ctl_info(struct ath5k_hw *ah)
1593 {
1594         struct ath5k_eeprom_info *ee = &ah->ah_capabilities.cap_eeprom;
1595         struct ath5k_edge_power *rep;
1596         unsigned int fmask, pmask;
1597         unsigned int ctl_mode;
1598         int ret, i, j;
1599         u32 offset;
1600         u16 val;
1601
1602         pmask = AR5K_EEPROM_POWER_M;
1603         fmask = AR5K_EEPROM_FREQ_M(ee->ee_version);
1604         offset = AR5K_EEPROM_CTL(ee->ee_version);
1605         ee->ee_ctls = AR5K_EEPROM_N_CTLS(ee->ee_version);
1606         for (i = 0; i < ee->ee_ctls; i += 2) {
1607                 AR5K_EEPROM_READ(offset++, val);
1608                 ee->ee_ctl[i] = (val >> 8) & 0xff;
1609                 ee->ee_ctl[i + 1] = val & 0xff;
1610         }
1611
1612         offset = AR5K_EEPROM_GROUP8_OFFSET;
1613         if (ee->ee_version >= AR5K_EEPROM_VERSION_4_0)
1614                 offset += AR5K_EEPROM_TARGET_PWRSTART(ee->ee_misc1) -
1615                         AR5K_EEPROM_GROUP5_OFFSET;
1616         else
1617                 offset += AR5K_EEPROM_GROUPS_START(ee->ee_version);
1618
1619         rep = ee->ee_ctl_pwr;
1620         for(i = 0; i < ee->ee_ctls; i++) {
1621                 switch(ee->ee_ctl[i] & AR5K_CTL_MODE_M) {
1622                 case AR5K_CTL_11A:
1623                 case AR5K_CTL_TURBO:
1624                         ctl_mode = AR5K_EEPROM_MODE_11A;
1625                         break;
1626                 default:
1627                         ctl_mode = AR5K_EEPROM_MODE_11G;
1628                         break;
1629                 }
1630                 if (ee->ee_ctl[i] == 0) {
1631                         if (ee->ee_version >= AR5K_EEPROM_VERSION_3_3)
1632                                 offset += 8;
1633                         else
1634                                 offset += 7;
1635                         rep += AR5K_EEPROM_N_EDGES;
1636                         continue;
1637                 }
1638                 if (ee->ee_version >= AR5K_EEPROM_VERSION_3_3) {
1639                         for (j = 0; j < AR5K_EEPROM_N_EDGES; j += 2) {
1640                                 AR5K_EEPROM_READ(offset++, val);
1641                                 rep[j].freq = (val >> 8) & fmask;
1642                                 rep[j + 1].freq = val & fmask;
1643                         }
1644                         for (j = 0; j < AR5K_EEPROM_N_EDGES; j += 2) {
1645                                 AR5K_EEPROM_READ(offset++, val);
1646                                 rep[j].edge = (val >> 8) & pmask;
1647                                 rep[j].flag = (val >> 14) & 1;
1648                                 rep[j + 1].edge = val & pmask;
1649                                 rep[j + 1].flag = (val >> 6) & 1;
1650                         }
1651                 } else {
1652                         AR5K_EEPROM_READ(offset++, val);
1653                         rep[0].freq = (val >> 9) & fmask;
1654                         rep[1].freq = (val >> 2) & fmask;
1655                         rep[2].freq = (val << 5) & fmask;
1656
1657                         AR5K_EEPROM_READ(offset++, val);
1658                         rep[2].freq |= (val >> 11) & 0x1f;
1659                         rep[3].freq = (val >> 4) & fmask;
1660                         rep[4].freq = (val << 3) & fmask;
1661
1662                         AR5K_EEPROM_READ(offset++, val);
1663                         rep[4].freq |= (val >> 13) & 0x7;
1664                         rep[5].freq = (val >> 6) & fmask;
1665                         rep[6].freq = (val << 1) & fmask;
1666
1667                         AR5K_EEPROM_READ(offset++, val);
1668                         rep[6].freq |= (val >> 15) & 0x1;
1669                         rep[7].freq = (val >> 8) & fmask;
1670
1671                         rep[0].edge = (val >> 2) & pmask;
1672                         rep[1].edge = (val << 4) & pmask;
1673
1674                         AR5K_EEPROM_READ(offset++, val);
1675                         rep[1].edge |= (val >> 12) & 0xf;
1676                         rep[2].edge = (val >> 6) & pmask;
1677                         rep[3].edge = val & pmask;
1678
1679                         AR5K_EEPROM_READ(offset++, val);
1680                         rep[4].edge = (val >> 10) & pmask;
1681                         rep[5].edge = (val >> 4) & pmask;
1682                         rep[6].edge = (val << 2) & pmask;
1683
1684                         AR5K_EEPROM_READ(offset++, val);
1685                         rep[6].edge |= (val >> 14) & 0x3;
1686                         rep[7].edge = (val >> 8) & pmask;
1687                 }
1688                 for (j = 0; j < AR5K_EEPROM_N_EDGES; j++) {
1689                         rep[j].freq = ath5k_eeprom_bin2freq(ee,
1690                                 rep[j].freq, ctl_mode);
1691                 }
1692                 rep += AR5K_EEPROM_N_EDGES;
1693         }
1694
1695         return 0;
1696 }
1697
1698 static int
1699 ath5k_eeprom_read_spur_chans(struct ath5k_hw *ah)
1700 {
1701         struct ath5k_eeprom_info *ee = &ah->ah_capabilities.cap_eeprom;
1702         u32 offset;
1703         u16 val;
1704         int ret = 0, i;
1705
1706         offset = AR5K_EEPROM_CTL(ee->ee_version) +
1707                                 AR5K_EEPROM_N_CTLS(ee->ee_version);
1708
1709         if (ee->ee_version < AR5K_EEPROM_VERSION_5_3) {
1710                 /* No spur info for 5GHz */
1711                 ee->ee_spur_chans[0][0] = AR5K_EEPROM_NO_SPUR;
1712                 /* 2 channels for 2GHz (2464/2420) */
1713                 ee->ee_spur_chans[0][1] = AR5K_EEPROM_5413_SPUR_CHAN_1;
1714                 ee->ee_spur_chans[1][1] = AR5K_EEPROM_5413_SPUR_CHAN_2;
1715                 ee->ee_spur_chans[2][1] = AR5K_EEPROM_NO_SPUR;
1716         } else if (ee->ee_version >= AR5K_EEPROM_VERSION_5_3) {
1717                 for (i = 0; i < AR5K_EEPROM_N_SPUR_CHANS; i++) {
1718                         AR5K_EEPROM_READ(offset, val);
1719                         ee->ee_spur_chans[i][0] = val;
1720                         AR5K_EEPROM_READ(offset + AR5K_EEPROM_N_SPUR_CHANS,
1721                                                                         val);
1722                         ee->ee_spur_chans[i][1] = val;
1723                         offset++;
1724                 }
1725         }
1726
1727         return ret;
1728 }
1729
1730 /*
1731  * Initialize eeprom data structure
1732  */
1733 int
1734 ath5k_eeprom_init(struct ath5k_hw *ah)
1735 {
1736         int err;
1737
1738         err = ath5k_eeprom_init_header(ah);
1739         if (err < 0)
1740                 return err;
1741
1742         err = ath5k_eeprom_init_modes(ah);
1743         if (err < 0)
1744                 return err;
1745
1746         err = ath5k_eeprom_read_pcal_info(ah);
1747         if (err < 0)
1748                 return err;
1749
1750         err = ath5k_eeprom_read_ctl_info(ah);
1751         if (err < 0)
1752                 return err;
1753
1754         err = ath5k_eeprom_read_spur_chans(ah);
1755         if (err < 0)
1756                 return err;
1757
1758         return 0;
1759 }
1760
1761 /*
1762  * Read the MAC address from eeprom
1763  */
1764 int ath5k_eeprom_read_mac(struct ath5k_hw *ah, u8 *mac)
1765 {
1766         u8 mac_d[ETH_ALEN] = {};
1767         u32 total, offset;
1768         u16 data;
1769         int octet, ret;
1770
1771         ret = ath5k_hw_eeprom_read(ah, 0x20, &data);
1772         if (ret)
1773                 return ret;
1774
1775         for (offset = 0x1f, octet = 0, total = 0; offset >= 0x1d; offset--) {
1776                 ret = ath5k_hw_eeprom_read(ah, offset, &data);
1777                 if (ret)
1778                         return ret;
1779
1780                 total += data;
1781                 mac_d[octet + 1] = data & 0xff;
1782                 mac_d[octet] = data >> 8;
1783                 octet += 2;
1784         }
1785
1786         if (!total || total == 3 * 0xffff)
1787                 return -EINVAL;
1788
1789         memcpy(mac, mac_d, ETH_ALEN);
1790
1791         return 0;
1792 }