1 // SPDX-License-Identifier: GPL-2.0
2 /******************************************************************************
3 *
4 * Copyright(c) 2007 - 2011 Realtek Corporation. All rights reserved.
5 *
6 ******************************************************************************/
7
8 #include <linux/kernel.h>
9 #include "odm_precomp.h"
10
CheckPositive(struct dm_odm_t * pDM_Odm,const u32 Condition1,const u32 Condition2)11 static bool CheckPositive(
12 struct dm_odm_t *pDM_Odm, const u32 Condition1, const u32 Condition2
13 )
14 {
15 u8 _BoardType =
16 ((pDM_Odm->BoardType & BIT4) >> 4) << 0 | /* _GLNA */
17 ((pDM_Odm->BoardType & BIT3) >> 3) << 1 | /* _GPA */
18 ((pDM_Odm->BoardType & BIT7) >> 7) << 2 | /* _ALNA */
19 ((pDM_Odm->BoardType & BIT6) >> 6) << 3 | /* _APA */
20 ((pDM_Odm->BoardType & BIT2) >> 2) << 4; /* _BT */
21
22 u32 cond1 = Condition1, cond2 = Condition2;
23 u32 driver1 =
24 pDM_Odm->CutVersion << 24 |
25 pDM_Odm->SupportPlatform << 16 |
26 pDM_Odm->PackageType << 12 |
27 pDM_Odm->SupportInterface << 8 |
28 _BoardType;
29
30 u32 driver2 =
31 pDM_Odm->TypeGLNA << 0 |
32 pDM_Odm->TypeGPA << 8 |
33 pDM_Odm->TypeALNA << 16 |
34 pDM_Odm->TypeAPA << 24;
35
36
37 /* Value Defined Check =============== */
38 /* QFN Type [15:12] and Cut Version [27:24] need to do value check */
39
40 if (((cond1 & 0x0000F000) != 0) && ((cond1 & 0x0000F000) != (driver1 & 0x0000F000)))
41 return false;
42 if (((cond1 & 0x0F000000) != 0) && ((cond1 & 0x0F000000) != (driver1 & 0x0F000000)))
43 return false;
44
45 /* Bit Defined Check ================ */
46 /* We don't care [31:28] and [23:20] */
47 /* */
48 cond1 &= 0x000F0FFF;
49 driver1 &= 0x000F0FFF;
50
51 if ((cond1 & driver1) == cond1) {
52 u32 bitMask = 0;
53
54 if ((cond1 & 0x0F) == 0) /* BoardType is DONTCARE */
55 return true;
56
57 if ((cond1 & BIT0) != 0) /* GLNA */
58 bitMask |= 0x000000FF;
59 if ((cond1 & BIT1) != 0) /* GPA */
60 bitMask |= 0x0000FF00;
61 if ((cond1 & BIT2) != 0) /* ALNA */
62 bitMask |= 0x00FF0000;
63 if ((cond1 & BIT3) != 0) /* APA */
64 bitMask |= 0xFF000000;
65
66 /* BoardType of each RF path is matched */
67 if ((cond2 & bitMask) == (driver2 & bitMask))
68 return true;
69 }
70 return false;
71 }
72
CheckNegative(struct dm_odm_t * pDM_Odm,const u32 Condition1,const u32 Condition2)73 static bool CheckNegative(
74 struct dm_odm_t *pDM_Odm, const u32 Condition1, const u32 Condition2
75 )
76 {
77 return true;
78 }
79
80 /******************************************************************************
81 * AGC_TAB.TXT
82 ******************************************************************************/
83
84 static u32 Array_MP_8723B_AGC_TAB[] = {
85 0xC78, 0xFD000001,
86 0xC78, 0xFC010001,
87 0xC78, 0xFB020001,
88 0xC78, 0xFA030001,
89 0xC78, 0xF9040001,
90 0xC78, 0xF8050001,
91 0xC78, 0xF7060001,
92 0xC78, 0xF6070001,
93 0xC78, 0xF5080001,
94 0xC78, 0xF4090001,
95 0xC78, 0xF30A0001,
96 0xC78, 0xF20B0001,
97 0xC78, 0xF10C0001,
98 0xC78, 0xF00D0001,
99 0xC78, 0xEF0E0001,
100 0xC78, 0xEE0F0001,
101 0xC78, 0xED100001,
102 0xC78, 0xEC110001,
103 0xC78, 0xEB120001,
104 0xC78, 0xEA130001,
105 0xC78, 0xE9140001,
106 0xC78, 0xE8150001,
107 0xC78, 0xE7160001,
108 0xC78, 0xE6170001,
109 0xC78, 0xE5180001,
110 0xC78, 0xE4190001,
111 0xC78, 0xE31A0001,
112 0xC78, 0xA51B0001,
113 0xC78, 0xA41C0001,
114 0xC78, 0xA31D0001,
115 0xC78, 0x671E0001,
116 0xC78, 0x661F0001,
117 0xC78, 0x65200001,
118 0xC78, 0x64210001,
119 0xC78, 0x63220001,
120 0xC78, 0x4A230001,
121 0xC78, 0x49240001,
122 0xC78, 0x48250001,
123 0xC78, 0x47260001,
124 0xC78, 0x46270001,
125 0xC78, 0x45280001,
126 0xC78, 0x44290001,
127 0xC78, 0x432A0001,
128 0xC78, 0x422B0001,
129 0xC78, 0x292C0001,
130 0xC78, 0x282D0001,
131 0xC78, 0x272E0001,
132 0xC78, 0x262F0001,
133 0xC78, 0x0A300001,
134 0xC78, 0x09310001,
135 0xC78, 0x08320001,
136 0xC78, 0x07330001,
137 0xC78, 0x06340001,
138 0xC78, 0x05350001,
139 0xC78, 0x04360001,
140 0xC78, 0x03370001,
141 0xC78, 0x02380001,
142 0xC78, 0x01390001,
143 0xC78, 0x013A0001,
144 0xC78, 0x013B0001,
145 0xC78, 0x013C0001,
146 0xC78, 0x013D0001,
147 0xC78, 0x013E0001,
148 0xC78, 0x013F0001,
149 0xC78, 0xFC400001,
150 0xC78, 0xFB410001,
151 0xC78, 0xFA420001,
152 0xC78, 0xF9430001,
153 0xC78, 0xF8440001,
154 0xC78, 0xF7450001,
155 0xC78, 0xF6460001,
156 0xC78, 0xF5470001,
157 0xC78, 0xF4480001,
158 0xC78, 0xF3490001,
159 0xC78, 0xF24A0001,
160 0xC78, 0xF14B0001,
161 0xC78, 0xF04C0001,
162 0xC78, 0xEF4D0001,
163 0xC78, 0xEE4E0001,
164 0xC78, 0xED4F0001,
165 0xC78, 0xEC500001,
166 0xC78, 0xEB510001,
167 0xC78, 0xEA520001,
168 0xC78, 0xE9530001,
169 0xC78, 0xE8540001,
170 0xC78, 0xE7550001,
171 0xC78, 0xE6560001,
172 0xC78, 0xE5570001,
173 0xC78, 0xE4580001,
174 0xC78, 0xE3590001,
175 0xC78, 0xA65A0001,
176 0xC78, 0xA55B0001,
177 0xC78, 0xA45C0001,
178 0xC78, 0xA35D0001,
179 0xC78, 0x675E0001,
180 0xC78, 0x665F0001,
181 0xC78, 0x65600001,
182 0xC78, 0x64610001,
183 0xC78, 0x63620001,
184 0xC78, 0x62630001,
185 0xC78, 0x61640001,
186 0xC78, 0x48650001,
187 0xC78, 0x47660001,
188 0xC78, 0x46670001,
189 0xC78, 0x45680001,
190 0xC78, 0x44690001,
191 0xC78, 0x436A0001,
192 0xC78, 0x426B0001,
193 0xC78, 0x286C0001,
194 0xC78, 0x276D0001,
195 0xC78, 0x266E0001,
196 0xC78, 0x256F0001,
197 0xC78, 0x24700001,
198 0xC78, 0x09710001,
199 0xC78, 0x08720001,
200 0xC78, 0x07730001,
201 0xC78, 0x06740001,
202 0xC78, 0x05750001,
203 0xC78, 0x04760001,
204 0xC78, 0x03770001,
205 0xC78, 0x02780001,
206 0xC78, 0x01790001,
207 0xC78, 0x017A0001,
208 0xC78, 0x017B0001,
209 0xC78, 0x017C0001,
210 0xC78, 0x017D0001,
211 0xC78, 0x017E0001,
212 0xC78, 0x017F0001,
213 0xC50, 0x69553422,
214 0xC50, 0x69553420,
215 0x824, 0x00390204,
216
217 };
218
ODM_ReadAndConfig_MP_8723B_AGC_TAB(struct dm_odm_t * pDM_Odm)219 void ODM_ReadAndConfig_MP_8723B_AGC_TAB(struct dm_odm_t *pDM_Odm)
220 {
221 u32 i = 0;
222 u32 ArrayLen = ARRAY_SIZE(Array_MP_8723B_AGC_TAB);
223 u32 *Array = Array_MP_8723B_AGC_TAB;
224
225 for (i = 0; i < ArrayLen; i += 2) {
226 u32 v1 = Array[i];
227 u32 v2 = Array[i+1];
228
229 /* This (offset, data) pair doesn't care the condition. */
230 if (v1 < 0x40000000) {
231 odm_ConfigBB_AGC_8723B(pDM_Odm, v1, bMaskDWord, v2);
232 continue;
233 } else {
234 /* This line is the beginning of branch. */
235 bool bMatched = true;
236 u8 cCond = (u8)((v1 & (BIT29|BIT28)) >> 28);
237
238 if (cCond == COND_ELSE) { /* ELSE, ENDIF */
239 bMatched = true;
240 READ_NEXT_PAIR(v1, v2, i);
241 } else if (!CheckPositive(pDM_Odm, v1, v2)) {
242 bMatched = false;
243 READ_NEXT_PAIR(v1, v2, i);
244 READ_NEXT_PAIR(v1, v2, i);
245 } else {
246 READ_NEXT_PAIR(v1, v2, i);
247 if (!CheckNegative(pDM_Odm, v1, v2))
248 bMatched = false;
249 else
250 bMatched = true;
251 READ_NEXT_PAIR(v1, v2, i);
252 }
253
254 if (!bMatched) {
255 /* Condition isn't matched.
256 * Discard the following (offset, data) pairs.
257 */
258 while (v1 < 0x40000000 && i < ArrayLen-2)
259 READ_NEXT_PAIR(v1, v2, i);
260
261 i -= 2; /* prevent from for-loop += 2 */
262 } else {
263 /* Configure matched pairs and skip to end of if-else. */
264 while (v1 < 0x40000000 && i < ArrayLen-2) {
265 odm_ConfigBB_AGC_8723B(pDM_Odm, v1, bMaskDWord, v2);
266 READ_NEXT_PAIR(v1, v2, i);
267 }
268
269 /* Keeps reading until ENDIF. */
270 cCond = (u8)((v1 & (BIT29|BIT28)) >> 28);
271 while (cCond != COND_ENDIF && i < ArrayLen-2) {
272 READ_NEXT_PAIR(v1, v2, i);
273 cCond = (u8)((v1 & (BIT29|BIT28)) >> 28);
274 }
275 }
276 }
277 }
278 }
279
280 /******************************************************************************
281 * PHY_REG.TXT
282 ******************************************************************************/
283
284 static u32 Array_MP_8723B_PHY_REG[] = {
285 0x800, 0x80040000,
286 0x804, 0x00000003,
287 0x808, 0x0000FC00,
288 0x80C, 0x0000000A,
289 0x810, 0x10001331,
290 0x814, 0x020C3D10,
291 0x818, 0x02200385,
292 0x81C, 0x00000000,
293 0x820, 0x01000100,
294 0x824, 0x00190204,
295 0x828, 0x00000000,
296 0x82C, 0x00000000,
297 0x830, 0x00000000,
298 0x834, 0x00000000,
299 0x838, 0x00000000,
300 0x83C, 0x00000000,
301 0x840, 0x00010000,
302 0x844, 0x00000000,
303 0x848, 0x00000000,
304 0x84C, 0x00000000,
305 0x850, 0x00000000,
306 0x854, 0x00000000,
307 0x858, 0x569A11A9,
308 0x85C, 0x01000014,
309 0x860, 0x66F60110,
310 0x864, 0x061F0649,
311 0x868, 0x00000000,
312 0x86C, 0x27272700,
313 0x870, 0x07000760,
314 0x874, 0x25004000,
315 0x878, 0x00000808,
316 0x87C, 0x00000000,
317 0x880, 0xB0000C1C,
318 0x884, 0x00000001,
319 0x888, 0x00000000,
320 0x88C, 0xCCC000C0,
321 0x890, 0x00000800,
322 0x894, 0xFFFFFFFE,
323 0x898, 0x40302010,
324 0x89C, 0x00706050,
325 0x900, 0x00000000,
326 0x904, 0x00000023,
327 0x908, 0x00000000,
328 0x90C, 0x81121111,
329 0x910, 0x00000002,
330 0x914, 0x00000201,
331 0xA00, 0x00D047C8,
332 0xA04, 0x80FF800C,
333 0xA08, 0x8C838300,
334 0xA0C, 0x2E7F120F,
335 0xA10, 0x9500BB78,
336 0xA14, 0x1114D028,
337 0xA18, 0x00881117,
338 0xA1C, 0x89140F00,
339 0xA20, 0x1A1B0000,
340 0xA24, 0x090E1317,
341 0xA28, 0x00000204,
342 0xA2C, 0x00D30000,
343 0xA70, 0x101FBF00,
344 0xA74, 0x00000007,
345 0xA78, 0x00000900,
346 0xA7C, 0x225B0606,
347 0xA80, 0x21806490,
348 0xB2C, 0x00000000,
349 0xC00, 0x48071D40,
350 0xC04, 0x03A05611,
351 0xC08, 0x000000E4,
352 0xC0C, 0x6C6C6C6C,
353 0xC10, 0x08800000,
354 0xC14, 0x40000100,
355 0xC18, 0x08800000,
356 0xC1C, 0x40000100,
357 0xC20, 0x00000000,
358 0xC24, 0x00000000,
359 0xC28, 0x00000000,
360 0xC2C, 0x00000000,
361 0xC30, 0x69E9AC44,
362 0xC34, 0x469652AF,
363 0xC38, 0x49795994,
364 0xC3C, 0x0A97971C,
365 0xC40, 0x1F7C403F,
366 0xC44, 0x000100B7,
367 0xC48, 0xEC020107,
368 0xC4C, 0x007F037F,
369 0xC50, 0x69553420,
370 0xC54, 0x43BC0094,
371 0xC58, 0x00013149,
372 0xC5C, 0x00250492,
373 0xC60, 0x00000000,
374 0xC64, 0x7112848B,
375 0xC68, 0x47C00BFF,
376 0xC6C, 0x00000036,
377 0xC70, 0x2C7F000D,
378 0xC74, 0x020610DB,
379 0xC78, 0x0000001F,
380 0xC7C, 0x00B91612,
381 0xC80, 0x390000E4,
382 0xC84, 0x20F60000,
383 0xC88, 0x40000100,
384 0xC8C, 0x20200000,
385 0xC90, 0x00020E1A,
386 0xC94, 0x00000000,
387 0xC98, 0x00020E1A,
388 0xC9C, 0x00007F7F,
389 0xCA0, 0x00000000,
390 0xCA4, 0x000300A0,
391 0xCA8, 0x00000000,
392 0xCAC, 0x00000000,
393 0xCB0, 0x00000000,
394 0xCB4, 0x00000000,
395 0xCB8, 0x00000000,
396 0xCBC, 0x28000000,
397 0xCC0, 0x00000000,
398 0xCC4, 0x00000000,
399 0xCC8, 0x00000000,
400 0xCCC, 0x00000000,
401 0xCD0, 0x00000000,
402 0xCD4, 0x00000000,
403 0xCD8, 0x64B22427,
404 0xCDC, 0x00766932,
405 0xCE0, 0x00222222,
406 0xCE4, 0x00000000,
407 0xCE8, 0x37644302,
408 0xCEC, 0x2F97D40C,
409 0xD00, 0x00000740,
410 0xD04, 0x40020401,
411 0xD08, 0x0000907F,
412 0xD0C, 0x20010201,
413 0xD10, 0xA0633333,
414 0xD14, 0x3333BC53,
415 0xD18, 0x7A8F5B6F,
416 0xD2C, 0xCC979975,
417 0xD30, 0x00000000,
418 0xD34, 0x80608000,
419 0xD38, 0x00000000,
420 0xD3C, 0x00127353,
421 0xD40, 0x00000000,
422 0xD44, 0x00000000,
423 0xD48, 0x00000000,
424 0xD4C, 0x00000000,
425 0xD50, 0x6437140A,
426 0xD54, 0x00000000,
427 0xD58, 0x00000282,
428 0xD5C, 0x30032064,
429 0xD60, 0x4653DE68,
430 0xD64, 0x04518A3C,
431 0xD68, 0x00002101,
432 0xD6C, 0x2A201C16,
433 0xD70, 0x1812362E,
434 0xD74, 0x322C2220,
435 0xD78, 0x000E3C24,
436 0xE00, 0x2D2D2D2D,
437 0xE04, 0x2D2D2D2D,
438 0xE08, 0x0390272D,
439 0xE10, 0x2D2D2D2D,
440 0xE14, 0x2D2D2D2D,
441 0xE18, 0x2D2D2D2D,
442 0xE1C, 0x2D2D2D2D,
443 0xE28, 0x00000000,
444 0xE30, 0x1000DC1F,
445 0xE34, 0x10008C1F,
446 0xE38, 0x02140102,
447 0xE3C, 0x681604C2,
448 0xE40, 0x01007C00,
449 0xE44, 0x01004800,
450 0xE48, 0xFB000000,
451 0xE4C, 0x000028D1,
452 0xE50, 0x1000DC1F,
453 0xE54, 0x10008C1F,
454 0xE58, 0x02140102,
455 0xE5C, 0x28160D05,
456 0xE60, 0x00000008,
457 0xE68, 0x001B2556,
458 0xE6C, 0x00C00096,
459 0xE70, 0x00C00096,
460 0xE74, 0x01000056,
461 0xE78, 0x01000014,
462 0xE7C, 0x01000056,
463 0xE80, 0x01000014,
464 0xE84, 0x00C00096,
465 0xE88, 0x01000056,
466 0xE8C, 0x00C00096,
467 0xED0, 0x00C00096,
468 0xED4, 0x00C00096,
469 0xED8, 0x00C00096,
470 0xEDC, 0x000000D6,
471 0xEE0, 0x000000D6,
472 0xEEC, 0x01C00016,
473 0xF14, 0x00000003,
474 0xF4C, 0x00000000,
475 0xF00, 0x00000300,
476 0x820, 0x01000100,
477 0x800, 0x83040000,
478
479 };
480
ODM_ReadAndConfig_MP_8723B_PHY_REG(struct dm_odm_t * pDM_Odm)481 void ODM_ReadAndConfig_MP_8723B_PHY_REG(struct dm_odm_t *pDM_Odm)
482 {
483 u32 i = 0;
484 u32 ArrayLen = ARRAY_SIZE(Array_MP_8723B_PHY_REG);
485 u32 *Array = Array_MP_8723B_PHY_REG;
486
487 for (i = 0; i < ArrayLen; i += 2) {
488 u32 v1 = Array[i];
489 u32 v2 = Array[i+1];
490
491 /* This (offset, data) pair doesn't care the condition. */
492 if (v1 < 0x40000000) {
493 odm_ConfigBB_PHY_8723B(pDM_Odm, v1, bMaskDWord, v2);
494 continue;
495 } else {
496 /* This line is the beginning of branch. */
497 bool bMatched = true;
498 u8 cCond = (u8)((v1 & (BIT29|BIT28)) >> 28);
499
500 if (cCond == COND_ELSE) { /* ELSE, ENDIF */
501 bMatched = true;
502 READ_NEXT_PAIR(v1, v2, i);
503 } else if (!CheckPositive(pDM_Odm, v1, v2)) {
504 bMatched = false;
505 READ_NEXT_PAIR(v1, v2, i);
506 READ_NEXT_PAIR(v1, v2, i);
507 } else {
508 READ_NEXT_PAIR(v1, v2, i);
509 if (!CheckNegative(pDM_Odm, v1, v2))
510 bMatched = false;
511 else
512 bMatched = true;
513 READ_NEXT_PAIR(v1, v2, i);
514 }
515
516 if (!bMatched) {
517 /* Condition isn't matched.
518 * Discard the following (offset, data) pairs.
519 */
520 while (v1 < 0x40000000 && i < ArrayLen-2)
521 READ_NEXT_PAIR(v1, v2, i);
522
523 i -= 2; /* prevent from for-loop += 2 */
524 } else { /* Configure matched pairs and skip to end of if-else. */
525 while (v1 < 0x40000000 && i < ArrayLen-2) {
526 odm_ConfigBB_PHY_8723B(pDM_Odm, v1, bMaskDWord, v2);
527 READ_NEXT_PAIR(v1, v2, i);
528 }
529
530 /* Keeps reading until ENDIF. */
531 cCond = (u8)((v1 & (BIT29|BIT28)) >> 28);
532 while (cCond != COND_ENDIF && i < ArrayLen-2) {
533 READ_NEXT_PAIR(v1, v2, i);
534 cCond = (u8)((v1 & (BIT29|BIT28)) >> 28);
535 }
536 }
537 }
538 }
539 }
540
541 /******************************************************************************
542 * PHY_REG_PG.TXT
543 ******************************************************************************/
544
545 static u32 Array_MP_8723B_PHY_REG_PG[] = {
546 0, 0x00000e08, 0x0000ff00, 0x00003800,
547 0, 0x0000086c, 0xffffff00, 0x32343600,
548 0, 0x00000e00, 0xffffffff, 0x40424444,
549 0, 0x00000e04, 0xffffffff, 0x28323638,
550 0, 0x00000e10, 0xffffffff, 0x38404244,
551 0, 0x00000e14, 0xffffffff, 0x26303436
552 };
553
ODM_ReadAndConfig_MP_8723B_PHY_REG_PG(struct dm_odm_t * pDM_Odm)554 void ODM_ReadAndConfig_MP_8723B_PHY_REG_PG(struct dm_odm_t *pDM_Odm)
555 {
556 u32 i = 0;
557 u32 *Array = Array_MP_8723B_PHY_REG_PG;
558
559 pDM_Odm->PhyRegPgVersion = 1;
560 pDM_Odm->PhyRegPgValueType = PHY_REG_PG_EXACT_VALUE;
561
562 for (i = 0; i < ARRAY_SIZE(Array_MP_8723B_PHY_REG_PG); i += 4) {
563 u32 v1 = Array[i];
564 u32 v2 = Array[i+1];
565 u32 v3 = Array[i+2];
566 u32 v4 = Array[i+3];
567
568 odm_ConfigBB_PHY_REG_PG_8723B(pDM_Odm, v1, v2, v3, v4);
569 }
570 }
571