1 // SPDX-License-Identifier: GPL-2.0-only
3 * (c) Copyright 2002-2010, Ralink Technology, Inc.
4 * Copyright (C) 2014 Felix Fietkau <nbd@openwrt.org>
5 * Copyright (C) 2015 Jakub Kicinski <kubakici@wp.pl>
6 * Copyright (C) 2018 Stanislaw Gruszka <stf_xl@wp.pl>
13 #include "../mt76x02_phy.h"
15 static void mt76x0_vht_cap_mask(struct ieee80211_supported_band
*sband
)
17 struct ieee80211_sta_vht_cap
*vht_cap
= &sband
->vht_cap
;
21 vht_cap
->cap
&= ~IEEE80211_VHT_CAP_RXLDPC
;
22 for (i
= 0; i
< 8; i
++) {
24 mcs_map
|= (IEEE80211_VHT_MCS_SUPPORT_0_7
<< (i
* 2));
27 (IEEE80211_VHT_MCS_NOT_SUPPORTED
<< (i
* 2));
29 vht_cap
->vht_mcs
.rx_mcs_map
= cpu_to_le16(mcs_map
);
30 vht_cap
->vht_mcs
.tx_mcs_map
= cpu_to_le16(mcs_map
);
34 mt76x0_set_wlan_state(struct mt76x02_dev
*dev
, u32 val
, bool enable
)
36 u32 mask
= MT_CMB_CTRL_XTAL_RDY
| MT_CMB_CTRL_PLL_LD
;
38 /* Note: we don't turn off WLAN_CLK because that makes the device
39 * not respond properly on the probe path.
40 * In case anyone (PSM?) wants to use this function we can
41 * bring the clock stuff back and fixup the probe path.
45 val
|= (MT_WLAN_FUN_CTRL_WLAN_EN
|
46 MT_WLAN_FUN_CTRL_WLAN_CLK_EN
);
48 val
&= ~(MT_WLAN_FUN_CTRL_WLAN_EN
);
50 mt76_wr(dev
, MT_WLAN_FUN_CTRL
, val
);
53 /* Note: vendor driver tries to disable/enable wlan here and retry
54 * but the code which does it is so buggy it must have never
55 * triggered, so don't bother.
57 if (enable
&& !mt76_poll(dev
, MT_CMB_CTRL
, mask
, mask
, 2000))
58 dev_err(dev
->mt76
.dev
, "PLL and XTAL check failed\n");
61 void mt76x0_chip_onoff(struct mt76x02_dev
*dev
, bool enable
, bool reset
)
65 val
= mt76_rr(dev
, MT_WLAN_FUN_CTRL
);
68 val
|= MT_WLAN_FUN_CTRL_GPIO_OUT_EN
;
69 val
&= ~MT_WLAN_FUN_CTRL_FRC_WL_ANT_SEL
;
71 if (val
& MT_WLAN_FUN_CTRL_WLAN_EN
) {
72 val
|= (MT_WLAN_FUN_CTRL_WLAN_RESET
|
73 MT_WLAN_FUN_CTRL_WLAN_RESET_RF
);
74 mt76_wr(dev
, MT_WLAN_FUN_CTRL
, val
);
77 val
&= ~(MT_WLAN_FUN_CTRL_WLAN_RESET
|
78 MT_WLAN_FUN_CTRL_WLAN_RESET_RF
);
82 mt76_wr(dev
, MT_WLAN_FUN_CTRL
, val
);
85 mt76x0_set_wlan_state(dev
, val
, enable
);
87 EXPORT_SYMBOL_GPL(mt76x0_chip_onoff
);
89 static void mt76x0_reset_csr_bbp(struct mt76x02_dev
*dev
)
91 mt76_wr(dev
, MT_MAC_SYS_CTRL
,
92 MT_MAC_SYS_CTRL_RESET_CSR
|
93 MT_MAC_SYS_CTRL_RESET_BBP
);
95 mt76_clear(dev
, MT_MAC_SYS_CTRL
,
96 MT_MAC_SYS_CTRL_RESET_CSR
|
97 MT_MAC_SYS_CTRL_RESET_BBP
);
100 #define RANDOM_WRITE(dev, tab) \
101 mt76_wr_rp(dev, MT_MCU_MEMMAP_WLAN, \
102 tab, ARRAY_SIZE(tab))
104 static int mt76x0_init_bbp(struct mt76x02_dev
*dev
)
108 ret
= mt76x0_phy_wait_bbp_ready(dev
);
112 RANDOM_WRITE(dev
, mt76x0_bbp_init_tab
);
114 for (i
= 0; i
< ARRAY_SIZE(mt76x0_bbp_switch_tab
); i
++) {
115 const struct mt76x0_bbp_switch_item
*item
= &mt76x0_bbp_switch_tab
[i
];
116 const struct mt76_reg_pair
*pair
= &item
->reg_pair
;
118 if (((RF_G_BAND
| RF_BW_20
) & item
->bw_band
) == (RF_G_BAND
| RF_BW_20
))
119 mt76_wr(dev
, pair
->reg
, pair
->value
);
122 RANDOM_WRITE(dev
, mt76x0_dcoc_tab
);
127 static void mt76x0_init_mac_registers(struct mt76x02_dev
*dev
)
129 RANDOM_WRITE(dev
, common_mac_reg_table
);
131 /* Enable PBF and MAC clock SYS_CTRL[11:10] = 0x3 */
132 RANDOM_WRITE(dev
, mt76x0_mac_reg_table
);
134 /* Release BBP and MAC reset MAC_SYS_CTRL[1:0] = 0x0 */
135 mt76_clear(dev
, MT_MAC_SYS_CTRL
, 0x3);
137 /* Set 0x141C[15:12]=0xF */
138 mt76_set(dev
, MT_EXT_CCA_CFG
, 0xf000);
140 mt76_clear(dev
, MT_FCE_L2_STUFF
, MT_FCE_L2_STUFF_WR_MPDU_LEN_EN
);
143 * tx_ring 9 is for mgmt frame
144 * tx_ring 8 is for in-band command frame.
145 * WMM_RG0_TXQMA: this register setting is for FCE to
146 * define the rule of tx_ring 9
147 * WMM_RG1_TXQMA: this register setting is for FCE to
148 * define the rule of tx_ring 8
150 mt76_rmw(dev
, MT_WMM_CTRL
, 0x3ff, 0x201);
153 void mt76x0_mac_stop(struct mt76x02_dev
*dev
)
157 mt76_clear(dev
, MT_TXOP_CTRL_CFG
, MT_TXOP_ED_CCA_EN
);
159 /* Page count on TxQ */
160 while (i
-- && ((mt76_rr(dev
, 0x0438) & 0xffffffff) ||
161 (mt76_rr(dev
, 0x0a30) & 0x000000ff) ||
162 (mt76_rr(dev
, 0x0a34) & 0x00ff00ff)))
165 if (!mt76_poll(dev
, MT_MAC_STATUS
, MT_MAC_STATUS_TX
, 0, 1000))
166 dev_warn(dev
->mt76
.dev
, "Warning: MAC TX did not stop!\n");
168 mt76_clear(dev
, MT_MAC_SYS_CTRL
, MT_MAC_SYS_CTRL_ENABLE_RX
|
169 MT_MAC_SYS_CTRL_ENABLE_TX
);
171 /* Page count on RxQ */
172 for (i
= 0; i
< 200; i
++) {
173 if (!(mt76_rr(dev
, MT_RXQ_STA
) & 0x00ff0000) &&
174 !mt76_rr(dev
, 0x0a30) &&
175 !mt76_rr(dev
, 0x0a34)) {
183 if (!mt76_poll(dev
, MT_MAC_STATUS
, MT_MAC_STATUS_RX
, 0, 1000))
184 dev_warn(dev
->mt76
.dev
, "Warning: MAC RX did not stop!\n");
186 EXPORT_SYMBOL_GPL(mt76x0_mac_stop
);
188 int mt76x0_init_hardware(struct mt76x02_dev
*dev
)
192 if (!mt76x02_wait_for_wpdma(&dev
->mt76
, 1000))
195 /* Wait for ASIC ready after FW load. */
196 if (!mt76x02_wait_for_mac(&dev
->mt76
))
199 mt76x0_reset_csr_bbp(dev
);
200 ret
= mt76x02_mcu_function_select(dev
, Q_SELECT
, 1);
204 mt76x0_init_mac_registers(dev
);
206 if (!mt76x02_wait_for_txrx_idle(&dev
->mt76
))
209 ret
= mt76x0_init_bbp(dev
);
213 dev
->mt76
.rxfilter
= mt76_rr(dev
, MT_RX_FILTR_CFG
);
215 for (i
= 0; i
< 16; i
++)
216 for (k
= 0; k
< 4; k
++)
217 mt76x02_mac_shared_key_setup(dev
, i
, k
, NULL
);
219 for (i
= 0; i
< 256; i
++)
220 mt76x02_mac_wcid_setup(dev
, i
, 0, NULL
);
222 ret
= mt76x0_eeprom_init(dev
);
226 mt76x0_phy_init(dev
);
230 EXPORT_SYMBOL_GPL(mt76x0_init_hardware
);
233 mt76x0_init_txpower(struct mt76x02_dev
*dev
,
234 struct ieee80211_supported_band
*sband
)
236 struct ieee80211_channel
*chan
;
237 struct mt76_rate_power t
;
241 for (i
= 0; i
< sband
->n_channels
; i
++) {
242 chan
= &sband
->channels
[i
];
244 mt76x0_get_tx_power_per_rate(dev
, chan
, &t
);
245 mt76x0_get_power_info(dev
, chan
, &tp
);
247 chan
->orig_mpwr
= (mt76x02_get_max_rate_power(&t
) + tp
) / 2;
248 chan
->max_power
= min_t(int, chan
->max_reg_power
,
253 int mt76x0_register_device(struct mt76x02_dev
*dev
)
257 mt76x02_init_device(dev
);
258 mt76x02_config_mac_addr_list(dev
);
260 ret
= mt76_register_device(&dev
->mt76
, true, mt76x02_rates
,
261 ARRAY_SIZE(mt76x02_rates
));
265 if (dev
->mt76
.cap
.has_5ghz
) {
266 /* overwrite unsupported features */
267 mt76x0_vht_cap_mask(&dev
->mphy
.sband_5g
.sband
);
268 mt76x0_init_txpower(dev
, &dev
->mphy
.sband_5g
.sband
);
271 if (dev
->mt76
.cap
.has_2ghz
)
272 mt76x0_init_txpower(dev
, &dev
->mphy
.sband_2g
.sband
);
274 mt76x02_init_debugfs(dev
);
278 EXPORT_SYMBOL_GPL(mt76x0_register_device
);