This source file includes following definitions.
- rtl88eu_phy_rf6052_set_bandwidth
- rtl88eu_phy_rf6052_set_cck_txpower
- getpowerbase88e
- get_rx_power_val_by_reg
- write_ofdm_pwr_reg
- rtl88eu_phy_rf6052_set_ofdm_txpower
1
2
3
4
5
6
7
8 #include <osdep_service.h>
9 #include <drv_types.h>
10 #include <phy.h>
11 #include <rf.h>
12 #include <rtl8188e_hal.h>
13
14 void rtl88eu_phy_rf6052_set_bandwidth(struct adapter *adapt,
15 enum ht_channel_width bandwidth)
16 {
17 struct hal_data_8188e *hal_data = adapt->HalData;
18
19 switch (bandwidth) {
20 case HT_CHANNEL_WIDTH_20:
21 hal_data->RfRegChnlVal[0] = ((hal_data->RfRegChnlVal[0] &
22 0xfffff3ff) | BIT(10) | BIT(11));
23 phy_set_rf_reg(adapt, RF_PATH_A, RF_CHNLBW, bRFRegOffsetMask,
24 hal_data->RfRegChnlVal[0]);
25 break;
26 case HT_CHANNEL_WIDTH_40:
27 hal_data->RfRegChnlVal[0] = ((hal_data->RfRegChnlVal[0] &
28 0xfffff3ff) | BIT(10));
29 phy_set_rf_reg(adapt, RF_PATH_A, RF_CHNLBW, bRFRegOffsetMask,
30 hal_data->RfRegChnlVal[0]);
31 break;
32 default:
33 break;
34 }
35 }
36
37 void rtl88eu_phy_rf6052_set_cck_txpower(struct adapter *adapt, u8 *powerlevel)
38 {
39 struct hal_data_8188e *hal_data = adapt->HalData;
40 struct dm_priv *pdmpriv = &hal_data->dmpriv;
41 struct mlme_ext_priv *pmlmeext = &adapt->mlmeextpriv;
42 u32 tx_agc[2] = {0, 0}, tmpval = 0, pwrtrac_value;
43 u8 idx1, idx2;
44 u8 *ptr;
45 u8 direction;
46
47 if (pmlmeext->sitesurvey_res.state == SCAN_PROCESS) {
48 tx_agc[RF_PATH_A] = 0x3f3f3f3f;
49 tx_agc[RF_PATH_B] = 0x3f3f3f3f;
50 for (idx1 = RF_PATH_A; idx1 <= RF_PATH_B; idx1++) {
51 tx_agc[idx1] = powerlevel[idx1] |
52 (powerlevel[idx1]<<8) |
53 (powerlevel[idx1]<<16) |
54 (powerlevel[idx1]<<24);
55 }
56 } else {
57 if (pdmpriv->DynamicTxHighPowerLvl == TxHighPwrLevel_Level1) {
58 tx_agc[RF_PATH_A] = 0x10101010;
59 tx_agc[RF_PATH_B] = 0x10101010;
60 } else if (pdmpriv->DynamicTxHighPowerLvl == TxHighPwrLevel_Level2) {
61 tx_agc[RF_PATH_A] = 0x00000000;
62 tx_agc[RF_PATH_B] = 0x00000000;
63 } else {
64 for (idx1 = RF_PATH_A; idx1 <= RF_PATH_B; idx1++) {
65 tx_agc[idx1] = powerlevel[idx1] |
66 (powerlevel[idx1]<<8) |
67 (powerlevel[idx1]<<16) |
68 (powerlevel[idx1]<<24);
69 }
70 if (hal_data->EEPROMRegulatory == 0) {
71 tmpval = hal_data->MCSTxPowerLevelOriginalOffset[0][6] +
72 (hal_data->MCSTxPowerLevelOriginalOffset[0][7]<<8);
73 tx_agc[RF_PATH_A] += tmpval;
74
75 tmpval = hal_data->MCSTxPowerLevelOriginalOffset[0][14] +
76 (hal_data->MCSTxPowerLevelOriginalOffset[0][15]<<24);
77 tx_agc[RF_PATH_B] += tmpval;
78 }
79 }
80 }
81 for (idx1 = RF_PATH_A; idx1 <= RF_PATH_B; idx1++) {
82 ptr = (u8 *)(&(tx_agc[idx1]));
83 for (idx2 = 0; idx2 < 4; idx2++) {
84 if (*ptr > RF6052_MAX_TX_PWR)
85 *ptr = RF6052_MAX_TX_PWR;
86 ptr++;
87 }
88 }
89 rtl88eu_dm_txpower_track_adjust(&hal_data->odmpriv, 1, &direction,
90 &pwrtrac_value);
91
92 if (direction == 1) {
93
94 tx_agc[0] += pwrtrac_value;
95 tx_agc[1] += pwrtrac_value;
96 } else if (direction == 2) {
97
98 tx_agc[0] -= pwrtrac_value;
99 tx_agc[1] -= pwrtrac_value;
100 }
101
102
103 tmpval = tx_agc[RF_PATH_A]&0xff;
104 phy_set_bb_reg(adapt, rTxAGC_A_CCK1_Mcs32, bMaskByte1, tmpval);
105 tmpval = tx_agc[RF_PATH_A]>>8;
106 phy_set_bb_reg(adapt, rTxAGC_B_CCK11_A_CCK2_11, 0xffffff00, tmpval);
107
108
109 tmpval = tx_agc[RF_PATH_B]>>24;
110 phy_set_bb_reg(adapt, rTxAGC_B_CCK11_A_CCK2_11, bMaskByte0, tmpval);
111 tmpval = tx_agc[RF_PATH_B]&0x00ffffff;
112 phy_set_bb_reg(adapt, rTxAGC_B_CCK1_55_Mcs32, 0xffffff00, tmpval);
113 }
114
115
116
117 static void getpowerbase88e(struct adapter *adapt, u8 *pwr_level_ofdm,
118 u8 *pwr_level_bw20, u8 *pwr_level_bw40,
119 u8 channel, u32 *ofdmbase, u32 *mcs_base)
120 {
121 u32 powerbase0, powerbase1;
122 u8 i, powerlevel[2];
123
124 for (i = 0; i < 2; i++) {
125 powerbase0 = pwr_level_ofdm[i];
126
127 powerbase0 = (powerbase0<<24) | (powerbase0<<16) |
128 (powerbase0<<8) | powerbase0;
129 *(ofdmbase+i) = powerbase0;
130 }
131
132 if (adapt->HalData->CurrentChannelBW == HT_CHANNEL_WIDTH_20)
133 powerlevel[0] = pwr_level_bw20[0];
134 else
135 powerlevel[0] = pwr_level_bw40[0];
136 powerbase1 = powerlevel[0];
137 powerbase1 = (powerbase1<<24) | (powerbase1<<16) |
138 (powerbase1<<8) | powerbase1;
139 *mcs_base = powerbase1;
140 }
141 static void get_rx_power_val_by_reg(struct adapter *adapt, u8 channel,
142 u8 index, u32 *powerbase0, u32 *powerbase1,
143 u32 *out_val)
144 {
145 struct hal_data_8188e *hal_data = adapt->HalData;
146 struct dm_priv *pdmpriv = &hal_data->dmpriv;
147 u8 i, chnlGroup = 0, pwr_diff_limit[4], customer_pwr_limit;
148 s8 pwr_diff = 0;
149 u32 write_val, customer_limit, rf;
150 u8 regulatory = hal_data->EEPROMRegulatory;
151
152
153
154 for (rf = 0; rf < 2; rf++) {
155 u8 j = index + (rf ? 8 : 0);
156
157 switch (regulatory) {
158 case 0:
159 chnlGroup = 0;
160 write_val = hal_data->MCSTxPowerLevelOriginalOffset[chnlGroup][index+(rf ? 8 : 0)] +
161 ((index < 2) ? powerbase0[rf] : powerbase1[rf]);
162 break;
163 case 1:
164
165 if (hal_data->pwrGroupCnt == 1)
166 chnlGroup = 0;
167 if (hal_data->pwrGroupCnt >= hal_data->PGMaxGroup)
168 Hal_GetChnlGroup88E(channel, &chnlGroup);
169
170 write_val = hal_data->MCSTxPowerLevelOriginalOffset[chnlGroup][index+(rf ? 8 : 0)] +
171 ((index < 2) ? powerbase0[rf] : powerbase1[rf]);
172 break;
173 case 2:
174
175 write_val = (index < 2) ? powerbase0[rf] : powerbase1[rf];
176 break;
177 case 3:
178
179 chnlGroup = 0;
180
181 if (index < 2)
182 pwr_diff = hal_data->TxPwrLegacyHtDiff[rf][channel-1];
183 else if (hal_data->CurrentChannelBW == HT_CHANNEL_WIDTH_20)
184 pwr_diff = hal_data->TxPwrHt20Diff[rf][channel-1];
185
186 if (hal_data->CurrentChannelBW == HT_CHANNEL_WIDTH_40)
187 customer_pwr_limit = hal_data->PwrGroupHT40[rf][channel-1];
188 else
189 customer_pwr_limit = hal_data->PwrGroupHT20[rf][channel-1];
190
191 if (pwr_diff >= customer_pwr_limit)
192 pwr_diff = 0;
193 else
194 pwr_diff = customer_pwr_limit - pwr_diff;
195
196 for (i = 0; i < 4; i++) {
197 pwr_diff_limit[i] = (u8)((hal_data->MCSTxPowerLevelOriginalOffset[chnlGroup][j] &
198 (0x7f << (i * 8))) >> (i * 8));
199
200 if (pwr_diff_limit[i] > pwr_diff)
201 pwr_diff_limit[i] = pwr_diff;
202 }
203 customer_limit = (pwr_diff_limit[3]<<24) |
204 (pwr_diff_limit[2]<<16) |
205 (pwr_diff_limit[1]<<8) |
206 (pwr_diff_limit[0]);
207 write_val = customer_limit + ((index < 2) ? powerbase0[rf] : powerbase1[rf]);
208 break;
209 default:
210 chnlGroup = 0;
211 write_val = hal_data->MCSTxPowerLevelOriginalOffset[chnlGroup][j] +
212 ((index < 2) ? powerbase0[rf] : powerbase1[rf]);
213 break;
214 }
215
216
217
218
219 if (pdmpriv->DynamicTxHighPowerLvl == TxHighPwrLevel_Level1)
220 write_val = 0x14141414;
221 else if (pdmpriv->DynamicTxHighPowerLvl == TxHighPwrLevel_Level2)
222 write_val = 0x00000000;
223
224 *(out_val+rf) = write_val;
225 }
226 }
227
228 static void write_ofdm_pwr_reg(struct adapter *adapt, u8 index, u32 *pvalue)
229 {
230 u16 regoffset_a[6] = { rTxAGC_A_Rate18_06, rTxAGC_A_Rate54_24,
231 rTxAGC_A_Mcs03_Mcs00, rTxAGC_A_Mcs07_Mcs04,
232 rTxAGC_A_Mcs11_Mcs08, rTxAGC_A_Mcs15_Mcs12 };
233 u16 regoffset_b[6] = { rTxAGC_B_Rate18_06, rTxAGC_B_Rate54_24,
234 rTxAGC_B_Mcs03_Mcs00, rTxAGC_B_Mcs07_Mcs04,
235 rTxAGC_B_Mcs11_Mcs08, rTxAGC_B_Mcs15_Mcs12 };
236 u8 i, rf, pwr_val[4];
237 u32 write_val;
238 u16 regoffset;
239
240 for (rf = 0; rf < 2; rf++) {
241 write_val = pvalue[rf];
242 for (i = 0; i < 4; i++) {
243 pwr_val[i] = (u8)((write_val & (0x7f<<(i*8)))>>(i*8));
244 if (pwr_val[i] > RF6052_MAX_TX_PWR)
245 pwr_val[i] = RF6052_MAX_TX_PWR;
246 }
247 write_val = (pwr_val[3]<<24) | (pwr_val[2]<<16) |
248 (pwr_val[1]<<8) | pwr_val[0];
249
250 if (rf == 0)
251 regoffset = regoffset_a[index];
252 else
253 regoffset = regoffset_b[index];
254
255 phy_set_bb_reg(adapt, regoffset, bMaskDWord, write_val);
256 }
257 }
258
259 void rtl88eu_phy_rf6052_set_ofdm_txpower(struct adapter *adapt,
260 u8 *pwr_level_ofdm,
261 u8 *pwr_level_bw20,
262 u8 *pwr_level_bw40, u8 channel)
263 {
264 u32 write_val[2], powerbase0[2], powerbase1[2], pwrtrac_value;
265 u8 direction;
266 u8 index = 0;
267
268 getpowerbase88e(adapt, pwr_level_ofdm, pwr_level_bw20, pwr_level_bw40,
269 channel, &powerbase0[0], &powerbase1[0]);
270
271 rtl88eu_dm_txpower_track_adjust(&adapt->HalData->odmpriv, 0,
272 &direction, &pwrtrac_value);
273
274 for (index = 0; index < 6; index++) {
275 get_rx_power_val_by_reg(adapt, channel, index,
276 &powerbase0[0], &powerbase1[0],
277 &write_val[0]);
278
279 if (direction == 1) {
280 write_val[0] += pwrtrac_value;
281 write_val[1] += pwrtrac_value;
282 } else if (direction == 2) {
283 write_val[0] -= pwrtrac_value;
284 write_val[1] -= pwrtrac_value;
285 }
286 write_ofdm_pwr_reg(adapt, index, &write_val[0]);
287 }
288 }