mac80211: b43: backport b43 patches from wireless testing
[openwrt/svn-archive/archive.git] / package / kernel / mac80211 / patches / 800-b43-backports-form-wireless-testing-master-master-20.patch
1 backport b43 patches from wireless testing
2
3 This brings b43 up to wireless-testing/master master-2014-07-10
4
5 --- a/drivers/net/wireless/b43/main.c
6 +++ b/drivers/net/wireless/b43/main.c
7 @@ -122,7 +122,11 @@ static const struct bcma_device_id b43_b
8 BCMA_CORE(BCMA_MANUF_BCM, BCMA_CORE_80211, 0x11, BCMA_ANY_CLASS),
9 BCMA_CORE(BCMA_MANUF_BCM, BCMA_CORE_80211, 0x17, BCMA_ANY_CLASS),
10 BCMA_CORE(BCMA_MANUF_BCM, BCMA_CORE_80211, 0x18, BCMA_ANY_CLASS),
11 + BCMA_CORE(BCMA_MANUF_BCM, BCMA_CORE_80211, 0x1C, BCMA_ANY_CLASS),
12 BCMA_CORE(BCMA_MANUF_BCM, BCMA_CORE_80211, 0x1D, BCMA_ANY_CLASS),
13 + BCMA_CORE(BCMA_MANUF_BCM, BCMA_CORE_80211, 0x1E, BCMA_ANY_CLASS),
14 + BCMA_CORE(BCMA_MANUF_BCM, BCMA_CORE_80211, 0x28, BCMA_ANY_CLASS),
15 + BCMA_CORE(BCMA_MANUF_BCM, BCMA_CORE_80211, 0x2A, BCMA_ANY_CLASS),
16 BCMA_CORETABLE_END
17 };
18 MODULE_DEVICE_TABLE(bcma, b43_bcma_tbl);
19 @@ -2201,52 +2205,82 @@ err_format:
20 return -EPROTO;
21 }
22
23 +/* http://bcm-v4.sipsolutions.net/802.11/Init/Firmware */
24 static int b43_try_request_fw(struct b43_request_fw_context *ctx)
25 {
26 struct b43_wldev *dev = ctx->dev;
27 struct b43_firmware *fw = &ctx->dev->fw;
28 + struct b43_phy *phy = &dev->phy;
29 const u8 rev = ctx->dev->dev->core_rev;
30 const char *filename;
31 - u32 tmshigh;
32 int err;
33
34 - /* Files for HT and LCN were found by trying one by one */
35 -
36 /* Get microcode */
37 - if ((rev >= 5) && (rev <= 10)) {
38 - filename = "ucode5";
39 - } else if ((rev >= 11) && (rev <= 12)) {
40 - filename = "ucode11";
41 - } else if (rev == 13) {
42 - filename = "ucode13";
43 - } else if (rev == 14) {
44 - filename = "ucode14";
45 - } else if (rev == 15) {
46 + filename = NULL;
47 + switch (rev) {
48 + case 42:
49 + if (phy->type == B43_PHYTYPE_AC)
50 + filename = "ucode42";
51 + break;
52 + case 40:
53 + if (phy->type == B43_PHYTYPE_AC)
54 + filename = "ucode40";
55 + break;
56 + case 33:
57 + if (phy->type == B43_PHYTYPE_LCN40)
58 + filename = "ucode33_lcn40";
59 + break;
60 + case 30:
61 + if (phy->type == B43_PHYTYPE_N)
62 + filename = "ucode30_mimo";
63 + break;
64 + case 29:
65 + if (phy->type == B43_PHYTYPE_HT)
66 + filename = "ucode29_mimo";
67 + break;
68 + case 26:
69 + if (phy->type == B43_PHYTYPE_HT)
70 + filename = "ucode26_mimo";
71 + break;
72 + case 28:
73 + case 25:
74 + if (phy->type == B43_PHYTYPE_N)
75 + filename = "ucode25_mimo";
76 + else if (phy->type == B43_PHYTYPE_LCN)
77 + filename = "ucode25_lcn";
78 + break;
79 + case 24:
80 + if (phy->type == B43_PHYTYPE_LCN)
81 + filename = "ucode24_lcn";
82 + break;
83 + case 23:
84 + if (phy->type == B43_PHYTYPE_N)
85 + filename = "ucode16_mimo";
86 + break;
87 + case 16 ... 19:
88 + if (phy->type == B43_PHYTYPE_N)
89 + filename = "ucode16_mimo";
90 + else if (phy->type == B43_PHYTYPE_LP)
91 + filename = "ucode16_lp";
92 + break;
93 + case 15:
94 filename = "ucode15";
95 - } else {
96 - switch (dev->phy.type) {
97 - case B43_PHYTYPE_N:
98 - if (rev >= 16)
99 - filename = "ucode16_mimo";
100 - else
101 - goto err_no_ucode;
102 - break;
103 - case B43_PHYTYPE_HT:
104 - if (rev == 29)
105 - filename = "ucode29_mimo";
106 - else
107 - goto err_no_ucode;
108 - break;
109 - case B43_PHYTYPE_LCN:
110 - if (rev == 24)
111 - filename = "ucode24_mimo";
112 - else
113 - goto err_no_ucode;
114 - break;
115 - default:
116 - goto err_no_ucode;
117 - }
118 + break;
119 + case 14:
120 + filename = "ucode14";
121 + break;
122 + case 13:
123 + filename = "ucode13";
124 + break;
125 + case 11 ... 12:
126 + filename = "ucode11";
127 + break;
128 + case 5 ... 10:
129 + filename = "ucode5";
130 + break;
131 }
132 + if (!filename)
133 + goto err_no_ucode;
134 err = b43_do_request_fw(ctx, filename, &fw->ucode, true);
135 if (err)
136 goto err_load;
137 @@ -2268,117 +2302,121 @@ static int b43_try_request_fw(struct b43
138 goto err_load;
139
140 /* Get initvals */
141 + filename = NULL;
142 switch (dev->phy.type) {
143 - case B43_PHYTYPE_A:
144 - if ((rev >= 5) && (rev <= 10)) {
145 - tmshigh = ssb_read32(dev->dev->sdev, SSB_TMSHIGH);
146 - if (tmshigh & B43_TMSHIGH_HAVE_2GHZ_PHY)
147 - filename = "a0g1initvals5";
148 - else
149 - filename = "a0g0initvals5";
150 - } else
151 - goto err_no_initvals;
152 - break;
153 case B43_PHYTYPE_G:
154 - if ((rev >= 5) && (rev <= 10))
155 - filename = "b0g0initvals5";
156 - else if (rev >= 13)
157 + if (rev == 13)
158 filename = "b0g0initvals13";
159 - else
160 - goto err_no_initvals;
161 + else if (rev >= 5 && rev <= 10)
162 + filename = "b0g0initvals5";
163 break;
164 case B43_PHYTYPE_N:
165 - if (rev >= 16)
166 + if (rev == 30)
167 + filename = "n16initvals30";
168 + else if (rev == 28 || rev == 25)
169 + filename = "n0initvals25";
170 + else if (rev == 24)
171 + filename = "n0initvals24";
172 + else if (rev == 23)
173 + filename = "n0initvals16"; /* What about n0initvals22? */
174 + else if (rev >= 16 && rev <= 18)
175 filename = "n0initvals16";
176 - else if ((rev >= 11) && (rev <= 12))
177 + else if (rev >= 11 && rev <= 12)
178 filename = "n0initvals11";
179 - else
180 - goto err_no_initvals;
181 break;
182 case B43_PHYTYPE_LP:
183 - if (rev == 13)
184 - filename = "lp0initvals13";
185 + if (rev >= 16 && rev <= 18)
186 + filename = "lp0initvals16";
187 + else if (rev == 15)
188 + filename = "lp0initvals15";
189 else if (rev == 14)
190 filename = "lp0initvals14";
191 - else if (rev >= 15)
192 - filename = "lp0initvals15";
193 - else
194 - goto err_no_initvals;
195 + else if (rev == 13)
196 + filename = "lp0initvals13";
197 break;
198 case B43_PHYTYPE_HT:
199 if (rev == 29)
200 filename = "ht0initvals29";
201 - else
202 - goto err_no_initvals;
203 + else if (rev == 26)
204 + filename = "ht0initvals26";
205 break;
206 case B43_PHYTYPE_LCN:
207 if (rev == 24)
208 filename = "lcn0initvals24";
209 - else
210 - goto err_no_initvals;
211 break;
212 - default:
213 - goto err_no_initvals;
214 + case B43_PHYTYPE_LCN40:
215 + if (rev == 33)
216 + filename = "lcn400initvals33";
217 + break;
218 + case B43_PHYTYPE_AC:
219 + if (rev == 42)
220 + filename = "ac1initvals42";
221 + else if (rev == 40)
222 + filename = "ac0initvals40";
223 + break;
224 }
225 + if (!filename)
226 + goto err_no_initvals;
227 err = b43_do_request_fw(ctx, filename, &fw->initvals, false);
228 if (err)
229 goto err_load;
230
231 /* Get bandswitch initvals */
232 + filename = NULL;
233 switch (dev->phy.type) {
234 - case B43_PHYTYPE_A:
235 - if ((rev >= 5) && (rev <= 10)) {
236 - tmshigh = ssb_read32(dev->dev->sdev, SSB_TMSHIGH);
237 - if (tmshigh & B43_TMSHIGH_HAVE_2GHZ_PHY)
238 - filename = "a0g1bsinitvals5";
239 - else
240 - filename = "a0g0bsinitvals5";
241 - } else if (rev >= 11)
242 - filename = NULL;
243 - else
244 - goto err_no_initvals;
245 - break;
246 case B43_PHYTYPE_G:
247 - if ((rev >= 5) && (rev <= 10))
248 + if (rev == 13)
249 + filename = "b0g0bsinitvals13";
250 + else if (rev >= 5 && rev <= 10)
251 filename = "b0g0bsinitvals5";
252 - else if (rev >= 11)
253 - filename = NULL;
254 - else
255 - goto err_no_initvals;
256 break;
257 case B43_PHYTYPE_N:
258 - if (rev >= 16)
259 + if (rev == 30)
260 + filename = "n16bsinitvals30";
261 + else if (rev == 28 || rev == 25)
262 + filename = "n0bsinitvals25";
263 + else if (rev == 24)
264 + filename = "n0bsinitvals24";
265 + else if (rev == 23)
266 + filename = "n0bsinitvals16"; /* What about n0bsinitvals22? */
267 + else if (rev >= 16 && rev <= 18)
268 filename = "n0bsinitvals16";
269 - else if ((rev >= 11) && (rev <= 12))
270 + else if (rev >= 11 && rev <= 12)
271 filename = "n0bsinitvals11";
272 - else
273 - goto err_no_initvals;
274 break;
275 case B43_PHYTYPE_LP:
276 - if (rev == 13)
277 - filename = "lp0bsinitvals13";
278 + if (rev >= 16 && rev <= 18)
279 + filename = "lp0bsinitvals16";
280 + else if (rev == 15)
281 + filename = "lp0bsinitvals15";
282 else if (rev == 14)
283 filename = "lp0bsinitvals14";
284 - else if (rev >= 15)
285 - filename = "lp0bsinitvals15";
286 - else
287 - goto err_no_initvals;
288 + else if (rev == 13)
289 + filename = "lp0bsinitvals13";
290 break;
291 case B43_PHYTYPE_HT:
292 if (rev == 29)
293 filename = "ht0bsinitvals29";
294 - else
295 - goto err_no_initvals;
296 + else if (rev == 26)
297 + filename = "ht0bsinitvals26";
298 break;
299 case B43_PHYTYPE_LCN:
300 if (rev == 24)
301 filename = "lcn0bsinitvals24";
302 - else
303 - goto err_no_initvals;
304 break;
305 - default:
306 - goto err_no_initvals;
307 + case B43_PHYTYPE_LCN40:
308 + if (rev == 33)
309 + filename = "lcn400bsinitvals33";
310 + break;
311 + case B43_PHYTYPE_AC:
312 + if (rev == 42)
313 + filename = "ac1bsinitvals42";
314 + else if (rev == 40)
315 + filename = "ac0bsinitvals40";
316 + break;
317 }
318 + if (!filename)
319 + goto err_no_initvals;
320 err = b43_do_request_fw(ctx, filename, &fw->initvals_band, false);
321 if (err)
322 goto err_load;
323 @@ -3742,7 +3780,9 @@ static int b43_switch_band(struct b43_wl
324 b43dbg(dev->wl, "Switching to %s GHz band\n",
325 band_to_string(chan->band));
326
327 - b43_software_rfkill(dev, true);
328 + /* Some new devices don't need disabling radio for band switching */
329 + if (!(phy->type == B43_PHYTYPE_N && phy->rev >= 3))
330 + b43_software_rfkill(dev, true);
331
332 phy->gmode = gmode;
333 b43_phy_put_into_reset(dev);
334 @@ -3796,38 +3836,29 @@ static void b43_set_retry_limits(struct
335 static int b43_op_config(struct ieee80211_hw *hw, u32 changed)
336 {
337 struct b43_wl *wl = hw_to_b43_wl(hw);
338 - struct b43_wldev *dev;
339 - struct b43_phy *phy;
340 + struct b43_wldev *dev = wl->current_dev;
341 + struct b43_phy *phy = &dev->phy;
342 struct ieee80211_conf *conf = &hw->conf;
343 int antenna;
344 int err = 0;
345 - bool reload_bss = false;
346
347 mutex_lock(&wl->mutex);
348 -
349 - dev = wl->current_dev;
350 -
351 b43_mac_suspend(dev);
352
353 - /* Switch the band (if necessary). This might change the active core. */
354 - err = b43_switch_band(dev, conf->chandef.chan);
355 - if (err)
356 - goto out_unlock_mutex;
357 + if (changed & IEEE80211_CONF_CHANGE_CHANNEL) {
358 + phy->chandef = &conf->chandef;
359 + phy->channel = conf->chandef.chan->hw_value;
360
361 - /* Need to reload all settings if the core changed */
362 - if (dev != wl->current_dev) {
363 - dev = wl->current_dev;
364 - changed = ~0;
365 - reload_bss = true;
366 - }
367 + /* Switch the band (if necessary). */
368 + err = b43_switch_band(dev, conf->chandef.chan);
369 + if (err)
370 + goto out_mac_enable;
371
372 - phy = &dev->phy;
373 -
374 - if (conf_is_ht(conf))
375 - phy->is_40mhz =
376 - (conf_is_ht40_minus(conf) || conf_is_ht40_plus(conf));
377 - else
378 - phy->is_40mhz = false;
379 + /* Switch to the requested channel.
380 + * The firmware takes care of races with the TX handler.
381 + */
382 + b43_switch_channel(dev, phy->channel);
383 + }
384
385 if (changed & IEEE80211_CONF_CHANGE_RETRY_LIMITS)
386 b43_set_retry_limits(dev, conf->short_frame_max_tx_count,
387 @@ -3836,11 +3867,6 @@ static int b43_op_config(struct ieee8021
388 if (!changed)
389 goto out_mac_enable;
390
391 - /* Switch to the requested channel.
392 - * The firmware takes care of races with the TX handler. */
393 - if (conf->chandef.chan->hw_value != phy->channel)
394 - b43_switch_channel(dev, conf->chandef.chan->hw_value);
395 -
396 dev->wl->radiotap_enabled = !!(conf->flags & IEEE80211_CONF_MONITOR);
397
398 /* Adjust the desired TX power level. */
399 @@ -3876,12 +3902,8 @@ static int b43_op_config(struct ieee8021
400
401 out_mac_enable:
402 b43_mac_enable(dev);
403 -out_unlock_mutex:
404 mutex_unlock(&wl->mutex);
405
406 - if (wl->vif && reload_bss)
407 - b43_op_bss_info_changed(hw, wl->vif, &wl->vif->bss_conf, ~0);
408 -
409 return err;
410 }
411
412 @@ -4307,6 +4329,7 @@ static char *b43_phy_name(struct b43_wld
413 static int b43_phy_versioning(struct b43_wldev *dev)
414 {
415 struct b43_phy *phy = &dev->phy;
416 + const u8 core_rev = dev->dev->core_rev;
417 u32 tmp;
418 u8 analog_type;
419 u8 phy_type;
420 @@ -4321,20 +4344,20 @@ static int b43_phy_versioning(struct b43
421 analog_type = (tmp & B43_PHYVER_ANALOG) >> B43_PHYVER_ANALOG_SHIFT;
422 phy_type = (tmp & B43_PHYVER_TYPE) >> B43_PHYVER_TYPE_SHIFT;
423 phy_rev = (tmp & B43_PHYVER_VERSION);
424 +
425 + /* LCNXN is continuation of N which run out of revisions */
426 + if (phy_type == B43_PHYTYPE_LCNXN) {
427 + phy_type = B43_PHYTYPE_N;
428 + phy_rev += 16;
429 + }
430 +
431 switch (phy_type) {
432 - case B43_PHYTYPE_A:
433 - if (phy_rev >= 4)
434 - unsupported = 1;
435 - break;
436 - case B43_PHYTYPE_B:
437 - if (phy_rev != 2 && phy_rev != 4 && phy_rev != 6
438 - && phy_rev != 7)
439 - unsupported = 1;
440 - break;
441 +#ifdef CPTCFG_B43_PHY_G
442 case B43_PHYTYPE_G:
443 if (phy_rev > 9)
444 unsupported = 1;
445 break;
446 +#endif
447 #ifdef CPTCFG_B43_PHY_N
448 case B43_PHYTYPE_N:
449 if (phy_rev > 9)
450 @@ -4372,7 +4395,15 @@ static int b43_phy_versioning(struct b43
451 analog_type, phy_type, b43_phy_name(dev, phy_type), phy_rev);
452
453 /* Get RADIO versioning */
454 - if (dev->dev->core_rev >= 24) {
455 + if (core_rev == 40 || core_rev == 42) {
456 + radio_manuf = 0x17F;
457 +
458 + b43_write16(dev, B43_MMIO_RADIO24_CONTROL, 0);
459 + radio_rev = b43_read16(dev, B43_MMIO_RADIO24_DATA);
460 +
461 + b43_write16(dev, B43_MMIO_RADIO24_CONTROL, 1);
462 + radio_ver = b43_read16(dev, B43_MMIO_RADIO24_DATA);
463 + } else if (core_rev >= 24) {
464 u16 radio24[3];
465
466 for (tmp = 0; tmp < 3; tmp++) {
467 @@ -5164,6 +5195,7 @@ static void b43_supported_bands(struct b
468 static int b43_wireless_core_attach(struct b43_wldev *dev)
469 {
470 struct b43_wl *wl = dev->wl;
471 + struct b43_phy *phy = &dev->phy;
472 int err;
473 u32 tmp;
474 bool have_2ghz_phy = false, have_5ghz_phy = false;
475 @@ -5181,6 +5213,8 @@ static int b43_wireless_core_attach(stru
476 goto out;
477 }
478
479 + phy->do_full_init = true;
480 +
481 /* Try to guess supported bands for the first init needs */
482 switch (dev->dev->bus_type) {
483 #ifdef CPTCFG_B43_BCMA
484 --- a/drivers/net/wireless/b43/phy_common.c
485 +++ b/drivers/net/wireless/b43/phy_common.c
486 @@ -45,11 +45,10 @@ int b43_phy_allocate(struct b43_wldev *d
487 phy->ops = NULL;
488
489 switch (phy->type) {
490 - case B43_PHYTYPE_A:
491 - phy->ops = &b43_phyops_a;
492 - break;
493 case B43_PHYTYPE_G:
494 +#ifdef CPTCFG_B43_PHY_G
495 phy->ops = &b43_phyops_g;
496 +#endif
497 break;
498 case B43_PHYTYPE_N:
499 #ifdef CPTCFG_B43_PHY_N
500 @@ -94,18 +93,25 @@ int b43_phy_init(struct b43_wldev *dev)
501 const struct b43_phy_operations *ops = phy->ops;
502 int err;
503
504 - phy->channel = ops->get_default_chan(dev);
505 + /* During PHY init we need to use some channel. On the first init this
506 + * function is called *before* b43_op_config, so our pointer is NULL.
507 + */
508 + if (!phy->chandef) {
509 + phy->chandef = &dev->wl->hw->conf.chandef;
510 + phy->channel = phy->chandef->chan->hw_value;
511 + }
512
513 phy->ops->switch_analog(dev, true);
514 b43_software_rfkill(dev, false);
515 +
516 err = ops->init(dev);
517 if (err) {
518 b43err(dev->wl, "PHY init failed\n");
519 goto err_block_rf;
520 }
521 - /* Make sure to switch hardware and firmware (SHM) to
522 - * the default channel. */
523 - err = b43_switch_channel(dev, ops->get_default_chan(dev));
524 + phy->do_full_init = false;
525 +
526 + err = b43_switch_channel(dev, phy->channel);
527 if (err) {
528 b43err(dev->wl, "PHY init: Channel switch to default failed\n");
529 goto err_phy_exit;
530 @@ -114,6 +120,7 @@ int b43_phy_init(struct b43_wldev *dev)
531 return 0;
532
533 err_phy_exit:
534 + phy->do_full_init = true;
535 if (ops->exit)
536 ops->exit(dev);
537 err_block_rf:
538 @@ -127,6 +134,7 @@ void b43_phy_exit(struct b43_wldev *dev)
539 const struct b43_phy_operations *ops = dev->phy.ops;
540
541 b43_software_rfkill(dev, true);
542 + dev->phy.do_full_init = true;
543 if (ops->exit)
544 ops->exit(dev);
545 }
546 @@ -403,9 +411,6 @@ int b43_switch_channel(struct b43_wldev
547 u16 channelcookie, savedcookie;
548 int err;
549
550 - if (new_channel == B43_DEFAULT_CHANNEL)
551 - new_channel = phy->ops->get_default_chan(dev);
552 -
553 /* First we set the channel radio code to prevent the
554 * firmware from sending ghost packets.
555 */
556 @@ -423,7 +428,6 @@ int b43_switch_channel(struct b43_wldev
557 if (err)
558 goto err_restore_cookie;
559
560 - dev->phy.channel = new_channel;
561 /* Wait for the radio to tune to the channel and stabilize. */
562 msleep(8);
563
564 @@ -542,10 +546,9 @@ void b43_phyop_switch_analog_generic(str
565 }
566
567
568 -bool b43_channel_type_is_40mhz(enum nl80211_channel_type channel_type)
569 +bool b43_is_40mhz(struct b43_wldev *dev)
570 {
571 - return (channel_type == NL80211_CHAN_HT40MINUS ||
572 - channel_type == NL80211_CHAN_HT40PLUS);
573 + return dev->phy.chandef->width == NL80211_CHAN_WIDTH_40;
574 }
575
576 /* http://bcm-v4.sipsolutions.net/802.11/PHY/N/BmacPhyClkFgc */
577 --- a/drivers/net/wireless/b43/phy_common.h
578 +++ b/drivers/net/wireless/b43/phy_common.h
579 @@ -228,12 +228,12 @@ struct b43_phy {
580 bool supports_2ghz;
581 bool supports_5ghz;
582
583 - /* HT info */
584 - bool is_40mhz;
585 -
586 /* Is GMODE (2 GHz mode) bit enabled? */
587 bool gmode;
588
589 + /* After power reset full init has to be performed */
590 + bool do_full_init;
591 +
592 /* Analog Type */
593 u8 analog;
594 /* B43_PHYTYPE_ */
595 @@ -264,9 +264,8 @@ struct b43_phy {
596 unsigned long next_txpwr_check_time;
597
598 /* Current channel */
599 + struct cfg80211_chan_def *chandef;
600 unsigned int channel;
601 - u16 channel_freq;
602 - enum nl80211_channel_type channel_type;
603
604 /* PHY TX errors counter. */
605 atomic_t txerr_cnt;
606 @@ -397,10 +396,6 @@ void b43_phy_take_out_of_reset(struct b4
607 * b43_switch_channel - Switch to another channel
608 */
609 int b43_switch_channel(struct b43_wldev *dev, unsigned int new_channel);
610 -/**
611 - * B43_DEFAULT_CHANNEL - Switch to the default channel.
612 - */
613 -#define B43_DEFAULT_CHANNEL UINT_MAX
614
615 /**
616 * b43_software_rfkill - Turn the radio ON or OFF in software.
617 @@ -451,7 +446,7 @@ int b43_phy_shm_tssi_read(struct b43_wld
618 */
619 void b43_phyop_switch_analog_generic(struct b43_wldev *dev, bool on);
620
621 -bool b43_channel_type_is_40mhz(enum nl80211_channel_type channel_type);
622 +bool b43_is_40mhz(struct b43_wldev *dev);
623
624 void b43_phy_force_clock(struct b43_wldev *dev, bool force);
625
626 --- a/drivers/net/wireless/b43/phy_n.c
627 +++ b/drivers/net/wireless/b43/phy_n.c
628 @@ -590,7 +590,103 @@ static void b43_nphy_set_rf_sequence(str
629 * Radio 0x2057
630 **************************************************/
631
632 -/* http://bcm-v4.sipsolutions.net/PHY/radio2057_rcal */
633 +static void b43_radio_2057_chantab_upload(struct b43_wldev *dev,
634 + const struct b43_nphy_chantabent_rev7 *e_r7,
635 + const struct b43_nphy_chantabent_rev7_2g *e_r7_2g)
636 +{
637 + if (e_r7_2g) {
638 + b43_radio_write(dev, R2057_VCOCAL_COUNTVAL0, e_r7_2g->radio_vcocal_countval0);
639 + b43_radio_write(dev, R2057_VCOCAL_COUNTVAL1, e_r7_2g->radio_vcocal_countval1);
640 + b43_radio_write(dev, R2057_RFPLL_REFMASTER_SPAREXTALSIZE, e_r7_2g->radio_rfpll_refmaster_sparextalsize);
641 + b43_radio_write(dev, R2057_RFPLL_LOOPFILTER_R1, e_r7_2g->radio_rfpll_loopfilter_r1);
642 + b43_radio_write(dev, R2057_RFPLL_LOOPFILTER_C2, e_r7_2g->radio_rfpll_loopfilter_c2);
643 + b43_radio_write(dev, R2057_RFPLL_LOOPFILTER_C1, e_r7_2g->radio_rfpll_loopfilter_c1);
644 + b43_radio_write(dev, R2057_CP_KPD_IDAC, e_r7_2g->radio_cp_kpd_idac);
645 + b43_radio_write(dev, R2057_RFPLL_MMD0, e_r7_2g->radio_rfpll_mmd0);
646 + b43_radio_write(dev, R2057_RFPLL_MMD1, e_r7_2g->radio_rfpll_mmd1);
647 + b43_radio_write(dev, R2057_VCOBUF_TUNE, e_r7_2g->radio_vcobuf_tune);
648 + b43_radio_write(dev, R2057_LOGEN_MX2G_TUNE, e_r7_2g->radio_logen_mx2g_tune);
649 + b43_radio_write(dev, R2057_LOGEN_INDBUF2G_TUNE, e_r7_2g->radio_logen_indbuf2g_tune);
650 + b43_radio_write(dev, R2057_TXMIX2G_TUNE_BOOST_PU_CORE0, e_r7_2g->radio_txmix2g_tune_boost_pu_core0);
651 + b43_radio_write(dev, R2057_PAD2G_TUNE_PUS_CORE0, e_r7_2g->radio_pad2g_tune_pus_core0);
652 + b43_radio_write(dev, R2057_LNA2G_TUNE_CORE0, e_r7_2g->radio_lna2g_tune_core0);
653 + b43_radio_write(dev, R2057_TXMIX2G_TUNE_BOOST_PU_CORE1, e_r7_2g->radio_txmix2g_tune_boost_pu_core1);
654 + b43_radio_write(dev, R2057_PAD2G_TUNE_PUS_CORE1, e_r7_2g->radio_pad2g_tune_pus_core1);
655 + b43_radio_write(dev, R2057_LNA2G_TUNE_CORE1, e_r7_2g->radio_lna2g_tune_core1);
656 +
657 + } else {
658 + b43_radio_write(dev, R2057_VCOCAL_COUNTVAL0, e_r7->radio_vcocal_countval0);
659 + b43_radio_write(dev, R2057_VCOCAL_COUNTVAL1, e_r7->radio_vcocal_countval1);
660 + b43_radio_write(dev, R2057_RFPLL_REFMASTER_SPAREXTALSIZE, e_r7->radio_rfpll_refmaster_sparextalsize);
661 + b43_radio_write(dev, R2057_RFPLL_LOOPFILTER_R1, e_r7->radio_rfpll_loopfilter_r1);
662 + b43_radio_write(dev, R2057_RFPLL_LOOPFILTER_C2, e_r7->radio_rfpll_loopfilter_c2);
663 + b43_radio_write(dev, R2057_RFPLL_LOOPFILTER_C1, e_r7->radio_rfpll_loopfilter_c1);
664 + b43_radio_write(dev, R2057_CP_KPD_IDAC, e_r7->radio_cp_kpd_idac);
665 + b43_radio_write(dev, R2057_RFPLL_MMD0, e_r7->radio_rfpll_mmd0);
666 + b43_radio_write(dev, R2057_RFPLL_MMD1, e_r7->radio_rfpll_mmd1);
667 + b43_radio_write(dev, R2057_VCOBUF_TUNE, e_r7->radio_vcobuf_tune);
668 + b43_radio_write(dev, R2057_LOGEN_MX2G_TUNE, e_r7->radio_logen_mx2g_tune);
669 + b43_radio_write(dev, R2057_LOGEN_MX5G_TUNE, e_r7->radio_logen_mx5g_tune);
670 + b43_radio_write(dev, R2057_LOGEN_INDBUF2G_TUNE, e_r7->radio_logen_indbuf2g_tune);
671 + b43_radio_write(dev, R2057_LOGEN_INDBUF5G_TUNE, e_r7->radio_logen_indbuf5g_tune);
672 + b43_radio_write(dev, R2057_TXMIX2G_TUNE_BOOST_PU_CORE0, e_r7->radio_txmix2g_tune_boost_pu_core0);
673 + b43_radio_write(dev, R2057_PAD2G_TUNE_PUS_CORE0, e_r7->radio_pad2g_tune_pus_core0);
674 + b43_radio_write(dev, R2057_PGA_BOOST_TUNE_CORE0, e_r7->radio_pga_boost_tune_core0);
675 + b43_radio_write(dev, R2057_TXMIX5G_BOOST_TUNE_CORE0, e_r7->radio_txmix5g_boost_tune_core0);
676 + b43_radio_write(dev, R2057_PAD5G_TUNE_MISC_PUS_CORE0, e_r7->radio_pad5g_tune_misc_pus_core0);
677 + b43_radio_write(dev, R2057_LNA2G_TUNE_CORE0, e_r7->radio_lna2g_tune_core0);
678 + b43_radio_write(dev, R2057_LNA5G_TUNE_CORE0, e_r7->radio_lna5g_tune_core0);
679 + b43_radio_write(dev, R2057_TXMIX2G_TUNE_BOOST_PU_CORE1, e_r7->radio_txmix2g_tune_boost_pu_core1);
680 + b43_radio_write(dev, R2057_PAD2G_TUNE_PUS_CORE1, e_r7->radio_pad2g_tune_pus_core1);
681 + b43_radio_write(dev, R2057_PGA_BOOST_TUNE_CORE1, e_r7->radio_pga_boost_tune_core1);
682 + b43_radio_write(dev, R2057_TXMIX5G_BOOST_TUNE_CORE1, e_r7->radio_txmix5g_boost_tune_core1);
683 + b43_radio_write(dev, R2057_PAD5G_TUNE_MISC_PUS_CORE1, e_r7->radio_pad5g_tune_misc_pus_core1);
684 + b43_radio_write(dev, R2057_LNA2G_TUNE_CORE1, e_r7->radio_lna2g_tune_core1);
685 + b43_radio_write(dev, R2057_LNA5G_TUNE_CORE1, e_r7->radio_lna5g_tune_core1);
686 + }
687 +}
688 +
689 +static void b43_radio_2057_setup(struct b43_wldev *dev,
690 + const struct b43_nphy_chantabent_rev7 *tabent_r7,
691 + const struct b43_nphy_chantabent_rev7_2g *tabent_r7_2g)
692 +{
693 + struct b43_phy *phy = &dev->phy;
694 +
695 + b43_radio_2057_chantab_upload(dev, tabent_r7, tabent_r7_2g);
696 +
697 + switch (phy->radio_rev) {
698 + case 0 ... 4:
699 + case 6:
700 + if (b43_current_band(dev->wl) == IEEE80211_BAND_2GHZ) {
701 + b43_radio_write(dev, R2057_RFPLL_LOOPFILTER_R1, 0x3f);
702 + b43_radio_write(dev, R2057_CP_KPD_IDAC, 0x3f);
703 + b43_radio_write(dev, R2057_RFPLL_LOOPFILTER_C1, 0x8);
704 + b43_radio_write(dev, R2057_RFPLL_LOOPFILTER_C2, 0x8);
705 + } else {
706 + b43_radio_write(dev, R2057_RFPLL_LOOPFILTER_R1, 0x1f);
707 + b43_radio_write(dev, R2057_CP_KPD_IDAC, 0x3f);
708 + b43_radio_write(dev, R2057_RFPLL_LOOPFILTER_C1, 0x8);
709 + b43_radio_write(dev, R2057_RFPLL_LOOPFILTER_C2, 0x8);
710 + }
711 + break;
712 + /* TODO */
713 + }
714 +
715 + /* TODO */
716 +
717 + usleep_range(50, 100);
718 +
719 + /* VCO calibration */
720 + b43_radio_mask(dev, R2057_RFPLL_MISC_EN, ~0x01);
721 + b43_radio_mask(dev, R2057_RFPLL_MISC_CAL_RESETN, ~0x04);
722 + b43_radio_set(dev, R2057_RFPLL_MISC_CAL_RESETN, 0x4);
723 + b43_radio_set(dev, R2057_RFPLL_MISC_EN, 0x01);
724 + usleep_range(300, 600);
725 +}
726 +
727 +/* Calibrate resistors in LPF of PLL?
728 + * http://bcm-v4.sipsolutions.net/PHY/radio205x_rcal
729 + */
730 static u8 b43_radio_2057_rcal(struct b43_wldev *dev)
731 {
732 struct b43_phy *phy = &dev->phy;
733 @@ -603,15 +699,25 @@ static u8 b43_radio_2057_rcal(struct b43
734 b43_radio_maskset(dev, 0x1ca, ~0x2, 0x1);
735 }
736
737 + /* Enable */
738 b43_radio_set(dev, R2057_RCAL_CONFIG, 0x1);
739 udelay(10);
740 - b43_radio_set(dev, R2057_RCAL_CONFIG, 0x3);
741 - if (!b43_radio_wait_value(dev, R2057_RCCAL_N1_1, 1, 1, 100, 1000000)) {
742 +
743 + /* Start */
744 + b43_radio_set(dev, R2057_RCAL_CONFIG, 0x2);
745 + usleep_range(100, 200);
746 +
747 + /* Stop */
748 + b43_radio_mask(dev, R2057_RCAL_CONFIG, ~0x2);
749 +
750 + /* Wait and check for result */
751 + if (!b43_radio_wait_value(dev, R2057_RCAL_STATUS, 1, 1, 100, 1000000)) {
752 b43err(dev->wl, "Radio 0x2057 rcal timeout\n");
753 return 0;
754 }
755 - b43_radio_mask(dev, R2057_RCAL_CONFIG, ~0x2);
756 tmp = b43_radio_read(dev, R2057_RCAL_STATUS) & 0x3E;
757 +
758 + /* Disable */
759 b43_radio_mask(dev, R2057_RCAL_CONFIG, ~0x1);
760
761 if (phy->radio_rev == 5) {
762 @@ -627,7 +733,9 @@ static u8 b43_radio_2057_rcal(struct b43
763 return tmp & 0x3e;
764 }
765
766 -/* http://bcm-v4.sipsolutions.net/PHY/radio2057_rccal */
767 +/* Calibrate the internal RC oscillator?
768 + * http://bcm-v4.sipsolutions.net/PHY/radio2057_rccal
769 + */
770 static u16 b43_radio_2057_rccal(struct b43_wldev *dev)
771 {
772 struct b43_phy *phy = &dev->phy;
773 @@ -635,49 +743,76 @@ static u16 b43_radio_2057_rccal(struct b
774 phy->radio_rev == 6);
775 u16 tmp;
776
777 + /* Setup cal */
778 if (special) {
779 b43_radio_write(dev, R2057_RCCAL_MASTER, 0x61);
780 b43_radio_write(dev, R2057_RCCAL_TRC0, 0xC0);
781 } else {
782 - b43_radio_write(dev, 0x1AE, 0x61);
783 + b43_radio_write(dev, R2057v7_RCCAL_MASTER, 0x61);
784 b43_radio_write(dev, R2057_RCCAL_TRC0, 0xE1);
785 }
786 b43_radio_write(dev, R2057_RCCAL_X1, 0x6E);
787 +
788 + /* Start, wait, stop */
789 b43_radio_write(dev, R2057_RCCAL_START_R1_Q1_P1, 0x55);
790 - if (!b43_radio_wait_value(dev, R2057_RCCAL_DONE_OSCCAP, 1, 1, 500,
791 + if (!b43_radio_wait_value(dev, R2057_RCCAL_DONE_OSCCAP, 2, 2, 500,
792 5000000))
793 b43dbg(dev->wl, "Radio 0x2057 rccal timeout\n");
794 + usleep_range(35, 70);
795 b43_radio_write(dev, R2057_RCCAL_START_R1_Q1_P1, 0x15);
796 + usleep_range(70, 140);
797 +
798 + /* Setup cal */
799 if (special) {
800 b43_radio_write(dev, R2057_RCCAL_MASTER, 0x69);
801 b43_radio_write(dev, R2057_RCCAL_TRC0, 0xB0);
802 } else {
803 - b43_radio_write(dev, 0x1AE, 0x69);
804 + b43_radio_write(dev, R2057v7_RCCAL_MASTER, 0x69);
805 b43_radio_write(dev, R2057_RCCAL_TRC0, 0xD5);
806 }
807 b43_radio_write(dev, R2057_RCCAL_X1, 0x6E);
808 +
809 + /* Start, wait, stop */
810 + usleep_range(35, 70);
811 b43_radio_write(dev, R2057_RCCAL_START_R1_Q1_P1, 0x55);
812 - if (!b43_radio_wait_value(dev, R2057_RCCAL_DONE_OSCCAP, 1, 1, 500,
813 + usleep_range(70, 140);
814 + if (!b43_radio_wait_value(dev, R2057_RCCAL_DONE_OSCCAP, 2, 2, 500,
815 5000000))
816 b43dbg(dev->wl, "Radio 0x2057 rccal timeout\n");
817 + usleep_range(35, 70);
818 b43_radio_write(dev, R2057_RCCAL_START_R1_Q1_P1, 0x15);
819 + usleep_range(70, 140);
820 +
821 + /* Setup cal */
822 if (special) {
823 b43_radio_write(dev, R2057_RCCAL_MASTER, 0x73);
824 b43_radio_write(dev, R2057_RCCAL_X1, 0x28);
825 b43_radio_write(dev, R2057_RCCAL_TRC0, 0xB0);
826 } else {
827 - b43_radio_write(dev, 0x1AE, 0x73);
828 + b43_radio_write(dev, R2057v7_RCCAL_MASTER, 0x73);
829 b43_radio_write(dev, R2057_RCCAL_X1, 0x6E);
830 b43_radio_write(dev, R2057_RCCAL_TRC0, 0x99);
831 }
832 +
833 + /* Start, wait, stop */
834 + usleep_range(35, 70);
835 b43_radio_write(dev, R2057_RCCAL_START_R1_Q1_P1, 0x55);
836 - if (!b43_radio_wait_value(dev, R2057_RCCAL_DONE_OSCCAP, 1, 1, 500,
837 + usleep_range(70, 140);
838 + if (!b43_radio_wait_value(dev, R2057_RCCAL_DONE_OSCCAP, 2, 2, 500,
839 5000000)) {
840 b43err(dev->wl, "Radio 0x2057 rcal timeout\n");
841 return 0;
842 }
843 tmp = b43_radio_read(dev, R2057_RCCAL_DONE_OSCCAP);
844 + usleep_range(35, 70);
845 b43_radio_write(dev, R2057_RCCAL_START_R1_Q1_P1, 0x15);
846 + usleep_range(70, 140);
847 +
848 + if (special)
849 + b43_radio_mask(dev, R2057_RCCAL_MASTER, ~0x1);
850 + else
851 + b43_radio_mask(dev, R2057v7_RCCAL_MASTER, ~0x1);
852 +
853 return tmp;
854 }
855
856 @@ -700,13 +835,11 @@ static void b43_radio_2057_init_post(str
857 b43_radio_mask(dev, R2057_RFPLL_MISC_CAL_RESETN, ~0x78);
858 b43_radio_mask(dev, R2057_XTAL_CONFIG2, ~0x80);
859
860 - if (dev->phy.n->init_por) {
861 + if (dev->phy.do_full_init) {
862 b43_radio_2057_rcal(dev);
863 b43_radio_2057_rccal(dev);
864 }
865 b43_radio_mask(dev, R2057_RFPLL_MASTER, ~0x8);
866 -
867 - dev->phy.n->init_por = false;
868 }
869
870 /* http://bcm-v4.sipsolutions.net/802.11/Radio/2057/Init */
871 @@ -800,6 +933,7 @@ static void b43_chantab_radio_2056_uploa
872 static void b43_radio_2056_setup(struct b43_wldev *dev,
873 const struct b43_nphy_channeltab_entry_rev3 *e)
874 {
875 + struct b43_phy *phy = &dev->phy;
876 struct ssb_sprom *sprom = dev->dev->bus_sprom;
877 enum ieee80211_band band = b43_current_band(dev->wl);
878 u16 offset;
879 @@ -897,7 +1031,7 @@ static void b43_radio_2056_setup(struct
880 offset | B2056_TX_MIXG_BOOST_TUNE,
881 mixg_boost);
882 } else {
883 - bias = dev->phy.is_40mhz ? 0x40 : 0x20;
884 + bias = b43_is_40mhz(dev) ? 0x40 : 0x20;
885 b43_radio_write(dev,
886 offset | B2056_TX_INTPAG_IMAIN_STAT,
887 bias);
888 @@ -911,7 +1045,7 @@ static void b43_radio_2056_setup(struct
889 b43_radio_write(dev, offset | B2056_TX_PA_SPARE1, 0xee);
890 }
891 } else if (dev->phy.n->ipa5g_on && band == IEEE80211_BAND_5GHZ) {
892 - u16 freq = dev->phy.channel_freq;
893 + u16 freq = phy->chandef->chan->center_freq;
894 if (freq < 5100) {
895 paa_boost = 0xA;
896 pada_boost = 0x77;
897 @@ -1028,7 +1162,7 @@ static void b43_radio_init2056_post(stru
898 b43_radio_mask(dev, B2056_SYN_COM_RESET, ~0x2);
899 b43_radio_mask(dev, B2056_SYN_PLL_MAST2, ~0xFC);
900 b43_radio_mask(dev, B2056_SYN_RCCAL_CTRL0, ~0x1);
901 - if (dev->phy.n->init_por)
902 + if (dev->phy.do_full_init)
903 b43_radio_2056_rcal(dev);
904 }
905
906 @@ -1041,8 +1175,6 @@ static void b43_radio_init2056(struct b4
907 b43_radio_init2056_pre(dev);
908 b2056_upload_inittabs(dev, 0, 0);
909 b43_radio_init2056_post(dev);
910 -
911 - dev->phy.n->init_por = false;
912 }
913
914 /**************************************************
915 @@ -1214,8 +1346,7 @@ static u16 b43_nphy_gen_load_samples(str
916 u16 bw, len, rot, angle;
917 struct b43_c32 *samples;
918
919 -
920 - bw = (dev->phy.is_40mhz) ? 40 : 20;
921 + bw = b43_is_40mhz(dev) ? 40 : 20;
922 len = bw << 3;
923
924 if (test) {
925 @@ -1224,7 +1355,7 @@ static u16 b43_nphy_gen_load_samples(str
926 else
927 bw = 80;
928
929 - if (dev->phy.is_40mhz)
930 + if (b43_is_40mhz(dev))
931 bw <<= 1;
932
933 len = bw << 1;
934 @@ -1252,7 +1383,8 @@ static u16 b43_nphy_gen_load_samples(str
935
936 /* http://bcm-v4.sipsolutions.net/802.11/PHY/N/RunSamples */
937 static void b43_nphy_run_samples(struct b43_wldev *dev, u16 samps, u16 loops,
938 - u16 wait, bool iqmode, bool dac_test)
939 + u16 wait, bool iqmode, bool dac_test,
940 + bool modify_bbmult)
941 {
942 struct b43_phy_n *nphy = dev->phy.n;
943 int i;
944 @@ -1266,12 +1398,10 @@ static void b43_nphy_run_samples(struct
945 nphy->bb_mult_save = (tmp & 0xFFFF) | 0x80000000;
946 }
947
948 - /* TODO: add modify_bbmult argument */
949 - if (!dev->phy.is_40mhz)
950 - tmp = 0x6464;
951 - else
952 - tmp = 0x4747;
953 - b43_ntab_write(dev, B43_NTAB16(15, 87), tmp);
954 + if (modify_bbmult) {
955 + tmp = !b43_is_40mhz(dev) ? 0x6464 : 0x4747;
956 + b43_ntab_write(dev, B43_NTAB16(15, 87), tmp);
957 + }
958
959 b43_phy_write(dev, B43_NPHY_SAMP_DEPCNT, (samps - 1));
960
961 @@ -1289,10 +1419,8 @@ static void b43_nphy_run_samples(struct
962 b43_phy_mask(dev, B43_NPHY_IQLOCAL_CMDGCTL, 0x7FFF);
963 b43_phy_set(dev, B43_NPHY_IQLOCAL_CMDGCTL, 0x8000);
964 } else {
965 - if (dac_test)
966 - b43_phy_write(dev, B43_NPHY_SAMP_CMD, 5);
967 - else
968 - b43_phy_write(dev, B43_NPHY_SAMP_CMD, 1);
969 + tmp = dac_test ? 5 : 1;
970 + b43_phy_write(dev, B43_NPHY_SAMP_CMD, tmp);
971 }
972 for (i = 0; i < 100; i++) {
973 if (!(b43_phy_read(dev, B43_NPHY_RFSEQST) & 1)) {
974 @@ -1679,6 +1807,7 @@ static int b43_nphy_poll_rssi(struct b43
975 /* http://bcm-v4.sipsolutions.net/802.11/PHY/N/RSSICalRev3 */
976 static void b43_nphy_rev3_rssi_cal(struct b43_wldev *dev)
977 {
978 + struct b43_phy *phy = &dev->phy;
979 struct b43_phy_n *nphy = dev->phy.n;
980
981 u16 saved_regs_phy_rfctl[2];
982 @@ -1901,9 +2030,9 @@ static void b43_nphy_rev3_rssi_cal(struc
983
984 /* Remember for which channel we store configuration */
985 if (b43_current_band(dev->wl) == IEEE80211_BAND_2GHZ)
986 - nphy->rssical_chanspec_2G.center_freq = dev->phy.channel_freq;
987 + nphy->rssical_chanspec_2G.center_freq = phy->chandef->chan->center_freq;
988 else
989 - nphy->rssical_chanspec_5G.center_freq = dev->phy.channel_freq;
990 + nphy->rssical_chanspec_5G.center_freq = phy->chandef->chan->center_freq;
991
992 /* End of calibration, restore configuration */
993 b43_nphy_classifier(dev, 7, class);
994 @@ -2196,7 +2325,7 @@ static void b43_nphy_gain_ctl_workaround
995 b43_phy_write(dev, B43_NPHY_C1_NBCLIPTHRES, 0x84);
996 b43_phy_write(dev, B43_NPHY_C2_NBCLIPTHRES, 0x84);
997
998 - if (!dev->phy.is_40mhz) {
999 + if (!b43_is_40mhz(dev)) {
1000 /* Set dwell lengths */
1001 b43_phy_write(dev, B43_NPHY_CLIP1_NBDWELL_LEN, 0x002B);
1002 b43_phy_write(dev, B43_NPHY_CLIP2_NBDWELL_LEN, 0x002B);
1003 @@ -2210,7 +2339,7 @@ static void b43_nphy_gain_ctl_workaround
1004 b43_phy_maskset(dev, B43_NPHY_C2_CLIPWBTHRES,
1005 ~B43_NPHY_C2_CLIPWBTHRES_CLIP2, 21);
1006
1007 - if (!dev->phy.is_40mhz) {
1008 + if (!b43_is_40mhz(dev)) {
1009 b43_phy_maskset(dev, B43_NPHY_C1_CGAINI,
1010 ~B43_NPHY_C1_CGAINI_GAINBKOFF, 0x1);
1011 b43_phy_maskset(dev, B43_NPHY_C2_CGAINI,
1012 @@ -2225,12 +2354,12 @@ static void b43_nphy_gain_ctl_workaround
1013
1014 if (nphy->gain_boost) {
1015 if (b43_current_band(dev->wl) == IEEE80211_BAND_2GHZ &&
1016 - dev->phy.is_40mhz)
1017 + b43_is_40mhz(dev))
1018 code = 4;
1019 else
1020 code = 5;
1021 } else {
1022 - code = dev->phy.is_40mhz ? 6 : 7;
1023 + code = b43_is_40mhz(dev) ? 6 : 7;
1024 }
1025
1026 /* Set HPVGA2 index */
1027 @@ -2302,7 +2431,7 @@ static void b43_nphy_gain_ctl_workaround
1028 static u16 b43_nphy_read_lpf_ctl(struct b43_wldev *dev, u16 offset)
1029 {
1030 if (!offset)
1031 - offset = (dev->phy.is_40mhz) ? 0x159 : 0x154;
1032 + offset = b43_is_40mhz(dev) ? 0x159 : 0x154;
1033 return b43_ntab_read(dev, B43_NTAB16(7, offset)) & 0x7;
1034 }
1035
1036 @@ -2375,13 +2504,13 @@ static void b43_nphy_workarounds_rev7plu
1037 lpf_40 = b43_nphy_read_lpf_ctl(dev, 0x159);
1038 lpf_11b = b43_nphy_read_lpf_ctl(dev, 0x152);
1039 if (b43_nphy_ipa(dev)) {
1040 - if ((phy->radio_rev == 5 && phy->is_40mhz) ||
1041 + if ((phy->radio_rev == 5 && b43_is_40mhz(dev)) ||
1042 phy->radio_rev == 7 || phy->radio_rev == 8) {
1043 bcap_val = b43_radio_read(dev, 0x16b);
1044 scap_val = b43_radio_read(dev, 0x16a);
1045 scap_val_11b = scap_val;
1046 bcap_val_11b = bcap_val;
1047 - if (phy->radio_rev == 5 && phy->is_40mhz) {
1048 + if (phy->radio_rev == 5 && b43_is_40mhz(dev)) {
1049 scap_val_11n_20 = scap_val;
1050 bcap_val_11n_20 = bcap_val;
1051 scap_val_11n_40 = bcap_val_11n_40 = 0xc;
1052 @@ -2523,7 +2652,7 @@ static void b43_nphy_workarounds_rev7plu
1053 }
1054 }
1055 } else if (phy->radio_rev == 7 || phy->radio_rev == 8) {
1056 - if (!phy->is_40mhz) {
1057 + if (!b43_is_40mhz(dev)) {
1058 b43_radio_write(dev, 0x5F, 0x14);
1059 b43_radio_write(dev, 0xE8, 0x12);
1060 } else {
1061 @@ -2532,7 +2661,7 @@ static void b43_nphy_workarounds_rev7plu
1062 }
1063 }
1064 } else {
1065 - u16 freq = phy->channel_freq;
1066 + u16 freq = phy->chandef->chan->center_freq;
1067 if ((freq >= 5180 && freq <= 5230) ||
1068 (freq >= 5745 && freq <= 5805)) {
1069 b43_radio_write(dev, 0x7D, 0xFF);
1070 @@ -2596,7 +2725,7 @@ static void b43_nphy_workarounds_rev7plu
1071 b43_ntab_write(dev, B43_NTAB16(7, 0x123), 0x77);
1072 b43_ntab_write(dev, B43_NTAB16(7, 0x12A), 0x77);
1073
1074 - if (!phy->is_40mhz) {
1075 + if (!b43_is_40mhz(dev)) {
1076 b43_ntab_write(dev, B43_NTAB32(16, 0x03), 0x18D);
1077 b43_ntab_write(dev, B43_NTAB32(16, 0x7F), 0x18D);
1078 } else {
1079 @@ -2695,7 +2824,7 @@ static void b43_nphy_workarounds_rev3plu
1080
1081 b43_phy_maskset(dev, B43_NPHY_SGILTRNOFFSET, 0xF0FF, 0x0700);
1082
1083 - if (!dev->phy.is_40mhz) {
1084 + if (!b43_is_40mhz(dev)) {
1085 b43_ntab_write(dev, B43_NTAB32(16, 3), 0x18D);
1086 b43_ntab_write(dev, B43_NTAB32(16, 127), 0x18D);
1087 } else {
1088 @@ -2950,12 +3079,13 @@ static void b43_nphy_workarounds(struct
1089 * http://bcm-v4.sipsolutions.net/802.11/PHY/N/TXTone
1090 */
1091 static int b43_nphy_tx_tone(struct b43_wldev *dev, u32 freq, u16 max_val,
1092 - bool iqmode, bool dac_test)
1093 + bool iqmode, bool dac_test, bool modify_bbmult)
1094 {
1095 u16 samp = b43_nphy_gen_load_samples(dev, freq, max_val, dac_test);
1096 if (samp == 0)
1097 return -1;
1098 - b43_nphy_run_samples(dev, samp, 0xFFFF, 0, iqmode, dac_test);
1099 + b43_nphy_run_samples(dev, samp, 0xFFFF, 0, iqmode, dac_test,
1100 + modify_bbmult);
1101 return 0;
1102 }
1103
1104 @@ -3118,7 +3248,7 @@ static void b43_nphy_tx_power_ctrl(struc
1105 b43_phy_maskset(dev, B43_NPHY_BPHY_CTL3,
1106 ~B43_NPHY_BPHY_CTL3_SCALE, 0x5A);
1107
1108 - if (dev->phy.rev < 2 && dev->phy.is_40mhz)
1109 + if (dev->phy.rev < 2 && b43_is_40mhz(dev))
1110 b43_hf_write(dev, b43_hf_read(dev) | B43_HF_TSSIRPSMW);
1111 } else {
1112 b43_ntab_write_bulk(dev, B43_NTAB16(26, 64), 84,
1113 @@ -3172,7 +3302,7 @@ static void b43_nphy_tx_power_ctrl(struc
1114 else if (dev->phy.rev < 2)
1115 b43_phy_maskset(dev, B43_NPHY_BPHY_CTL3, ~0xFF, 0x40);
1116
1117 - if (dev->phy.rev < 2 && dev->phy.is_40mhz)
1118 + if (dev->phy.rev < 2 && b43_is_40mhz(dev))
1119 b43_hf_write(dev, b43_hf_read(dev) & ~B43_HF_TSSIRPSMW);
1120
1121 if (b43_nphy_ipa(dev)) {
1122 @@ -3188,12 +3318,13 @@ static void b43_nphy_tx_power_ctrl(struc
1123 /* http://bcm-v4.sipsolutions.net/802.11/PHY/N/TxPwrFix */
1124 static void b43_nphy_tx_power_fix(struct b43_wldev *dev)
1125 {
1126 + struct b43_phy *phy = &dev->phy;
1127 struct b43_phy_n *nphy = dev->phy.n;
1128 struct ssb_sprom *sprom = dev->dev->bus_sprom;
1129
1130 u8 txpi[2], bbmult, i;
1131 u16 tmp, radio_gain, dac_gain;
1132 - u16 freq = dev->phy.channel_freq;
1133 + u16 freq = phy->chandef->chan->center_freq;
1134 u32 txgain;
1135 /* u32 gaintbl; rev3+ */
1136
1137 @@ -3238,7 +3369,11 @@ static void b43_nphy_tx_power_fix(struct
1138 */
1139
1140 for (i = 0; i < 2; i++) {
1141 - txgain = *(b43_nphy_get_tx_gain_table(dev) + txpi[i]);
1142 + const u32 *table = b43_nphy_get_tx_gain_table(dev);
1143 +
1144 + if (!table)
1145 + break;
1146 + txgain = *(table + txpi[i]);
1147
1148 if (dev->phy.rev >= 3)
1149 radio_gain = (txgain >> 16) & 0x1FFFF;
1150 @@ -3392,7 +3527,7 @@ static void b43_nphy_tx_power_ctl_idle_t
1151 b43_nphy_rf_ctl_override(dev, 0x2000, 0, 3, false);
1152
1153 b43_nphy_stop_playback(dev);
1154 - b43_nphy_tx_tone(dev, 0xFA0, 0, false, false);
1155 + b43_nphy_tx_tone(dev, 4000, 0, false, false, false);
1156 udelay(20);
1157 tmp = b43_nphy_poll_rssi(dev, N_RSSI_TSSI_2G, rssi, 1);
1158 b43_nphy_stop_playback(dev);
1159 @@ -3443,21 +3578,21 @@ static void b43_nphy_tx_prepare_adjusted
1160 delta = 0;
1161 switch (stf_mode) {
1162 case 0:
1163 - if (dev->phy.is_40mhz && dev->phy.rev >= 5) {
1164 + if (b43_is_40mhz(dev) && dev->phy.rev >= 5) {
1165 idx = 68;
1166 } else {
1167 delta = 1;
1168 - idx = dev->phy.is_40mhz ? 52 : 4;
1169 + idx = b43_is_40mhz(dev) ? 52 : 4;
1170 }
1171 break;
1172 case 1:
1173 - idx = dev->phy.is_40mhz ? 76 : 28;
1174 + idx = b43_is_40mhz(dev) ? 76 : 28;
1175 break;
1176 case 2:
1177 - idx = dev->phy.is_40mhz ? 84 : 36;
1178 + idx = b43_is_40mhz(dev) ? 84 : 36;
1179 break;
1180 case 3:
1181 - idx = dev->phy.is_40mhz ? 92 : 44;
1182 + idx = b43_is_40mhz(dev) ? 92 : 44;
1183 break;
1184 }
1185
1186 @@ -3478,6 +3613,7 @@ static void b43_nphy_tx_prepare_adjusted
1187 /* http://bcm-v4.sipsolutions.net/802.11/PHY/N/TxPwrCtrlSetup */
1188 static void b43_nphy_tx_power_ctl_setup(struct b43_wldev *dev)
1189 {
1190 + struct b43_phy *phy = &dev->phy;
1191 struct b43_phy_n *nphy = dev->phy.n;
1192 struct ssb_sprom *sprom = dev->dev->bus_sprom;
1193
1194 @@ -3487,7 +3623,7 @@ static void b43_nphy_tx_power_ctl_setup(
1195 s32 num, den, pwr;
1196 u32 regval[64];
1197
1198 - u16 freq = dev->phy.channel_freq;
1199 + u16 freq = phy->chandef->chan->center_freq;
1200 u16 tmp;
1201 u16 r; /* routing */
1202 u8 i, c;
1203 @@ -3651,6 +3787,9 @@ static void b43_nphy_tx_gain_table_uploa
1204 int i;
1205
1206 table = b43_nphy_get_tx_gain_table(dev);
1207 + if (!table)
1208 + return;
1209 +
1210 b43_ntab_write_bulk(dev, B43_NTAB32(26, 192), 128, table);
1211 b43_ntab_write_bulk(dev, B43_NTAB32(27, 192), 128, table);
1212
1213 @@ -3709,21 +3848,28 @@ static void b43_nphy_pa_override(struct
1214 }
1215 }
1216
1217 -/* http://bcm-v4.sipsolutions.net/802.11/PHY/N/TxLpFbw */
1218 -static void b43_nphy_tx_lp_fbw(struct b43_wldev *dev)
1219 +/*
1220 + * TX low-pass filter bandwidth setup
1221 + * http://bcm-v4.sipsolutions.net/802.11/PHY/N/TxLpFbw
1222 + */
1223 +static void b43_nphy_tx_lpf_bw(struct b43_wldev *dev)
1224 {
1225 u16 tmp;
1226
1227 - if (dev->phy.rev >= 3) {
1228 - if (b43_nphy_ipa(dev)) {
1229 - tmp = 4;
1230 - b43_phy_write(dev, B43_NPHY_TXF_40CO_B32S2,
1231 - (((((tmp << 3) | tmp) << 3) | tmp) << 3) | tmp);
1232 - }
1233 + if (dev->phy.rev < 3 || dev->phy.rev >= 7)
1234 + return;
1235
1236 - tmp = 1;
1237 + if (b43_nphy_ipa(dev))
1238 + tmp = b43_is_40mhz(dev) ? 5 : 4;
1239 + else
1240 + tmp = b43_is_40mhz(dev) ? 3 : 1;
1241 + b43_phy_write(dev, B43_NPHY_TXF_40CO_B32S2,
1242 + (tmp << 9) | (tmp << 6) | (tmp << 3) | tmp);
1243 +
1244 + if (b43_nphy_ipa(dev)) {
1245 + tmp = b43_is_40mhz(dev) ? 4 : 1;
1246 b43_phy_write(dev, B43_NPHY_TXF_40CO_B1S2,
1247 - (((((tmp << 3) | tmp) << 3) | tmp) << 3) | tmp);
1248 + (tmp << 9) | (tmp << 6) | (tmp << 3) | tmp);
1249 }
1250 }
1251
1252 @@ -3996,7 +4142,7 @@ static void b43_nphy_spur_workaround(str
1253
1254 if (nphy->gband_spurwar_en) {
1255 /* TODO: N PHY Adjust Analog Pfbw (7) */
1256 - if (channel == 11 && dev->phy.is_40mhz)
1257 + if (channel == 11 && b43_is_40mhz(dev))
1258 ; /* TODO: N PHY Adjust Min Noise Var(2, tone, noise)*/
1259 else
1260 ; /* TODO: N PHY Adjust Min Noise Var(0, NULL, NULL)*/
1261 @@ -4290,7 +4436,7 @@ static void b43_nphy_int_pa_set_tx_dig_f
1262 b43_phy_write(dev, B43_PHY_N(offset[i] + j),
1263 tbl_tx_filter_coef_rev4[i][j]);
1264
1265 - if (dev->phy.is_40mhz) {
1266 + if (b43_is_40mhz(dev)) {
1267 for (j = 0; j < 15; j++)
1268 b43_phy_write(dev, B43_PHY_N(offset[0] + j),
1269 tbl_tx_filter_coef_rev4[3][j]);
1270 @@ -4349,6 +4495,9 @@ static struct nphy_txgains b43_nphy_get_
1271
1272 for (i = 0; i < 2; ++i) {
1273 table = b43_nphy_get_tx_gain_table(dev);
1274 + if (!table)
1275 + break;
1276 +
1277 if (dev->phy.rev >= 3) {
1278 target.ipa[i] = (table[index[i]] >> 16) & 0xF;
1279 target.pad[i] = (table[index[i]] >> 20) & 0xF;
1280 @@ -4504,8 +4653,9 @@ static void b43_nphy_save_cal(struct b43
1281 txcal_radio_regs[2] = b43_radio_read(dev, 0x8D);
1282 txcal_radio_regs[3] = b43_radio_read(dev, 0xBC);
1283 }
1284 - iqcal_chanspec->center_freq = dev->phy.channel_freq;
1285 - iqcal_chanspec->channel_type = dev->phy.channel_type;
1286 + iqcal_chanspec->center_freq = dev->phy.chandef->chan->center_freq;
1287 + iqcal_chanspec->channel_type =
1288 + cfg80211_get_chandef_type(dev->phy.chandef);
1289 b43_ntab_read_bulk(dev, B43_NTAB16(15, 80), 8, table);
1290
1291 if (nphy->hang_avoid)
1292 @@ -4585,6 +4735,7 @@ static int b43_nphy_cal_tx_iq_lo(struct
1293 struct nphy_txgains target,
1294 bool full, bool mphase)
1295 {
1296 + struct b43_phy *phy = &dev->phy;
1297 struct b43_phy_n *nphy = dev->phy.n;
1298 int i;
1299 int error = 0;
1300 @@ -4625,7 +4776,7 @@ static int b43_nphy_cal_tx_iq_lo(struct
1301 (dev->phy.rev == 5 && nphy->ipa2g_on &&
1302 b43_current_band(dev->wl) == IEEE80211_BAND_2GHZ);
1303 if (phy6or5x) {
1304 - if (dev->phy.is_40mhz) {
1305 + if (b43_is_40mhz(dev)) {
1306 b43_ntab_write_bulk(dev, B43_NTAB16(15, 0), 18,
1307 tbl_tx_iqlo_cal_loft_ladder_40);
1308 b43_ntab_write_bulk(dev, B43_NTAB16(15, 32), 18,
1309 @@ -4640,16 +4791,16 @@ static int b43_nphy_cal_tx_iq_lo(struct
1310
1311 b43_phy_write(dev, B43_NPHY_IQLOCAL_CMDGCTL, 0x8AA9);
1312
1313 - if (!dev->phy.is_40mhz)
1314 + if (!b43_is_40mhz(dev))
1315 freq = 2500;
1316 else
1317 freq = 5000;
1318
1319 if (nphy->mphase_cal_phase_id > 2)
1320 - b43_nphy_run_samples(dev, (dev->phy.is_40mhz ? 40 : 20) * 8,
1321 - 0xFFFF, 0, true, false);
1322 + b43_nphy_run_samples(dev, (b43_is_40mhz(dev) ? 40 : 20) * 8,
1323 + 0xFFFF, 0, true, false, false);
1324 else
1325 - error = b43_nphy_tx_tone(dev, freq, 250, true, false);
1326 + error = b43_nphy_tx_tone(dev, freq, 250, true, false, false);
1327
1328 if (error == 0) {
1329 if (nphy->mphase_cal_phase_id > 2) {
1330 @@ -4777,9 +4928,9 @@ static int b43_nphy_cal_tx_iq_lo(struct
1331 nphy->txiqlocal_bestc);
1332 nphy->txiqlocal_coeffsvalid = true;
1333 nphy->txiqlocal_chanspec.center_freq =
1334 - dev->phy.channel_freq;
1335 + phy->chandef->chan->center_freq;
1336 nphy->txiqlocal_chanspec.channel_type =
1337 - dev->phy.channel_type;
1338 + cfg80211_get_chandef_type(phy->chandef);
1339 } else {
1340 length = 11;
1341 if (dev->phy.rev < 3)
1342 @@ -4815,8 +4966,8 @@ static void b43_nphy_reapply_tx_cal_coef
1343 bool equal = true;
1344
1345 if (!nphy->txiqlocal_coeffsvalid ||
1346 - nphy->txiqlocal_chanspec.center_freq != dev->phy.channel_freq ||
1347 - nphy->txiqlocal_chanspec.channel_type != dev->phy.channel_type)
1348 + nphy->txiqlocal_chanspec.center_freq != dev->phy.chandef->chan->center_freq ||
1349 + nphy->txiqlocal_chanspec.channel_type != cfg80211_get_chandef_type(dev->phy.chandef))
1350 return;
1351
1352 b43_ntab_read_bulk(dev, B43_NTAB16(15, 80), 7, buffer);
1353 @@ -4972,11 +5123,11 @@ static int b43_nphy_rev2_cal_rx_iq(struc
1354 if (playtone) {
1355 ret = b43_nphy_tx_tone(dev, 4000,
1356 (nphy->rxcalparams & 0xFFFF),
1357 - false, false);
1358 + false, false, true);
1359 playtone = false;
1360 } else {
1361 - b43_nphy_run_samples(dev, 160, 0xFFFF, 0,
1362 - false, false);
1363 + b43_nphy_run_samples(dev, 160, 0xFFFF, 0, false,
1364 + false, true);
1365 }
1366
1367 if (ret == 0) {
1368 @@ -5348,7 +5499,7 @@ static int b43_phy_initn(struct b43_wlde
1369 b43_phy_write(dev, B43_NPHY_TXMACDELAY, 0x0320);
1370 if (phy->rev >= 3 && phy->rev <= 6)
1371 b43_phy_write(dev, B43_NPHY_PLOAD_CSENSE_EXTLEN, 0x0032);
1372 - b43_nphy_tx_lp_fbw(dev);
1373 + b43_nphy_tx_lpf_bw(dev);
1374 if (phy->rev >= 3)
1375 b43_nphy_spur_workaround(dev);
1376
1377 @@ -5434,14 +5585,14 @@ static void b43_nphy_channel_setup(struc
1378 if (dev->phy.rev < 3)
1379 b43_nphy_adjust_lna_gain_table(dev);
1380
1381 - b43_nphy_tx_lp_fbw(dev);
1382 + b43_nphy_tx_lpf_bw(dev);
1383
1384 if (dev->phy.rev >= 3 &&
1385 dev->phy.n->spur_avoid != B43_SPUR_AVOID_DISABLE) {
1386 bool avoid = false;
1387 if (dev->phy.n->spur_avoid == B43_SPUR_AVOID_FORCE) {
1388 avoid = true;
1389 - } else if (!b43_channel_type_is_40mhz(phy->channel_type)) {
1390 + } else if (!b43_is_40mhz(dev)) {
1391 if ((ch >= 5 && ch <= 8) || ch == 13 || ch == 14)
1392 avoid = true;
1393 } else { /* 40MHz */
1394 @@ -5488,10 +5639,17 @@ static int b43_nphy_set_channel(struct b
1395
1396 const struct b43_nphy_channeltab_entry_rev2 *tabent_r2 = NULL;
1397 const struct b43_nphy_channeltab_entry_rev3 *tabent_r3 = NULL;
1398 + const struct b43_nphy_chantabent_rev7 *tabent_r7 = NULL;
1399 + const struct b43_nphy_chantabent_rev7_2g *tabent_r7_2g = NULL;
1400
1401 u8 tmp;
1402
1403 - if (dev->phy.rev >= 3) {
1404 + if (phy->rev >= 7) {
1405 + r2057_get_chantabent_rev7(dev, channel->center_freq,
1406 + &tabent_r7, &tabent_r7_2g);
1407 + if (!tabent_r7 && !tabent_r7_2g)
1408 + return -ESRCH;
1409 + } else if (phy->rev >= 3) {
1410 tabent_r3 = b43_nphy_get_chantabent_rev3(dev,
1411 channel->center_freq);
1412 if (!tabent_r3)
1413 @@ -5506,20 +5664,36 @@ static int b43_nphy_set_channel(struct b
1414 /* Channel is set later in common code, but we need to set it on our
1415 own to let this function's subcalls work properly. */
1416 phy->channel = channel->hw_value;
1417 - phy->channel_freq = channel->center_freq;
1418
1419 +#if 0
1420 if (b43_channel_type_is_40mhz(phy->channel_type) !=
1421 b43_channel_type_is_40mhz(channel_type))
1422 ; /* TODO: BMAC BW Set (channel_type) */
1423 +#endif
1424
1425 - if (channel_type == NL80211_CHAN_HT40PLUS)
1426 - b43_phy_set(dev, B43_NPHY_RXCTL,
1427 - B43_NPHY_RXCTL_BSELU20);
1428 - else if (channel_type == NL80211_CHAN_HT40MINUS)
1429 - b43_phy_mask(dev, B43_NPHY_RXCTL,
1430 - ~B43_NPHY_RXCTL_BSELU20);
1431 + if (channel_type == NL80211_CHAN_HT40PLUS) {
1432 + b43_phy_set(dev, B43_NPHY_RXCTL, B43_NPHY_RXCTL_BSELU20);
1433 + if (phy->rev >= 7)
1434 + b43_phy_set(dev, 0x310, 0x8000);
1435 + } else if (channel_type == NL80211_CHAN_HT40MINUS) {
1436 + b43_phy_mask(dev, B43_NPHY_RXCTL, ~B43_NPHY_RXCTL_BSELU20);
1437 + if (phy->rev >= 7)
1438 + b43_phy_mask(dev, 0x310, (u16)~0x8000);
1439 + }
1440
1441 - if (dev->phy.rev >= 3) {
1442 + if (phy->rev >= 7) {
1443 + const struct b43_phy_n_sfo_cfg *phy_regs = tabent_r7 ?
1444 + &(tabent_r7->phy_regs) : &(tabent_r7_2g->phy_regs);
1445 +
1446 + if (phy->radio_rev <= 4 || phy->radio_rev == 6) {
1447 + tmp = (channel->band == IEEE80211_BAND_5GHZ) ? 2 : 0;
1448 + b43_radio_maskset(dev, R2057_TIA_CONFIG_CORE0, ~2, tmp);
1449 + b43_radio_maskset(dev, R2057_TIA_CONFIG_CORE1, ~2, tmp);
1450 + }
1451 +
1452 + b43_radio_2057_setup(dev, tabent_r7, tabent_r7_2g);
1453 + b43_nphy_channel_setup(dev, phy_regs, channel);
1454 + } else if (phy->rev >= 3) {
1455 tmp = (channel->band == IEEE80211_BAND_5GHZ) ? 4 : 0;
1456 b43_radio_maskset(dev, 0x08, 0xFFFB, tmp);
1457 b43_radio_2056_setup(dev, tabent_r3);
1458 @@ -5561,7 +5735,6 @@ static void b43_nphy_op_prepare_structs(
1459 nphy->hang_avoid = (phy->rev == 3 || phy->rev == 4);
1460 nphy->spur_avoid = (phy->rev >= 3) ?
1461 B43_SPUR_AVOID_AUTO : B43_SPUR_AVOID_DISABLE;
1462 - nphy->init_por = true;
1463 nphy->gain_boost = true; /* this way we follow wl, assume it is true */
1464 nphy->txrx_chain = 2; /* sth different than 0 and 1 for now */
1465 nphy->phyrxchain = 3; /* to avoid b43_nphy_set_rx_core_state like wl */
1466 @@ -5602,8 +5775,6 @@ static void b43_nphy_op_prepare_structs(
1467 nphy->ipa2g_on = sprom->fem.ghz2.extpa_gain == 2;
1468 nphy->ipa5g_on = sprom->fem.ghz5.extpa_gain == 2;
1469 }
1470 -
1471 - nphy->init_por = true;
1472 }
1473
1474 static void b43_nphy_op_free(struct b43_wldev *dev)
1475 @@ -5714,10 +5885,12 @@ static void b43_nphy_op_software_rfkill(
1476 }
1477 } else {
1478 if (dev->phy.rev >= 7) {
1479 - b43_radio_2057_init(dev);
1480 + if (!dev->phy.radio_on)
1481 + b43_radio_2057_init(dev);
1482 b43_switch_channel(dev, dev->phy.channel);
1483 } else if (dev->phy.rev >= 3) {
1484 - b43_radio_init2056(dev);
1485 + if (!dev->phy.radio_on)
1486 + b43_radio_init2056(dev);
1487 b43_switch_channel(dev, dev->phy.channel);
1488 } else {
1489 b43_radio_init2055(dev);
1490 --- a/drivers/net/wireless/b43/phy_n.h
1491 +++ b/drivers/net/wireless/b43/phy_n.h
1492 @@ -931,7 +931,6 @@ struct b43_phy_n {
1493 u16 papd_epsilon_offset[2];
1494 s32 preamble_override;
1495 u32 bb_mult_save;
1496 - bool init_por;
1497
1498 bool gain_boost;
1499 bool elna_gain_config;
1500 --- a/drivers/net/wireless/b43/tables_nphy.c
1501 +++ b/drivers/net/wireless/b43/tables_nphy.c
1502 @@ -2146,7 +2146,196 @@ static const u16 b43_ntab_antswctl_r3[4]
1503 }
1504 };
1505
1506 -/* TX gain tables */
1507 +/* static tables, PHY revision >= 7 */
1508 +
1509 +/* Copied from brcmsmac (5.75.11) */
1510 +static const u32 b43_ntab_tmap_r7[] = {
1511 + 0x8a88aa80, 0x8aaaaa8a, 0x8a8a8aa8, 0x00000888,
1512 + 0x88000000, 0x8a8a88aa, 0x8aa88888, 0x8888a8a8,
1513 + 0xf1111110, 0x11111111, 0x11f11111, 0x00000111,
1514 + 0x11000000, 0x1111f111, 0x11111111, 0x111111f1,
1515 + 0x8a88aa80, 0x8aaaaa8a, 0x8a8a8aa8, 0x000aa888,
1516 + 0x88880000, 0x8a8a88aa, 0x8aa88888, 0x8888a8a8,
1517 + 0xa1111110, 0x11111111, 0x11c11111, 0x00000111,
1518 + 0x11000000, 0x1111a111, 0x11111111, 0x111111a1,
1519 + 0xa2222220, 0x22222222, 0x22c22222, 0x00000222,
1520 + 0x22000000, 0x2222a222, 0x22222222, 0x222222a2,
1521 + 0xf1111110, 0x11111111, 0x11f11111, 0x00011111,
1522 + 0x11110000, 0x1111f111, 0x11111111, 0x111111f1,
1523 + 0xa8aa88a0, 0xa88888a8, 0xa8a8a88a, 0x00088aaa,
1524 + 0xaaaa0000, 0xa8a8aa88, 0xa88aaaaa, 0xaaaa8a8a,
1525 + 0xaaa8aaa0, 0x8aaa8aaa, 0xaa8a8a8a, 0x000aaa88,
1526 + 0x8aaa0000, 0xaaa8a888, 0x8aa88a8a, 0x8a88a888,
1527 + 0x08080a00, 0x0a08080a, 0x080a0a08, 0x00080808,
1528 + 0x080a0000, 0x080a0808, 0x080a0808, 0x0a0a0a08,
1529 + 0xa0a0a0a0, 0x80a0a080, 0x8080a0a0, 0x00008080,
1530 + 0x80a00000, 0x80a080a0, 0xa080a0a0, 0x8080a0a0,
1531 + 0x00000000, 0x00000000, 0x00000000, 0x00000000,
1532 + 0x00000000, 0x00000000, 0x00000000, 0x00000000,
1533 + 0x00000000, 0x00000000, 0x00000000, 0x00000000,
1534 + 0x00000000, 0x00000000, 0x00000000, 0x00000000,
1535 + 0x00000000, 0x00000000, 0x00000000, 0x00000000,
1536 + 0x00000000, 0x00000000, 0x00000000, 0x00000000,
1537 + 0x00000000, 0x00000000, 0x00000000, 0x00000000,
1538 + 0x00000000, 0x00000000, 0x00000000, 0x00000000,
1539 + 0x00000000, 0x00000000, 0x00000000, 0x00000000,
1540 + 0x00000000, 0x00000000, 0x00000000, 0x00000000,
1541 + 0x00000000, 0x00000000, 0x00000000, 0x00000000,
1542 + 0x00000000, 0x00000000, 0x00000000, 0x00000000,
1543 + 0x99999000, 0x9b9b99bb, 0x9bb99999, 0x9999b9b9,
1544 + 0x9b99bb90, 0x9bbbbb9b, 0x9b9b9bb9, 0x00000999,
1545 + 0x88000000, 0x8a8a88aa, 0x8aa88888, 0x8888a8a8,
1546 + 0x8a88aa80, 0x8aaaaa8a, 0x8a8a8aa8, 0x00aaa888,
1547 + 0x22000000, 0x2222b222, 0x22222222, 0x222222b2,
1548 + 0xb2222220, 0x22222222, 0x22d22222, 0x00000222,
1549 + 0x11000000, 0x1111a111, 0x11111111, 0x111111a1,
1550 + 0xa1111110, 0x11111111, 0x11c11111, 0x00000111,
1551 + 0x33000000, 0x3333b333, 0x33333333, 0x333333b3,
1552 + 0xb3333330, 0x33333333, 0x33d33333, 0x00000333,
1553 + 0x22000000, 0x2222a222, 0x22222222, 0x222222a2,
1554 + 0xa2222220, 0x22222222, 0x22c22222, 0x00000222,
1555 + 0x99b99b00, 0x9b9b99bb, 0x9bb99999, 0x9999b9b9,
1556 + 0x9b99bb99, 0x9bbbbb9b, 0x9b9b9bb9, 0x00000999,
1557 + 0x88000000, 0x8a8a88aa, 0x8aa88888, 0x8888a8a8,
1558 + 0x8a88aa88, 0x8aaaaa8a, 0x8a8a8aa8, 0x08aaa888,
1559 + 0x22222200, 0x2222f222, 0x22222222, 0x222222f2,
1560 + 0x22222222, 0x22222222, 0x22f22222, 0x00000222,
1561 + 0x11000000, 0x1111f111, 0x11111111, 0x11111111,
1562 + 0xf1111111, 0x11111111, 0x11f11111, 0x01111111,
1563 + 0xbb9bb900, 0xb9b9bb99, 0xb99bbbbb, 0xbbbb9b9b,
1564 + 0xb9bb99bb, 0xb99999b9, 0xb9b9b99b, 0x00000bbb,
1565 + 0xaa000000, 0xa8a8aa88, 0xa88aaaaa, 0xaaaa8a8a,
1566 + 0xa8aa88aa, 0xa88888a8, 0xa8a8a88a, 0x0a888aaa,
1567 + 0xaa000000, 0xa8a8aa88, 0xa88aaaaa, 0xaaaa8a8a,
1568 + 0xa8aa88a0, 0xa88888a8, 0xa8a8a88a, 0x00000aaa,
1569 + 0x88000000, 0x8a8a88aa, 0x8aa88888, 0x8888a8a8,
1570 + 0x8a88aa80, 0x8aaaaa8a, 0x8a8a8aa8, 0x00000888,
1571 + 0xbbbbbb00, 0x999bbbbb, 0x9bb99b9b, 0xb9b9b9bb,
1572 + 0xb9b99bbb, 0xb9b9b9bb, 0xb9bb9b99, 0x00000999,
1573 + 0x8a000000, 0xaa88a888, 0xa88888aa, 0xa88a8a88,
1574 + 0xa88aa88a, 0x88a8aaaa, 0xa8aa8aaa, 0x0888a88a,
1575 + 0x0b0b0b00, 0x090b0b0b, 0x0b090b0b, 0x0909090b,
1576 + 0x09090b0b, 0x09090b0b, 0x09090b09, 0x00000909,
1577 + 0x0a000000, 0x0a080808, 0x080a080a, 0x080a0a08,
1578 + 0x080a080a, 0x0808080a, 0x0a0a0a08, 0x0808080a,
1579 + 0xb0b0b000, 0x9090b0b0, 0x90b09090, 0xb0b0b090,
1580 + 0xb0b090b0, 0x90b0b0b0, 0xb0b09090, 0x00000090,
1581 + 0x80000000, 0xa080a080, 0xa08080a0, 0xa0808080,
1582 + 0xa080a080, 0x80a0a0a0, 0xa0a080a0, 0x00a0a0a0,
1583 + 0x22000000, 0x2222f222, 0x22222222, 0x222222f2,
1584 + 0xf2222220, 0x22222222, 0x22f22222, 0x00000222,
1585 + 0x11000000, 0x1111f111, 0x11111111, 0x111111f1,
1586 + 0xf1111110, 0x11111111, 0x11f11111, 0x00000111,
1587 + 0x33000000, 0x3333f333, 0x33333333, 0x333333f3,
1588 + 0xf3333330, 0x33333333, 0x33f33333, 0x00000333,
1589 + 0x22000000, 0x2222f222, 0x22222222, 0x222222f2,
1590 + 0xf2222220, 0x22222222, 0x22f22222, 0x00000222,
1591 + 0x99000000, 0x9b9b99bb, 0x9bb99999, 0x9999b9b9,
1592 + 0x9b99bb90, 0x9bbbbb9b, 0x9b9b9bb9, 0x00000999,
1593 + 0x88000000, 0x8a8a88aa, 0x8aa88888, 0x8888a8a8,
1594 + 0x8a88aa80, 0x8aaaaa8a, 0x8a8a8aa8, 0x00000888,
1595 + 0x88888000, 0x8a8a88aa, 0x8aa88888, 0x8888a8a8,
1596 + 0x8a88aa80, 0x8aaaaa8a, 0x8a8a8aa8, 0x00000888,
1597 + 0x88000000, 0x8a8a88aa, 0x8aa88888, 0x8888a8a8,
1598 + 0x8a88aa80, 0x8aaaaa8a, 0x8a8a8aa8, 0x00aaa888,
1599 + 0x88a88a00, 0x8a8a88aa, 0x8aa88888, 0x8888a8a8,
1600 + 0x8a88aa88, 0x8aaaaa8a, 0x8a8a8aa8, 0x000aa888,
1601 + 0x88880000, 0x8a8a88aa, 0x8aa88888, 0x8888a8a8,
1602 + 0x8a88aa88, 0x8aaaaa8a, 0x8a8a8aa8, 0x08aaa888,
1603 + 0x11000000, 0x1111a111, 0x11111111, 0x111111a1,
1604 + 0xa1111110, 0x11111111, 0x11c11111, 0x00000111,
1605 + 0x11000000, 0x1111a111, 0x11111111, 0x111111a1,
1606 + 0xa1111110, 0x11111111, 0x11c11111, 0x00000111,
1607 + 0x88000000, 0x8a8a88aa, 0x8aa88888, 0x8888a8a8,
1608 + 0x8a88aa80, 0x8aaaaa8a, 0x8a8a8aa8, 0x00000888,
1609 + 0x88000000, 0x8a8a88aa, 0x8aa88888, 0x8888a8a8,
1610 + 0x8a88aa80, 0x8aaaaa8a, 0x8a8a8aa8, 0x00000888,
1611 + 0x00000000, 0x00000000, 0x00000000, 0x00000000,
1612 + 0x00000000, 0x00000000, 0x00000000, 0x00000000,
1613 + 0x00000000, 0x00000000, 0x00000000, 0x00000000,
1614 + 0x00000000, 0x00000000, 0x00000000, 0x00000000,
1615 + 0x00000000, 0x00000000, 0x00000000, 0x00000000,
1616 + 0x00000000, 0x00000000, 0x00000000, 0x00000000,
1617 + 0x00000000, 0x00000000, 0x00000000, 0x00000000,
1618 + 0x00000000, 0x00000000, 0x00000000, 0x00000000,
1619 + 0x00000000, 0x00000000, 0x00000000, 0x00000000,
1620 + 0x00000000, 0x00000000, 0x00000000, 0x00000000,
1621 + 0x00000000, 0x00000000, 0x00000000, 0x00000000,
1622 + 0x00000000, 0x00000000, 0x00000000, 0x00000000,
1623 +};
1624 +
1625 +/* Extracted from MMIO dump of 6.30.223.141 */
1626 +static const u32 b43_ntab_noisevar_r7[] = {
1627 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1628 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1629 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1630 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1631 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1632 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1633 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1634 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1635 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1636 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1637 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1638 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1639 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1640 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1641 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1642 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1643 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1644 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1645 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1646 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1647 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1648 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1649 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1650 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1651 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1652 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1653 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1654 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1655 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1656 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1657 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1658 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1659 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1660 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1661 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1662 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1663 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1664 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1665 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1666 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1667 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1668 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1669 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1670 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1671 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1672 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1673 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1674 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1675 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1676 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1677 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1678 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1679 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1680 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1681 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1682 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1683 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1684 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1685 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1686 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1687 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1688 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1689 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1690 + 0x020c020c, 0x0000014d, 0x020c020c, 0x0000014d,
1691 +};
1692 +
1693 +/**************************************************
1694 + * TX gain tables
1695 + **************************************************/
1696 +
1697 static const u32 b43_ntab_tx_gain_rev0_1_2[] = {
1698 0x03cc2b44, 0x03cc2b42, 0x03cc2a44, 0x03cc2a42,
1699 0x03cc2944, 0x03c82b44, 0x03c82b42, 0x03c82a44,
1700 @@ -2182,7 +2371,9 @@ static const u32 b43_ntab_tx_gain_rev0_1
1701 0x03801442, 0x03801344, 0x03801342, 0x00002b00,
1702 };
1703
1704 -static const u32 b43_ntab_tx_gain_rev3plus_2ghz[] = {
1705 +/* EPA 2 GHz */
1706 +
1707 +static const u32 b43_ntab_tx_gain_epa_rev3_2g[] = {
1708 0x1f410044, 0x1f410042, 0x1f410040, 0x1f41003e,
1709 0x1f41003c, 0x1f41003b, 0x1f410039, 0x1f410037,
1710 0x1e410044, 0x1e410042, 0x1e410040, 0x1e41003e,
1711 @@ -2217,7 +2408,9 @@ static const u32 b43_ntab_tx_gain_rev3pl
1712 0x1041003c, 0x1041003b, 0x10410039, 0x10410037,
1713 };
1714
1715 -static const u32 b43_ntab_tx_gain_rev3_5ghz[] = {
1716 +/* EPA 5 GHz */
1717 +
1718 +static const u32 b43_ntab_tx_gain_epa_rev3_5g[] = {
1719 0xcff70044, 0xcff70042, 0xcff70040, 0xcff7003e,
1720 0xcff7003c, 0xcff7003b, 0xcff70039, 0xcff70037,
1721 0xcef70044, 0xcef70042, 0xcef70040, 0xcef7003e,
1722 @@ -2252,7 +2445,7 @@ static const u32 b43_ntab_tx_gain_rev3_5
1723 0xc0f7003c, 0xc0f7003b, 0xc0f70039, 0xc0f70037,
1724 };
1725
1726 -static const u32 b43_ntab_tx_gain_rev4_5ghz[] = {
1727 +static const u32 b43_ntab_tx_gain_epa_rev4_5g[] = {
1728 0x2ff20044, 0x2ff20042, 0x2ff20040, 0x2ff2003e,
1729 0x2ff2003c, 0x2ff2003b, 0x2ff20039, 0x2ff20037,
1730 0x2ef20044, 0x2ef20042, 0x2ef20040, 0x2ef2003e,
1731 @@ -2287,7 +2480,7 @@ static const u32 b43_ntab_tx_gain_rev4_5
1732 0x20d2003a, 0x20d20038, 0x20d20036, 0x20d20034,
1733 };
1734
1735 -static const u32 b43_ntab_tx_gain_rev5plus_5ghz[] = {
1736 +static const u32 b43_ntab_tx_gain_epa_rev5_5g[] = {
1737 0x0f62004a, 0x0f620048, 0x0f620046, 0x0f620044,
1738 0x0f620042, 0x0f620040, 0x0f62003e, 0x0f62003c,
1739 0x0e620044, 0x0e620042, 0x0e620040, 0x0e62003e,
1740 @@ -2322,7 +2515,9 @@ static const u32 b43_ntab_tx_gain_rev5pl
1741 0x0062003b, 0x00620039, 0x00620037, 0x00620035,
1742 };
1743
1744 -static const u32 txpwrctrl_tx_gain_ipa[] = {
1745 +/* IPA 2 GHz */
1746 +
1747 +static const u32 b43_ntab_tx_gain_ipa_rev3_2g[] = {
1748 0x5ff7002d, 0x5ff7002b, 0x5ff7002a, 0x5ff70029,
1749 0x5ff70028, 0x5ff70027, 0x5ff70026, 0x5ff70025,
1750 0x5ef7002d, 0x5ef7002b, 0x5ef7002a, 0x5ef70029,
1751 @@ -2357,7 +2552,7 @@ static const u32 txpwrctrl_tx_gain_ipa[]
1752 0x50f70028, 0x50f70027, 0x50f70026, 0x50f70025,
1753 };
1754
1755 -static const u32 txpwrctrl_tx_gain_ipa_rev5[] = {
1756 +static const u32 b43_ntab_tx_gain_ipa_rev5_2g[] = {
1757 0x1ff7002d, 0x1ff7002b, 0x1ff7002a, 0x1ff70029,
1758 0x1ff70028, 0x1ff70027, 0x1ff70026, 0x1ff70025,
1759 0x1ef7002d, 0x1ef7002b, 0x1ef7002a, 0x1ef70029,
1760 @@ -2392,7 +2587,7 @@ static const u32 txpwrctrl_tx_gain_ipa_r
1761 0x10f70028, 0x10f70027, 0x10f70026, 0x10f70025,
1762 };
1763
1764 -static const u32 txpwrctrl_tx_gain_ipa_rev6[] = {
1765 +static const u32 b43_ntab_tx_gain_ipa_rev6_2g[] = {
1766 0x0ff7002d, 0x0ff7002b, 0x0ff7002a, 0x0ff70029,
1767 0x0ff70028, 0x0ff70027, 0x0ff70026, 0x0ff70025,
1768 0x0ef7002d, 0x0ef7002b, 0x0ef7002a, 0x0ef70029,
1769 @@ -2427,7 +2622,45 @@ static const u32 txpwrctrl_tx_gain_ipa_r
1770 0x00f70028, 0x00f70027, 0x00f70026, 0x00f70025,
1771 };
1772
1773 -static const u32 txpwrctrl_tx_gain_ipa_5g[] = {
1774 +/* Extracted from MMIO dump of 6.30.223.141 */
1775 +static const u32 b43_ntab_tx_gain_ipa_2057_rev9_2g[] = {
1776 + 0x60ff0031, 0x60e7002c, 0x60cf002a, 0x60c70029,
1777 + 0x60b70029, 0x60a70029, 0x609f002a, 0x6097002b,
1778 + 0x6087002e, 0x60770031, 0x606f0032, 0x60670034,
1779 + 0x60670031, 0x605f0033, 0x605f0031, 0x60570033,
1780 + 0x60570030, 0x6057002d, 0x6057002b, 0x604f002d,
1781 + 0x604f002b, 0x604f0029, 0x604f0026, 0x60470029,
1782 + 0x60470027, 0x603f0029, 0x603f0027, 0x603f0025,
1783 + 0x60370029, 0x60370027, 0x60370024, 0x602f002a,
1784 + 0x602f0028, 0x602f0026, 0x602f0024, 0x6027002a,
1785 + 0x60270028, 0x60270026, 0x60270024, 0x60270022,
1786 + 0x601f002b, 0x601f0029, 0x601f0027, 0x601f0024,
1787 + 0x601f0022, 0x601f0020, 0x601f001f, 0x601f001d,
1788 + 0x60170029, 0x60170027, 0x60170025, 0x60170023,
1789 + 0x60170021, 0x6017001f, 0x6017001d, 0x6017001c,
1790 + 0x6017001a, 0x60170018, 0x60170018, 0x60170016,
1791 + 0x60170015, 0x600f0029, 0x600f0027, 0x600f0025,
1792 + 0x600f0023, 0x600f0021, 0x600f001f, 0x600f001d,
1793 + 0x600f001c, 0x600f001a, 0x600f0019, 0x600f0018,
1794 + 0x600f0016, 0x600f0015, 0x600f0115, 0x600f0215,
1795 + 0x600f0315, 0x600f0415, 0x600f0515, 0x600f0615,
1796 + 0x600f0715, 0x600f0715, 0x600f0715, 0x600f0715,
1797 + 0x600f0715, 0x600f0715, 0x600f0715, 0x600f0715,
1798 + 0x600f0715, 0x600f0715, 0x600f0715, 0x600f0715,
1799 + 0x600f0715, 0x600f0715, 0x600f0715, 0x600f0715,
1800 + 0x600f0715, 0x600f0715, 0x600f0715, 0x600f0715,
1801 + 0x600f0715, 0x600f0715, 0x600f0715, 0x600f0715,
1802 + 0x600f0715, 0x600f0715, 0x600f0715, 0x600f0715,
1803 + 0x600f0715, 0x600f0715, 0x600f0715, 0x600f0715,
1804 + 0x600f0715, 0x600f0715, 0x600f0715, 0x600f0715,
1805 + 0x600f0715, 0x600f0715, 0x600f0715, 0x600f0715,
1806 + 0x600f0715, 0x600f0715, 0x600f0715, 0x600f0715,
1807 + 0x600f0715, 0x600f0715, 0x600f0715, 0x600f0715,
1808 +};
1809 +
1810 +/* IPA 2 5Hz */
1811 +
1812 +static const u32 b43_ntab_tx_gain_ipa_rev3_5g[] = {
1813 0x7ff70035, 0x7ff70033, 0x7ff70032, 0x7ff70031,
1814 0x7ff7002f, 0x7ff7002e, 0x7ff7002d, 0x7ff7002b,
1815 0x7ff7002a, 0x7ff70029, 0x7ff70028, 0x7ff70027,
1816 @@ -2462,6 +2695,42 @@ static const u32 txpwrctrl_tx_gain_ipa_5
1817 0x70f70021, 0x70f70020, 0x70f70020, 0x70f7001f,
1818 };
1819
1820 +/* Extracted from MMIO dump of 6.30.223.141 */
1821 +static const u32 b43_ntab_tx_gain_ipa_2057_rev9_5g[] = {
1822 + 0x7f7f0053, 0x7f7f004b, 0x7f7f0044, 0x7f7f003f,
1823 + 0x7f7f0039, 0x7f7f0035, 0x7f7f0032, 0x7f7f0030,
1824 + 0x7f7f002d, 0x7e7f0030, 0x7e7f002d, 0x7d7f0032,
1825 + 0x7d7f002f, 0x7d7f002c, 0x7c7f0032, 0x7c7f0030,
1826 + 0x7c7f002d, 0x7b7f0030, 0x7b7f002e, 0x7b7f002b,
1827 + 0x7a7f0032, 0x7a7f0030, 0x7a7f002d, 0x7a7f002b,
1828 + 0x797f0030, 0x797f002e, 0x797f002b, 0x797f0029,
1829 + 0x787f0030, 0x787f002d, 0x787f002b, 0x777f0032,
1830 + 0x777f0030, 0x777f002d, 0x777f002b, 0x767f0031,
1831 + 0x767f002f, 0x767f002c, 0x767f002a, 0x757f0031,
1832 + 0x757f002f, 0x757f002c, 0x757f002a, 0x747f0030,
1833 + 0x747f002d, 0x747f002b, 0x737f0032, 0x737f002f,
1834 + 0x737f002c, 0x737f002a, 0x727f0030, 0x727f002d,
1835 + 0x727f002b, 0x727f0029, 0x717f0030, 0x717f002d,
1836 + 0x717f002b, 0x707f0031, 0x707f002f, 0x707f002c,
1837 + 0x707f002a, 0x707f0027, 0x707f0025, 0x707f0023,
1838 + 0x707f0021, 0x707f001f, 0x707f001d, 0x707f001c,
1839 + 0x707f001a, 0x707f0019, 0x707f0017, 0x707f0016,
1840 + 0x707f0015, 0x707f0014, 0x707f0012, 0x707f0012,
1841 + 0x707f0011, 0x707f0010, 0x707f000f, 0x707f000e,
1842 + 0x707f000d, 0x707f000d, 0x707f000c, 0x707f000b,
1843 + 0x707f000a, 0x707f000a, 0x707f0009, 0x707f0008,
1844 + 0x707f0008, 0x707f0008, 0x707f0008, 0x707f0007,
1845 + 0x707f0007, 0x707f0006, 0x707f0006, 0x707f0006,
1846 + 0x707f0005, 0x707f0005, 0x707f0005, 0x707f0004,
1847 + 0x707f0004, 0x707f0004, 0x707f0003, 0x707f0003,
1848 + 0x707f0003, 0x707f0003, 0x707f0003, 0x707f0003,
1849 + 0x707f0003, 0x707f0003, 0x707f0003, 0x707f0003,
1850 + 0x707f0002, 0x707f0002, 0x707f0002, 0x707f0002,
1851 + 0x707f0002, 0x707f0002, 0x707f0002, 0x707f0002,
1852 + 0x707f0002, 0x707f0001, 0x707f0001, 0x707f0001,
1853 + 0x707f0001, 0x707f0001, 0x707f0001, 0x707f0001,
1854 +};
1855 +
1856 const s8 b43_ntab_papd_pga_gain_delta_ipa_2g[] = {
1857 -114, -108, -98, -91, -84, -78, -70, -62,
1858 -54, -46, -39, -31, -23, -15, -8, 0
1859 @@ -3031,31 +3300,8 @@ void b43_ntab_write_bulk(struct b43_wlde
1860 b43_ntab_write_bulk(dev, offset, ARRAY_SIZE(data), data); \
1861 } while (0)
1862
1863 -static void b43_nphy_tables_init_rev3(struct b43_wldev *dev)
1864 +static void b43_nphy_tables_init_shared_lut(struct b43_wldev *dev)
1865 {
1866 - struct ssb_sprom *sprom = dev->dev->bus_sprom;
1867 - u8 antswlut;
1868 -
1869 - if (b43_current_band(dev->wl) == IEEE80211_BAND_5GHZ)
1870 - antswlut = sprom->fem.ghz5.antswlut;
1871 - else
1872 - antswlut = sprom->fem.ghz2.antswlut;
1873 -
1874 - /* Static tables */
1875 - ntab_upload(dev, B43_NTAB_FRAMESTRUCT_R3, b43_ntab_framestruct_r3);
1876 - ntab_upload(dev, B43_NTAB_PILOT_R3, b43_ntab_pilot_r3);
1877 - ntab_upload(dev, B43_NTAB_TMAP_R3, b43_ntab_tmap_r3);
1878 - ntab_upload(dev, B43_NTAB_INTLEVEL_R3, b43_ntab_intlevel_r3);
1879 - ntab_upload(dev, B43_NTAB_TDTRN_R3, b43_ntab_tdtrn_r3);
1880 - ntab_upload(dev, B43_NTAB_NOISEVAR_R3, b43_ntab_noisevar_r3);
1881 - ntab_upload(dev, B43_NTAB_MCS_R3, b43_ntab_mcs_r3);
1882 - ntab_upload(dev, B43_NTAB_TDI20A0_R3, b43_ntab_tdi20a0_r3);
1883 - ntab_upload(dev, B43_NTAB_TDI20A1_R3, b43_ntab_tdi20a1_r3);
1884 - ntab_upload(dev, B43_NTAB_TDI40A0_R3, b43_ntab_tdi40a0_r3);
1885 - ntab_upload(dev, B43_NTAB_TDI40A1_R3, b43_ntab_tdi40a1_r3);
1886 - ntab_upload(dev, B43_NTAB_PILOTLT_R3, b43_ntab_pilotlt_r3);
1887 - ntab_upload(dev, B43_NTAB_CHANEST_R3, b43_ntab_channelest_r3);
1888 - ntab_upload(dev, B43_NTAB_FRAMELT_R3, b43_ntab_framelookup_r3);
1889 ntab_upload(dev, B43_NTAB_C0_ESTPLT_R3, b43_ntab_estimatepowerlt0_r3);
1890 ntab_upload(dev, B43_NTAB_C1_ESTPLT_R3, b43_ntab_estimatepowerlt1_r3);
1891 ntab_upload(dev, B43_NTAB_C0_ADJPLT_R3, b43_ntab_adjustpower0_r3);
1892 @@ -3066,6 +3312,107 @@ static void b43_nphy_tables_init_rev3(st
1893 ntab_upload(dev, B43_NTAB_C1_IQLT_R3, b43_ntab_iqlt1_r3);
1894 ntab_upload(dev, B43_NTAB_C0_LOFEEDTH_R3, b43_ntab_loftlt0_r3);
1895 ntab_upload(dev, B43_NTAB_C1_LOFEEDTH_R3, b43_ntab_loftlt1_r3);
1896 +}
1897 +
1898 +static void b43_nphy_tables_init_rev7_volatile(struct b43_wldev *dev)
1899 +{
1900 + struct ssb_sprom *sprom = dev->dev->bus_sprom;
1901 + u8 antswlut;
1902 + int core, offset, i;
1903 +
1904 + const int antswlut0_offsets[] = { 0, 4, 8, }; /* Offsets for values */
1905 + const u8 antswlut0_values[][3] = {
1906 + { 0x2, 0x12, 0x8 }, /* Core 0 */
1907 + { 0x2, 0x18, 0x2 }, /* Core 1 */
1908 + };
1909 +
1910 + if (b43_current_band(dev->wl) == IEEE80211_BAND_5GHZ)
1911 + antswlut = sprom->fem.ghz5.antswlut;
1912 + else
1913 + antswlut = sprom->fem.ghz2.antswlut;
1914 +
1915 + switch (antswlut) {
1916 + case 0:
1917 + for (core = 0; core < 2; core++) {
1918 + for (i = 0; i < ARRAY_SIZE(antswlut0_values[0]); i++) {
1919 + offset = core ? 0x20 : 0x00;
1920 + offset += antswlut0_offsets[i];
1921 + b43_ntab_write(dev, B43_NTAB8(9, offset),
1922 + antswlut0_values[core][i]);
1923 + }
1924 + }
1925 + break;
1926 + default:
1927 + b43err(dev->wl, "Unsupported antswlut: %d\n", antswlut);
1928 + break;
1929 + }
1930 +}
1931 +
1932 +static void b43_nphy_tables_init_rev16(struct b43_wldev *dev)
1933 +{
1934 + /* Static tables */
1935 + if (dev->phy.do_full_init) {
1936 + ntab_upload(dev, B43_NTAB_NOISEVAR_R7, b43_ntab_noisevar_r7);
1937 + b43_nphy_tables_init_shared_lut(dev);
1938 + }
1939 +
1940 + /* Volatile tables */
1941 + b43_nphy_tables_init_rev7_volatile(dev);
1942 +}
1943 +
1944 +static void b43_nphy_tables_init_rev7(struct b43_wldev *dev)
1945 +{
1946 + /* Static tables */
1947 + if (dev->phy.do_full_init) {
1948 + ntab_upload(dev, B43_NTAB_FRAMESTRUCT_R3, b43_ntab_framestruct_r3);
1949 + ntab_upload(dev, B43_NTAB_PILOT_R3, b43_ntab_pilot_r3);
1950 + ntab_upload(dev, B43_NTAB_TMAP_R7, b43_ntab_tmap_r7);
1951 + ntab_upload(dev, B43_NTAB_INTLEVEL_R3, b43_ntab_intlevel_r3);
1952 + ntab_upload(dev, B43_NTAB_TDTRN_R3, b43_ntab_tdtrn_r3);
1953 + ntab_upload(dev, B43_NTAB_NOISEVAR_R7, b43_ntab_noisevar_r7);
1954 + ntab_upload(dev, B43_NTAB_MCS_R3, b43_ntab_mcs_r3);
1955 + ntab_upload(dev, B43_NTAB_TDI20A0_R3, b43_ntab_tdi20a0_r3);
1956 + ntab_upload(dev, B43_NTAB_TDI20A1_R3, b43_ntab_tdi20a1_r3);
1957 + ntab_upload(dev, B43_NTAB_TDI40A0_R3, b43_ntab_tdi40a0_r3);
1958 + ntab_upload(dev, B43_NTAB_TDI40A1_R3, b43_ntab_tdi40a1_r3);
1959 + ntab_upload(dev, B43_NTAB_PILOTLT_R3, b43_ntab_pilotlt_r3);
1960 + ntab_upload(dev, B43_NTAB_CHANEST_R3, b43_ntab_channelest_r3);
1961 + ntab_upload(dev, B43_NTAB_FRAMELT_R3, b43_ntab_framelookup_r3);
1962 + b43_nphy_tables_init_shared_lut(dev);
1963 + }
1964 +
1965 + /* Volatile tables */
1966 + b43_nphy_tables_init_rev7_volatile(dev);
1967 +}
1968 +
1969 +static void b43_nphy_tables_init_rev3(struct b43_wldev *dev)
1970 +{
1971 + struct ssb_sprom *sprom = dev->dev->bus_sprom;
1972 + u8 antswlut;
1973 +
1974 + if (b43_current_band(dev->wl) == IEEE80211_BAND_5GHZ)
1975 + antswlut = sprom->fem.ghz5.antswlut;
1976 + else
1977 + antswlut = sprom->fem.ghz2.antswlut;
1978 +
1979 + /* Static tables */
1980 + if (dev->phy.do_full_init) {
1981 + ntab_upload(dev, B43_NTAB_FRAMESTRUCT_R3, b43_ntab_framestruct_r3);
1982 + ntab_upload(dev, B43_NTAB_PILOT_R3, b43_ntab_pilot_r3);
1983 + ntab_upload(dev, B43_NTAB_TMAP_R3, b43_ntab_tmap_r3);
1984 + ntab_upload(dev, B43_NTAB_INTLEVEL_R3, b43_ntab_intlevel_r3);
1985 + ntab_upload(dev, B43_NTAB_TDTRN_R3, b43_ntab_tdtrn_r3);
1986 + ntab_upload(dev, B43_NTAB_NOISEVAR_R3, b43_ntab_noisevar_r3);
1987 + ntab_upload(dev, B43_NTAB_MCS_R3, b43_ntab_mcs_r3);
1988 + ntab_upload(dev, B43_NTAB_TDI20A0_R3, b43_ntab_tdi20a0_r3);
1989 + ntab_upload(dev, B43_NTAB_TDI20A1_R3, b43_ntab_tdi20a1_r3);
1990 + ntab_upload(dev, B43_NTAB_TDI40A0_R3, b43_ntab_tdi40a0_r3);
1991 + ntab_upload(dev, B43_NTAB_TDI40A1_R3, b43_ntab_tdi40a1_r3);
1992 + ntab_upload(dev, B43_NTAB_PILOTLT_R3, b43_ntab_pilotlt_r3);
1993 + ntab_upload(dev, B43_NTAB_CHANEST_R3, b43_ntab_channelest_r3);
1994 + ntab_upload(dev, B43_NTAB_FRAMELT_R3, b43_ntab_framelookup_r3);
1995 + b43_nphy_tables_init_shared_lut(dev);
1996 + }
1997
1998 /* Volatile tables */
1999 if (antswlut < ARRAY_SIZE(b43_ntab_antswctl_r3))
2000 @@ -3078,20 +3425,22 @@ static void b43_nphy_tables_init_rev3(st
2001 static void b43_nphy_tables_init_rev0(struct b43_wldev *dev)
2002 {
2003 /* Static tables */
2004 - ntab_upload(dev, B43_NTAB_FRAMESTRUCT, b43_ntab_framestruct);
2005 - ntab_upload(dev, B43_NTAB_FRAMELT, b43_ntab_framelookup);
2006 - ntab_upload(dev, B43_NTAB_TMAP, b43_ntab_tmap);
2007 - ntab_upload(dev, B43_NTAB_TDTRN, b43_ntab_tdtrn);
2008 - ntab_upload(dev, B43_NTAB_INTLEVEL, b43_ntab_intlevel);
2009 - ntab_upload(dev, B43_NTAB_PILOT, b43_ntab_pilot);
2010 - ntab_upload(dev, B43_NTAB_TDI20A0, b43_ntab_tdi20a0);
2011 - ntab_upload(dev, B43_NTAB_TDI20A1, b43_ntab_tdi20a1);
2012 - ntab_upload(dev, B43_NTAB_TDI40A0, b43_ntab_tdi40a0);
2013 - ntab_upload(dev, B43_NTAB_TDI40A1, b43_ntab_tdi40a1);
2014 - ntab_upload(dev, B43_NTAB_CHANEST, b43_ntab_channelest);
2015 - ntab_upload(dev, B43_NTAB_MCS, b43_ntab_mcs);
2016 - ntab_upload(dev, B43_NTAB_NOISEVAR10, b43_ntab_noisevar10);
2017 - ntab_upload(dev, B43_NTAB_NOISEVAR11, b43_ntab_noisevar11);
2018 + if (dev->phy.do_full_init) {
2019 + ntab_upload(dev, B43_NTAB_FRAMESTRUCT, b43_ntab_framestruct);
2020 + ntab_upload(dev, B43_NTAB_FRAMELT, b43_ntab_framelookup);
2021 + ntab_upload(dev, B43_NTAB_TMAP, b43_ntab_tmap);
2022 + ntab_upload(dev, B43_NTAB_TDTRN, b43_ntab_tdtrn);
2023 + ntab_upload(dev, B43_NTAB_INTLEVEL, b43_ntab_intlevel);
2024 + ntab_upload(dev, B43_NTAB_PILOT, b43_ntab_pilot);
2025 + ntab_upload(dev, B43_NTAB_TDI20A0, b43_ntab_tdi20a0);
2026 + ntab_upload(dev, B43_NTAB_TDI20A1, b43_ntab_tdi20a1);
2027 + ntab_upload(dev, B43_NTAB_TDI40A0, b43_ntab_tdi40a0);
2028 + ntab_upload(dev, B43_NTAB_TDI40A1, b43_ntab_tdi40a1);
2029 + ntab_upload(dev, B43_NTAB_CHANEST, b43_ntab_channelest);
2030 + ntab_upload(dev, B43_NTAB_MCS, b43_ntab_mcs);
2031 + ntab_upload(dev, B43_NTAB_NOISEVAR10, b43_ntab_noisevar10);
2032 + ntab_upload(dev, B43_NTAB_NOISEVAR11, b43_ntab_noisevar11);
2033 + }
2034
2035 /* Volatile tables */
2036 ntab_upload(dev, B43_NTAB_BDI, b43_ntab_bdi);
2037 @@ -3111,7 +3460,11 @@ static void b43_nphy_tables_init_rev0(st
2038 /* http://bcm-v4.sipsolutions.net/802.11/PHY/N/InitTables */
2039 void b43_nphy_tables_init(struct b43_wldev *dev)
2040 {
2041 - if (dev->phy.rev >= 3)
2042 + if (dev->phy.rev >= 16)
2043 + b43_nphy_tables_init_rev16(dev);
2044 + else if (dev->phy.rev >= 7)
2045 + b43_nphy_tables_init_rev7(dev);
2046 + else if (dev->phy.rev >= 3)
2047 b43_nphy_tables_init_rev3(dev);
2048 else
2049 b43_nphy_tables_init_rev0(dev);
2050 @@ -3120,23 +3473,45 @@ void b43_nphy_tables_init(struct b43_wld
2051 /* http://bcm-v4.sipsolutions.net/802.11/PHY/N/GetIpaGainTbl */
2052 static const u32 *b43_nphy_get_ipa_gain_table(struct b43_wldev *dev)
2053 {
2054 + struct b43_phy *phy = &dev->phy;
2055 +
2056 if (b43_current_band(dev->wl) == IEEE80211_BAND_2GHZ) {
2057 - if (dev->phy.rev >= 6) {
2058 - if (dev->dev->chip_id == 47162)
2059 - return txpwrctrl_tx_gain_ipa_rev5;
2060 - return txpwrctrl_tx_gain_ipa_rev6;
2061 - } else if (dev->phy.rev >= 5) {
2062 - return txpwrctrl_tx_gain_ipa_rev5;
2063 - } else {
2064 - return txpwrctrl_tx_gain_ipa;
2065 + switch (phy->rev) {
2066 + case 16:
2067 + if (phy->radio_rev == 9)
2068 + return b43_ntab_tx_gain_ipa_2057_rev9_2g;
2069 + case 6:
2070 + if (dev->dev->chip_id == BCMA_CHIP_ID_BCM47162)
2071 + return b43_ntab_tx_gain_ipa_rev5_2g;
2072 + return b43_ntab_tx_gain_ipa_rev6_2g;
2073 + case 5:
2074 + return b43_ntab_tx_gain_ipa_rev5_2g;
2075 + case 4:
2076 + case 3:
2077 + return b43_ntab_tx_gain_ipa_rev3_2g;
2078 + default:
2079 + b43err(dev->wl,
2080 + "No 2GHz IPA gain table available for this device\n");
2081 + return NULL;
2082 }
2083 } else {
2084 - return txpwrctrl_tx_gain_ipa_5g;
2085 + switch (phy->rev) {
2086 + case 16:
2087 + if (phy->radio_rev == 9)
2088 + return b43_ntab_tx_gain_ipa_2057_rev9_5g;
2089 + case 3 ... 6:
2090 + return b43_ntab_tx_gain_ipa_rev3_5g;
2091 + default:
2092 + b43err(dev->wl,
2093 + "No 5GHz IPA gain table available for this device\n");
2094 + return NULL;
2095 + }
2096 }
2097 }
2098
2099 const u32 *b43_nphy_get_tx_gain_table(struct b43_wldev *dev)
2100 {
2101 + struct b43_phy *phy = &dev->phy;
2102 enum ieee80211_band band = b43_current_band(dev->wl);
2103 struct ssb_sprom *sprom = dev->dev->bus_sprom;
2104
2105 @@ -3148,19 +3523,36 @@ const u32 *b43_nphy_get_tx_gain_table(st
2106 (dev->phy.n->ipa5g_on && band == IEEE80211_BAND_5GHZ)) {
2107 return b43_nphy_get_ipa_gain_table(dev);
2108 } else if (b43_current_band(dev->wl) == IEEE80211_BAND_5GHZ) {
2109 - if (dev->phy.rev == 3)
2110 - return b43_ntab_tx_gain_rev3_5ghz;
2111 - if (dev->phy.rev == 4)
2112 + switch (phy->rev) {
2113 + case 6:
2114 + case 5:
2115 + return b43_ntab_tx_gain_epa_rev5_5g;
2116 + case 4:
2117 return sprom->fem.ghz5.extpa_gain == 3 ?
2118 - b43_ntab_tx_gain_rev4_5ghz :
2119 - b43_ntab_tx_gain_rev4_5ghz; /* FIXME */
2120 - else
2121 - return b43_ntab_tx_gain_rev5plus_5ghz;
2122 + b43_ntab_tx_gain_epa_rev4_5g :
2123 + b43_ntab_tx_gain_epa_rev4_5g; /* FIXME */
2124 + case 3:
2125 + return b43_ntab_tx_gain_epa_rev3_5g;
2126 + default:
2127 + b43err(dev->wl,
2128 + "No 5GHz EPA gain table available for this device\n");
2129 + return NULL;
2130 + }
2131 } else {
2132 - if (dev->phy.rev >= 5 && sprom->fem.ghz5.extpa_gain == 3)
2133 - return b43_ntab_tx_gain_rev3plus_2ghz; /* FIXME */
2134 - else
2135 - return b43_ntab_tx_gain_rev3plus_2ghz;
2136 + switch (phy->rev) {
2137 + case 6:
2138 + case 5:
2139 + if (sprom->fem.ghz5.extpa_gain == 3)
2140 + return b43_ntab_tx_gain_epa_rev3_2g; /* FIXME */
2141 + /* fall through */
2142 + case 4:
2143 + case 3:
2144 + return b43_ntab_tx_gain_epa_rev3_2g;
2145 + default:
2146 + b43err(dev->wl,
2147 + "No 2GHz EPA gain table available for this device\n");
2148 + return NULL;
2149 + }
2150 }
2151 }
2152
2153 @@ -3187,7 +3579,7 @@ struct nphy_gain_ctl_workaround_entry *b
2154 /* Some workarounds to the workarounds... */
2155 if (ghz5 && dev->phy.rev >= 6) {
2156 if (dev->phy.radio_rev == 11 &&
2157 - !b43_channel_type_is_40mhz(dev->phy.channel_type))
2158 + !b43_is_40mhz(dev))
2159 e->cliplo_gain = 0x2d;
2160 } else if (!ghz5 && dev->phy.rev >= 5) {
2161 static const int gain_data[] = {0x0062, 0x0064, 0x006a, 0x106a,
2162 --- a/drivers/net/wireless/b43/Kconfig
2163 +++ b/drivers/net/wireless/b43/Kconfig
2164 @@ -37,7 +37,7 @@ config B43_SSB
2165 choice
2166 prompt "Supported bus types"
2167 depends on B43
2168 - default B43_BCMA_AND_SSB
2169 + default B43_BUSES_BCMA_AND_SSB
2170
2171 config B43_BUSES_BCMA_AND_SSB
2172 bool "BCMA and SSB"
2173 @@ -123,6 +123,15 @@ config B43_PIO
2174 select SSB_BLOCKIO
2175 default y
2176
2177 +config B43_PHY_G
2178 + bool "Support for G-PHY (802.11g) devices"
2179 + depends on B43 && B43_SSB
2180 + default y
2181 + ---help---
2182 + This PHY type can be found in the following chipsets:
2183 + PCI: BCM4306, BCM4311, BCM4318
2184 + SoC: BCM4712, BCM5352E
2185 +
2186 config B43_PHY_N
2187 bool "Support for 802.11n (N-PHY) devices"
2188 depends on B43
2189 --- a/drivers/net/wireless/b43/phy_ht.c
2190 +++ b/drivers/net/wireless/b43/phy_ht.c
2191 @@ -596,7 +596,7 @@ static void b43_phy_ht_tx_power_ctl_setu
2192 u8 target[3];
2193 s16 a1[3], b0[3], b1[3];
2194
2195 - u16 freq = dev->phy.channel_freq;
2196 + u16 freq = dev->phy.chandef->chan->center_freq;
2197 int i, c;
2198
2199 if (b43_current_band(dev->wl) == IEEE80211_BAND_2GHZ) {
2200 --- a/drivers/net/wireless/b43/phy_a.h
2201 +++ b/drivers/net/wireless/b43/phy_a.h
2202 @@ -123,8 +123,4 @@ struct b43_phy_a {
2203 */
2204 void b43_phy_inita(struct b43_wldev *dev);
2205
2206 -
2207 -struct b43_phy_operations;
2208 -extern const struct b43_phy_operations b43_phyops_a;
2209 -
2210 #endif /* LINUX_B43_PHY_A_H_ */
2211 --- a/drivers/net/wireless/b43/Makefile
2212 +++ b/drivers/net/wireless/b43/Makefile
2213 @@ -1,13 +1,11 @@
2214 b43-y += main.o
2215 b43-y += bus.o
2216 -b43-y += tables.o
2217 +b43-$(CPTCFG_B43_PHY_G) += phy_a.o phy_g.o tables.o lo.o wa.o
2218 b43-$(CPTCFG_B43_PHY_N) += tables_nphy.o
2219 b43-$(CPTCFG_B43_PHY_N) += radio_2055.o
2220 b43-$(CPTCFG_B43_PHY_N) += radio_2056.o
2221 b43-$(CPTCFG_B43_PHY_N) += radio_2057.o
2222 b43-y += phy_common.o
2223 -b43-y += phy_g.o
2224 -b43-y += phy_a.o
2225 b43-$(CPTCFG_B43_PHY_N) += phy_n.o
2226 b43-$(CPTCFG_B43_PHY_LP) += phy_lp.o
2227 b43-$(CPTCFG_B43_PHY_LP) += tables_lpphy.o
2228 @@ -17,8 +15,6 @@ b43-$(CPTCFG_B43_PHY_HT) += radio_2059.o
2229 b43-$(CPTCFG_B43_PHY_LCN) += phy_lcn.o tables_phy_lcn.o
2230 b43-y += sysfs.o
2231 b43-y += xmit.o
2232 -b43-y += lo.o
2233 -b43-y += wa.o
2234 b43-y += dma.o
2235 b43-y += pio.o
2236 b43-y += rfkill.o
2237 --- a/drivers/net/wireless/b43/phy_a.c
2238 +++ b/drivers/net/wireless/b43/phy_a.c
2239 @@ -573,7 +573,7 @@ static void b43_aphy_op_pwork_60sec(stru
2240 {//TODO
2241 }
2242
2243 -const struct b43_phy_operations b43_phyops_a = {
2244 +static const struct b43_phy_operations b43_phyops_a = {
2245 .allocate = b43_aphy_op_allocate,
2246 .free = b43_aphy_op_free,
2247 .prepare_structs = b43_aphy_op_prepare_structs,
2248 --- a/drivers/net/wireless/b43/radio_2057.c
2249 +++ b/drivers/net/wireless/b43/radio_2057.c
2250 @@ -26,7 +26,7 @@
2251 #include "radio_2057.h"
2252 #include "phy_common.h"
2253
2254 -static u16 r2057_rev4_init[42][2] = {
2255 +static u16 r2057_rev4_init[][2] = {
2256 { 0x0E, 0x20 }, { 0x31, 0x00 }, { 0x32, 0x00 }, { 0x33, 0x00 },
2257 { 0x35, 0x26 }, { 0x3C, 0xff }, { 0x3D, 0xff }, { 0x3E, 0xff },
2258 { 0x3F, 0xff }, { 0x62, 0x33 }, { 0x8A, 0xf0 }, { 0x8B, 0x10 },
2259 @@ -40,7 +40,7 @@ static u16 r2057_rev4_init[42][2] = {
2260 { 0x1AB, 0x00 }, { 0x1AC, 0x00 },
2261 };
2262
2263 -static u16 r2057_rev5_init[44][2] = {
2264 +static u16 r2057_rev5_init[][2] = {
2265 { 0x00, 0x00 }, { 0x01, 0x57 }, { 0x02, 0x20 }, { 0x23, 0x6 },
2266 { 0x31, 0x00 }, { 0x32, 0x00 }, { 0x33, 0x00 }, { 0x51, 0x70 },
2267 { 0x59, 0x88 }, { 0x5C, 0x20 }, { 0x62, 0x33 }, { 0x63, 0x0f },
2268 @@ -54,7 +54,7 @@ static u16 r2057_rev5_init[44][2] = {
2269 { 0x1AC, 0x00 }, { 0x1B7, 0x0c }, { 0x1C1, 0x01 }, { 0x1C2, 0x80 },
2270 };
2271
2272 -static u16 r2057_rev5a_init[45][2] = {
2273 +static u16 r2057_rev5a_init[][2] = {
2274 { 0x00, 0x15 }, { 0x01, 0x57 }, { 0x02, 0x20 }, { 0x23, 0x6 },
2275 { 0x31, 0x00 }, { 0x32, 0x00 }, { 0x33, 0x00 }, { 0x51, 0x70 },
2276 { 0x59, 0x88 }, { 0x5C, 0x20 }, { 0x62, 0x33 }, { 0x63, 0x0f },
2277 @@ -69,7 +69,7 @@ static u16 r2057_rev5a_init[45][2] = {
2278 { 0x1C2, 0x80 },
2279 };
2280
2281 -static u16 r2057_rev7_init[54][2] = {
2282 +static u16 r2057_rev7_init[][2] = {
2283 { 0x00, 0x00 }, { 0x01, 0x57 }, { 0x02, 0x20 }, { 0x31, 0x00 },
2284 { 0x32, 0x00 }, { 0x33, 0x00 }, { 0x51, 0x70 }, { 0x59, 0x88 },
2285 { 0x5C, 0x20 }, { 0x62, 0x33 }, { 0x63, 0x0f }, { 0x64, 0x13 },
2286 @@ -86,7 +86,8 @@ static u16 r2057_rev7_init[54][2] = {
2287 { 0x1B7, 0x05 }, { 0x1C2, 0xa0 },
2288 };
2289
2290 -static u16 r2057_rev8_init[54][2] = {
2291 +/* TODO: Which devices should use it?
2292 +static u16 r2057_rev8_init[][2] = {
2293 { 0x00, 0x08 }, { 0x01, 0x57 }, { 0x02, 0x20 }, { 0x31, 0x00 },
2294 { 0x32, 0x00 }, { 0x33, 0x00 }, { 0x51, 0x70 }, { 0x59, 0x88 },
2295 { 0x5C, 0x20 }, { 0x62, 0x33 }, { 0x63, 0x0f }, { 0x64, 0x0f },
2296 @@ -102,6 +103,47 @@ static u16 r2057_rev8_init[54][2] = {
2297 { 0x1A6, 0x00 }, { 0x1AA, 0x00 }, { 0x1AB, 0x00 }, { 0x1AC, 0x00 },
2298 { 0x1B7, 0x05 }, { 0x1C2, 0xa0 },
2299 };
2300 +*/
2301 +
2302 +#define RADIOREGS7(r00, r01, r02, r03, r04, r05, r06, r07, r08, r09, \
2303 + r10, r11, r12, r13, r14, r15, r16, r17, r18, r19, \
2304 + r20, r21, r22, r23, r24, r25, r26, r27) \
2305 + .radio_vcocal_countval0 = r00, \
2306 + .radio_vcocal_countval1 = r01, \
2307 + .radio_rfpll_refmaster_sparextalsize = r02, \
2308 + .radio_rfpll_loopfilter_r1 = r03, \
2309 + .radio_rfpll_loopfilter_c2 = r04, \
2310 + .radio_rfpll_loopfilter_c1 = r05, \
2311 + .radio_cp_kpd_idac = r06, \
2312 + .radio_rfpll_mmd0 = r07, \
2313 + .radio_rfpll_mmd1 = r08, \
2314 + .radio_vcobuf_tune = r09, \
2315 + .radio_logen_mx2g_tune = r10, \
2316 + .radio_logen_mx5g_tune = r11, \
2317 + .radio_logen_indbuf2g_tune = r12, \
2318 + .radio_logen_indbuf5g_tune = r13, \
2319 + .radio_txmix2g_tune_boost_pu_core0 = r14, \
2320 + .radio_pad2g_tune_pus_core0 = r15, \
2321 + .radio_pga_boost_tune_core0 = r16, \
2322 + .radio_txmix5g_boost_tune_core0 = r17, \
2323 + .radio_pad5g_tune_misc_pus_core0 = r18, \
2324 + .radio_lna2g_tune_core0 = r19, \
2325 + .radio_lna5g_tune_core0 = r20, \
2326 + .radio_txmix2g_tune_boost_pu_core1 = r21, \
2327 + .radio_pad2g_tune_pus_core1 = r22, \
2328 + .radio_pga_boost_tune_core1 = r23, \
2329 + .radio_txmix5g_boost_tune_core1 = r24, \
2330 + .radio_pad5g_tune_misc_pus_core1 = r25, \
2331 + .radio_lna2g_tune_core1 = r26, \
2332 + .radio_lna5g_tune_core1 = r27
2333 +
2334 +#define PHYREGS(r0, r1, r2, r3, r4, r5) \
2335 + .phy_regs.phy_bw1a = r0, \
2336 + .phy_regs.phy_bw2 = r1, \
2337 + .phy_regs.phy_bw3 = r2, \
2338 + .phy_regs.phy_bw4 = r3, \
2339 + .phy_regs.phy_bw5 = r4, \
2340 + .phy_regs.phy_bw6 = r5
2341
2342 void r2057_upload_inittabs(struct b43_wldev *dev)
2343 {
2344 @@ -109,33 +151,69 @@ void r2057_upload_inittabs(struct b43_wl
2345 u16 *table = NULL;
2346 u16 size, i;
2347
2348 - if (phy->rev == 7) {
2349 + switch (phy->rev) {
2350 + case 7:
2351 table = r2057_rev4_init[0];
2352 size = ARRAY_SIZE(r2057_rev4_init);
2353 - } else if (phy->rev == 8 || phy->rev == 9) {
2354 + break;
2355 + case 8:
2356 if (phy->radio_rev == 5) {
2357 - if (phy->radio_rev == 8) {
2358 - table = r2057_rev5_init[0];
2359 - size = ARRAY_SIZE(r2057_rev5_init);
2360 - } else {
2361 - table = r2057_rev5a_init[0];
2362 - size = ARRAY_SIZE(r2057_rev5a_init);
2363 - }
2364 + table = r2057_rev5_init[0];
2365 + size = ARRAY_SIZE(r2057_rev5_init);
2366 } else if (phy->radio_rev == 7) {
2367 table = r2057_rev7_init[0];
2368 size = ARRAY_SIZE(r2057_rev7_init);
2369 - } else if (phy->radio_rev == 9) {
2370 - table = r2057_rev8_init[0];
2371 - size = ARRAY_SIZE(r2057_rev8_init);
2372 }
2373 + break;
2374 + case 9:
2375 + if (phy->radio_rev == 5) {
2376 + table = r2057_rev5a_init[0];
2377 + size = ARRAY_SIZE(r2057_rev5a_init);
2378 + }
2379 + break;
2380 }
2381
2382 + B43_WARN_ON(!table);
2383 +
2384 if (table) {
2385 - for (i = 0; i < 10; i++) {
2386 - pr_info("radio_write 0x%X ", *table);
2387 - table++;
2388 - pr_info("0x%X\n", *table);
2389 - table++;
2390 + for (i = 0; i < size; i++, table += 2)
2391 + b43_radio_write(dev, table[0], table[1]);
2392 + }
2393 +}
2394 +
2395 +void r2057_get_chantabent_rev7(struct b43_wldev *dev, u16 freq,
2396 + const struct b43_nphy_chantabent_rev7 **tabent_r7,
2397 + const struct b43_nphy_chantabent_rev7_2g **tabent_r7_2g)
2398 +{
2399 + struct b43_phy *phy = &dev->phy;
2400 + const struct b43_nphy_chantabent_rev7 *e_r7 = NULL;
2401 + const struct b43_nphy_chantabent_rev7_2g *e_r7_2g = NULL;
2402 + unsigned int len, i;
2403 +
2404 + *tabent_r7 = NULL;
2405 + *tabent_r7_2g = NULL;
2406 +
2407 + /* TODO */
2408 + switch (phy->rev) {
2409 + default:
2410 + break;
2411 + }
2412 +
2413 + if (e_r7) {
2414 + for (i = 0; i < len; i++, e_r7++) {
2415 + if (e_r7->freq == freq) {
2416 + *tabent_r7 = e_r7;
2417 + return;
2418 + }
2419 + }
2420 + } else if (e_r7_2g) {
2421 + for (i = 0; i < len; i++, e_r7_2g++) {
2422 + if (e_r7_2g->freq == freq) {
2423 + *tabent_r7_2g = e_r7_2g;
2424 + return;
2425 + }
2426 }
2427 + } else {
2428 + B43_WARN_ON(1);
2429 }
2430 }
2431 --- a/drivers/net/wireless/b43/radio_2057.h
2432 +++ b/drivers/net/wireless/b43/radio_2057.h
2433 @@ -425,6 +425,72 @@
2434
2435 #define R2057_VCM_MASK 0x7
2436
2437 +struct b43_nphy_chantabent_rev7 {
2438 + /* The channel frequency in MHz */
2439 + u16 freq;
2440 + /* Radio regs values on channelswitch */
2441 + u8 radio_vcocal_countval0;
2442 + u8 radio_vcocal_countval1;
2443 + u8 radio_rfpll_refmaster_sparextalsize;
2444 + u8 radio_rfpll_loopfilter_r1;
2445 + u8 radio_rfpll_loopfilter_c2;
2446 + u8 radio_rfpll_loopfilter_c1;
2447 + u8 radio_cp_kpd_idac;
2448 + u8 radio_rfpll_mmd0;
2449 + u8 radio_rfpll_mmd1;
2450 + u8 radio_vcobuf_tune;
2451 + u8 radio_logen_mx2g_tune;
2452 + u8 radio_logen_mx5g_tune;
2453 + u8 radio_logen_indbuf2g_tune;
2454 + u8 radio_logen_indbuf5g_tune;
2455 + u8 radio_txmix2g_tune_boost_pu_core0;
2456 + u8 radio_pad2g_tune_pus_core0;
2457 + u8 radio_pga_boost_tune_core0;
2458 + u8 radio_txmix5g_boost_tune_core0;
2459 + u8 radio_pad5g_tune_misc_pus_core0;
2460 + u8 radio_lna2g_tune_core0;
2461 + u8 radio_lna5g_tune_core0;
2462 + u8 radio_txmix2g_tune_boost_pu_core1;
2463 + u8 radio_pad2g_tune_pus_core1;
2464 + u8 radio_pga_boost_tune_core1;
2465 + u8 radio_txmix5g_boost_tune_core1;
2466 + u8 radio_pad5g_tune_misc_pus_core1;
2467 + u8 radio_lna2g_tune_core1;
2468 + u8 radio_lna5g_tune_core1;
2469 + /* PHY res values on channelswitch */
2470 + struct b43_phy_n_sfo_cfg phy_regs;
2471 +};
2472 +
2473 +struct b43_nphy_chantabent_rev7_2g {
2474 + /* The channel frequency in MHz */
2475 + u16 freq;
2476 + /* Radio regs values on channelswitch */
2477 + u8 radio_vcocal_countval0;
2478 + u8 radio_vcocal_countval1;
2479 + u8 radio_rfpll_refmaster_sparextalsize;
2480 + u8 radio_rfpll_loopfilter_r1;
2481 + u8 radio_rfpll_loopfilter_c2;
2482 + u8 radio_rfpll_loopfilter_c1;
2483 + u8 radio_cp_kpd_idac;
2484 + u8 radio_rfpll_mmd0;
2485 + u8 radio_rfpll_mmd1;
2486 + u8 radio_vcobuf_tune;
2487 + u8 radio_logen_mx2g_tune;
2488 + u8 radio_logen_indbuf2g_tune;
2489 + u8 radio_txmix2g_tune_boost_pu_core0;
2490 + u8 radio_pad2g_tune_pus_core0;
2491 + u8 radio_lna2g_tune_core0;
2492 + u8 radio_txmix2g_tune_boost_pu_core1;
2493 + u8 radio_pad2g_tune_pus_core1;
2494 + u8 radio_lna2g_tune_core1;
2495 + /* PHY regs values on channelswitch */
2496 + struct b43_phy_n_sfo_cfg phy_regs;
2497 +};
2498 +
2499 void r2057_upload_inittabs(struct b43_wldev *dev);
2500
2501 +void r2057_get_chantabent_rev7(struct b43_wldev *dev, u16 freq,
2502 + const struct b43_nphy_chantabent_rev7 **tabent_r7,
2503 + const struct b43_nphy_chantabent_rev7_2g **tabent_r7_2g);
2504 +
2505 #endif /* B43_RADIO_2057_H_ */
2506 --- a/drivers/net/wireless/b43/tables_nphy.h
2507 +++ b/drivers/net/wireless/b43/tables_nphy.h
2508 @@ -165,6 +165,10 @@ struct nphy_gain_ctl_workaround_entry *b
2509 #define B43_NTAB_C1_LOFEEDTH_R3 B43_NTAB16(27, 448) /* Local Oscillator Feed Through lookup 1 */
2510 #define B43_NTAB_C1_PAPD_COMP_R3 B43_NTAB16(27, 576)
2511
2512 +/* Static N-PHY tables, PHY revision >= 7 */
2513 +#define B43_NTAB_TMAP_R7 B43_NTAB32(12, 0) /* TM AP */
2514 +#define B43_NTAB_NOISEVAR_R7 B43_NTAB32(16, 0) /* noise variance */
2515 +
2516 #define B43_NTAB_TX_IQLO_CAL_LOFT_LADDER_40_SIZE 18
2517 #define B43_NTAB_TX_IQLO_CAL_LOFT_LADDER_20_SIZE 18
2518 #define B43_NTAB_TX_IQLO_CAL_IQIMB_LADDER_40_SIZE 18