aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/staging/vt6655/channel.c
blob: 4122875ebcaaab15fbbcfa61b1cbf50e243d8e01 (plain) (blame)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
// SPDX-License-Identifier: GPL-2.0+
/*
 * Copyright (c) 1996, 2003 VIA Networking Technologies, Inc.
 * All rights reserved.
 *
 */

#include "baseband.h"
#include "channel.h"
#include "device.h"
#include "rf.h"

static struct ieee80211_rate vnt_rates_bg[] = {
	{ .bitrate = 10,  .hw_value = RATE_1M },
	{ .bitrate = 20,  .hw_value = RATE_2M },
	{ .bitrate = 55,  .hw_value = RATE_5M },
	{ .bitrate = 110, .hw_value = RATE_11M },
	{ .bitrate = 60,  .hw_value = RATE_6M },
	{ .bitrate = 90,  .hw_value = RATE_9M },
	{ .bitrate = 120, .hw_value = RATE_12M },
	{ .bitrate = 180, .hw_value = RATE_18M },
	{ .bitrate = 240, .hw_value = RATE_24M },
	{ .bitrate = 360, .hw_value = RATE_36M },
	{ .bitrate = 480, .hw_value = RATE_48M },
	{ .bitrate = 540, .hw_value = RATE_54M },
};

static struct ieee80211_channel vnt_channels_2ghz[] = {
	{ .center_freq = 2412, .hw_value = 1 },
	{ .center_freq = 2417, .hw_value = 2 },
	{ .center_freq = 2422, .hw_value = 3 },
	{ .center_freq = 2427, .hw_value = 4 },
	{ .center_freq = 2432, .hw_value = 5 },
	{ .center_freq = 2437, .hw_value = 6 },
	{ .center_freq = 2442, .hw_value = 7 },
	{ .center_freq = 2447, .hw_value = 8 },
	{ .center_freq = 2452, .hw_value = 9 },
	{ .center_freq = 2457, .hw_value = 10 },
	{ .center_freq = 2462, .hw_value = 11 },
	{ .center_freq = 2467, .hw_value = 12 },
	{ .center_freq = 2472, .hw_value = 13 },
	{ .center_freq = 2484, .hw_value = 14 }
};

static struct ieee80211_supported_band vnt_supported_2ghz_band = {
	.channels = vnt_channels_2ghz,
	.n_channels = ARRAY_SIZE(vnt_channels_2ghz),
	.bitrates = vnt_rates_bg,
	.n_bitrates = ARRAY_SIZE(vnt_rates_bg),
};

static void vnt_init_band(struct vnt_private *priv,
			  struct ieee80211_supported_band *supported_band,
			  enum nl80211_band band)
{
	int i;

	for (i = 0; i < supported_band->n_channels; i++) {
		supported_band->channels[i].max_power = 0x3f;
		supported_band->channels[i].flags =
			IEEE80211_CHAN_NO_HT40;
	}

	priv->hw->wiphy->bands[band] = supported_band;
}

void vnt_init_bands(struct vnt_private *priv)
{
	vnt_init_band(priv, &vnt_supported_2ghz_band, NL80211_BAND_2GHZ);
}

/**
 * set_channel() - Set NIC media channel
 *
 * @priv: The adapter to be set
 * @ch: Channel to be set
 *
 * Return Value: true if succeeded; false if failed.
 *
 */
bool set_channel(struct vnt_private *priv, struct ieee80211_channel *ch)
{
	bool ret = true;

	if (priv->byCurrentCh == ch->hw_value)
		return ret;

	/* Set VGA to max sensitivity */
	if (priv->bUpdateBBVGA &&
	    priv->byBBVGACurrent != priv->abyBBVGA[0]) {
		priv->byBBVGACurrent = priv->abyBBVGA[0];

		bb_set_vga_gain_offset(priv, priv->byBBVGACurrent);
	}

	/* clear NAV */
	vt6655_mac_reg_bits_on(priv->port_offset, MAC_REG_MACCR, MACCR_CLRNAV);

	/* TX_PE will reserve 3 us for MAX2829 A mode only,
	 * it is for better TX throughput
	 */

	priv->byCurrentCh = ch->hw_value;
	ret &= RFbSelectChannel(priv, priv->byRFType,
				ch->hw_value);

	/* Init Synthesizer Table */
	if (priv->bEnablePSMode)
		rf_write_wake_prog_syn(priv, priv->byRFType, ch->hw_value);

	bb_software_reset(priv);

	if (priv->local_id > REV_ID_VT3253_B1) {
		unsigned long flags;

		spin_lock_irqsave(&priv->lock, flags);

		/* set HW default power register */
		VT6655_MAC_SELECT_PAGE1(priv->port_offset);
		RFbSetPower(priv, RATE_1M, priv->byCurrentCh);
		iowrite8(priv->byCurPwr, priv->port_offset + MAC_REG_PWRCCK);
		RFbSetPower(priv, RATE_6M, priv->byCurrentCh);
		iowrite8(priv->byCurPwr, priv->port_offset + MAC_REG_PWROFDM);
		VT6655_MAC_SELECT_PAGE0(priv->port_offset);

		spin_unlock_irqrestore(&priv->lock, flags);
	}

	if (priv->byBBType == BB_TYPE_11B)
		RFbSetPower(priv, RATE_1M, priv->byCurrentCh);
	else
		RFbSetPower(priv, RATE_6M, priv->byCurrentCh);

	return ret;
}