xref: /linux/drivers/net/wireless/realtek/rtw89/mac_be.c (revision 8a5f956a9fb7d74fff681145082acfad5afa6bb8)
1 // SPDX-License-Identifier: GPL-2.0 OR BSD-3-Clause
2 /* Copyright(c) 2019-2020  Realtek Corporation
3  */
4 
5 #include "debug.h"
6 #include "efuse.h"
7 #include "fw.h"
8 #include "mac.h"
9 #include "reg.h"
10 
11 static const u32 rtw89_mac_mem_base_addrs_be[RTW89_MAC_MEM_NUM] = {
12 	[RTW89_MAC_MEM_AXIDMA]	        = AXIDMA_BASE_ADDR_BE,
13 	[RTW89_MAC_MEM_SHARED_BUF]	= SHARED_BUF_BASE_ADDR_BE,
14 	[RTW89_MAC_MEM_DMAC_TBL]	= DMAC_TBL_BASE_ADDR_BE,
15 	[RTW89_MAC_MEM_SHCUT_MACHDR]	= SHCUT_MACHDR_BASE_ADDR_BE,
16 	[RTW89_MAC_MEM_STA_SCHED]	= STA_SCHED_BASE_ADDR_BE,
17 	[RTW89_MAC_MEM_RXPLD_FLTR_CAM]	= RXPLD_FLTR_CAM_BASE_ADDR_BE,
18 	[RTW89_MAC_MEM_SECURITY_CAM]	= SEC_CAM_BASE_ADDR_BE,
19 	[RTW89_MAC_MEM_WOW_CAM]		= WOW_CAM_BASE_ADDR_BE,
20 	[RTW89_MAC_MEM_CMAC_TBL]	= CMAC_TBL_BASE_ADDR_BE,
21 	[RTW89_MAC_MEM_ADDR_CAM]	= ADDR_CAM_BASE_ADDR_BE,
22 	[RTW89_MAC_MEM_BA_CAM]		= BA_CAM_BASE_ADDR_BE,
23 	[RTW89_MAC_MEM_BCN_IE_CAM0]	= BCN_IE_CAM0_BASE_ADDR_BE,
24 	[RTW89_MAC_MEM_BCN_IE_CAM1]	= BCN_IE_CAM1_BASE_ADDR_BE,
25 	[RTW89_MAC_MEM_TXD_FIFO_0]	= TXD_FIFO_0_BASE_ADDR_BE,
26 	[RTW89_MAC_MEM_TXD_FIFO_1]	= TXD_FIFO_1_BASE_ADDR_BE,
27 	[RTW89_MAC_MEM_TXDATA_FIFO_0]	= TXDATA_FIFO_0_BASE_ADDR_BE,
28 	[RTW89_MAC_MEM_TXDATA_FIFO_1]	= TXDATA_FIFO_1_BASE_ADDR_BE,
29 	[RTW89_MAC_MEM_CPU_LOCAL]	= CPU_LOCAL_BASE_ADDR_BE,
30 	[RTW89_MAC_MEM_BSSID_CAM]	= BSSID_CAM_BASE_ADDR_BE,
31 	[RTW89_MAC_MEM_WD_PAGE]		= WD_PAGE_BASE_ADDR_BE,
32 	[RTW89_MAC_MEM_MLD_TBL]		= MLD_TBL_BASE_ADDR_BE,
33 };
34 
35 static const struct rtw89_port_reg rtw89_port_base_be = {
36 	.port_cfg = R_BE_PORT_CFG_P0,
37 	.tbtt_prohib = R_BE_TBTT_PROHIB_P0,
38 	.bcn_area = R_BE_BCN_AREA_P0,
39 	.bcn_early = R_BE_BCNERLYINT_CFG_P0,
40 	.tbtt_early = R_BE_TBTTERLYINT_CFG_P0,
41 	.tbtt_agg = R_BE_TBTT_AGG_P0,
42 	.bcn_space = R_BE_BCN_SPACE_CFG_P0,
43 	.bcn_forcetx = R_BE_BCN_FORCETX_P0,
44 	.bcn_err_cnt = R_BE_BCN_ERR_CNT_P0,
45 	.bcn_err_flag = R_BE_BCN_ERR_FLAG_P0,
46 	.dtim_ctrl = R_BE_DTIM_CTRL_P0,
47 	.tbtt_shift = R_BE_TBTT_SHIFT_P0,
48 	.bcn_cnt_tmr = R_BE_BCN_CNT_TMR_P0,
49 	.tsftr_l = R_BE_TSFTR_LOW_P0,
50 	.tsftr_h = R_BE_TSFTR_HIGH_P0,
51 	.md_tsft = R_BE_WMTX_MOREDATA_TSFT_STMP_CTL,
52 	.bss_color = R_BE_PTCL_BSS_COLOR_0,
53 	.mbssid = R_BE_MBSSID_CTRL,
54 	.mbssid_drop = R_BE_MBSSID_DROP_0,
55 	.tsf_sync = R_BE_PORT_0_TSF_SYNC,
56 	.ptcl_dbg = R_BE_PTCL_DBG,
57 	.ptcl_dbg_info = R_BE_PTCL_DBG_INFO,
58 	.bcn_drop_all = R_BE_BCN_DROP_ALL0,
59 	.bcn_psr_rpt = R_BE_BCN_PSR_RPT_P0,
60 	.hiq_win = {R_BE_P0MB_HGQ_WINDOW_CFG_0, R_BE_PORT_HGQ_WINDOW_CFG,
61 		    R_BE_PORT_HGQ_WINDOW_CFG + 1, R_BE_PORT_HGQ_WINDOW_CFG + 2,
62 		    R_BE_PORT_HGQ_WINDOW_CFG + 3},
63 };
64 
65 static int rtw89_mac_check_mac_en_be(struct rtw89_dev *rtwdev, u8 mac_idx,
66 				     enum rtw89_mac_hwmod_sel sel)
67 {
68 	if (sel == RTW89_DMAC_SEL &&
69 	    test_bit(RTW89_FLAG_DMAC_FUNC, rtwdev->flags))
70 		return 0;
71 	if (sel == RTW89_CMAC_SEL && mac_idx == RTW89_MAC_0 &&
72 	    test_bit(RTW89_FLAG_CMAC0_FUNC, rtwdev->flags))
73 		return 0;
74 	if (sel == RTW89_CMAC_SEL && mac_idx == RTW89_MAC_1 &&
75 	    test_bit(RTW89_FLAG_CMAC1_FUNC, rtwdev->flags))
76 		return 0;
77 
78 	return -EFAULT;
79 }
80 
81 static bool is_qta_poh(struct rtw89_dev *rtwdev)
82 {
83 	return rtwdev->hci.type == RTW89_HCI_TYPE_PCIE;
84 }
85 
86 static void hfc_get_mix_info_be(struct rtw89_dev *rtwdev)
87 {
88 	struct rtw89_hfc_param *param = &rtwdev->mac.hfc_param;
89 	struct rtw89_hfc_prec_cfg *prec_cfg = &param->prec_cfg;
90 	struct rtw89_hfc_pub_cfg *pub_cfg = &param->pub_cfg;
91 	struct rtw89_hfc_pub_info *info = &param->pub_info;
92 	u32 val;
93 
94 	val = rtw89_read32(rtwdev, R_BE_PUB_PAGE_INFO1);
95 	info->g0_used = u32_get_bits(val, B_BE_G0_USE_PG_MASK);
96 	info->g1_used = u32_get_bits(val, B_BE_G1_USE_PG_MASK);
97 
98 	val = rtw89_read32(rtwdev, R_BE_PUB_PAGE_INFO3);
99 	info->g0_aval = u32_get_bits(val, B_BE_G0_AVAL_PG_MASK);
100 	info->g1_aval = u32_get_bits(val, B_BE_G1_AVAL_PG_MASK);
101 	info->pub_aval = u32_get_bits(rtw89_read32(rtwdev, R_BE_PUB_PAGE_INFO2),
102 				      B_BE_PUB_AVAL_PG_MASK);
103 	info->wp_aval = u32_get_bits(rtw89_read32(rtwdev, R_BE_WP_PAGE_INFO1),
104 				     B_BE_WP_AVAL_PG_MASK);
105 
106 	val = rtw89_read32(rtwdev, R_BE_HCI_FC_CTRL);
107 	param->en = !!(val & B_BE_HCI_FC_EN);
108 	param->h2c_en = !!(val & B_BE_HCI_FC_CH12_EN);
109 	param->mode = u32_get_bits(val, B_BE_HCI_FC_MODE_MASK);
110 	prec_cfg->ch011_full_cond = u32_get_bits(val, B_BE_HCI_FC_WD_FULL_COND_MASK);
111 	prec_cfg->h2c_full_cond = u32_get_bits(val, B_BE_HCI_FC_CH12_FULL_COND_MASK);
112 	prec_cfg->wp_ch07_full_cond =
113 		u32_get_bits(val, B_BE_HCI_FC_WP_CH07_FULL_COND_MASK);
114 	prec_cfg->wp_ch811_full_cond =
115 		u32_get_bits(val, B_BE_HCI_FC_WP_CH811_FULL_COND_MASK);
116 
117 	val = rtw89_read32(rtwdev, R_BE_CH_PAGE_CTRL);
118 	prec_cfg->ch011_prec = u32_get_bits(val, B_BE_PREC_PAGE_CH011_V1_MASK);
119 	prec_cfg->h2c_prec = u32_get_bits(val, B_BE_PREC_PAGE_CH12_V1_MASK);
120 
121 	val = rtw89_read32(rtwdev, R_BE_PUB_PAGE_CTRL2);
122 	pub_cfg->pub_max = u32_get_bits(val, B_BE_PUBPG_ALL_MASK);
123 
124 	val = rtw89_read32(rtwdev, R_BE_WP_PAGE_CTRL1);
125 	prec_cfg->wp_ch07_prec = u32_get_bits(val, B_BE_PREC_PAGE_WP_CH07_MASK);
126 	prec_cfg->wp_ch811_prec = u32_get_bits(val, B_BE_PREC_PAGE_WP_CH811_MASK);
127 
128 	val = rtw89_read32(rtwdev, R_BE_WP_PAGE_CTRL2);
129 	pub_cfg->wp_thrd = u32_get_bits(val, B_BE_WP_THRD_MASK);
130 
131 	val = rtw89_read32(rtwdev, R_BE_PUB_PAGE_CTRL1);
132 	pub_cfg->grp0 = u32_get_bits(val, B_BE_PUBPG_G0_MASK);
133 	pub_cfg->grp1 = u32_get_bits(val, B_BE_PUBPG_G1_MASK);
134 }
135 
136 static void hfc_h2c_cfg_be(struct rtw89_dev *rtwdev)
137 {
138 	struct rtw89_hfc_param *param = &rtwdev->mac.hfc_param;
139 	const struct rtw89_hfc_prec_cfg *prec_cfg = &param->prec_cfg;
140 	u32 val;
141 
142 	val = u32_encode_bits(prec_cfg->h2c_prec, B_BE_PREC_PAGE_CH12_V1_MASK);
143 	rtw89_write32(rtwdev, R_BE_CH_PAGE_CTRL, val);
144 }
145 
146 static void hfc_mix_cfg_be(struct rtw89_dev *rtwdev)
147 {
148 	struct rtw89_hfc_param *param = &rtwdev->mac.hfc_param;
149 	const struct rtw89_hfc_prec_cfg *prec_cfg = &param->prec_cfg;
150 	const struct rtw89_hfc_pub_cfg *pub_cfg = &param->pub_cfg;
151 	u32 val;
152 
153 	val = u32_encode_bits(prec_cfg->ch011_prec, B_BE_PREC_PAGE_CH011_V1_MASK) |
154 	      u32_encode_bits(prec_cfg->h2c_prec, B_BE_PREC_PAGE_CH12_V1_MASK);
155 	rtw89_write32(rtwdev, R_BE_CH_PAGE_CTRL, val);
156 
157 	val = u32_encode_bits(pub_cfg->pub_max, B_BE_PUBPG_ALL_MASK);
158 	rtw89_write32(rtwdev, R_BE_PUB_PAGE_CTRL2, val);
159 
160 	val = u32_encode_bits(prec_cfg->wp_ch07_prec, B_BE_PREC_PAGE_WP_CH07_MASK) |
161 	      u32_encode_bits(prec_cfg->wp_ch811_prec, B_BE_PREC_PAGE_WP_CH811_MASK);
162 	rtw89_write32(rtwdev, R_BE_WP_PAGE_CTRL1, val);
163 
164 	val = u32_replace_bits(rtw89_read32(rtwdev, R_BE_HCI_FC_CTRL),
165 			       param->mode, B_BE_HCI_FC_MODE_MASK);
166 	val = u32_replace_bits(val, prec_cfg->ch011_full_cond,
167 			       B_BE_HCI_FC_WD_FULL_COND_MASK);
168 	val = u32_replace_bits(val, prec_cfg->h2c_full_cond,
169 			       B_BE_HCI_FC_CH12_FULL_COND_MASK);
170 	val = u32_replace_bits(val, prec_cfg->wp_ch07_full_cond,
171 			       B_BE_HCI_FC_WP_CH07_FULL_COND_MASK);
172 	val = u32_replace_bits(val, prec_cfg->wp_ch811_full_cond,
173 			       B_BE_HCI_FC_WP_CH811_FULL_COND_MASK);
174 	rtw89_write32(rtwdev, R_BE_HCI_FC_CTRL, val);
175 }
176 
177 static void hfc_func_en_be(struct rtw89_dev *rtwdev, bool en, bool h2c_en)
178 {
179 	struct rtw89_hfc_param *param = &rtwdev->mac.hfc_param;
180 	u32 val;
181 
182 	val = rtw89_read32(rtwdev, R_BE_HCI_FC_CTRL);
183 	param->en = en;
184 	param->h2c_en = h2c_en;
185 	val = en ? (val | B_BE_HCI_FC_EN) : (val & ~B_BE_HCI_FC_EN);
186 	val = h2c_en ? (val | B_BE_HCI_FC_CH12_EN) :
187 		       (val & ~B_BE_HCI_FC_CH12_EN);
188 	rtw89_write32(rtwdev, R_BE_HCI_FC_CTRL, val);
189 }
190 
191 static void dle_func_en_be(struct rtw89_dev *rtwdev, bool enable)
192 {
193 	if (enable)
194 		rtw89_write32_set(rtwdev, R_BE_DMAC_FUNC_EN,
195 				  B_BE_DLE_WDE_EN | B_BE_DLE_PLE_EN);
196 	else
197 		rtw89_write32_clr(rtwdev, R_BE_DMAC_FUNC_EN,
198 				  B_BE_DLE_WDE_EN | B_BE_DLE_PLE_EN);
199 }
200 
201 static void dle_clk_en_be(struct rtw89_dev *rtwdev, bool enable)
202 {
203 	if (enable)
204 		rtw89_write32_set(rtwdev, R_BE_DMAC_CLK_EN,
205 				  B_BE_DLE_WDE_CLK_EN | B_BE_DLE_PLE_CLK_EN);
206 	else
207 		rtw89_write32_clr(rtwdev, R_BE_DMAC_CLK_EN,
208 				  B_BE_DLE_WDE_CLK_EN | B_BE_DLE_PLE_CLK_EN);
209 }
210 
211 static int dle_mix_cfg_be(struct rtw89_dev *rtwdev, const struct rtw89_dle_mem *cfg)
212 {
213 	const struct rtw89_dle_size *wde_size_cfg, *ple_size_cfg;
214 	u32 bound;
215 	u32 val;
216 
217 	wde_size_cfg = cfg->wde_size;
218 	ple_size_cfg = cfg->ple_size;
219 
220 	val = rtw89_read32(rtwdev, R_BE_WDE_PKTBUF_CFG);
221 
222 	switch (wde_size_cfg->pge_size) {
223 	default:
224 	case RTW89_WDE_PG_64:
225 		val = u32_replace_bits(val, S_AX_WDE_PAGE_SEL_64,
226 				       B_BE_WDE_PAGE_SEL_MASK);
227 		break;
228 	case RTW89_WDE_PG_128:
229 		val = u32_replace_bits(val, S_AX_WDE_PAGE_SEL_128,
230 				       B_BE_WDE_PAGE_SEL_MASK);
231 		break;
232 	case RTW89_WDE_PG_256:
233 		rtw89_err(rtwdev, "[ERR]WDE DLE doesn't support 256 byte!\n");
234 		return -EINVAL;
235 	}
236 
237 	bound = wde_size_cfg->srt_ofst / DLE_BOUND_UNIT;
238 	val = u32_replace_bits(val, bound, B_BE_WDE_START_BOUND_MASK);
239 	val = u32_replace_bits(val, wde_size_cfg->lnk_pge_num,
240 			       B_BE_WDE_FREE_PAGE_NUM_MASK);
241 	rtw89_write32(rtwdev, R_BE_WDE_PKTBUF_CFG, val);
242 
243 	val = rtw89_read32(rtwdev, R_BE_PLE_PKTBUF_CFG);
244 
245 	switch (ple_size_cfg->pge_size) {
246 	default:
247 	case RTW89_PLE_PG_64:
248 		rtw89_err(rtwdev, "[ERR]PLE DLE doesn't support 64 byte!\n");
249 		return -EINVAL;
250 	case RTW89_PLE_PG_128:
251 		val = u32_replace_bits(val, S_AX_PLE_PAGE_SEL_128,
252 				       B_BE_PLE_PAGE_SEL_MASK);
253 		break;
254 	case RTW89_PLE_PG_256:
255 		val = u32_replace_bits(val, S_AX_PLE_PAGE_SEL_256,
256 				       B_BE_PLE_PAGE_SEL_MASK);
257 		break;
258 	}
259 
260 	bound = ple_size_cfg->srt_ofst / DLE_BOUND_UNIT;
261 	val = u32_replace_bits(val, bound, B_BE_PLE_START_BOUND_MASK);
262 	val = u32_replace_bits(val, ple_size_cfg->lnk_pge_num,
263 			       B_BE_PLE_FREE_PAGE_NUM_MASK);
264 	rtw89_write32(rtwdev, R_BE_PLE_PKTBUF_CFG, val);
265 
266 	return 0;
267 }
268 
269 static int chk_dle_rdy_be(struct rtw89_dev *rtwdev, bool wde_or_ple)
270 {
271 	u32 reg, mask;
272 	u32 ini;
273 
274 	if (wde_or_ple) {
275 		reg = R_AX_WDE_INI_STATUS;
276 		mask = WDE_MGN_INI_RDY;
277 	} else {
278 		reg = R_AX_PLE_INI_STATUS;
279 		mask = PLE_MGN_INI_RDY;
280 	}
281 
282 	return read_poll_timeout(rtw89_read32, ini, (ini & mask) == mask, 1,
283 				2000, false, rtwdev, reg);
284 }
285 
286 #define INVALID_QT_WCPU U16_MAX
287 #define SET_QUOTA_VAL(_min_x, _max_x, _module, _idx)			\
288 	do {								\
289 		val = u32_encode_bits(_min_x, B_BE_ ## _module ## _Q ## _idx ## _MIN_SIZE_MASK) | \
290 		      u32_encode_bits(_max_x, B_BE_ ## _module ## _Q ## _idx ## _MAX_SIZE_MASK);  \
291 		rtw89_write32(rtwdev,					\
292 			      R_BE_ ## _module ## _QTA ## _idx ## _CFG,	\
293 			      val);					\
294 	} while (0)
295 #define SET_QUOTA(_x, _module, _idx)					\
296 	SET_QUOTA_VAL(min_cfg->_x, max_cfg->_x, _module, _idx)
297 
298 static void wde_quota_cfg_be(struct rtw89_dev *rtwdev,
299 			     const struct rtw89_wde_quota *min_cfg,
300 			     const struct rtw89_wde_quota *max_cfg,
301 			     u16 ext_wde_min_qt_wcpu)
302 {
303 	u16 min_qt_wcpu = ext_wde_min_qt_wcpu != INVALID_QT_WCPU ?
304 			  ext_wde_min_qt_wcpu : min_cfg->wcpu;
305 	u16 max_qt_wcpu = max(max_cfg->wcpu, min_qt_wcpu);
306 	u32 val;
307 
308 	SET_QUOTA(hif, WDE, 0);
309 	SET_QUOTA_VAL(min_qt_wcpu, max_qt_wcpu, WDE, 1);
310 	SET_QUOTA_VAL(0, 0, WDE, 2);
311 	SET_QUOTA(pkt_in, WDE, 3);
312 	SET_QUOTA(cpu_io, WDE, 4);
313 }
314 
315 static void ple_quota_cfg_be(struct rtw89_dev *rtwdev,
316 			     const struct rtw89_ple_quota *min_cfg,
317 			     const struct rtw89_ple_quota *max_cfg)
318 {
319 	u32 val;
320 
321 	SET_QUOTA(cma0_tx, PLE, 0);
322 	SET_QUOTA(cma1_tx, PLE, 1);
323 	SET_QUOTA(c2h, PLE, 2);
324 	SET_QUOTA(h2c, PLE, 3);
325 	SET_QUOTA(wcpu, PLE, 4);
326 	SET_QUOTA(mpdu_proc, PLE, 5);
327 	SET_QUOTA(cma0_dma, PLE, 6);
328 	SET_QUOTA(cma1_dma, PLE, 7);
329 	SET_QUOTA(bb_rpt, PLE, 8);
330 	SET_QUOTA(wd_rel, PLE, 9);
331 	SET_QUOTA(cpu_io, PLE, 10);
332 	SET_QUOTA(tx_rpt, PLE, 11);
333 	SET_QUOTA(h2d, PLE, 12);
334 }
335 
336 static void rtw89_mac_hci_func_en_be(struct rtw89_dev *rtwdev)
337 {
338 	rtw89_write32_set(rtwdev, R_BE_HCI_FUNC_EN, B_BE_HCI_TXDMA_EN |
339 						    B_BE_HCI_RXDMA_EN);
340 }
341 
342 static void rtw89_mac_dmac_func_pre_en_be(struct rtw89_dev *rtwdev)
343 {
344 	u32 val;
345 
346 	val = rtw89_read32(rtwdev, R_BE_HAXI_INIT_CFG1);
347 
348 	switch (rtwdev->hci.type) {
349 	case RTW89_HCI_TYPE_PCIE:
350 		val = u32_replace_bits(val, S_BE_DMA_MOD_PCIE_NO_DATA_CPU,
351 				       B_BE_DMA_MODE_MASK);
352 		break;
353 	case RTW89_HCI_TYPE_USB:
354 		val = u32_replace_bits(val, S_BE_DMA_MOD_USB, B_BE_DMA_MODE_MASK);
355 		val = (val & ~B_BE_STOP_AXI_MST) | B_BE_TXDMA_EN | B_BE_RXDMA_EN;
356 		break;
357 	case RTW89_HCI_TYPE_SDIO:
358 		val = u32_replace_bits(val, S_BE_DMA_MOD_SDIO, B_BE_DMA_MODE_MASK);
359 		val = (val & ~B_BE_STOP_AXI_MST) | B_BE_TXDMA_EN | B_BE_RXDMA_EN;
360 		break;
361 	default:
362 		return;
363 	}
364 
365 	rtw89_write32(rtwdev, R_BE_HAXI_INIT_CFG1, val);
366 
367 	rtw89_write32_clr(rtwdev, R_BE_HAXI_DMA_STOP1,
368 			  B_BE_STOP_CH0 | B_BE_STOP_CH1 | B_BE_STOP_CH2 |
369 			  B_BE_STOP_CH3 | B_BE_STOP_CH4 | B_BE_STOP_CH5 |
370 			  B_BE_STOP_CH6 | B_BE_STOP_CH7 | B_BE_STOP_CH8 |
371 			  B_BE_STOP_CH9 | B_BE_STOP_CH10 | B_BE_STOP_CH11 |
372 			  B_BE_STOP_CH12 | B_BE_STOP_CH13 | B_BE_STOP_CH14);
373 
374 	rtw89_write32_set(rtwdev, R_BE_DMAC_TABLE_CTRL, B_BE_DMAC_ADDR_MODE);
375 }
376 
377 static
378 int rtw89_mac_write_xtal_si_be(struct rtw89_dev *rtwdev, u8 offset, u8 val, u8 mask)
379 {
380 	u32 val32;
381 	int ret;
382 
383 	val32 = u32_encode_bits(offset, B_BE_WL_XTAL_SI_ADDR_MASK) |
384 		u32_encode_bits(val, B_BE_WL_XTAL_SI_DATA_MASK) |
385 		u32_encode_bits(mask, B_BE_WL_XTAL_SI_BITMASK_MASK) |
386 		u32_encode_bits(XTAL_SI_NORMAL_WRITE, B_BE_WL_XTAL_SI_MODE_MASK) |
387 		u32_encode_bits(0, B_BE_WL_XTAL_SI_CHIPID_MASK) |
388 		B_BE_WL_XTAL_SI_CMD_POLL;
389 	rtw89_write32(rtwdev, R_BE_WLAN_XTAL_SI_CTRL, val32);
390 
391 	ret = read_poll_timeout(rtw89_read32, val32, !(val32 & B_BE_WL_XTAL_SI_CMD_POLL),
392 				50, 50000, false, rtwdev, R_BE_WLAN_XTAL_SI_CTRL);
393 	if (ret) {
394 		rtw89_warn(rtwdev, "xtal si not ready(W): offset=%x val=%x mask=%x\n",
395 			   offset, val, mask);
396 		return ret;
397 	}
398 
399 	return 0;
400 }
401 
402 static
403 int rtw89_mac_read_xtal_si_be(struct rtw89_dev *rtwdev, u8 offset, u8 *val)
404 {
405 	u32 val32;
406 	int ret;
407 
408 	val32 = u32_encode_bits(offset, B_BE_WL_XTAL_SI_ADDR_MASK) |
409 		u32_encode_bits(0x0, B_BE_WL_XTAL_SI_DATA_MASK) |
410 		u32_encode_bits(0x0, B_BE_WL_XTAL_SI_BITMASK_MASK) |
411 		u32_encode_bits(XTAL_SI_NORMAL_READ, B_BE_WL_XTAL_SI_MODE_MASK) |
412 		u32_encode_bits(0, B_BE_WL_XTAL_SI_CHIPID_MASK) |
413 		B_BE_WL_XTAL_SI_CMD_POLL;
414 	rtw89_write32(rtwdev, R_BE_WLAN_XTAL_SI_CTRL, val32);
415 
416 	ret = read_poll_timeout(rtw89_read32, val32, !(val32 & B_BE_WL_XTAL_SI_CMD_POLL),
417 				50, 50000, false, rtwdev, R_BE_WLAN_XTAL_SI_CTRL);
418 	if (ret) {
419 		rtw89_warn(rtwdev, "xtal si not ready(R): offset=%x\n", offset);
420 		return ret;
421 	}
422 
423 	*val = rtw89_read8(rtwdev, R_BE_WLAN_XTAL_SI_CTRL + 1);
424 
425 	return 0;
426 }
427 
428 static void rtw89_mac_disable_cpu_be(struct rtw89_dev *rtwdev)
429 {
430 	u32 val32;
431 
432 	clear_bit(RTW89_FLAG_FW_RDY, rtwdev->flags);
433 
434 	rtw89_write32_clr(rtwdev, R_BE_PLATFORM_ENABLE, B_BE_WCPU_EN);
435 	rtw89_write32_set(rtwdev, R_BE_PLATFORM_ENABLE, B_BE_HOLD_AFTER_RESET);
436 	rtw89_write32_set(rtwdev, R_BE_PLATFORM_ENABLE, B_BE_WCPU_EN);
437 
438 	val32 = rtw89_read32(rtwdev, R_BE_WCPU_FW_CTRL);
439 	val32 &= B_BE_RUN_ENV_MASK;
440 	rtw89_write32(rtwdev, R_BE_WCPU_FW_CTRL, val32);
441 
442 	rtw89_write32_set(rtwdev, R_BE_DCPU_PLATFORM_ENABLE, B_BE_DCPU_PLATFORM_EN);
443 
444 	rtw89_write32(rtwdev, R_BE_UDM0, 0);
445 	rtw89_write32(rtwdev, R_BE_HALT_C2H, 0);
446 	rtw89_write32(rtwdev, R_BE_UDM2, 0);
447 }
448 
449 static void set_cpu_en(struct rtw89_dev *rtwdev, bool include_bb)
450 {
451 	u32 set = B_BE_WLANCPU_FWDL_EN;
452 
453 	if (include_bb)
454 		set |= B_BE_BBMCU0_FWDL_EN;
455 
456 	rtw89_write32_set(rtwdev, R_BE_WCPU_FW_CTRL, set);
457 }
458 
459 static int wcpu_on(struct rtw89_dev *rtwdev, u8 boot_reason, bool dlfw)
460 {
461 	u32 val32;
462 	int ret;
463 
464 	val32 = rtw89_read32(rtwdev, R_BE_HALT_C2H);
465 	if (val32) {
466 		rtw89_warn(rtwdev, "[SER] AON L2 Debug register not empty before Boot.\n");
467 		rtw89_warn(rtwdev, "[SER] %s: R_BE_HALT_C2H = 0x%x\n", __func__, val32);
468 	}
469 	val32 = rtw89_read32(rtwdev, R_BE_UDM1);
470 	if (val32) {
471 		rtw89_warn(rtwdev, "[SER] AON L2 Debug register not empty before Boot.\n");
472 		rtw89_warn(rtwdev, "[SER] %s: R_BE_UDM1 = 0x%x\n", __func__, val32);
473 	}
474 	val32 = rtw89_read32(rtwdev, R_BE_UDM2);
475 	if (val32) {
476 		rtw89_warn(rtwdev, "[SER] AON L2 Debug register not empty before Boot.\n");
477 		rtw89_warn(rtwdev, "[SER] %s: R_BE_UDM2 = 0x%x\n", __func__, val32);
478 	}
479 
480 	rtw89_write32(rtwdev, R_BE_UDM1, 0);
481 	rtw89_write32(rtwdev, R_BE_UDM2, 0);
482 	rtw89_write32(rtwdev, R_BE_HALT_H2C, 0);
483 	rtw89_write32(rtwdev, R_BE_HALT_C2H, 0);
484 	rtw89_write32(rtwdev, R_BE_HALT_H2C_CTRL, 0);
485 	rtw89_write32(rtwdev, R_BE_HALT_C2H_CTRL, 0);
486 
487 	val32 = rtw89_read32(rtwdev, R_BE_HISR0);
488 	rtw89_write32(rtwdev, R_BE_HISR0, B_BE_HALT_C2H_INT);
489 	rtw89_debug(rtwdev, RTW89_DBG_SER, "HISR0=0x%x\n", val32);
490 
491 	rtw89_write32_set(rtwdev, R_BE_SYS_CLK_CTRL, B_BE_CPU_CLK_EN);
492 	rtw89_write32_clr(rtwdev, R_BE_SYS_CFG5,
493 			  B_BE_WDT_WAKE_PCIE_EN | B_BE_WDT_WAKE_USB_EN);
494 	rtw89_write32_clr(rtwdev, R_BE_WCPU_FW_CTRL,
495 			  B_BE_WDT_PLT_RST_EN | B_BE_WCPU_ROM_CUT_GET);
496 
497 	rtw89_write16_mask(rtwdev, R_BE_BOOT_REASON, B_BE_BOOT_REASON_MASK, boot_reason);
498 	rtw89_write32_clr(rtwdev, R_BE_PLATFORM_ENABLE, B_BE_WCPU_EN);
499 	rtw89_write32_clr(rtwdev, R_BE_PLATFORM_ENABLE, B_BE_HOLD_AFTER_RESET);
500 	rtw89_write32_set(rtwdev, R_BE_PLATFORM_ENABLE, B_BE_WCPU_EN);
501 
502 	if (!dlfw) {
503 		ret = rtw89_fw_check_rdy(rtwdev, RTW89_FWDL_CHECK_FREERTOS_DONE);
504 		if (ret)
505 			return ret;
506 	}
507 
508 	return 0;
509 }
510 
511 static int rtw89_mac_fwdl_enable_wcpu_be(struct rtw89_dev *rtwdev,
512 					 u8 boot_reason, bool dlfw,
513 					 bool include_bb)
514 {
515 	set_cpu_en(rtwdev, include_bb);
516 
517 	return wcpu_on(rtwdev, boot_reason, dlfw);
518 }
519 
520 static const u8 fwdl_status_map[] = {
521 	[0] = RTW89_FWDL_INITIAL_STATE,
522 	[1] = RTW89_FWDL_FWDL_ONGOING,
523 	[4] = RTW89_FWDL_CHECKSUM_FAIL,
524 	[5] = RTW89_FWDL_SECURITY_FAIL,
525 	[6] = RTW89_FWDL_SECURITY_FAIL,
526 	[7] = RTW89_FWDL_CV_NOT_MATCH,
527 	[8] = RTW89_FWDL_RSVD0,
528 	[2] = RTW89_FWDL_WCPU_FWDL_RDY,
529 	[3] = RTW89_FWDL_WCPU_FW_INIT_RDY,
530 	[9] = RTW89_FWDL_RSVD0,
531 };
532 
533 static u8 fwdl_get_status_be(struct rtw89_dev *rtwdev, enum rtw89_fwdl_check_type type)
534 {
535 	bool check_pass = false;
536 	u32 val32;
537 	u8 st;
538 
539 	val32 = rtw89_read32(rtwdev, R_BE_WCPU_FW_CTRL);
540 
541 	switch (type) {
542 	case RTW89_FWDL_CHECK_WCPU_FWDL_DONE:
543 		check_pass = !(val32 & B_BE_WLANCPU_FWDL_EN);
544 		break;
545 	case RTW89_FWDL_CHECK_DCPU_FWDL_DONE:
546 		check_pass = !(val32 & B_BE_DATACPU_FWDL_EN);
547 		break;
548 	case RTW89_FWDL_CHECK_BB0_FWDL_DONE:
549 		check_pass = !(val32 & B_BE_BBMCU0_FWDL_EN);
550 		break;
551 	case RTW89_FWDL_CHECK_BB1_FWDL_DONE:
552 		check_pass = !(val32 & B_BE_BBMCU1_FWDL_EN);
553 		break;
554 	default:
555 		break;
556 	}
557 
558 	if (check_pass)
559 		return RTW89_FWDL_WCPU_FW_INIT_RDY;
560 
561 	st = u32_get_bits(val32, B_BE_WCPU_FWDL_STATUS_MASK);
562 	if (st < ARRAY_SIZE(fwdl_status_map))
563 		return fwdl_status_map[st];
564 
565 	return st;
566 }
567 
568 static int rtw89_fwdl_check_path_ready_be(struct rtw89_dev *rtwdev,
569 					  bool h2c_or_fwdl)
570 {
571 	u32 check = h2c_or_fwdl ? B_BE_H2C_PATH_RDY : B_BE_DLFW_PATH_RDY;
572 	u32 val;
573 
574 	return read_poll_timeout_atomic(rtw89_read32, val, val & check,
575 					1, 1000000, false,
576 					rtwdev, R_BE_WCPU_FW_CTRL);
577 }
578 
579 static int dmac_func_en_be(struct rtw89_dev *rtwdev)
580 {
581 	return 0;
582 }
583 
584 static int cmac_func_en_be(struct rtw89_dev *rtwdev, u8 mac_idx, bool en)
585 {
586 	u32 reg;
587 
588 	if (mac_idx > RTW89_MAC_1)
589 		return -EINVAL;
590 
591 	if (mac_idx == RTW89_MAC_0)
592 		return 0;
593 
594 	if (en) {
595 		rtw89_write32_set(rtwdev, R_BE_AFE_CTRL1, B_BE_AFE_CTRL1_SET);
596 		rtw89_write32_clr(rtwdev, R_BE_SYS_ISO_CTRL_EXTEND, B_BE_R_SYM_ISO_CMAC12PP);
597 		rtw89_write32_set(rtwdev, R_BE_FEN_RST_ENABLE, B_BE_CMAC1_FEN);
598 
599 		reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_CK_EN, mac_idx);
600 		rtw89_write32_set(rtwdev, reg, B_BE_CK_EN_SET);
601 
602 		reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_CMAC_FUNC_EN, mac_idx);
603 		rtw89_write32_set(rtwdev, reg, B_BE_CMAC_FUNC_EN_SET);
604 
605 		set_bit(RTW89_FLAG_CMAC1_FUNC, rtwdev->flags);
606 	} else {
607 		reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_CMAC_FUNC_EN, mac_idx);
608 		rtw89_write32_clr(rtwdev, reg, B_BE_CMAC_FUNC_EN_SET);
609 
610 		reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_CK_EN, mac_idx);
611 		rtw89_write32_clr(rtwdev, reg, B_BE_CK_EN_SET);
612 
613 		rtw89_write32_clr(rtwdev, R_BE_FEN_RST_ENABLE, B_BE_CMAC1_FEN);
614 		rtw89_write32_set(rtwdev, R_BE_SYS_ISO_CTRL_EXTEND, B_BE_R_SYM_ISO_CMAC12PP);
615 		rtw89_write32_clr(rtwdev, R_BE_AFE_CTRL1, B_BE_AFE_CTRL1_SET);
616 
617 		clear_bit(RTW89_FLAG_CMAC1_FUNC, rtwdev->flags);
618 	}
619 
620 	return 0;
621 }
622 
623 static int chip_func_en_be(struct rtw89_dev *rtwdev)
624 {
625 	return 0;
626 }
627 
628 static int sys_init_be(struct rtw89_dev *rtwdev)
629 {
630 	int ret;
631 
632 	ret = dmac_func_en_be(rtwdev);
633 	if (ret)
634 		return ret;
635 
636 	ret = cmac_func_en_be(rtwdev, RTW89_MAC_0, true);
637 	if (ret)
638 		return ret;
639 
640 	ret = chip_func_en_be(rtwdev);
641 	if (ret)
642 		return ret;
643 
644 	return ret;
645 }
646 
647 static int sta_sch_init_be(struct rtw89_dev *rtwdev)
648 {
649 	u32 p_val;
650 	int ret;
651 
652 	ret = rtw89_mac_check_mac_en(rtwdev, RTW89_MAC_0, RTW89_DMAC_SEL);
653 	if (ret)
654 		return ret;
655 
656 	rtw89_write8_set(rtwdev, R_BE_SS_CTRL, B_BE_SS_EN);
657 
658 	ret = read_poll_timeout(rtw89_read32, p_val, p_val & B_BE_SS_INIT_DONE,
659 				1, TRXCFG_WAIT_CNT, false, rtwdev, R_BE_SS_CTRL);
660 	if (ret) {
661 		rtw89_err(rtwdev, "[ERR]STA scheduler init\n");
662 		return ret;
663 	}
664 
665 	rtw89_write32_set(rtwdev, R_BE_SS_CTRL, B_BE_WARM_INIT);
666 	rtw89_write32_clr(rtwdev, R_BE_SS_CTRL, B_BE_BAND_TRIG_EN | B_BE_BAND1_TRIG_EN);
667 
668 	return 0;
669 }
670 
671 static int mpdu_proc_init_be(struct rtw89_dev *rtwdev)
672 {
673 	u32 val32;
674 	int ret;
675 
676 	ret = rtw89_mac_check_mac_en(rtwdev, RTW89_MAC_0, RTW89_DMAC_SEL);
677 	if (ret)
678 		return ret;
679 
680 	rtw89_write32_set(rtwdev, R_BE_MPDU_PROC, B_BE_APPEND_FCS);
681 	rtw89_write32(rtwdev, R_BE_CUT_AMSDU_CTRL, TRXCFG_MPDU_PROC_CUT_CTRL);
682 
683 	val32 = rtw89_read32(rtwdev, R_BE_HDR_SHCUT_SETTING);
684 	val32 |= (B_BE_TX_HW_SEQ_EN | B_BE_TX_HW_ACK_POLICY_EN | B_BE_TX_MAC_MPDU_PROC_EN);
685 	val32 &= ~B_BE_TX_ADDR_MLD_TO_LIK;
686 	rtw89_write32_set(rtwdev, R_BE_HDR_SHCUT_SETTING, val32);
687 
688 	rtw89_write32(rtwdev, R_BE_RX_HDRTRNS, TRXCFG_MPDU_PROC_RX_HDR_CONV);
689 
690 	val32 = rtw89_read32(rtwdev, R_BE_DISP_FWD_WLAN_0);
691 	val32 = u32_replace_bits(val32, 1, B_BE_FWD_WLAN_CPU_TYPE_0_DATA_MASK);
692 	val32 = u32_replace_bits(val32, 1, B_BE_FWD_WLAN_CPU_TYPE_0_MNG_MASK);
693 	val32 = u32_replace_bits(val32, 1, B_BE_FWD_WLAN_CPU_TYPE_0_CTL_MASK);
694 	val32 = u32_replace_bits(val32, 1, B_BE_FWD_WLAN_CPU_TYPE_1_MASK);
695 	rtw89_write32(rtwdev, R_BE_DISP_FWD_WLAN_0, val32);
696 
697 	return 0;
698 }
699 
700 static int sec_eng_init_be(struct rtw89_dev *rtwdev)
701 {
702 	u32 val32;
703 	int ret;
704 
705 	ret = rtw89_mac_check_mac_en(rtwdev, RTW89_MAC_0, RTW89_DMAC_SEL);
706 	if (ret)
707 		return ret;
708 
709 	val32 = rtw89_read32(rtwdev, R_BE_SEC_ENG_CTRL);
710 	val32 |= B_BE_CLK_EN_CGCMP | B_BE_CLK_EN_WAPI | B_BE_CLK_EN_WEP_TKIP |
711 		 B_BE_SEC_TX_ENC | B_BE_SEC_RX_DEC |
712 		 B_BE_MC_DEC | B_BE_BC_DEC |
713 		 B_BE_BMC_MGNT_DEC | B_BE_UC_MGNT_DEC |
714 		 B_BE_SEC_PRE_ENQUE_TX;
715 	rtw89_write32(rtwdev, R_BE_SEC_ENG_CTRL, val32);
716 
717 	rtw89_write32_set(rtwdev, R_BE_SEC_MPDU_PROC, B_BE_APPEND_ICV | B_BE_APPEND_MIC);
718 
719 	return 0;
720 }
721 
722 static int txpktctrl_init_be(struct rtw89_dev *rtwdev)
723 {
724 	struct rtw89_mac_dle_rsvd_qt_cfg qt_cfg;
725 	u32 val32;
726 	int ret;
727 
728 	ret = rtw89_mac_get_dle_rsvd_qt_cfg(rtwdev, DLE_RSVD_QT_MPDU_INFO, &qt_cfg);
729 	if (ret) {
730 		rtw89_err(rtwdev, "get dle rsvd qt %d cfg fail %d\n",
731 			  DLE_RSVD_QT_MPDU_INFO, ret);
732 		return ret;
733 	}
734 
735 	val32 = rtw89_read32(rtwdev, R_BE_TXPKTCTL_MPDUINFO_CFG);
736 	val32 = u32_replace_bits(val32, qt_cfg.pktid, B_BE_MPDUINFO_PKTID_MASK);
737 	val32 = u32_replace_bits(val32, MPDU_INFO_B1_OFST, B_BE_MPDUINFO_B1_BADDR_MASK);
738 	val32 |= B_BE_MPDUINFO_FEN;
739 	rtw89_write32(rtwdev, R_BE_TXPKTCTL_MPDUINFO_CFG, val32);
740 
741 	return 0;
742 }
743 
744 static int mlo_init_be(struct rtw89_dev *rtwdev)
745 {
746 	u32 val32;
747 	int ret;
748 
749 	val32 = rtw89_read32(rtwdev, R_BE_MLO_INIT_CTL);
750 
751 	val32 |= B_BE_MLO_TABLE_REINIT;
752 	rtw89_write32(rtwdev, R_BE_MLO_INIT_CTL, val32);
753 	val32 &= ~B_BE_MLO_TABLE_REINIT;
754 	rtw89_write32(rtwdev, R_BE_MLO_INIT_CTL, val32);
755 
756 	ret = read_poll_timeout_atomic(rtw89_read32, val32,
757 				       val32 & B_BE_MLO_TABLE_INIT_DONE,
758 				       1, 1000, false, rtwdev, R_BE_MLO_INIT_CTL);
759 	if (ret)
760 		rtw89_err(rtwdev, "[MLO]%s: MLO init polling timeout\n", __func__);
761 
762 	rtw89_write32_set(rtwdev, R_BE_SS_CTRL, B_BE_MLO_HW_CHGLINK_EN);
763 	rtw89_write32_set(rtwdev, R_BE_CMAC_SHARE_ACQCHK_CFG_0, B_BE_R_MACID_ACQ_CHK_EN);
764 
765 	return ret;
766 }
767 
768 static int dmac_init_be(struct rtw89_dev *rtwdev, u8 mac_idx)
769 {
770 	int ret;
771 
772 	ret = rtw89_mac_dle_init(rtwdev, rtwdev->mac.qta_mode, RTW89_QTA_INVALID);
773 	if (ret) {
774 		rtw89_err(rtwdev, "[ERR]DLE init %d\n", ret);
775 		return ret;
776 	}
777 
778 	ret = rtw89_mac_preload_init(rtwdev, mac_idx, rtwdev->mac.qta_mode);
779 	if (ret) {
780 		rtw89_err(rtwdev, "[ERR]preload init %d\n", ret);
781 		return ret;
782 	}
783 
784 	ret = rtw89_mac_hfc_init(rtwdev, true, true, true);
785 	if (ret) {
786 		rtw89_err(rtwdev, "[ERR]HCI FC init %d\n", ret);
787 		return ret;
788 	}
789 
790 	ret = sta_sch_init_be(rtwdev);
791 	if (ret) {
792 		rtw89_err(rtwdev, "[ERR]STA SCH init %d\n", ret);
793 		return ret;
794 	}
795 
796 	ret = mpdu_proc_init_be(rtwdev);
797 	if (ret) {
798 		rtw89_err(rtwdev, "[ERR]MPDU Proc init %d\n", ret);
799 		return ret;
800 	}
801 
802 	ret = sec_eng_init_be(rtwdev);
803 	if (ret) {
804 		rtw89_err(rtwdev, "[ERR]Security Engine init %d\n", ret);
805 		return ret;
806 	}
807 
808 	ret = txpktctrl_init_be(rtwdev);
809 	if (ret) {
810 		rtw89_err(rtwdev, "[ERR]TX pkt ctrl init %d\n", ret);
811 		return ret;
812 	}
813 
814 	ret = mlo_init_be(rtwdev);
815 	if (ret) {
816 		rtw89_err(rtwdev, "[ERR]MLO init %d\n", ret);
817 		return ret;
818 	}
819 
820 	return ret;
821 }
822 
823 static int scheduler_init_be(struct rtw89_dev *rtwdev, u8 mac_idx)
824 {
825 	u32 val32;
826 	u32 reg;
827 	int ret;
828 
829 	ret = rtw89_mac_check_mac_en(rtwdev, mac_idx, RTW89_CMAC_SEL);
830 	if (ret)
831 		return ret;
832 
833 	reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_HE_CTN_CHK_CCA_NAV, mac_idx);
834 	val32 = B_BE_HE_CTN_CHK_CCA_P20 | B_BE_HE_CTN_CHK_EDCCA_P20 |
835 		B_BE_HE_CTN_CHK_CCA_BITMAP | B_BE_HE_CTN_CHK_EDCCA_BITMAP |
836 		B_BE_HE_CTN_CHK_NO_GNT_WL | B_BE_HE_CTN_CHK_BASIC_NAV |
837 		B_BE_HE_CTN_CHK_INTRA_NAV | B_BE_HE_CTN_CHK_TX_NAV;
838 	rtw89_write32(rtwdev, reg, val32);
839 
840 	reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_HE_SIFS_CHK_CCA_NAV, mac_idx);
841 	val32 = B_BE_HE_SIFS_CHK_EDCCA_P20 | B_BE_HE_SIFS_CHK_EDCCA_BITMAP |
842 		B_BE_HE_SIFS_CHK_NO_GNT_WL;
843 	rtw89_write32(rtwdev, reg, val32);
844 
845 	reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_TB_CHK_CCA_NAV, mac_idx);
846 	val32 = B_BE_TB_CHK_EDCCA_BITMAP | B_BE_TB_CHK_NO_GNT_WL | B_BE_TB_CHK_BASIC_NAV;
847 	rtw89_write32(rtwdev, reg, val32);
848 
849 	reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_CCA_CFG_0, mac_idx);
850 	rtw89_write32_clr(rtwdev, reg, B_BE_NO_GNT_WL_EN);
851 
852 	if (is_qta_poh(rtwdev)) {
853 		reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_PREBKF_CFG_0, mac_idx);
854 		rtw89_write32_mask(rtwdev, reg, B_BE_PREBKF_TIME_MASK,
855 				   SCH_PREBKF_24US);
856 
857 		reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_CTN_CFG_0, mac_idx);
858 		rtw89_write32_mask(rtwdev, reg, B_BE_PREBKF_TIME_NONAC_MASK,
859 				   SCH_PREBKF_24US);
860 	}
861 
862 	reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_EDCA_BCNQ_PARAM, mac_idx);
863 	rtw89_write32_mask(rtwdev, reg, B_BE_BCNQ_CW_MASK, 0x32);
864 	rtw89_write32_mask(rtwdev, reg, B_BE_BCNQ_AIFS_MASK, BCN_IFS_25US);
865 
866 	return 0;
867 }
868 
869 static int addr_cam_init_be(struct rtw89_dev *rtwdev, u8 mac_idx)
870 {
871 	u32 val32;
872 	u16 val16;
873 	u32 reg;
874 	int ret;
875 
876 	ret = rtw89_mac_check_mac_en(rtwdev, mac_idx, RTW89_CMAC_SEL);
877 	if (ret)
878 		return ret;
879 
880 	reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_ADDR_CAM_CTRL, mac_idx);
881 	val32 = rtw89_read32(rtwdev, reg);
882 	val32 = u32_replace_bits(val32, ADDR_CAM_SERCH_RANGE, B_BE_ADDR_CAM_RANGE_MASK);
883 	val32 |= B_BE_ADDR_CAM_EN;
884 	if (mac_idx == RTW89_MAC_0)
885 		val32 |= B_BE_ADDR_CAM_CLR;
886 	rtw89_write32(rtwdev, reg, val32);
887 
888 	reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_ADDR_CAM_CTRL, mac_idx);
889 	ret = read_poll_timeout_atomic(rtw89_read16, val16, !(val16 & B_BE_ADDR_CAM_CLR),
890 				       1, TRXCFG_WAIT_CNT, false, rtwdev, reg);
891 	if (ret)
892 		rtw89_err(rtwdev, "[ERR]ADDR_CAM reset\n");
893 
894 	return ret;
895 }
896 
897 static int rtw89_mac_typ_fltr_opt_be(struct rtw89_dev *rtwdev,
898 				     enum rtw89_machdr_frame_type type,
899 				     enum rtw89_mac_fwd_target fwd_target,
900 				     u8 mac_idx)
901 {
902 	u32 reg;
903 	u32 val;
904 
905 	switch (fwd_target) {
906 	case RTW89_FWD_DONT_CARE:
907 		val = RX_FLTR_FRAME_DROP_BE;
908 		break;
909 	case RTW89_FWD_TO_HOST:
910 	case RTW89_FWD_TO_WLAN_CPU:
911 		val = RX_FLTR_FRAME_ACCEPT_BE;
912 		break;
913 	default:
914 		rtw89_err(rtwdev, "[ERR]set rx filter fwd target err\n");
915 		return -EINVAL;
916 	}
917 
918 	switch (type) {
919 	case RTW89_MGNT:
920 		reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_MGNT_FLTR, mac_idx);
921 		break;
922 	case RTW89_CTRL:
923 		reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_CTRL_FLTR, mac_idx);
924 		break;
925 	case RTW89_DATA:
926 		reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_DATA_FLTR, mac_idx);
927 		break;
928 	default:
929 		rtw89_err(rtwdev, "[ERR]set rx filter type err\n");
930 		return -EINVAL;
931 	}
932 	rtw89_write32(rtwdev, reg, val);
933 
934 	return 0;
935 }
936 
937 static int rx_fltr_init_be(struct rtw89_dev *rtwdev, u8 mac_idx)
938 {
939 	u32 reg;
940 	u32 val;
941 
942 	rtw89_mac_typ_fltr_opt_be(rtwdev, RTW89_MGNT, RTW89_FWD_TO_HOST, mac_idx);
943 	rtw89_mac_typ_fltr_opt_be(rtwdev, RTW89_CTRL, RTW89_FWD_TO_HOST, mac_idx);
944 	rtw89_mac_typ_fltr_opt_be(rtwdev, RTW89_DATA, RTW89_FWD_TO_HOST, mac_idx);
945 
946 	reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_RX_FLTR_OPT, mac_idx);
947 	val = B_BE_A_BC_CAM_MATCH | B_BE_A_UC_CAM_MATCH | B_BE_A_MC |
948 	      B_BE_A_BC | B_BE_A_A1_MATCH | B_BE_SNIFFER_MODE |
949 	      u32_encode_bits(15, B_BE_UID_FILTER_MASK);
950 	rtw89_write32(rtwdev, reg, val);
951 	u32p_replace_bits(&rtwdev->hal.rx_fltr, 15, B_BE_UID_FILTER_MASK);
952 
953 	reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_PLCP_HDR_FLTR, mac_idx);
954 	val = B_BE_HE_SIGB_CRC_CHK | B_BE_VHT_MU_SIGB_CRC_CHK |
955 	      B_BE_VHT_SU_SIGB_CRC_CHK | B_BE_SIGA_CRC_CHK |
956 	      B_BE_LSIG_PARITY_CHK_EN | B_BE_CCK_SIG_CHK | B_BE_CCK_CRC_CHK;
957 	rtw89_write16(rtwdev, reg, val);
958 
959 	return 0;
960 }
961 
962 static int cca_ctrl_init_be(struct rtw89_dev *rtwdev, u8 mac_idx)
963 {
964 	return 0;
965 }
966 
967 static int nav_ctrl_init_be(struct rtw89_dev *rtwdev, u8 mac_idx)
968 {
969 	u32 val32;
970 	u32 reg;
971 
972 	reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_WMAC_NAV_CTL, mac_idx);
973 
974 	val32 = rtw89_read32(rtwdev, reg);
975 	val32 &= ~B_BE_WMAC_PLCP_UP_NAV_EN;
976 	val32 |= B_BE_WMAC_TF_UP_NAV_EN | B_BE_WMAC_NAV_UPPER_EN;
977 	val32 = u32_replace_bits(val32, NAV_25MS, B_BE_WMAC_NAV_UPPER_MASK);
978 
979 	rtw89_write32(rtwdev, reg, val32);
980 
981 	return 0;
982 }
983 
984 static int spatial_reuse_init_be(struct rtw89_dev *rtwdev, u8 mac_idx)
985 {
986 	u32 reg;
987 	int ret;
988 
989 	ret = rtw89_mac_check_mac_en(rtwdev, mac_idx, RTW89_CMAC_SEL);
990 	if (ret)
991 		return ret;
992 
993 	reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_RX_SR_CTRL, mac_idx);
994 	rtw89_write8_clr(rtwdev, reg, B_BE_SR_EN | B_BE_SR_CTRL_PLCP_EN);
995 
996 	reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_BSSID_SRC_CTRL, mac_idx);
997 	rtw89_write8_set(rtwdev, reg, B_BE_PLCP_SRC_EN);
998 
999 	return 0;
1000 }
1001 
1002 static int tmac_init_be(struct rtw89_dev *rtwdev, u8 mac_idx)
1003 {
1004 	u32 reg;
1005 
1006 	reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_TB_PPDU_CTRL, mac_idx);
1007 	rtw89_write32_clr(rtwdev, reg, B_BE_QOSNULL_UPD_MUEDCA_EN);
1008 
1009 	reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_WMTX_TCR_BE_4, mac_idx);
1010 	rtw89_write32_mask(rtwdev, reg, B_BE_EHT_HE_PPDU_4XLTF_ZLD_USTIMER_MASK, 0x12);
1011 	rtw89_write32_mask(rtwdev, reg, B_BE_EHT_HE_PPDU_2XLTF_ZLD_USTIMER_MASK, 0xe);
1012 
1013 	return 0;
1014 }
1015 
1016 static int trxptcl_init_be(struct rtw89_dev *rtwdev, u8 mac_idx)
1017 {
1018 	const struct rtw89_chip_info *chip = rtwdev->chip;
1019 	const struct rtw89_rrsr_cfgs *rrsr = chip->rrsr_cfgs;
1020 	struct rtw89_hal *hal = &rtwdev->hal;
1021 	u32 val32;
1022 	u32 reg;
1023 	int ret;
1024 
1025 	ret = rtw89_mac_check_mac_en(rtwdev, mac_idx, RTW89_CMAC_SEL);
1026 	if (ret)
1027 		return ret;
1028 
1029 	reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_MAC_LOOPBACK, mac_idx);
1030 	val32 = rtw89_read32(rtwdev, reg);
1031 	val32 = u32_replace_bits(val32, S_BE_MACLBK_PLCP_DLY_DEF,
1032 				 B_BE_MACLBK_PLCP_DLY_MASK);
1033 	val32 &= ~B_BE_MACLBK_EN;
1034 	rtw89_write32(rtwdev, reg, val32);
1035 
1036 	reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_TRXPTCL_RESP_0, mac_idx);
1037 	val32 = rtw89_read32(rtwdev, reg);
1038 	val32 = u32_replace_bits(val32, WMAC_SPEC_SIFS_CCK,
1039 				 B_BE_WMAC_SPEC_SIFS_CCK_MASK);
1040 	val32 = u32_replace_bits(val32, WMAC_SPEC_SIFS_OFDM_1115E,
1041 				 B_BE_WMAC_SPEC_SIFS_OFDM_MASK);
1042 	rtw89_write32(rtwdev, reg, val32);
1043 
1044 	reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_WMAC_ACK_BA_RESP_LEGACY, mac_idx);
1045 	rtw89_write32_clr(rtwdev, reg, B_BE_ACK_BA_RESP_LEGACY_CHK_EDCCA);
1046 
1047 	reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_WMAC_ACK_BA_RESP_HE, mac_idx);
1048 	rtw89_write32_clr(rtwdev, reg, B_BE_ACK_BA_RESP_HE_CHK_EDCCA);
1049 
1050 	reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_WMAC_ACK_BA_RESP_EHT_LEG_PUNC, mac_idx);
1051 	rtw89_write32_clr(rtwdev, reg, B_BE_ACK_BA_EHT_LEG_PUNC_CHK_EDCCA);
1052 
1053 	reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_RXTRIG_TEST_USER_2, mac_idx);
1054 	rtw89_write32_set(rtwdev, reg, B_BE_RXTRIG_FCSCHK_EN);
1055 
1056 	reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_TRXPTCL_RESP_1, mac_idx);
1057 	val32 = rtw89_read32(rtwdev, reg);
1058 	val32 &= B_BE_FTM_RRSR_RATE_EN_MASK | B_BE_WMAC_RESP_DOPPLEB_BE_EN |
1059 		 B_BE_WMAC_RESP_DCM_EN | B_BE_WMAC_RESP_REF_RATE_MASK;
1060 	rtw89_write32(rtwdev, reg, val32);
1061 	rtw89_write32_mask(rtwdev, reg, rrsr->ref_rate.mask, rrsr->ref_rate.data);
1062 
1063 	reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_PTCL_RRSR1, mac_idx);
1064 	val32 = rtw89_read32(rtwdev, reg);
1065 	val32 &= B_BE_RRSR_RATE_EN_MASK | B_BE_RRSR_CCK_MASK | B_BE_RSC_MASK;
1066 	rtw89_write32(rtwdev, reg, val32);
1067 
1068 	reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_PTCL_RRSR0, mac_idx);
1069 	val32 = rtw89_read32(rtwdev, reg);
1070 	val32 &= B_BE_RRSR_OFDM_MASK | B_BE_RRSR_HT_MASK | B_BE_RRSR_VHT_MASK |
1071 		 B_BE_RRSR_HE_MASK;
1072 	rtw89_write32(rtwdev, reg, val32);
1073 
1074 	if (chip->chip_id == RTL8922A && hal->cv == CHIP_CAV) {
1075 		reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_PTCL_RRSR1, mac_idx);
1076 		rtw89_write32_mask(rtwdev, reg, B_BE_RSC_MASK, 1);
1077 	}
1078 
1079 	return 0;
1080 }
1081 
1082 static int rst_bacam_be(struct rtw89_dev *rtwdev)
1083 {
1084 	u32 val;
1085 	int ret;
1086 
1087 	rtw89_write32_mask(rtwdev, R_BE_RESPBA_CAM_CTRL, B_BE_BACAM_RST_MASK,
1088 			   S_BE_BACAM_RST_ALL);
1089 
1090 	ret = read_poll_timeout_atomic(rtw89_read32_mask, val, val == S_BE_BACAM_RST_DONE,
1091 				       1, 1000, false,
1092 				       rtwdev, R_BE_RESPBA_CAM_CTRL, B_BE_BACAM_RST_MASK);
1093 	if (ret)
1094 		rtw89_err(rtwdev, "[ERR]bacam rst timeout\n");
1095 
1096 	return ret;
1097 }
1098 
1099 #define PLD_RLS_MAX_PG 127
1100 #define RX_MAX_LEN_UNIT 512
1101 #define RX_SPEC_MAX_LEN (11454 + RX_MAX_LEN_UNIT)
1102 
1103 static int rmac_init_be(struct rtw89_dev *rtwdev, u8 mac_idx)
1104 {
1105 	u32 rx_min_qta, rx_max_len, rx_max_pg;
1106 	u16 val16;
1107 	u32 reg;
1108 	int ret;
1109 
1110 	ret = rtw89_mac_check_mac_en(rtwdev, mac_idx, RTW89_CMAC_SEL);
1111 	if (ret)
1112 		return ret;
1113 
1114 	if (mac_idx == RTW89_MAC_0) {
1115 		ret = rst_bacam_be(rtwdev);
1116 		if (ret)
1117 			return ret;
1118 	}
1119 
1120 	reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_DLK_PROTECT_CTL, mac_idx);
1121 	val16 = rtw89_read16(rtwdev, reg);
1122 	val16 = u16_replace_bits(val16, TRXCFG_RMAC_DATA_TO, B_BE_RX_DLK_DATA_TIME_MASK);
1123 	val16 = u16_replace_bits(val16, TRXCFG_RMAC_CCA_TO, B_BE_RX_DLK_CCA_TIME_MASK);
1124 	val16 |= B_BE_RX_DLK_RST_EN;
1125 	rtw89_write16(rtwdev, reg, val16);
1126 
1127 	if (mac_idx == RTW89_MAC_0)
1128 		rx_min_qta = rtwdev->mac.dle_info.c0_rx_qta;
1129 	else
1130 		rx_min_qta = rtwdev->mac.dle_info.c1_rx_qta;
1131 	rx_max_pg = min_t(u32, rx_min_qta, PLD_RLS_MAX_PG);
1132 	rx_max_len = rx_max_pg * rtwdev->mac.dle_info.ple_pg_size;
1133 	rx_max_len = min_t(u32, rx_max_len, RX_SPEC_MAX_LEN);
1134 	rx_max_len /= RX_MAX_LEN_UNIT;
1135 
1136 	reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_RX_FLTR_OPT, mac_idx);
1137 	rtw89_write32_mask(rtwdev, reg, B_BE_RX_MPDU_MAX_LEN_MASK, rx_max_len);
1138 
1139 	reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_PLCP_HDR_FLTR, mac_idx);
1140 	rtw89_write8_clr(rtwdev, reg, B_BE_VHT_SU_SIGB_CRC_CHK);
1141 
1142 	reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_RCR, mac_idx);
1143 	rtw89_write16_set(rtwdev, reg, B_BE_BUSY_CHKSN);
1144 
1145 	reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_RX_PLCP_EXT_OPTION_1, mac_idx);
1146 	rtw89_write16_set(rtwdev, reg, B_BE_PLCP_SU_PSDU_LEN_SRC);
1147 
1148 	return 0;
1149 }
1150 
1151 static int resp_pktctl_init_be(struct rtw89_dev *rtwdev, u8 mac_idx)
1152 {
1153 	struct rtw89_mac_dle_rsvd_qt_cfg qt_cfg;
1154 	enum rtw89_mac_dle_rsvd_qt_type type;
1155 	u32 reg;
1156 	int ret;
1157 
1158 	if (mac_idx == RTW89_MAC_1)
1159 		type = DLE_RSVD_QT_B1_CSI;
1160 	else
1161 		type = DLE_RSVD_QT_B0_CSI;
1162 
1163 	ret = rtw89_mac_get_dle_rsvd_qt_cfg(rtwdev, type, &qt_cfg);
1164 	if (ret) {
1165 		rtw89_err(rtwdev, "get dle rsvd qt %d cfg fail %d\n", type, ret);
1166 		return ret;
1167 	}
1168 
1169 	reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_RESP_CSI_RESERVED_PAGE, mac_idx);
1170 	rtw89_write32_mask(rtwdev, reg, B_BE_CSI_RESERVED_START_PAGE_MASK, qt_cfg.pktid);
1171 	rtw89_write32_mask(rtwdev, reg, B_BE_CSI_RESERVED_PAGE_NUM_MASK, qt_cfg.pg_num);
1172 
1173 	return 0;
1174 }
1175 
1176 static int cmac_com_init_be(struct rtw89_dev *rtwdev, u8 mac_idx)
1177 {
1178 	u32 val32;
1179 	int ret;
1180 
1181 	ret = rtw89_mac_check_mac_en(rtwdev, mac_idx, RTW89_CMAC_SEL);
1182 	if (ret)
1183 		return ret;
1184 
1185 	if (mac_idx == RTW89_MAC_0) {
1186 		val32 = rtw89_read32(rtwdev, R_BE_TX_SUB_BAND_VALUE);
1187 		val32 = u32_replace_bits(val32, S_BE_TXSB_20M_8, B_BE_TXSB_20M_MASK);
1188 		val32 = u32_replace_bits(val32, S_BE_TXSB_40M_4, B_BE_TXSB_40M_MASK);
1189 		val32 = u32_replace_bits(val32, S_BE_TXSB_80M_2, B_BE_TXSB_80M_MASK);
1190 		val32 = u32_replace_bits(val32, S_BE_TXSB_160M_1, B_BE_TXSB_160M_MASK);
1191 		rtw89_write32(rtwdev, R_BE_TX_SUB_BAND_VALUE, val32);
1192 	} else {
1193 		val32 = rtw89_read32(rtwdev, R_BE_TX_SUB_BAND_VALUE_C1);
1194 		val32 = u32_replace_bits(val32, S_BE_TXSB_20M_2, B_BE_TXSB_20M_MASK);
1195 		val32 = u32_replace_bits(val32, S_BE_TXSB_40M_1, B_BE_TXSB_40M_MASK);
1196 		val32 = u32_replace_bits(val32, S_BE_TXSB_80M_0, B_BE_TXSB_80M_MASK);
1197 		val32 = u32_replace_bits(val32, S_BE_TXSB_160M_0, B_BE_TXSB_160M_MASK);
1198 		rtw89_write32(rtwdev, R_BE_TX_SUB_BAND_VALUE_C1, val32);
1199 	}
1200 
1201 	return 0;
1202 }
1203 
1204 static int ptcl_init_be(struct rtw89_dev *rtwdev, u8 mac_idx)
1205 {
1206 	u32 val32;
1207 	u8 val8;
1208 	u32 reg;
1209 	int ret;
1210 
1211 	ret = rtw89_mac_check_mac_en(rtwdev, mac_idx, RTW89_CMAC_SEL);
1212 	if (ret)
1213 		return ret;
1214 
1215 	if (is_qta_poh(rtwdev)) {
1216 		reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_SIFS_SETTING, mac_idx);
1217 		val32 = rtw89_read32(rtwdev, reg);
1218 		val32 = u32_replace_bits(val32, S_AX_CTS2S_TH_1K,
1219 					 B_BE_HW_CTS2SELF_PKT_LEN_TH_MASK);
1220 		val32 = u32_replace_bits(val32, S_AX_CTS2S_TH_SEC_256B,
1221 					 B_BE_HW_CTS2SELF_PKT_LEN_TH_TWW_MASK);
1222 		val32 |= B_BE_HW_CTS2SELF_EN;
1223 		rtw89_write32(rtwdev, reg, val32);
1224 
1225 		reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_PTCL_FSM_MON, mac_idx);
1226 		val32 = rtw89_read32(rtwdev, reg);
1227 		val32 = u32_replace_bits(val32, S_AX_PTCL_TO_2MS,
1228 					 B_BE_PTCL_TX_ARB_TO_THR_MASK);
1229 		val32 &= ~B_BE_PTCL_TX_ARB_TO_MODE;
1230 		rtw89_write32(rtwdev, reg, val32);
1231 	}
1232 
1233 	reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_PTCL_COMMON_SETTING_0, mac_idx);
1234 	val8 = rtw89_read8(rtwdev, reg);
1235 	val8 |= B_BE_CMAC_TX_MODE_0 | B_BE_CMAC_TX_MODE_1;
1236 	val8 &= ~(B_BE_PTCL_TRIGGER_SS_EN_0 |
1237 		  B_BE_PTCL_TRIGGER_SS_EN_1 |
1238 		  B_BE_PTCL_TRIGGER_SS_EN_UL);
1239 	rtw89_write8(rtwdev, reg, val8);
1240 
1241 	reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_AMPDU_AGG_LIMIT, mac_idx);
1242 	rtw89_write32_mask(rtwdev, reg, B_BE_AMPDU_MAX_TIME_MASK, AMPDU_MAX_TIME);
1243 
1244 	return 0;
1245 }
1246 
1247 static int cmac_dma_init_be(struct rtw89_dev *rtwdev, u8 mac_idx)
1248 {
1249 	u32 val32;
1250 	u32 reg;
1251 	int ret;
1252 
1253 	ret = rtw89_mac_check_mac_en(rtwdev, mac_idx, RTW89_CMAC_SEL);
1254 	if (ret)
1255 		return ret;
1256 
1257 	reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_RX_CTRL_1, mac_idx);
1258 
1259 	val32 = rtw89_read32(rtwdev, reg);
1260 	val32 = u32_replace_bits(val32, WLCPU_RXCH2_QID,
1261 				 B_BE_RXDMA_TXRPT_QUEUE_ID_SW_MASK);
1262 	val32 = u32_replace_bits(val32, WLCPU_RXCH2_QID,
1263 				 B_BE_RXDMA_F2PCMDRPT_QUEUE_ID_SW_MASK);
1264 	rtw89_write32(rtwdev, reg, val32);
1265 
1266 	return 0;
1267 }
1268 
1269 static int cmac_init_be(struct rtw89_dev *rtwdev, u8 mac_idx)
1270 {
1271 	int ret;
1272 
1273 	ret = scheduler_init_be(rtwdev, mac_idx);
1274 	if (ret) {
1275 		rtw89_err(rtwdev, "[ERR]CMAC%d SCH init %d\n", mac_idx, ret);
1276 		return ret;
1277 	}
1278 
1279 	ret = addr_cam_init_be(rtwdev, mac_idx);
1280 	if (ret) {
1281 		rtw89_err(rtwdev, "[ERR]CMAC%d ADDR_CAM reset %d\n", mac_idx,
1282 			  ret);
1283 		return ret;
1284 	}
1285 
1286 	ret = rx_fltr_init_be(rtwdev, mac_idx);
1287 	if (ret) {
1288 		rtw89_err(rtwdev, "[ERR]CMAC%d RX filter init %d\n", mac_idx,
1289 			  ret);
1290 		return ret;
1291 	}
1292 
1293 	ret = cca_ctrl_init_be(rtwdev, mac_idx);
1294 	if (ret) {
1295 		rtw89_err(rtwdev, "[ERR]CMAC%d CCA CTRL init %d\n", mac_idx,
1296 			  ret);
1297 		return ret;
1298 	}
1299 
1300 	ret = nav_ctrl_init_be(rtwdev, mac_idx);
1301 	if (ret) {
1302 		rtw89_err(rtwdev, "[ERR]CMAC%d NAV CTRL init %d\n", mac_idx,
1303 			  ret);
1304 		return ret;
1305 	}
1306 
1307 	ret = spatial_reuse_init_be(rtwdev, mac_idx);
1308 	if (ret) {
1309 		rtw89_err(rtwdev, "[ERR]CMAC%d Spatial Reuse init %d\n",
1310 			  mac_idx, ret);
1311 		return ret;
1312 	}
1313 
1314 	ret = tmac_init_be(rtwdev, mac_idx);
1315 	if (ret) {
1316 		rtw89_err(rtwdev, "[ERR]CMAC%d TMAC init %d\n", mac_idx, ret);
1317 		return ret;
1318 	}
1319 
1320 	ret = trxptcl_init_be(rtwdev, mac_idx);
1321 	if (ret) {
1322 		rtw89_err(rtwdev, "[ERR]CMAC%d TRXPTCL init %d\n", mac_idx, ret);
1323 		return ret;
1324 	}
1325 
1326 	ret = rmac_init_be(rtwdev, mac_idx);
1327 	if (ret) {
1328 		rtw89_err(rtwdev, "[ERR]CMAC%d RMAC init %d\n", mac_idx, ret);
1329 		return ret;
1330 	}
1331 
1332 	ret = resp_pktctl_init_be(rtwdev, mac_idx);
1333 	if (ret) {
1334 		rtw89_err(rtwdev, "[ERR]CMAC%d resp pktctl init %d\n", mac_idx, ret);
1335 		return ret;
1336 	}
1337 
1338 	ret = cmac_com_init_be(rtwdev, mac_idx);
1339 	if (ret) {
1340 		rtw89_err(rtwdev, "[ERR]CMAC%d Com init %d\n", mac_idx, ret);
1341 		return ret;
1342 	}
1343 
1344 	ret = ptcl_init_be(rtwdev, mac_idx);
1345 	if (ret) {
1346 		rtw89_err(rtwdev, "[ERR]CMAC%d PTCL init %d\n", mac_idx, ret);
1347 		return ret;
1348 	}
1349 
1350 	ret = cmac_dma_init_be(rtwdev, mac_idx);
1351 	if (ret) {
1352 		rtw89_err(rtwdev, "[ERR]CMAC%d DMA init %d\n", mac_idx, ret);
1353 		return ret;
1354 	}
1355 
1356 	return ret;
1357 }
1358 
1359 static int tx_idle_poll_band_be(struct rtw89_dev *rtwdev, u8 mac_idx)
1360 {
1361 	u32 reg;
1362 	u8 val8;
1363 	int ret;
1364 
1365 	ret = rtw89_mac_check_mac_en(rtwdev, mac_idx, RTW89_CMAC_SEL);
1366 	if (ret)
1367 		return ret;
1368 
1369 	reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_PTCL_TX_CTN_SEL, mac_idx);
1370 
1371 	ret = read_poll_timeout_atomic(rtw89_read8, val8, !(val8 & B_BE_PTCL_BUSY),
1372 				       30, 66000, false, rtwdev, reg);
1373 
1374 	return ret;
1375 }
1376 
1377 static int dle_buf_req_be(struct rtw89_dev *rtwdev, u16 buf_len, bool wd, u16 *pkt_id)
1378 {
1379 	u32 val, reg;
1380 	int ret;
1381 
1382 	reg = wd ? R_BE_WD_BUF_REQ : R_BE_PL_BUF_REQ;
1383 	val = buf_len;
1384 	val |= B_BE_WD_BUF_REQ_EXEC;
1385 	rtw89_write32(rtwdev, reg, val);
1386 
1387 	reg = wd ? R_BE_WD_BUF_STATUS : R_BE_PL_BUF_STATUS;
1388 
1389 	ret = read_poll_timeout(rtw89_read32, val, val & B_BE_WD_BUF_STAT_DONE,
1390 				1, 2000, false, rtwdev, reg);
1391 	if (ret)
1392 		return ret;
1393 
1394 	*pkt_id = u32_get_bits(val, B_BE_WD_BUF_STAT_PKTID_MASK);
1395 	if (*pkt_id == S_WD_BUF_STAT_PKTID_INVALID)
1396 		return -ENOENT;
1397 
1398 	return 0;
1399 }
1400 
1401 static int set_cpuio_be(struct rtw89_dev *rtwdev,
1402 			struct rtw89_cpuio_ctrl *ctrl_para, bool wd)
1403 {
1404 	u32 val_op0, val_op1, val_op2, val_op3;
1405 	u32 val, cmd_type, reg;
1406 	int ret;
1407 
1408 	cmd_type = ctrl_para->cmd_type;
1409 
1410 	reg = wd ? R_BE_WD_CPUQ_OP_3 : R_BE_PL_CPUQ_OP_3;
1411 	val_op3 = u32_replace_bits(0, ctrl_para->start_pktid,
1412 				   B_BE_WD_CPUQ_OP_STRT_PKTID_MASK);
1413 	val_op3 = u32_replace_bits(val_op3, ctrl_para->end_pktid,
1414 				   B_BE_WD_CPUQ_OP_END_PKTID_MASK);
1415 	rtw89_write32(rtwdev, reg, val_op3);
1416 
1417 	reg = wd ? R_BE_WD_CPUQ_OP_1 : R_BE_PL_CPUQ_OP_1;
1418 	val_op1 = u32_replace_bits(0, ctrl_para->src_pid,
1419 				   B_BE_WD_CPUQ_OP_SRC_PID_MASK);
1420 	val_op1 = u32_replace_bits(val_op1, ctrl_para->src_qid,
1421 				   B_BE_WD_CPUQ_OP_SRC_QID_MASK);
1422 	val_op1 = u32_replace_bits(val_op1, ctrl_para->macid,
1423 				   B_BE_WD_CPUQ_OP_SRC_MACID_MASK);
1424 	rtw89_write32(rtwdev, reg, val_op1);
1425 
1426 	reg = wd ? R_BE_WD_CPUQ_OP_2 : R_BE_PL_CPUQ_OP_2;
1427 	val_op2 = u32_replace_bits(0, ctrl_para->dst_pid,
1428 				   B_BE_WD_CPUQ_OP_DST_PID_MASK);
1429 	val_op2 = u32_replace_bits(val_op2, ctrl_para->dst_qid,
1430 				   B_BE_WD_CPUQ_OP_DST_QID_MASK);
1431 	val_op2 = u32_replace_bits(val_op2, ctrl_para->macid,
1432 				   B_BE_WD_CPUQ_OP_DST_MACID_MASK);
1433 	rtw89_write32(rtwdev, reg, val_op2);
1434 
1435 	reg = wd ? R_BE_WD_CPUQ_OP_0 : R_BE_PL_CPUQ_OP_0;
1436 	val_op0 = u32_replace_bits(0, cmd_type,
1437 				   B_BE_WD_CPUQ_OP_CMD_TYPE_MASK);
1438 	val_op0 = u32_replace_bits(val_op0, ctrl_para->pkt_num,
1439 				   B_BE_WD_CPUQ_OP_PKTNUM_MASK);
1440 	val_op0 |= B_BE_WD_CPUQ_OP_EXEC;
1441 	rtw89_write32(rtwdev, reg, val_op0);
1442 
1443 	reg = wd ? R_BE_WD_CPUQ_OP_STATUS : R_BE_PL_CPUQ_OP_STATUS;
1444 
1445 	ret = read_poll_timeout(rtw89_read32, val, val & B_BE_WD_CPUQ_OP_STAT_DONE,
1446 				1, 2000, false, rtwdev, reg);
1447 	if (ret) {
1448 		rtw89_err(rtwdev, "[ERR]set cpuio wd timeout\n");
1449 		rtw89_err(rtwdev, "[ERR]op_0=0x%X, op_1=0x%X, op_2=0x%X\n",
1450 			  val_op0, val_op1, val_op2);
1451 		return ret;
1452 	}
1453 
1454 	if (cmd_type == CPUIO_OP_CMD_GET_NEXT_PID ||
1455 	    cmd_type == CPUIO_OP_CMD_GET_1ST_PID)
1456 		ctrl_para->pktid = u32_get_bits(val, B_BE_WD_CPUQ_OP_PKTID_MASK);
1457 
1458 	return 0;
1459 }
1460 
1461 static int dle_upd_qta_aval_page_be(struct rtw89_dev *rtwdev,
1462 				    enum rtw89_mac_dle_ctrl_type type,
1463 				    enum rtw89_mac_dle_ple_quota_id quota_id)
1464 {
1465 	u32 val;
1466 
1467 	if (type == DLE_CTRL_TYPE_WDE) {
1468 		rtw89_write32_mask(rtwdev, R_BE_WDE_BUFMGN_CTL,
1469 				   B_BE_WDE_AVAL_UPD_QTAID_MASK, quota_id);
1470 		rtw89_write32_set(rtwdev, R_BE_WDE_BUFMGN_CTL, B_BE_WDE_AVAL_UPD_REQ);
1471 
1472 		return read_poll_timeout(rtw89_read32, val,
1473 					 !(val & B_BE_WDE_AVAL_UPD_REQ),
1474 					 1, 2000, false, rtwdev, R_BE_WDE_BUFMGN_CTL);
1475 	} else if (type == DLE_CTRL_TYPE_PLE) {
1476 		rtw89_write32_mask(rtwdev, R_BE_PLE_BUFMGN_CTL,
1477 				   B_BE_PLE_AVAL_UPD_QTAID_MASK, quota_id);
1478 		rtw89_write32_set(rtwdev, R_BE_PLE_BUFMGN_CTL, B_BE_PLE_AVAL_UPD_REQ);
1479 
1480 		return read_poll_timeout(rtw89_read32, val,
1481 					 !(val & B_BE_PLE_AVAL_UPD_REQ),
1482 					 1, 2000, false, rtwdev, R_BE_PLE_BUFMGN_CTL);
1483 	}
1484 
1485 	rtw89_warn(rtwdev, "%s wrong type %d\n", __func__, type);
1486 	return -EINVAL;
1487 }
1488 
1489 static int dle_quota_change_be(struct rtw89_dev *rtwdev, bool band1_en)
1490 {
1491 	int ret;
1492 
1493 	if (band1_en) {
1494 		ret = dle_upd_qta_aval_page_be(rtwdev, DLE_CTRL_TYPE_PLE,
1495 					       PLE_QTAID_B0_TXPL);
1496 		if (ret) {
1497 			rtw89_err(rtwdev, "update PLE B0 TX avail page fail %d\n", ret);
1498 			return ret;
1499 		}
1500 
1501 		ret = dle_upd_qta_aval_page_be(rtwdev, DLE_CTRL_TYPE_PLE,
1502 					       PLE_QTAID_CMAC0_RX);
1503 		if (ret) {
1504 			rtw89_err(rtwdev, "update PLE CMAC0 RX avail page fail %d\n", ret);
1505 			return ret;
1506 		}
1507 	} else {
1508 		ret = dle_upd_qta_aval_page_be(rtwdev, DLE_CTRL_TYPE_PLE,
1509 					       PLE_QTAID_B1_TXPL);
1510 		if (ret) {
1511 			rtw89_err(rtwdev, "update PLE B1 TX avail page fail %d\n", ret);
1512 			return ret;
1513 		}
1514 
1515 		ret = dle_upd_qta_aval_page_be(rtwdev, DLE_CTRL_TYPE_PLE,
1516 					       PLE_QTAID_CMAC1_RX);
1517 		if (ret) {
1518 			rtw89_err(rtwdev, "update PLE CMAC1 RX avail page fail %d\n", ret);
1519 			return ret;
1520 		}
1521 	}
1522 
1523 	return 0;
1524 }
1525 
1526 static int preload_init_be(struct rtw89_dev *rtwdev, u8 mac_idx,
1527 			   enum rtw89_qta_mode mode)
1528 {
1529 	u32 max_preld_size, min_rsvd_size;
1530 	u32 val32;
1531 	u32 reg;
1532 
1533 	max_preld_size = mac_idx == RTW89_MAC_0 ?
1534 			 PRELD_B0_ENT_NUM : PRELD_B1_ENT_NUM;
1535 	max_preld_size *= PRELD_AMSDU_SIZE;
1536 
1537 	reg = mac_idx == RTW89_MAC_0 ? R_BE_TXPKTCTL_B0_PRELD_CFG0 :
1538 				       R_BE_TXPKTCTL_B1_PRELD_CFG0;
1539 	val32 = rtw89_read32(rtwdev, reg);
1540 	val32 = u32_replace_bits(val32, max_preld_size, B_BE_B0_PRELD_USEMAXSZ_MASK);
1541 	val32 |= B_BE_B0_PRELD_FEN;
1542 	rtw89_write32(rtwdev, reg, val32);
1543 
1544 	min_rsvd_size = PRELD_AMSDU_SIZE;
1545 	reg = mac_idx == RTW89_MAC_0 ? R_BE_TXPKTCTL_B0_PRELD_CFG1 :
1546 				       R_BE_TXPKTCTL_B1_PRELD_CFG1;
1547 	val32 = rtw89_read32(rtwdev, reg);
1548 	val32 = u32_replace_bits(val32, PRELD_NEXT_WND, B_BE_B0_PRELD_NXT_TXENDWIN_MASK);
1549 	val32 = u32_replace_bits(val32, min_rsvd_size, B_BE_B0_PRELD_NXT_RSVMINSZ_MASK);
1550 	rtw89_write32(rtwdev, reg, val32);
1551 
1552 	return 0;
1553 }
1554 
1555 static int dbcc_bb_ctrl_be(struct rtw89_dev *rtwdev, bool bb1_en)
1556 {
1557 	u32 set = B_BE_FEN_BB1PLAT_RSTB | B_BE_FEN_BB1_IP_RSTN;
1558 
1559 	if (bb1_en)
1560 		rtw89_write32_set(rtwdev, R_BE_FEN_RST_ENABLE, set);
1561 	else
1562 		rtw89_write32_clr(rtwdev, R_BE_FEN_RST_ENABLE, set);
1563 
1564 	return 0;
1565 }
1566 
1567 static int enable_imr_be(struct rtw89_dev *rtwdev, u8 mac_idx,
1568 			 enum rtw89_mac_hwmod_sel sel)
1569 {
1570 	const struct rtw89_chip_info *chip = rtwdev->chip;
1571 	const struct rtw89_imr_table *table;
1572 	const struct rtw89_reg_imr *reg;
1573 	u32 addr;
1574 	u32 val;
1575 	int i;
1576 
1577 	if (sel == RTW89_DMAC_SEL)
1578 		table = chip->imr_dmac_table;
1579 	else if (sel == RTW89_CMAC_SEL)
1580 		table = chip->imr_cmac_table;
1581 	else
1582 		return -EINVAL;
1583 
1584 	for (i = 0; i < table->n_regs; i++) {
1585 		reg = &table->regs[i];
1586 		addr = rtw89_mac_reg_by_idx(rtwdev, reg->addr, mac_idx);
1587 
1588 		val = rtw89_read32(rtwdev, addr);
1589 		val &= ~reg->clr;
1590 		val |= reg->set;
1591 		rtw89_write32(rtwdev, addr, val);
1592 	}
1593 
1594 	return 0;
1595 }
1596 
1597 static void err_imr_ctrl_be(struct rtw89_dev *rtwdev, bool en)
1598 {
1599 	u32 v32_dmac = en ? DMAC_ERR_IMR_EN : DMAC_ERR_IMR_DIS;
1600 	u32 v32_cmac0 = en ? CMAC0_ERR_IMR_EN : CMAC0_ERR_IMR_DIS;
1601 	u32 v32_cmac1 = en ? CMAC1_ERR_IMR_EN : CMAC1_ERR_IMR_DIS;
1602 
1603 	v32_dmac &= ~B_BE_DMAC_NOTX_ERR_INT_EN;
1604 
1605 	rtw89_write32(rtwdev, R_BE_DMAC_ERR_IMR, v32_dmac);
1606 	rtw89_write32(rtwdev, R_BE_CMAC_ERR_IMR, v32_cmac0);
1607 
1608 	if (rtwdev->dbcc_en)
1609 		rtw89_write32(rtwdev, R_BE_CMAC_ERR_IMR_C1, v32_cmac1);
1610 }
1611 
1612 static int band1_enable_be(struct rtw89_dev *rtwdev)
1613 {
1614 	int ret;
1615 
1616 	ret = tx_idle_poll_band_be(rtwdev, RTW89_MAC_0);
1617 	if (ret) {
1618 		rtw89_err(rtwdev, "[ERR]tx idle poll %d\n", ret);
1619 		return ret;
1620 	}
1621 
1622 	ret = rtw89_mac_dle_quota_change(rtwdev, rtwdev->mac.qta_mode, true);
1623 	if (ret) {
1624 		rtw89_err(rtwdev, "[ERR]DLE quota change %d\n", ret);
1625 		return ret;
1626 	}
1627 
1628 	ret = preload_init_be(rtwdev, RTW89_MAC_1, rtwdev->mac.qta_mode);
1629 	if (ret) {
1630 		rtw89_err(rtwdev, "[ERR]preload init B1 %d\n", ret);
1631 		return ret;
1632 	}
1633 
1634 	ret = cmac_func_en_be(rtwdev, RTW89_MAC_1, true);
1635 	if (ret) {
1636 		rtw89_err(rtwdev, "[ERR]CMAC%d func en %d\n", RTW89_MAC_1, ret);
1637 		return ret;
1638 	}
1639 
1640 	ret = cmac_init_be(rtwdev, RTW89_MAC_1);
1641 	if (ret) {
1642 		rtw89_err(rtwdev, "[ERR]CMAC%d init %d\n", RTW89_MAC_1, ret);
1643 		return ret;
1644 	}
1645 
1646 	ret = dbcc_bb_ctrl_be(rtwdev, true);
1647 	if (ret) {
1648 		rtw89_err(rtwdev, "[ERR]enable bb 1 %d\n", ret);
1649 		return ret;
1650 	}
1651 
1652 	ret = enable_imr_be(rtwdev, RTW89_MAC_1, RTW89_CMAC_SEL);
1653 	if (ret) {
1654 		rtw89_err(rtwdev, "[ERR] enable CMAC1 IMR %d\n", ret);
1655 		return ret;
1656 	}
1657 
1658 	return 0;
1659 }
1660 
1661 static int band1_disable_be(struct rtw89_dev *rtwdev)
1662 {
1663 	int ret;
1664 
1665 	ret = dbcc_bb_ctrl_be(rtwdev, false);
1666 	if (ret) {
1667 		rtw89_err(rtwdev, "[ERR]disable bb 1 %d\n", ret);
1668 		return ret;
1669 	}
1670 
1671 	ret = cmac_func_en_be(rtwdev, RTW89_MAC_1, false);
1672 	if (ret) {
1673 		rtw89_err(rtwdev, "[ERR]CMAC%d func dis %d\n", RTW89_MAC_1, ret);
1674 		return ret;
1675 	}
1676 
1677 	ret = rtw89_mac_dle_quota_change(rtwdev, rtwdev->mac.qta_mode, false);
1678 	if (ret) {
1679 		rtw89_err(rtwdev, "[ERR]DLE quota change %d\n", ret);
1680 		return ret;
1681 	}
1682 
1683 	return 0;
1684 }
1685 
1686 static int dbcc_enable_be(struct rtw89_dev *rtwdev, bool enable)
1687 {
1688 	int ret;
1689 
1690 	if (enable) {
1691 		ret = band1_enable_be(rtwdev);
1692 		if (ret) {
1693 			rtw89_err(rtwdev, "[ERR] band1_enable %d\n", ret);
1694 			return ret;
1695 		}
1696 
1697 		if (test_bit(RTW89_FLAG_FW_RDY, rtwdev->flags)) {
1698 			ret = rtw89_fw_h2c_notify_dbcc(rtwdev, true);
1699 			if (ret) {
1700 				rtw89_err(rtwdev, "%s:[ERR] notify dbcc1 fail %d\n",
1701 					  __func__, ret);
1702 				return ret;
1703 			}
1704 		}
1705 	} else {
1706 		if (test_bit(RTW89_FLAG_FW_RDY, rtwdev->flags)) {
1707 			ret = rtw89_fw_h2c_notify_dbcc(rtwdev, false);
1708 			if (ret) {
1709 				rtw89_err(rtwdev, "%s:[ERR] notify dbcc1 fail %d\n",
1710 					  __func__, ret);
1711 				return ret;
1712 			}
1713 		}
1714 
1715 		ret = band1_disable_be(rtwdev);
1716 		if (ret) {
1717 			rtw89_err(rtwdev, "[ERR] band1_disable %d\n", ret);
1718 			return ret;
1719 		}
1720 	}
1721 
1722 	return 0;
1723 }
1724 
1725 static int set_host_rpr_be(struct rtw89_dev *rtwdev)
1726 {
1727 	u32 val32;
1728 	u32 mode;
1729 	u32 fltr;
1730 	bool poh;
1731 
1732 	poh = is_qta_poh(rtwdev);
1733 
1734 	if (poh) {
1735 		mode = RTW89_RPR_MODE_POH;
1736 		fltr = S_BE_WDRLS_FLTR_TXOK | S_BE_WDRLS_FLTR_RTYLMT |
1737 		       S_BE_WDRLS_FLTR_LIFTIM | S_BE_WDRLS_FLTR_MACID;
1738 	} else {
1739 		mode = RTW89_RPR_MODE_STF;
1740 		fltr = 0;
1741 	}
1742 
1743 	rtw89_write32_mask(rtwdev, R_BE_WDRLS_CFG, B_BE_WDRLS_MODE_MASK, mode);
1744 
1745 	val32 = rtw89_read32(rtwdev, R_BE_RLSRPT0_CFG1);
1746 	val32 = u32_replace_bits(val32, fltr, B_BE_RLSRPT0_FLTR_MAP_MASK);
1747 	val32 = u32_replace_bits(val32, 30, B_BE_RLSRPT0_AGGNUM_MASK);
1748 	val32 = u32_replace_bits(val32, 255, B_BE_RLSRPT0_TO_MASK);
1749 	rtw89_write32(rtwdev, R_BE_RLSRPT0_CFG1, val32);
1750 
1751 	return 0;
1752 }
1753 
1754 static int trx_init_be(struct rtw89_dev *rtwdev)
1755 {
1756 	enum rtw89_core_chip_id chip_id = rtwdev->chip->chip_id;
1757 	enum rtw89_qta_mode qta_mode = rtwdev->mac.qta_mode;
1758 	int ret;
1759 
1760 	ret = dmac_init_be(rtwdev, 0);
1761 	if (ret) {
1762 		rtw89_err(rtwdev, "[ERR]DMAC init %d\n", ret);
1763 		return ret;
1764 	}
1765 
1766 	ret = cmac_init_be(rtwdev, 0);
1767 	if (ret) {
1768 		rtw89_err(rtwdev, "[ERR]CMAC%d init %d\n", 0, ret);
1769 		return ret;
1770 	}
1771 
1772 	if (rtw89_mac_is_qta_dbcc(rtwdev, qta_mode)) {
1773 		ret = dbcc_enable_be(rtwdev, true);
1774 		if (ret) {
1775 			rtw89_err(rtwdev, "[ERR]dbcc_enable init %d\n", ret);
1776 			return ret;
1777 		}
1778 	}
1779 
1780 	ret = enable_imr_be(rtwdev, RTW89_MAC_0, RTW89_DMAC_SEL);
1781 	if (ret) {
1782 		rtw89_err(rtwdev, "[ERR] enable DMAC IMR %d\n", ret);
1783 		return ret;
1784 	}
1785 
1786 	ret = enable_imr_be(rtwdev, RTW89_MAC_0, RTW89_CMAC_SEL);
1787 	if (ret) {
1788 		rtw89_err(rtwdev, "[ERR] to enable CMAC0 IMR %d\n", ret);
1789 		return ret;
1790 	}
1791 
1792 	err_imr_ctrl_be(rtwdev, true);
1793 
1794 	ret = set_host_rpr_be(rtwdev);
1795 	if (ret) {
1796 		rtw89_err(rtwdev, "[ERR] set host rpr %d\n", ret);
1797 		return ret;
1798 	}
1799 
1800 	if (chip_id == RTL8922A)
1801 		rtw89_write32_clr(rtwdev, R_BE_RSP_CHK_SIG,
1802 				  B_BE_RSP_STATIC_RTS_CHK_SERV_BW_EN);
1803 
1804 	return 0;
1805 }
1806 
1807 int rtw89_mac_cfg_gnt_v2(struct rtw89_dev *rtwdev,
1808 			 const struct rtw89_mac_ax_coex_gnt *gnt_cfg)
1809 {
1810 	u32 val = 0;
1811 
1812 	if (gnt_cfg->band[0].gnt_bt)
1813 		val |= B_BE_GNT_BT_BB0_VAL | B_BE_GNT_BT_RX_BB0_VAL |
1814 		       B_BE_GNT_BT_TX_BB0_VAL;
1815 
1816 	if (gnt_cfg->band[0].gnt_bt_sw_en)
1817 		val |= B_BE_GNT_BT_BB0_SWCTRL | B_BE_GNT_BT_RX_BB0_SWCTRL |
1818 		       B_BE_GNT_BT_TX_BB0_SWCTRL;
1819 
1820 	if (gnt_cfg->band[0].gnt_wl)
1821 		val |= B_BE_GNT_WL_BB0_VAL | B_BE_GNT_WL_RX_VAL |
1822 		       B_BE_GNT_WL_TX_VAL | B_BE_GNT_WL_BB_PWR_VAL;
1823 
1824 	if (gnt_cfg->band[0].gnt_wl_sw_en)
1825 		val |= B_BE_GNT_WL_BB0_SWCTRL | B_BE_GNT_WL_RX_SWCTRL |
1826 		       B_BE_GNT_WL_TX_SWCTRL | B_BE_GNT_WL_BB_PWR_SWCTRL;
1827 
1828 	if (gnt_cfg->band[1].gnt_bt)
1829 		val |= B_BE_GNT_BT_BB1_VAL | B_BE_GNT_BT_RX_BB1_VAL |
1830 		       B_BE_GNT_BT_TX_BB1_VAL;
1831 
1832 	if (gnt_cfg->band[1].gnt_bt_sw_en)
1833 		val |= B_BE_GNT_BT_BB1_SWCTRL | B_BE_GNT_BT_RX_BB1_SWCTRL |
1834 		       B_BE_GNT_BT_TX_BB1_SWCTRL;
1835 
1836 	if (gnt_cfg->band[1].gnt_wl)
1837 		val |= B_BE_GNT_WL_BB1_VAL | B_BE_GNT_WL_RX_VAL |
1838 		       B_BE_GNT_WL_TX_VAL | B_BE_GNT_WL_BB_PWR_VAL;
1839 
1840 	if (gnt_cfg->band[1].gnt_wl_sw_en)
1841 		val |= B_BE_GNT_WL_BB1_SWCTRL | B_BE_GNT_WL_RX_SWCTRL |
1842 		       B_BE_GNT_WL_TX_SWCTRL | B_BE_GNT_WL_BB_PWR_SWCTRL;
1843 
1844 	if (gnt_cfg->bt[0].wlan_act_en)
1845 		val |= B_BE_WL_ACT_SWCTRL;
1846 	if (gnt_cfg->bt[0].wlan_act)
1847 		val |= B_BE_WL_ACT_VAL;
1848 	if (gnt_cfg->bt[1].wlan_act_en)
1849 		val |= B_BE_WL_ACT2_SWCTRL;
1850 	if (gnt_cfg->bt[1].wlan_act)
1851 		val |= B_BE_WL_ACT2_VAL;
1852 
1853 	rtw89_write32(rtwdev, R_BE_GNT_SW_CTRL, val);
1854 
1855 	return 0;
1856 }
1857 EXPORT_SYMBOL(rtw89_mac_cfg_gnt_v2);
1858 
1859 int rtw89_mac_cfg_ctrl_path_v2(struct rtw89_dev *rtwdev, bool wl)
1860 {
1861 	struct rtw89_btc *btc = &rtwdev->btc;
1862 	struct rtw89_btc_dm *dm = &btc->dm;
1863 	struct rtw89_mac_ax_gnt *g = dm->gnt.band;
1864 	struct rtw89_mac_ax_wl_act *gbt = dm->gnt.bt;
1865 	int i;
1866 
1867 	if (wl)
1868 		return 0;
1869 
1870 	for (i = 0; i < RTW89_PHY_NUM; i++) {
1871 		g[i].gnt_bt_sw_en = 1;
1872 		g[i].gnt_bt = 1;
1873 		g[i].gnt_wl_sw_en = 1;
1874 		g[i].gnt_wl = 0;
1875 		gbt[i].wlan_act = 1;
1876 		gbt[i].wlan_act_en = 0;
1877 	}
1878 
1879 	return rtw89_mac_cfg_gnt_v2(rtwdev, &dm->gnt);
1880 }
1881 EXPORT_SYMBOL(rtw89_mac_cfg_ctrl_path_v2);
1882 
1883 static
1884 int rtw89_mac_cfg_plt_be(struct rtw89_dev *rtwdev, struct rtw89_mac_ax_plt *plt)
1885 {
1886 	u32 reg;
1887 	u16 val;
1888 	int ret;
1889 
1890 	ret = rtw89_mac_check_mac_en(rtwdev, plt->band, RTW89_CMAC_SEL);
1891 	if (ret)
1892 		return ret;
1893 
1894 	reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_BT_PLT, plt->band);
1895 	val = (plt->tx & RTW89_MAC_AX_PLT_LTE_RX ? B_BE_TX_PLT_GNT_LTE_RX : 0) |
1896 	      (plt->tx & RTW89_MAC_AX_PLT_GNT_BT_TX ? B_BE_TX_PLT_GNT_BT_TX : 0) |
1897 	      (plt->tx & RTW89_MAC_AX_PLT_GNT_BT_RX ? B_BE_TX_PLT_GNT_BT_RX : 0) |
1898 	      (plt->tx & RTW89_MAC_AX_PLT_GNT_WL ? B_BE_TX_PLT_GNT_WL : 0) |
1899 	      (plt->rx & RTW89_MAC_AX_PLT_LTE_RX ? B_BE_RX_PLT_GNT_LTE_RX : 0) |
1900 	      (plt->rx & RTW89_MAC_AX_PLT_GNT_BT_TX ? B_BE_RX_PLT_GNT_BT_TX : 0) |
1901 	      (plt->rx & RTW89_MAC_AX_PLT_GNT_BT_RX ? B_BE_RX_PLT_GNT_BT_RX : 0) |
1902 	      (plt->rx & RTW89_MAC_AX_PLT_GNT_WL ? B_BE_RX_PLT_GNT_WL : 0) |
1903 	      B_BE_PLT_EN;
1904 	rtw89_write16(rtwdev, reg, val);
1905 
1906 	return 0;
1907 }
1908 
1909 static u16 rtw89_mac_get_plt_cnt_be(struct rtw89_dev *rtwdev, u8 band)
1910 {
1911 	u32 reg;
1912 	u16 cnt;
1913 
1914 	reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_BT_PLT, band);
1915 	cnt = rtw89_read32_mask(rtwdev, reg, B_BE_BT_PLT_PKT_CNT_MASK);
1916 	rtw89_write16_set(rtwdev, reg, B_BE_BT_PLT_RST);
1917 
1918 	return cnt;
1919 }
1920 
1921 static int rtw89_set_hw_sch_tx_en_v2(struct rtw89_dev *rtwdev, u8 mac_idx,
1922 				     u32 tx_en, u32 tx_en_mask)
1923 {
1924 	u32 reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_CTN_DRV_TXEN, mac_idx);
1925 	u32 val;
1926 	int ret;
1927 
1928 	ret = rtw89_mac_check_mac_en(rtwdev, mac_idx, RTW89_CMAC_SEL);
1929 	if (ret)
1930 		return ret;
1931 
1932 	val = rtw89_read32(rtwdev, reg);
1933 	val = (val & ~tx_en_mask) | (tx_en & tx_en_mask);
1934 	rtw89_write32(rtwdev, reg, val);
1935 
1936 	return 0;
1937 }
1938 
1939 int rtw89_mac_stop_sch_tx_v2(struct rtw89_dev *rtwdev, u8 mac_idx,
1940 			     u32 *tx_en, enum rtw89_sch_tx_sel sel)
1941 {
1942 	int ret;
1943 
1944 	*tx_en = rtw89_read32(rtwdev,
1945 			      rtw89_mac_reg_by_idx(rtwdev, R_BE_CTN_DRV_TXEN, mac_idx));
1946 
1947 	switch (sel) {
1948 	case RTW89_SCH_TX_SEL_ALL:
1949 		ret = rtw89_set_hw_sch_tx_en_v2(rtwdev, mac_idx, 0,
1950 						B_BE_CTN_TXEN_ALL_MASK);
1951 		if (ret)
1952 			return ret;
1953 		break;
1954 	case RTW89_SCH_TX_SEL_HIQ:
1955 		ret = rtw89_set_hw_sch_tx_en_v2(rtwdev, mac_idx,
1956 						0, B_BE_CTN_TXEN_HGQ);
1957 		if (ret)
1958 			return ret;
1959 		break;
1960 	case RTW89_SCH_TX_SEL_MG0:
1961 		ret = rtw89_set_hw_sch_tx_en_v2(rtwdev, mac_idx,
1962 						0, B_BE_CTN_TXEN_MGQ);
1963 		if (ret)
1964 			return ret;
1965 		break;
1966 	case RTW89_SCH_TX_SEL_MACID:
1967 		ret = rtw89_set_hw_sch_tx_en_v2(rtwdev, mac_idx, 0,
1968 						B_BE_CTN_TXEN_ALL_MASK);
1969 		if (ret)
1970 			return ret;
1971 		break;
1972 	default:
1973 		return 0;
1974 	}
1975 
1976 	return 0;
1977 }
1978 EXPORT_SYMBOL(rtw89_mac_stop_sch_tx_v2);
1979 
1980 int rtw89_mac_resume_sch_tx_v2(struct rtw89_dev *rtwdev, u8 mac_idx, u32 tx_en)
1981 {
1982 	int ret;
1983 
1984 	ret = rtw89_set_hw_sch_tx_en_v2(rtwdev, mac_idx, tx_en,
1985 					B_BE_CTN_TXEN_ALL_MASK);
1986 	if (ret)
1987 		return ret;
1988 
1989 	return 0;
1990 }
1991 EXPORT_SYMBOL(rtw89_mac_resume_sch_tx_v2);
1992 
1993 void rtw89_mac_cfg_phy_rpt_be(struct rtw89_dev *rtwdev, u8 mac_idx, bool enable)
1994 {
1995 	u32 reg, val;
1996 
1997 	reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_RCR, mac_idx);
1998 	val = enable ? MAC_AX_PHY_RPT_SIZE_8 : MAC_AX_PHY_RPT_SIZE_0;
1999 	rtw89_write32_mask(rtwdev, reg, B_BE_PHY_RPT_SZ_MASK, val);
2000 	rtw89_write32_mask(rtwdev, reg, B_BE_HDR_CNV_SZ_MASK, MAC_AX_HDR_CNV_SIZE_0);
2001 
2002 	reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_DRV_INFO_OPTION, mac_idx);
2003 	rtw89_write32_mask(rtwdev, reg, B_BE_DRV_INFO_PHYRPT_EN, enable);
2004 }
2005 EXPORT_SYMBOL(rtw89_mac_cfg_phy_rpt_be);
2006 
2007 static
2008 int rtw89_mac_cfg_ppdu_status_be(struct rtw89_dev *rtwdev, u8 mac_idx, bool enable)
2009 {
2010 	u32 reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_PPDU_STAT, mac_idx);
2011 	int ret;
2012 
2013 	ret = rtw89_mac_check_mac_en(rtwdev, mac_idx, RTW89_CMAC_SEL);
2014 	if (ret)
2015 		return ret;
2016 
2017 	if (!enable) {
2018 		rtw89_write32_clr(rtwdev, reg, B_BE_PPDU_STAT_RPT_EN);
2019 		return 0;
2020 	}
2021 
2022 	rtw89_write32_mask(rtwdev, R_BE_HW_PPDU_STATUS, B_BE_FWD_PPDU_STAT_MASK, 3);
2023 	rtw89_write32(rtwdev, reg, B_BE_PPDU_STAT_RPT_EN | B_BE_PPDU_MAC_INFO |
2024 				   B_BE_APP_RX_CNT_RPT | B_BE_APP_PLCP_HDR_RPT |
2025 				   B_BE_PPDU_STAT_RPT_CRC32 | B_BE_PPDU_STAT_RPT_DMA);
2026 
2027 	return 0;
2028 }
2029 
2030 static bool rtw89_mac_get_txpwr_cr_be(struct rtw89_dev *rtwdev,
2031 				      enum rtw89_phy_idx phy_idx,
2032 				      u32 reg_base, u32 *cr)
2033 {
2034 	enum rtw89_qta_mode mode = rtwdev->mac.qta_mode;
2035 	int ret;
2036 
2037 	ret = rtw89_mac_check_mac_en(rtwdev, (enum rtw89_mac_idx)phy_idx,
2038 				     RTW89_CMAC_SEL);
2039 	if (ret) {
2040 		if (test_bit(RTW89_FLAG_SER_HANDLING, rtwdev->flags))
2041 			return false;
2042 
2043 		rtw89_err(rtwdev, "[TXPWR] check mac enable failed\n");
2044 		return false;
2045 	}
2046 
2047 	if (reg_base < R_BE_PWR_MODULE || reg_base > R_BE_CMAC_FUNC_EN_C1) {
2048 		rtw89_err(rtwdev, "[TXPWR] reg_base=0x%x exceed txpwr cr\n",
2049 			  reg_base);
2050 		return false;
2051 	}
2052 
2053 	*cr = rtw89_mac_reg_by_idx(rtwdev, reg_base, phy_idx);
2054 
2055 	if (*cr >= CMAC1_START_ADDR_BE && *cr <= CMAC1_END_ADDR_BE) {
2056 		if (mode == RTW89_QTA_SCC) {
2057 			rtw89_err(rtwdev,
2058 				  "[TXPWR] addr=0x%x but hw not enable\n",
2059 				  *cr);
2060 			return false;
2061 		}
2062 	}
2063 
2064 	return true;
2065 }
2066 
2067 static int rtw89_mac_init_bfee_be(struct rtw89_dev *rtwdev, u8 mac_idx)
2068 {
2069 	u32 reg;
2070 	u32 val;
2071 	int ret;
2072 
2073 	ret = rtw89_mac_check_mac_en(rtwdev, mac_idx, RTW89_CMAC_SEL);
2074 	if (ret)
2075 		return ret;
2076 
2077 	rtw89_mac_bfee_ctrl(rtwdev, mac_idx, true);
2078 
2079 	reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_TRXPTCL_RESP_CSI_CTRL_0, mac_idx);
2080 	rtw89_write32_set(rtwdev, reg, B_BE_BFMEE_BFPARAM_SEL |
2081 				       B_BE_BFMEE_USE_NSTS |
2082 				       B_BE_BFMEE_CSI_GID_SEL |
2083 				       B_BE_BFMEE_CSI_FORCE_RETE_EN);
2084 	rtw89_write32_mask(rtwdev, reg, B_BE_BFMEE_CSI_RSC_MASK, CSI_RX_BW_CFG);
2085 
2086 	reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_CSIRPT_OPTION, mac_idx);
2087 	rtw89_write32_set(rtwdev, reg, B_BE_CSIPRT_VHTSU_AID_EN |
2088 				       B_BE_CSIPRT_HESU_AID_EN |
2089 				       B_BE_CSIPRT_EHTSU_AID_EN);
2090 
2091 	reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_TRXPTCL_RESP_CSI_RRSC, mac_idx);
2092 	rtw89_write32(rtwdev, reg, CSI_RRSC_BMAP_BE);
2093 
2094 	reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_TRXPTCL_RESP_CSI_CTRL_1, mac_idx);
2095 	rtw89_write32_mask(rtwdev, reg, B_BE_BFMEE_BE_CSI_RRSC_BITMAP_MASK,
2096 			   CSI_RRSC_BITMAP_CFG);
2097 
2098 	reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_TRXPTCL_RESP_CSI_RATE, mac_idx);
2099 	val = u32_encode_bits(CSI_INIT_RATE_HT, B_BE_BFMEE_HT_CSI_RATE_MASK) |
2100 	      u32_encode_bits(CSI_INIT_RATE_VHT, B_BE_BFMEE_VHT_CSI_RATE_MASK) |
2101 	      u32_encode_bits(CSI_INIT_RATE_HE, B_BE_BFMEE_HE_CSI_RATE_MASK) |
2102 	      u32_encode_bits(CSI_INIT_RATE_EHT, B_BE_BFMEE_EHT_CSI_RATE_MASK);
2103 
2104 	rtw89_write32(rtwdev, reg, val);
2105 
2106 	return 0;
2107 }
2108 
2109 static int rtw89_mac_set_csi_para_reg_be(struct rtw89_dev *rtwdev,
2110 					 struct rtw89_vif_link *rtwvif_link,
2111 					 struct rtw89_sta_link *rtwsta_link)
2112 {
2113 	u8 nc = 1, nr = 3, ng = 0, cb = 1, cs = 1, ldpc_en = 1, stbc_en = 1;
2114 	struct ieee80211_link_sta *link_sta;
2115 	u8 mac_idx = rtwvif_link->mac_idx;
2116 	u8 port_sel = rtwvif_link->port;
2117 	u8 sound_dim = 3, t;
2118 	u8 *phy_cap;
2119 	u32 reg;
2120 	u16 val;
2121 	int ret;
2122 
2123 	ret = rtw89_mac_check_mac_en(rtwdev, mac_idx, RTW89_CMAC_SEL);
2124 	if (ret)
2125 		return ret;
2126 
2127 	rcu_read_lock();
2128 
2129 	link_sta = rtw89_sta_rcu_dereference_link(rtwsta_link, true);
2130 	phy_cap = link_sta->he_cap.he_cap_elem.phy_cap_info;
2131 
2132 	if ((phy_cap[3] & IEEE80211_HE_PHY_CAP3_SU_BEAMFORMER) ||
2133 	    (phy_cap[4] & IEEE80211_HE_PHY_CAP4_MU_BEAMFORMER)) {
2134 		ldpc_en &= !!(phy_cap[1] & IEEE80211_HE_PHY_CAP1_LDPC_CODING_IN_PAYLOAD);
2135 		stbc_en &= !!(phy_cap[2] & IEEE80211_HE_PHY_CAP2_STBC_RX_UNDER_80MHZ);
2136 		t = u8_get_bits(phy_cap[5],
2137 				IEEE80211_HE_PHY_CAP5_BEAMFORMEE_NUM_SND_DIM_UNDER_80MHZ_MASK);
2138 		sound_dim = min(sound_dim, t);
2139 	}
2140 
2141 	if ((link_sta->vht_cap.cap & IEEE80211_VHT_CAP_MU_BEAMFORMER_CAPABLE) ||
2142 	    (link_sta->vht_cap.cap & IEEE80211_VHT_CAP_SU_BEAMFORMER_CAPABLE)) {
2143 		ldpc_en &= !!(link_sta->vht_cap.cap & IEEE80211_VHT_CAP_RXLDPC);
2144 		stbc_en &= !!(link_sta->vht_cap.cap & IEEE80211_VHT_CAP_RXSTBC_MASK);
2145 		t = u32_get_bits(link_sta->vht_cap.cap,
2146 				 IEEE80211_VHT_CAP_SOUNDING_DIMENSIONS_MASK);
2147 		sound_dim = min(sound_dim, t);
2148 	}
2149 
2150 	nc = min(nc, sound_dim);
2151 	nr = min(nr, sound_dim);
2152 
2153 	rcu_read_unlock();
2154 
2155 	reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_TRXPTCL_RESP_CSI_CTRL_0, mac_idx);
2156 	rtw89_write32_set(rtwdev, reg, B_BE_BFMEE_BFPARAM_SEL);
2157 
2158 	val = u16_encode_bits(nc, B_BE_BFMEE_CSIINFO0_NC_MASK) |
2159 	      u16_encode_bits(nr, B_BE_BFMEE_CSIINFO0_NR_MASK) |
2160 	      u16_encode_bits(ng, B_BE_BFMEE_CSIINFO0_NG_MASK) |
2161 	      u16_encode_bits(cb, B_BE_BFMEE_CSIINFO0_CB_MASK) |
2162 	      u16_encode_bits(cs, B_BE_BFMEE_CSIINFO0_CS_MASK) |
2163 	      u16_encode_bits(ldpc_en, B_BE_BFMEE_CSIINFO0_LDPC_EN) |
2164 	      u16_encode_bits(stbc_en, B_BE_BFMEE_CSIINFO0_STBC_EN);
2165 
2166 	if (port_sel == 0)
2167 		reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_TRXPTCL_RESP_CSI_CTRL_0,
2168 					   mac_idx);
2169 	else
2170 		reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_TRXPTCL_RESP_CSI_CTRL_1,
2171 					   mac_idx);
2172 
2173 	rtw89_write16(rtwdev, reg, val);
2174 
2175 	return 0;
2176 }
2177 
2178 static int rtw89_mac_csi_rrsc_be(struct rtw89_dev *rtwdev,
2179 				 struct rtw89_vif_link *rtwvif_link,
2180 				 struct rtw89_sta_link *rtwsta_link)
2181 {
2182 	u32 rrsc = BIT(RTW89_MAC_BF_RRSC_6M) | BIT(RTW89_MAC_BF_RRSC_24M);
2183 	struct ieee80211_link_sta *link_sta;
2184 	u8 mac_idx = rtwvif_link->mac_idx;
2185 	int ret;
2186 	u32 reg;
2187 
2188 	ret = rtw89_mac_check_mac_en(rtwdev, mac_idx, RTW89_CMAC_SEL);
2189 	if (ret)
2190 		return ret;
2191 
2192 	rcu_read_lock();
2193 
2194 	link_sta = rtw89_sta_rcu_dereference_link(rtwsta_link, true);
2195 
2196 	if (link_sta->he_cap.has_he) {
2197 		rrsc |= (BIT(RTW89_MAC_BF_RRSC_HE_MSC0) |
2198 			 BIT(RTW89_MAC_BF_RRSC_HE_MSC3) |
2199 			 BIT(RTW89_MAC_BF_RRSC_HE_MSC5));
2200 	}
2201 	if (link_sta->vht_cap.vht_supported) {
2202 		rrsc |= (BIT(RTW89_MAC_BF_RRSC_VHT_MSC0) |
2203 			 BIT(RTW89_MAC_BF_RRSC_VHT_MSC3) |
2204 			 BIT(RTW89_MAC_BF_RRSC_VHT_MSC5));
2205 	}
2206 	if (link_sta->ht_cap.ht_supported) {
2207 		rrsc |= (BIT(RTW89_MAC_BF_RRSC_HT_MSC0) |
2208 			 BIT(RTW89_MAC_BF_RRSC_HT_MSC3) |
2209 			 BIT(RTW89_MAC_BF_RRSC_HT_MSC5));
2210 	}
2211 
2212 	rcu_read_unlock();
2213 
2214 	reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_TRXPTCL_RESP_CSI_CTRL_0, mac_idx);
2215 	rtw89_write32_set(rtwdev, reg, B_BE_BFMEE_BFPARAM_SEL);
2216 	rtw89_write32_clr(rtwdev, reg, B_BE_BFMEE_CSI_FORCE_RETE_EN);
2217 
2218 	reg = rtw89_mac_reg_by_idx(rtwdev, R_BE_TRXPTCL_RESP_CSI_RRSC, mac_idx);
2219 	rtw89_write32(rtwdev, reg, rrsc);
2220 
2221 	return 0;
2222 }
2223 
2224 static void rtw89_mac_bf_assoc_be(struct rtw89_dev *rtwdev,
2225 				  struct rtw89_vif_link *rtwvif_link,
2226 				  struct rtw89_sta_link *rtwsta_link)
2227 {
2228 	struct ieee80211_link_sta *link_sta;
2229 	bool has_beamformer_cap;
2230 
2231 	rcu_read_lock();
2232 
2233 	link_sta = rtw89_sta_rcu_dereference_link(rtwsta_link, true);
2234 	has_beamformer_cap = rtw89_sta_has_beamformer_cap(link_sta);
2235 
2236 	rcu_read_unlock();
2237 
2238 	if (has_beamformer_cap) {
2239 		rtw89_debug(rtwdev, RTW89_DBG_BF,
2240 			    "initialize bfee for new association\n");
2241 		rtw89_mac_init_bfee_be(rtwdev, rtwvif_link->mac_idx);
2242 		rtw89_mac_set_csi_para_reg_be(rtwdev, rtwvif_link, rtwsta_link);
2243 		rtw89_mac_csi_rrsc_be(rtwdev, rtwvif_link, rtwsta_link);
2244 	}
2245 }
2246 
2247 static void dump_err_status_dispatcher_be(struct rtw89_dev *rtwdev)
2248 {
2249 	rtw89_info(rtwdev, "R_BE_DISP_HOST_IMR=0x%08x ",
2250 		   rtw89_read32(rtwdev, R_BE_DISP_HOST_IMR));
2251 	rtw89_info(rtwdev, "R_BE_DISP_ERROR_ISR1=0x%08x\n",
2252 		   rtw89_read32(rtwdev, R_BE_DISP_ERROR_ISR1));
2253 	rtw89_info(rtwdev, "R_BE_DISP_CPU_IMR=0x%08x ",
2254 		   rtw89_read32(rtwdev, R_BE_DISP_CPU_IMR));
2255 	rtw89_info(rtwdev, "R_BE_DISP_ERROR_ISR2=0x%08x\n",
2256 		   rtw89_read32(rtwdev, R_BE_DISP_ERROR_ISR2));
2257 	rtw89_info(rtwdev, "R_BE_DISP_OTHER_IMR=0x%08x ",
2258 		   rtw89_read32(rtwdev, R_BE_DISP_OTHER_IMR));
2259 	rtw89_info(rtwdev, "R_BE_DISP_ERROR_ISR0=0x%08x\n",
2260 		   rtw89_read32(rtwdev, R_BE_DISP_ERROR_ISR0));
2261 }
2262 
2263 static void rtw89_mac_dump_qta_lost_be(struct rtw89_dev *rtwdev)
2264 {
2265 	struct rtw89_mac_dle_dfi_qempty qempty;
2266 	struct rtw89_mac_dle_dfi_quota quota;
2267 	struct rtw89_mac_dle_dfi_ctrl ctrl;
2268 	u32 val, not_empty, i;
2269 	int ret;
2270 
2271 	qempty.dle_type = DLE_CTRL_TYPE_PLE;
2272 	qempty.grpsel = 0;
2273 	qempty.qempty = ~(u32)0;
2274 	ret = rtw89_mac_dle_dfi_qempty_cfg(rtwdev, &qempty);
2275 	if (ret)
2276 		rtw89_warn(rtwdev, "%s: query DLE fail\n", __func__);
2277 	else
2278 		rtw89_info(rtwdev, "DLE group0 empty: 0x%x\n", qempty.qempty);
2279 
2280 	for (not_empty = ~qempty.qempty, i = 0; not_empty != 0; not_empty >>= 1, i++) {
2281 		if (!(not_empty & BIT(0)))
2282 			continue;
2283 		ctrl.type = DLE_CTRL_TYPE_PLE;
2284 		ctrl.target = DLE_DFI_TYPE_QLNKTBL;
2285 		ctrl.addr = (QLNKTBL_ADDR_INFO_SEL_0 ? QLNKTBL_ADDR_INFO_SEL : 0) |
2286 			    u32_encode_bits(i, QLNKTBL_ADDR_TBL_IDX_MASK);
2287 		ret = rtw89_mac_dle_dfi_cfg(rtwdev, &ctrl);
2288 		if (ret)
2289 			rtw89_warn(rtwdev, "%s: query DLE fail\n", __func__);
2290 		else
2291 			rtw89_info(rtwdev, "qidx%d pktcnt = %d\n", i,
2292 				   u32_get_bits(ctrl.out_data,
2293 						QLNKTBL_DATA_SEL1_PKT_CNT_MASK));
2294 	}
2295 
2296 	quota.dle_type = DLE_CTRL_TYPE_PLE;
2297 	quota.qtaid = 6;
2298 	ret = rtw89_mac_dle_dfi_quota_cfg(rtwdev, &quota);
2299 	if (ret)
2300 		rtw89_warn(rtwdev, "%s: query DLE fail\n", __func__);
2301 	else
2302 		rtw89_info(rtwdev, "quota6 rsv/use: 0x%x/0x%x\n",
2303 			   quota.rsv_pgnum, quota.use_pgnum);
2304 
2305 	val = rtw89_read32(rtwdev, R_BE_PLE_QTA6_CFG);
2306 	rtw89_info(rtwdev, "[PLE][CMAC0_RX]min_pgnum=0x%x\n",
2307 		   u32_get_bits(val, B_BE_PLE_Q6_MIN_SIZE_MASK));
2308 	rtw89_info(rtwdev, "[PLE][CMAC0_RX]max_pgnum=0x%x\n",
2309 		   u32_get_bits(val, B_BE_PLE_Q6_MAX_SIZE_MASK));
2310 	val = rtw89_read32(rtwdev, R_BE_RX_FLTR_OPT);
2311 	rtw89_info(rtwdev, "[PLE][CMAC0_RX]B_BE_RX_MPDU_MAX_LEN=0x%x\n",
2312 		   u32_get_bits(val, B_BE_RX_MPDU_MAX_LEN_MASK));
2313 	rtw89_info(rtwdev, "R_BE_RSP_CHK_SIG=0x%08x\n",
2314 		   rtw89_read32(rtwdev, R_BE_RSP_CHK_SIG));
2315 	rtw89_info(rtwdev, "R_BE_TRXPTCL_RESP_0=0x%08x\n",
2316 		   rtw89_read32(rtwdev, R_BE_TRXPTCL_RESP_0));
2317 
2318 	if (!rtw89_mac_check_mac_en(rtwdev, RTW89_MAC_1, RTW89_CMAC_SEL)) {
2319 		quota.dle_type = DLE_CTRL_TYPE_PLE;
2320 		quota.qtaid = 7;
2321 		ret = rtw89_mac_dle_dfi_quota_cfg(rtwdev, &quota);
2322 		if (ret)
2323 			rtw89_warn(rtwdev, "%s: query DLE fail\n", __func__);
2324 		else
2325 			rtw89_info(rtwdev, "quota7 rsv/use: 0x%x/0x%x\n",
2326 				   quota.rsv_pgnum, quota.use_pgnum);
2327 
2328 		val = rtw89_read32(rtwdev, R_BE_PLE_QTA7_CFG);
2329 		rtw89_info(rtwdev, "[PLE][CMAC1_RX]min_pgnum=0x%x\n",
2330 			   u32_get_bits(val, B_BE_PLE_Q7_MIN_SIZE_MASK));
2331 		rtw89_info(rtwdev, "[PLE][CMAC1_RX]max_pgnum=0x%x\n",
2332 			   u32_get_bits(val, B_BE_PLE_Q7_MAX_SIZE_MASK));
2333 		val = rtw89_read32(rtwdev, R_BE_RX_FLTR_OPT_C1);
2334 		rtw89_info(rtwdev, "[PLE][CMAC1_RX]B_BE_RX_MPDU_MAX_LEN=0x%x\n",
2335 			   u32_get_bits(val, B_BE_RX_MPDU_MAX_LEN_MASK));
2336 		rtw89_info(rtwdev, "R_BE_RSP_CHK_SIG_C1=0x%08x\n",
2337 			   rtw89_read32(rtwdev, R_BE_RSP_CHK_SIG_C1));
2338 		rtw89_info(rtwdev, "R_BE_TRXPTCL_RESP_0_C1=0x%08x\n",
2339 			   rtw89_read32(rtwdev, R_BE_TRXPTCL_RESP_0_C1));
2340 	}
2341 
2342 	rtw89_info(rtwdev, "R_BE_DLE_EMPTY0=0x%08x\n",
2343 		   rtw89_read32(rtwdev, R_BE_DLE_EMPTY0));
2344 	rtw89_info(rtwdev, "R_BE_DLE_EMPTY1=0x%08x\n",
2345 		   rtw89_read32(rtwdev, R_BE_DLE_EMPTY1));
2346 
2347 	dump_err_status_dispatcher_be(rtwdev);
2348 }
2349 
2350 static int rtw89_wow_config_mac_be(struct rtw89_dev *rtwdev, bool enable_wow)
2351 {
2352 	if (enable_wow) {
2353 		rtw89_write32_set(rtwdev, R_BE_RX_STOP, B_BE_HOST_RX_STOP);
2354 		rtw89_write32_clr(rtwdev, R_BE_RX_FLTR_OPT, B_BE_SNIFFER_MODE);
2355 		rtw89_mac_cpu_io_rx(rtwdev, enable_wow);
2356 		rtw89_mac_cfg_ppdu_status(rtwdev, RTW89_MAC_0, false);
2357 		rtw89_write32(rtwdev, R_BE_FWD_ERR, 0);
2358 		rtw89_write32(rtwdev, R_BE_FWD_ACTN0, 0);
2359 		rtw89_write32(rtwdev, R_BE_FWD_ACTN1, 0);
2360 		rtw89_write32(rtwdev, R_BE_FWD_ACTN2, 0);
2361 		rtw89_write32(rtwdev, R_BE_FWD_TF0, 0);
2362 		rtw89_write32(rtwdev, R_BE_FWD_TF1, 0);
2363 		rtw89_write32(rtwdev, R_BE_FWD_ERR, 0);
2364 		rtw89_write32(rtwdev, R_BE_HW_PPDU_STATUS, 0);
2365 		rtw89_write8(rtwdev, R_BE_DBG_WOW_READY, WOWLAN_NOT_READY);
2366 	} else {
2367 		rtw89_mac_cpu_io_rx(rtwdev, enable_wow);
2368 		rtw89_write32_clr(rtwdev, R_BE_RX_STOP, B_BE_HOST_RX_STOP);
2369 		rtw89_write32_set(rtwdev, R_BE_RX_FLTR_OPT, R_BE_RX_FLTR_OPT);
2370 		rtw89_mac_cfg_ppdu_status(rtwdev, RTW89_MAC_0, true);
2371 	}
2372 
2373 	return 0;
2374 }
2375 
2376 static void rtw89_mac_dump_cmac_err_status_be(struct rtw89_dev *rtwdev,
2377 					      u8 band)
2378 {
2379 	u32 offset = 0;
2380 	u32 cmac_err;
2381 	int ret;
2382 
2383 	ret = rtw89_mac_check_mac_en(rtwdev, band, RTW89_CMAC_SEL);
2384 	if (ret) {
2385 		rtw89_info(rtwdev, "[CMAC] : CMAC%d not enabled\n", band);
2386 		return;
2387 	}
2388 
2389 	if (band)
2390 		offset = RTW89_MAC_BE_BAND_REG_OFFSET;
2391 
2392 	cmac_err = rtw89_read32(rtwdev, R_BE_CMAC_ERR_ISR + offset);
2393 	rtw89_info(rtwdev, "R_BE_CMAC_ERR_ISR [%d]=0x%08x\n", band,
2394 		   rtw89_read32(rtwdev, R_BE_CMAC_ERR_ISR + offset));
2395 	rtw89_info(rtwdev, "R_BE_CMAC_FUNC_EN [%d]=0x%08x\n", band,
2396 		   rtw89_read32(rtwdev, R_BE_CMAC_FUNC_EN + offset));
2397 	rtw89_info(rtwdev, "R_BE_CK_EN [%d]=0x%08x\n", band,
2398 		   rtw89_read32(rtwdev, R_BE_CK_EN + offset));
2399 
2400 	if (cmac_err & B_BE_SCHEDULE_TOP_ERR_IND) {
2401 		rtw89_info(rtwdev, "R_BE_SCHEDULE_ERR_IMR [%d]=0x%08x\n", band,
2402 			   rtw89_read32(rtwdev, R_BE_SCHEDULE_ERR_IMR + offset));
2403 		rtw89_info(rtwdev, "R_BE_SCHEDULE_ERR_ISR [%d]=0x%08x\n", band,
2404 			   rtw89_read32(rtwdev, R_BE_SCHEDULE_ERR_ISR + offset));
2405 	}
2406 
2407 	if (cmac_err & B_BE_PTCL_TOP_ERR_IND) {
2408 		rtw89_info(rtwdev, "R_BE_PTCL_IMR0 [%d]=0x%08x\n", band,
2409 			   rtw89_read32(rtwdev, R_BE_PTCL_IMR0 + offset));
2410 		rtw89_info(rtwdev, "R_BE_PTCL_ISR0 [%d]=0x%08x\n", band,
2411 			   rtw89_read32(rtwdev, R_BE_PTCL_ISR0 + offset));
2412 		rtw89_info(rtwdev, "R_BE_PTCL_IMR1 [%d]=0x%08x\n", band,
2413 			   rtw89_read32(rtwdev, R_BE_PTCL_IMR1 + offset));
2414 		rtw89_info(rtwdev, "R_BE_PTCL_ISR1 [%d]=0x%08x\n", band,
2415 			   rtw89_read32(rtwdev, R_BE_PTCL_ISR1 + offset));
2416 	}
2417 
2418 	if (cmac_err & B_BE_DMA_TOP_ERR_IND) {
2419 		rtw89_info(rtwdev, "R_BE_RX_ERROR_FLAG_IMR [%d]=0x%08x\n", band,
2420 			   rtw89_read32(rtwdev, R_BE_RX_ERROR_FLAG_IMR + offset));
2421 		rtw89_info(rtwdev, "R_BE_RX_ERROR_FLAG [%d]=0x%08x\n", band,
2422 			   rtw89_read32(rtwdev, R_BE_RX_ERROR_FLAG + offset));
2423 		rtw89_info(rtwdev, "R_BE_TX_ERROR_FLAG_IMR [%d]=0x%08x\n", band,
2424 			   rtw89_read32(rtwdev, R_BE_TX_ERROR_FLAG_IMR + offset));
2425 		rtw89_info(rtwdev, "R_BE_TX_ERROR_FLAG [%d]=0x%08x\n", band,
2426 			   rtw89_read32(rtwdev, R_BE_TX_ERROR_FLAG + offset));
2427 		rtw89_info(rtwdev, "R_BE_RX_ERROR_FLAG_IMR_1 [%d]=0x%08x\n", band,
2428 			   rtw89_read32(rtwdev, R_BE_RX_ERROR_FLAG_IMR_1 + offset));
2429 		rtw89_info(rtwdev, "R_BE_RX_ERROR_FLAG_1 [%d]=0x%08x\n", band,
2430 			   rtw89_read32(rtwdev, R_BE_RX_ERROR_FLAG_1 + offset));
2431 	}
2432 
2433 	if (cmac_err & B_BE_PHYINTF_ERR_IND) {
2434 		rtw89_info(rtwdev, "R_BE_PHYINFO_ERR_IMR [%d]=0x%08x\n", band,
2435 			   rtw89_read32(rtwdev, R_BE_PHYINFO_ERR_IMR_V1 + offset));
2436 		rtw89_info(rtwdev, "R_BE_PHYINFO_ERR_ISR [%d]=0x%08x\n", band,
2437 			   rtw89_read32(rtwdev, R_BE_PHYINFO_ERR_ISR + offset));
2438 	}
2439 
2440 	if (cmac_err & B_AX_TXPWR_CTRL_ERR_IND) {
2441 		rtw89_info(rtwdev, "R_BE_TXPWR_ERR_FLAG [%d]=0x%08x\n", band,
2442 			   rtw89_read32(rtwdev, R_BE_TXPWR_ERR_FLAG + offset));
2443 		rtw89_info(rtwdev, "R_BE_TXPWR_ERR_IMR [%d]=0x%08x\n", band,
2444 			   rtw89_read32(rtwdev, R_BE_TXPWR_ERR_IMR + offset));
2445 	}
2446 
2447 	if (cmac_err & (B_BE_WMAC_RX_ERR_IND | B_BE_WMAC_TX_ERR_IND |
2448 			B_BE_WMAC_RX_IDLETO_IDCT | B_BE_PTCL_TX_IDLETO_IDCT)) {
2449 		rtw89_info(rtwdev, "R_BE_DBGSEL_TRXPTCL [%d]=0x%08x\n", band,
2450 			   rtw89_read32(rtwdev, R_BE_DBGSEL_TRXPTCL + offset));
2451 		rtw89_info(rtwdev, "R_BE_TRXPTCL_ERROR_INDICA_MASK [%d]=0x%08x\n", band,
2452 			   rtw89_read32(rtwdev, R_BE_TRXPTCL_ERROR_INDICA_MASK + offset));
2453 		rtw89_info(rtwdev, "R_BE_TRXPTCL_ERROR_INDICA [%d]=0x%08x\n", band,
2454 			   rtw89_read32(rtwdev, R_BE_TRXPTCL_ERROR_INDICA + offset));
2455 		rtw89_info(rtwdev, "R_BE_RX_ERR_IMR [%d]=0x%08x\n", band,
2456 			   rtw89_read32(rtwdev, R_BE_RX_ERR_IMR + offset));
2457 		rtw89_info(rtwdev, "R_BE_RX_ERR_ISR [%d]=0x%08x\n", band,
2458 			   rtw89_read32(rtwdev, R_BE_RX_ERR_ISR + offset));
2459 	}
2460 
2461 	rtw89_info(rtwdev, "R_BE_CMAC_ERR_IMR [%d]=0x%08x\n", band,
2462 		   rtw89_read32(rtwdev, R_BE_CMAC_ERR_IMR + offset));
2463 }
2464 
2465 static void rtw89_mac_dump_err_status_be(struct rtw89_dev *rtwdev,
2466 					 enum mac_ax_err_info err)
2467 {
2468 	if (err != MAC_AX_ERR_L1_ERR_DMAC &&
2469 	    err != MAC_AX_ERR_L0_PROMOTE_TO_L1 &&
2470 	    err != MAC_AX_ERR_L0_ERR_CMAC0 &&
2471 	    err != MAC_AX_ERR_L0_ERR_CMAC1 &&
2472 	    err != MAC_AX_ERR_RXI300)
2473 		return;
2474 
2475 	rtw89_info(rtwdev, "--->\nerr=0x%x\n", err);
2476 	rtw89_info(rtwdev, "R_BE_SER_DBG_INFO=0x%08x\n",
2477 		   rtw89_read32(rtwdev, R_BE_SER_DBG_INFO));
2478 	rtw89_info(rtwdev, "R_BE_SER_L0_DBG_CNT=0x%08x\n",
2479 		   rtw89_read32(rtwdev, R_BE_SER_L0_DBG_CNT));
2480 	rtw89_info(rtwdev, "R_BE_SER_L0_DBG_CNT1=0x%08x\n",
2481 		   rtw89_read32(rtwdev, R_BE_SER_L0_DBG_CNT1));
2482 	rtw89_info(rtwdev, "R_BE_SER_L0_DBG_CNT2=0x%08x\n",
2483 		   rtw89_read32(rtwdev, R_BE_SER_L0_DBG_CNT2));
2484 	rtw89_info(rtwdev, "R_BE_SER_L0_DBG_CNT3=0x%08x\n",
2485 		   rtw89_read32(rtwdev, R_BE_SER_L0_DBG_CNT3));
2486 	if (!rtw89_mac_check_mac_en(rtwdev, RTW89_MAC_1, RTW89_CMAC_SEL)) {
2487 		rtw89_info(rtwdev, "R_BE_SER_L0_DBG_CNT_C1=0x%08x\n",
2488 			   rtw89_read32(rtwdev, R_BE_SER_L0_DBG_CNT_C1));
2489 		rtw89_info(rtwdev, "R_BE_SER_L0_DBG_CNT1_C1=0x%08x\n",
2490 			   rtw89_read32(rtwdev, R_BE_SER_L0_DBG_CNT1_C1));
2491 	}
2492 	rtw89_info(rtwdev, "R_BE_SER_L1_DBG_CNT_0=0x%08x\n",
2493 		   rtw89_read32(rtwdev, R_BE_SER_L1_DBG_CNT_0));
2494 	rtw89_info(rtwdev, "R_BE_SER_L1_DBG_CNT_1=0x%08x\n",
2495 		   rtw89_read32(rtwdev, R_BE_SER_L1_DBG_CNT_1));
2496 	rtw89_info(rtwdev, "R_BE_SER_L1_DBG_CNT_2=0x%08x\n",
2497 		   rtw89_read32(rtwdev, R_BE_SER_L1_DBG_CNT_2));
2498 	rtw89_info(rtwdev, "R_BE_SER_L1_DBG_CNT_3=0x%08x\n",
2499 		   rtw89_read32(rtwdev, R_BE_SER_L1_DBG_CNT_3));
2500 	rtw89_info(rtwdev, "R_BE_SER_L1_DBG_CNT_4=0x%08x\n",
2501 		   rtw89_read32(rtwdev, R_BE_SER_L1_DBG_CNT_4));
2502 	rtw89_info(rtwdev, "R_BE_SER_L1_DBG_CNT_5=0x%08x\n",
2503 		   rtw89_read32(rtwdev, R_BE_SER_L1_DBG_CNT_5));
2504 	rtw89_info(rtwdev, "R_BE_SER_L1_DBG_CNT_6=0x%08x\n",
2505 		   rtw89_read32(rtwdev, R_BE_SER_L1_DBG_CNT_6));
2506 	rtw89_info(rtwdev, "R_BE_SER_L1_DBG_CNT_7=0x%08x\n",
2507 		   rtw89_read32(rtwdev, R_BE_SER_L1_DBG_CNT_7));
2508 
2509 	rtw89_mac_dump_dmac_err_status(rtwdev);
2510 	rtw89_mac_dump_cmac_err_status_be(rtwdev, RTW89_MAC_0);
2511 	rtw89_mac_dump_cmac_err_status_be(rtwdev, RTW89_MAC_1);
2512 
2513 	rtwdev->hci.ops->dump_err_status(rtwdev);
2514 
2515 	if (err == MAC_AX_ERR_L0_PROMOTE_TO_L1)
2516 		rtw89_mac_dump_l0_to_l1(rtwdev, err);
2517 
2518 	rtw89_info(rtwdev, "<---\n");
2519 }
2520 
2521 static bool mac_is_txq_empty_be(struct rtw89_dev *rtwdev)
2522 {
2523 	struct rtw89_mac_dle_dfi_qempty qempty;
2524 	u32 val32, msk32;
2525 	u32 grpnum;
2526 	int ret;
2527 	int i;
2528 
2529 	grpnum = rtwdev->chip->wde_qempty_acq_grpnum;
2530 	qempty.dle_type = DLE_CTRL_TYPE_WDE;
2531 
2532 	for (i = 0; i < grpnum; i++) {
2533 		qempty.grpsel = i;
2534 		ret = rtw89_mac_dle_dfi_qempty_cfg(rtwdev, &qempty);
2535 		if (ret) {
2536 			rtw89_warn(rtwdev,
2537 				   "%s: failed to dle dfi acq empty: %d\n",
2538 				   __func__, ret);
2539 			return false;
2540 		}
2541 
2542 		/* Each acq group contains 32 queues (8 macid * 4 acq),
2543 		 * but here, we can simply check if all bits are set.
2544 		 */
2545 		if (qempty.qempty != MASKDWORD)
2546 			return false;
2547 	}
2548 
2549 	qempty.grpsel = rtwdev->chip->wde_qempty_mgq_grpsel;
2550 	ret = rtw89_mac_dle_dfi_qempty_cfg(rtwdev, &qempty);
2551 	if (ret) {
2552 		rtw89_warn(rtwdev, "%s: failed to dle dfi mgq empty: %d\n",
2553 			   __func__, ret);
2554 		return false;
2555 	}
2556 
2557 	msk32 = B_CMAC0_MGQ_NORMAL_BE | B_CMAC1_MGQ_NORMAL_BE;
2558 	if ((qempty.qempty & msk32) != msk32)
2559 		return false;
2560 
2561 	msk32 = B_BE_WDE_EMPTY_QUE_OTHERS;
2562 	val32 = rtw89_read32(rtwdev, R_BE_DLE_EMPTY0);
2563 	return (val32 & msk32) == msk32;
2564 }
2565 
2566 const struct rtw89_mac_gen_def rtw89_mac_gen_be = {
2567 	.band1_offset = RTW89_MAC_BE_BAND_REG_OFFSET,
2568 	.filter_model_addr = R_BE_FILTER_MODEL_ADDR,
2569 	.indir_access_addr = R_BE_INDIR_ACCESS_ENTRY,
2570 	.mem_base_addrs = rtw89_mac_mem_base_addrs_be,
2571 	.mem_page_size = MAC_MEM_DUMP_PAGE_SIZE_BE,
2572 	.rx_fltr = R_BE_RX_FLTR_OPT,
2573 	.port_base = &rtw89_port_base_be,
2574 	.agg_len_ht = R_BE_AGG_LEN_HT_0,
2575 	.ps_status = R_BE_WMTX_POWER_BE_BIT_CTL,
2576 
2577 	.muedca_ctrl = {
2578 		.addr = R_BE_MUEDCA_EN,
2579 		.mask = B_BE_MUEDCA_EN_0 | B_BE_SET_MUEDCATIMER_TF_0,
2580 	},
2581 	.bfee_ctrl = {
2582 		.addr = R_BE_BFMEE_RESP_OPTION,
2583 		.mask = B_BE_BFMEE_HT_NDPA_EN | B_BE_BFMEE_VHT_NDPA_EN |
2584 			B_BE_BFMEE_HE_NDPA_EN | B_BE_BFMEE_EHT_NDPA_EN,
2585 	},
2586 	.narrow_bw_ru_dis = {
2587 		.addr = R_BE_RXTRIG_TEST_USER_2,
2588 		.mask = B_BE_RXTRIG_RU26_DIS,
2589 	},
2590 	.wow_ctrl = {.addr = R_BE_WOW_CTRL, .mask = B_BE_WOW_WOWEN,},
2591 	.agg_limit = {.addr = R_BE_AMPDU_AGG_LIMIT, .mask = B_BE_AMPDU_MAX_TIME_MASK,},
2592 	.txcnt_limit = {.addr = R_BE_TXCNT, .mask = B_BE_L_TXCNT_LMT_MASK,},
2593 
2594 	.check_mac_en = rtw89_mac_check_mac_en_be,
2595 	.sys_init = sys_init_be,
2596 	.trx_init = trx_init_be,
2597 	.hci_func_en = rtw89_mac_hci_func_en_be,
2598 	.dmac_func_pre_en = rtw89_mac_dmac_func_pre_en_be,
2599 	.dle_func_en = dle_func_en_be,
2600 	.dle_clk_en = dle_clk_en_be,
2601 	.bf_assoc = rtw89_mac_bf_assoc_be,
2602 
2603 	.typ_fltr_opt = rtw89_mac_typ_fltr_opt_be,
2604 	.cfg_ppdu_status = rtw89_mac_cfg_ppdu_status_be,
2605 	.cfg_phy_rpt = rtw89_mac_cfg_phy_rpt_be,
2606 
2607 	.dle_mix_cfg = dle_mix_cfg_be,
2608 	.chk_dle_rdy = chk_dle_rdy_be,
2609 	.dle_buf_req = dle_buf_req_be,
2610 	.hfc_func_en = hfc_func_en_be,
2611 	.hfc_h2c_cfg = hfc_h2c_cfg_be,
2612 	.hfc_mix_cfg = hfc_mix_cfg_be,
2613 	.hfc_get_mix_info = hfc_get_mix_info_be,
2614 	.wde_quota_cfg = wde_quota_cfg_be,
2615 	.ple_quota_cfg = ple_quota_cfg_be,
2616 	.set_cpuio = set_cpuio_be,
2617 	.dle_quota_change = dle_quota_change_be,
2618 
2619 	.disable_cpu = rtw89_mac_disable_cpu_be,
2620 	.fwdl_enable_wcpu = rtw89_mac_fwdl_enable_wcpu_be,
2621 	.fwdl_get_status = fwdl_get_status_be,
2622 	.fwdl_check_path_ready = rtw89_fwdl_check_path_ready_be,
2623 	.fwdl_secure_idmem_share_mode = NULL,
2624 	.parse_efuse_map = rtw89_parse_efuse_map_be,
2625 	.parse_phycap_map = rtw89_parse_phycap_map_be,
2626 	.cnv_efuse_state = rtw89_cnv_efuse_state_be,
2627 	.efuse_read_fw_secure = rtw89_efuse_read_fw_secure_be,
2628 
2629 	.cfg_plt = rtw89_mac_cfg_plt_be,
2630 	.get_plt_cnt = rtw89_mac_get_plt_cnt_be,
2631 
2632 	.get_txpwr_cr = rtw89_mac_get_txpwr_cr_be,
2633 
2634 	.write_xtal_si = rtw89_mac_write_xtal_si_be,
2635 	.read_xtal_si = rtw89_mac_read_xtal_si_be,
2636 
2637 	.dump_qta_lost = rtw89_mac_dump_qta_lost_be,
2638 	.dump_err_status = rtw89_mac_dump_err_status_be,
2639 
2640 	.is_txq_empty = mac_is_txq_empty_be,
2641 
2642 	.prep_chan_list = rtw89_hw_scan_prep_chan_list_be,
2643 	.free_chan_list = rtw89_hw_scan_free_chan_list_be,
2644 	.add_chan_list = rtw89_hw_scan_add_chan_list_be,
2645 	.add_chan_list_pno = rtw89_pno_scan_add_chan_list_be,
2646 	.scan_offload = rtw89_fw_h2c_scan_offload_be,
2647 
2648 	.wow_config_mac = rtw89_wow_config_mac_be,
2649 };
2650 EXPORT_SYMBOL(rtw89_mac_gen_be);
2651