aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/net/wireless/b43/tables_lpphy.c
diff options
context:
space:
mode:
authorGábor Stefanik <netrolller.3d@gmail.com>2009-08-26 14:51:25 -0400
committerJohn W. Linville <linville@tuxdriver.com>2009-08-28 14:40:52 -0400
commit68ec53292c7f09056152efa9a6ee2591c794f08c (patch)
treed0b0441033a8a885c93f4b94ee4ee9eb044e0233 /drivers/net/wireless/b43/tables_lpphy.c
parentd8fa338ee01e7de029d2441a8c2b9c5fbfeac82f (diff)
b43: Fix and update LP-PHY code
-Fix a few nasty typos (b43_phy_* operations instead of b43_radio_*) in the channel tune routines. -Fix some typos & spec errors found by MMIO tracing. -Optimize b43_phy_write & b43_phy_mask/set/maskset to use only the minimal number of MMIO accesses. (Write is possible using a single 32-bit MMIO write, while set/mask/maskset can be done in 3 16-bit MMIOs). -Set the default channel back to 1, as the bug forcing us to use channel 7 is now fixed. With this, the device comes up, scans, associates, transmits, receives, monitors and injects on all channels - in other words, it's fully functional. Sensitivity and TX power are still sub-optimal, due to the lack of calibration (that's next on my list). Signed-off-by: Gábor Stefanik <netrolller.3d@gmail.com> Signed-off-by: John W. Linville <linville@tuxdriver.com>
Diffstat (limited to 'drivers/net/wireless/b43/tables_lpphy.c')
-rw-r--r--drivers/net/wireless/b43/tables_lpphy.c79
1 files changed, 45 insertions, 34 deletions
diff --git a/drivers/net/wireless/b43/tables_lpphy.c b/drivers/net/wireless/b43/tables_lpphy.c
index 60d472f285af..c784def19b19 100644
--- a/drivers/net/wireless/b43/tables_lpphy.c
+++ b/drivers/net/wireless/b43/tables_lpphy.c
@@ -624,30 +624,35 @@ u32 b43_lptab_read(struct b43_wldev *dev, u32 offset)
624void b43_lptab_read_bulk(struct b43_wldev *dev, u32 offset, 624void b43_lptab_read_bulk(struct b43_wldev *dev, u32 offset,
625 unsigned int nr_elements, void *_data) 625 unsigned int nr_elements, void *_data)
626{ 626{
627 u32 type, value; 627 u32 type;
628 u8 *data = _data; 628 u8 *data = _data;
629 unsigned int i; 629 unsigned int i;
630 630
631 type = offset & B43_LPTAB_TYPEMASK; 631 type = offset & B43_LPTAB_TYPEMASK;
632 offset &= ~B43_LPTAB_TYPEMASK;
633 B43_WARN_ON(offset > 0xFFFF);
634
635 b43_phy_write(dev, B43_LPPHY_TABLE_ADDR, offset);
636
632 for (i = 0; i < nr_elements; i++) { 637 for (i = 0; i < nr_elements; i++) {
633 value = b43_lptab_read(dev, offset);
634 switch (type) { 638 switch (type) {
635 case B43_LPTAB_8BIT: 639 case B43_LPTAB_8BIT:
636 *data = value; 640 *data = b43_phy_read(dev, B43_LPPHY_TABLEDATALO) & 0xFF;
637 data++; 641 data++;
638 break; 642 break;
639 case B43_LPTAB_16BIT: 643 case B43_LPTAB_16BIT:
640 *((u16 *)data) = value; 644 *((u16 *)data) = b43_phy_read(dev, B43_LPPHY_TABLEDATALO);
641 data += 2; 645 data += 2;
642 break; 646 break;
643 case B43_LPTAB_32BIT: 647 case B43_LPTAB_32BIT:
644 *((u32 *)data) = value; 648 *((u32 *)data) = b43_phy_read(dev, B43_LPPHY_TABLEDATAHI);
649 *((u32 *)data) <<= 16;
650 *((u32 *)data) |= b43_phy_read(dev, B43_LPPHY_TABLEDATALO);
645 data += 4; 651 data += 4;
646 break; 652 break;
647 default: 653 default:
648 B43_WARN_ON(1); 654 B43_WARN_ON(1);
649 } 655 }
650 offset++;
651 } 656 }
652} 657}
653 658
@@ -688,26 +693,34 @@ void b43_lptab_write_bulk(struct b43_wldev *dev, u32 offset,
688 unsigned int i; 693 unsigned int i;
689 694
690 type = offset & B43_LPTAB_TYPEMASK; 695 type = offset & B43_LPTAB_TYPEMASK;
696 offset &= ~B43_LPTAB_TYPEMASK;
697 B43_WARN_ON(offset > 0xFFFF);
698
699 b43_phy_write(dev, B43_LPPHY_TABLE_ADDR, offset);
700
691 for (i = 0; i < nr_elements; i++) { 701 for (i = 0; i < nr_elements; i++) {
692 switch (type) { 702 switch (type) {
693 case B43_LPTAB_8BIT: 703 case B43_LPTAB_8BIT:
694 value = *data; 704 value = *data;
695 data++; 705 data++;
706 B43_WARN_ON(value & ~0xFF);
707 b43_phy_write(dev, B43_LPPHY_TABLEDATALO, value);
696 break; 708 break;
697 case B43_LPTAB_16BIT: 709 case B43_LPTAB_16BIT:
698 value = *((u16 *)data); 710 value = *((u16 *)data);
699 data += 2; 711 data += 2;
712 B43_WARN_ON(value & ~0xFFFF);
713 b43_phy_write(dev, B43_LPPHY_TABLEDATALO, value);
700 break; 714 break;
701 case B43_LPTAB_32BIT: 715 case B43_LPTAB_32BIT:
702 value = *((u32 *)data); 716 value = *((u32 *)data);
703 data += 4; 717 data += 4;
718 b43_phy_write(dev, B43_LPPHY_TABLEDATAHI, value >> 16);
719 b43_phy_write(dev, B43_LPPHY_TABLEDATALO, value);
704 break; 720 break;
705 default: 721 default:
706 B43_WARN_ON(1); 722 B43_WARN_ON(1);
707 value = 0;
708 } 723 }
709 b43_lptab_write(dev, offset, value);
710 offset++;
711 } 724 }
712} 725}
713 726
@@ -777,7 +790,7 @@ static const u8 lpphy_pll_fraction_table[] = {
777 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 790 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80,
778}; 791};
779 792
780static const u16 lpphy_iq_local_table[] = { 793static const u16 lpphy_iqlo_cal_table[] = {
781 0x0200, 0x0300, 0x0400, 0x0600, 0x0800, 0x0b00, 0x1000, 0x1001, 0x1002, 794 0x0200, 0x0300, 0x0400, 0x0600, 0x0800, 0x0b00, 0x1000, 0x1001, 0x1002,
782 0x1003, 0x1004, 0x1005, 0x1006, 0x1007, 0x1707, 0x2007, 0x2d07, 0x4007, 795 0x1003, 0x1004, 0x1005, 0x1006, 0x1007, 0x1707, 0x2007, 0x2d07, 0x4007,
783 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 796 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000,
@@ -789,10 +802,17 @@ static const u16 lpphy_iq_local_table[] = {
789 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 802 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000,
790 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x4000, 0x0000, 0x0000, 803 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x4000, 0x0000, 0x0000,
791 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 804 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000,
792 0x0000, 0x0000, 805 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000,
793}; 806};
794 807
795static const u16 lpphy_ofdm_cck_gain_table[] = { 808static const u16 lpphy_rev0_ofdm_cck_gain_table[] = {
809 0x0001, 0x0001, 0x0001, 0x0001, 0x1001, 0x2001, 0x3001, 0x4001, 0x5001,
810 0x6001, 0x7001, 0x7011, 0x7021, 0x2035, 0x2045, 0x2055, 0x2065, 0x2075,
811 0x006d, 0x007d, 0x014d, 0x015d, 0x115d, 0x035d, 0x135d, 0x055d, 0x155d,
812 0x0d5d, 0x1d5d, 0x2d5d, 0x555d, 0x655d, 0x755d,
813};
814
815static const u16 lpphy_rev1_ofdm_cck_gain_table[] = {
796 0x5000, 0x6000, 0x7000, 0x0001, 0x1001, 0x2001, 0x3001, 0x4001, 0x5001, 816 0x5000, 0x6000, 0x7000, 0x0001, 0x1001, 0x2001, 0x3001, 0x4001, 0x5001,
797 0x6001, 0x7001, 0x7011, 0x7021, 0x2035, 0x2045, 0x2055, 0x2065, 0x2075, 817 0x6001, 0x7001, 0x7011, 0x7021, 0x2035, 0x2045, 0x2055, 0x2065, 0x2075,
798 0x006d, 0x007d, 0x014d, 0x015d, 0x115d, 0x035d, 0x135d, 0x055d, 0x155d, 818 0x006d, 0x007d, 0x014d, 0x015d, 0x115d, 0x035d, 0x135d, 0x055d, 0x155d,
@@ -2263,11 +2283,18 @@ void lpphy_rev0_1_table_init(struct b43_wldev *dev)
2263 b43_lptab_write_bulk(dev, B43_LPTAB8(6, 0), 2283 b43_lptab_write_bulk(dev, B43_LPTAB8(6, 0),
2264 ARRAY_SIZE(lpphy_pll_fraction_table), lpphy_pll_fraction_table); 2284 ARRAY_SIZE(lpphy_pll_fraction_table), lpphy_pll_fraction_table);
2265 b43_lptab_write_bulk(dev, B43_LPTAB16(0, 0), 2285 b43_lptab_write_bulk(dev, B43_LPTAB16(0, 0),
2266 ARRAY_SIZE(lpphy_iq_local_table), lpphy_iq_local_table); 2286 ARRAY_SIZE(lpphy_iqlo_cal_table), lpphy_iqlo_cal_table);
2267 b43_lptab_write_bulk(dev, B43_LPTAB16(13, 0), 2287 if (dev->phy.rev == 0) {
2268 ARRAY_SIZE(lpphy_ofdm_cck_gain_table), lpphy_ofdm_cck_gain_table); 2288 b43_lptab_write_bulk(dev, B43_LPTAB16(13, 0),
2269 b43_lptab_write_bulk(dev, B43_LPTAB16(12, 0), 2289 ARRAY_SIZE(lpphy_rev0_ofdm_cck_gain_table), lpphy_rev0_ofdm_cck_gain_table);
2270 ARRAY_SIZE(lpphy_ofdm_cck_gain_table), lpphy_ofdm_cck_gain_table); 2290 b43_lptab_write_bulk(dev, B43_LPTAB16(12, 0),
2291 ARRAY_SIZE(lpphy_rev0_ofdm_cck_gain_table), lpphy_rev0_ofdm_cck_gain_table);
2292 } else {
2293 b43_lptab_write_bulk(dev, B43_LPTAB16(13, 0),
2294 ARRAY_SIZE(lpphy_rev1_ofdm_cck_gain_table), lpphy_rev1_ofdm_cck_gain_table);
2295 b43_lptab_write_bulk(dev, B43_LPTAB16(12, 0),
2296 ARRAY_SIZE(lpphy_rev1_ofdm_cck_gain_table), lpphy_rev1_ofdm_cck_gain_table);
2297}
2271 b43_lptab_write_bulk(dev, B43_LPTAB16(15, 0), 2298 b43_lptab_write_bulk(dev, B43_LPTAB16(15, 0),
2272 ARRAY_SIZE(lpphy_gain_delta_table), lpphy_gain_delta_table); 2299 ARRAY_SIZE(lpphy_gain_delta_table), lpphy_gain_delta_table);
2273 b43_lptab_write_bulk(dev, B43_LPTAB32(10, 0), 2300 b43_lptab_write_bulk(dev, B43_LPTAB32(10, 0),
@@ -2281,22 +2308,6 @@ void lpphy_rev2plus_table_init(struct b43_wldev *dev)
2281 2308
2282 B43_WARN_ON(dev->phy.rev < 2); 2309 B43_WARN_ON(dev->phy.rev < 2);
2283 2310
2284 /*
2285 * FIXME This code follows the specs, but it looks wrong:
2286 * In each pass, it writes 4 bytes to an offset in table ID 7,
2287 * then increments the offset by 1 for the next pass. This results
2288 * in the first 3 bytes of each pass except the first one getting
2289 * written to a location that has already been zeroed in the previous
2290 * pass.
2291 * This is what the vendor driver does, but it still looks suspicious.
2292 *
2293 * This should probably suffice:
2294 *
2295 * for (i = 0; i < 704; i+=4)
2296 * b43_lptab_write(dev, B43_LPTAB32(7, i), 0)
2297 *
2298 * This should be tested once the code is functional.
2299 */
2300 for (i = 0; i < 704; i++) 2311 for (i = 0; i < 704; i++)
2301 b43_lptab_write(dev, B43_LPTAB32(7, i), 0); 2312 b43_lptab_write(dev, B43_LPTAB32(7, i), 0);
2302 2313
@@ -2323,7 +2334,7 @@ void lpphy_rev2plus_table_init(struct b43_wldev *dev)
2323 b43_lptab_write_bulk(dev, B43_LPTAB8(6, 0), 2334 b43_lptab_write_bulk(dev, B43_LPTAB8(6, 0),
2324 ARRAY_SIZE(lpphy_pll_fraction_table), lpphy_pll_fraction_table); 2335 ARRAY_SIZE(lpphy_pll_fraction_table), lpphy_pll_fraction_table);
2325 b43_lptab_write_bulk(dev, B43_LPTAB16(0, 0), 2336 b43_lptab_write_bulk(dev, B43_LPTAB16(0, 0),
2326 ARRAY_SIZE(lpphy_iq_local_table), lpphy_iq_local_table); 2337 ARRAY_SIZE(lpphy_iqlo_cal_table), lpphy_iqlo_cal_table);
2327 b43_lptab_write_bulk(dev, B43_LPTAB32(9, 0), 2338 b43_lptab_write_bulk(dev, B43_LPTAB32(9, 0),
2328 ARRAY_SIZE(lpphy_papd_eps_table), lpphy_papd_eps_table); 2339 ARRAY_SIZE(lpphy_papd_eps_table), lpphy_papd_eps_table);
2329 b43_lptab_write_bulk(dev, B43_LPTAB32(10, 0), 2340 b43_lptab_write_bulk(dev, B43_LPTAB32(10, 0),