Beispiel #1
0
/* Calibrate the internal RC oscillator? */
static void b43_radio_2057_rccal(struct b43_wldev *dev)
{
	const u16 radio_values[3][2] = {
		{ 0x61, 0xE9 }, { 0x69, 0xD5 }, { 0x73, 0x99 },
	};
	int i;

	for (i = 0; i < 3; i++) {
		b43_radio_write(dev, R2059_RCCAL_MASTER, radio_values[i][0]);
		b43_radio_write(dev, R2059_RCCAL_X1, 0x6E);
		b43_radio_write(dev, R2059_RCCAL_TRC0, radio_values[i][1]);

		/* Start */
		b43_radio_write(dev, R2059_RCCAL_START_R1_Q1_P1, 0x55);

		/* Wait */
		if (!b43_radio_wait_value(dev, R2059_RCCAL_DONE_OSCCAP, 2, 2,
					  500, 5000000))
			b43err(dev->wl, "Radio 0x2059 rccal timeout\n");

		/* Stop */
		b43_radio_write(dev, R2059_RCCAL_START_R1_Q1_P1, 0x15);
	}

	b43_radio_mask(dev, R2059_RCCAL_MASTER, ~0x1);
}
Beispiel #2
0
/* wlc_lcnphy_rev0_baseband_init */
static void b43_phy_lcn_rev0_baseband_init(struct b43_wldev *dev)
{
	b43_radio_write(dev, 0x11c, 0);

	b43_phy_write(dev, 0x43b, 0);
	b43_phy_write(dev, 0x43c, 0);
	b43_phy_write(dev, 0x44c, 0);
	b43_phy_write(dev, 0x4e6, 0);
	b43_phy_write(dev, 0x4f9, 0);
	b43_phy_write(dev, 0x4b0, 0);
	b43_phy_write(dev, 0x938, 0);
	b43_phy_write(dev, 0x4b0, 0);
	b43_phy_write(dev, 0x44e, 0);

	b43_phy_set(dev, 0x567, 0x03);

	b43_phy_set(dev, 0x44a, 0x44);
	b43_phy_write(dev, 0x44a, 0x80);

	if (!(dev->dev->bus_sprom->boardflags_lo & B43_BFL_FEM))
		; /* TODO */
	b43_phy_maskset(dev, 0x634, ~0xff, 0xc);
	if (dev->dev->bus_sprom->boardflags_lo & B43_BFL_FEM) {
		b43_phy_maskset(dev, 0x634, ~0xff, 0xa);
		b43_phy_write(dev, 0x910, 0x1);
	}

	b43_phy_write(dev, 0x910, 0x1);

	b43_phy_maskset(dev, 0x448, ~0x300, 0x100);
	b43_phy_maskset(dev, 0x608, ~0xff, 0x17);
	b43_phy_maskset(dev, 0x604, ~0x7ff, 0x3ea);
}
Beispiel #3
0
static void b43_phy_ht_tssi_setup(struct b43_wldev *dev)
{
	static const u16 routing[] = { R2059_C1, R2059_C2, R2059_C3, };
	int core;

	/* 0x159 is probably TX_SSI_MUX or TSSIG (by comparing to N-PHY) */
	for (core = 0; core < 3; core++) {
		b43_radio_set(dev, 0x8bf, 0x1);
		b43_radio_write(dev, routing[core] | 0x0159, 0x0011);
	}
}
void r2057_upload_inittabs(struct b43_wldev *dev)
{
	struct b43_phy *phy = &dev->phy;
	u16 *table = NULL;
	u16 size, i;

	switch (phy->rev) {
	case 7:
		table = r2057_rev4_init[0];
		size = ARRAY_SIZE(r2057_rev4_init);
		break;
	case 8:
		if (phy->radio_rev == 5) {
			table = r2057_rev5_init[0];
			size = ARRAY_SIZE(r2057_rev5_init);
		} else if (phy->radio_rev == 7) {
			table = r2057_rev7_init[0];
			size = ARRAY_SIZE(r2057_rev7_init);
		}
		break;
	case 9:
		if (phy->radio_rev == 5) {
			table = r2057_rev5a_init[0];
			size = ARRAY_SIZE(r2057_rev5a_init);
		}
		break;
	case 16:
		if (phy->radio_rev == 9) {
			table = r2057_rev9_init[0];
			size = ARRAY_SIZE(r2057_rev9_init);
		}
		break;
	case 17:
		if (phy->radio_rev == 14) {
			table = r2057_rev14_init[0];
			size = ARRAY_SIZE(r2057_rev14_init);
		}
		break;
	}

	B43_WARN_ON(!table);

	if (table) {
		for (i = 0; i < size; i++, table += 2)
			b43_radio_write(dev, table[0], table[1]);
	}
}
Beispiel #5
0
void r2059_upload_inittabs(struct b43_wldev *dev)
{
	struct b43_phy *phy = &dev->phy;
	u16 *table = NULL;
	u16 size, i;

	switch (phy->rev) {
	case 1:
		table = r2059_phy_rev1_init[0];
		size = ARRAY_SIZE(r2059_phy_rev1_init);
		break;
	default:
		B43_WARN_ON(1);
		return;
	}

	for (i = 0; i < size; i++, table += 2)
		b43_radio_write(dev, R2059_ALL | table[0], table[1]);
}
Beispiel #6
0
static void b43_phy_ht_rssi_select(struct b43_wldev *dev, u8 core_sel,
				   u8 rssi_type)
{
	static const u16 ctl_regs[3][2] = {
		{ B43_PHY_HT_AFE_C1, B43_PHY_HT_AFE_C1_OVER, },
		{ B43_PHY_HT_AFE_C2, B43_PHY_HT_AFE_C2_OVER, },
		{ B43_PHY_HT_AFE_C3, B43_PHY_HT_AFE_C3_OVER, },
	};
	static const u16 radio_r[] = { R2059_SYN, R2059_TXRX0, R2059_RXRX1, };
	int core;

	if (core_sel == 0) {
		b43err(dev->wl, "RSSI selection for core off not implemented yet\n");
	} else {
		for (core = 0; core < 3; core++) {
			/* Check if caller requested a one specific core */
			if ((core_sel == 1 && core != 0) ||
			    (core_sel == 2 && core != 1) ||
			    (core_sel == 3 && core != 2))
				continue;

			switch (rssi_type) {
			case 4:
				b43_phy_set(dev, ctl_regs[core][0], 0x3 << 8);
				b43_phy_set(dev, ctl_regs[core][0], 0x3 << 10);
				b43_phy_set(dev, ctl_regs[core][1], 0x1 << 9);
				b43_phy_set(dev, ctl_regs[core][1], 0x1 << 10);

				b43_radio_set(dev, R2059_RXRX1 | 0xbf, 0x1);
				b43_radio_write(dev, radio_r[core] | 0x159,
						0x11);
				break;
			default:
				b43err(dev->wl, "RSSI selection for type %d not implemented yet\n",
				       rssi_type);
			}
		}
	}
}
static void b43_radio_2059_init(struct b43_wldev *dev)
{
	const u16 routing[] = { R2059_SYN, R2059_TXRX0, R2059_RXRX1 };
	const u16 radio_values[3][2] = {
		{ 0x61, 0xE9 }, { 0x69, 0xD5 }, { 0x73, 0x99 },
	};
	u16 i, j;

	b43_radio_write(dev, R2059_ALL | 0x51, 0x0070);
	b43_radio_write(dev, R2059_ALL | 0x5a, 0x0003);

	for (i = 0; i < ARRAY_SIZE(routing); i++)
		b43_radio_set(dev, routing[i] | 0x146, 0x3);

	b43_radio_set(dev, 0x2e, 0x0078);
	b43_radio_set(dev, 0xc0, 0x0080);
	msleep(2);
	b43_radio_mask(dev, 0x2e, ~0x0078);
	b43_radio_mask(dev, 0xc0, ~0x0080);

	if (1) { /* FIXME */
		b43_radio_set(dev, R2059_RXRX1 | 0x4, 0x1);
		udelay(10);
		b43_radio_set(dev, R2059_RXRX1 | 0x0BF, 0x1);
		b43_radio_maskset(dev, R2059_RXRX1 | 0x19B, 0x3, 0x2);

		b43_radio_set(dev, R2059_RXRX1 | 0x4, 0x2);
		udelay(100);
		b43_radio_mask(dev, R2059_RXRX1 | 0x4, ~0x2);

		for (i = 0; i < 10000; i++) {
			if (b43_radio_read(dev, R2059_RXRX1 | 0x145) & 1) {
				i = 0;
				break;
			}
			udelay(100);
		}
		if (i)
			b43err(dev->wl, "radio 0x945 timeout\n");

		b43_radio_mask(dev, R2059_RXRX1 | 0x4, ~0x1);
		b43_radio_set(dev, 0xa, 0x60);

		for (i = 0; i < 3; i++) {
			b43_radio_write(dev, 0x17F, radio_values[i][0]);
			b43_radio_write(dev, 0x13D, 0x6E);
			b43_radio_write(dev, 0x13E, radio_values[i][1]);
			b43_radio_write(dev, 0x13C, 0x55);

			for (j = 0; j < 10000; j++) {
				if (b43_radio_read(dev, 0x140) & 2) {
					j = 0;
					break;
				}
				udelay(500);
			}
			if (j)
				b43err(dev->wl, "radio 0x140 timeout\n");

			b43_radio_write(dev, 0x13C, 0x15);
		}

		b43_radio_mask(dev, 0x17F, ~0x1);
	}

	b43_radio_mask(dev, 0x11, ~0x0008);
}
static void b43_radio_2059_channel_setup(struct b43_wldev *dev,
			const struct b43_phy_ht_channeltab_e_radio2059 *e)
{
	u8 i;
	u16 routing;

	b43_radio_write(dev, 0x16, e->radio_syn16);
	b43_radio_write(dev, 0x17, e->radio_syn17);
	b43_radio_write(dev, 0x22, e->radio_syn22);
	b43_radio_write(dev, 0x25, e->radio_syn25);
	b43_radio_write(dev, 0x27, e->radio_syn27);
	b43_radio_write(dev, 0x28, e->radio_syn28);
	b43_radio_write(dev, 0x29, e->radio_syn29);
	b43_radio_write(dev, 0x2c, e->radio_syn2c);
	b43_radio_write(dev, 0x2d, e->radio_syn2d);
	b43_radio_write(dev, 0x37, e->radio_syn37);
	b43_radio_write(dev, 0x41, e->radio_syn41);
	b43_radio_write(dev, 0x43, e->radio_syn43);
	b43_radio_write(dev, 0x47, e->radio_syn47);
	b43_radio_write(dev, 0x4a, e->radio_syn4a);
	b43_radio_write(dev, 0x58, e->radio_syn58);
	b43_radio_write(dev, 0x5a, e->radio_syn5a);
	b43_radio_write(dev, 0x6a, e->radio_syn6a);
	b43_radio_write(dev, 0x6d, e->radio_syn6d);
	b43_radio_write(dev, 0x6e, e->radio_syn6e);
	b43_radio_write(dev, 0x92, e->radio_syn92);
	b43_radio_write(dev, 0x98, e->radio_syn98);

	for (i = 0; i < 2; i++) {
		routing = i ? R2059_RXRX1 : R2059_TXRX0;
		b43_radio_write(dev, routing | 0x4a, e->radio_rxtx4a);
		b43_radio_write(dev, routing | 0x58, e->radio_rxtx58);
		b43_radio_write(dev, routing | 0x5a, e->radio_rxtx5a);
		b43_radio_write(dev, routing | 0x6a, e->radio_rxtx6a);
		b43_radio_write(dev, routing | 0x6d, e->radio_rxtx6d);
		b43_radio_write(dev, routing | 0x6e, e->radio_rxtx6e);
		b43_radio_write(dev, routing | 0x92, e->radio_rxtx92);
		b43_radio_write(dev, routing | 0x98, e->radio_rxtx98);
	}

	udelay(50);

	/* Calibration */
	b43_radio_mask(dev, 0x2b, ~0x1);
	b43_radio_mask(dev, 0x2e, ~0x4);
	b43_radio_set(dev, 0x2e, 0x4);
	b43_radio_set(dev, 0x2b, 0x1);

	udelay(300);
}
Beispiel #9
0
/* wlc_lcnphy_radio_2064_channel_tune_4313 */
static void b43_radio_2064_channel_setup(struct b43_wldev *dev)
{
	u16 save[2];

	b43_radio_set(dev, 0x09d, 0x4);
	b43_radio_write(dev, 0x09e, 0xf);

	/* Channel specific values in theory, in practice always the same */
	b43_radio_write(dev, 0x02a, 0xb);
	b43_radio_maskset(dev, 0x030, ~0x3, 0xa);
	b43_radio_maskset(dev, 0x091, ~0x3, 0);
	b43_radio_maskset(dev, 0x038, ~0xf, 0x7);
	b43_radio_maskset(dev, 0x030, ~0xc, 0x8);
	b43_radio_maskset(dev, 0x05e, ~0xf, 0x8);
	b43_radio_maskset(dev, 0x05e, ~0xf0, 0x80);
	b43_radio_write(dev, 0x06c, 0x80);

	save[0] = b43_radio_read(dev, 0x044);
	save[1] = b43_radio_read(dev, 0x12b);

	b43_radio_set(dev, 0x044, 0x7);
	b43_radio_set(dev, 0x12b, 0xe);

	/* TODO */

	b43_radio_write(dev, 0x040, 0xfb);

	b43_radio_write(dev, 0x041, 0x9a);
	b43_radio_write(dev, 0x042, 0xa3);
	b43_radio_write(dev, 0x043, 0x0c);

	/* TODO */

	b43_radio_set(dev, 0x044, 0x0c);
	udelay(1);

	b43_radio_write(dev, 0x044, save[0]);
	b43_radio_write(dev, 0x12b, save[1]);

	if (dev->phy.rev == 1) {
		/* brcmsmac uses outdated 0x3 for 0x038 */
		b43_radio_write(dev, 0x038, 0x0);
		b43_radio_write(dev, 0x091, 0x7);
	}
}
Beispiel #10
0
/* wlc_lcnphy_vbat_temp_sense_setup */
static void b43_phy_lcn_sense_setup(struct b43_wldev *dev,
				    enum lcn_sense_type sense_type)
{
	u8 auxpga_vmidcourse, auxpga_vmidfine, auxpga_gain;
	u16 auxpga_vmid;
	u8 tx_pwr_idx;
	u8 i;

	u16 save_radio_regs[6][2] = {
		{ 0x007, 0 }, { 0x0ff, 0 }, { 0x11f, 0 }, { 0x005, 0 },
		{ 0x025, 0 }, { 0x112, 0 },
	};
	u16 save_phy_regs[14][2] = {
		{ 0x503, 0 }, { 0x4a4, 0 }, { 0x4d0, 0 }, { 0x4d9, 0 },
		{ 0x4da, 0 }, { 0x4a6, 0 }, { 0x938, 0 }, { 0x939, 0 },
		{ 0x4d8, 0 }, { 0x4d0, 0 }, { 0x4d7, 0 }, { 0x4a5, 0 },
		{ 0x40d, 0 }, { 0x4a2, 0 },
	};
	u16 save_radio_4a4;

	msleep(1);

	/* Save */
	for (i = 0; i < 6; i++)
		save_radio_regs[i][1] = b43_radio_read(dev,
						       save_radio_regs[i][0]);
	for (i = 0; i < 14; i++)
		save_phy_regs[i][1] = b43_phy_read(dev, save_phy_regs[i][0]);
	b43_mac_suspend(dev);
	save_radio_4a4 = b43_radio_read(dev, 0x4a4);
	/* wlc_lcnphy_set_tx_pwr_ctrl(pi, LCNPHY_TX_PWR_CTRL_OFF); */
	tx_pwr_idx = dev->phy.lcn->tx_pwr_curr_idx;

	/* Setup */
	/* TODO: wlc_lcnphy_set_tx_pwr_by_index(pi, 127); */
	b43_radio_set(dev, 0x007, 0x1);
	b43_radio_set(dev, 0x0ff, 0x10);
	b43_radio_set(dev, 0x11f, 0x4);

	b43_phy_mask(dev, 0x503, ~0x1);
	b43_phy_mask(dev, 0x503, ~0x4);
	b43_phy_mask(dev, 0x4a4, ~0x4000);
	b43_phy_mask(dev, 0x4a4, (u16) ~0x8000);
	b43_phy_mask(dev, 0x4d0, ~0x20);
	b43_phy_set(dev, 0x4a5, 0xff);
	b43_phy_maskset(dev, 0x4a5, ~0x7000, 0x5000);
	b43_phy_mask(dev, 0x4a5, ~0x700);
	b43_phy_maskset(dev, 0x40d, ~0xff, 64);
	b43_phy_maskset(dev, 0x40d, ~0x700, 0x600);
	b43_phy_maskset(dev, 0x4a2, ~0xff, 64);
	b43_phy_maskset(dev, 0x4a2, ~0x700, 0x600);
	b43_phy_maskset(dev, 0x4d9, ~0x70, 0x20);
	b43_phy_maskset(dev, 0x4d9, ~0x700, 0x300);
	b43_phy_maskset(dev, 0x4d9, ~0x7000, 0x1000);
	b43_phy_mask(dev, 0x4da, ~0x1000);
	b43_phy_set(dev, 0x4da, 0x2000);
	b43_phy_set(dev, 0x4a6, 0x8000);

	b43_radio_write(dev, 0x025, 0xc);
	b43_radio_set(dev, 0x005, 0x8);
	b43_phy_set(dev, 0x938, 0x4);
	b43_phy_set(dev, 0x939, 0x4);
	b43_phy_set(dev, 0x4a4, 0x1000);

	/* FIXME: don't hardcode */
	b43_lcntab_write(dev, B43_LCNTAB16(0x8, 0x6), 0x640);

	switch (sense_type) {
	case B43_SENSE_TEMP:
		b43_phy_set(dev, 0x4d7, 0x8);
		b43_phy_maskset(dev, 0x4d7, ~0x7000, 0x1000);
		auxpga_vmidcourse = 8;
		auxpga_vmidfine = 0x4;
		auxpga_gain = 2;
		b43_radio_set(dev, 0x082, 0x20);
		break;
	case B43_SENSE_VBAT:
		b43_phy_set(dev, 0x4d7, 0x8);
		b43_phy_maskset(dev, 0x4d7, ~0x7000, 0x3000);
		auxpga_vmidcourse = 7;
		auxpga_vmidfine = 0xa;
		auxpga_gain = 2;
		break;
	}
	auxpga_vmid = (0x200 | (auxpga_vmidcourse << 4) | auxpga_vmidfine);

	b43_phy_set(dev, 0x4d8, 0x1);
	b43_phy_maskset(dev, 0x4d8, ~(0x3ff << 2), auxpga_vmid << 2);
	b43_phy_set(dev, 0x4d8, 0x2);
	b43_phy_maskset(dev, 0x4d8, ~(0x7 << 12), auxpga_gain << 12);
	b43_phy_set(dev, 0x4d0, 0x20);
	b43_radio_write(dev, 0x112, 0x6);

	/* TODO: dummy transmission? */
	/* Wait if not done */
	if (!(b43_phy_read(dev, 0x476) & 0x8000))
		udelay(10);

	/* Restore */
	for (i = 0; i < 6; i++)
		b43_radio_write(dev, save_radio_regs[i][0],
				save_radio_regs[i][1]);
	for (i = 0; i < 14; i++)
		b43_phy_write(dev, save_phy_regs[i][0], save_phy_regs[i][1]);
	/* TODO: wlc_lcnphy_set_tx_pwr_by_index(tx_pwr_idx) */
	b43_radio_write(dev, 0x4a4, save_radio_4a4);

	b43_mac_enable(dev);

	msleep(1);
}
Beispiel #11
0
/* wlc_radio_2064_init */
static void b43_radio_2064_init(struct b43_wldev *dev)
{
	if (b43_current_band(dev->wl) == IEEE80211_BAND_2GHZ) {
		b43_radio_write(dev, 0x09c, 0x0020);
		b43_radio_write(dev, 0x105, 0x0008);
	} else {
		/* TODO */
	}
	b43_radio_write(dev, 0x032, 0x0062);
	b43_radio_write(dev, 0x033, 0x0019);
	b43_radio_write(dev, 0x090, 0x0010);
	b43_radio_write(dev, 0x010, 0x0000);
	if (dev->phy.rev == 1) {
		b43_radio_write(dev, 0x060, 0x007f);
		b43_radio_write(dev, 0x061, 0x0072);
		b43_radio_write(dev, 0x062, 0x007f);
	}
	b43_radio_write(dev, 0x01d, 0x0002);
	b43_radio_write(dev, 0x01e, 0x0006);

	b43_phy_write(dev, 0x4ea, 0x4688);
	b43_phy_maskset(dev, 0x4eb, ~0x7, 0x2);
	b43_phy_mask(dev, 0x4eb, ~0x01c0);
	b43_phy_maskset(dev, 0x46a, 0xff00, 0x19);

	b43_lcntab_write(dev, B43_LCNTAB16(0x00, 0x55), 0);

	b43_radio_mask(dev, 0x05b, (u16) ~0xff02);
	b43_radio_set(dev, 0x004, 0x40);
	b43_radio_set(dev, 0x120, 0x10);
	b43_radio_set(dev, 0x078, 0x80);
	b43_radio_set(dev, 0x129, 0x2);
	b43_radio_set(dev, 0x057, 0x1);
	b43_radio_set(dev, 0x05b, 0x2);

	/* TODO: wait for some bit to be set */
	b43_radio_read(dev, 0x05c);

	b43_radio_mask(dev, 0x05b, (u16) ~0xff02);
	b43_radio_mask(dev, 0x057, (u16) ~0xff01);

	b43_phy_write(dev, 0x933, 0x2d6b);
	b43_phy_write(dev, 0x934, 0x2d6b);
	b43_phy_write(dev, 0x935, 0x2d6b);
	b43_phy_write(dev, 0x936, 0x2d6b);
	b43_phy_write(dev, 0x937, 0x016b);

	b43_radio_mask(dev, 0x057, (u16) ~0xff02);
	b43_radio_write(dev, 0x0c2, 0x006f);
}
Beispiel #12
0
static void b43_radio_2059_channel_setup(struct b43_wldev *dev,
			const struct b43_phy_ht_channeltab_e_radio2059 *e)
{
	static const u16 routing[] = { R2059_C1, R2059_C2, R2059_C3, };
	u16 r;
	int core;

	b43_radio_write(dev, 0x16, e->radio_syn16);
	b43_radio_write(dev, 0x17, e->radio_syn17);
	b43_radio_write(dev, 0x22, e->radio_syn22);
	b43_radio_write(dev, 0x25, e->radio_syn25);
	b43_radio_write(dev, 0x27, e->radio_syn27);
	b43_radio_write(dev, 0x28, e->radio_syn28);
	b43_radio_write(dev, 0x29, e->radio_syn29);
	b43_radio_write(dev, 0x2c, e->radio_syn2c);
	b43_radio_write(dev, 0x2d, e->radio_syn2d);
	b43_radio_write(dev, 0x37, e->radio_syn37);
	b43_radio_write(dev, 0x41, e->radio_syn41);
	b43_radio_write(dev, 0x43, e->radio_syn43);
	b43_radio_write(dev, 0x47, e->radio_syn47);

	for (core = 0; core < 3; core++) {
		r = routing[core];
		b43_radio_write(dev, r | 0x4a, e->radio_rxtx4a);
		b43_radio_write(dev, r | 0x58, e->radio_rxtx58);
		b43_radio_write(dev, r | 0x5a, e->radio_rxtx5a);
		b43_radio_write(dev, r | 0x6a, e->radio_rxtx6a);
		b43_radio_write(dev, r | 0x6d, e->radio_rxtx6d);
		b43_radio_write(dev, r | 0x6e, e->radio_rxtx6e);
		b43_radio_write(dev, r | 0x92, e->radio_rxtx92);
		b43_radio_write(dev, r | 0x98, e->radio_rxtx98);
	}

	udelay(50);

	/* Calibration */
	b43_radio_mask(dev, R2059_RFPLL_MISC_EN, ~0x1);
	b43_radio_mask(dev, R2059_RFPLL_MISC_CAL_RESETN, ~0x4);
	b43_radio_set(dev, R2059_RFPLL_MISC_CAL_RESETN, 0x4);
	b43_radio_set(dev, R2059_RFPLL_MISC_EN, 0x1);

	udelay(300);
}