xref: /OK3568_Linux_fs/kernel/drivers/net/wireless/rockchip_wlan/rtl8723bs/hal/phydm/phydm_ccx.c (revision 4882a59341e53eb6f0b4789bf948001014eff981)
1 /******************************************************************************
2  *
3  * Copyright(c) 2007 - 2017 Realtek Corporation.
4  *
5  * This program is free software; you can redistribute it and/or modify it
6  * under the terms of version 2 of the GNU General Public License as
7  * published by the Free Software Foundation.
8  *
9  * This program is distributed in the hope that it will be useful, but WITHOUT
10  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
11  * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
12  * more details.
13  *
14  *****************************************************************************/
15 
16 #include "mp_precomp.h"
17 #include "phydm_precomp.h"
18 
19 /*Set NHM period, threshold, disable ignore cca or not, disable ignore txon or not*/
20 void
phydm_nhm_init(void * p_dm_void)21 phydm_nhm_init(
22 	void			*p_dm_void
23 )
24 {
25 	struct PHY_DM_STRUCT	*p_dm = (struct PHY_DM_STRUCT *)p_dm_void;
26 	struct _CCX_INFO		*ccx_info = &p_dm->dm_ccx_info;
27 
28 	PHYDM_DBG(p_dm, DBG_ENV_MNTR, ("[%s]===>\n", __FUNCTION__));
29 	PHYDM_DBG(p_dm, DBG_ENV_MNTR, ("cur_ig_value=0x%x\n", p_dm->dm_dig_table.cur_ig_value));
30 
31 	phydm_set_nhm_th_by_igi(p_dm, p_dm->dm_dig_table.cur_ig_value);
32 
33 	ccx_info->nhm_period = 0xC350;
34 	ccx_info->nhm_inexclude_cca = NHM_EXCLUDE_CCA;
35 	ccx_info->nhm_inexclude_txon = NHM_EXCLUDE_TXON;
36 
37 	phydm_nhm_setting(p_dm, SET_NHM_SETTING);
38 }
39 
40 boolean
phydm_cal_nhm_cnt(void * p_dm_void)41 phydm_cal_nhm_cnt(
42 	void		*p_dm_void
43 )
44 {
45 	struct PHY_DM_STRUCT		*p_dm = (struct PHY_DM_STRUCT *)p_dm_void;
46 	struct _CCX_INFO		*ccx_info = &p_dm->dm_ccx_info;
47 	u8						noisy_nhm_th_index, low_pwr_cnt = 0, high_pwr_cnt = 0;
48 	u8						noisy_nhm_th = 0x52;
49 	u8						i;
50 	boolean					noisy = false, clean = true;
51 
52 	PHYDM_DBG(p_dm, DBG_ENV_MNTR, ("[%s]===>\n", __FUNCTION__));
53 
54 	if (!(p_dm->support_ability & ODM_BB_ENV_MONITOR))
55 		return noisy;
56 
57 	/*nhm_th = 0x52 means 0x52/2-110 = -69dbm*/
58 	/* IGI < 0x14 */
59 	if (ccx_info->nhm_th[10] < noisy_nhm_th)
60 		return	clean;
61 	else if (ccx_info->nhm_th[0] > noisy_nhm_th)
62 		return	(p_dm->noisy_decision) ? noisy : clean;
63 	/* 0x14 <= IGI <= 0x37*/
64 	else {
65 		/* search index */
66 		noisy_nhm_th_index = (noisy_nhm_th - ccx_info->nhm_th[0]) << 2;
67 
68 		for (i = 0; i <= 11; i++) {
69 			if (i <= noisy_nhm_th_index)
70 				low_pwr_cnt += ccx_info->nhm_result[i];
71 			else
72 				high_pwr_cnt += ccx_info->nhm_result[i];
73 		}
74 
75 		if (low_pwr_cnt + high_pwr_cnt == 0)
76 			return noisy;		/* noisy environment */
77 		else if (low_pwr_cnt - high_pwr_cnt >= 100)
78 			return clean;		/* clean environment */
79 		else
80 			return noisy;		/* noisy environment */
81 	}
82 }
83 
84 void
phydm_nhm_setting(void * p_dm_void,u8 nhm_setting)85 phydm_nhm_setting(
86 	void		*p_dm_void,
87 	u8	nhm_setting
88 )
89 {
90 	struct PHY_DM_STRUCT	*p_dm = (struct PHY_DM_STRUCT *)p_dm_void;
91 	struct _CCX_INFO	*ccx_info = &p_dm->dm_ccx_info;
92 
93 	PHYDM_DBG(p_dm, DBG_ENV_MNTR, ("[%s]===>\n", __FUNCTION__));
94 
95 	if (nhm_setting == SET_NHM_SETTING) {
96 		PHYDM_DBG(p_dm, DBG_ENV_MNTR,
97 		("nhm_th=(H->L)[0x%x 0x%x 0x%x 0x%x 0x%x 0x%x 0x%x 0x%x 0x%x 0x%x 0x%x]\n",
98 		ccx_info->nhm_th[10], ccx_info->nhm_th[9], ccx_info->nhm_th[8],
99 		ccx_info->nhm_th[7], ccx_info->nhm_th[6], ccx_info->nhm_th[5],
100 		ccx_info->nhm_th[4], ccx_info->nhm_th[3], ccx_info->nhm_th[2],
101 		ccx_info->nhm_th[1], ccx_info->nhm_th[0]));
102 	}
103 
104 	if (p_dm->support_ic_type & ODM_IC_11AC_SERIES) {
105 
106 		if (nhm_setting == SET_NHM_SETTING) {
107 
108 			/*Set inexclude_cca, inexclude_txon*/
109 			odm_set_bb_reg(p_dm, ODM_REG_NHM_TH9_TH10_11AC, BIT(9), ccx_info->nhm_inexclude_cca);
110 			odm_set_bb_reg(p_dm, ODM_REG_NHM_TH9_TH10_11AC, BIT(10), ccx_info->nhm_inexclude_txon);
111 
112 			/*Set NHM period*/
113 			odm_set_bb_reg(p_dm, ODM_REG_CCX_PERIOD_11AC, MASKHWORD, ccx_info->nhm_period);
114 
115 			/*Set NHM threshold*/ /*Unit: PWdB U(8,1)*/
116 			odm_set_bb_reg(p_dm, ODM_REG_NHM_TH3_TO_TH0_11AC, MASKBYTE0, ccx_info->nhm_th[0]);
117 			odm_set_bb_reg(p_dm, ODM_REG_NHM_TH3_TO_TH0_11AC, MASKBYTE1, ccx_info->nhm_th[1]);
118 			odm_set_bb_reg(p_dm, ODM_REG_NHM_TH3_TO_TH0_11AC, MASKBYTE2, ccx_info->nhm_th[2]);
119 			odm_set_bb_reg(p_dm, ODM_REG_NHM_TH3_TO_TH0_11AC, MASKBYTE3, ccx_info->nhm_th[3]);
120 			odm_set_bb_reg(p_dm, ODM_REG_NHM_TH7_TO_TH4_11AC, MASKBYTE0, ccx_info->nhm_th[4]);
121 			odm_set_bb_reg(p_dm, ODM_REG_NHM_TH7_TO_TH4_11AC, MASKBYTE1, ccx_info->nhm_th[5]);
122 			odm_set_bb_reg(p_dm, ODM_REG_NHM_TH7_TO_TH4_11AC, MASKBYTE2, ccx_info->nhm_th[6]);
123 			odm_set_bb_reg(p_dm, ODM_REG_NHM_TH7_TO_TH4_11AC, MASKBYTE3, ccx_info->nhm_th[7]);
124 			odm_set_bb_reg(p_dm, ODM_REG_NHM_TH8_11AC, MASKBYTE0, ccx_info->nhm_th[8]);
125 			odm_set_bb_reg(p_dm, ODM_REG_NHM_TH9_TH10_11AC, MASKBYTE2, ccx_info->nhm_th[9]);
126 			odm_set_bb_reg(p_dm, ODM_REG_NHM_TH9_TH10_11AC, MASKBYTE3, ccx_info->nhm_th[10]);
127 
128 			/*CCX EN*/
129 			odm_set_bb_reg(p_dm, ODM_REG_NHM_TH9_TH10_11AC, BIT(8), CCX_EN);
130 
131 		} else if (nhm_setting == STORE_NHM_SETTING) {
132 
133 			/*Store pervious disable_ignore_cca, disable_ignore_txon*/
134 			ccx_info->nhm_inexclude_cca_restore = (enum nhm_inexclude_cca)odm_get_bb_reg(p_dm, ODM_REG_NHM_TH9_TH10_11AC, BIT(9));
135 			ccx_info->nhm_inexclude_txon_restore = (enum nhm_inexclude_txon)odm_get_bb_reg(p_dm, ODM_REG_NHM_TH9_TH10_11AC, BIT(10));
136 
137 			/*Store pervious NHM period*/
138 			ccx_info->nhm_period_restore = (u16)odm_get_bb_reg(p_dm, ODM_REG_CCX_PERIOD_11AC, MASKHWORD);
139 
140 			/*Store NHM threshold*/
141 			ccx_info->nhm_th_restore[0] = (u8)odm_get_bb_reg(p_dm, ODM_REG_NHM_TH3_TO_TH0_11AC, MASKBYTE0);
142 			ccx_info->nhm_th_restore[1] = (u8)odm_get_bb_reg(p_dm, ODM_REG_NHM_TH3_TO_TH0_11AC, MASKBYTE1);
143 			ccx_info->nhm_th_restore[2] = (u8)odm_get_bb_reg(p_dm, ODM_REG_NHM_TH3_TO_TH0_11AC, MASKBYTE2);
144 			ccx_info->nhm_th_restore[3] = (u8)odm_get_bb_reg(p_dm, ODM_REG_NHM_TH3_TO_TH0_11AC, MASKBYTE3);
145 			ccx_info->nhm_th_restore[4] = (u8)odm_get_bb_reg(p_dm, ODM_REG_NHM_TH7_TO_TH4_11AC, MASKBYTE0);
146 			ccx_info->nhm_th_restore[5] = (u8)odm_get_bb_reg(p_dm, ODM_REG_NHM_TH7_TO_TH4_11AC, MASKBYTE1);
147 			ccx_info->nhm_th_restore[6] = (u8)odm_get_bb_reg(p_dm, ODM_REG_NHM_TH7_TO_TH4_11AC, MASKBYTE2);
148 			ccx_info->nhm_th_restore[7] = (u8)odm_get_bb_reg(p_dm, ODM_REG_NHM_TH7_TO_TH4_11AC, MASKBYTE3);
149 			ccx_info->nhm_th_restore[8] = (u8)odm_get_bb_reg(p_dm, ODM_REG_NHM_TH8_11AC, MASKBYTE0);
150 			ccx_info->nhm_th_restore[9] = (u8)odm_get_bb_reg(p_dm, ODM_REG_NHM_TH9_TH10_11AC, MASKBYTE2);
151 			ccx_info->nhm_th_restore[10] = (u8)odm_get_bb_reg(p_dm, ODM_REG_NHM_TH9_TH10_11AC, MASKBYTE3);
152 		} else if (nhm_setting == RESTORE_NHM_SETTING) {
153 
154 			/*Set disable_ignore_cca, disable_ignore_txon*/
155 			odm_set_bb_reg(p_dm, ODM_REG_NHM_TH9_TH10_11AC, BIT(9), ccx_info->nhm_inexclude_cca_restore);
156 			odm_set_bb_reg(p_dm, ODM_REG_NHM_TH9_TH10_11AC, BIT(10), ccx_info->nhm_inexclude_txon_restore);
157 
158 			/*Set NHM period*/
159 			odm_set_bb_reg(p_dm, ODM_REG_CCX_PERIOD_11AC, MASKHWORD, ccx_info->nhm_period);
160 
161 			/*Set NHM threshold*/
162 			odm_set_bb_reg(p_dm, ODM_REG_NHM_TH3_TO_TH0_11AC, MASKBYTE0, ccx_info->nhm_th_restore[0]);
163 			odm_set_bb_reg(p_dm, ODM_REG_NHM_TH3_TO_TH0_11AC, MASKBYTE1, ccx_info->nhm_th_restore[1]);
164 			odm_set_bb_reg(p_dm, ODM_REG_NHM_TH3_TO_TH0_11AC, MASKBYTE2, ccx_info->nhm_th_restore[2]);
165 			odm_set_bb_reg(p_dm, ODM_REG_NHM_TH3_TO_TH0_11AC, MASKBYTE3, ccx_info->nhm_th_restore[3]);
166 			odm_set_bb_reg(p_dm, ODM_REG_NHM_TH7_TO_TH4_11AC, MASKBYTE0, ccx_info->nhm_th_restore[4]);
167 			odm_set_bb_reg(p_dm, ODM_REG_NHM_TH7_TO_TH4_11AC, MASKBYTE1, ccx_info->nhm_th_restore[5]);
168 			odm_set_bb_reg(p_dm, ODM_REG_NHM_TH7_TO_TH4_11AC, MASKBYTE2, ccx_info->nhm_th_restore[6]);
169 			odm_set_bb_reg(p_dm, ODM_REG_NHM_TH7_TO_TH4_11AC, MASKBYTE3, ccx_info->nhm_th_restore[7]);
170 			odm_set_bb_reg(p_dm, ODM_REG_NHM_TH8_11AC, MASKBYTE0, ccx_info->nhm_th_restore[8]);
171 			odm_set_bb_reg(p_dm, ODM_REG_NHM_TH9_TH10_11AC, MASKBYTE2, ccx_info->nhm_th_restore[9]);
172 			odm_set_bb_reg(p_dm, ODM_REG_NHM_TH9_TH10_11AC, MASKBYTE3, ccx_info->nhm_th_restore[10]);
173 		} else
174 			return;
175 	}
176 
177 	else if (p_dm->support_ic_type & ODM_IC_11N_SERIES) {
178 
179 		if (nhm_setting == SET_NHM_SETTING) {
180 
181 			/*Set disable_ignore_cca, disable_ignore_txon*/
182 			odm_set_bb_reg(p_dm, ODM_REG_NHM_TH9_TH10_11N, BIT(9), ccx_info->nhm_inexclude_cca);
183 			odm_set_bb_reg(p_dm, ODM_REG_NHM_TH9_TH10_11N, BIT(10), ccx_info->nhm_inexclude_txon);
184 
185 			/*Set NHM period*/
186 			odm_set_bb_reg(p_dm, ODM_REG_CCX_PERIOD_11N, MASKHWORD, ccx_info->nhm_period);
187 
188 			/*Set NHM threshold*/
189 			odm_set_bb_reg(p_dm, ODM_REG_NHM_TH3_TO_TH0_11N, MASKBYTE0, ccx_info->nhm_th[0]);
190 			odm_set_bb_reg(p_dm, ODM_REG_NHM_TH3_TO_TH0_11N, MASKBYTE1, ccx_info->nhm_th[1]);
191 			odm_set_bb_reg(p_dm, ODM_REG_NHM_TH3_TO_TH0_11N, MASKBYTE2, ccx_info->nhm_th[2]);
192 			odm_set_bb_reg(p_dm, ODM_REG_NHM_TH3_TO_TH0_11N, MASKBYTE3, ccx_info->nhm_th[3]);
193 			odm_set_bb_reg(p_dm, ODM_REG_NHM_TH7_TO_TH4_11N, MASKBYTE0, ccx_info->nhm_th[4]);
194 			odm_set_bb_reg(p_dm, ODM_REG_NHM_TH7_TO_TH4_11N, MASKBYTE1, ccx_info->nhm_th[5]);
195 			odm_set_bb_reg(p_dm, ODM_REG_NHM_TH7_TO_TH4_11N, MASKBYTE2, ccx_info->nhm_th[6]);
196 			odm_set_bb_reg(p_dm, ODM_REG_NHM_TH7_TO_TH4_11N, MASKBYTE3, ccx_info->nhm_th[7]);
197 			odm_set_bb_reg(p_dm, ODM_REG_NHM_TH8_11N, MASKBYTE0, ccx_info->nhm_th[8]);
198 			odm_set_bb_reg(p_dm, ODM_REG_NHM_TH9_TH10_11N, MASKBYTE2, ccx_info->nhm_th[9]);
199 			odm_set_bb_reg(p_dm, ODM_REG_NHM_TH9_TH10_11N, MASKBYTE3, ccx_info->nhm_th[10]);
200 
201 			/*CCX EN*/
202 			odm_set_bb_reg(p_dm, ODM_REG_NHM_TH9_TH10_11N, BIT(8), CCX_EN);
203 		} else if (nhm_setting == STORE_NHM_SETTING) {
204 
205 			/*Store pervious disable_ignore_cca, disable_ignore_txon*/
206 			ccx_info->nhm_inexclude_cca_restore = (enum nhm_inexclude_cca)odm_get_bb_reg(p_dm, ODM_REG_NHM_TH9_TH10_11N, BIT(9));
207 			ccx_info->nhm_inexclude_txon_restore = (enum nhm_inexclude_txon)odm_get_bb_reg(p_dm, ODM_REG_NHM_TH9_TH10_11N, BIT(10));
208 
209 			/*Store pervious NHM period*/
210 			ccx_info->nhm_period_restore = (u16)odm_get_bb_reg(p_dm, ODM_REG_CCX_PERIOD_11N, MASKHWORD);
211 
212 			/*Store NHM threshold*/
213 			ccx_info->nhm_th_restore[0] = (u8)odm_get_bb_reg(p_dm, ODM_REG_NHM_TH3_TO_TH0_11N, MASKBYTE0);
214 			ccx_info->nhm_th_restore[1] = (u8)odm_get_bb_reg(p_dm, ODM_REG_NHM_TH3_TO_TH0_11N, MASKBYTE1);
215 			ccx_info->nhm_th_restore[2] = (u8)odm_get_bb_reg(p_dm, ODM_REG_NHM_TH3_TO_TH0_11N, MASKBYTE2);
216 			ccx_info->nhm_th_restore[3] = (u8)odm_get_bb_reg(p_dm, ODM_REG_NHM_TH3_TO_TH0_11N, MASKBYTE3);
217 			ccx_info->nhm_th_restore[4] = (u8)odm_get_bb_reg(p_dm, ODM_REG_NHM_TH7_TO_TH4_11N, MASKBYTE0);
218 			ccx_info->nhm_th_restore[5] = (u8)odm_get_bb_reg(p_dm, ODM_REG_NHM_TH7_TO_TH4_11N, MASKBYTE1);
219 			ccx_info->nhm_th_restore[6] = (u8)odm_get_bb_reg(p_dm, ODM_REG_NHM_TH7_TO_TH4_11N, MASKBYTE2);
220 			ccx_info->nhm_th_restore[7] = (u8)odm_get_bb_reg(p_dm, ODM_REG_NHM_TH7_TO_TH4_11N, MASKBYTE3);
221 			ccx_info->nhm_th_restore[8] = (u8)odm_get_bb_reg(p_dm, ODM_REG_NHM_TH8_11N, MASKBYTE0);
222 			ccx_info->nhm_th_restore[9] = (u8)odm_get_bb_reg(p_dm, ODM_REG_NHM_TH9_TH10_11N, MASKBYTE2);
223 			ccx_info->nhm_th_restore[10] = (u8)odm_get_bb_reg(p_dm, ODM_REG_NHM_TH9_TH10_11N, MASKBYTE3);
224 
225 		} else if (nhm_setting == RESTORE_NHM_SETTING) {
226 
227 			/*Set disable_ignore_cca, disable_ignore_txon*/
228 			odm_set_bb_reg(p_dm, ODM_REG_NHM_TH9_TH10_11N, BIT(9), ccx_info->nhm_inexclude_cca_restore);
229 			odm_set_bb_reg(p_dm, ODM_REG_NHM_TH9_TH10_11N, BIT(10), ccx_info->nhm_inexclude_txon_restore);
230 
231 			/*Set NHM period*/
232 			odm_set_bb_reg(p_dm, ODM_REG_CCX_PERIOD_11N, MASKHWORD, ccx_info->nhm_period_restore);
233 
234 			/*Set NHM threshold*/
235 			odm_set_bb_reg(p_dm, ODM_REG_NHM_TH3_TO_TH0_11N, MASKBYTE0, ccx_info->nhm_th_restore[0]);
236 			odm_set_bb_reg(p_dm, ODM_REG_NHM_TH3_TO_TH0_11N, MASKBYTE1, ccx_info->nhm_th_restore[1]);
237 			odm_set_bb_reg(p_dm, ODM_REG_NHM_TH3_TO_TH0_11N, MASKBYTE2, ccx_info->nhm_th_restore[2]);
238 			odm_set_bb_reg(p_dm, ODM_REG_NHM_TH3_TO_TH0_11N, MASKBYTE3, ccx_info->nhm_th_restore[3]);
239 			odm_set_bb_reg(p_dm, ODM_REG_NHM_TH7_TO_TH4_11N, MASKBYTE0, ccx_info->nhm_th_restore[4]);
240 			odm_set_bb_reg(p_dm, ODM_REG_NHM_TH7_TO_TH4_11N, MASKBYTE1, ccx_info->nhm_th_restore[5]);
241 			odm_set_bb_reg(p_dm, ODM_REG_NHM_TH7_TO_TH4_11N, MASKBYTE2, ccx_info->nhm_th_restore[6]);
242 			odm_set_bb_reg(p_dm, ODM_REG_NHM_TH7_TO_TH4_11N, MASKBYTE3, ccx_info->nhm_th_restore[7]);
243 			odm_set_bb_reg(p_dm, ODM_REG_NHM_TH8_11N, MASKBYTE0, ccx_info->nhm_th_restore[8]);
244 			odm_set_bb_reg(p_dm, ODM_REG_NHM_TH9_TH10_11N, MASKBYTE2, ccx_info->nhm_th_restore[9]);
245 			odm_set_bb_reg(p_dm, ODM_REG_NHM_TH9_TH10_11N, MASKBYTE3, ccx_info->nhm_th_restore[10]);
246 		} else
247 			return;
248 
249 	}
250 }
251 
252 void
phydm_nhm_trigger(void * p_dm_void)253 phydm_nhm_trigger(
254 	void		*p_dm_void
255 )
256 {
257 	struct PHY_DM_STRUCT		*p_dm = (struct PHY_DM_STRUCT *)p_dm_void;
258 
259 	PHYDM_DBG(p_dm, DBG_ENV_MNTR, ("[%s]===>\n", __FUNCTION__));
260 
261 	if (p_dm->support_ic_type & ODM_IC_11AC_SERIES) {
262 
263 		/*Trigger NHM*/
264 		odm_set_bb_reg(p_dm, ODM_REG_NHM_TH9_TH10_11AC, BIT(1), 0);
265 		odm_set_bb_reg(p_dm, ODM_REG_NHM_TH9_TH10_11AC, BIT(1), 1);
266 	} else if (p_dm->support_ic_type & ODM_IC_11N_SERIES) {
267 
268 		/*Trigger NHM*/
269 		odm_set_bb_reg(p_dm, ODM_REG_NHM_TH9_TH10_11N, BIT(1), 0);
270 		odm_set_bb_reg(p_dm, ODM_REG_NHM_TH9_TH10_11N, BIT(1), 1);
271 	}
272 }
273 
274 void
phydm_get_nhm_result(void * p_dm_void)275 phydm_get_nhm_result(
276 	void		*p_dm_void
277 )
278 {
279 	struct PHY_DM_STRUCT		*p_dm = (struct PHY_DM_STRUCT *)p_dm_void;
280 	struct _CCX_INFO		*ccx_info = &p_dm->dm_ccx_info;
281 	u32			value32;
282 	u8			i;
283 
284 	PHYDM_DBG(p_dm, DBG_ENV_MNTR, ("[%s]===>\n", __FUNCTION__));
285 
286 	if (p_dm->support_ic_type & ODM_IC_11AC_SERIES) {
287 
288 		value32 = odm_read_4byte(p_dm, ODM_REG_NHM_CNT_11AC);
289 		ccx_info->nhm_result[0] = (u8)(value32 & MASKBYTE0);
290 		ccx_info->nhm_result[1] = (u8)((value32 & MASKBYTE1) >> 8);
291 		ccx_info->nhm_result[2] = (u8)((value32 & MASKBYTE2) >> 16);
292 		ccx_info->nhm_result[3] = (u8)((value32 & MASKBYTE3) >> 24);
293 
294 		value32 = odm_read_4byte(p_dm, ODM_REG_NHM_CNT7_TO_CNT4_11AC);
295 		ccx_info->nhm_result[4] = (u8)(value32 & MASKBYTE0);
296 		ccx_info->nhm_result[5] = (u8)((value32 & MASKBYTE1) >> 8);
297 		ccx_info->nhm_result[6] = (u8)((value32 & MASKBYTE2) >> 16);
298 		ccx_info->nhm_result[7] = (u8)((value32 & MASKBYTE3) >> 24);
299 
300 		value32 = odm_read_4byte(p_dm, ODM_REG_NHM_CNT11_TO_CNT8_11AC);
301 		ccx_info->nhm_result[8] = (u8)(value32 & MASKBYTE0);
302 		ccx_info->nhm_result[9] = (u8)((value32 & MASKBYTE1) >> 8);
303 		ccx_info->nhm_result[10] = (u8)((value32 & MASKBYTE2) >> 16);
304 		ccx_info->nhm_result[11] = (u8)((value32 & MASKBYTE3) >> 24);
305 
306 		/*Get NHM duration*/
307 		value32 = odm_read_4byte(p_dm, ODM_REG_NHM_DUR_READY_11AC);
308 		ccx_info->nhm_duration = (u16)(value32 & MASKLWORD);
309 
310 	}
311 
312 	else if (p_dm->support_ic_type & ODM_IC_11N_SERIES) {
313 
314 		value32 = odm_read_4byte(p_dm, ODM_REG_NHM_CNT_11N);
315 		ccx_info->nhm_result[0] = (u8)(value32 & MASKBYTE0);
316 		ccx_info->nhm_result[1] = (u8)((value32 & MASKBYTE1) >> 8);
317 		ccx_info->nhm_result[2] = (u8)((value32 & MASKBYTE2) >> 16);
318 		ccx_info->nhm_result[3] = (u8)((value32 & MASKBYTE3) >> 24);
319 
320 		value32 = odm_read_4byte(p_dm, ODM_REG_NHM_CNT7_TO_CNT4_11N);
321 		ccx_info->nhm_result[4] = (u8)(value32 & MASKBYTE0);
322 		ccx_info->nhm_result[5] = (u8)((value32 & MASKBYTE1) >> 8);
323 		ccx_info->nhm_result[6] = (u8)((value32 & MASKBYTE2) >> 16);
324 		ccx_info->nhm_result[7] = (u8)((value32 & MASKBYTE3) >> 24);
325 
326 		value32 = odm_read_4byte(p_dm, ODM_REG_NHM_CNT9_TO_CNT8_11N);
327 		ccx_info->nhm_result[8] = (u8)((value32 & MASKBYTE2) >> 16);
328 		ccx_info->nhm_result[9] = (u8)((value32 & MASKBYTE3) >> 24);
329 
330 		value32 = odm_read_4byte(p_dm, ODM_REG_NHM_CNT10_TO_CNT11_11N);
331 		ccx_info->nhm_result[10] = (u8)((value32 & MASKBYTE2) >> 16);
332 		ccx_info->nhm_result[11] = (u8)((value32 & MASKBYTE3) >> 24);
333 
334 		/*Get NHM duration*/
335 		value32 = odm_read_4byte(p_dm, ODM_REG_NHM_CNT10_TO_CNT11_11N);
336 		ccx_info->nhm_duration = (u16)(value32 & MASKLWORD);
337 
338 	}
339 
340 	/* sum all nhm_result */
341 	ccx_info->nhm_result_total = 0;
342 	for (i = 0; i <= 11; i++)
343 		ccx_info->nhm_result_total += ccx_info->nhm_result[i];
344 
345 		PHYDM_DBG(p_dm, DBG_ENV_MNTR,
346 		("nhm_result=(H->L)[%d %d %d %d (igi) %d %d %d %d %d %d %d %d]\n",
347 			ccx_info->nhm_result[11], ccx_info->nhm_result[10], ccx_info->nhm_result[9],
348 			ccx_info->nhm_result[8], ccx_info->nhm_result[7], ccx_info->nhm_result[6],
349 			ccx_info->nhm_result[5], ccx_info->nhm_result[4], ccx_info->nhm_result[3],
350 			ccx_info->nhm_result[2], ccx_info->nhm_result[1], ccx_info->nhm_result[0]));
351 }
352 
353 boolean
phydm_check_nhm_rdy(void * p_dm_void)354 phydm_check_nhm_rdy(
355 	void		*p_dm_void
356 )
357 {
358 	struct PHY_DM_STRUCT		*p_dm = (struct PHY_DM_STRUCT *)p_dm_void;
359 	u8			i;
360 	boolean			is_ready = false;
361 
362 	if (p_dm->support_ic_type & ODM_IC_11AC_SERIES) {
363 
364 		for (i = 0; i < 200; i++) {
365 			ODM_delay_ms(1);
366 			if (odm_get_bb_reg(p_dm, ODM_REG_NHM_DUR_READY_11AC, BIT(16))) {
367 				is_ready = 1;
368 				break;
369 			}
370 		}
371 	}
372 
373 	else if (p_dm->support_ic_type & ODM_IC_11N_SERIES) {
374 
375 		for (i = 0; i < 200; i++) {
376 			ODM_delay_ms(1);
377 			if (odm_get_bb_reg(p_dm, ODM_REG_NHM_DUR_READY_11AC, BIT(17))) {
378 				is_ready = 1;
379 				break;
380 			}
381 		}
382 	}
383 	PHYDM_DBG(p_dm, DBG_ENV_MNTR, ("[%s]NHM rdy=%d\n", __FUNCTION__, is_ready));
384 	return is_ready;
385 }
386 
387 void
phydm_store_nhm_setting(void * p_dm_void)388 phydm_store_nhm_setting(
389 	void		*p_dm_void
390 )
391 {
392 	struct PHY_DM_STRUCT	*p_dm = (struct PHY_DM_STRUCT *)p_dm_void;
393 
394 	PHYDM_DBG(p_dm, DBG_ENV_MNTR, ("[%s]===>\n", __FUNCTION__));
395 
396 	if (p_dm->support_ic_type & ODM_IC_11AC_SERIES) {
397 
398 
399 	} else if (p_dm->support_ic_type & ODM_IC_11N_SERIES) {
400 
401 
402 
403 	}
404 }
405 
406 void
phydm_clm_setting(void * p_dm_void)407 phydm_clm_setting(
408 	void			*p_dm_void
409 )
410 {
411 	struct PHY_DM_STRUCT		*p_dm = (struct PHY_DM_STRUCT *)p_dm_void;
412 	struct _CCX_INFO	*ccx_info = &p_dm->dm_ccx_info;
413 
414 	if (p_dm->support_ic_type & ODM_IC_11AC_SERIES) {
415 
416 		odm_set_bb_reg(p_dm, ODM_REG_CCX_PERIOD_11AC, MASKLWORD, ccx_info->clm_period);	/*4us sample 1 time*/
417 		odm_set_bb_reg(p_dm, ODM_REG_CLM_11AC, BIT(8), 0x1); /*Enable CCX for CLM*/
418 
419 	} else if (p_dm->support_ic_type & ODM_IC_11N_SERIES) {
420 
421 		odm_set_bb_reg(p_dm, ODM_REG_CCX_PERIOD_11N, MASKLWORD, ccx_info->clm_period);
422 		odm_set_bb_reg(p_dm, ODM_REG_CLM_11N, BIT(8), 0x1);	/*Enable CCX for CLM*/
423 	}
424 
425 	PHYDM_DBG(p_dm, DBG_ENV_MNTR, ("[%s]CLM period=%dus\n", __func__, ccx_info->clm_period * 4));
426 
427 }
428 
429 void
phydm_clm_trigger(void * p_dm_void)430 phydm_clm_trigger(
431 	void			*p_dm_void
432 )
433 {
434 	struct PHY_DM_STRUCT		*p_dm = (struct PHY_DM_STRUCT *)p_dm_void;
435 
436 	PHYDM_DBG(p_dm, DBG_ENV_MNTR, ("[%s]===>\n", __FUNCTION__));
437 
438 	if (p_dm->support_ic_type & ODM_IC_11AC_SERIES) {
439 		odm_set_bb_reg(p_dm, ODM_REG_CLM_11AC, BIT(0), 0x0);	/*Trigger CLM*/
440 		odm_set_bb_reg(p_dm, ODM_REG_CLM_11AC, BIT(0), 0x1);
441 	} else if (p_dm->support_ic_type & ODM_IC_11N_SERIES) {
442 		odm_set_bb_reg(p_dm, ODM_REG_CLM_11N, BIT(0), 0x0);	/*Trigger CLM*/
443 		odm_set_bb_reg(p_dm, ODM_REG_CLM_11N, BIT(0), 0x1);
444 	}
445 }
446 
447 boolean
phydm_check_clm_rdy(void * p_dm_void)448 phydm_check_clm_rdy(
449 	void			*p_dm_void
450 )
451 {
452 	struct PHY_DM_STRUCT		*p_dm = (struct PHY_DM_STRUCT *)p_dm_void;
453 	boolean			is_ready = false;
454 	u8				i;
455 
456 	if (p_dm->support_ic_type & ODM_IC_11AC_SERIES) {
457 		for (i = 0; i < 200; i++) {
458 			ODM_delay_ms(1);
459 			if (odm_get_bb_reg(p_dm, ODM_REG_CLM_RESULT_11AC, BIT(16))) {
460 				is_ready = 1;
461 				break;
462 			}
463 		}
464 	} else if (p_dm->support_ic_type & ODM_IC_11N_SERIES) {
465 		for (i = 0; i < 200; i++) {
466 			ODM_delay_ms(1);
467 			if (odm_get_bb_reg(p_dm, ODM_REG_CLM_READY_11N, BIT(16))) {
468 				is_ready = 1;
469 				break;
470 			}
471 		}
472 	}
473 	PHYDM_DBG(p_dm, DBG_ENV_MNTR, ("[%s]CLM rdy=%d\n", __FUNCTION__, is_ready));
474 	return is_ready;
475 }
476 
477 void
phydm_get_clm_result(void * p_dm_void)478 phydm_get_clm_result(
479 	void			*p_dm_void
480 )
481 {
482 	struct PHY_DM_STRUCT		*p_dm = (struct PHY_DM_STRUCT *)p_dm_void;
483 	struct _CCX_INFO	*ccx_info = &p_dm->dm_ccx_info;
484 
485 	u32			value32 = 0;
486 
487 	if (p_dm->support_ic_type & ODM_IC_11AC_SERIES)
488 		value32 = odm_get_bb_reg(p_dm, ODM_REG_CLM_RESULT_11AC, MASKDWORD);
489 	else if (p_dm->support_ic_type & ODM_IC_11N_SERIES)
490 		value32 = odm_get_bb_reg(p_dm, ODM_REG_CLM_RESULT_11N, MASKDWORD);
491 
492 	ccx_info->clm_result = (u16)(value32 & MASKLWORD);
493 
494 	PHYDM_DBG(p_dm, DBG_ENV_MNTR, ("[%s]CLM result = %dus\n", __func__, ccx_info->clm_result * 4));
495 
496 }
497 
498 void
phydm_ccx_monitor(void * p_dm_void)499 phydm_ccx_monitor(
500 	void			*p_dm_void
501 )
502 {
503 	struct PHY_DM_STRUCT	*p_dm = (struct PHY_DM_STRUCT *)p_dm_void;
504 
505 	if (!(p_dm->support_ability & ODM_BB_ENV_MONITOR))
506 		return;
507 
508 	PHYDM_DBG(p_dm, DBG_ENV_MNTR, ("[%s]===>\n", __FUNCTION__));
509 
510 	phydm_ccx_monitor_result(p_dm);
511 	phydm_ccx_monitor_trigger(p_dm, (u16)0xC350);	/*monitor 200ms*/
512 }
513 
514 void
phydm_ccx_monitor_trigger(void * p_dm_void,u16 monitor_time)515 phydm_ccx_monitor_trigger(
516 	void			*p_dm_void,
517 	u16				monitor_time		/*unit 4us*/
518 )
519 {
520 	u8			nhm_th[11], i, igi;
521 	struct PHY_DM_STRUCT	*p_dm = (struct PHY_DM_STRUCT *)p_dm_void;
522 	struct _CCX_INFO		*ccx_info = &p_dm->dm_ccx_info;
523 
524 	if (!(p_dm->support_ability & ODM_BB_ENV_MONITOR))
525 		return;
526 
527 	PHYDM_DBG(p_dm, DBG_ENV_MNTR, ("[%s]===>\n", __FUNCTION__));
528 
529 	/* check if NHM threshold is changed */
530 	if (p_dm->support_ic_type & ODM_IC_11AC_SERIES) {
531 
532 		nhm_th[0] = (u8)odm_get_bb_reg(p_dm, ODM_REG_NHM_TH3_TO_TH0_11AC, MASKBYTE0);
533 		nhm_th[1] = (u8)odm_get_bb_reg(p_dm, ODM_REG_NHM_TH3_TO_TH0_11AC, MASKBYTE1);
534 		nhm_th[2] = (u8)odm_get_bb_reg(p_dm, ODM_REG_NHM_TH3_TO_TH0_11AC, MASKBYTE2);
535 		nhm_th[3] = (u8)odm_get_bb_reg(p_dm, ODM_REG_NHM_TH3_TO_TH0_11AC, MASKBYTE3);
536 		nhm_th[4] = (u8)odm_get_bb_reg(p_dm, ODM_REG_NHM_TH7_TO_TH4_11AC, MASKBYTE0);
537 		nhm_th[5] = (u8)odm_get_bb_reg(p_dm, ODM_REG_NHM_TH7_TO_TH4_11AC, MASKBYTE1);
538 		nhm_th[6] = (u8)odm_get_bb_reg(p_dm, ODM_REG_NHM_TH7_TO_TH4_11AC, MASKBYTE2);
539 		nhm_th[7] = (u8)odm_get_bb_reg(p_dm, ODM_REG_NHM_TH7_TO_TH4_11AC, MASKBYTE3);
540 		nhm_th[8] = (u8)odm_get_bb_reg(p_dm, ODM_REG_NHM_TH8_11AC, MASKBYTE0);
541 		nhm_th[9] = (u8)odm_get_bb_reg(p_dm, ODM_REG_NHM_TH9_TH10_11AC, MASKBYTE2);
542 		nhm_th[10] = (u8)odm_get_bb_reg(p_dm, ODM_REG_NHM_TH9_TH10_11AC, MASKBYTE3);
543 	} else if (p_dm->support_ic_type & ODM_IC_11N_SERIES) {
544 
545 		nhm_th[0] = (u8)odm_get_bb_reg(p_dm, ODM_REG_NHM_TH3_TO_TH0_11N, MASKBYTE0);
546 		nhm_th[1] = (u8)odm_get_bb_reg(p_dm, ODM_REG_NHM_TH3_TO_TH0_11N, MASKBYTE1);
547 		nhm_th[2] = (u8)odm_get_bb_reg(p_dm, ODM_REG_NHM_TH3_TO_TH0_11N, MASKBYTE2);
548 		nhm_th[3] = (u8)odm_get_bb_reg(p_dm, ODM_REG_NHM_TH3_TO_TH0_11N, MASKBYTE3);
549 		nhm_th[4] = (u8)odm_get_bb_reg(p_dm, ODM_REG_NHM_TH7_TO_TH4_11N, MASKBYTE0);
550 		nhm_th[5] = (u8)odm_get_bb_reg(p_dm, ODM_REG_NHM_TH7_TO_TH4_11N, MASKBYTE1);
551 		nhm_th[6] = (u8)odm_get_bb_reg(p_dm, ODM_REG_NHM_TH7_TO_TH4_11N, MASKBYTE2);
552 		nhm_th[7] = (u8)odm_get_bb_reg(p_dm, ODM_REG_NHM_TH7_TO_TH4_11N, MASKBYTE3);
553 		nhm_th[8] = (u8)odm_get_bb_reg(p_dm, ODM_REG_NHM_TH8_11N, MASKBYTE0);
554 		nhm_th[9] = (u8)odm_get_bb_reg(p_dm, ODM_REG_NHM_TH9_TH10_11N, MASKBYTE2);
555 		nhm_th[10] = (u8)odm_get_bb_reg(p_dm, ODM_REG_NHM_TH9_TH10_11N, MASKBYTE3);
556 	}
557 
558 	for (i = 0; i <= 10; i++) {
559 
560 		if (nhm_th[i] != ccx_info->nhm_th[i]) {
561 			PHYDM_DBG(p_dm, DBG_ENV_MNTR,
562 				("nhm_th[%d] != ccx_info->nhm_th[%d]!!\n", i, i));
563 		}
564 	}
565 
566 	igi = (u8)odm_get_bb_reg(p_dm, 0xC50, MASKBYTE0);
567 	phydm_set_nhm_th_by_igi(p_dm, igi);
568 
569 	ccx_info->nhm_period = monitor_time;
570 	ccx_info->nhm_inexclude_cca = NHM_EXCLUDE_CCA;
571 	ccx_info->nhm_inexclude_txon = NHM_EXCLUDE_TXON;
572 
573 	phydm_nhm_setting(p_dm, SET_NHM_SETTING);
574 	phydm_nhm_trigger(p_dm);
575 
576 	ccx_info->echo_clm_en = true;
577 	ccx_info->clm_period = monitor_time;
578 	phydm_clm_setting(p_dm);
579 	phydm_clm_trigger(p_dm);
580 
581 }
582 
583 void
phydm_ccx_monitor_result(void * p_dm_void)584 phydm_ccx_monitor_result(
585 	void			*p_dm_void
586 )
587 {
588 	struct PHY_DM_STRUCT	*p_dm = (struct PHY_DM_STRUCT *)p_dm_void;
589 	struct _CCX_INFO		*ccx_info = &p_dm->dm_ccx_info;
590 	u32						nhm_ratio = 0, clm_ratio = 0;
591 
592 	if (!(p_dm->support_ability & ODM_BB_ENV_MONITOR))
593 		return;
594 
595 	if (phydm_check_nhm_rdy(p_dm))
596 		phydm_get_nhm_result(p_dm);
597 
598 	if (phydm_check_clm_rdy(p_dm))
599 		phydm_get_clm_result(p_dm);
600 
601 	if (ccx_info->clm_period != 0)
602 		clm_ratio = (ccx_info->clm_result*100) / ccx_info->clm_period;
603 
604 	if (ccx_info->nhm_result_total != 0)
605 		nhm_ratio = ((ccx_info->nhm_result_total - ccx_info->nhm_result[0])*100) >> 8;
606 
607 	ccx_info->clm_ratio = (u8)clm_ratio;
608 	ccx_info->nhm_ratio = (u8)nhm_ratio;
609 
610 	PHYDM_DBG(p_dm, DBG_ENV_MNTR, ("[%s]echo_igi=0x%x, nhm_ratio=%d, clm_ratio=%d\n",
611 		__FUNCTION__, ccx_info->echo_igi, nhm_ratio, clm_ratio));
612 
613 	}
614 
615 void
phydm_set_nhm_th_by_igi(void * p_dm_void,u8 igi)616 phydm_set_nhm_th_by_igi(
617 	void			*p_dm_void,
618 	u8				igi
619 )
620 {
621 	struct PHY_DM_STRUCT	*p_dm = (struct PHY_DM_STRUCT *)p_dm_void;
622 	struct _CCX_INFO		*ccx_info = &p_dm->dm_ccx_info;
623 	u8	i;
624 
625 	ccx_info->echo_igi = igi;
626 	ccx_info->nhm_th[0] = (ccx_info->echo_igi - CCA_CAP) * IGI_TO_NHM_TH_MULTIPLIER;
627 	for (i = 1; i <= 10; i++)
628 		ccx_info->nhm_th[i] = ccx_info->nhm_th[0] + 2 * IGI_TO_NHM_TH_MULTIPLIER * i;
629 
630 	PHYDM_DBG(p_dm, DBG_ENV_MNTR, ("[%s]echo_igi=0x%x\n", __FUNCTION__, ccx_info->echo_igi));
631 }
632 
633