staging: r8188eu: clean up spacing style issues in core/rtw_efuse.c
[linux-2.6-microblaze.git] / drivers / staging / r8188eu / core / rtw_efuse.c
1 // SPDX-License-Identifier: GPL-2.0
2 /* Copyright(c) 2007 - 2011 Realtek Corporation. */
3
4 #define _RTW_EFUSE_C_
5
6 #include "../include/osdep_service.h"
7 #include "../include/drv_types.h"
8 #include "../include/rtw_efuse.h"
9
10 /*------------------------Define local variable------------------------------*/
11 u8 fakeEfuseBank;
12 u32 fakeEfuseUsedBytes;
13 u8 fakeEfuseContent[EFUSE_MAX_HW_SIZE] = {0};
14 u8 fakeEfuseInitMap[EFUSE_MAX_MAP_LEN] = {0};
15 u8 fakeEfuseModifiedMap[EFUSE_MAX_MAP_LEN] = {0};
16
17 u32 BTEfuseUsedBytes;
18 u8 BTEfuseContent[EFUSE_MAX_BT_BANK][EFUSE_MAX_HW_SIZE];
19 u8 BTEfuseInitMap[EFUSE_BT_MAX_MAP_LEN] = {0};
20 u8 BTEfuseModifiedMap[EFUSE_BT_MAX_MAP_LEN] = {0};
21
22 u32 fakeBTEfuseUsedBytes;
23 u8 fakeBTEfuseContent[EFUSE_MAX_BT_BANK][EFUSE_MAX_HW_SIZE];
24 u8 fakeBTEfuseInitMap[EFUSE_BT_MAX_MAP_LEN] = {0};
25 u8 fakeBTEfuseModifiedMap[EFUSE_BT_MAX_MAP_LEN] = {0};
26 /*------------------------Define local variable------------------------------*/
27
28 /*  */
29 #define REG_EFUSE_CTRL          0x0030
30 #define EFUSE_CTRL                      REG_EFUSE_CTRL          /*  E-Fuse Control. */
31 /*  */
32
33 bool
34 Efuse_Read1ByteFromFakeContent(
35                         struct adapter *pAdapter,
36                         u16 Offset,
37                 u8 *Value);
38 bool
39 Efuse_Read1ByteFromFakeContent(
40                         struct adapter *pAdapter,
41                         u16 Offset,
42                 u8 *Value)
43 {
44         if (Offset >= EFUSE_MAX_HW_SIZE)
45                 return false;
46         if (fakeEfuseBank == 0)
47                 *Value = fakeEfuseContent[Offset];
48         else
49                 *Value = fakeBTEfuseContent[fakeEfuseBank - 1][Offset];
50         return true;
51 }
52
53 static bool
54 Efuse_Write1ByteToFakeContent(
55                         struct adapter *pAdapter,
56                         u16 Offset,
57                         u8 Value)
58 {
59         if (Offset >= EFUSE_MAX_HW_SIZE)
60                 return false;
61         if (fakeEfuseBank == 0) {
62                 fakeEfuseContent[Offset] = Value;
63         } else {
64                 fakeBTEfuseContent[fakeEfuseBank - 1][Offset] = Value;
65         }
66         return true;
67 }
68
69 /*-----------------------------------------------------------------------------
70  * Function:    Efuse_PowerSwitch
71  *
72  * Overview:    When we want to enable write operation, we should change to
73  *                              pwr on state. When we stop write, we should switch to 500k mode
74  *                              and disable LDO 2.5V.
75  *
76  * Input:       NONE
77  *
78  * Output:      NONE
79  *
80  * Return:      NONE
81  *
82  * Revised History:
83  * When                 Who             Remark
84  * 11/17/2008   MHC             Create Version 0.
85  *
86  *---------------------------------------------------------------------------*/
87 void
88 Efuse_PowerSwitch(
89                 struct adapter *pAdapter,
90                 u8 write,
91                 u8 PwrState)
92 {
93         pAdapter->HalFunc.EfusePowerSwitch(pAdapter, write, PwrState);
94 }
95
96 /*-----------------------------------------------------------------------------
97  * Function:    efuse_GetCurrentSize
98  *
99  * Overview:    Get current efuse size!!!
100  *
101  * Input:       NONE
102  *
103  * Output:      NONE
104  *
105  * Return:      NONE
106  *
107  * Revised History:
108  * When                 Who             Remark
109  * 11/16/2008   MHC             Create Version 0.
110  *
111  *---------------------------------------------------------------------------*/
112 u16
113 Efuse_GetCurrentSize(
114         struct adapter *pAdapter,
115         u8 efuseType,
116         bool pseudo)
117 {
118         u16 ret = 0;
119
120         ret = pAdapter->HalFunc.EfuseGetCurrentSize(pAdapter, efuseType, pseudo);
121
122         return ret;
123 }
124
125 /*  11/16/2008 MH Add description. Get current efuse area enabled word!!. */
126 u8
127 Efuse_CalculateWordCnts(u8 word_en)
128 {
129         u8 word_cnts = 0;
130         if (!(word_en & BIT(0)))
131                 word_cnts++; /*  0 : write enable */
132         if (!(word_en & BIT(1)))
133                 word_cnts++;
134         if (!(word_en & BIT(2)))
135                 word_cnts++;
136         if (!(word_en & BIT(3)))
137                 word_cnts++;
138         return word_cnts;
139 }
140
141 /*  */
142 /*      Description: */
143 /*              Execute E-Fuse read byte operation. */
144 /*              Referred from SD1 Richard. */
145 /*  */
146 /*      Assumption: */
147 /*              1. Boot from E-Fuse and successfully auto-load. */
148 /*              2. PASSIVE_LEVEL (USB interface) */
149 /*  */
150 /*      Created by Roger, 2008.10.21. */
151 /*  */
152 void
153 ReadEFuseByte(
154                 struct adapter *Adapter,
155                 u16 _offset,
156                 u8 *pbuf,
157                 bool pseudo)
158 {
159         u32 value32;
160         u8 readbyte;
161         u16 retry;
162
163         if (pseudo) {
164                 Efuse_Read1ByteFromFakeContent(Adapter, _offset, pbuf);
165                 return;
166         }
167
168         /* Write Address */
169         rtw_write8(Adapter, EFUSE_CTRL + 1, (_offset & 0xff));
170         readbyte = rtw_read8(Adapter, EFUSE_CTRL + 2);
171         rtw_write8(Adapter, EFUSE_CTRL + 2, ((_offset >> 8) & 0x03) | (readbyte & 0xfc));
172
173         /* Write bit 32 0 */
174         readbyte = rtw_read8(Adapter, EFUSE_CTRL + 3);
175         rtw_write8(Adapter, EFUSE_CTRL + 3, (readbyte & 0x7f));
176
177         /* Check bit 32 read-ready */
178         retry = 0;
179         value32 = rtw_read32(Adapter, EFUSE_CTRL);
180         while (!(((value32 >> 24) & 0xff) & 0x80)  && (retry < 10000)) {
181                 value32 = rtw_read32(Adapter, EFUSE_CTRL);
182                 retry++;
183         }
184
185         /*  20100205 Joseph: Add delay suggested by SD1 Victor. */
186         /*  This fix the problem that Efuse read error in high temperature condition. */
187         /*  Designer says that there shall be some delay after ready bit is set, or the */
188         /*  result will always stay on last data we read. */
189         udelay(50);
190         value32 = rtw_read32(Adapter, EFUSE_CTRL);
191
192         *pbuf = (u8)(value32 & 0xff);
193 }
194
195 /*  */
196 /*      Description: */
197 /*              1. Execute E-Fuse read byte operation according as map offset and */
198 /*                  save to E-Fuse table. */
199 /*              2. Referred from SD1 Richard. */
200 /*  */
201 /*      Assumption: */
202 /*              1. Boot from E-Fuse and successfully auto-load. */
203 /*              2. PASSIVE_LEVEL (USB interface) */
204 /*  */
205 /*      Created by Roger, 2008.10.21. */
206 /*  */
207 /*      2008/12/12 MH   1. Reorganize code flow and reserve bytes. and add description. */
208 /*                                      2. Add efuse utilization collect. */
209 /*      2008/12/22 MH   Read Efuse must check if we write section 1 data again!!! Sec1 */
210 /*                                      write addr must be after sec5. */
211 /*  */
212
213 static void efuse_ReadEFuse(struct adapter *Adapter, u8 efuseType, u16 _offset, u16 _size_byte, u8 *pbuf, bool pseudo)
214 {
215         Adapter->HalFunc.ReadEFuse(Adapter, efuseType, _offset, _size_byte, pbuf, pseudo);
216 }
217
218 void EFUSE_GetEfuseDefinition(struct adapter *pAdapter, u8 efuseType, u8 type, void *pOut, bool pseudo
219         )
220 {
221         pAdapter->HalFunc.EFUSEGetEfuseDefinition(pAdapter, efuseType, type, pOut, pseudo);
222 }
223
224 /*-----------------------------------------------------------------------------
225  * Function:    EFUSE_Read1Byte
226  *
227  * Overview:    Copy from WMAC fot EFUSE read 1 byte.
228  *
229  * Input:       NONE
230  *
231  * Output:      NONE
232  *
233  * Return:      NONE
234  *
235  * Revised History:
236  * When                 Who             Remark
237  * 09/23/2008   MHC             Copy from WMAC.
238  *
239  *---------------------------------------------------------------------------*/
240 u8 EFUSE_Read1Byte(struct adapter *Adapter, u16 Address)
241 {
242         u8 data;
243         u8 Bytetemp = {0x00};
244         u8 temp = {0x00};
245         u32 k = 0;
246         u16 contentLen = 0;
247
248         EFUSE_GetEfuseDefinition(Adapter, EFUSE_WIFI, TYPE_EFUSE_REAL_CONTENT_LEN, (void *)&contentLen, false);
249
250         if (Address < contentLen) {     /* E-fuse 512Byte */
251                 /* Write E-fuse Register address bit0~7 */
252                 temp = Address & 0xFF;
253                 rtw_write8(Adapter, EFUSE_CTRL + 1, temp);
254                 Bytetemp = rtw_read8(Adapter, EFUSE_CTRL + 2);
255                 /* Write E-fuse Register address bit8~9 */
256                 temp = ((Address >> 8) & 0x03) | (Bytetemp & 0xFC);
257                 rtw_write8(Adapter, EFUSE_CTRL + 2, temp);
258
259                 /* Write 0x30[31]= 0 */
260                 Bytetemp = rtw_read8(Adapter, EFUSE_CTRL + 3);
261                 temp = Bytetemp & 0x7F;
262                 rtw_write8(Adapter, EFUSE_CTRL + 3, temp);
263
264                 /* Wait Write-ready (0x30[31]= 1) */
265                 Bytetemp = rtw_read8(Adapter, EFUSE_CTRL + 3);
266                 while (!(Bytetemp & 0x80)) {
267                         Bytetemp = rtw_read8(Adapter, EFUSE_CTRL + 3);
268                         k++;
269                         if (k == 1000) {
270                                 k = 0;
271                                 break;
272                         }
273                 }
274                 data = rtw_read8(Adapter, EFUSE_CTRL);
275                 return data;
276         } else {
277                 return 0xFF;
278         }
279
280 } /* EFUSE_Read1Byte */
281
282 /*  11/16/2008 MH Read one byte from real Efuse. */
283 u8 efuse_OneByteRead(struct adapter *pAdapter, u16 addr, u8 *data, bool pseudo)
284 {
285         u8 tmpidx = 0;
286         u8 result;
287
288         if (pseudo) {
289                 result = Efuse_Read1ByteFromFakeContent(pAdapter, addr, data);
290                 return result;
291         }
292         /*  -----------------e-fuse reg ctrl --------------------------------- */
293         /* address */
294         rtw_write8(pAdapter, EFUSE_CTRL + 1, (u8)(addr & 0xff));
295         rtw_write8(pAdapter, EFUSE_CTRL + 2, ((u8)((addr >> 8) & 0x03)) |
296                    (rtw_read8(pAdapter, EFUSE_CTRL + 2) & 0xFC));
297
298         rtw_write8(pAdapter, EFUSE_CTRL + 3,  0x72);/* read cmd */
299
300         while (!(0x80 & rtw_read8(pAdapter, EFUSE_CTRL + 3)) && (tmpidx < 100))
301                 tmpidx++;
302         if (tmpidx < 100) {
303                 *data = rtw_read8(pAdapter, EFUSE_CTRL);
304                 result = true;
305         } else {
306                 *data = 0xff;
307                 result = false;
308         }
309         return result;
310 }
311
312 /*  11/16/2008 MH Write one byte to reald Efuse. */
313 u8 efuse_OneByteWrite(struct adapter *pAdapter, u16 addr, u8 data, bool pseudo)
314 {
315         u8 tmpidx = 0;
316         u8 result;
317
318         if (pseudo) {
319                 result = Efuse_Write1ByteToFakeContent(pAdapter, addr, data);
320                 return result;
321         }
322
323         /*  -----------------e-fuse reg ctrl --------------------------------- */
324         /* address */
325         rtw_write8(pAdapter, EFUSE_CTRL + 1, (u8)(addr & 0xff));
326         rtw_write8(pAdapter, EFUSE_CTRL + 2,
327                    (rtw_read8(pAdapter, EFUSE_CTRL + 2) & 0xFC) |
328                    (u8)((addr >> 8) & 0x03));
329         rtw_write8(pAdapter, EFUSE_CTRL, data);/* data */
330
331         rtw_write8(pAdapter, EFUSE_CTRL + 3, 0xF2);/* write cmd */
332
333         while ((0x80 &  rtw_read8(pAdapter, EFUSE_CTRL + 3)) && (tmpidx < 100))
334                 tmpidx++;
335
336         if (tmpidx < 100)
337                 result = true;
338         else
339                 result = false;
340
341         return result;
342 }
343
344 int Efuse_PgPacketRead(struct adapter *pAdapter, u8 offset, u8 *data, bool pseudo)
345 {
346         int     ret = 0;
347
348         ret =  pAdapter->HalFunc.Efuse_PgPacketRead(pAdapter, offset, data, pseudo);
349
350         return ret;
351 }
352
353 int Efuse_PgPacketWrite(struct adapter *pAdapter, u8 offset, u8 word_en, u8 *data, bool pseudo)
354 {
355         int ret;
356
357         ret =  pAdapter->HalFunc.Efuse_PgPacketWrite(pAdapter, offset, word_en, data, pseudo);
358
359         return ret;
360 }
361
362 static int Efuse_PgPacketWrite_BT(struct adapter *pAdapter, u8 offset, u8 word_en, u8 *data, bool pseudo)
363 {
364         int ret;
365
366         ret =  pAdapter->HalFunc.Efuse_PgPacketWrite_BT(pAdapter, offset, word_en, data, pseudo);
367
368         return ret;
369 }
370
371 /*-----------------------------------------------------------------------------
372  * Function:    efuse_WordEnableDataRead
373  *
374  * Overview:    Read allowed word in current efuse section data.
375  *
376  * Input:       NONE
377  *
378  * Output:      NONE
379  *
380  * Return:      NONE
381  *
382  * Revised History:
383  * When                 Who             Remark
384  * 11/16/2008   MHC             Create Version 0.
385  * 11/21/2008   MHC             Fix Write bug when we only enable late word.
386  *
387  *---------------------------------------------------------------------------*/
388 void efuse_WordEnableDataRead(u8 word_en, u8 *sourdata, u8 *targetdata)
389 {
390         if (!(word_en & BIT(0))) {
391                 targetdata[0] = sourdata[0];
392                 targetdata[1] = sourdata[1];
393         }
394         if (!(word_en & BIT(1))) {
395                 targetdata[2] = sourdata[2];
396                 targetdata[3] = sourdata[3];
397         }
398         if (!(word_en & BIT(2))) {
399                 targetdata[4] = sourdata[4];
400                 targetdata[5] = sourdata[5];
401         }
402         if (!(word_en & BIT(3))) {
403                 targetdata[6] = sourdata[6];
404                 targetdata[7] = sourdata[7];
405         }
406 }
407
408 u8 Efuse_WordEnableDataWrite(struct adapter *pAdapter, u16 efuse_addr, u8 word_en, u8 *data, bool pseudo)
409 {
410         u8 ret = 0;
411
412         ret =  pAdapter->HalFunc.Efuse_WordEnableDataWrite(pAdapter, efuse_addr, word_en, data, pseudo);
413
414         return ret;
415 }
416
417 static u8 efuse_read8(struct adapter *padapter, u16 address, u8 *value)
418 {
419         return efuse_OneByteRead(padapter, address, value, false);
420 }
421
422 static u8 efuse_write8(struct adapter *padapter, u16 address, u8 *value)
423 {
424         return efuse_OneByteWrite(padapter, address, *value, false);
425 }
426
427 /*
428  * read/wirte raw efuse data
429  */
430 u8 rtw_efuse_access(struct adapter *padapter, u8 write, u16 start_addr, u16 cnts, u8 *data)
431 {
432         int i = 0;
433         u16 real_content_len = 0, max_available_size = 0;
434         u8 res = _FAIL;
435         u8 (*rw8)(struct adapter *, u16, u8*);
436
437         EFUSE_GetEfuseDefinition(padapter, EFUSE_WIFI, TYPE_EFUSE_REAL_CONTENT_LEN, (void *)&real_content_len, false);
438         EFUSE_GetEfuseDefinition(padapter, EFUSE_WIFI, TYPE_AVAILABLE_EFUSE_BYTES_TOTAL, (void *)&max_available_size, false);
439
440         if (start_addr > real_content_len)
441                 return _FAIL;
442
443         if (write) {
444                 if ((start_addr + cnts) > max_available_size)
445                         return _FAIL;
446                 rw8 = &efuse_write8;
447         } else {
448                 rw8 = &efuse_read8;
449         }
450
451         Efuse_PowerSwitch(padapter, write, true);
452
453         /*  e-fuse one byte read / write */
454         for (i = 0; i < cnts; i++) {
455                 if (start_addr >= real_content_len) {
456                         res = _FAIL;
457                         break;
458                 }
459
460                 res = rw8(padapter, start_addr++, data++);
461                 if (_FAIL == res)
462                         break;
463         }
464
465         Efuse_PowerSwitch(padapter, write, false);
466
467         return res;
468 }
469 /*  */
470 u16 efuse_GetMaxSize(struct adapter *padapter)
471 {
472         u16 max_size;
473         EFUSE_GetEfuseDefinition(padapter, EFUSE_WIFI, TYPE_AVAILABLE_EFUSE_BYTES_TOTAL, (void *)&max_size, false);
474         return max_size;
475 }
476 /*  */
477 u8 efuse_GetCurrentSize(struct adapter *padapter, u16 *size)
478 {
479         Efuse_PowerSwitch(padapter, false, true);
480         *size = Efuse_GetCurrentSize(padapter, EFUSE_WIFI, false);
481         Efuse_PowerSwitch(padapter, false, false);
482
483         return _SUCCESS;
484 }
485 /*  */
486 u8 rtw_efuse_map_read(struct adapter *padapter, u16 addr, u16 cnts, u8 *data)
487 {
488         u16 mapLen = 0;
489
490         EFUSE_GetEfuseDefinition(padapter, EFUSE_WIFI, TYPE_EFUSE_MAP_LEN, (void *)&mapLen, false);
491
492         if ((addr + cnts) > mapLen)
493                 return _FAIL;
494
495         Efuse_PowerSwitch(padapter, false, true);
496
497         efuse_ReadEFuse(padapter, EFUSE_WIFI, addr, cnts, data, false);
498
499         Efuse_PowerSwitch(padapter, false, false);
500
501         return _SUCCESS;
502 }
503
504 u8 rtw_BT_efuse_map_read(struct adapter *padapter, u16 addr, u16 cnts, u8 *data)
505 {
506         u16 mapLen = 0;
507
508         EFUSE_GetEfuseDefinition(padapter, EFUSE_BT, TYPE_EFUSE_MAP_LEN, (void *)&mapLen, false);
509
510         if ((addr + cnts) > mapLen)
511                 return _FAIL;
512
513         Efuse_PowerSwitch(padapter, false, true);
514
515         efuse_ReadEFuse(padapter, EFUSE_BT, addr, cnts, data, false);
516
517         Efuse_PowerSwitch(padapter, false, false);
518
519         return _SUCCESS;
520 }
521 /*  */
522 u8 rtw_efuse_map_write(struct adapter *padapter, u16 addr, u16 cnts, u8 *data)
523 {
524         u8 offset, word_en;
525         u8 *map;
526         u8 newdata[PGPKT_DATA_SIZE + 1];
527         s32     i, idx;
528         u8 ret = _SUCCESS;
529         u16 mapLen = 0;
530
531         EFUSE_GetEfuseDefinition(padapter, EFUSE_WIFI, TYPE_EFUSE_MAP_LEN, (void *)&mapLen, false);
532
533         if ((addr + cnts) > mapLen)
534                 return _FAIL;
535
536         map = kzalloc(mapLen, GFP_KERNEL);
537         if (!map)
538                 return _FAIL;
539
540         ret = rtw_efuse_map_read(padapter, 0, mapLen, map);
541         if (ret == _FAIL)
542                 goto exit;
543
544         Efuse_PowerSwitch(padapter, true, true);
545
546         offset = (addr >> 3);
547         word_en = 0xF;
548         memset(newdata, 0xFF, PGPKT_DATA_SIZE + 1);
549         i = addr & 0x7; /*  index of one package */
550         idx = 0;        /*  data index */
551
552         if (i & 0x1) {
553                 /*  odd start */
554                 if (data[idx] != map[addr + idx]) {
555                         word_en &= ~BIT(i >> 1);
556                         newdata[i - 1] = map[addr + idx - 1];
557                         newdata[i] = data[idx];
558                 }
559                 i++;
560                 idx++;
561         }
562         do {
563                 for (; i < PGPKT_DATA_SIZE; i += 2) {
564                         if (cnts == idx)
565                                 break;
566                         if ((cnts - idx) == 1) {
567                                 if (data[idx] != map[addr + idx]) {
568                                         word_en &= ~BIT(i >> 1);
569                                         newdata[i] = data[idx];
570                                         newdata[i + 1] = map[addr + idx + 1];
571                                 }
572                                 idx++;
573                                 break;
574                         } else {
575                                 if ((data[idx] != map[addr + idx]) ||
576                                     (data[idx + 1] != map[addr + idx + 1])) {
577                                         word_en &= ~BIT(i >> 1);
578                                         newdata[i] = data[idx];
579                                         newdata[i + 1] = data[idx + 1];
580                                 }
581                                 idx += 2;
582                         }
583                         if (idx == cnts)
584                                 break;
585                 }
586
587                 if (word_en != 0xF) {
588                         ret = Efuse_PgPacketWrite(padapter, offset, word_en, newdata, false);
589                         DBG_88E("offset=%x\n", offset);
590                         DBG_88E("word_en=%x\n", word_en);
591
592                         for (i = 0; i < PGPKT_DATA_SIZE; i++)
593                                 DBG_88E("data=%x \t", newdata[i]);
594                         if (ret == _FAIL)
595                                 break;
596                 }
597
598                 if (idx == cnts)
599                         break;
600
601                 offset++;
602                 i = 0;
603                 word_en = 0xF;
604                 memset(newdata, 0xFF, PGPKT_DATA_SIZE);
605         } while (1);
606
607         Efuse_PowerSwitch(padapter, true, false);
608 exit:
609         kfree(map);
610         return ret;
611 }
612
613 /*  */
614 u8 rtw_BT_efuse_map_write(struct adapter *padapter, u16 addr, u16 cnts, u8 *data)
615 {
616         u8 offset, word_en;
617         u8 *map;
618         u8 newdata[PGPKT_DATA_SIZE + 1];
619         s32     i, idx;
620         u8 ret = _SUCCESS;
621         u16 mapLen = 0;
622
623         EFUSE_GetEfuseDefinition(padapter, EFUSE_BT, TYPE_EFUSE_MAP_LEN, (void *)&mapLen, false);
624
625         if ((addr + cnts) > mapLen)
626                 return _FAIL;
627
628         map = kzalloc(mapLen, GFP_KERNEL);
629         if (!map)
630                 return _FAIL;
631
632         ret = rtw_BT_efuse_map_read(padapter, 0, mapLen, map);
633         if (ret == _FAIL)
634                 goto exit;
635
636         Efuse_PowerSwitch(padapter, true, true);
637
638         offset = (addr >> 3);
639         word_en = 0xF;
640         memset(newdata, 0xFF, PGPKT_DATA_SIZE + 1);
641         i = addr & 0x7; /*  index of one package */
642         idx = 0;        /*  data index */
643
644         if (i & 0x1) {
645                 /*  odd start */
646                 if (data[idx] != map[addr + idx]) {
647                         word_en &= ~BIT(i >> 1);
648                         newdata[i - 1] = map[addr + idx - 1];
649                         newdata[i] = data[idx];
650                 }
651                 i++;
652                 idx++;
653         }
654         do {
655                 for (; i < PGPKT_DATA_SIZE; i += 2) {
656                         if (cnts == idx)
657                                 break;
658                         if ((cnts - idx) == 1) {
659                                 if (data[idx] != map[addr + idx]) {
660                                         word_en &= ~BIT(i >> 1);
661                                         newdata[i] = data[idx];
662                                         newdata[i + 1] = map[addr + idx + 1];
663                                 }
664                                 idx++;
665                                 break;
666                         } else {
667                                 if ((data[idx] != map[addr + idx]) ||
668                                     (data[idx + 1] != map[addr + idx + 1])) {
669                                         word_en &= ~BIT(i >> 1);
670                                         newdata[i] = data[idx];
671                                         newdata[i + 1] = data[idx + 1];
672                                 }
673                                 idx += 2;
674                         }
675                         if (idx == cnts)
676                                 break;
677                 }
678
679                 if (word_en != 0xF) {
680                         DBG_88E("%s: offset=%#X\n", __func__, offset);
681                         DBG_88E("%s: word_en=%#X\n", __func__, word_en);
682                         DBG_88E("%s: data=", __func__);
683                         for (i = 0; i < PGPKT_DATA_SIZE; i++)
684                                 DBG_88E("0x%02X ", newdata[i]);
685                         DBG_88E("\n");
686
687                         ret = Efuse_PgPacketWrite_BT(padapter, offset, word_en, newdata, false);
688                         if (ret == _FAIL)
689                                 break;
690                 }
691
692                 if (idx == cnts)
693                         break;
694
695                 offset++;
696                 i = 0;
697                 word_en = 0xF;
698                 memset(newdata, 0xFF, PGPKT_DATA_SIZE);
699         } while (1);
700
701         Efuse_PowerSwitch(padapter, true, false);
702
703 exit:
704
705         kfree(map);
706
707         return ret;
708 }
709
710 /*-----------------------------------------------------------------------------
711  * Function:    efuse_ShadowRead1Byte
712  *                      efuse_ShadowRead2Byte
713  *                      efuse_ShadowRead4Byte
714  *
715  * Overview:    Read from efuse init map by one/two/four bytes !!!!!
716  *
717  * Input:       NONE
718  *
719  * Output:      NONE
720  *
721  * Return:      NONE
722  *
723  * Revised History:
724  * When                 Who             Remark
725  * 11/12/2008   MHC             Create Version 0.
726  *
727  *---------------------------------------------------------------------------*/
728 static void
729 efuse_ShadowRead1Byte(
730                 struct adapter *pAdapter,
731                 u16 Offset,
732                 u8 *Value)
733 {
734         struct eeprom_priv *pEEPROM = GET_EEPROM_EFUSE_PRIV(pAdapter);
735
736         *Value = pEEPROM->efuse_eeprom_data[Offset];
737
738 }       /*  EFUSE_ShadowRead1Byte */
739
740 /* Read Two Bytes */
741 static void
742 efuse_ShadowRead2Byte(
743                 struct adapter *pAdapter,
744                 u16 Offset,
745                 u16 *Value)
746 {
747         struct eeprom_priv *pEEPROM = GET_EEPROM_EFUSE_PRIV(pAdapter);
748
749         *Value = pEEPROM->efuse_eeprom_data[Offset];
750         *Value |= pEEPROM->efuse_eeprom_data[Offset + 1] << 8;
751
752 }       /*  EFUSE_ShadowRead2Byte */
753
754 /* Read Four Bytes */
755 static void
756 efuse_ShadowRead4Byte(
757                 struct adapter *pAdapter,
758                 u16 Offset,
759                 u32 *Value)
760 {
761         struct eeprom_priv *pEEPROM = GET_EEPROM_EFUSE_PRIV(pAdapter);
762
763         *Value = pEEPROM->efuse_eeprom_data[Offset];
764         *Value |= pEEPROM->efuse_eeprom_data[Offset + 1] << 8;
765         *Value |= pEEPROM->efuse_eeprom_data[Offset + 2] << 16;
766         *Value |= pEEPROM->efuse_eeprom_data[Offset + 3] << 24;
767
768 }       /*  efuse_ShadowRead4Byte */
769
770 /*-----------------------------------------------------------------------------
771  * Function:    Efuse_ReadAllMap
772  *
773  * Overview:    Read All Efuse content
774  *
775  * Input:       NONE
776  *
777  * Output:      NONE
778  *
779  * Return:      NONE
780  *
781  * Revised History:
782  * When                 Who             Remark
783  * 11/11/2008   MHC             Create Version 0.
784  *
785  *---------------------------------------------------------------------------*/
786 static void Efuse_ReadAllMap(struct adapter *pAdapter, u8 efuseType, u8 *Efuse, bool pseudo)
787 {
788         u16 mapLen = 0;
789
790         Efuse_PowerSwitch(pAdapter, false, true);
791
792         EFUSE_GetEfuseDefinition(pAdapter, efuseType, TYPE_EFUSE_MAP_LEN, (void *)&mapLen, pseudo);
793
794         efuse_ReadEFuse(pAdapter, efuseType, 0, mapLen, Efuse, pseudo);
795
796         Efuse_PowerSwitch(pAdapter, false, false);
797 }
798
799 /*-----------------------------------------------------------------------------
800  * Function:    EFUSE_ShadowMapUpdate
801  *
802  * Overview:    Transfer current EFUSE content to shadow init and modify map.
803  *
804  * Input:       NONE
805  *
806  * Output:      NONE
807  *
808  * Return:      NONE
809  *
810  * Revised History:
811  * When                 Who             Remark
812  * 11/13/2008   MHC             Create Version 0.
813  *
814  *---------------------------------------------------------------------------*/
815 void EFUSE_ShadowMapUpdate(
816         struct adapter *pAdapter,
817         u8 efuseType,
818         bool pseudo)
819 {
820         struct eeprom_priv *pEEPROM = GET_EEPROM_EFUSE_PRIV(pAdapter);
821         u16 mapLen = 0;
822
823         EFUSE_GetEfuseDefinition(pAdapter, efuseType, TYPE_EFUSE_MAP_LEN, (void *)&mapLen, pseudo);
824
825         if (pEEPROM->bautoload_fail_flag)
826                 memset(pEEPROM->efuse_eeprom_data, 0xFF, mapLen);
827         else
828                 Efuse_ReadAllMap(pAdapter, efuseType, pEEPROM->efuse_eeprom_data, pseudo);
829 } /*  EFUSE_ShadowMapUpdate */
830
831 /*-----------------------------------------------------------------------------
832  * Function:    EFUSE_ShadowRead
833  *
834  * Overview:    Read from efuse init map !!!!!
835  *
836  * Input:       NONE
837  *
838  * Output:      NONE
839  *
840  * Return:      NONE
841  *
842  * Revised History:
843  * When                 Who             Remark
844  * 11/12/2008   MHC             Create Version 0.
845  *
846  *---------------------------------------------------------------------------*/
847 void EFUSE_ShadowRead(struct adapter *pAdapter, u8 Type, u16 Offset, u32 *Value)
848 {
849         if (Type == 1)
850                 efuse_ShadowRead1Byte(pAdapter, Offset, (u8 *)Value);
851         else if (Type == 2)
852                 efuse_ShadowRead2Byte(pAdapter, Offset, (u16 *)Value);
853         else if (Type == 4)
854                 efuse_ShadowRead4Byte(pAdapter, Offset, (u32 *)Value);
855
856 }       /*  EFUSE_ShadowRead */