hc
2023-12-11 d2ccde1c8e90d38cee87a1b0309ad2827f3fd30d
kernel/drivers/net/wireless/mediatek/mt76/mt76x0/eeprom.c
....@@ -1,18 +1,11 @@
1
+// SPDX-License-Identifier: GPL-2.0-only
12 /*
23 * Copyright (C) 2014 Felix Fietkau <nbd@openwrt.org>
34 * Copyright (C) 2015 Jakub Kicinski <kubakici@wp.pl>
45 * Copyright (C) 2018 Stanislaw Gruszka <stf_xl@wp.pl>
5
- *
6
- * This program is free software; you can redistribute it and/or modify
7
- * it under the terms of the GNU General Public License version 2
8
- * as published by the Free Software Foundation
9
- *
10
- * This program is distributed in the hope that it will be useful,
11
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
12
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13
- * GNU General Public License for more details.
146 */
157
8
+#include <linux/module.h>
169 #include <linux/of.h>
1710 #include <linux/mtd/mtd.h>
1811 #include <linux/mtd/partitions.h>
....@@ -20,81 +13,20 @@
2013 #include <asm/unaligned.h>
2114 #include "mt76x0.h"
2215 #include "eeprom.h"
23
-
24
-static bool
25
-field_valid(u8 val)
26
-{
27
- return val != 0xff;
28
-}
29
-
30
-static s8
31
-field_validate(u8 val)
32
-{
33
- if (!field_valid(val))
34
- return 0;
35
-
36
- return val;
37
-}
38
-
39
-static inline int
40
-sign_extend(u32 val, unsigned int size)
41
-{
42
- bool sign = val & BIT(size - 1);
43
-
44
- val &= BIT(size - 1) - 1;
45
-
46
- return sign ? val : -val;
47
-}
48
-
49
-static int
50
-mt76x0_efuse_read(struct mt76x0_dev *dev, u16 addr, u8 *data,
51
- enum mt76x0_eeprom_access_modes mode)
52
-{
53
- u32 val;
54
- int i;
55
-
56
- val = mt76_rr(dev, MT_EFUSE_CTRL);
57
- val &= ~(MT_EFUSE_CTRL_AIN |
58
- MT_EFUSE_CTRL_MODE);
59
- val |= FIELD_PREP(MT_EFUSE_CTRL_AIN, addr & ~0xf) |
60
- FIELD_PREP(MT_EFUSE_CTRL_MODE, mode) |
61
- MT_EFUSE_CTRL_KICK;
62
- mt76_wr(dev, MT_EFUSE_CTRL, val);
63
-
64
- if (!mt76_poll(dev, MT_EFUSE_CTRL, MT_EFUSE_CTRL_KICK, 0, 1000))
65
- return -ETIMEDOUT;
66
-
67
- val = mt76_rr(dev, MT_EFUSE_CTRL);
68
- if ((val & MT_EFUSE_CTRL_AOUT) == MT_EFUSE_CTRL_AOUT) {
69
- /* Parts of eeprom not in the usage map (0x80-0xc0,0xf0)
70
- * will not return valid data but it's ok.
71
- */
72
- memset(data, 0xff, 16);
73
- return 0;
74
- }
75
-
76
- for (i = 0; i < 4; i++) {
77
- val = mt76_rr(dev, MT_EFUSE_DATA(i));
78
- put_unaligned_le32(val, data + 4 * i);
79
- }
80
-
81
- return 0;
82
-}
16
+#include "../mt76x02_phy.h"
8317
8418 #define MT_MAP_READS DIV_ROUND_UP(MT_EFUSE_USAGE_MAP_SIZE, 16)
8519 static int
86
-mt76x0_efuse_physical_size_check(struct mt76x0_dev *dev)
20
+mt76x0_efuse_physical_size_check(struct mt76x02_dev *dev)
8721 {
8822 u8 data[MT_MAP_READS * 16];
8923 int ret, i;
9024 u32 start = 0, end = 0, cnt_free;
9125
92
- for (i = 0; i < MT_MAP_READS; i++) {
93
- ret = mt76x0_efuse_read(dev, MT_EE_USAGE_MAP_START + i * 16,
94
- data + i * 16, MT_EE_PHYSICAL_READ);
95
- if (ret)
96
- return ret;
97
- }
26
+ ret = mt76x02_get_efuse_data(dev, MT_EE_USAGE_MAP_START, data,
27
+ sizeof(data), MT_EE_PHYSICAL_READ);
28
+ if (ret)
29
+ return ret;
9830
9931 for (i = 0; i < MT_EFUSE_USAGE_MAP_SIZE; i++)
10032 if (!data[i]) {
....@@ -105,341 +37,321 @@
10537 cnt_free = end - start + 1;
10638
10739 if (MT_EFUSE_USAGE_MAP_SIZE - cnt_free < 5) {
108
- dev_err(dev->mt76.dev, "Error: your device needs default EEPROM file and this driver doesn't support it!\n");
40
+ dev_err(dev->mt76.dev,
41
+ "driver does not support default EEPROM\n");
10942 return -EINVAL;
11043 }
11144
11245 return 0;
11346 }
11447
115
-static void
116
-mt76x0_set_chip_cap(struct mt76x0_dev *dev, u8 *eeprom)
48
+static void mt76x0_set_chip_cap(struct mt76x02_dev *dev)
11749 {
118
- enum mt76x2_board_type { BOARD_TYPE_2GHZ = 1, BOARD_TYPE_5GHZ = 2 };
119
- u16 nic_conf0 = get_unaligned_le16(eeprom + MT_EE_NIC_CONF_0);
120
- u16 nic_conf1 = get_unaligned_le16(eeprom + MT_EE_NIC_CONF_1);
50
+ u16 nic_conf0 = mt76x02_eeprom_get(dev, MT_EE_NIC_CONF_0);
51
+ u16 nic_conf1 = mt76x02_eeprom_get(dev, MT_EE_NIC_CONF_1);
12152
122
- dev_dbg(dev->mt76.dev, "NIC_CONF0: %04x NIC_CONF1: %04x\n", nic_conf0, nic_conf1);
53
+ mt76x02_eeprom_parse_hw_cap(dev);
54
+ dev_dbg(dev->mt76.dev, "2GHz %d 5GHz %d\n",
55
+ dev->mt76.cap.has_2ghz, dev->mt76.cap.has_5ghz);
12356
124
- switch (FIELD_GET(MT_EE_NIC_CONF_0_BOARD_TYPE, nic_conf0)) {
125
- case BOARD_TYPE_5GHZ:
126
- dev->ee->has_5ghz = true;
127
- break;
128
- case BOARD_TYPE_2GHZ:
129
- dev->ee->has_2ghz = true;
130
- break;
131
- default:
132
- dev->ee->has_2ghz = true;
133
- dev->ee->has_5ghz = true;
134
- break;
57
+ if (dev->no_2ghz) {
58
+ dev->mt76.cap.has_2ghz = false;
59
+ dev_dbg(dev->mt76.dev, "mask out 2GHz support\n");
13560 }
13661
137
- dev_dbg(dev->mt76.dev, "Has 2GHZ %d 5GHZ %d\n", dev->ee->has_2ghz, dev->ee->has_5ghz);
62
+ if (is_mt7630(dev)) {
63
+ dev->mt76.cap.has_5ghz = false;
64
+ dev_dbg(dev->mt76.dev, "mask out 5GHz support\n");
65
+ }
13866
139
- if (!field_valid(nic_conf1 & 0xff))
67
+ if (!mt76x02_field_valid(nic_conf1 & 0xff))
14068 nic_conf1 &= 0xff00;
14169
14270 if (nic_conf1 & MT_EE_NIC_CONF_1_HW_RF_CTRL)
14371 dev_err(dev->mt76.dev,
144
- "Error: this driver does not support HW RF ctrl\n");
72
+ "driver does not support HW RF ctrl\n");
14573
146
- if (!field_valid(nic_conf0 >> 8))
74
+ if (!mt76x02_field_valid(nic_conf0 >> 8))
14775 return;
14876
14977 if (FIELD_GET(MT_EE_NIC_CONF_0_RX_PATH, nic_conf0) > 1 ||
15078 FIELD_GET(MT_EE_NIC_CONF_0_TX_PATH, nic_conf0) > 1)
151
- dev_err(dev->mt76.dev,
152
- "Error: device has more than 1 RX/TX stream!\n");
153
-
154
- dev->ee->pa_type = FIELD_GET(MT_EE_NIC_CONF_0_PA_TYPE, nic_conf0);
155
- dev_dbg(dev->mt76.dev, "PA Type %d\n", dev->ee->pa_type);
79
+ dev_err(dev->mt76.dev, "invalid tx-rx stream\n");
15680 }
15781
158
-static int
159
-mt76x0_set_macaddr(struct mt76x0_dev *dev, const u8 *eeprom)
82
+static void mt76x0_set_temp_offset(struct mt76x02_dev *dev)
16083 {
161
- const void *src = eeprom + MT_EE_MAC_ADDR;
84
+ u8 val;
16285
163
- ether_addr_copy(dev->macaddr, src);
86
+ val = mt76x02_eeprom_get(dev, MT_EE_2G_TARGET_POWER) >> 8;
87
+ if (mt76x02_field_valid(val))
88
+ dev->cal.rx.temp_offset = mt76x02_sign_extend(val, 8);
89
+ else
90
+ dev->cal.rx.temp_offset = -10;
91
+}
16492
165
- if (!is_valid_ether_addr(dev->macaddr)) {
166
- eth_random_addr(dev->macaddr);
167
- dev_info(dev->mt76.dev,
168
- "Invalid MAC address, using random address %pM\n",
169
- dev->macaddr);
93
+static void mt76x0_set_freq_offset(struct mt76x02_dev *dev)
94
+{
95
+ struct mt76x02_rx_freq_cal *caldata = &dev->cal.rx;
96
+ u8 val;
97
+
98
+ val = mt76x02_eeprom_get(dev, MT_EE_FREQ_OFFSET);
99
+ if (!mt76x02_field_valid(val))
100
+ val = 0;
101
+ caldata->freq_offset = val;
102
+
103
+ val = mt76x02_eeprom_get(dev, MT_EE_TSSI_BOUND4) >> 8;
104
+ if (!mt76x02_field_valid(val))
105
+ val = 0;
106
+
107
+ caldata->freq_offset -= mt76x02_sign_extend(val, 8);
108
+}
109
+
110
+void mt76x0_read_rx_gain(struct mt76x02_dev *dev)
111
+{
112
+ struct ieee80211_channel *chan = dev->mphy.chandef.chan;
113
+ struct mt76x02_rx_freq_cal *caldata = &dev->cal.rx;
114
+ s8 val, lna_5g[3], lna_2g;
115
+ u16 rssi_offset;
116
+ int i;
117
+
118
+ mt76x02_get_rx_gain(dev, chan->band, &rssi_offset, &lna_2g, lna_5g);
119
+ caldata->lna_gain = mt76x02_get_lna_gain(dev, &lna_2g, lna_5g, chan);
120
+
121
+ for (i = 0; i < ARRAY_SIZE(caldata->rssi_offset); i++) {
122
+ val = rssi_offset >> (8 * i);
123
+ if (val < -10 || val > 10)
124
+ val = 0;
125
+
126
+ caldata->rssi_offset[i] = val;
127
+ }
128
+}
129
+
130
+static s8 mt76x0_get_delta(struct mt76x02_dev *dev)
131
+{
132
+ struct cfg80211_chan_def *chandef = &dev->mphy.chandef;
133
+ u8 val;
134
+
135
+ if (chandef->width == NL80211_CHAN_WIDTH_80) {
136
+ val = mt76x02_eeprom_get(dev, MT_EE_5G_TARGET_POWER) >> 8;
137
+ } else if (chandef->width == NL80211_CHAN_WIDTH_40) {
138
+ u16 data;
139
+
140
+ data = mt76x02_eeprom_get(dev, MT_EE_TX_POWER_DELTA_BW40);
141
+ if (chandef->chan->band == NL80211_BAND_5GHZ)
142
+ val = data >> 8;
143
+ else
144
+ val = data;
145
+ } else {
146
+ return 0;
170147 }
171148
172
- mt76_wr(dev, MT_MAC_ADDR_DW0, get_unaligned_le32(dev->macaddr));
173
- mt76_wr(dev, MT_MAC_ADDR_DW1, get_unaligned_le16(dev->macaddr + 4) |
174
- FIELD_PREP(MT_MAC_ADDR_DW1_U2ME_MASK, 0xff));
149
+ return mt76x02_rate_power_val(val);
150
+}
151
+
152
+void mt76x0_get_tx_power_per_rate(struct mt76x02_dev *dev,
153
+ struct ieee80211_channel *chan,
154
+ struct mt76_rate_power *t)
155
+{
156
+ bool is_2ghz = chan->band == NL80211_BAND_2GHZ;
157
+ u16 val, addr;
158
+ s8 delta;
159
+
160
+ memset(t, 0, sizeof(*t));
161
+
162
+ /* cck 1M, 2M, 5.5M, 11M */
163
+ val = mt76x02_eeprom_get(dev, MT_EE_TX_POWER_BYRATE_BASE);
164
+ t->cck[0] = t->cck[1] = s6_to_s8(val);
165
+ t->cck[2] = t->cck[3] = s6_to_s8(val >> 8);
166
+
167
+ /* ofdm 6M, 9M, 12M, 18M */
168
+ addr = is_2ghz ? MT_EE_TX_POWER_BYRATE_BASE + 2 : 0x120;
169
+ val = mt76x02_eeprom_get(dev, addr);
170
+ t->ofdm[0] = t->ofdm[1] = s6_to_s8(val);
171
+ t->ofdm[2] = t->ofdm[3] = s6_to_s8(val >> 8);
172
+
173
+ /* ofdm 24M, 36M, 48M, 54M */
174
+ addr = is_2ghz ? MT_EE_TX_POWER_BYRATE_BASE + 4 : 0x122;
175
+ val = mt76x02_eeprom_get(dev, addr);
176
+ t->ofdm[4] = t->ofdm[5] = s6_to_s8(val);
177
+ t->ofdm[6] = t->ofdm[7] = s6_to_s8(val >> 8);
178
+
179
+ /* ht-vht mcs 1ss 0, 1, 2, 3 */
180
+ addr = is_2ghz ? MT_EE_TX_POWER_BYRATE_BASE + 6 : 0x124;
181
+ val = mt76x02_eeprom_get(dev, addr);
182
+ t->ht[0] = t->ht[1] = t->vht[0] = t->vht[1] = s6_to_s8(val);
183
+ t->ht[2] = t->ht[3] = t->vht[2] = t->vht[3] = s6_to_s8(val >> 8);
184
+
185
+ /* ht-vht mcs 1ss 4, 5, 6 */
186
+ addr = is_2ghz ? MT_EE_TX_POWER_BYRATE_BASE + 8 : 0x126;
187
+ val = mt76x02_eeprom_get(dev, addr);
188
+ t->ht[4] = t->ht[5] = t->vht[4] = t->vht[5] = s6_to_s8(val);
189
+ t->ht[6] = t->ht[7] = t->vht[6] = t->vht[7] = s6_to_s8(val >> 8);
190
+
191
+ /* ht-vht mcs 1ss 0, 1, 2, 3 stbc */
192
+ addr = is_2ghz ? MT_EE_TX_POWER_BYRATE_BASE + 14 : 0xec;
193
+ val = mt76x02_eeprom_get(dev, addr);
194
+ t->stbc[0] = t->stbc[1] = s6_to_s8(val);
195
+ t->stbc[2] = t->stbc[3] = s6_to_s8(val >> 8);
196
+
197
+ /* ht-vht mcs 1ss 4, 5, 6 stbc */
198
+ addr = is_2ghz ? MT_EE_TX_POWER_BYRATE_BASE + 16 : 0xee;
199
+ val = mt76x02_eeprom_get(dev, addr);
200
+ t->stbc[4] = t->stbc[5] = s6_to_s8(val);
201
+ t->stbc[6] = t->stbc[7] = s6_to_s8(val >> 8);
202
+
203
+ /* vht mcs 8, 9 5GHz */
204
+ val = mt76x02_eeprom_get(dev, 0x132);
205
+ t->vht[8] = s6_to_s8(val);
206
+ t->vht[9] = s6_to_s8(val >> 8);
207
+
208
+ delta = mt76x0_tssi_enabled(dev) ? 0 : mt76x0_get_delta(dev);
209
+ mt76x02_add_rate_power_offset(t, delta);
210
+}
211
+
212
+void mt76x0_get_power_info(struct mt76x02_dev *dev,
213
+ struct ieee80211_channel *chan, s8 *tp)
214
+{
215
+ static const struct mt76x0_chan_map {
216
+ u8 chan;
217
+ u8 offset;
218
+ } chan_map[] = {
219
+ { 2, 0 }, { 4, 2 }, { 6, 4 }, { 8, 6 },
220
+ { 10, 8 }, { 12, 10 }, { 14, 12 }, { 38, 0 },
221
+ { 44, 2 }, { 48, 4 }, { 54, 6 }, { 60, 8 },
222
+ { 64, 10 }, { 102, 12 }, { 108, 14 }, { 112, 16 },
223
+ { 118, 18 }, { 124, 20 }, { 128, 22 }, { 134, 24 },
224
+ { 140, 26 }, { 151, 28 }, { 157, 30 }, { 161, 32 },
225
+ { 167, 34 }, { 171, 36 }, { 175, 38 },
226
+ };
227
+ u8 offset, addr;
228
+ int i, idx = 0;
229
+ u16 data;
230
+
231
+ if (mt76x0_tssi_enabled(dev)) {
232
+ s8 target_power;
233
+
234
+ if (chan->band == NL80211_BAND_5GHZ)
235
+ data = mt76x02_eeprom_get(dev, MT_EE_5G_TARGET_POWER);
236
+ else
237
+ data = mt76x02_eeprom_get(dev, MT_EE_2G_TARGET_POWER);
238
+ target_power = (data & 0xff) - dev->mt76.rate_power.ofdm[7];
239
+ *tp = target_power + mt76x0_get_delta(dev);
240
+
241
+ return;
242
+ }
243
+
244
+ for (i = 0; i < ARRAY_SIZE(chan_map); i++) {
245
+ if (chan->hw_value <= chan_map[i].chan) {
246
+ idx = (chan->hw_value == chan_map[i].chan);
247
+ offset = chan_map[i].offset;
248
+ break;
249
+ }
250
+ }
251
+ if (i == ARRAY_SIZE(chan_map))
252
+ offset = chan_map[0].offset;
253
+
254
+ if (chan->band == NL80211_BAND_2GHZ) {
255
+ addr = MT_EE_TX_POWER_DELTA_BW80 + offset;
256
+ } else {
257
+ switch (chan->hw_value) {
258
+ case 42:
259
+ offset = 2;
260
+ break;
261
+ case 58:
262
+ offset = 8;
263
+ break;
264
+ case 106:
265
+ offset = 14;
266
+ break;
267
+ case 122:
268
+ offset = 20;
269
+ break;
270
+ case 155:
271
+ offset = 30;
272
+ break;
273
+ default:
274
+ break;
275
+ }
276
+ addr = MT_EE_TX_POWER_0_GRP4_TSSI_SLOPE + 2 + offset;
277
+ }
278
+
279
+ data = mt76x02_eeprom_get(dev, addr);
280
+ *tp = data >> (8 * idx);
281
+ if (*tp < 0 || *tp > 0x3f)
282
+ *tp = 5;
283
+}
284
+
285
+static int mt76x0_check_eeprom(struct mt76x02_dev *dev)
286
+{
287
+ u16 val;
288
+
289
+ val = get_unaligned_le16(dev->mt76.eeprom.data);
290
+ if (!val)
291
+ val = get_unaligned_le16(dev->mt76.eeprom.data +
292
+ MT_EE_PCI_ID);
293
+
294
+ switch (val) {
295
+ case 0x7650:
296
+ case 0x7610:
297
+ return 0;
298
+ default:
299
+ dev_err(dev->mt76.dev, "EEPROM data check failed: %04x\n",
300
+ val);
301
+ return -EINVAL;
302
+ }
303
+}
304
+
305
+static int mt76x0_load_eeprom(struct mt76x02_dev *dev)
306
+{
307
+ int found;
308
+
309
+ found = mt76_eeprom_init(&dev->mt76, MT76X0_EEPROM_SIZE);
310
+ if (found < 0)
311
+ return found;
312
+
313
+ if (found && !mt76x0_check_eeprom(dev))
314
+ return 0;
315
+
316
+ found = mt76x0_efuse_physical_size_check(dev);
317
+ if (found < 0)
318
+ return found;
319
+
320
+ return mt76x02_get_efuse_data(dev, 0, dev->mt76.eeprom.data,
321
+ MT76X0_EEPROM_SIZE, MT_EE_READ);
322
+}
323
+
324
+int mt76x0_eeprom_init(struct mt76x02_dev *dev)
325
+{
326
+ u8 version, fae;
327
+ u16 data;
328
+ int err;
329
+
330
+ err = mt76x0_load_eeprom(dev);
331
+ if (err < 0)
332
+ return err;
333
+
334
+ data = mt76x02_eeprom_get(dev, MT_EE_VERSION);
335
+ version = data >> 8;
336
+ fae = data;
337
+
338
+ if (version > MT76X0U_EE_MAX_VER)
339
+ dev_warn(dev->mt76.dev,
340
+ "Warning: unsupported EEPROM version %02hhx\n",
341
+ version);
342
+ dev_info(dev->mt76.dev, "EEPROM ver:%02hhx fae:%02hhx\n",
343
+ version, fae);
344
+
345
+ memcpy(dev->mt76.macaddr, (u8 *)dev->mt76.eeprom.data + MT_EE_MAC_ADDR,
346
+ ETH_ALEN);
347
+ mt76_eeprom_override(&dev->mt76);
348
+ mt76x02_mac_setaddr(dev, dev->mt76.macaddr);
349
+
350
+ mt76x0_set_chip_cap(dev);
351
+ mt76x0_set_freq_offset(dev);
352
+ mt76x0_set_temp_offset(dev);
175353
176354 return 0;
177355 }
178356
179
-static void
180
-mt76x0_set_temp_offset(struct mt76x0_dev *dev, u8 *eeprom)
181
-{
182
- u8 temp = eeprom[MT_EE_TEMP_OFFSET];
183
-
184
- if (field_valid(temp))
185
- dev->ee->temp_off = sign_extend(temp, 8);
186
- else
187
- dev->ee->temp_off = -10;
188
-}
189
-
190
-static void
191
-mt76x0_set_country_reg(struct mt76x0_dev *dev, u8 *eeprom)
192
-{
193
- /* Note: - region 31 is not valid for mt76x0 (see rtmp_init.c)
194
- * - comments in rtmp_def.h are incorrect (see rt_channel.c)
195
- */
196
- static const struct reg_channel_bounds chan_bounds[] = {
197
- /* EEPROM country regions 0 - 7 */
198
- { 1, 11 }, { 1, 13 }, { 10, 2 }, { 10, 4 },
199
- { 14, 1 }, { 1, 14 }, { 3, 7 }, { 5, 9 },
200
- /* EEPROM country regions 32 - 33 */
201
- { 1, 11 }, { 1, 14 }
202
- };
203
- u8 val = eeprom[MT_EE_COUNTRY_REGION_2GHZ];
204
- int idx = -1;
205
-
206
- dev_dbg(dev->mt76.dev, "REG 2GHZ %u REG 5GHZ %u\n", val, eeprom[MT_EE_COUNTRY_REGION_5GHZ]);
207
- if (val < 8)
208
- idx = val;
209
- if (val > 31 && val < 33)
210
- idx = val - 32 + 8;
211
-
212
- if (idx != -1)
213
- dev_info(dev->mt76.dev,
214
- "EEPROM country region %02hhx (channels %hhd-%hhd)\n",
215
- val, chan_bounds[idx].start,
216
- chan_bounds[idx].start + chan_bounds[idx].num - 1);
217
- else
218
- idx = 5; /* channels 1 - 14 */
219
-
220
- dev->ee->reg = chan_bounds[idx];
221
-
222
- /* TODO: country region 33 is special - phy should be set to B-mode
223
- * before entering channel 14 (see sta/connect.c)
224
- */
225
-}
226
-
227
-static void
228
-mt76x0_set_rf_freq_off(struct mt76x0_dev *dev, u8 *eeprom)
229
-{
230
- u8 comp;
231
-
232
- dev->ee->rf_freq_off = field_validate(eeprom[MT_EE_FREQ_OFFSET]);
233
- comp = field_validate(eeprom[MT_EE_FREQ_OFFSET_COMPENSATION]);
234
-
235
- if (comp & BIT(7))
236
- dev->ee->rf_freq_off -= comp & 0x7f;
237
- else
238
- dev->ee->rf_freq_off += comp;
239
-}
240
-
241
-static void
242
-mt76x0_set_lna_gain(struct mt76x0_dev *dev, u8 *eeprom)
243
-{
244
- u8 gain;
245
-
246
- dev->ee->lna_gain_2ghz = eeprom[MT_EE_LNA_GAIN_2GHZ];
247
- dev->ee->lna_gain_5ghz[0] = eeprom[MT_EE_LNA_GAIN_5GHZ_0];
248
-
249
- gain = eeprom[MT_EE_LNA_GAIN_5GHZ_1];
250
- if (gain == 0xff || gain == 0)
251
- dev->ee->lna_gain_5ghz[1] = dev->ee->lna_gain_5ghz[0];
252
- else
253
- dev->ee->lna_gain_5ghz[1] = gain;
254
-
255
- gain = eeprom[MT_EE_LNA_GAIN_5GHZ_2];
256
- if (gain == 0xff || gain == 0)
257
- dev->ee->lna_gain_5ghz[2] = dev->ee->lna_gain_5ghz[0];
258
- else
259
- dev->ee->lna_gain_5ghz[2] = gain;
260
-}
261
-
262
-static void
263
-mt76x0_set_rssi_offset(struct mt76x0_dev *dev, u8 *eeprom)
264
-{
265
- int i;
266
- s8 *rssi_offset = dev->ee->rssi_offset_2ghz;
267
-
268
- for (i = 0; i < 2; i++) {
269
- rssi_offset[i] = eeprom[MT_EE_RSSI_OFFSET + i];
270
-
271
- if (rssi_offset[i] < -10 || rssi_offset[i] > 10) {
272
- dev_warn(dev->mt76.dev,
273
- "Warning: EEPROM RSSI is invalid %02hhx\n",
274
- rssi_offset[i]);
275
- rssi_offset[i] = 0;
276
- }
277
- }
278
-
279
- rssi_offset = dev->ee->rssi_offset_5ghz;
280
-
281
- for (i = 0; i < 3; i++) {
282
- rssi_offset[i] = eeprom[MT_EE_RSSI_OFFSET_5GHZ + i];
283
-
284
- if (rssi_offset[i] < -10 || rssi_offset[i] > 10) {
285
- dev_warn(dev->mt76.dev,
286
- "Warning: EEPROM RSSI is invalid %02hhx\n",
287
- rssi_offset[i]);
288
- rssi_offset[i] = 0;
289
- }
290
- }
291
-}
292
-
293
-static u32
294
-calc_bw40_power_rate(u32 value, int delta)
295
-{
296
- u32 ret = 0;
297
- int i, tmp;
298
-
299
- for (i = 0; i < 4; i++) {
300
- tmp = s6_to_int((value >> i*8) & 0xff) + delta;
301
- ret |= (u32)(int_to_s6(tmp)) << i*8;
302
- }
303
-
304
- return ret;
305
-}
306
-
307
-static s8
308
-get_delta(u8 val)
309
-{
310
- s8 ret;
311
-
312
- if (!field_valid(val) || !(val & BIT(7)))
313
- return 0;
314
-
315
- ret = val & 0x1f;
316
- if (ret > 8)
317
- ret = 8;
318
- if (val & BIT(6))
319
- ret = -ret;
320
-
321
- return ret;
322
-}
323
-
324
-static void
325
-mt76x0_set_tx_power_per_rate(struct mt76x0_dev *dev, u8 *eeprom)
326
-{
327
- s8 bw40_delta_2g, bw40_delta_5g;
328
- u32 val;
329
- int i;
330
-
331
- bw40_delta_2g = get_delta(eeprom[MT_EE_TX_POWER_DELTA_BW40]);
332
- bw40_delta_5g = get_delta(eeprom[MT_EE_TX_POWER_DELTA_BW40 + 1]);
333
-
334
- for (i = 0; i < 5; i++) {
335
- val = get_unaligned_le32(eeprom + MT_EE_TX_POWER_BYRATE(i));
336
-
337
- /* Skip last 16 bits. */
338
- if (i == 4)
339
- val &= 0x0000ffff;
340
-
341
- dev->ee->tx_pwr_cfg_2g[i][0] = val;
342
- dev->ee->tx_pwr_cfg_2g[i][1] = calc_bw40_power_rate(val, bw40_delta_2g);
343
- }
344
-
345
- /* Reading per rate tx power for 5 GHz band is a bit more complex. Note
346
- * we mix 16 bit and 32 bit reads and sometimes do shifts.
347
- */
348
- val = get_unaligned_le16(eeprom + 0x120);
349
- val <<= 16;
350
- dev->ee->tx_pwr_cfg_5g[0][0] = val;
351
- dev->ee->tx_pwr_cfg_5g[0][1] = calc_bw40_power_rate(val, bw40_delta_5g);
352
-
353
- val = get_unaligned_le32(eeprom + 0x122);
354
- dev->ee->tx_pwr_cfg_5g[1][0] = val;
355
- dev->ee->tx_pwr_cfg_5g[1][1] = calc_bw40_power_rate(val, bw40_delta_5g);
356
-
357
- val = get_unaligned_le16(eeprom + 0x126);
358
- dev->ee->tx_pwr_cfg_5g[2][0] = val;
359
- dev->ee->tx_pwr_cfg_5g[2][1] = calc_bw40_power_rate(val, bw40_delta_5g);
360
-
361
- val = get_unaligned_le16(eeprom + 0xec);
362
- val <<= 16;
363
- dev->ee->tx_pwr_cfg_5g[3][0] = val;
364
- dev->ee->tx_pwr_cfg_5g[3][1] = calc_bw40_power_rate(val, bw40_delta_5g);
365
-
366
- val = get_unaligned_le16(eeprom + 0xee);
367
- dev->ee->tx_pwr_cfg_5g[4][0] = val;
368
- dev->ee->tx_pwr_cfg_5g[4][1] = calc_bw40_power_rate(val, bw40_delta_5g);
369
-}
370
-
371
-static void
372
-mt76x0_set_tx_power_per_chan(struct mt76x0_dev *dev, u8 *eeprom)
373
-{
374
- int i;
375
- u8 tx_pwr;
376
-
377
- for (i = 0; i < 14; i++) {
378
- tx_pwr = eeprom[MT_EE_TX_POWER_OFFSET_2GHZ + i];
379
- if (tx_pwr <= 0x3f && tx_pwr > 0)
380
- dev->ee->tx_pwr_per_chan[i] = tx_pwr;
381
- else
382
- dev->ee->tx_pwr_per_chan[i] = 5;
383
- }
384
-
385
- for (i = 0; i < 40; i++) {
386
- tx_pwr = eeprom[MT_EE_TX_POWER_OFFSET_5GHZ + i];
387
- if (tx_pwr <= 0x3f && tx_pwr > 0)
388
- dev->ee->tx_pwr_per_chan[14 + i] = tx_pwr;
389
- else
390
- dev->ee->tx_pwr_per_chan[14 + i] = 5;
391
- }
392
-
393
- dev->ee->tx_pwr_per_chan[54] = dev->ee->tx_pwr_per_chan[22];
394
- dev->ee->tx_pwr_per_chan[55] = dev->ee->tx_pwr_per_chan[28];
395
- dev->ee->tx_pwr_per_chan[56] = dev->ee->tx_pwr_per_chan[34];
396
- dev->ee->tx_pwr_per_chan[57] = dev->ee->tx_pwr_per_chan[44];
397
-}
398
-
399
-int
400
-mt76x0_eeprom_init(struct mt76x0_dev *dev)
401
-{
402
- u8 *eeprom;
403
- int i, ret;
404
-
405
- ret = mt76x0_efuse_physical_size_check(dev);
406
- if (ret)
407
- return ret;
408
-
409
- dev->ee = devm_kzalloc(dev->mt76.dev, sizeof(*dev->ee), GFP_KERNEL);
410
- if (!dev->ee)
411
- return -ENOMEM;
412
-
413
- eeprom = kmalloc(MT76X0_EEPROM_SIZE, GFP_KERNEL);
414
- if (!eeprom)
415
- return -ENOMEM;
416
-
417
- for (i = 0; i + 16 <= MT76X0_EEPROM_SIZE; i += 16) {
418
- ret = mt76x0_efuse_read(dev, i, eeprom + i, MT_EE_READ);
419
- if (ret)
420
- goto out;
421
- }
422
-
423
- if (eeprom[MT_EE_VERSION_EE] > MT76X0U_EE_MAX_VER)
424
- dev_warn(dev->mt76.dev,
425
- "Warning: unsupported EEPROM version %02hhx\n",
426
- eeprom[MT_EE_VERSION_EE]);
427
- dev_info(dev->mt76.dev, "EEPROM ver:%02hhx fae:%02hhx\n",
428
- eeprom[MT_EE_VERSION_EE], eeprom[MT_EE_VERSION_FAE]);
429
-
430
- mt76x0_set_macaddr(dev, eeprom);
431
- mt76x0_set_chip_cap(dev, eeprom);
432
- mt76x0_set_country_reg(dev, eeprom);
433
- mt76x0_set_rf_freq_off(dev, eeprom);
434
- mt76x0_set_temp_offset(dev, eeprom);
435
- mt76x0_set_lna_gain(dev, eeprom);
436
- mt76x0_set_rssi_offset(dev, eeprom);
437
- dev->chainmask = 0x0101;
438
-
439
- mt76x0_set_tx_power_per_rate(dev, eeprom);
440
- mt76x0_set_tx_power_per_chan(dev, eeprom);
441
-
442
-out:
443
- kfree(eeprom);
444
- return ret;
445
-}
357
+MODULE_LICENSE("Dual BSD/GPL");