3 #define DWORD unsigned int
5 static int BcmDoChipSelect(struct bcm_mini_adapter
*Adapter
, unsigned int offset
);
6 static int BcmGetActiveDSD(struct bcm_mini_adapter
*Adapter
);
7 static int BcmGetActiveISO(struct bcm_mini_adapter
*Adapter
);
8 static unsigned int BcmGetEEPROMSize(struct bcm_mini_adapter
*Adapter
);
9 static int BcmGetFlashCSInfo(struct bcm_mini_adapter
*Adapter
);
10 static unsigned int BcmGetFlashSectorSize(struct bcm_mini_adapter
*Adapter
, unsigned int FlashSectorSizeSig
, unsigned int FlashSectorSize
);
12 static VOID
BcmValidateNvmType(struct bcm_mini_adapter
*Adapter
);
13 static int BcmGetNvmSize(struct bcm_mini_adapter
*Adapter
);
14 static unsigned int BcmGetFlashSize(struct bcm_mini_adapter
*Adapter
);
15 static NVM_TYPE
BcmGetNvmType(struct bcm_mini_adapter
*Adapter
);
17 static int BcmGetSectionValEndOffset(struct bcm_mini_adapter
*Adapter
, FLASH2X_SECTION_VAL eFlash2xSectionVal
);
19 static B_UINT8
IsOffsetWritable(struct bcm_mini_adapter
*Adapter
, unsigned int uiOffset
);
20 static int IsSectionWritable(struct bcm_mini_adapter
*Adapter
, FLASH2X_SECTION_VAL Section
);
21 static int IsSectionExistInVendorInfo(struct bcm_mini_adapter
*Adapter
, FLASH2X_SECTION_VAL section
);
23 static int ReadDSDPriority(struct bcm_mini_adapter
*Adapter
, FLASH2X_SECTION_VAL dsd
);
24 static int ReadDSDSignature(struct bcm_mini_adapter
*Adapter
, FLASH2X_SECTION_VAL dsd
);
25 static int ReadISOPriority(struct bcm_mini_adapter
*Adapter
, FLASH2X_SECTION_VAL iso
);
26 static int ReadISOSignature(struct bcm_mini_adapter
*Adapter
, FLASH2X_SECTION_VAL iso
);
28 static int CorruptDSDSig(struct bcm_mini_adapter
*Adapter
, FLASH2X_SECTION_VAL eFlash2xSectionVal
);
29 static int CorruptISOSig(struct bcm_mini_adapter
*Adapter
, FLASH2X_SECTION_VAL eFlash2xSectionVal
);
30 static int SaveHeaderIfPresent(struct bcm_mini_adapter
*Adapter
, PUCHAR pBuff
, unsigned int uiSectAlignAddr
);
31 static int WriteToFlashWithoutSectorErase(struct bcm_mini_adapter
*Adapter
, PUINT pBuff
,
32 FLASH2X_SECTION_VAL eFlash2xSectionVal
,
33 unsigned int uiOffset
, unsigned int uiNumBytes
);
34 static FLASH2X_SECTION_VAL
getHighestPriDSD(struct bcm_mini_adapter
*Adapter
);
35 static FLASH2X_SECTION_VAL
getHighestPriISO(struct bcm_mini_adapter
*Adapter
);
37 static int BeceemFlashBulkRead(
38 struct bcm_mini_adapter
*Adapter
,
40 unsigned int uiOffset
,
41 unsigned int uiNumBytes
);
43 static int BeceemFlashBulkWrite(
44 struct bcm_mini_adapter
*Adapter
,
46 unsigned int uiOffset
,
47 unsigned int uiNumBytes
,
50 static int GetFlashBaseAddr(struct bcm_mini_adapter
*Adapter
);
52 static int ReadBeceemEEPROMBulk(struct bcm_mini_adapter
*Adapter
, unsigned int dwAddress
, unsigned int *pdwData
, unsigned int dwNumData
);
54 /* Procedure: ReadEEPROMStatusRegister
56 * Description: Reads the standard EEPROM Status Register.
59 * Adapter - ptr to Adapter object instance
63 static UCHAR
ReadEEPROMStatusRegister(struct bcm_mini_adapter
*Adapter
)
66 DWORD dwRetries
= MAX_EEPROM_RETRIES
* RETRIES_PER_DELAY
;
67 unsigned int uiStatus
= 0;
68 unsigned int value
= 0;
69 unsigned int value1
= 0;
71 /* Read the EEPROM status register */
72 value
= EEPROM_READ_STATUS_REGISTER
;
73 wrmalt(Adapter
, EEPROM_CMDQ_SPI_REG
, &value
, sizeof(value
));
75 while (dwRetries
!= 0) {
78 rdmalt(Adapter
, EEPROM_SPI_Q_STATUS1_REG
, &uiStatus
, sizeof(uiStatus
));
79 if (Adapter
->device_removed
== TRUE
) {
80 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Modem has got removed hence exiting....");
84 /* Wait for Avail bit to be set. */
85 if ((uiStatus
& EEPROM_READ_DATA_AVAIL
) != 0) {
86 /* Clear the Avail/Full bits - which ever is set. */
87 value
= uiStatus
& (EEPROM_READ_DATA_AVAIL
| EEPROM_READ_DATA_FULL
);
88 wrmalt(Adapter
, EEPROM_SPI_Q_STATUS1_REG
, &value
, sizeof(value
));
91 rdmalt(Adapter
, EEPROM_READ_DATAQ_REG
, &value
, sizeof(value
));
92 uiData
= (UCHAR
)value
;
99 rdmalt(Adapter
, EEPROM_SPI_Q_STATUS1_REG
, &value
, sizeof(value
));
100 rdmalt(Adapter
, EEPROM_SPI_Q_STATUS_REG
, &value1
, sizeof(value1
));
101 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "0x3004 = %x 0x3008 = %x, retries = %d failed.\n", value
, value1
, MAX_EEPROM_RETRIES
* RETRIES_PER_DELAY
);
104 if (!(dwRetries
%RETRIES_PER_DELAY
))
109 } /* ReadEEPROMStatusRegister */
112 * Procedure: ReadBeceemEEPROMBulk
114 * Description: This routine reads 16Byte data from EEPROM
117 * Adapter - ptr to Adapter object instance
118 * dwAddress - EEPROM Offset to read the data from.
119 * pdwData - Pointer to double word where data needs to be stored in. // dwNumWords - Number of words. Valid values are 4 ONLY.
125 int ReadBeceemEEPROMBulk(struct bcm_mini_adapter
*Adapter
,
131 DWORD dwRetries
= MAX_EEPROM_RETRIES
* RETRIES_PER_DELAY
;
132 unsigned int uiStatus
= 0;
133 unsigned int value
= 0;
134 unsigned int value1
= 0;
137 /* Flush the read and cmd queue. */
138 value
= (EEPROM_READ_QUEUE_FLUSH
| EEPROM_CMD_QUEUE_FLUSH
);
139 wrmalt(Adapter
, SPI_FLUSH_REG
, &value
, sizeof(value
));
141 wrmalt(Adapter
, SPI_FLUSH_REG
, &value
, sizeof(value
));
143 /* Clear the Avail/Full bits. */
144 value
= (EEPROM_READ_DATA_AVAIL
| EEPROM_READ_DATA_FULL
);
145 wrmalt(Adapter
, EEPROM_SPI_Q_STATUS1_REG
, &value
, sizeof(value
));
147 value
= dwAddress
| ((dwNumWords
== 4) ? EEPROM_16_BYTE_PAGE_READ
: EEPROM_4_BYTE_PAGE_READ
);
148 wrmalt(Adapter
, EEPROM_CMDQ_SPI_REG
, &value
, sizeof(value
));
150 while (dwRetries
!= 0) {
152 rdmalt(Adapter
, EEPROM_SPI_Q_STATUS1_REG
, &uiStatus
, sizeof(uiStatus
));
153 if (Adapter
->device_removed
== TRUE
) {
154 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Modem has got Removed.hence exiting from loop...");
158 /* If we are reading 16 bytes we want to be sure that the queue
159 * is full before we read. In the other cases we are ok if the
160 * queue has data available
162 if (dwNumWords
== 4) {
163 if ((uiStatus
& EEPROM_READ_DATA_FULL
) != 0) {
164 /* Clear the Avail/Full bits - which ever is set. */
165 value
= (uiStatus
& (EEPROM_READ_DATA_AVAIL
| EEPROM_READ_DATA_FULL
));
166 wrmalt(Adapter
, EEPROM_SPI_Q_STATUS1_REG
, &value
, sizeof(value
));
169 } else if (dwNumWords
== 1) {
170 if ((uiStatus
& EEPROM_READ_DATA_AVAIL
) != 0) {
171 /* We just got Avail and we have to read 32bits so we
172 * need this sleep for Cardbus kind of devices.
174 if (Adapter
->chip_id
== 0xBECE0210)
177 /* Clear the Avail/Full bits - which ever is set. */
178 value
= (uiStatus
& (EEPROM_READ_DATA_AVAIL
| EEPROM_READ_DATA_FULL
));
179 wrmalt(Adapter
, EEPROM_SPI_Q_STATUS1_REG
, &value
, sizeof(value
));
187 if (dwRetries
== 0) {
190 rdmalt(Adapter
, EEPROM_SPI_Q_STATUS1_REG
, &value
, sizeof(value
));
191 rdmalt(Adapter
, EEPROM_SPI_Q_STATUS_REG
, &value1
, sizeof(value1
));
192 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "dwNumWords %d 0x3004 = %x 0x3008 = %x retries = %d failed.\n",
193 dwNumWords
, value
, value1
, MAX_EEPROM_RETRIES
* RETRIES_PER_DELAY
);
194 return STATUS_FAILURE
;
197 if (!(dwRetries
%RETRIES_PER_DELAY
))
201 for (dwIndex
= 0; dwIndex
< dwNumWords
; dwIndex
++) {
202 /* We get only a byte at a time - from LSB to MSB. We shift it into an integer. */
203 pvalue
= (PUCHAR
)(pdwData
+ dwIndex
);
206 rdmalt(Adapter
, EEPROM_READ_DATAQ_REG
, &value
, sizeof(value
));
211 rdmalt(Adapter
, EEPROM_READ_DATAQ_REG
, &value
, sizeof(value
));
216 rdmalt(Adapter
, EEPROM_READ_DATAQ_REG
, &value
, sizeof(value
));
221 rdmalt(Adapter
, EEPROM_READ_DATAQ_REG
, &value
, sizeof(value
));
226 return STATUS_SUCCESS
;
227 } /* ReadBeceemEEPROMBulk() */
230 * Procedure: ReadBeceemEEPROM
232 * Description: This routine reads 4 data from EEPROM. It uses 1 or 2 page
233 * reads to do this operation.
236 * Adapter - ptr to Adapter object instance
237 * uiOffset - EEPROM Offset to read the data from.
238 * pBuffer - Pointer to word where data needs to be stored in.
244 int ReadBeceemEEPROM(struct bcm_mini_adapter
*Adapter
,
248 unsigned int uiData
[8] = {0};
249 unsigned int uiByteOffset
= 0;
250 unsigned int uiTempOffset
= 0;
252 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, " ====> ");
254 uiTempOffset
= uiOffset
- (uiOffset
% MAX_RW_SIZE
);
255 uiByteOffset
= uiOffset
- uiTempOffset
;
257 ReadBeceemEEPROMBulk(Adapter
, uiTempOffset
, (PUINT
)&uiData
[0], 4);
259 /* A word can overlap at most over 2 pages. In that case we read the
262 if (uiByteOffset
> 12)
263 ReadBeceemEEPROMBulk(Adapter
, uiTempOffset
+ MAX_RW_SIZE
, (PUINT
)&uiData
[4], 4);
265 memcpy((PUCHAR
)pBuffer
, (((PUCHAR
)&uiData
[0]) + uiByteOffset
), 4);
267 return STATUS_SUCCESS
;
268 } /* ReadBeceemEEPROM() */
270 int ReadMacAddressFromNVM(struct bcm_mini_adapter
*Adapter
)
273 unsigned char puMacAddr
[6];
275 Status
= BeceemNVMRead(Adapter
,
276 (PUINT
)&puMacAddr
[0],
277 INIT_PARAMS_1_MACADDRESS_ADDRESS
,
280 if (Status
== STATUS_SUCCESS
)
281 memcpy(Adapter
->dev
->dev_addr
, puMacAddr
, MAC_ADDRESS_SIZE
);
287 * Procedure: BeceemEEPROMBulkRead
289 * Description: Reads the EEPROM and returns the Data.
292 * Adapter - ptr to Adapter object instance
293 * pBuffer - Buffer to store the data read from EEPROM
294 * uiOffset - Offset of EEPROM from where data should be read
295 * uiNumBytes - Number of bytes to be read from the EEPROM.
298 * OSAL_STATUS_SUCCESS - if EEPROM read is successful.
299 * <FAILURE> - if failed.
302 int BeceemEEPROMBulkRead(struct bcm_mini_adapter
*Adapter
,
304 unsigned int uiOffset
,
305 unsigned int uiNumBytes
)
307 unsigned int uiData
[4] = {0};
308 /* unsigned int uiAddress = 0; */
309 unsigned int uiBytesRemaining
= uiNumBytes
;
310 unsigned int uiIndex
= 0;
311 unsigned int uiTempOffset
= 0;
312 unsigned int uiExtraBytes
= 0;
313 unsigned int uiFailureRetries
= 0;
314 PUCHAR pcBuff
= (PUCHAR
)pBuffer
;
316 if (uiOffset
% MAX_RW_SIZE
&& uiBytesRemaining
) {
317 uiTempOffset
= uiOffset
- (uiOffset
% MAX_RW_SIZE
);
318 uiExtraBytes
= uiOffset
- uiTempOffset
;
319 ReadBeceemEEPROMBulk(Adapter
, uiTempOffset
, (PUINT
)&uiData
[0], 4);
320 if (uiBytesRemaining
>= (MAX_RW_SIZE
- uiExtraBytes
)) {
321 memcpy(pBuffer
, (((PUCHAR
)&uiData
[0]) + uiExtraBytes
), MAX_RW_SIZE
- uiExtraBytes
);
322 uiBytesRemaining
-= (MAX_RW_SIZE
- uiExtraBytes
);
323 uiIndex
+= (MAX_RW_SIZE
- uiExtraBytes
);
324 uiOffset
+= (MAX_RW_SIZE
- uiExtraBytes
);
326 memcpy(pBuffer
, (((PUCHAR
)&uiData
[0]) + uiExtraBytes
), uiBytesRemaining
);
327 uiIndex
+= uiBytesRemaining
;
328 uiOffset
+= uiBytesRemaining
;
329 uiBytesRemaining
= 0;
333 while (uiBytesRemaining
&& uiFailureRetries
!= 128) {
334 if (Adapter
->device_removed
)
337 if (uiBytesRemaining
>= MAX_RW_SIZE
) {
338 /* For the requests more than or equal to 16 bytes, use bulk
339 * read function to make the access faster.
340 * We read 4 Dwords of data
342 if (ReadBeceemEEPROMBulk(Adapter
, uiOffset
, &uiData
[0], 4) == 0) {
343 memcpy(pcBuff
+ uiIndex
, &uiData
[0], MAX_RW_SIZE
);
344 uiOffset
+= MAX_RW_SIZE
;
345 uiBytesRemaining
-= MAX_RW_SIZE
;
346 uiIndex
+= MAX_RW_SIZE
;
349 mdelay(3); /* sleep for a while before retry... */
351 } else if (uiBytesRemaining
>= 4) {
352 if (ReadBeceemEEPROM(Adapter
, uiOffset
, &uiData
[0]) == 0) {
353 memcpy(pcBuff
+ uiIndex
, &uiData
[0], 4);
355 uiBytesRemaining
-= 4;
359 mdelay(3); /* sleep for a while before retry... */
362 /* Handle the reads less than 4 bytes... */
363 PUCHAR pCharBuff
= (PUCHAR
)pBuffer
;
364 pCharBuff
+= uiIndex
;
365 if (ReadBeceemEEPROM(Adapter
, uiOffset
, &uiData
[0]) == 0) {
366 memcpy(pCharBuff
, &uiData
[0], uiBytesRemaining
); /* copy only bytes requested. */
367 uiBytesRemaining
= 0;
370 mdelay(3); /* sleep for a while before retry... */
379 * Procedure: BeceemFlashBulkRead
381 * Description: Reads the FLASH and returns the Data.
384 * Adapter - ptr to Adapter object instance
385 * pBuffer - Buffer to store the data read from FLASH
386 * uiOffset - Offset of FLASH from where data should be read
387 * uiNumBytes - Number of bytes to be read from the FLASH.
390 * OSAL_STATUS_SUCCESS - if FLASH read is successful.
391 * <FAILURE> - if failed.
394 static int BeceemFlashBulkRead(struct bcm_mini_adapter
*Adapter
,
396 unsigned int uiOffset
,
397 unsigned int uiNumBytes
)
399 unsigned int uiIndex
= 0;
400 unsigned int uiBytesToRead
= uiNumBytes
;
402 unsigned int uiPartOffset
= 0;
405 if (Adapter
->device_removed
) {
406 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Device Got Removed");
410 /* Adding flash Base address
411 * uiOffset = uiOffset + GetFlashBaseAddr(Adapter);
413 #if defined(BCM_SHM_INTERFACE) && !defined(FLASH_DIRECT_ACCESS)
414 Status
= bcmflash_raw_read((uiOffset
/FLASH_PART_SIZE
), (uiOffset
% FLASH_PART_SIZE
), (unsigned char *)pBuffer
, uiNumBytes
);
418 Adapter
->SelectedChip
= RESET_CHIP_SELECT
;
420 if (uiOffset
% MAX_RW_SIZE
) {
421 BcmDoChipSelect(Adapter
, uiOffset
);
422 uiPartOffset
= (uiOffset
& (FLASH_PART_SIZE
- 1)) + GetFlashBaseAddr(Adapter
);
424 uiBytesToRead
= MAX_RW_SIZE
- (uiOffset
% MAX_RW_SIZE
);
425 uiBytesToRead
= MIN(uiNumBytes
, uiBytesToRead
);
427 bytes
= rdm(Adapter
, uiPartOffset
, (PCHAR
)pBuffer
+ uiIndex
, uiBytesToRead
);
430 Adapter
->SelectedChip
= RESET_CHIP_SELECT
;
434 uiIndex
+= uiBytesToRead
;
435 uiOffset
+= uiBytesToRead
;
436 uiNumBytes
-= uiBytesToRead
;
440 BcmDoChipSelect(Adapter
, uiOffset
);
441 uiPartOffset
= (uiOffset
& (FLASH_PART_SIZE
- 1)) + GetFlashBaseAddr(Adapter
);
443 uiBytesToRead
= MIN(uiNumBytes
, MAX_RW_SIZE
);
445 bytes
= rdm(Adapter
, uiPartOffset
, (PCHAR
)pBuffer
+ uiIndex
, uiBytesToRead
);
451 uiIndex
+= uiBytesToRead
;
452 uiOffset
+= uiBytesToRead
;
453 uiNumBytes
-= uiBytesToRead
;
455 Adapter
->SelectedChip
= RESET_CHIP_SELECT
;
460 * Procedure: BcmGetFlashSize
462 * Description: Finds the size of FLASH.
465 * Adapter - ptr to Adapter object instance
468 * unsigned int - size of the FLASH Storage.
472 static unsigned int BcmGetFlashSize(struct bcm_mini_adapter
*Adapter
)
474 if (IsFlash2x(Adapter
))
475 return Adapter
->psFlash2xCSInfo
->OffsetFromDSDStartForDSDHeader
+ sizeof(DSD_HEADER
);
481 * Procedure: BcmGetEEPROMSize
483 * Description: Finds the size of EEPROM.
486 * Adapter - ptr to Adapter object instance
489 * unsigned int - size of the EEPROM Storage.
493 static unsigned int BcmGetEEPROMSize(struct bcm_mini_adapter
*Adapter
)
495 unsigned int uiData
= 0;
496 unsigned int uiIndex
= 0;
499 * if EEPROM is present and already Calibrated,it will have
500 * 'BECM' string at 0th offset.
501 * To find the EEPROM size read the possible boundaries of the
502 * EEPROM like 4K,8K etc..accessing the EEPROM beyond its size will
503 * result in wrap around. So when we get the End of the EEPROM we will
504 * get 'BECM' string which is indeed at offset 0.
506 BeceemEEPROMBulkRead(Adapter
, &uiData
, 0x0, 4);
507 if (uiData
== BECM
) {
508 for (uiIndex
= 2; uiIndex
<= 256; uiIndex
*= 2) {
509 BeceemEEPROMBulkRead(Adapter
, &uiData
, uiIndex
* 1024, 4);
511 return uiIndex
* 1024;
515 * EEPROM may not be present or not programmed
518 if (BeceemEEPROMBulkWrite(Adapter
, (PUCHAR
)&uiData
, 0, 4, TRUE
) == 0) {
520 for (uiIndex
= 2; uiIndex
<= 256; uiIndex
*= 2) {
521 BeceemEEPROMBulkRead(Adapter
, &uiData
, uiIndex
* 1024, 4);
522 if (uiData
== 0xBABEFACE)
523 return uiIndex
* 1024;
531 * Procedure: FlashSectorErase
533 * Description: Finds the sector size of the FLASH.
536 * Adapter - ptr to Adapter object instance
537 * addr - sector start address
538 * numOfSectors - number of sectors to be erased.
545 static int FlashSectorErase(struct bcm_mini_adapter
*Adapter
,
547 unsigned int numOfSectors
)
549 unsigned int iIndex
= 0, iRetries
= 0;
550 unsigned int uiStatus
= 0;
554 for (iIndex
= 0; iIndex
< numOfSectors
; iIndex
++) {
556 wrmalt(Adapter
, FLASH_SPI_CMDQ_REG
, &value
, sizeof(value
));
558 value
= (0xd8000000 | (addr
& 0xFFFFFF));
559 wrmalt(Adapter
, FLASH_SPI_CMDQ_REG
, &value
, sizeof(value
));
563 value
= (FLASH_CMD_STATUS_REG_READ
<< 24);
564 if (wrmalt(Adapter
, FLASH_SPI_CMDQ_REG
, &value
, sizeof(value
)) < 0) {
565 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Programing of FLASH_SPI_CMDQ_REG fails");
566 return STATUS_FAILURE
;
569 bytes
= rdmalt(Adapter
, FLASH_SPI_READQ_REG
, &uiStatus
, sizeof(uiStatus
));
572 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Reading status of FLASH_SPI_READQ_REG fails");
576 /* After every try lets make the CPU free for 10 ms. generally time taken by the
577 * the sector erase cycle is 500 ms to 40000 msec. hence sleeping 10 ms
578 * won't hamper performance in any case.
581 } while ((uiStatus
& 0x1) && (iRetries
< 400));
583 if (uiStatus
& 0x1) {
584 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "iRetries crossing the limit of 80000\n");
585 return STATUS_FAILURE
;
588 addr
+= Adapter
->uiSectorSize
;
593 * Procedure: flashByteWrite
595 * Description: Performs Byte by Byte write to flash
598 * Adapter - ptr to Adapter object instance
599 * uiOffset - Offset of the flash where data needs to be written to.
600 * pData - Address of Data to be written.
606 static int flashByteWrite(struct bcm_mini_adapter
*Adapter
,
607 unsigned int uiOffset
,
610 unsigned int uiStatus
= 0;
611 int iRetries
= MAX_FLASH_RETRIES
* FLASH_PER_RETRIES_DELAY
; /* 3 */
613 ULONG ulData
= *(PUCHAR
)pData
;
616 * need not write 0xFF because write requires an erase and erase will
617 * make whole sector 0xFF.
621 return STATUS_SUCCESS
;
623 /* DumpDebug(NVM_RW,("flashWrite ====>\n")); */
624 value
= (FLASH_CMD_WRITE_ENABLE
<< 24);
625 if (wrmalt(Adapter
, FLASH_SPI_CMDQ_REG
, &value
, sizeof(value
)) < 0) {
626 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Write enable in FLASH_SPI_CMDQ_REG register fails");
627 return STATUS_FAILURE
;
630 if (wrm(Adapter
, FLASH_SPI_WRITEQ_REG
, (PCHAR
)&ulData
, 4) < 0) {
631 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "DATA Write on FLASH_SPI_WRITEQ_REG fails");
632 return STATUS_FAILURE
;
634 value
= (0x02000000 | (uiOffset
& 0xFFFFFF));
635 if (wrmalt(Adapter
, FLASH_SPI_CMDQ_REG
, &value
, sizeof(value
)) < 0) {
636 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Programming of FLASH_SPI_CMDQ_REG fails");
637 return STATUS_FAILURE
;
643 value
= (FLASH_CMD_STATUS_REG_READ
<< 24);
644 if (wrmalt(Adapter
, FLASH_SPI_CMDQ_REG
, &value
, sizeof(value
)) < 0) {
645 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Programing of FLASH_SPI_CMDQ_REG fails");
646 return STATUS_FAILURE
;
649 bytes
= rdmalt(Adapter
, FLASH_SPI_READQ_REG
, &uiStatus
, sizeof(uiStatus
));
652 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Reading status of FLASH_SPI_READQ_REG fails");
656 if (iRetries
&& ((iRetries
% FLASH_PER_RETRIES_DELAY
) == 0))
659 } while ((uiStatus
& 0x1) && (iRetries
> 0));
661 if (uiStatus
& 0x1) {
662 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Flash Write fails even after checking status for 200 times.");
663 return STATUS_FAILURE
;
666 return STATUS_SUCCESS
;
670 * Procedure: flashWrite
672 * Description: Performs write to flash
675 * Adapter - ptr to Adapter object instance
676 * uiOffset - Offset of the flash where data needs to be written to.
677 * pData - Address of Data to be written.
683 static int flashWrite(struct bcm_mini_adapter
*Adapter
,
684 unsigned int uiOffset
,
687 /* unsigned int uiStatus = 0;
689 * unsigned int uiReadBack = 0;
691 unsigned int uiStatus
= 0;
692 int iRetries
= MAX_FLASH_RETRIES
* FLASH_PER_RETRIES_DELAY
; /* 3 */
694 unsigned int uiErasePattern
[4] = {0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF};
697 * need not write 0xFFFFFFFF because write requires an erase and erase will
698 * make whole sector 0xFFFFFFFF.
700 if (!memcmp(pData
, uiErasePattern
, MAX_RW_SIZE
))
703 value
= (FLASH_CMD_WRITE_ENABLE
<< 24);
705 if (wrmalt(Adapter
, FLASH_SPI_CMDQ_REG
, &value
, sizeof(value
)) < 0) {
706 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Write Enable of FLASH_SPI_CMDQ_REG fails");
707 return STATUS_FAILURE
;
710 if (wrm(Adapter
, uiOffset
, (PCHAR
)pData
, MAX_RW_SIZE
) < 0) {
711 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Data write fails...");
712 return STATUS_FAILURE
;
717 value
= (FLASH_CMD_STATUS_REG_READ
<< 24);
718 if (wrmalt(Adapter
, FLASH_SPI_CMDQ_REG
, &value
, sizeof(value
)) < 0) {
719 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Programing of FLASH_SPI_CMDQ_REG fails");
720 return STATUS_FAILURE
;
723 bytes
= rdmalt(Adapter
, FLASH_SPI_READQ_REG
, &uiStatus
, sizeof(uiStatus
));
726 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Reading status of FLASH_SPI_READQ_REG fails");
731 /* this will ensure that in there will be no changes in the current path.
732 * currently one rdm/wrm takes 125 us.
733 * Hence 125 *2 * FLASH_PER_RETRIES_DELAY > 3 ms(worst case delay)
734 * Hence current implementation cycle will intoduce no delay in current path
736 if (iRetries
&& ((iRetries
% FLASH_PER_RETRIES_DELAY
) == 0))
738 } while ((uiStatus
& 0x1) && (iRetries
> 0));
740 if (uiStatus
& 0x1) {
741 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Flash Write fails even after checking status for 200 times.");
742 return STATUS_FAILURE
;
745 return STATUS_SUCCESS
;
748 /*-----------------------------------------------------------------------------
749 * Procedure: flashByteWriteStatus
751 * Description: Performs byte by byte write to flash with write done status check
754 * Adapter - ptr to Adapter object instance
755 * uiOffset - Offset of the flash where data needs to be written to.
756 * pData - Address of the Data to be written.
761 static int flashByteWriteStatus(struct bcm_mini_adapter
*Adapter
,
762 unsigned int uiOffset
,
765 unsigned int uiStatus
= 0;
766 int iRetries
= MAX_FLASH_RETRIES
* FLASH_PER_RETRIES_DELAY
; /* 3 */
767 ULONG ulData
= *(PUCHAR
)pData
;
772 * need not write 0xFFFFFFFF because write requires an erase and erase will
773 * make whole sector 0xFFFFFFFF.
777 return STATUS_SUCCESS
;
779 /* DumpDebug(NVM_RW,("flashWrite ====>\n")); */
781 value
= (FLASH_CMD_WRITE_ENABLE
<< 24);
782 if (wrmalt(Adapter
, FLASH_SPI_CMDQ_REG
, &value
, sizeof(value
)) < 0) {
783 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Write enable in FLASH_SPI_CMDQ_REG register fails");
784 return STATUS_SUCCESS
;
786 if (wrm(Adapter
, FLASH_SPI_WRITEQ_REG
, (PCHAR
)&ulData
, 4) < 0) {
787 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "DATA Write on FLASH_SPI_WRITEQ_REG fails");
788 return STATUS_FAILURE
;
790 value
= (0x02000000 | (uiOffset
& 0xFFFFFF));
791 if (wrmalt(Adapter
, FLASH_SPI_CMDQ_REG
, &value
, sizeof(value
)) < 0) {
792 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Programming of FLASH_SPI_CMDQ_REG fails");
793 return STATUS_FAILURE
;
799 value
= (FLASH_CMD_STATUS_REG_READ
<< 24);
800 if (wrmalt(Adapter
, FLASH_SPI_CMDQ_REG
, &value
, sizeof(value
)) < 0) {
801 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Programing of FLASH_SPI_CMDQ_REG fails");
802 return STATUS_FAILURE
;
805 bytes
= rdmalt(Adapter
, FLASH_SPI_READQ_REG
, &uiStatus
, sizeof(uiStatus
));
808 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Reading status of FLASH_SPI_READQ_REG fails");
813 if (iRetries
&& ((iRetries
% FLASH_PER_RETRIES_DELAY
) == 0))
816 } while ((uiStatus
& 0x1) && (iRetries
> 0));
818 if (uiStatus
& 0x1) {
819 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Flash Write fails even after checking status for 200 times.");
820 return STATUS_FAILURE
;
823 return STATUS_SUCCESS
;
826 * Procedure: flashWriteStatus
828 * Description: Performs write to flash with write done status check
831 * Adapter - ptr to Adapter object instance
832 * uiOffset - Offset of the flash where data needs to be written to.
833 * pData - Address of the Data to be written.
839 static int flashWriteStatus(struct bcm_mini_adapter
*Adapter
,
840 unsigned int uiOffset
,
843 unsigned int uiStatus
= 0;
844 int iRetries
= MAX_FLASH_RETRIES
* FLASH_PER_RETRIES_DELAY
; /* 3 */
845 /* unsigned int uiReadBack = 0; */
847 unsigned int uiErasePattern
[4] = {0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF};
851 * need not write 0xFFFFFFFF because write requires an erase and erase will
852 * make whole sector 0xFFFFFFFF.
854 if (!memcmp(pData
, uiErasePattern
, MAX_RW_SIZE
))
857 value
= (FLASH_CMD_WRITE_ENABLE
<< 24);
858 if (wrmalt(Adapter
, FLASH_SPI_CMDQ_REG
, &value
, sizeof(value
)) < 0) {
859 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Write Enable of FLASH_SPI_CMDQ_REG fails");
860 return STATUS_FAILURE
;
863 if (wrm(Adapter
, uiOffset
, (PCHAR
)pData
, MAX_RW_SIZE
) < 0) {
864 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Data write fails...");
865 return STATUS_FAILURE
;
870 value
= (FLASH_CMD_STATUS_REG_READ
<< 24);
871 if (wrmalt(Adapter
, FLASH_SPI_CMDQ_REG
, &value
, sizeof(value
)) < 0) {
872 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Programing of FLASH_SPI_CMDQ_REG fails");
873 return STATUS_FAILURE
;
876 bytes
= rdmalt(Adapter
, FLASH_SPI_READQ_REG
, &uiStatus
, sizeof(uiStatus
));
879 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Reading status of FLASH_SPI_READQ_REG fails");
883 /* this will ensure that in there will be no changes in the current path.
884 * currently one rdm/wrm takes 125 us.
885 * Hence 125 *2 * FLASH_PER_RETRIES_DELAY >3 ms(worst case delay)
886 * Hence current implementation cycle will intoduce no delay in current path
888 if (iRetries
&& ((iRetries
% FLASH_PER_RETRIES_DELAY
) == 0))
891 } while ((uiStatus
& 0x1) && (iRetries
> 0));
893 if (uiStatus
& 0x1) {
894 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Flash Write fails even after checking status for 200 times.");
895 return STATUS_FAILURE
;
898 return STATUS_SUCCESS
;
902 * Procedure: BcmRestoreBlockProtectStatus
904 * Description: Restores the original block protection status.
907 * Adapter - ptr to Adapter object instance
908 * ulWriteStatus -Original status
914 static VOID
BcmRestoreBlockProtectStatus(struct bcm_mini_adapter
*Adapter
, ULONG ulWriteStatus
)
917 value
= (FLASH_CMD_WRITE_ENABLE
<< 24);
918 wrmalt(Adapter
, FLASH_SPI_CMDQ_REG
, &value
, sizeof(value
));
921 value
= (FLASH_CMD_STATUS_REG_WRITE
<< 24) | (ulWriteStatus
<< 16);
922 wrmalt(Adapter
, FLASH_SPI_CMDQ_REG
, &value
, sizeof(value
));
927 * Procedure: BcmFlashUnProtectBlock
929 * Description: UnProtects appropriate blocks for writing.
932 * Adapter - ptr to Adapter object instance
933 * uiOffset - Offset of the flash where data needs to be written to. This should be Sector aligned.
935 * ULONG - Status value before UnProtect.
939 static ULONG
BcmFlashUnProtectBlock(struct bcm_mini_adapter
*Adapter
, unsigned int uiOffset
, unsigned int uiLength
)
942 ULONG ulWriteStatus
= 0;
945 uiOffset
= uiOffset
&0x000FFFFF;
947 * Implemented only for 1MB Flash parts.
949 if (FLASH_PART_SST25VF080B
== Adapter
->ulFlashID
) {
951 * Get Current BP status.
953 value
= (FLASH_CMD_STATUS_REG_READ
<< 24);
954 wrmalt(Adapter
, FLASH_SPI_CMDQ_REG
, &value
, sizeof(value
));
957 * Read status will be WWXXYYZZ. We have to take only WW.
959 rdmalt(Adapter
, FLASH_SPI_READQ_REG
, (PUINT
)&ulStatus
, sizeof(ulStatus
));
961 ulWriteStatus
= ulStatus
;
963 * Bits [5-2] give current block level protection status.
964 * Bit5: BP3 - DONT CARE
965 * BP2-BP0: 0 - NO PROTECTION, 1 - UPPER 1/16, 2 - UPPER 1/8, 3 - UPPER 1/4
966 * 4 - UPPER 1/2. 5 to 7 - ALL BLOCKS
970 if ((uiOffset
+uiLength
) <= 0x80000) {
972 * Offset comes in lower half of 1MB. Protect the upper half.
973 * Clear BP1 and BP0 and set BP2.
975 ulWriteStatus
|= (0x4<<2);
976 ulWriteStatus
&= ~(0x3<<2);
977 } else if ((uiOffset
+ uiLength
) <= 0xC0000) {
979 * Offset comes below Upper 1/4. Upper 1/4 can be protected.
980 * Clear BP2 and set BP1 and BP0.
982 ulWriteStatus
|= (0x3<<2);
983 ulWriteStatus
&= ~(0x1<<4);
984 } else if ((uiOffset
+ uiLength
) <= 0xE0000) {
986 * Offset comes below Upper 1/8. Upper 1/8 can be protected.
987 * Clear BP2 and BP0 and set BP1
989 ulWriteStatus
|= (0x1<<3);
990 ulWriteStatus
&= ~(0x5<<2);
991 } else if ((uiOffset
+ uiLength
) <= 0xF0000) {
993 * Offset comes below Upper 1/16. Only upper 1/16 can be protected.
994 * Set BP0 and Clear BP2,BP1.
996 ulWriteStatus
|= (0x1<<2);
997 ulWriteStatus
&= ~(0x3<<3);
1001 * Clear BP2,BP1 and BP0.
1003 ulWriteStatus
&= ~(0x7<<2);
1006 value
= (FLASH_CMD_WRITE_ENABLE
<< 24);
1007 wrmalt(Adapter
, FLASH_SPI_CMDQ_REG
, &value
, sizeof(value
));
1009 value
= (FLASH_CMD_STATUS_REG_WRITE
<< 24) | (ulWriteStatus
<< 16);
1010 wrmalt(Adapter
, FLASH_SPI_CMDQ_REG
, &value
, sizeof(value
));
1018 * Procedure: BeceemFlashBulkWrite
1020 * Description: Performs write to the flash
1023 * Adapter - ptr to Adapter object instance
1024 * pBuffer - Data to be written.
1025 * uiOffset - Offset of the flash where data needs to be written to.
1026 * uiNumBytes - Number of bytes to be written.
1027 * bVerify - read verify flag.
1033 static int BeceemFlashBulkWrite(struct bcm_mini_adapter
*Adapter
,
1035 unsigned int uiOffset
,
1036 unsigned int uiNumBytes
,
1039 PCHAR pTempBuff
= NULL
;
1040 PUCHAR pcBuffer
= (PUCHAR
)pBuffer
;
1041 unsigned int uiIndex
= 0;
1042 unsigned int uiOffsetFromSectStart
= 0;
1043 unsigned int uiSectAlignAddr
= 0;
1044 unsigned int uiCurrSectOffsetAddr
= 0;
1045 unsigned int uiSectBoundary
= 0;
1046 unsigned int uiNumSectTobeRead
= 0;
1047 UCHAR ucReadBk
[16] = {0};
1049 int Status
= STATUS_SUCCESS
;
1050 unsigned int uiTemp
= 0;
1051 unsigned int index
= 0;
1052 unsigned int uiPartOffset
= 0;
1054 #if defined(BCM_SHM_INTERFACE) && !defined(FLASH_DIRECT_ACCESS)
1055 Status
= bcmflash_raw_write((uiOffset
/ FLASH_PART_SIZE
), (uiOffset
% FLASH_PART_SIZE
), (unsigned char *)pBuffer
, uiNumBytes
);
1059 uiOffsetFromSectStart
= uiOffset
& ~(Adapter
->uiSectorSize
- 1);
1061 /* Adding flash Base address
1062 * uiOffset = uiOffset + GetFlashBaseAddr(Adapter);
1065 uiSectAlignAddr
= uiOffset
& ~(Adapter
->uiSectorSize
- 1);
1066 uiCurrSectOffsetAddr
= uiOffset
& (Adapter
->uiSectorSize
- 1);
1067 uiSectBoundary
= uiSectAlignAddr
+ Adapter
->uiSectorSize
;
1069 pTempBuff
= kmalloc(Adapter
->uiSectorSize
, GFP_KERNEL
);
1071 goto BeceemFlashBulkWrite_EXIT
;
1073 * check if the data to be written is overlapped across sectors
1075 if (uiOffset
+uiNumBytes
< uiSectBoundary
) {
1076 uiNumSectTobeRead
= 1;
1078 /* Number of sectors = Last sector start address/First sector start address */
1079 uiNumSectTobeRead
= (uiCurrSectOffsetAddr
+ uiNumBytes
) / Adapter
->uiSectorSize
;
1080 if ((uiCurrSectOffsetAddr
+ uiNumBytes
)%Adapter
->uiSectorSize
)
1081 uiNumSectTobeRead
++;
1083 /* Check whether Requested sector is writable or not in case of flash2x write. But if write call is
1084 * for DSD calibration, allow it without checking of sector permission
1087 if (IsFlash2x(Adapter
) && (Adapter
->bAllDSDWriteAllow
== FALSE
)) {
1089 uiTemp
= uiNumSectTobeRead
;
1091 if (IsOffsetWritable(Adapter
, uiOffsetFromSectStart
+ index
* Adapter
->uiSectorSize
) == FALSE
) {
1092 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Sector Starting at offset <0X%X> is not writable",
1093 (uiOffsetFromSectStart
+ index
* Adapter
->uiSectorSize
));
1094 Status
= SECTOR_IS_NOT_WRITABLE
;
1095 goto BeceemFlashBulkWrite_EXIT
;
1097 uiTemp
= uiTemp
- 1;
1101 Adapter
->SelectedChip
= RESET_CHIP_SELECT
;
1102 while (uiNumSectTobeRead
) {
1103 /* do_gettimeofday(&tv1);
1104 * BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "\nTime In start of write :%ld ms\n",(tv1.tv_sec *1000 + tv1.tv_usec /1000));
1106 uiPartOffset
= (uiSectAlignAddr
& (FLASH_PART_SIZE
- 1)) + GetFlashBaseAddr(Adapter
);
1108 BcmDoChipSelect(Adapter
, uiSectAlignAddr
);
1110 if (0 != BeceemFlashBulkRead(Adapter
,
1112 uiOffsetFromSectStart
,
1113 Adapter
->uiSectorSize
)) {
1115 goto BeceemFlashBulkWrite_EXIT
;
1118 /* do_gettimeofday(&tr);
1119 * BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "Total time taken by Read :%ld ms\n", (tr.tv_sec *1000 + tr.tv_usec/1000) - (tv1.tv_sec *1000 + tv1.tv_usec/1000));
1121 ulStatus
= BcmFlashUnProtectBlock(Adapter
, uiSectAlignAddr
, Adapter
->uiSectorSize
);
1123 if (uiNumSectTobeRead
> 1) {
1124 memcpy(&pTempBuff
[uiCurrSectOffsetAddr
], pcBuffer
, uiSectBoundary
- (uiSectAlignAddr
+ uiCurrSectOffsetAddr
));
1125 pcBuffer
+= ((uiSectBoundary
- (uiSectAlignAddr
+ uiCurrSectOffsetAddr
)));
1126 uiNumBytes
-= (uiSectBoundary
- (uiSectAlignAddr
+ uiCurrSectOffsetAddr
));
1128 memcpy(&pTempBuff
[uiCurrSectOffsetAddr
], pcBuffer
, uiNumBytes
);
1131 if (IsFlash2x(Adapter
))
1132 SaveHeaderIfPresent(Adapter
, (PUCHAR
)pTempBuff
, uiOffsetFromSectStart
);
1134 FlashSectorErase(Adapter
, uiPartOffset
, 1);
1135 /* do_gettimeofday(&te);
1136 * BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "Total time taken by Erase :%ld ms\n", (te.tv_sec *1000 + te.tv_usec/1000) - (tr.tv_sec *1000 + tr.tv_usec/1000));
1138 for (uiIndex
= 0; uiIndex
< Adapter
->uiSectorSize
; uiIndex
+= Adapter
->ulFlashWriteSize
) {
1139 if (Adapter
->device_removed
) {
1141 goto BeceemFlashBulkWrite_EXIT
;
1144 if (STATUS_SUCCESS
!= (*Adapter
->fpFlashWrite
)(Adapter
, uiPartOffset
+ uiIndex
, (&pTempBuff
[uiIndex
]))) {
1146 goto BeceemFlashBulkWrite_EXIT
;
1150 /* do_gettimeofday(&tw);
1151 * BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "Total time taken in Write to Flash :%ld ms\n", (tw.tv_sec *1000 + tw.tv_usec/1000) - (te.tv_sec *1000 + te.tv_usec/1000));
1153 for (uiIndex
= 0; uiIndex
< Adapter
->uiSectorSize
; uiIndex
+= MAX_RW_SIZE
) {
1154 if (STATUS_SUCCESS
== BeceemFlashBulkRead(Adapter
, (PUINT
)ucReadBk
, uiOffsetFromSectStart
+ uiIndex
, MAX_RW_SIZE
)) {
1155 if (Adapter
->ulFlashWriteSize
== 1) {
1156 unsigned int uiReadIndex
= 0;
1157 for (uiReadIndex
= 0; uiReadIndex
< 16; uiReadIndex
++) {
1158 if (ucReadBk
[uiReadIndex
] != pTempBuff
[uiIndex
+ uiReadIndex
]) {
1159 if (STATUS_SUCCESS
!= (*Adapter
->fpFlashWriteWithStatusCheck
)(Adapter
, uiPartOffset
+ uiIndex
+ uiReadIndex
, &pTempBuff
[uiIndex
+uiReadIndex
])) {
1160 Status
= STATUS_FAILURE
;
1161 goto BeceemFlashBulkWrite_EXIT
;
1166 if (memcmp(ucReadBk
, &pTempBuff
[uiIndex
], MAX_RW_SIZE
)) {
1167 if (STATUS_SUCCESS
!= (*Adapter
->fpFlashWriteWithStatusCheck
)(Adapter
, uiPartOffset
+ uiIndex
, &pTempBuff
[uiIndex
])) {
1168 Status
= STATUS_FAILURE
;
1169 goto BeceemFlashBulkWrite_EXIT
;
1175 /* do_gettimeofday(&twv);
1176 * BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "Total time taken in Write to Flash verification :%ld ms\n", (twv.tv_sec *1000 + twv.tv_usec/1000) - (tw.tv_sec *1000 + tw.tv_usec/1000));
1179 BcmRestoreBlockProtectStatus(Adapter
, ulStatus
);
1183 uiCurrSectOffsetAddr
= 0;
1184 uiSectAlignAddr
= uiSectBoundary
;
1185 uiSectBoundary
+= Adapter
->uiSectorSize
;
1186 uiOffsetFromSectStart
+= Adapter
->uiSectorSize
;
1187 uiNumSectTobeRead
--;
1189 /* do_gettimeofday(&tv2);
1190 * BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "Time after Write :%ld ms\n",(tv2.tv_sec *1000 + tv2.tv_usec/1000));
1191 * BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "Total time taken by in Write is :%ld ms\n", (tv2.tv_sec *1000 + tv2.tv_usec/1000) - (tv1.tv_sec *1000 + tv1.tv_usec/1000));
1195 BeceemFlashBulkWrite_EXIT
:
1197 BcmRestoreBlockProtectStatus(Adapter
, ulStatus
);
1201 Adapter
->SelectedChip
= RESET_CHIP_SELECT
;
1206 * Procedure: BeceemFlashBulkWriteStatus
1208 * Description: Writes to Flash. Checks the SPI status after each write.
1211 * Adapter - ptr to Adapter object instance
1212 * pBuffer - Data to be written.
1213 * uiOffset - Offset of the flash where data needs to be written to.
1214 * uiNumBytes - Number of bytes to be written.
1215 * bVerify - read verify flag.
1221 static int BeceemFlashBulkWriteStatus(struct bcm_mini_adapter
*Adapter
,
1223 unsigned int uiOffset
,
1224 unsigned int uiNumBytes
,
1227 PCHAR pTempBuff
= NULL
;
1228 PUCHAR pcBuffer
= (PUCHAR
)pBuffer
;
1229 unsigned int uiIndex
= 0;
1230 unsigned int uiOffsetFromSectStart
= 0;
1231 unsigned int uiSectAlignAddr
= 0;
1232 unsigned int uiCurrSectOffsetAddr
= 0;
1233 unsigned int uiSectBoundary
= 0;
1234 unsigned int uiNumSectTobeRead
= 0;
1235 UCHAR ucReadBk
[16] = {0};
1237 unsigned int Status
= STATUS_SUCCESS
;
1238 unsigned int uiTemp
= 0;
1239 unsigned int index
= 0;
1240 unsigned int uiPartOffset
= 0;
1242 uiOffsetFromSectStart
= uiOffset
& ~(Adapter
->uiSectorSize
- 1);
1244 /* uiOffset += Adapter->ulFlashCalStart;
1245 * Adding flash Base address
1246 * uiOffset = uiOffset + GetFlashBaseAddr(Adapter);
1248 uiSectAlignAddr
= uiOffset
& ~(Adapter
->uiSectorSize
- 1);
1249 uiCurrSectOffsetAddr
= uiOffset
& (Adapter
->uiSectorSize
- 1);
1250 uiSectBoundary
= uiSectAlignAddr
+ Adapter
->uiSectorSize
;
1252 pTempBuff
= kmalloc(Adapter
->uiSectorSize
, GFP_KERNEL
);
1254 goto BeceemFlashBulkWriteStatus_EXIT
;
1257 * check if the data to be written is overlapped across sectors
1259 if (uiOffset
+uiNumBytes
< uiSectBoundary
) {
1260 uiNumSectTobeRead
= 1;
1262 /* Number of sectors = Last sector start address/First sector start address */
1263 uiNumSectTobeRead
= (uiCurrSectOffsetAddr
+ uiNumBytes
) / Adapter
->uiSectorSize
;
1264 if ((uiCurrSectOffsetAddr
+ uiNumBytes
)%Adapter
->uiSectorSize
)
1265 uiNumSectTobeRead
++;
1268 if (IsFlash2x(Adapter
) && (Adapter
->bAllDSDWriteAllow
== FALSE
)) {
1270 uiTemp
= uiNumSectTobeRead
;
1272 if (IsOffsetWritable(Adapter
, uiOffsetFromSectStart
+ index
* Adapter
->uiSectorSize
) == FALSE
) {
1273 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Sector Starting at offset <0X%x> is not writable",
1274 (uiOffsetFromSectStart
+ index
* Adapter
->uiSectorSize
));
1275 Status
= SECTOR_IS_NOT_WRITABLE
;
1276 goto BeceemFlashBulkWriteStatus_EXIT
;
1278 uiTemp
= uiTemp
- 1;
1283 Adapter
->SelectedChip
= RESET_CHIP_SELECT
;
1284 while (uiNumSectTobeRead
) {
1285 uiPartOffset
= (uiSectAlignAddr
& (FLASH_PART_SIZE
- 1)) + GetFlashBaseAddr(Adapter
);
1287 BcmDoChipSelect(Adapter
, uiSectAlignAddr
);
1288 if (0 != BeceemFlashBulkRead(Adapter
,
1290 uiOffsetFromSectStart
,
1291 Adapter
->uiSectorSize
)) {
1293 goto BeceemFlashBulkWriteStatus_EXIT
;
1296 ulStatus
= BcmFlashUnProtectBlock(Adapter
, uiOffsetFromSectStart
, Adapter
->uiSectorSize
);
1298 if (uiNumSectTobeRead
> 1) {
1299 memcpy(&pTempBuff
[uiCurrSectOffsetAddr
], pcBuffer
, uiSectBoundary
- (uiSectAlignAddr
+ uiCurrSectOffsetAddr
));
1300 pcBuffer
+= ((uiSectBoundary
- (uiSectAlignAddr
+ uiCurrSectOffsetAddr
)));
1301 uiNumBytes
-= (uiSectBoundary
- (uiSectAlignAddr
+ uiCurrSectOffsetAddr
));
1303 memcpy(&pTempBuff
[uiCurrSectOffsetAddr
], pcBuffer
, uiNumBytes
);
1306 if (IsFlash2x(Adapter
))
1307 SaveHeaderIfPresent(Adapter
, (PUCHAR
)pTempBuff
, uiOffsetFromSectStart
);
1309 FlashSectorErase(Adapter
, uiPartOffset
, 1);
1311 for (uiIndex
= 0; uiIndex
< Adapter
->uiSectorSize
; uiIndex
+= Adapter
->ulFlashWriteSize
) {
1312 if (Adapter
->device_removed
) {
1314 goto BeceemFlashBulkWriteStatus_EXIT
;
1317 if (STATUS_SUCCESS
!= (*Adapter
->fpFlashWriteWithStatusCheck
)(Adapter
, uiPartOffset
+uiIndex
, &pTempBuff
[uiIndex
])) {
1319 goto BeceemFlashBulkWriteStatus_EXIT
;
1324 for (uiIndex
= 0; uiIndex
< Adapter
->uiSectorSize
; uiIndex
+= MAX_RW_SIZE
) {
1325 if (STATUS_SUCCESS
== BeceemFlashBulkRead(Adapter
, (PUINT
)ucReadBk
, uiOffsetFromSectStart
+ uiIndex
, MAX_RW_SIZE
)) {
1326 if (memcmp(ucReadBk
, &pTempBuff
[uiIndex
], MAX_RW_SIZE
)) {
1327 Status
= STATUS_FAILURE
;
1328 goto BeceemFlashBulkWriteStatus_EXIT
;
1335 BcmRestoreBlockProtectStatus(Adapter
, ulStatus
);
1339 uiCurrSectOffsetAddr
= 0;
1340 uiSectAlignAddr
= uiSectBoundary
;
1341 uiSectBoundary
+= Adapter
->uiSectorSize
;
1342 uiOffsetFromSectStart
+= Adapter
->uiSectorSize
;
1343 uiNumSectTobeRead
--;
1348 BeceemFlashBulkWriteStatus_EXIT
:
1350 BcmRestoreBlockProtectStatus(Adapter
, ulStatus
);
1353 Adapter
->SelectedChip
= RESET_CHIP_SELECT
;
1358 * Procedure: PropagateCalParamsFromEEPROMToMemory
1360 * Description: Dumps the calibration section of EEPROM to DDR.
1363 * Adapter - ptr to Adapter object instance
1369 int PropagateCalParamsFromEEPROMToMemory(struct bcm_mini_adapter
*Adapter
)
1371 PCHAR pBuff
= kmalloc(BUFFER_4K
, GFP_KERNEL
);
1372 unsigned int uiEepromSize
= 0;
1373 unsigned int uiIndex
= 0;
1374 unsigned int uiBytesToCopy
= 0;
1375 unsigned int uiCalStartAddr
= EEPROM_CALPARAM_START
;
1376 unsigned int uiMemoryLoc
= EEPROM_CAL_DATA_INTERNAL_LOC
;
1383 if (0 != BeceemEEPROMBulkRead(Adapter
, &uiEepromSize
, EEPROM_SIZE_OFFSET
, 4)) {
1388 uiEepromSize
>>= 16;
1389 if (uiEepromSize
> 1024 * 1024) {
1394 uiBytesToCopy
= MIN(BUFFER_4K
, uiEepromSize
);
1396 while (uiBytesToCopy
) {
1397 if (0 != BeceemEEPROMBulkRead(Adapter
, (PUINT
)pBuff
, uiCalStartAddr
, uiBytesToCopy
)) {
1401 wrm(Adapter
, uiMemoryLoc
, (PCHAR
)(((PULONG
)pBuff
) + uiIndex
), uiBytesToCopy
);
1402 uiMemoryLoc
+= uiBytesToCopy
;
1403 uiEepromSize
-= uiBytesToCopy
;
1404 uiCalStartAddr
+= uiBytesToCopy
;
1405 uiIndex
+= uiBytesToCopy
/ 4;
1406 uiBytesToCopy
= MIN(BUFFER_4K
, uiEepromSize
);
1410 wrmalt(Adapter
, EEPROM_CAL_DATA_INTERNAL_LOC
- 4, &value
, sizeof(value
));
1412 wrmalt(Adapter
, EEPROM_CAL_DATA_INTERNAL_LOC
- 8, &value
, sizeof(value
));
1419 * Procedure: PropagateCalParamsFromFlashToMemory
1421 * Description: Dumps the calibration section of EEPROM to DDR.
1424 * Adapter - ptr to Adapter object instance
1430 int PropagateCalParamsFromFlashToMemory(struct bcm_mini_adapter
*Adapter
)
1433 unsigned int uiEepromSize
= 0;
1434 unsigned int uiBytesToCopy
= 0;
1435 /* unsigned int uiIndex = 0; */
1436 unsigned int uiCalStartAddr
= EEPROM_CALPARAM_START
;
1437 unsigned int uiMemoryLoc
= EEPROM_CAL_DATA_INTERNAL_LOC
;
1442 * Write the signature first. This will ensure firmware does not access EEPROM.
1445 wrmalt(Adapter
, EEPROM_CAL_DATA_INTERNAL_LOC
- 4, &value
, sizeof(value
));
1447 wrmalt(Adapter
, EEPROM_CAL_DATA_INTERNAL_LOC
- 8, &value
, sizeof(value
));
1449 if (0 != BeceemNVMRead(Adapter
, &uiEepromSize
, EEPROM_SIZE_OFFSET
, 4))
1452 uiEepromSize
= ntohl(uiEepromSize
);
1453 uiEepromSize
>>= 16;
1456 * subtract the auto init section size
1458 uiEepromSize
-= EEPROM_CALPARAM_START
;
1460 if (uiEepromSize
> 1024 * 1024)
1463 pBuff
= kmalloc(uiEepromSize
, GFP_KERNEL
);
1467 if (0 != BeceemNVMRead(Adapter
, (PUINT
)pBuff
, uiCalStartAddr
, uiEepromSize
)) {
1474 uiBytesToCopy
= MIN(BUFFER_4K
, uiEepromSize
);
1476 while (uiBytesToCopy
) {
1477 Status
= wrm(Adapter
, uiMemoryLoc
, (PCHAR
)pPtr
, uiBytesToCopy
);
1479 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "wrm failed with status :%d", Status
);
1483 pPtr
+= uiBytesToCopy
;
1484 uiEepromSize
-= uiBytesToCopy
;
1485 uiMemoryLoc
+= uiBytesToCopy
;
1486 uiBytesToCopy
= MIN(BUFFER_4K
, uiEepromSize
);
1494 * Procedure: BeceemEEPROMReadBackandVerify
1496 * Description: Read back the data written and verifies.
1499 * Adapter - ptr to Adapter object instance
1500 * pBuffer - Data to be written.
1501 * uiOffset - Offset of the flash where data needs to be written to.
1502 * uiNumBytes - Number of bytes to be written.
1508 static int BeceemEEPROMReadBackandVerify(struct bcm_mini_adapter
*Adapter
,
1510 unsigned int uiOffset
,
1511 unsigned int uiNumBytes
)
1513 unsigned int uiRdbk
= 0;
1514 unsigned int uiIndex
= 0;
1515 unsigned int uiData
= 0;
1516 unsigned int auiData
[4] = {0};
1518 while (uiNumBytes
) {
1519 if (Adapter
->device_removed
)
1522 if (uiNumBytes
>= MAX_RW_SIZE
) {
1523 /* for the requests more than or equal to MAX_RW_SIZE bytes, use bulk read function to make the access faster. */
1524 BeceemEEPROMBulkRead(Adapter
, &auiData
[0], uiOffset
, MAX_RW_SIZE
);
1526 if (memcmp(&pBuffer
[uiIndex
], &auiData
[0], MAX_RW_SIZE
)) {
1528 BeceemEEPROMBulkWrite(Adapter
, (PUCHAR
)(pBuffer
+ uiIndex
), uiOffset
, MAX_RW_SIZE
, FALSE
);
1530 BeceemEEPROMBulkRead(Adapter
, &auiData
[0], uiOffset
, MAX_RW_SIZE
);
1532 if (memcmp(&pBuffer
[uiIndex
], &auiData
[0], MAX_RW_SIZE
))
1535 uiOffset
+= MAX_RW_SIZE
;
1536 uiNumBytes
-= MAX_RW_SIZE
;
1538 } else if (uiNumBytes
>= 4) {
1539 BeceemEEPROMBulkRead(Adapter
, &uiData
, uiOffset
, 4);
1540 if (uiData
!= pBuffer
[uiIndex
]) {
1542 BeceemEEPROMBulkWrite(Adapter
, (PUCHAR
)(pBuffer
+ uiIndex
), uiOffset
, 4, FALSE
);
1544 BeceemEEPROMBulkRead(Adapter
, &uiData
, uiOffset
, 4);
1545 if (uiData
!= pBuffer
[uiIndex
])
1552 /* Handle the reads less than 4 bytes... */
1554 memcpy(&uiData
, ((PUCHAR
)pBuffer
) + (uiIndex
* sizeof(unsigned int)), uiNumBytes
);
1555 BeceemEEPROMBulkRead(Adapter
, &uiRdbk
, uiOffset
, 4);
1557 if (memcmp(&uiData
, &uiRdbk
, uiNumBytes
))
1567 static VOID
BcmSwapWord(unsigned int *ptr1
)
1569 unsigned int tempval
= (unsigned int)*ptr1
;
1570 char *ptr2
= (char *)&tempval
;
1571 char *ptr
= (char *)ptr1
;
1580 * Procedure: BeceemEEPROMWritePage
1582 * Description: Performs page write (16bytes) to the EEPROM
1585 * Adapter - ptr to Adapter object instance
1586 * uiData - Data to be written.
1587 * uiOffset - Offset of the EEPROM where data needs to be written to.
1593 static int BeceemEEPROMWritePage(struct bcm_mini_adapter
*Adapter
, unsigned int uiData
[], unsigned int uiOffset
)
1595 unsigned int uiRetries
= MAX_EEPROM_RETRIES
* RETRIES_PER_DELAY
;
1596 unsigned int uiStatus
= 0;
1597 UCHAR uiEpromStatus
= 0;
1598 unsigned int value
= 0;
1600 /* Flush the Write/Read/Cmd queues. */
1601 value
= (EEPROM_WRITE_QUEUE_FLUSH
| EEPROM_CMD_QUEUE_FLUSH
| EEPROM_READ_QUEUE_FLUSH
);
1602 wrmalt(Adapter
, SPI_FLUSH_REG
, &value
, sizeof(value
));
1604 wrmalt(Adapter
, SPI_FLUSH_REG
, &value
, sizeof(value
));
1606 /* Clear the Empty/Avail/Full bits. After this it has been confirmed
1607 * that the bit was cleared by reading back the register. See NOTE below.
1608 * We also clear the Read queues as we do a EEPROM status register read
1611 value
= (EEPROM_WRITE_QUEUE_EMPTY
| EEPROM_WRITE_QUEUE_AVAIL
| EEPROM_WRITE_QUEUE_FULL
| EEPROM_READ_DATA_AVAIL
| EEPROM_READ_DATA_FULL
);
1612 wrmalt(Adapter
, EEPROM_SPI_Q_STATUS1_REG
, &value
, sizeof(value
));
1615 value
= EEPROM_WRITE_ENABLE
;
1616 wrmalt(Adapter
, EEPROM_CMDQ_SPI_REG
, &value
, sizeof(value
));
1618 /* We can write back to back 8bits * 16 into the queue and as we have
1619 * checked for the queue to be empty we can write in a burst.
1623 BcmSwapWord(&value
);
1624 wrm(Adapter
, EEPROM_WRITE_DATAQ_REG
, (PUCHAR
)&value
, 4);
1627 BcmSwapWord(&value
);
1628 wrm(Adapter
, EEPROM_WRITE_DATAQ_REG
, (PUCHAR
)&value
, 4);
1631 BcmSwapWord(&value
);
1632 wrm(Adapter
, EEPROM_WRITE_DATAQ_REG
, (PUCHAR
)&value
, 4);
1635 BcmSwapWord(&value
);
1636 wrm(Adapter
, EEPROM_WRITE_DATAQ_REG
, (PUCHAR
)&value
, 4);
1638 /* NOTE : After this write, on readback of EEPROM_SPI_Q_STATUS1_REG
1639 * shows that we see 7 for the EEPROM data write. Which means that
1640 * queue got full, also space is available as well as the queue is empty.
1641 * This may happen in sequence.
1643 value
= EEPROM_16_BYTE_PAGE_WRITE
| uiOffset
;
1644 wrmalt(Adapter
, EEPROM_CMDQ_SPI_REG
, &value
, sizeof(value
));
1646 /* Ideally we should loop here without tries and eventually succeed.
1647 * What we are checking if the previous write has completed, and this
1648 * may take time. We should wait till the Empty bit is set.
1651 rdmalt(Adapter
, EEPROM_SPI_Q_STATUS1_REG
, &uiStatus
, sizeof(uiStatus
));
1652 while ((uiStatus
& EEPROM_WRITE_QUEUE_EMPTY
) == 0) {
1654 if (uiRetries
== 0) {
1655 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "0x0f003004 = %x, %d retries failed.\n", uiStatus
, MAX_EEPROM_RETRIES
* RETRIES_PER_DELAY
);
1656 return STATUS_FAILURE
;
1659 if (!(uiRetries
%RETRIES_PER_DELAY
))
1663 rdmalt(Adapter
, EEPROM_SPI_Q_STATUS1_REG
, &uiStatus
, sizeof(uiStatus
));
1664 if (Adapter
->device_removed
== TRUE
) {
1665 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Modem got removed hence exiting from loop....");
1670 if (uiRetries
!= 0) {
1671 /* Clear the ones that are set - either, Empty/Full/Avail bits */
1672 value
= (uiStatus
& (EEPROM_WRITE_QUEUE_EMPTY
| EEPROM_WRITE_QUEUE_AVAIL
| EEPROM_WRITE_QUEUE_FULL
));
1673 wrmalt(Adapter
, EEPROM_SPI_Q_STATUS1_REG
, &value
, sizeof(value
));
1676 /* Here we should check if the EEPROM status register is correct before
1677 * proceeding. Bit 0 in the EEPROM Status register should be 0 before
1678 * we proceed further. A 1 at Bit 0 indicates that the EEPROM is busy
1679 * with the previous write. Note also that issuing this read finally
1680 * means the previous write to the EEPROM has completed.
1682 uiRetries
= MAX_EEPROM_RETRIES
* RETRIES_PER_DELAY
;
1684 while (uiRetries
!= 0) {
1685 uiEpromStatus
= ReadEEPROMStatusRegister(Adapter
);
1686 if (Adapter
->device_removed
== TRUE
) {
1687 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Modem has got removed hence exiting from loop...");
1690 if ((EEPROM_STATUS_REG_WRITE_BUSY
& uiEpromStatus
) == 0) {
1691 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "EEPROM status register = %x tries = %d\n", uiEpromStatus
, (MAX_EEPROM_RETRIES
* RETRIES_PER_DELAY
- uiRetries
));
1692 return STATUS_SUCCESS
;
1695 if (uiRetries
== 0) {
1696 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "0x0f003004 = %x, for EEPROM status read %d retries failed.\n", uiEpromStatus
, MAX_EEPROM_RETRIES
* RETRIES_PER_DELAY
);
1697 return STATUS_FAILURE
;
1700 if (!(uiRetries
%RETRIES_PER_DELAY
))
1704 return STATUS_SUCCESS
;
1705 } /* BeceemEEPROMWritePage */
1708 * Procedure: BeceemEEPROMBulkWrite
1710 * Description: Performs write to the EEPROM
1713 * Adapter - ptr to Adapter object instance
1714 * pBuffer - Data to be written.
1715 * uiOffset - Offset of the EEPROM where data needs to be written to.
1716 * uiNumBytes - Number of bytes to be written.
1717 * bVerify - read verify flag.
1723 int BeceemEEPROMBulkWrite(struct bcm_mini_adapter
*Adapter
,
1725 unsigned int uiOffset
,
1726 unsigned int uiNumBytes
,
1729 unsigned int uiBytesToCopy
= uiNumBytes
;
1730 /* unsigned int uiRdbk = 0; */
1731 unsigned int uiData
[4] = {0};
1732 unsigned int uiIndex
= 0;
1733 unsigned int uiTempOffset
= 0;
1734 unsigned int uiExtraBytes
= 0;
1735 /* PUINT puiBuffer = (PUINT)pBuffer;
1739 if (uiOffset
% MAX_RW_SIZE
&& uiBytesToCopy
) {
1740 uiTempOffset
= uiOffset
- (uiOffset
% MAX_RW_SIZE
);
1741 uiExtraBytes
= uiOffset
- uiTempOffset
;
1743 BeceemEEPROMBulkRead(Adapter
, &uiData
[0], uiTempOffset
, MAX_RW_SIZE
);
1745 if (uiBytesToCopy
>= (16 - uiExtraBytes
)) {
1746 memcpy((((PUCHAR
)&uiData
[0]) + uiExtraBytes
), pBuffer
, MAX_RW_SIZE
- uiExtraBytes
);
1748 if (STATUS_FAILURE
== BeceemEEPROMWritePage(Adapter
, uiData
, uiTempOffset
))
1749 return STATUS_FAILURE
;
1751 uiBytesToCopy
-= (MAX_RW_SIZE
- uiExtraBytes
);
1752 uiIndex
+= (MAX_RW_SIZE
- uiExtraBytes
);
1753 uiOffset
+= (MAX_RW_SIZE
- uiExtraBytes
);
1755 memcpy((((PUCHAR
)&uiData
[0]) + uiExtraBytes
), pBuffer
, uiBytesToCopy
);
1757 if (STATUS_FAILURE
== BeceemEEPROMWritePage(Adapter
, uiData
, uiTempOffset
))
1758 return STATUS_FAILURE
;
1760 uiIndex
+= uiBytesToCopy
;
1761 uiOffset
+= uiBytesToCopy
;
1766 while (uiBytesToCopy
) {
1767 if (Adapter
->device_removed
)
1770 if (uiBytesToCopy
>= MAX_RW_SIZE
) {
1771 if (STATUS_FAILURE
== BeceemEEPROMWritePage(Adapter
, (PUINT
) &pBuffer
[uiIndex
], uiOffset
))
1772 return STATUS_FAILURE
;
1774 uiIndex
+= MAX_RW_SIZE
;
1775 uiOffset
+= MAX_RW_SIZE
;
1776 uiBytesToCopy
-= MAX_RW_SIZE
;
1779 * To program non 16byte aligned data, read 16byte and then update.
1781 BeceemEEPROMBulkRead(Adapter
, &uiData
[0], uiOffset
, 16);
1782 memcpy(&uiData
[0], pBuffer
+ uiIndex
, uiBytesToCopy
);
1784 if (STATUS_FAILURE
== BeceemEEPROMWritePage(Adapter
, uiData
, uiOffset
))
1785 return STATUS_FAILURE
;
1795 * Procedure: BeceemNVMRead
1797 * Description: Reads n number of bytes from NVM.
1800 * Adapter - ptr to Adapter object instance
1801 * pBuffer - Buffer to store the data read from NVM
1802 * uiOffset - Offset of NVM from where data should be read
1803 * uiNumBytes - Number of bytes to be read from the NVM.
1806 * OSAL_STATUS_SUCCESS - if NVM read is successful.
1807 * <FAILURE> - if failed.
1810 int BeceemNVMRead(struct bcm_mini_adapter
*Adapter
,
1812 unsigned int uiOffset
,
1813 unsigned int uiNumBytes
)
1817 #if !defined(BCM_SHM_INTERFACE) || defined(FLASH_DIRECT_ACCESS)
1818 unsigned int uiTemp
= 0, value
;
1821 if (Adapter
->eNVMType
== NVM_FLASH
) {
1822 if (Adapter
->bFlashRawRead
== FALSE
) {
1823 if (IsSectionExistInVendorInfo(Adapter
, Adapter
->eActiveDSD
))
1824 return vendorextnReadSection(Adapter
, (PUCHAR
)pBuffer
, Adapter
->eActiveDSD
, uiOffset
, uiNumBytes
);
1826 uiOffset
= uiOffset
+ Adapter
->ulFlashCalStart
;
1829 #if defined(BCM_SHM_INTERFACE) && !defined(FLASH_DIRECT_ACCESS)
1830 Status
= bcmflash_raw_read((uiOffset
/ FLASH_PART_SIZE
), (uiOffset
% FLASH_PART_SIZE
), (unsigned char *)pBuffer
, uiNumBytes
);
1832 rdmalt(Adapter
, 0x0f000C80, &uiTemp
, sizeof(uiTemp
));
1834 wrmalt(Adapter
, 0x0f000C80, &value
, sizeof(value
));
1835 Status
= BeceemFlashBulkRead(Adapter
,
1839 wrmalt(Adapter
, 0x0f000C80, &uiTemp
, sizeof(uiTemp
));
1841 } else if (Adapter
->eNVMType
== NVM_EEPROM
) {
1842 Status
= BeceemEEPROMBulkRead(Adapter
,
1854 * Procedure: BeceemNVMWrite
1856 * Description: Writes n number of bytes to NVM.
1859 * Adapter - ptr to Adapter object instance
1860 * pBuffer - Buffer contains the data to be written.
1861 * uiOffset - Offset of NVM where data to be written to.
1862 * uiNumBytes - Number of bytes to be written..
1865 * OSAL_STATUS_SUCCESS - if NVM write is successful.
1866 * <FAILURE> - if failed.
1869 int BeceemNVMWrite(struct bcm_mini_adapter
*Adapter
,
1871 unsigned int uiOffset
,
1872 unsigned int uiNumBytes
,
1876 unsigned int uiTemp
= 0;
1877 unsigned int uiMemoryLoc
= EEPROM_CAL_DATA_INTERNAL_LOC
;
1878 unsigned int uiIndex
= 0;
1880 #if !defined(BCM_SHM_INTERFACE) || defined(FLASH_DIRECT_ACCESS)
1884 unsigned int uiFlashOffset
= 0;
1886 if (Adapter
->eNVMType
== NVM_FLASH
) {
1887 if (IsSectionExistInVendorInfo(Adapter
, Adapter
->eActiveDSD
))
1888 Status
= vendorextnWriteSection(Adapter
, (PUCHAR
)pBuffer
, Adapter
->eActiveDSD
, uiOffset
, uiNumBytes
, bVerify
);
1890 uiFlashOffset
= uiOffset
+ Adapter
->ulFlashCalStart
;
1892 #if defined(BCM_SHM_INTERFACE) && !defined(FLASH_DIRECT_ACCESS)
1893 Status
= bcmflash_raw_write((uiFlashOffset
/ FLASH_PART_SIZE
), (uiFlashOffset
% FLASH_PART_SIZE
), (unsigned char *)pBuffer
, uiNumBytes
);
1895 rdmalt(Adapter
, 0x0f000C80, &uiTemp
, sizeof(uiTemp
));
1897 wrmalt(Adapter
, 0x0f000C80, &value
, sizeof(value
));
1899 if (Adapter
->bStatusWrite
== TRUE
)
1900 Status
= BeceemFlashBulkWriteStatus(Adapter
,
1907 Status
= BeceemFlashBulkWrite(Adapter
,
1915 if (uiOffset
>= EEPROM_CALPARAM_START
) {
1916 uiMemoryLoc
+= (uiOffset
- EEPROM_CALPARAM_START
);
1917 while (uiNumBytes
) {
1918 if (uiNumBytes
> BUFFER_4K
) {
1919 wrm(Adapter
, (uiMemoryLoc
+uiIndex
), (PCHAR
)(pBuffer
+ (uiIndex
/ 4)), BUFFER_4K
);
1920 uiNumBytes
-= BUFFER_4K
;
1921 uiIndex
+= BUFFER_4K
;
1923 wrm(Adapter
, uiMemoryLoc
+uiIndex
, (PCHAR
)(pBuffer
+ (uiIndex
/ 4)), uiNumBytes
);
1929 if ((uiOffset
+ uiNumBytes
) > EEPROM_CALPARAM_START
) {
1930 ULONG ulBytesTobeSkipped
= 0;
1931 PUCHAR pcBuffer
= (PUCHAR
)pBuffer
; /* char pointer to take care of odd byte cases. */
1932 uiNumBytes
-= (EEPROM_CALPARAM_START
- uiOffset
);
1933 ulBytesTobeSkipped
+= (EEPROM_CALPARAM_START
- uiOffset
);
1934 uiOffset
+= (EEPROM_CALPARAM_START
- uiOffset
);
1935 while (uiNumBytes
) {
1936 if (uiNumBytes
> BUFFER_4K
) {
1937 wrm(Adapter
, uiMemoryLoc
+ uiIndex
, (PCHAR
)&pcBuffer
[ulBytesTobeSkipped
+ uiIndex
], BUFFER_4K
);
1938 uiNumBytes
-= BUFFER_4K
;
1939 uiIndex
+= BUFFER_4K
;
1941 wrm(Adapter
, uiMemoryLoc
+ uiIndex
, (PCHAR
)&pcBuffer
[ulBytesTobeSkipped
+ uiIndex
], uiNumBytes
);
1948 /* restore the values. */
1949 wrmalt(Adapter
, 0x0f000C80, &uiTemp
, sizeof(uiTemp
));
1950 } else if (Adapter
->eNVMType
== NVM_EEPROM
) {
1951 Status
= BeceemEEPROMBulkWrite(Adapter
,
1957 Status
= BeceemEEPROMReadBackandVerify(Adapter
, (PUINT
)pBuffer
, uiOffset
, uiNumBytes
);
1965 * Procedure: BcmUpdateSectorSize
1967 * Description: Updates the sector size to FLASH.
1970 * Adapter - ptr to Adapter object instance
1971 * uiSectorSize - sector size
1974 * OSAL_STATUS_SUCCESS - if NVM write is successful.
1975 * <FAILURE> - if failed.
1978 int BcmUpdateSectorSize(struct bcm_mini_adapter
*Adapter
, unsigned int uiSectorSize
)
1981 FLASH_CS_INFO sFlashCsInfo
= {0};
1982 unsigned int uiTemp
= 0;
1983 unsigned int uiSectorSig
= 0;
1984 unsigned int uiCurrentSectorSize
= 0;
1987 rdmalt(Adapter
, 0x0f000C80, &uiTemp
, sizeof(uiTemp
));
1989 wrmalt(Adapter
, 0x0f000C80, &value
, sizeof(value
));
1992 * Before updating the sector size in the reserved area, check if already present.
1994 BeceemFlashBulkRead(Adapter
, (PUINT
)&sFlashCsInfo
, Adapter
->ulFlashControlSectionStart
, sizeof(sFlashCsInfo
));
1995 uiSectorSig
= ntohl(sFlashCsInfo
.FlashSectorSizeSig
);
1996 uiCurrentSectorSize
= ntohl(sFlashCsInfo
.FlashSectorSize
);
1998 if (uiSectorSig
== FLASH_SECTOR_SIZE_SIG
) {
1999 if ((uiCurrentSectorSize
<= MAX_SECTOR_SIZE
) && (uiCurrentSectorSize
>= MIN_SECTOR_SIZE
)) {
2000 if (uiSectorSize
== uiCurrentSectorSize
) {
2001 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "Provided sector size is same as programmed in Flash");
2002 Status
= STATUS_SUCCESS
;
2008 if ((uiSectorSize
<= MAX_SECTOR_SIZE
) && (uiSectorSize
>= MIN_SECTOR_SIZE
)) {
2009 sFlashCsInfo
.FlashSectorSize
= htonl(uiSectorSize
);
2010 sFlashCsInfo
.FlashSectorSizeSig
= htonl(FLASH_SECTOR_SIZE_SIG
);
2012 Status
= BeceemFlashBulkWrite(Adapter
,
2013 (PUINT
)&sFlashCsInfo
,
2014 Adapter
->ulFlashControlSectionStart
,
2015 sizeof(sFlashCsInfo
),
2020 /* restore the values. */
2021 wrmalt(Adapter
, 0x0f000C80, &uiTemp
, sizeof(uiTemp
));
2027 * Procedure: BcmGetFlashSectorSize
2029 * Description: Finds the sector size of the FLASH.
2032 * Adapter - ptr to Adapter object instance
2035 * unsigned int - sector size.
2039 static unsigned int BcmGetFlashSectorSize(struct bcm_mini_adapter
*Adapter
, unsigned int FlashSectorSizeSig
, unsigned int FlashSectorSize
)
2041 unsigned int uiSectorSize
= 0;
2042 unsigned int uiSectorSig
= 0;
2044 if (Adapter
->bSectorSizeOverride
&&
2045 (Adapter
->uiSectorSizeInCFG
<= MAX_SECTOR_SIZE
&&
2046 Adapter
->uiSectorSizeInCFG
>= MIN_SECTOR_SIZE
)) {
2047 Adapter
->uiSectorSize
= Adapter
->uiSectorSizeInCFG
;
2049 uiSectorSig
= FlashSectorSizeSig
;
2051 if (uiSectorSig
== FLASH_SECTOR_SIZE_SIG
) {
2052 uiSectorSize
= FlashSectorSize
;
2054 * If the sector size stored in the FLASH makes sense then use it.
2056 if (uiSectorSize
<= MAX_SECTOR_SIZE
&& uiSectorSize
>= MIN_SECTOR_SIZE
) {
2057 Adapter
->uiSectorSize
= uiSectorSize
;
2058 } else if (Adapter
->uiSectorSizeInCFG
<= MAX_SECTOR_SIZE
&&
2059 Adapter
->uiSectorSizeInCFG
>= MIN_SECTOR_SIZE
) {
2060 /* No valid size in FLASH, check if Config file has it. */
2061 Adapter
->uiSectorSize
= Adapter
->uiSectorSizeInCFG
;
2063 /* Init to Default, if none of the above works. */
2064 Adapter
->uiSectorSize
= DEFAULT_SECTOR_SIZE
;
2067 if (Adapter
->uiSectorSizeInCFG
<= MAX_SECTOR_SIZE
&&
2068 Adapter
->uiSectorSizeInCFG
>= MIN_SECTOR_SIZE
)
2069 Adapter
->uiSectorSize
= Adapter
->uiSectorSizeInCFG
;
2071 Adapter
->uiSectorSize
= DEFAULT_SECTOR_SIZE
;
2075 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "Sector size :%x\n", Adapter
->uiSectorSize
);
2077 return Adapter
->uiSectorSize
;
2081 * Procedure: BcmInitEEPROMQueues
2083 * Description: Initialization of EEPROM queues.
2086 * Adapter - ptr to Adapter object instance
2089 * <OSAL_STATUS_CODE>
2092 static int BcmInitEEPROMQueues(struct bcm_mini_adapter
*Adapter
)
2094 unsigned int value
= 0;
2095 /* CHIP Bug : Clear the Avail bits on the Read queue. The default
2096 * value on this register is supposed to be 0x00001102.
2097 * But we get 0x00001122.
2099 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "Fixing reset value on 0x0f003004 register\n");
2100 value
= EEPROM_READ_DATA_AVAIL
;
2101 wrmalt(Adapter
, EEPROM_SPI_Q_STATUS1_REG
, &value
, sizeof(value
));
2103 /* Flush the all the EEPROM queues. */
2104 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, " Flushing the queues\n");
2105 value
= EEPROM_ALL_QUEUE_FLUSH
;
2106 wrmalt(Adapter
, SPI_FLUSH_REG
, &value
, sizeof(value
));
2109 wrmalt(Adapter
, SPI_FLUSH_REG
, &value
, sizeof(value
));
2111 /* Read the EEPROM Status Register. Just to see, no real purpose. */
2112 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "EEPROM Status register value = %x\n", ReadEEPROMStatusRegister(Adapter
));
2114 return STATUS_SUCCESS
;
2115 } /* BcmInitEEPROMQueues() */
2118 * Procedure: BcmInitNVM
2120 * Description: Initialization of NVM, EEPROM size,FLASH size, sector size etc.
2123 * Adapter - ptr to Adapter object instance
2126 * <OSAL_STATUS_CODE>
2129 int BcmInitNVM(struct bcm_mini_adapter
*ps_adapter
)
2131 BcmValidateNvmType(ps_adapter
);
2132 BcmInitEEPROMQueues(ps_adapter
);
2134 if (ps_adapter
->eNVMType
== NVM_AUTODETECT
) {
2135 ps_adapter
->eNVMType
= BcmGetNvmType(ps_adapter
);
2136 if (ps_adapter
->eNVMType
== NVM_UNKNOWN
)
2137 BCM_DEBUG_PRINT(ps_adapter
, DBG_TYPE_PRINTK
, 0, 0, "NVM Type is unknown!!\n");
2138 } else if (ps_adapter
->eNVMType
== NVM_FLASH
) {
2139 BcmGetFlashCSInfo(ps_adapter
);
2142 BcmGetNvmSize(ps_adapter
);
2144 return STATUS_SUCCESS
;
2147 /* BcmGetNvmSize : set the EEPROM or flash size in Adapter.
2150 * Adapter data structure
2155 static int BcmGetNvmSize(struct bcm_mini_adapter
*Adapter
)
2157 if (Adapter
->eNVMType
== NVM_EEPROM
)
2158 Adapter
->uiNVMDSDSize
= BcmGetEEPROMSize(Adapter
);
2159 else if (Adapter
->eNVMType
== NVM_FLASH
)
2160 Adapter
->uiNVMDSDSize
= BcmGetFlashSize(Adapter
);
2166 * Procedure: BcmValidateNvm
2168 * Description: Validates the NVM Type option selected against the device
2171 * Adapter - ptr to Adapter object instance
2177 static VOID
BcmValidateNvmType(struct bcm_mini_adapter
*Adapter
)
2180 * if forcing the FLASH through CFG file, we should ensure device really has a FLASH.
2181 * Accessing the FLASH address without the FLASH being present can cause hang/freeze etc.
2182 * So if NVM_FLASH is selected for older chipsets, change it to AUTODETECT where EEPROM is 1st choice.
2185 if (Adapter
->eNVMType
== NVM_FLASH
&&
2186 Adapter
->chip_id
< 0xBECE3300)
2187 Adapter
->eNVMType
= NVM_AUTODETECT
;
2191 * Procedure: BcmReadFlashRDID
2193 * Description: Reads ID from Serial Flash
2196 * Adapter - ptr to Adapter object instance
2202 static ULONG
BcmReadFlashRDID(struct bcm_mini_adapter
*Adapter
)
2208 * Read ID Instruction.
2210 value
= (FLASH_CMD_READ_ID
<< 24);
2211 wrmalt(Adapter
, FLASH_SPI_CMDQ_REG
, &value
, sizeof(value
));
2217 * Read SPI READQ REG. The output will be WWXXYYZZ.
2218 * The ID is 3Bytes long and is WWXXYY. ZZ needs to be Ignored.
2220 rdmalt(Adapter
, FLASH_SPI_READQ_REG
, (PUINT
)&ulRDID
, sizeof(ulRDID
));
2225 int BcmAllocFlashCSStructure(struct bcm_mini_adapter
*psAdapter
)
2228 BCM_DEBUG_PRINT(psAdapter
, DBG_TYPE_PRINTK
, 0, 0, "Adapter structure point is NULL");
2231 psAdapter
->psFlashCSInfo
= (PFLASH_CS_INFO
)kzalloc(sizeof(FLASH_CS_INFO
), GFP_KERNEL
);
2232 if (psAdapter
->psFlashCSInfo
== NULL
) {
2233 BCM_DEBUG_PRINT(psAdapter
, DBG_TYPE_PRINTK
, 0, 0, "Can't Allocate memory for Flash 1.x");
2237 psAdapter
->psFlash2xCSInfo
= (PFLASH2X_CS_INFO
)kzalloc(sizeof(FLASH2X_CS_INFO
), GFP_KERNEL
);
2238 if (!psAdapter
->psFlash2xCSInfo
) {
2239 BCM_DEBUG_PRINT(psAdapter
, DBG_TYPE_PRINTK
, 0, 0, "Can't Allocate memory for Flash 2.x");
2240 kfree(psAdapter
->psFlashCSInfo
);
2244 psAdapter
->psFlash2xVendorInfo
= (PFLASH2X_VENDORSPECIFIC_INFO
)kzalloc(sizeof(FLASH2X_VENDORSPECIFIC_INFO
), GFP_KERNEL
);
2245 if (!psAdapter
->psFlash2xVendorInfo
) {
2246 BCM_DEBUG_PRINT(psAdapter
, DBG_TYPE_PRINTK
, 0, 0, "Can't Allocate Vendor Info Memory for Flash 2.x");
2247 kfree(psAdapter
->psFlashCSInfo
);
2248 kfree(psAdapter
->psFlash2xCSInfo
);
2252 return STATUS_SUCCESS
;
2255 int BcmDeAllocFlashCSStructure(struct bcm_mini_adapter
*psAdapter
)
2258 BCM_DEBUG_PRINT(psAdapter
, DBG_TYPE_PRINTK
, 0, 0, "Adapter structure point is NULL");
2261 kfree(psAdapter
->psFlashCSInfo
);
2262 kfree(psAdapter
->psFlash2xCSInfo
);
2263 kfree(psAdapter
->psFlash2xVendorInfo
);
2264 return STATUS_SUCCESS
;
2267 static int BcmDumpFlash2XCSStructure(PFLASH2X_CS_INFO psFlash2xCSInfo
, struct bcm_mini_adapter
*Adapter
)
2269 unsigned int Index
= 0;
2271 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "**********************FLASH2X CS Structure *******************");
2272 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "Signature is :%x", (psFlash2xCSInfo
->MagicNumber
));
2273 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "Flash Major Version :%d", MAJOR_VERSION(psFlash2xCSInfo
->FlashLayoutVersion
));
2274 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "Flash Minor Version :%d", MINOR_VERSION(psFlash2xCSInfo
->FlashLayoutVersion
));
2275 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, " ISOImageMajorVersion:0x%x", (psFlash2xCSInfo
->ISOImageVersion
));
2276 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "SCSIFirmwareMajorVersion :0x%x", (psFlash2xCSInfo
->SCSIFirmwareVersion
));
2277 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "OffsetFromZeroForPart1ISOImage :0x%x", (psFlash2xCSInfo
->OffsetFromZeroForPart1ISOImage
));
2278 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "OffsetFromZeroForScsiFirmware :0x%x", (psFlash2xCSInfo
->OffsetFromZeroForScsiFirmware
));
2279 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "SizeOfScsiFirmware :0x%x", (psFlash2xCSInfo
->SizeOfScsiFirmware
));
2280 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "OffsetFromZeroForPart2ISOImage :0x%x", (psFlash2xCSInfo
->OffsetFromZeroForPart2ISOImage
));
2281 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "OffsetFromZeroForDSDStart :0x%x", (psFlash2xCSInfo
->OffsetFromZeroForDSDStart
));
2282 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "OffsetFromZeroForDSDEnd :0x%x", (psFlash2xCSInfo
->OffsetFromZeroForDSDEnd
));
2283 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "OffsetFromZeroForVSAStart :0x%x", (psFlash2xCSInfo
->OffsetFromZeroForVSAStart
));
2284 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "OffsetFromZeroForVSAEnd :0x%x", (psFlash2xCSInfo
->OffsetFromZeroForVSAEnd
));
2285 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "OffsetFromZeroForControlSectionStart :0x%x", (psFlash2xCSInfo
->OffsetFromZeroForControlSectionStart
));
2286 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "OffsetFromZeroForControlSectionData :0x%x", (psFlash2xCSInfo
->OffsetFromZeroForControlSectionData
));
2287 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "CDLessInactivityTimeout :0x%x", (psFlash2xCSInfo
->CDLessInactivityTimeout
));
2288 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "NewImageSignature :0x%x", (psFlash2xCSInfo
->NewImageSignature
));
2289 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "FlashSectorSizeSig :0x%x", (psFlash2xCSInfo
->FlashSectorSizeSig
));
2290 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "FlashSectorSize :0x%x", (psFlash2xCSInfo
->FlashSectorSize
));
2291 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "FlashWriteSupportSize :0x%x", (psFlash2xCSInfo
->FlashWriteSupportSize
));
2292 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "TotalFlashSize :0x%X", (psFlash2xCSInfo
->TotalFlashSize
));
2293 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "FlashBaseAddr :0x%x", (psFlash2xCSInfo
->FlashBaseAddr
));
2294 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "FlashPartMaxSize :0x%x", (psFlash2xCSInfo
->FlashPartMaxSize
));
2295 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "IsCDLessDeviceBootSig :0x%x", (psFlash2xCSInfo
->IsCDLessDeviceBootSig
));
2296 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "MassStorageTimeout :0x%x", (psFlash2xCSInfo
->MassStorageTimeout
));
2297 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "OffsetISOImage1Part1Start :0x%x", (psFlash2xCSInfo
->OffsetISOImage1Part1Start
));
2298 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "OffsetISOImage1Part1End :0x%x", (psFlash2xCSInfo
->OffsetISOImage1Part1End
));
2299 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "OffsetISOImage1Part2Start :0x%x", (psFlash2xCSInfo
->OffsetISOImage1Part2Start
));
2300 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "OffsetISOImage1Part2End :0x%x", (psFlash2xCSInfo
->OffsetISOImage1Part2End
));
2301 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "OffsetISOImage1Part3Start :0x%x", (psFlash2xCSInfo
->OffsetISOImage1Part3Start
));
2302 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "OffsetISOImage1Part3End :0x%x", (psFlash2xCSInfo
->OffsetISOImage1Part3End
));
2303 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "OffsetISOImage2Part1Start :0x%x", (psFlash2xCSInfo
->OffsetISOImage2Part1Start
));
2304 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "OffsetISOImage2Part1End :0x%x", (psFlash2xCSInfo
->OffsetISOImage2Part1End
));
2305 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "OffsetISOImage2Part2Start :0x%x", (psFlash2xCSInfo
->OffsetISOImage2Part2Start
));
2306 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "OffsetISOImage2Part2End :0x%x", (psFlash2xCSInfo
->OffsetISOImage2Part2End
));
2307 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "OffsetISOImage2Part3Start :0x%x", (psFlash2xCSInfo
->OffsetISOImage2Part3Start
));
2308 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "OffsetISOImage2Part3End :0x%x", (psFlash2xCSInfo
->OffsetISOImage2Part3End
));
2309 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "OffsetFromDSDStartForDSDHeader :0x%x", (psFlash2xCSInfo
->OffsetFromDSDStartForDSDHeader
));
2310 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "OffsetFromZeroForDSD1Start :0x%x", (psFlash2xCSInfo
->OffsetFromZeroForDSD1Start
));
2311 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "OffsetFromZeroForDSD1End :0x%x", (psFlash2xCSInfo
->OffsetFromZeroForDSD1End
));
2312 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "OffsetFromZeroForDSD2Start :0x%x", (psFlash2xCSInfo
->OffsetFromZeroForDSD2Start
));
2313 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "OffsetFromZeroForDSD2End :0x%x", (psFlash2xCSInfo
->OffsetFromZeroForDSD2End
));
2314 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "OffsetFromZeroForVSA1Start :0x%x", (psFlash2xCSInfo
->OffsetFromZeroForVSA1Start
));
2315 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "OffsetFromZeroForVSA1End :0x%x", (psFlash2xCSInfo
->OffsetFromZeroForVSA1End
));
2316 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "OffsetFromZeroForVSA2Start :0x%x", (psFlash2xCSInfo
->OffsetFromZeroForVSA2Start
));
2317 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "OffsetFromZeroForVSA2End :0x%x", (psFlash2xCSInfo
->OffsetFromZeroForVSA2End
));
2318 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "Sector Access Bit Map is Defined as :");
2320 for (Index
= 0; Index
< (FLASH2X_TOTAL_SIZE
/ (DEFAULT_SECTOR_SIZE
* 16)); Index
++)
2321 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "SectorAccessBitMap[%d] :0x%x", Index
,
2322 (psFlash2xCSInfo
->SectorAccessBitMap
[Index
]));
2324 return STATUS_SUCCESS
;
2327 static int ConvertEndianOf2XCSStructure(PFLASH2X_CS_INFO psFlash2xCSInfo
)
2329 unsigned int Index
= 0;
2331 psFlash2xCSInfo
->MagicNumber
= ntohl(psFlash2xCSInfo
->MagicNumber
);
2332 psFlash2xCSInfo
->FlashLayoutVersion
= ntohl(psFlash2xCSInfo
->FlashLayoutVersion
);
2333 /* psFlash2xCSInfo->FlashLayoutMinorVersion = ntohs(psFlash2xCSInfo->FlashLayoutMinorVersion); */
2334 psFlash2xCSInfo
->ISOImageVersion
= ntohl(psFlash2xCSInfo
->ISOImageVersion
);
2335 psFlash2xCSInfo
->SCSIFirmwareVersion
= ntohl(psFlash2xCSInfo
->SCSIFirmwareVersion
);
2336 psFlash2xCSInfo
->OffsetFromZeroForPart1ISOImage
= ntohl(psFlash2xCSInfo
->OffsetFromZeroForPart1ISOImage
);
2337 psFlash2xCSInfo
->OffsetFromZeroForScsiFirmware
= ntohl(psFlash2xCSInfo
->OffsetFromZeroForScsiFirmware
);
2338 psFlash2xCSInfo
->SizeOfScsiFirmware
= ntohl(psFlash2xCSInfo
->SizeOfScsiFirmware
);
2339 psFlash2xCSInfo
->OffsetFromZeroForPart2ISOImage
= ntohl(psFlash2xCSInfo
->OffsetFromZeroForPart2ISOImage
);
2340 psFlash2xCSInfo
->OffsetFromZeroForDSDStart
= ntohl(psFlash2xCSInfo
->OffsetFromZeroForDSDStart
);
2341 psFlash2xCSInfo
->OffsetFromZeroForDSDEnd
= ntohl(psFlash2xCSInfo
->OffsetFromZeroForDSDEnd
);
2342 psFlash2xCSInfo
->OffsetFromZeroForVSAStart
= ntohl(psFlash2xCSInfo
->OffsetFromZeroForVSAStart
);
2343 psFlash2xCSInfo
->OffsetFromZeroForVSAEnd
= ntohl(psFlash2xCSInfo
->OffsetFromZeroForVSAEnd
);
2344 psFlash2xCSInfo
->OffsetFromZeroForControlSectionStart
= ntohl(psFlash2xCSInfo
->OffsetFromZeroForControlSectionStart
);
2345 psFlash2xCSInfo
->OffsetFromZeroForControlSectionData
= ntohl(psFlash2xCSInfo
->OffsetFromZeroForControlSectionData
);
2346 psFlash2xCSInfo
->CDLessInactivityTimeout
= ntohl(psFlash2xCSInfo
->CDLessInactivityTimeout
);
2347 psFlash2xCSInfo
->NewImageSignature
= ntohl(psFlash2xCSInfo
->NewImageSignature
);
2348 psFlash2xCSInfo
->FlashSectorSizeSig
= ntohl(psFlash2xCSInfo
->FlashSectorSizeSig
);
2349 psFlash2xCSInfo
->FlashSectorSize
= ntohl(psFlash2xCSInfo
->FlashSectorSize
);
2350 psFlash2xCSInfo
->FlashWriteSupportSize
= ntohl(psFlash2xCSInfo
->FlashWriteSupportSize
);
2351 psFlash2xCSInfo
->TotalFlashSize
= ntohl(psFlash2xCSInfo
->TotalFlashSize
);
2352 psFlash2xCSInfo
->FlashBaseAddr
= ntohl(psFlash2xCSInfo
->FlashBaseAddr
);
2353 psFlash2xCSInfo
->FlashPartMaxSize
= ntohl(psFlash2xCSInfo
->FlashPartMaxSize
);
2354 psFlash2xCSInfo
->IsCDLessDeviceBootSig
= ntohl(psFlash2xCSInfo
->IsCDLessDeviceBootSig
);
2355 psFlash2xCSInfo
->MassStorageTimeout
= ntohl(psFlash2xCSInfo
->MassStorageTimeout
);
2356 psFlash2xCSInfo
->OffsetISOImage1Part1Start
= ntohl(psFlash2xCSInfo
->OffsetISOImage1Part1Start
);
2357 psFlash2xCSInfo
->OffsetISOImage1Part1End
= ntohl(psFlash2xCSInfo
->OffsetISOImage1Part1End
);
2358 psFlash2xCSInfo
->OffsetISOImage1Part2Start
= ntohl(psFlash2xCSInfo
->OffsetISOImage1Part2Start
);
2359 psFlash2xCSInfo
->OffsetISOImage1Part2End
= ntohl(psFlash2xCSInfo
->OffsetISOImage1Part2End
);
2360 psFlash2xCSInfo
->OffsetISOImage1Part3Start
= ntohl(psFlash2xCSInfo
->OffsetISOImage1Part3Start
);
2361 psFlash2xCSInfo
->OffsetISOImage1Part3End
= ntohl(psFlash2xCSInfo
->OffsetISOImage1Part3End
);
2362 psFlash2xCSInfo
->OffsetISOImage2Part1Start
= ntohl(psFlash2xCSInfo
->OffsetISOImage2Part1Start
);
2363 psFlash2xCSInfo
->OffsetISOImage2Part1End
= ntohl(psFlash2xCSInfo
->OffsetISOImage2Part1End
);
2364 psFlash2xCSInfo
->OffsetISOImage2Part2Start
= ntohl(psFlash2xCSInfo
->OffsetISOImage2Part2Start
);
2365 psFlash2xCSInfo
->OffsetISOImage2Part2End
= ntohl(psFlash2xCSInfo
->OffsetISOImage2Part2End
);
2366 psFlash2xCSInfo
->OffsetISOImage2Part3Start
= ntohl(psFlash2xCSInfo
->OffsetISOImage2Part3Start
);
2367 psFlash2xCSInfo
->OffsetISOImage2Part3End
= ntohl(psFlash2xCSInfo
->OffsetISOImage2Part3End
);
2368 psFlash2xCSInfo
->OffsetFromDSDStartForDSDHeader
= ntohl(psFlash2xCSInfo
->OffsetFromDSDStartForDSDHeader
);
2369 psFlash2xCSInfo
->OffsetFromZeroForDSD1Start
= ntohl(psFlash2xCSInfo
->OffsetFromZeroForDSD1Start
);
2370 psFlash2xCSInfo
->OffsetFromZeroForDSD1End
= ntohl(psFlash2xCSInfo
->OffsetFromZeroForDSD1End
);
2371 psFlash2xCSInfo
->OffsetFromZeroForDSD2Start
= ntohl(psFlash2xCSInfo
->OffsetFromZeroForDSD2Start
);
2372 psFlash2xCSInfo
->OffsetFromZeroForDSD2End
= ntohl(psFlash2xCSInfo
->OffsetFromZeroForDSD2End
);
2373 psFlash2xCSInfo
->OffsetFromZeroForVSA1Start
= ntohl(psFlash2xCSInfo
->OffsetFromZeroForVSA1Start
);
2374 psFlash2xCSInfo
->OffsetFromZeroForVSA1End
= ntohl(psFlash2xCSInfo
->OffsetFromZeroForVSA1End
);
2375 psFlash2xCSInfo
->OffsetFromZeroForVSA2Start
= ntohl(psFlash2xCSInfo
->OffsetFromZeroForVSA2Start
);
2376 psFlash2xCSInfo
->OffsetFromZeroForVSA2End
= ntohl(psFlash2xCSInfo
->OffsetFromZeroForVSA2End
);
2378 for (Index
= 0; Index
< (FLASH2X_TOTAL_SIZE
/ (DEFAULT_SECTOR_SIZE
* 16)); Index
++)
2379 psFlash2xCSInfo
->SectorAccessBitMap
[Index
] = ntohl(psFlash2xCSInfo
->SectorAccessBitMap
[Index
]);
2381 return STATUS_SUCCESS
;
2384 static int ConvertEndianOfCSStructure(PFLASH_CS_INFO psFlashCSInfo
)
2386 /* unsigned int Index = 0; */
2387 psFlashCSInfo
->MagicNumber
= ntohl(psFlashCSInfo
->MagicNumber
);
2388 psFlashCSInfo
->FlashLayoutVersion
= ntohl(psFlashCSInfo
->FlashLayoutVersion
);
2389 psFlashCSInfo
->ISOImageVersion
= ntohl(psFlashCSInfo
->ISOImageVersion
);
2390 /* won't convert according to old assumption */
2391 psFlashCSInfo
->SCSIFirmwareVersion
= (psFlashCSInfo
->SCSIFirmwareVersion
);
2392 psFlashCSInfo
->OffsetFromZeroForPart1ISOImage
= ntohl(psFlashCSInfo
->OffsetFromZeroForPart1ISOImage
);
2393 psFlashCSInfo
->OffsetFromZeroForScsiFirmware
= ntohl(psFlashCSInfo
->OffsetFromZeroForScsiFirmware
);
2394 psFlashCSInfo
->SizeOfScsiFirmware
= ntohl(psFlashCSInfo
->SizeOfScsiFirmware
);
2395 psFlashCSInfo
->OffsetFromZeroForPart2ISOImage
= ntohl(psFlashCSInfo
->OffsetFromZeroForPart2ISOImage
);
2396 psFlashCSInfo
->OffsetFromZeroForCalibrationStart
= ntohl(psFlashCSInfo
->OffsetFromZeroForCalibrationStart
);
2397 psFlashCSInfo
->OffsetFromZeroForCalibrationEnd
= ntohl(psFlashCSInfo
->OffsetFromZeroForCalibrationEnd
);
2398 psFlashCSInfo
->OffsetFromZeroForVSAStart
= ntohl(psFlashCSInfo
->OffsetFromZeroForVSAStart
);
2399 psFlashCSInfo
->OffsetFromZeroForVSAEnd
= ntohl(psFlashCSInfo
->OffsetFromZeroForVSAEnd
);
2400 psFlashCSInfo
->OffsetFromZeroForControlSectionStart
= ntohl(psFlashCSInfo
->OffsetFromZeroForControlSectionStart
);
2401 psFlashCSInfo
->OffsetFromZeroForControlSectionData
= ntohl(psFlashCSInfo
->OffsetFromZeroForControlSectionData
);
2402 psFlashCSInfo
->CDLessInactivityTimeout
= ntohl(psFlashCSInfo
->CDLessInactivityTimeout
);
2403 psFlashCSInfo
->NewImageSignature
= ntohl(psFlashCSInfo
->NewImageSignature
);
2404 psFlashCSInfo
->FlashSectorSizeSig
= ntohl(psFlashCSInfo
->FlashSectorSizeSig
);
2405 psFlashCSInfo
->FlashSectorSize
= ntohl(psFlashCSInfo
->FlashSectorSize
);
2406 psFlashCSInfo
->FlashWriteSupportSize
= ntohl(psFlashCSInfo
->FlashWriteSupportSize
);
2407 psFlashCSInfo
->TotalFlashSize
= ntohl(psFlashCSInfo
->TotalFlashSize
);
2408 psFlashCSInfo
->FlashBaseAddr
= ntohl(psFlashCSInfo
->FlashBaseAddr
);
2409 psFlashCSInfo
->FlashPartMaxSize
= ntohl(psFlashCSInfo
->FlashPartMaxSize
);
2410 psFlashCSInfo
->IsCDLessDeviceBootSig
= ntohl(psFlashCSInfo
->IsCDLessDeviceBootSig
);
2411 psFlashCSInfo
->MassStorageTimeout
= ntohl(psFlashCSInfo
->MassStorageTimeout
);
2413 return STATUS_SUCCESS
;
2416 static int IsSectionExistInVendorInfo(struct bcm_mini_adapter
*Adapter
, FLASH2X_SECTION_VAL section
)
2418 return (Adapter
->uiVendorExtnFlag
&&
2419 (Adapter
->psFlash2xVendorInfo
->VendorSection
[section
].AccessFlags
& FLASH2X_SECTION_PRESENT
) &&
2420 (Adapter
->psFlash2xVendorInfo
->VendorSection
[section
].OffsetFromZeroForSectionStart
!= UNINIT_PTR_IN_CS
));
2423 static VOID
UpdateVendorInfo(struct bcm_mini_adapter
*Adapter
)
2426 unsigned int uiSizeSection
= 0;
2428 Adapter
->uiVendorExtnFlag
= FALSE
;
2430 for (i
= 0; i
< TOTAL_SECTIONS
; i
++)
2431 Adapter
->psFlash2xVendorInfo
->VendorSection
[i
].OffsetFromZeroForSectionStart
= UNINIT_PTR_IN_CS
;
2433 if (STATUS_SUCCESS
!= vendorextnGetSectionInfo(Adapter
, Adapter
->psFlash2xVendorInfo
))
2437 while (i
< TOTAL_SECTIONS
) {
2438 if (!(Adapter
->psFlash2xVendorInfo
->VendorSection
[i
].AccessFlags
& FLASH2X_SECTION_PRESENT
)) {
2443 Adapter
->uiVendorExtnFlag
= TRUE
;
2444 uiSizeSection
= (Adapter
->psFlash2xVendorInfo
->VendorSection
[i
].OffsetFromZeroForSectionEnd
-
2445 Adapter
->psFlash2xVendorInfo
->VendorSection
[i
].OffsetFromZeroForSectionStart
);
2449 if ((uiSizeSection
>= (Adapter
->psFlash2xCSInfo
->OffsetFromDSDStartForDSDHeader
+ sizeof(DSD_HEADER
))) &&
2450 (UNINIT_PTR_IN_CS
!= Adapter
->psFlash2xVendorInfo
->VendorSection
[i
].OffsetFromZeroForSectionStart
))
2451 Adapter
->psFlash2xCSInfo
->OffsetFromZeroForDSDStart
= Adapter
->psFlash2xCSInfo
->OffsetFromZeroForDSDEnd
= VENDOR_PTR_IN_CS
;
2453 Adapter
->psFlash2xCSInfo
->OffsetFromZeroForDSDStart
= Adapter
->psFlash2xCSInfo
->OffsetFromZeroForDSDEnd
= UNINIT_PTR_IN_CS
;
2457 if ((uiSizeSection
>= (Adapter
->psFlash2xCSInfo
->OffsetFromDSDStartForDSDHeader
+ sizeof(DSD_HEADER
))) &&
2458 (UNINIT_PTR_IN_CS
!= Adapter
->psFlash2xVendorInfo
->VendorSection
[i
].OffsetFromZeroForSectionStart
))
2459 Adapter
->psFlash2xCSInfo
->OffsetFromZeroForDSD1Start
= Adapter
->psFlash2xCSInfo
->OffsetFromZeroForDSD1End
= VENDOR_PTR_IN_CS
;
2461 Adapter
->psFlash2xCSInfo
->OffsetFromZeroForDSD1Start
= Adapter
->psFlash2xCSInfo
->OffsetFromZeroForDSD1End
= UNINIT_PTR_IN_CS
;
2465 if ((uiSizeSection
>= (Adapter
->psFlash2xCSInfo
->OffsetFromDSDStartForDSDHeader
+ sizeof(DSD_HEADER
))) &&
2466 (UNINIT_PTR_IN_CS
!= Adapter
->psFlash2xVendorInfo
->VendorSection
[i
].OffsetFromZeroForSectionStart
))
2467 Adapter
->psFlash2xCSInfo
->OffsetFromZeroForDSD2Start
= Adapter
->psFlash2xCSInfo
->OffsetFromZeroForDSD2End
= VENDOR_PTR_IN_CS
;
2469 Adapter
->psFlash2xCSInfo
->OffsetFromZeroForDSD2Start
= Adapter
->psFlash2xCSInfo
->OffsetFromZeroForDSD2End
= UNINIT_PTR_IN_CS
;
2472 if (UNINIT_PTR_IN_CS
!= Adapter
->psFlash2xVendorInfo
->VendorSection
[i
].OffsetFromZeroForSectionStart
)
2473 Adapter
->psFlash2xCSInfo
->OffsetFromZeroForVSAStart
= Adapter
->psFlash2xCSInfo
->OffsetFromZeroForVSAEnd
= VENDOR_PTR_IN_CS
;
2475 Adapter
->psFlash2xCSInfo
->OffsetFromZeroForVSAStart
= Adapter
->psFlash2xCSInfo
->OffsetFromZeroForVSAEnd
= UNINIT_PTR_IN_CS
;
2479 if (UNINIT_PTR_IN_CS
!= Adapter
->psFlash2xVendorInfo
->VendorSection
[i
].OffsetFromZeroForSectionStart
)
2480 Adapter
->psFlash2xCSInfo
->OffsetFromZeroForVSA1Start
= Adapter
->psFlash2xCSInfo
->OffsetFromZeroForVSA1End
= VENDOR_PTR_IN_CS
;
2482 Adapter
->psFlash2xCSInfo
->OffsetFromZeroForVSA1Start
= Adapter
->psFlash2xCSInfo
->OffsetFromZeroForVSA1End
= UNINIT_PTR_IN_CS
;
2485 if (UNINIT_PTR_IN_CS
!= Adapter
->psFlash2xVendorInfo
->VendorSection
[i
].OffsetFromZeroForSectionStart
)
2486 Adapter
->psFlash2xCSInfo
->OffsetFromZeroForVSA2Start
= Adapter
->psFlash2xCSInfo
->OffsetFromZeroForVSA2End
= VENDOR_PTR_IN_CS
;
2488 Adapter
->psFlash2xCSInfo
->OffsetFromZeroForVSA2Start
= Adapter
->psFlash2xCSInfo
->OffsetFromZeroForVSA2End
= UNINIT_PTR_IN_CS
;
2499 * Procedure: BcmGetFlashCSInfo
2501 * Description: Reads control structure and gets Cal section addresses.
2504 * Adapter - ptr to Adapter object instance
2510 static int BcmGetFlashCSInfo(struct bcm_mini_adapter
*Adapter
)
2512 /* FLASH_CS_INFO sFlashCsInfo = {0}; */
2514 #if !defined(BCM_SHM_INTERFACE) || defined(FLASH_DIRECT_ACCESS)
2518 unsigned int uiFlashLayoutMajorVersion
;
2519 Adapter
->uiFlashLayoutMinorVersion
= 0;
2520 Adapter
->uiFlashLayoutMajorVersion
= 0;
2521 Adapter
->ulFlashControlSectionStart
= FLASH_CS_INFO_START_ADDR
;
2523 Adapter
->uiFlashBaseAdd
= 0;
2524 Adapter
->ulFlashCalStart
= 0;
2525 memset(Adapter
->psFlashCSInfo
, 0 , sizeof(FLASH_CS_INFO
));
2526 memset(Adapter
->psFlash2xCSInfo
, 0 , sizeof(FLASH2X_CS_INFO
));
2528 if (!Adapter
->bDDRInitDone
) {
2529 value
= FLASH_CONTIGIOUS_START_ADDR_BEFORE_INIT
;
2530 wrmalt(Adapter
, 0xAF00A080, &value
, sizeof(value
));
2533 /* Reading first 8 Bytes to get the Flash Layout
2534 * MagicNumber(4 bytes) +FlashLayoutMinorVersion(2 Bytes) +FlashLayoutMajorVersion(2 Bytes)
2536 BeceemFlashBulkRead(Adapter
, (PUINT
)Adapter
->psFlashCSInfo
, Adapter
->ulFlashControlSectionStart
, 8);
2538 Adapter
->psFlashCSInfo
->FlashLayoutVersion
= ntohl(Adapter
->psFlashCSInfo
->FlashLayoutVersion
);
2539 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "Flash Layout Version :%X", (Adapter
->psFlashCSInfo
->FlashLayoutVersion
));
2540 /* BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "Flash Layout Minor Version :%d\n", ntohs(sFlashCsInfo.FlashLayoutMinorVersion)); */
2541 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "Signature is :%x\n", ntohl(Adapter
->psFlashCSInfo
->MagicNumber
));
2543 if (FLASH_CONTROL_STRUCT_SIGNATURE
== ntohl(Adapter
->psFlashCSInfo
->MagicNumber
)) {
2544 uiFlashLayoutMajorVersion
= MAJOR_VERSION((Adapter
->psFlashCSInfo
->FlashLayoutVersion
));
2545 Adapter
->uiFlashLayoutMinorVersion
= MINOR_VERSION((Adapter
->psFlashCSInfo
->FlashLayoutVersion
));
2547 Adapter
->uiFlashLayoutMinorVersion
= 0;
2548 uiFlashLayoutMajorVersion
= 0;
2551 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "FLASH LAYOUT MAJOR VERSION :%X", uiFlashLayoutMajorVersion
);
2553 if (uiFlashLayoutMajorVersion
< FLASH_2X_MAJOR_NUMBER
) {
2554 BeceemFlashBulkRead(Adapter
, (PUINT
)Adapter
->psFlashCSInfo
, Adapter
->ulFlashControlSectionStart
, sizeof(FLASH_CS_INFO
));
2555 ConvertEndianOfCSStructure(Adapter
->psFlashCSInfo
);
2556 Adapter
->ulFlashCalStart
= (Adapter
->psFlashCSInfo
->OffsetFromZeroForCalibrationStart
);
2558 if (!((Adapter
->uiFlashLayoutMajorVersion
== 1) && (Adapter
->uiFlashLayoutMinorVersion
== 1)))
2559 Adapter
->ulFlashControlSectionStart
= Adapter
->psFlashCSInfo
->OffsetFromZeroForControlSectionStart
;
2561 if ((FLASH_CONTROL_STRUCT_SIGNATURE
== (Adapter
->psFlashCSInfo
->MagicNumber
)) &&
2562 (SCSI_FIRMWARE_MINOR_VERSION
<= MINOR_VERSION(Adapter
->psFlashCSInfo
->SCSIFirmwareVersion
)) &&
2563 (FLASH_SECTOR_SIZE_SIG
== (Adapter
->psFlashCSInfo
->FlashSectorSizeSig
)) &&
2564 (BYTE_WRITE_SUPPORT
== (Adapter
->psFlashCSInfo
->FlashWriteSupportSize
))) {
2565 Adapter
->ulFlashWriteSize
= (Adapter
->psFlashCSInfo
->FlashWriteSupportSize
);
2566 Adapter
->fpFlashWrite
= flashByteWrite
;
2567 Adapter
->fpFlashWriteWithStatusCheck
= flashByteWriteStatus
;
2569 Adapter
->ulFlashWriteSize
= MAX_RW_SIZE
;
2570 Adapter
->fpFlashWrite
= flashWrite
;
2571 Adapter
->fpFlashWriteWithStatusCheck
= flashWriteStatus
;
2574 BcmGetFlashSectorSize(Adapter
, (Adapter
->psFlashCSInfo
->FlashSectorSizeSig
),
2575 (Adapter
->psFlashCSInfo
->FlashSectorSize
));
2576 Adapter
->uiFlashBaseAdd
= Adapter
->psFlashCSInfo
->FlashBaseAddr
& 0xFCFFFFFF;
2578 if (BcmFlash2xBulkRead(Adapter
, (PUINT
)Adapter
->psFlash2xCSInfo
, NO_SECTION_VAL
,
2579 Adapter
->ulFlashControlSectionStart
, sizeof(FLASH2X_CS_INFO
))) {
2580 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Unable to read CS structure\n");
2581 return STATUS_FAILURE
;
2584 ConvertEndianOf2XCSStructure(Adapter
->psFlash2xCSInfo
);
2585 BcmDumpFlash2XCSStructure(Adapter
->psFlash2xCSInfo
, Adapter
);
2586 if ((FLASH_CONTROL_STRUCT_SIGNATURE
== Adapter
->psFlash2xCSInfo
->MagicNumber
) &&
2587 (SCSI_FIRMWARE_MINOR_VERSION
<= MINOR_VERSION(Adapter
->psFlash2xCSInfo
->SCSIFirmwareVersion
)) &&
2588 (FLASH_SECTOR_SIZE_SIG
== Adapter
->psFlash2xCSInfo
->FlashSectorSizeSig
) &&
2589 (BYTE_WRITE_SUPPORT
== Adapter
->psFlash2xCSInfo
->FlashWriteSupportSize
)) {
2590 Adapter
->ulFlashWriteSize
= Adapter
->psFlash2xCSInfo
->FlashWriteSupportSize
;
2591 Adapter
->fpFlashWrite
= flashByteWrite
;
2592 Adapter
->fpFlashWriteWithStatusCheck
= flashByteWriteStatus
;
2594 Adapter
->ulFlashWriteSize
= MAX_RW_SIZE
;
2595 Adapter
->fpFlashWrite
= flashWrite
;
2596 Adapter
->fpFlashWriteWithStatusCheck
= flashWriteStatus
;
2599 BcmGetFlashSectorSize(Adapter
, Adapter
->psFlash2xCSInfo
->FlashSectorSizeSig
,
2600 Adapter
->psFlash2xCSInfo
->FlashSectorSize
);
2602 UpdateVendorInfo(Adapter
);
2604 BcmGetActiveDSD(Adapter
);
2605 BcmGetActiveISO(Adapter
);
2606 Adapter
->uiFlashBaseAdd
= Adapter
->psFlash2xCSInfo
->FlashBaseAddr
& 0xFCFFFFFF;
2607 Adapter
->ulFlashControlSectionStart
= Adapter
->psFlash2xCSInfo
->OffsetFromZeroForControlSectionStart
;
2610 * Concerns: what if CS sector size does not match with this sector size ???
2611 * what is the indication of AccessBitMap in CS in flash 2.x ????
2613 Adapter
->ulFlashID
= BcmReadFlashRDID(Adapter
);
2614 Adapter
->uiFlashLayoutMajorVersion
= uiFlashLayoutMajorVersion
;
2616 return STATUS_SUCCESS
;
2620 * Procedure: BcmGetNvmType
2622 * Description: Finds the type of NVM used.
2625 * Adapter - ptr to Adapter object instance
2632 static NVM_TYPE
BcmGetNvmType(struct bcm_mini_adapter
*Adapter
)
2634 unsigned int uiData
= 0;
2636 BeceemEEPROMBulkRead(Adapter
, &uiData
, 0x0, 4);
2641 * Read control struct and get cal addresses before accessing the flash
2643 BcmGetFlashCSInfo(Adapter
);
2645 BeceemFlashBulkRead(Adapter
, &uiData
, 0x0 + Adapter
->ulFlashCalStart
, 4);
2650 * even if there is no valid signature on EEPROM/FLASH find out if they really exist.
2651 * if exist select it.
2653 if (BcmGetEEPROMSize(Adapter
))
2656 /* TBD for Flash. */
2661 * BcmGetSectionValStartOffset - this will calculate the section's starting offset if section val is given
2662 * @Adapter : Drivers Private Data structure
2663 * @eFlashSectionVal : Flash secion value defined in enum FLASH2X_SECTION_VAL
2666 * On success it return the start offset of the provided section val
2667 * On Failure -returns STATUS_FAILURE
2670 int BcmGetSectionValStartOffset(struct bcm_mini_adapter
*Adapter
, FLASH2X_SECTION_VAL eFlashSectionVal
)
2673 * Considering all the section for which end offset can be calculated or directly given
2674 * in CS Structure. if matching case does not exist, return STATUS_FAILURE indicating section
2675 * endoffset can't be calculated or given in CS Structure.
2678 int SectStartOffset
= 0;
2680 SectStartOffset
= INVALID_OFFSET
;
2682 if (IsSectionExistInVendorInfo(Adapter
, eFlashSectionVal
))
2683 return Adapter
->psFlash2xVendorInfo
->VendorSection
[eFlashSectionVal
].OffsetFromZeroForSectionStart
;
2685 switch (eFlashSectionVal
) {
2687 if ((Adapter
->psFlash2xCSInfo
->OffsetISOImage1Part1Start
!= UNINIT_PTR_IN_CS
) &&
2688 (IsNonCDLessDevice(Adapter
) == FALSE
))
2689 SectStartOffset
= (Adapter
->psFlash2xCSInfo
->OffsetISOImage1Part1Start
);
2692 if ((Adapter
->psFlash2xCSInfo
->OffsetISOImage2Part1Start
!= UNINIT_PTR_IN_CS
) &&
2693 (IsNonCDLessDevice(Adapter
) == FALSE
))
2694 SectStartOffset
= (Adapter
->psFlash2xCSInfo
->OffsetISOImage2Part1Start
);
2697 if (Adapter
->psFlash2xCSInfo
->OffsetFromZeroForDSDStart
!= UNINIT_PTR_IN_CS
)
2698 SectStartOffset
= (Adapter
->psFlash2xCSInfo
->OffsetFromZeroForDSDStart
);
2701 if (Adapter
->psFlash2xCSInfo
->OffsetFromZeroForDSD1Start
!= UNINIT_PTR_IN_CS
)
2702 SectStartOffset
= (Adapter
->psFlash2xCSInfo
->OffsetFromZeroForDSD1Start
);
2705 if (Adapter
->psFlash2xCSInfo
->OffsetFromZeroForDSD2Start
!= UNINIT_PTR_IN_CS
)
2706 SectStartOffset
= (Adapter
->psFlash2xCSInfo
->OffsetFromZeroForDSD2Start
);
2709 if (Adapter
->psFlash2xCSInfo
->OffsetFromZeroForVSAStart
!= UNINIT_PTR_IN_CS
)
2710 SectStartOffset
= (Adapter
->psFlash2xCSInfo
->OffsetFromZeroForVSAStart
);
2713 if (Adapter
->psFlash2xCSInfo
->OffsetFromZeroForVSA1Start
!= UNINIT_PTR_IN_CS
)
2714 SectStartOffset
= (Adapter
->psFlash2xCSInfo
->OffsetFromZeroForVSA1Start
);
2717 if (Adapter
->psFlash2xCSInfo
->OffsetFromZeroForVSA2Start
!= UNINIT_PTR_IN_CS
)
2718 SectStartOffset
= (Adapter
->psFlash2xCSInfo
->OffsetFromZeroForVSA2Start
);
2721 if (Adapter
->psFlash2xCSInfo
->OffsetFromZeroForScsiFirmware
!= UNINIT_PTR_IN_CS
)
2722 SectStartOffset
= (Adapter
->psFlash2xCSInfo
->OffsetFromZeroForScsiFirmware
);
2724 case CONTROL_SECTION
:
2725 if (Adapter
->psFlash2xCSInfo
->OffsetFromZeroForControlSectionStart
!= UNINIT_PTR_IN_CS
)
2726 SectStartOffset
= (Adapter
->psFlash2xCSInfo
->OffsetFromZeroForControlSectionStart
);
2728 case ISO_IMAGE1_PART2
:
2729 if (Adapter
->psFlash2xCSInfo
->OffsetISOImage1Part2Start
!= UNINIT_PTR_IN_CS
)
2730 SectStartOffset
= (Adapter
->psFlash2xCSInfo
->OffsetISOImage1Part2Start
);
2732 case ISO_IMAGE1_PART3
:
2733 if (Adapter
->psFlash2xCSInfo
->OffsetISOImage1Part3Start
!= UNINIT_PTR_IN_CS
)
2734 SectStartOffset
= (Adapter
->psFlash2xCSInfo
->OffsetISOImage1Part3Start
);
2736 case ISO_IMAGE2_PART2
:
2737 if (Adapter
->psFlash2xCSInfo
->OffsetISOImage2Part2Start
!= UNINIT_PTR_IN_CS
)
2738 SectStartOffset
= (Adapter
->psFlash2xCSInfo
->OffsetISOImage2Part2Start
);
2740 case ISO_IMAGE2_PART3
:
2741 if (Adapter
->psFlash2xCSInfo
->OffsetISOImage2Part3Start
!= UNINIT_PTR_IN_CS
)
2742 SectStartOffset
= (Adapter
->psFlash2xCSInfo
->OffsetISOImage2Part3Start
);
2745 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Section Does not exist in Flash 2.x");
2746 SectStartOffset
= INVALID_OFFSET
;
2749 return SectStartOffset
;
2753 * BcmGetSectionValEndOffset - this will calculate the section's Ending offset if section val is given
2754 * @Adapter : Drivers Private Data structure
2755 * @eFlashSectionVal : Flash secion value defined in enum FLASH2X_SECTION_VAL
2758 * On success it return the end offset of the provided section val
2759 * On Failure -returns STATUS_FAILURE
2762 int BcmGetSectionValEndOffset(struct bcm_mini_adapter
*Adapter
, FLASH2X_SECTION_VAL eFlash2xSectionVal
)
2764 int SectEndOffset
= 0;
2766 SectEndOffset
= INVALID_OFFSET
;
2767 if (IsSectionExistInVendorInfo(Adapter
, eFlash2xSectionVal
))
2768 return Adapter
->psFlash2xVendorInfo
->VendorSection
[eFlash2xSectionVal
].OffsetFromZeroForSectionEnd
;
2770 switch (eFlash2xSectionVal
) {
2772 if ((Adapter
->psFlash2xCSInfo
->OffsetISOImage1Part1End
!= UNINIT_PTR_IN_CS
) &&
2773 (IsNonCDLessDevice(Adapter
) == FALSE
))
2774 SectEndOffset
= (Adapter
->psFlash2xCSInfo
->OffsetISOImage1Part1End
);
2777 if ((Adapter
->psFlash2xCSInfo
->OffsetISOImage2Part1End
!= UNINIT_PTR_IN_CS
) &&
2778 (IsNonCDLessDevice(Adapter
) == FALSE
))
2779 SectEndOffset
= (Adapter
->psFlash2xCSInfo
->OffsetISOImage2Part1End
);
2782 if (Adapter
->psFlash2xCSInfo
->OffsetFromZeroForDSDEnd
!= UNINIT_PTR_IN_CS
)
2783 SectEndOffset
= (Adapter
->psFlash2xCSInfo
->OffsetFromZeroForDSDEnd
);
2786 if (Adapter
->psFlash2xCSInfo
->OffsetFromZeroForDSD1End
!= UNINIT_PTR_IN_CS
)
2787 SectEndOffset
= (Adapter
->psFlash2xCSInfo
->OffsetFromZeroForDSD1End
);
2790 if (Adapter
->psFlash2xCSInfo
->OffsetFromZeroForDSD2End
!= UNINIT_PTR_IN_CS
)
2791 SectEndOffset
= (Adapter
->psFlash2xCSInfo
->OffsetFromZeroForDSD2End
);
2794 if (Adapter
->psFlash2xCSInfo
->OffsetFromZeroForVSAEnd
!= UNINIT_PTR_IN_CS
)
2795 SectEndOffset
= (Adapter
->psFlash2xCSInfo
->OffsetFromZeroForVSAEnd
);
2798 if (Adapter
->psFlash2xCSInfo
->OffsetFromZeroForVSA1End
!= UNINIT_PTR_IN_CS
)
2799 SectEndOffset
= (Adapter
->psFlash2xCSInfo
->OffsetFromZeroForVSA1End
);
2802 if (Adapter
->psFlash2xCSInfo
->OffsetFromZeroForVSA2End
!= UNINIT_PTR_IN_CS
)
2803 SectEndOffset
= (Adapter
->psFlash2xCSInfo
->OffsetFromZeroForVSA2End
);
2806 if (Adapter
->psFlash2xCSInfo
->OffsetFromZeroForScsiFirmware
!= UNINIT_PTR_IN_CS
)
2807 SectEndOffset
= ((Adapter
->psFlash2xCSInfo
->OffsetFromZeroForScsiFirmware
) +
2808 (Adapter
->psFlash2xCSInfo
->SizeOfScsiFirmware
));
2810 case CONTROL_SECTION
:
2811 /* Not Clear So Putting failure. confirm and fix it. */
2812 SectEndOffset
= STATUS_FAILURE
;
2813 case ISO_IMAGE1_PART2
:
2814 if (Adapter
->psFlash2xCSInfo
->OffsetISOImage1Part2End
!= UNINIT_PTR_IN_CS
)
2815 SectEndOffset
= (Adapter
->psFlash2xCSInfo
->OffsetISOImage1Part2End
);
2817 case ISO_IMAGE1_PART3
:
2818 if (Adapter
->psFlash2xCSInfo
->OffsetISOImage1Part3End
!= UNINIT_PTR_IN_CS
)
2819 SectEndOffset
= (Adapter
->psFlash2xCSInfo
->OffsetISOImage1Part3End
);
2821 case ISO_IMAGE2_PART2
:
2822 if (Adapter
->psFlash2xCSInfo
->OffsetISOImage2Part2End
!= UNINIT_PTR_IN_CS
)
2823 SectEndOffset
= (Adapter
->psFlash2xCSInfo
->OffsetISOImage2Part2End
);
2825 case ISO_IMAGE2_PART3
:
2826 if (Adapter
->psFlash2xCSInfo
->OffsetISOImage2Part3End
!= UNINIT_PTR_IN_CS
)
2827 SectEndOffset
= (Adapter
->psFlash2xCSInfo
->OffsetISOImage2Part3End
);
2830 SectEndOffset
= INVALID_OFFSET
;
2833 return SectEndOffset
;
2837 * BcmFlash2xBulkRead:- Read API for Flash Map 2.x .
2838 * @Adapter :Driver Private Data Structure
2839 * @pBuffer : Buffer where data has to be put after reading
2840 * @eFlashSectionVal :Flash Section Val defined in FLASH2X_SECTION_VAL
2841 * @uiOffsetWithinSectionVal :- Offset with in provided section
2842 * @uiNumBytes : Number of Bytes for Read
2845 * return true on success and STATUS_FAILURE on fail.
2848 int BcmFlash2xBulkRead(struct bcm_mini_adapter
*Adapter
,
2850 FLASH2X_SECTION_VAL eFlash2xSectionVal
,
2851 unsigned int uiOffsetWithinSectionVal
,
2852 unsigned int uiNumBytes
)
2854 int Status
= STATUS_SUCCESS
;
2855 int SectionStartOffset
= 0;
2856 unsigned int uiAbsoluteOffset
= 0;
2857 unsigned int uiTemp
= 0, value
= 0;
2860 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Adapter structure is NULL");
2863 if (Adapter
->device_removed
) {
2864 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Device has been removed");
2868 /* NO_SECTION_VAL means absolute offset is given. */
2869 if (eFlash2xSectionVal
== NO_SECTION_VAL
)
2870 SectionStartOffset
= 0;
2872 SectionStartOffset
= BcmGetSectionValStartOffset(Adapter
, eFlash2xSectionVal
);
2874 if (SectionStartOffset
== STATUS_FAILURE
) {
2875 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "This Section<%d> does not exixt in Flash 2.x Map ", eFlash2xSectionVal
);
2879 if (IsSectionExistInVendorInfo(Adapter
, eFlash2xSectionVal
))
2880 return vendorextnReadSection(Adapter
, (PUCHAR
)pBuffer
, eFlash2xSectionVal
, uiOffsetWithinSectionVal
, uiNumBytes
);
2882 /* calculating the absolute offset from FLASH; */
2883 uiAbsoluteOffset
= uiOffsetWithinSectionVal
+ SectionStartOffset
;
2884 rdmalt(Adapter
, 0x0f000C80, &uiTemp
, sizeof(uiTemp
));
2886 wrmalt(Adapter
, 0x0f000C80, &value
, sizeof(value
));
2887 Status
= BeceemFlashBulkRead(Adapter
, pBuffer
, uiAbsoluteOffset
, uiNumBytes
);
2888 wrmalt(Adapter
, 0x0f000C80, &uiTemp
, sizeof(uiTemp
));
2890 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Flash Read Failed with Status :%d", Status
);
2898 * BcmFlash2xBulkWrite :-API for Writing on the Flash Map 2.x.
2899 * @Adapter :Driver Private Data Structure
2900 * @pBuffer : Buffer From where data has to taken for writing
2901 * @eFlashSectionVal :Flash Section Val defined in FLASH2X_SECTION_VAL
2902 * @uiOffsetWithinSectionVal :- Offset with in provided section
2903 * @uiNumBytes : Number of Bytes for Write
2906 * return true on success and STATUS_FAILURE on fail.
2910 int BcmFlash2xBulkWrite(struct bcm_mini_adapter
*Adapter
,
2912 FLASH2X_SECTION_VAL eFlash2xSectVal
,
2913 unsigned int uiOffset
,
2914 unsigned int uiNumBytes
,
2915 unsigned int bVerify
)
2917 int Status
= STATUS_SUCCESS
;
2918 unsigned int FlashSectValStartOffset
= 0;
2919 unsigned int uiTemp
= 0, value
= 0;
2922 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Adapter structure is NULL");
2926 if (Adapter
->device_removed
) {
2927 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Device has been removed");
2931 /* NO_SECTION_VAL means absolute offset is given. */
2932 if (eFlash2xSectVal
== NO_SECTION_VAL
)
2933 FlashSectValStartOffset
= 0;
2935 FlashSectValStartOffset
= BcmGetSectionValStartOffset(Adapter
, eFlash2xSectVal
);
2937 if (FlashSectValStartOffset
== STATUS_FAILURE
) {
2938 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "This Section<%d> does not exixt in Flash Map 2.x", eFlash2xSectVal
);
2942 if (IsSectionExistInVendorInfo(Adapter
, eFlash2xSectVal
))
2943 return vendorextnWriteSection(Adapter
, (PUCHAR
)pBuffer
, eFlash2xSectVal
, uiOffset
, uiNumBytes
, bVerify
);
2945 /* calculating the absolute offset from FLASH; */
2946 uiOffset
= uiOffset
+ FlashSectValStartOffset
;
2948 rdmalt(Adapter
, 0x0f000C80, &uiTemp
, sizeof(uiTemp
));
2950 wrmalt(Adapter
, 0x0f000C80, &value
, sizeof(value
));
2952 Status
= BeceemFlashBulkWrite(Adapter
, pBuffer
, uiOffset
, uiNumBytes
, bVerify
);
2954 wrmalt(Adapter
, 0x0f000C80, &uiTemp
, sizeof(uiTemp
));
2956 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Flash Write failed with Status :%d", Status
);
2964 * BcmGetActiveDSD : Set the Active DSD in Adapter Structure which has to be dumped in DDR
2965 * @Adapter :-Drivers private Data Structure
2968 * Return STATUS_SUCESS if get success in setting the right DSD else negaive error code
2972 static int BcmGetActiveDSD(struct bcm_mini_adapter
*Adapter
)
2974 FLASH2X_SECTION_VAL uiHighestPriDSD
= 0;
2976 uiHighestPriDSD
= getHighestPriDSD(Adapter
);
2977 Adapter
->eActiveDSD
= uiHighestPriDSD
;
2979 if (DSD0
== uiHighestPriDSD
)
2980 Adapter
->ulFlashCalStart
= Adapter
->psFlash2xCSInfo
->OffsetFromZeroForDSDStart
;
2981 if (DSD1
== uiHighestPriDSD
)
2982 Adapter
->ulFlashCalStart
= Adapter
->psFlash2xCSInfo
->OffsetFromZeroForDSD1Start
;
2983 if (DSD2
== uiHighestPriDSD
)
2984 Adapter
->ulFlashCalStart
= Adapter
->psFlash2xCSInfo
->OffsetFromZeroForDSD2Start
;
2985 if (Adapter
->eActiveDSD
)
2986 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "Active DSD :%d", Adapter
->eActiveDSD
);
2987 if (Adapter
->eActiveDSD
== 0) {
2988 /* if No DSD gets Active, Make Active the DSD with WR permission */
2989 if (IsSectionWritable(Adapter
, DSD2
)) {
2990 Adapter
->eActiveDSD
= DSD2
;
2991 Adapter
->ulFlashCalStart
= Adapter
->psFlash2xCSInfo
->OffsetFromZeroForDSD2Start
;
2992 } else if (IsSectionWritable(Adapter
, DSD1
)) {
2993 Adapter
->eActiveDSD
= DSD1
;
2994 Adapter
->ulFlashCalStart
= Adapter
->psFlash2xCSInfo
->OffsetFromZeroForDSD1Start
;
2995 } else if (IsSectionWritable(Adapter
, DSD0
)) {
2996 Adapter
->eActiveDSD
= DSD0
;
2997 Adapter
->ulFlashCalStart
= Adapter
->psFlash2xCSInfo
->OffsetFromZeroForDSDStart
;
3001 return STATUS_SUCCESS
;
3005 * BcmGetActiveISO :- Set the Active ISO in Adapter Data Structue
3006 * @Adapter : Driver private Data Structure
3009 * Sucsess:- STATUS_SUCESS
3010 * Failure- : negative erro code
3014 static int BcmGetActiveISO(struct bcm_mini_adapter
*Adapter
)
3016 int HighestPriISO
= 0;
3018 HighestPriISO
= getHighestPriISO(Adapter
);
3020 Adapter
->eActiveISO
= HighestPriISO
;
3021 if (Adapter
->eActiveISO
== ISO_IMAGE2
)
3022 Adapter
->uiActiveISOOffset
= (Adapter
->psFlash2xCSInfo
->OffsetISOImage2Part1Start
);
3023 else if (Adapter
->eActiveISO
== ISO_IMAGE1
)
3024 Adapter
->uiActiveISOOffset
= (Adapter
->psFlash2xCSInfo
->OffsetISOImage1Part1Start
);
3026 if (Adapter
->eActiveISO
)
3027 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "Active ISO :%x", Adapter
->eActiveISO
);
3029 return STATUS_SUCCESS
;
3033 * IsOffsetWritable :- it will tell the access permission of the sector having passed offset
3034 * @Adapter : Drivers Private Data Structure
3035 * @uiOffset : Offset provided in the Flash
3038 * Success:-TRUE , offset is writable
3039 * Failure:-FALSE, offset is RO
3043 B_UINT8
IsOffsetWritable(struct bcm_mini_adapter
*Adapter
, unsigned int uiOffset
)
3045 unsigned int uiSectorNum
= 0;
3046 unsigned int uiWordOfSectorPermission
= 0;
3047 unsigned int uiBitofSectorePermission
= 0;
3048 B_UINT32 permissionBits
= 0;
3050 uiSectorNum
= uiOffset
/Adapter
->uiSectorSize
;
3052 /* calculating the word having this Sector Access permission from SectorAccessBitMap Array */
3053 uiWordOfSectorPermission
= Adapter
->psFlash2xCSInfo
->SectorAccessBitMap
[uiSectorNum
/ 16];
3055 /* calculating the bit index inside the word for this sector */
3056 uiBitofSectorePermission
= 2 * (15 - uiSectorNum
% 16);
3058 /* Setting Access permission */
3059 permissionBits
= uiWordOfSectorPermission
& (0x3 << uiBitofSectorePermission
);
3060 permissionBits
= (permissionBits
>> uiBitofSectorePermission
) & 0x3;
3061 if (permissionBits
== SECTOR_READWRITE_PERMISSION
)
3067 static int BcmDumpFlash2xSectionBitMap(PFLASH2X_BITMAP psFlash2xBitMap
)
3069 struct bcm_mini_adapter
*Adapter
= GET_BCM_ADAPTER(gblpnetdev
);
3071 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "***************Flash 2.x Section Bitmap***************");
3072 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "ISO_IMAGE1 :0X%x", psFlash2xBitMap
->ISO_IMAGE1
);
3073 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "ISO_IMAGE2 :0X%x", psFlash2xBitMap
->ISO_IMAGE2
);
3074 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "DSD0 :0X%x", psFlash2xBitMap
->DSD0
);
3075 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "DSD1 :0X%x", psFlash2xBitMap
->DSD1
);
3076 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "DSD2 :0X%x", psFlash2xBitMap
->DSD2
);
3077 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "VSA0 :0X%x", psFlash2xBitMap
->VSA0
);
3078 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "VSA1 :0X%x", psFlash2xBitMap
->VSA1
);
3079 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "VSA2 :0X%x", psFlash2xBitMap
->VSA2
);
3080 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "SCSI :0X%x", psFlash2xBitMap
->SCSI
);
3081 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "CONTROL_SECTION :0X%x", psFlash2xBitMap
->CONTROL_SECTION
);
3083 return STATUS_SUCCESS
;
3087 * BcmGetFlash2xSectionalBitMap :- It will provide the bit map of all the section present in Flash
3088 * 8bit has been assigned to every section.
3089 * bit[0] :Section present or not
3090 * bit[1] :section is valid or not
3091 * bit[2] : Secton is read only or has write permission too.
3092 * bit[3] : Active Section -
3093 * bit[7...4] = Reserved .
3095 * @Adapter:-Driver private Data Structure
3098 * Success:- STATUS_SUCESS
3099 * Failure:- negative error code
3102 int BcmGetFlash2xSectionalBitMap(struct bcm_mini_adapter
*Adapter
, PFLASH2X_BITMAP psFlash2xBitMap
)
3104 PFLASH2X_CS_INFO psFlash2xCSInfo
= Adapter
->psFlash2xCSInfo
;
3105 FLASH2X_SECTION_VAL uiHighestPriDSD
= 0;
3106 FLASH2X_SECTION_VAL uiHighestPriISO
= 0;
3107 BOOLEAN SetActiveDSDDone
= FALSE
;
3108 BOOLEAN SetActiveISODone
= FALSE
;
3110 /* For 1.x map all the section except DSD0 will be shown as not present
3111 * This part will be used by calibration tool to detect the number of DSD present in Flash.
3113 if (IsFlash2x(Adapter
) == FALSE
) {
3114 psFlash2xBitMap
->ISO_IMAGE2
= 0;
3115 psFlash2xBitMap
->ISO_IMAGE1
= 0;
3116 psFlash2xBitMap
->DSD0
= FLASH2X_SECTION_VALID
| FLASH2X_SECTION_ACT
| FLASH2X_SECTION_PRESENT
; /* 0xF; 0000(Reseved)1(Active)0(RW)1(valid)1(present) */
3117 psFlash2xBitMap
->DSD1
= 0;
3118 psFlash2xBitMap
->DSD2
= 0;
3119 psFlash2xBitMap
->VSA0
= 0;
3120 psFlash2xBitMap
->VSA1
= 0;
3121 psFlash2xBitMap
->VSA2
= 0;
3122 psFlash2xBitMap
->CONTROL_SECTION
= 0;
3123 psFlash2xBitMap
->SCSI
= 0;
3124 psFlash2xBitMap
->Reserved0
= 0;
3125 psFlash2xBitMap
->Reserved1
= 0;
3126 psFlash2xBitMap
->Reserved2
= 0;
3128 return STATUS_SUCCESS
;
3131 uiHighestPriDSD
= getHighestPriDSD(Adapter
);
3132 uiHighestPriISO
= getHighestPriISO(Adapter
);
3137 if ((psFlash2xCSInfo
->OffsetISOImage2Part1Start
) != UNINIT_PTR_IN_CS
) {
3138 /* Setting the 0th Bit representing the Section is present or not. */
3139 psFlash2xBitMap
->ISO_IMAGE2
= psFlash2xBitMap
->ISO_IMAGE2
| FLASH2X_SECTION_PRESENT
;
3141 if (ReadISOSignature(Adapter
, ISO_IMAGE2
) == ISO_IMAGE_MAGIC_NUMBER
)
3142 psFlash2xBitMap
->ISO_IMAGE2
|= FLASH2X_SECTION_VALID
;
3144 /* Calculation for extrating the Access permission */
3145 if (IsSectionWritable(Adapter
, ISO_IMAGE2
) == FALSE
)
3146 psFlash2xBitMap
->ISO_IMAGE2
|= FLASH2X_SECTION_RO
;
3148 if (SetActiveISODone
== FALSE
&& uiHighestPriISO
== ISO_IMAGE2
) {
3149 psFlash2xBitMap
->ISO_IMAGE2
|= FLASH2X_SECTION_ACT
;
3150 SetActiveISODone
= TRUE
;
3157 if ((psFlash2xCSInfo
->OffsetISOImage1Part1Start
) != UNINIT_PTR_IN_CS
) {
3158 /* Setting the 0th Bit representing the Section is present or not. */
3159 psFlash2xBitMap
->ISO_IMAGE1
= psFlash2xBitMap
->ISO_IMAGE1
| FLASH2X_SECTION_PRESENT
;
3161 if (ReadISOSignature(Adapter
, ISO_IMAGE1
) == ISO_IMAGE_MAGIC_NUMBER
)
3162 psFlash2xBitMap
->ISO_IMAGE1
|= FLASH2X_SECTION_VALID
;
3164 /* Calculation for extrating the Access permission */
3165 if (IsSectionWritable(Adapter
, ISO_IMAGE1
) == FALSE
)
3166 psFlash2xBitMap
->ISO_IMAGE1
|= FLASH2X_SECTION_RO
;
3168 if (SetActiveISODone
== FALSE
&& uiHighestPriISO
== ISO_IMAGE1
) {
3169 psFlash2xBitMap
->ISO_IMAGE1
|= FLASH2X_SECTION_ACT
;
3170 SetActiveISODone
= TRUE
;
3177 if ((psFlash2xCSInfo
->OffsetFromZeroForDSD2Start
) != UNINIT_PTR_IN_CS
) {
3178 /* Setting the 0th Bit representing the Section is present or not. */
3179 psFlash2xBitMap
->DSD2
= psFlash2xBitMap
->DSD2
| FLASH2X_SECTION_PRESENT
;
3181 if (ReadDSDSignature(Adapter
, DSD2
) == DSD_IMAGE_MAGIC_NUMBER
)
3182 psFlash2xBitMap
->DSD2
|= FLASH2X_SECTION_VALID
;
3184 /* Calculation for extrating the Access permission */
3185 if (IsSectionWritable(Adapter
, DSD2
) == FALSE
) {
3186 psFlash2xBitMap
->DSD2
|= FLASH2X_SECTION_RO
;
3188 /* Means section is writable */
3189 if ((SetActiveDSDDone
== FALSE
) && (uiHighestPriDSD
== DSD2
)) {
3190 psFlash2xBitMap
->DSD2
|= FLASH2X_SECTION_ACT
;
3191 SetActiveDSDDone
= TRUE
;
3199 if ((psFlash2xCSInfo
->OffsetFromZeroForDSD1Start
) != UNINIT_PTR_IN_CS
) {
3200 /* Setting the 0th Bit representing the Section is present or not. */
3201 psFlash2xBitMap
->DSD1
= psFlash2xBitMap
->DSD1
| FLASH2X_SECTION_PRESENT
;
3203 if (ReadDSDSignature(Adapter
, DSD1
) == DSD_IMAGE_MAGIC_NUMBER
)
3204 psFlash2xBitMap
->DSD1
|= FLASH2X_SECTION_VALID
;
3206 /* Calculation for extrating the Access permission */
3207 if (IsSectionWritable(Adapter
, DSD1
) == FALSE
) {
3208 psFlash2xBitMap
->DSD1
|= FLASH2X_SECTION_RO
;
3210 /* Means section is writable */
3211 if ((SetActiveDSDDone
== FALSE
) && (uiHighestPriDSD
== DSD1
)) {
3212 psFlash2xBitMap
->DSD1
|= FLASH2X_SECTION_ACT
;
3213 SetActiveDSDDone
= TRUE
;
3221 if ((psFlash2xCSInfo
->OffsetFromZeroForDSDStart
) != UNINIT_PTR_IN_CS
) {
3222 /* Setting the 0th Bit representing the Section is present or not. */
3223 psFlash2xBitMap
->DSD0
= psFlash2xBitMap
->DSD0
| FLASH2X_SECTION_PRESENT
;
3225 if (ReadDSDSignature(Adapter
, DSD0
) == DSD_IMAGE_MAGIC_NUMBER
)
3226 psFlash2xBitMap
->DSD0
|= FLASH2X_SECTION_VALID
;
3228 /* Setting Access permission */
3229 if (IsSectionWritable(Adapter
, DSD0
) == FALSE
) {
3230 psFlash2xBitMap
->DSD0
|= FLASH2X_SECTION_RO
;
3232 /* Means section is writable */
3233 if ((SetActiveDSDDone
== FALSE
) && (uiHighestPriDSD
== DSD0
)) {
3234 psFlash2xBitMap
->DSD0
|= FLASH2X_SECTION_ACT
;
3235 SetActiveDSDDone
= TRUE
;
3243 if ((psFlash2xCSInfo
->OffsetFromZeroForVSAStart
) != UNINIT_PTR_IN_CS
) {
3244 /* Setting the 0th Bit representing the Section is present or not. */
3245 psFlash2xBitMap
->VSA0
= psFlash2xBitMap
->VSA0
| FLASH2X_SECTION_PRESENT
;
3247 /* Setting the Access Bit. Map is not defined hece setting it always valid */
3248 psFlash2xBitMap
->VSA0
|= FLASH2X_SECTION_VALID
;
3250 /* Calculation for extrating the Access permission */
3251 if (IsSectionWritable(Adapter
, VSA0
) == FALSE
)
3252 psFlash2xBitMap
->VSA0
|= FLASH2X_SECTION_RO
;
3254 /* By Default section is Active */
3255 psFlash2xBitMap
->VSA0
|= FLASH2X_SECTION_ACT
;
3261 if ((psFlash2xCSInfo
->OffsetFromZeroForVSA1Start
) != UNINIT_PTR_IN_CS
) {
3262 /* Setting the 0th Bit representing the Section is present or not. */
3263 psFlash2xBitMap
->VSA1
= psFlash2xBitMap
->VSA1
| FLASH2X_SECTION_PRESENT
;
3265 /* Setting the Access Bit. Map is not defined hece setting it always valid */
3266 psFlash2xBitMap
->VSA1
|= FLASH2X_SECTION_VALID
;
3268 /* Checking For Access permission */
3269 if (IsSectionWritable(Adapter
, VSA1
) == FALSE
)
3270 psFlash2xBitMap
->VSA1
|= FLASH2X_SECTION_RO
;
3272 /* By Default section is Active */
3273 psFlash2xBitMap
->VSA1
|= FLASH2X_SECTION_ACT
;
3279 if ((psFlash2xCSInfo
->OffsetFromZeroForVSA2Start
) != UNINIT_PTR_IN_CS
) {
3280 /* Setting the 0th Bit representing the Section is present or not. */
3281 psFlash2xBitMap
->VSA2
= psFlash2xBitMap
->VSA2
| FLASH2X_SECTION_PRESENT
;
3283 /* Setting the Access Bit. Map is not defined hece setting it always valid */
3284 psFlash2xBitMap
->VSA2
|= FLASH2X_SECTION_VALID
;
3286 /* Checking For Access permission */
3287 if (IsSectionWritable(Adapter
, VSA2
) == FALSE
)
3288 psFlash2xBitMap
->VSA2
|= FLASH2X_SECTION_RO
;
3290 /* By Default section is Active */
3291 psFlash2xBitMap
->VSA2
|= FLASH2X_SECTION_ACT
;
3297 if ((psFlash2xCSInfo
->OffsetFromZeroForScsiFirmware
) != UNINIT_PTR_IN_CS
) {
3298 /* Setting the 0th Bit representing the Section is present or not. */
3299 psFlash2xBitMap
->SCSI
= psFlash2xBitMap
->SCSI
| FLASH2X_SECTION_PRESENT
;
3301 /* Setting the Access Bit. Map is not defined hece setting it always valid */
3302 psFlash2xBitMap
->SCSI
|= FLASH2X_SECTION_VALID
;
3304 /* Checking For Access permission */
3305 if (IsSectionWritable(Adapter
, SCSI
) == FALSE
)
3306 psFlash2xBitMap
->SCSI
|= FLASH2X_SECTION_RO
;
3308 /* By Default section is Active */
3309 psFlash2xBitMap
->SCSI
|= FLASH2X_SECTION_ACT
;
3315 if ((psFlash2xCSInfo
->OffsetFromZeroForControlSectionStart
) != UNINIT_PTR_IN_CS
) {
3316 /* Setting the 0th Bit representing the Section is present or not. */
3317 psFlash2xBitMap
->CONTROL_SECTION
= psFlash2xBitMap
->CONTROL_SECTION
| (FLASH2X_SECTION_PRESENT
);
3319 /* Setting the Access Bit. Map is not defined hece setting it always valid */
3320 psFlash2xBitMap
->CONTROL_SECTION
|= FLASH2X_SECTION_VALID
;
3322 /* Checking For Access permission */
3323 if (IsSectionWritable(Adapter
, CONTROL_SECTION
) == FALSE
)
3324 psFlash2xBitMap
->CONTROL_SECTION
|= FLASH2X_SECTION_RO
;
3326 /* By Default section is Active */
3327 psFlash2xBitMap
->CONTROL_SECTION
|= FLASH2X_SECTION_ACT
;
3331 * For Reserved Sections
3333 psFlash2xBitMap
->Reserved0
= 0;
3334 psFlash2xBitMap
->Reserved0
= 0;
3335 psFlash2xBitMap
->Reserved0
= 0;
3336 BcmDumpFlash2xSectionBitMap(psFlash2xBitMap
);
3338 return STATUS_SUCCESS
;
3342 * BcmSetActiveSection :- Set Active section is used to make priority field highest over other
3343 * section of same type.
3345 * @Adapater :- Bcm Driver Private Data Structure
3346 * @eFlash2xSectionVal :- Flash section val whose priority has to be made highest.
3348 * Return Value:- Make the priorit highest else return erorr code
3352 int BcmSetActiveSection(struct bcm_mini_adapter
*Adapter
, FLASH2X_SECTION_VAL eFlash2xSectVal
)
3354 unsigned int SectImagePriority
= 0;
3355 int Status
= STATUS_SUCCESS
;
3357 /* DSD_HEADER sDSD = {0};
3358 * ISO_HEADER sISO = {0};
3360 int HighestPriDSD
= 0 ;
3361 int HighestPriISO
= 0;
3363 Status
= IsSectionWritable(Adapter
, eFlash2xSectVal
);
3364 if (Status
!= TRUE
) {
3365 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Provided Section <%d> is not writable", eFlash2xSectVal
);
3366 return STATUS_FAILURE
;
3369 Adapter
->bHeaderChangeAllowed
= TRUE
;
3370 switch (eFlash2xSectVal
) {
3373 if (ReadISOSignature(Adapter
, eFlash2xSectVal
) == ISO_IMAGE_MAGIC_NUMBER
) {
3374 HighestPriISO
= getHighestPriISO(Adapter
);
3376 if (HighestPriISO
== eFlash2xSectVal
) {
3377 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "Given ISO<%x> already has highest priority", eFlash2xSectVal
);
3378 Status
= STATUS_SUCCESS
;
3382 SectImagePriority
= ReadISOPriority(Adapter
, HighestPriISO
) + 1;
3384 if ((SectImagePriority
<= 0) && IsSectionWritable(Adapter
, HighestPriISO
)) {
3385 /* This is a SPECIAL Case which will only happen if the current highest priority ISO has priority value = 0x7FFFFFFF.
3386 * We will write 1 to the current Highest priority ISO And then shall increase the priority of the requested ISO
3389 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "SectImagePriority wraparound happened, eFlash2xSectVal: 0x%x\n", eFlash2xSectVal
);
3390 SectImagePriority
= htonl(0x1);
3391 Status
= BcmFlash2xBulkWrite(Adapter
,
3394 0 + FIELD_OFFSET_IN_HEADER(PISO_HEADER
, ISOImagePriority
),
3398 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Priority has not been written properly");
3399 Status
= STATUS_FAILURE
;
3403 HighestPriISO
= getHighestPriISO(Adapter
);
3405 if (HighestPriISO
== eFlash2xSectVal
) {
3406 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "Given ISO<%x> already has highest priority", eFlash2xSectVal
);
3407 Status
= STATUS_SUCCESS
;
3411 SectImagePriority
= 2;
3414 SectImagePriority
= htonl(SectImagePriority
);
3416 Status
= BcmFlash2xBulkWrite(Adapter
,
3419 0 + FIELD_OFFSET_IN_HEADER(PISO_HEADER
, ISOImagePriority
),
3423 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Priority has not been written properly");
3427 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Signature is currupted. Hence can't increase the priority");
3428 Status
= STATUS_FAILURE
;
3435 if (ReadDSDSignature(Adapter
, eFlash2xSectVal
) == DSD_IMAGE_MAGIC_NUMBER
) {
3436 HighestPriDSD
= getHighestPriDSD(Adapter
);
3437 if ((HighestPriDSD
== eFlash2xSectVal
)) {
3438 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "Given DSD<%x> already has highest priority", eFlash2xSectVal
);
3439 Status
= STATUS_SUCCESS
;
3443 SectImagePriority
= ReadDSDPriority(Adapter
, HighestPriDSD
) + 1;
3444 if (SectImagePriority
<= 0) {
3445 /* This is a SPECIAL Case which will only happen if the current highest priority DSD has priority value = 0x7FFFFFFF.
3446 * We will write 1 to the current Highest priority DSD And then shall increase the priority of the requested DSD
3449 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, NVM_RW
, DBG_LVL_ALL
, "SectImagePriority wraparound happened, eFlash2xSectVal: 0x%x\n", eFlash2xSectVal
);
3450 SectImagePriority
= htonl(0x1);
3452 Status
= BcmFlash2xBulkWrite(Adapter
,
3455 Adapter
->psFlash2xCSInfo
->OffsetFromDSDStartForDSDHeader
+ FIELD_OFFSET_IN_HEADER(PDSD_HEADER
, DSDImagePriority
),
3459 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Priority has not been written properly");
3463 HighestPriDSD
= getHighestPriDSD(Adapter
);
3465 if ((HighestPriDSD
== eFlash2xSectVal
)) {
3466 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "Made the DSD: %x highest by reducing priority of other\n", eFlash2xSectVal
);
3467 Status
= STATUS_SUCCESS
;
3471 SectImagePriority
= htonl(0x2);
3472 Status
= BcmFlash2xBulkWrite(Adapter
,
3475 Adapter
->psFlash2xCSInfo
->OffsetFromDSDStartForDSDHeader
+ FIELD_OFFSET_IN_HEADER(PDSD_HEADER
, DSDImagePriority
),
3479 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Priority has not been written properly");
3483 HighestPriDSD
= getHighestPriDSD(Adapter
);
3484 if ((HighestPriDSD
== eFlash2xSectVal
)) {
3485 Status
= STATUS_SUCCESS
;
3489 SectImagePriority
= 3;
3491 SectImagePriority
= htonl(SectImagePriority
);
3492 Status
= BcmFlash2xBulkWrite(Adapter
,
3495 Adapter
->psFlash2xCSInfo
->OffsetFromDSDStartForDSDHeader
+ FIELD_OFFSET_IN_HEADER(PDSD_HEADER
, DSDImagePriority
),
3499 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Priority has not been written properly");
3500 Status
= STATUS_FAILURE
;
3504 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Signature is currupted. Hence can't increase the priority");
3505 Status
= STATUS_FAILURE
;
3512 /* Has to be decided */
3515 Status
= STATUS_FAILURE
;
3519 Adapter
->bHeaderChangeAllowed
= FALSE
;
3524 * BcmCopyISO - Used only for copying the ISO section
3525 * @Adapater :- Bcm Driver Private Data Structure
3526 * @sCopySectStrut :- Section copy structure
3528 * Return value:- SUCCESS if copies successfully else negative error code
3532 int BcmCopyISO(struct bcm_mini_adapter
*Adapter
, FLASH2X_COPY_SECTION sCopySectStrut
)
3535 FLASH2X_SECTION_VAL eISOReadPart
= 0, eISOWritePart
= 0;
3536 unsigned int uiReadOffsetWithinPart
= 0, uiWriteOffsetWithinPart
= 0;
3537 unsigned int uiTotalDataToCopy
= 0;
3538 BOOLEAN IsThisHeaderSector
= FALSE
;
3539 unsigned int sigOffset
= 0;
3540 unsigned int ISOLength
= 0;
3541 unsigned int Status
= STATUS_SUCCESS
;
3542 unsigned int SigBuff
[MAX_RW_SIZE
];
3545 if (ReadISOSignature(Adapter
, sCopySectStrut
.SrcSection
) != ISO_IMAGE_MAGIC_NUMBER
) {
3546 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "error as Source ISO Section does not have valid signature");
3547 return STATUS_FAILURE
;
3550 Status
= BcmFlash2xBulkRead(Adapter
,
3552 sCopySectStrut
.SrcSection
,
3553 0 + FIELD_OFFSET_IN_HEADER(PISO_HEADER
, ISOImageSize
),
3556 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Read failed while copying ISO\n");
3560 ISOLength
= htonl(ISOLength
);
3561 if (ISOLength
% Adapter
->uiSectorSize
)
3562 ISOLength
= Adapter
->uiSectorSize
* (1 + ISOLength
/Adapter
->uiSectorSize
);
3564 sigOffset
= FIELD_OFFSET_IN_HEADER(PISO_HEADER
, ISOImageMagicNumber
);
3566 Buff
= kzalloc(Adapter
->uiSectorSize
, GFP_KERNEL
);
3569 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Memory allocation failed for section size");
3573 if (sCopySectStrut
.SrcSection
== ISO_IMAGE1
&& sCopySectStrut
.DstSection
== ISO_IMAGE2
) {
3574 eISOReadPart
= ISO_IMAGE1
;
3575 eISOWritePart
= ISO_IMAGE2
;
3576 uiReadOffsetWithinPart
= 0;
3577 uiWriteOffsetWithinPart
= 0;
3579 uiTotalDataToCopy
= (Adapter
->psFlash2xCSInfo
->OffsetISOImage1Part1End
) -
3580 (Adapter
->psFlash2xCSInfo
->OffsetISOImage1Part1Start
) +
3581 (Adapter
->psFlash2xCSInfo
->OffsetISOImage1Part2End
) -
3582 (Adapter
->psFlash2xCSInfo
->OffsetISOImage1Part2Start
) +
3583 (Adapter
->psFlash2xCSInfo
->OffsetISOImage1Part3End
) -
3584 (Adapter
->psFlash2xCSInfo
->OffsetISOImage1Part3Start
);
3586 if (uiTotalDataToCopy
< ISOLength
) {
3587 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "error as Source ISO Section does not have valid signature");
3588 Status
= STATUS_FAILURE
;
3592 uiTotalDataToCopy
= (Adapter
->psFlash2xCSInfo
->OffsetISOImage2Part1End
) -
3593 (Adapter
->psFlash2xCSInfo
->OffsetISOImage2Part1Start
) +
3594 (Adapter
->psFlash2xCSInfo
->OffsetISOImage2Part2End
) -
3595 (Adapter
->psFlash2xCSInfo
->OffsetISOImage2Part2Start
) +
3596 (Adapter
->psFlash2xCSInfo
->OffsetISOImage2Part3End
) -
3597 (Adapter
->psFlash2xCSInfo
->OffsetISOImage2Part3Start
);
3599 if (uiTotalDataToCopy
< ISOLength
) {
3600 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "error as Dest ISO Section does not have enough section size");
3601 Status
= STATUS_FAILURE
;
3605 uiTotalDataToCopy
= ISOLength
;
3607 CorruptISOSig(Adapter
, ISO_IMAGE2
);
3608 while (uiTotalDataToCopy
) {
3609 if (uiTotalDataToCopy
== Adapter
->uiSectorSize
) {
3610 /* Setting for write of first sector. First sector is assumed to be written in last */
3611 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "Writing the signature sector");
3612 eISOReadPart
= ISO_IMAGE1
;
3613 uiReadOffsetWithinPart
= 0;
3614 eISOWritePart
= ISO_IMAGE2
;
3615 uiWriteOffsetWithinPart
= 0;
3616 IsThisHeaderSector
= TRUE
;
3618 uiReadOffsetWithinPart
= uiReadOffsetWithinPart
+ Adapter
->uiSectorSize
;
3619 uiWriteOffsetWithinPart
= uiWriteOffsetWithinPart
+ Adapter
->uiSectorSize
;
3621 if ((eISOReadPart
== ISO_IMAGE1
) && (uiReadOffsetWithinPart
== (Adapter
->psFlash2xCSInfo
->OffsetISOImage1Part1End
- Adapter
->psFlash2xCSInfo
->OffsetISOImage1Part1Start
))) {
3622 eISOReadPart
= ISO_IMAGE1_PART2
;
3623 uiReadOffsetWithinPart
= 0;
3626 if ((eISOReadPart
== ISO_IMAGE1_PART2
) && (uiReadOffsetWithinPart
== (Adapter
->psFlash2xCSInfo
->OffsetISOImage1Part2End
- Adapter
->psFlash2xCSInfo
->OffsetISOImage1Part2Start
))) {
3627 eISOReadPart
= ISO_IMAGE1_PART3
;
3628 uiReadOffsetWithinPart
= 0;
3631 if ((eISOWritePart
== ISO_IMAGE2
) && (uiWriteOffsetWithinPart
== (Adapter
->psFlash2xCSInfo
->OffsetISOImage2Part1End
- Adapter
->psFlash2xCSInfo
->OffsetISOImage2Part1Start
))) {
3632 eISOWritePart
= ISO_IMAGE2_PART2
;
3633 uiWriteOffsetWithinPart
= 0;
3636 if ((eISOWritePart
== ISO_IMAGE2_PART2
) && (uiWriteOffsetWithinPart
== (Adapter
->psFlash2xCSInfo
->OffsetISOImage2Part2End
- Adapter
->psFlash2xCSInfo
->OffsetISOImage2Part2Start
))) {
3637 eISOWritePart
= ISO_IMAGE2_PART3
;
3638 uiWriteOffsetWithinPart
= 0;
3642 Status
= BcmFlash2xBulkRead(Adapter
,
3645 uiReadOffsetWithinPart
,
3646 Adapter
->uiSectorSize
);
3648 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Read failed while copying ISO: Part: %x, OffsetWithinPart: %x\n", eISOReadPart
, uiReadOffsetWithinPart
);
3652 if (IsThisHeaderSector
== TRUE
) {
3653 /* If this is header sector write 0xFFFFFFFF at the sig time and in last write sig */
3654 memcpy(SigBuff
, Buff
+ sigOffset
, MAX_RW_SIZE
);
3656 for (i
= 0; i
< MAX_RW_SIZE
; i
++)
3657 *(Buff
+ sigOffset
+ i
) = 0xFF;
3659 Adapter
->bHeaderChangeAllowed
= TRUE
;
3660 Status
= BcmFlash2xBulkWrite(Adapter
,
3663 uiWriteOffsetWithinPart
,
3664 Adapter
->uiSectorSize
,
3667 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Write failed while copying ISO: Part: %x, OffsetWithinPart: %x\n", eISOWritePart
, uiWriteOffsetWithinPart
);
3671 Adapter
->bHeaderChangeAllowed
= FALSE
;
3672 if (IsThisHeaderSector
== TRUE
) {
3673 WriteToFlashWithoutSectorErase(Adapter
,
3678 IsThisHeaderSector
= FALSE
;
3680 /* subtracting the written Data */
3681 uiTotalDataToCopy
= uiTotalDataToCopy
- Adapter
->uiSectorSize
;
3685 if (sCopySectStrut
.SrcSection
== ISO_IMAGE2
&& sCopySectStrut
.DstSection
== ISO_IMAGE1
) {
3686 eISOReadPart
= ISO_IMAGE2
;
3687 eISOWritePart
= ISO_IMAGE1
;
3688 uiReadOffsetWithinPart
= 0;
3689 uiWriteOffsetWithinPart
= 0;
3691 uiTotalDataToCopy
= (Adapter
->psFlash2xCSInfo
->OffsetISOImage2Part1End
) -
3692 (Adapter
->psFlash2xCSInfo
->OffsetISOImage2Part1Start
) +
3693 (Adapter
->psFlash2xCSInfo
->OffsetISOImage2Part2End
) -
3694 (Adapter
->psFlash2xCSInfo
->OffsetISOImage2Part2Start
) +
3695 (Adapter
->psFlash2xCSInfo
->OffsetISOImage2Part3End
) -
3696 (Adapter
->psFlash2xCSInfo
->OffsetISOImage2Part3Start
);
3698 if (uiTotalDataToCopy
< ISOLength
) {
3699 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "error as Source ISO Section does not have valid signature");
3700 Status
= STATUS_FAILURE
;
3704 uiTotalDataToCopy
= (Adapter
->psFlash2xCSInfo
->OffsetISOImage1Part1End
) -
3705 (Adapter
->psFlash2xCSInfo
->OffsetISOImage1Part1Start
) +
3706 (Adapter
->psFlash2xCSInfo
->OffsetISOImage1Part2End
) -
3707 (Adapter
->psFlash2xCSInfo
->OffsetISOImage1Part2Start
) +
3708 (Adapter
->psFlash2xCSInfo
->OffsetISOImage1Part3End
) -
3709 (Adapter
->psFlash2xCSInfo
->OffsetISOImage1Part3Start
);
3711 if (uiTotalDataToCopy
< ISOLength
) {
3712 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "error as Dest ISO Section does not have enough section size");
3713 Status
= STATUS_FAILURE
;
3717 uiTotalDataToCopy
= ISOLength
;
3719 CorruptISOSig(Adapter
, ISO_IMAGE1
);
3721 while (uiTotalDataToCopy
) {
3722 if (uiTotalDataToCopy
== Adapter
->uiSectorSize
) {
3723 /* Setting for write of first sector. First sector is assumed to be written in last */
3724 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "Writing the signature sector");
3725 eISOReadPart
= ISO_IMAGE2
;
3726 uiReadOffsetWithinPart
= 0;
3727 eISOWritePart
= ISO_IMAGE1
;
3728 uiWriteOffsetWithinPart
= 0;
3729 IsThisHeaderSector
= TRUE
;
3731 uiReadOffsetWithinPart
= uiReadOffsetWithinPart
+ Adapter
->uiSectorSize
;
3732 uiWriteOffsetWithinPart
= uiWriteOffsetWithinPart
+ Adapter
->uiSectorSize
;
3734 if ((eISOReadPart
== ISO_IMAGE2
) && (uiReadOffsetWithinPart
== (Adapter
->psFlash2xCSInfo
->OffsetISOImage2Part1End
- Adapter
->psFlash2xCSInfo
->OffsetISOImage2Part1Start
))) {
3735 eISOReadPart
= ISO_IMAGE2_PART2
;
3736 uiReadOffsetWithinPart
= 0;
3739 if ((eISOReadPart
== ISO_IMAGE2_PART2
) && (uiReadOffsetWithinPart
== (Adapter
->psFlash2xCSInfo
->OffsetISOImage2Part2End
- Adapter
->psFlash2xCSInfo
->OffsetISOImage2Part2Start
))) {
3740 eISOReadPart
= ISO_IMAGE2_PART3
;
3741 uiReadOffsetWithinPart
= 0;
3744 if ((eISOWritePart
== ISO_IMAGE1
) && (uiWriteOffsetWithinPart
== (Adapter
->psFlash2xCSInfo
->OffsetISOImage1Part1End
- Adapter
->psFlash2xCSInfo
->OffsetISOImage1Part1Start
))) {
3745 eISOWritePart
= ISO_IMAGE1_PART2
;
3746 uiWriteOffsetWithinPart
= 0;
3749 if ((eISOWritePart
== ISO_IMAGE1_PART2
) && (uiWriteOffsetWithinPart
== (Adapter
->psFlash2xCSInfo
->OffsetISOImage1Part2End
- Adapter
->psFlash2xCSInfo
->OffsetISOImage1Part2Start
))) {
3750 eISOWritePart
= ISO_IMAGE1_PART3
;
3751 uiWriteOffsetWithinPart
= 0;
3755 Status
= BcmFlash2xBulkRead(Adapter
,
3758 uiReadOffsetWithinPart
,
3759 Adapter
->uiSectorSize
);
3761 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Read failed while copying ISO: Part: %x, OffsetWithinPart: %x\n", eISOReadPart
, uiReadOffsetWithinPart
);
3765 if (IsThisHeaderSector
== TRUE
) {
3766 /* If this is header sector write 0xFFFFFFFF at the sig time and in last write sig */
3767 memcpy(SigBuff
, Buff
+ sigOffset
, MAX_RW_SIZE
);
3769 for (i
= 0; i
< MAX_RW_SIZE
; i
++)
3770 *(Buff
+ sigOffset
+ i
) = 0xFF;
3772 Adapter
->bHeaderChangeAllowed
= TRUE
;
3773 Status
= BcmFlash2xBulkWrite(Adapter
,
3776 uiWriteOffsetWithinPart
,
3777 Adapter
->uiSectorSize
,
3780 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Write failed while copying ISO: Part: %x, OffsetWithinPart: %x\n", eISOWritePart
, uiWriteOffsetWithinPart
);
3784 Adapter
->bHeaderChangeAllowed
= FALSE
;
3785 if (IsThisHeaderSector
== TRUE
) {
3786 WriteToFlashWithoutSectorErase(Adapter
,
3792 IsThisHeaderSector
= FALSE
;
3795 /* subtracting the written Data */
3796 uiTotalDataToCopy
= uiTotalDataToCopy
- Adapter
->uiSectorSize
;
3806 * BcmFlash2xCorruptSig : this API is used to corrupt the written sig in Bcm Header present in flash section.
3807 * It will corrupt the sig, if Section is writable, by making first bytes as zero.
3808 * @Adapater :- Bcm Driver Private Data Structure
3809 * @eFlash2xSectionVal :- Flash section val which has header
3812 * Success :- If Section is present and writable, corrupt the sig and return STATUS_SUCCESS
3813 * Failure :-Return negative error code
3816 int BcmFlash2xCorruptSig(struct bcm_mini_adapter
*Adapter
, FLASH2X_SECTION_VAL eFlash2xSectionVal
)
3818 int Status
= STATUS_SUCCESS
;
3820 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Section Value :%x\n", eFlash2xSectionVal
);
3822 if ((eFlash2xSectionVal
== DSD0
) || (eFlash2xSectionVal
== DSD1
) || (eFlash2xSectionVal
== DSD2
)) {
3823 Status
= CorruptDSDSig(Adapter
, eFlash2xSectionVal
);
3824 } else if (eFlash2xSectionVal
== ISO_IMAGE1
|| eFlash2xSectionVal
== ISO_IMAGE2
) {
3825 Status
= CorruptISOSig(Adapter
, eFlash2xSectionVal
);
3827 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "Given Section <%d>does not have Header", eFlash2xSectionVal
);
3828 return STATUS_SUCCESS
;
3834 *BcmFlash2xWriteSig :-this API is used to Write the sig if requested Section has
3835 * header and Write Permission.
3836 * @Adapater :- Bcm Driver Private Data Structure
3837 * @eFlashSectionVal :- Flash section val which has header
3840 * Success :- If Section is present and writable write the sig and return STATUS_SUCCESS
3841 * Failure :-Return negative error code
3844 int BcmFlash2xWriteSig(struct bcm_mini_adapter
*Adapter
, FLASH2X_SECTION_VAL eFlashSectionVal
)
3846 unsigned int uiSignature
= 0;
3847 unsigned int uiOffset
= 0;
3849 /* DSD_HEADER dsdHeader = {0}; */
3850 if (Adapter
->bSigCorrupted
== FALSE
) {
3851 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "Signature is not corrupted by driver, hence not restoring\n");
3852 return STATUS_SUCCESS
;
3855 if (Adapter
->bAllDSDWriteAllow
== FALSE
) {
3856 if (IsSectionWritable(Adapter
, eFlashSectionVal
) == FALSE
) {
3857 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Section is not Writable...Hence can't Write signature");
3858 return SECTOR_IS_NOT_WRITABLE
;
3862 if ((eFlashSectionVal
== DSD0
) || (eFlashSectionVal
== DSD1
) || (eFlashSectionVal
== DSD2
)) {
3863 uiSignature
= htonl(DSD_IMAGE_MAGIC_NUMBER
);
3864 uiOffset
= Adapter
->psFlash2xCSInfo
->OffsetFromDSDStartForDSDHeader
;
3866 uiOffset
+= FIELD_OFFSET_IN_HEADER(PDSD_HEADER
, DSDImageMagicNumber
);
3868 if ((ReadDSDSignature(Adapter
, eFlashSectionVal
) & 0xFF000000) != CORRUPTED_PATTERN
) {
3869 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Corrupted Pattern is not there. Hence won't write sig");
3870 return STATUS_FAILURE
;
3872 } else if ((eFlashSectionVal
== ISO_IMAGE1
) || (eFlashSectionVal
== ISO_IMAGE2
)) {
3873 uiSignature
= htonl(ISO_IMAGE_MAGIC_NUMBER
);
3875 uiOffset
= FIELD_OFFSET_IN_HEADER(PISO_HEADER
, ISOImageMagicNumber
);
3876 if ((ReadISOSignature(Adapter
, eFlashSectionVal
) & 0xFF000000) != CORRUPTED_PATTERN
) {
3877 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Currupted Pattern is not there. Hence won't write sig");
3878 return STATUS_FAILURE
;
3881 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "GIVEN SECTION< %d > IS NOT VALID FOR SIG WRITE...", eFlashSectionVal
);
3882 return STATUS_FAILURE
;
3885 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "Restoring the signature");
3887 Adapter
->bHeaderChangeAllowed
= TRUE
;
3888 Adapter
->bSigCorrupted
= FALSE
;
3889 BcmFlash2xBulkWrite(Adapter
, &uiSignature
, eFlashSectionVal
, uiOffset
, SIGNATURE_SIZE
, TRUE
);
3890 Adapter
->bHeaderChangeAllowed
= FALSE
;
3892 return STATUS_SUCCESS
;
3896 * validateFlash2xReadWrite :- This API is used to validate the user request for Read/Write.
3897 * if requested Bytes goes beyond the Requested section, it reports error.
3898 * @Adapater :- Bcm Driver Private Data Structure
3899 * @psFlash2xReadWrite :-Flash2x Read/write structure pointer
3901 * Return values:-Return TRUE is request is valid else FALSE.
3904 int validateFlash2xReadWrite(struct bcm_mini_adapter
*Adapter
, PFLASH2X_READWRITE psFlash2xReadWrite
)
3906 unsigned int uiNumOfBytes
= 0;
3907 unsigned int uiSectStartOffset
= 0;
3908 unsigned int uiSectEndOffset
= 0;
3910 uiNumOfBytes
= psFlash2xReadWrite
->numOfBytes
;
3912 if (IsSectionExistInFlash(Adapter
, psFlash2xReadWrite
->Section
) != TRUE
) {
3913 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Section<%x> does not exixt in Flash", psFlash2xReadWrite
->Section
);
3916 uiSectStartOffset
= BcmGetSectionValStartOffset(Adapter
, psFlash2xReadWrite
->Section
);
3917 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "Start offset :%x ,section :%d\n", uiSectStartOffset
, psFlash2xReadWrite
->Section
);
3918 if ((psFlash2xReadWrite
->Section
== ISO_IMAGE1
) || (psFlash2xReadWrite
->Section
== ISO_IMAGE2
)) {
3919 if (psFlash2xReadWrite
->Section
== ISO_IMAGE1
) {
3920 uiSectEndOffset
= BcmGetSectionValEndOffset(Adapter
, ISO_IMAGE1
) -
3921 BcmGetSectionValStartOffset(Adapter
, ISO_IMAGE1
) +
3922 BcmGetSectionValEndOffset(Adapter
, ISO_IMAGE1_PART2
) -
3923 BcmGetSectionValStartOffset(Adapter
, ISO_IMAGE1_PART2
) +
3924 BcmGetSectionValEndOffset(Adapter
, ISO_IMAGE1_PART3
) -
3925 BcmGetSectionValStartOffset(Adapter
, ISO_IMAGE1_PART3
);
3926 } else if (psFlash2xReadWrite
->Section
== ISO_IMAGE2
) {
3927 uiSectEndOffset
= BcmGetSectionValEndOffset(Adapter
, ISO_IMAGE2
) -
3928 BcmGetSectionValStartOffset(Adapter
, ISO_IMAGE2
) +
3929 BcmGetSectionValEndOffset(Adapter
, ISO_IMAGE2_PART2
) -
3930 BcmGetSectionValStartOffset(Adapter
, ISO_IMAGE2_PART2
) +
3931 BcmGetSectionValEndOffset(Adapter
, ISO_IMAGE2_PART3
) -
3932 BcmGetSectionValStartOffset(Adapter
, ISO_IMAGE2_PART3
);
3935 /* since this uiSectEndoffset is the size of iso Image. hence for calculating the virtual endoffset
3936 * it should be added in startoffset. so that check done in last of this function can be valued.
3938 uiSectEndOffset
= uiSectStartOffset
+ uiSectEndOffset
;
3940 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "Total size of the ISO Image :%x", uiSectEndOffset
);
3942 uiSectEndOffset
= BcmGetSectionValEndOffset(Adapter
, psFlash2xReadWrite
->Section
);
3944 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "End offset :%x\n", uiSectEndOffset
);
3946 /* Checking the boundary condition */
3947 if ((uiSectStartOffset
+ psFlash2xReadWrite
->offset
+ uiNumOfBytes
) <= uiSectEndOffset
)
3950 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Invalid Request....");
3956 * IsFlash2x :- check for Flash 2.x
3957 * Adapater :- Bcm Driver Private Data Structure
3960 * return TRUE if flah2.x of hgher version else return false.
3963 int IsFlash2x(struct bcm_mini_adapter
*Adapter
)
3965 if (Adapter
->uiFlashLayoutMajorVersion
>= FLASH_2X_MAJOR_NUMBER
)
3972 * GetFlashBaseAddr :- Calculate the Flash Base address
3973 * @Adapater :- Bcm Driver Private Data Structure
3976 * Success :- Base Address of the Flash
3979 static int GetFlashBaseAddr(struct bcm_mini_adapter
*Adapter
)
3981 unsigned int uiBaseAddr
= 0;
3983 if (Adapter
->bDDRInitDone
) {
3985 * For All Valid Flash Versions... except 1.1, take the value from FlashBaseAddr
3986 * In case of Raw Read... use the default value
3988 if (Adapter
->uiFlashLayoutMajorVersion
&& (Adapter
->bFlashRawRead
== FALSE
) &&
3989 !((Adapter
->uiFlashLayoutMajorVersion
== 1) && (Adapter
->uiFlashLayoutMinorVersion
== 1)))
3990 uiBaseAddr
= Adapter
->uiFlashBaseAdd
;
3992 uiBaseAddr
= FLASH_CONTIGIOUS_START_ADDR_AFTER_INIT
;
3995 * For All Valid Flash Versions... except 1.1, take the value from FlashBaseAddr
3996 * In case of Raw Read... use the default value
3998 if (Adapter
->uiFlashLayoutMajorVersion
&& (Adapter
->bFlashRawRead
== FALSE
) &&
3999 !((Adapter
->uiFlashLayoutMajorVersion
== 1) && (Adapter
->uiFlashLayoutMinorVersion
== 1)))
4000 uiBaseAddr
= Adapter
->uiFlashBaseAdd
| FLASH_CONTIGIOUS_START_ADDR_BEFORE_INIT
;
4002 uiBaseAddr
= FLASH_CONTIGIOUS_START_ADDR_BEFORE_INIT
;
4009 * BcmCopySection :- This API is used to copy the One section in another. Both section should
4010 * be contiuous and of same size. Hence this Will not be applicabe to copy ISO.
4012 * @Adapater :- Bcm Driver Private Data Structure
4013 * @SrcSection :- Source section From where data has to be copied
4014 * @DstSection :- Destination section to which data has to be copied
4015 * @offset :- Offset from/to where data has to be copied from one section to another.
4016 * @numOfBytes :- number of byes that has to be copyed from one section to another at given offset.
4017 * in case of numofBytes equal zero complete section will be copied.
4019 * Success : Return STATUS_SUCCESS
4020 * Faillure :- return negative error code
4023 int BcmCopySection(struct bcm_mini_adapter
*Adapter
,
4024 FLASH2X_SECTION_VAL SrcSection
,
4025 FLASH2X_SECTION_VAL DstSection
,
4026 unsigned int offset
,
4027 unsigned int numOfBytes
)
4029 unsigned int BuffSize
= 0;
4030 unsigned int BytesToBeCopied
= 0;
4031 PUCHAR pBuff
= NULL
;
4032 int Status
= STATUS_SUCCESS
;
4034 if (SrcSection
== DstSection
) {
4035 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Source and Destination should be different ...try again");
4039 if ((SrcSection
!= DSD0
) && (SrcSection
!= DSD1
) && (SrcSection
!= DSD2
)) {
4040 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Source should be DSD subsection");
4044 if ((DstSection
!= DSD0
) && (DstSection
!= DSD1
) && (DstSection
!= DSD2
)) {
4045 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Destination should be DSD subsection");
4049 /* if offset zero means have to copy complete secton */
4050 if (numOfBytes
== 0) {
4051 numOfBytes
= BcmGetSectionValEndOffset(Adapter
, SrcSection
)
4052 - BcmGetSectionValStartOffset(Adapter
, SrcSection
);
4054 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "Section Size :0x%x", numOfBytes
);
4057 if ((offset
+ numOfBytes
) > BcmGetSectionValEndOffset(Adapter
, SrcSection
)
4058 - BcmGetSectionValStartOffset(Adapter
, SrcSection
)) {
4059 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, " Input parameters going beyond the section offS: %x numB: %x of Source Section\n",
4060 offset
, numOfBytes
);
4064 if ((offset
+ numOfBytes
) > BcmGetSectionValEndOffset(Adapter
, DstSection
)
4065 - BcmGetSectionValStartOffset(Adapter
, DstSection
)) {
4066 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Input parameters going beyond the section offS: %x numB: %x of Destination Section\n",
4067 offset
, numOfBytes
);
4071 if (numOfBytes
> Adapter
->uiSectorSize
)
4072 BuffSize
= Adapter
->uiSectorSize
;
4074 BuffSize
= numOfBytes
;
4076 pBuff
= (PCHAR
)kzalloc(BuffSize
, GFP_KERNEL
);
4078 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Memory allocation failed.. ");
4082 BytesToBeCopied
= Adapter
->uiSectorSize
;
4083 if (offset
% Adapter
->uiSectorSize
)
4084 BytesToBeCopied
= Adapter
->uiSectorSize
- (offset
% Adapter
->uiSectorSize
);
4085 if (BytesToBeCopied
> numOfBytes
)
4086 BytesToBeCopied
= numOfBytes
;
4088 Adapter
->bHeaderChangeAllowed
= TRUE
;
4091 Status
= BcmFlash2xBulkRead(Adapter
, (PUINT
)pBuff
, SrcSection
, offset
, BytesToBeCopied
);
4093 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Read failed at offset :%d for NOB :%d", SrcSection
, BytesToBeCopied
);
4096 Status
= BcmFlash2xBulkWrite(Adapter
, (PUINT
)pBuff
, DstSection
, offset
, BytesToBeCopied
, FALSE
);
4098 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Write failed at offset :%d for NOB :%d", DstSection
, BytesToBeCopied
);
4101 offset
= offset
+ BytesToBeCopied
;
4102 numOfBytes
= numOfBytes
- BytesToBeCopied
;
4104 if (numOfBytes
> Adapter
->uiSectorSize
)
4105 BytesToBeCopied
= Adapter
->uiSectorSize
;
4107 BytesToBeCopied
= numOfBytes
;
4109 } while (numOfBytes
> 0);
4112 Adapter
->bHeaderChangeAllowed
= FALSE
;
4118 * SaveHeaderIfPresent :- This API is use to Protect the Header in case of Header Sector write
4119 * @Adapater :- Bcm Driver Private Data Structure
4120 * @pBuff :- Data buffer that has to be written in sector having the header map.
4121 * @uiOffset :- Flash offset that has to be written.
4124 * Success :- On success return STATUS_SUCCESS
4125 * Faillure :- Return negative error code
4128 int SaveHeaderIfPresent(struct bcm_mini_adapter
*Adapter
, PUCHAR pBuff
, unsigned int uiOffset
)
4130 unsigned int offsetToProtect
= 0, HeaderSizeToProtect
= 0;
4131 BOOLEAN bHasHeader
= FALSE
;
4132 PUCHAR pTempBuff
= NULL
;
4133 unsigned int uiSectAlignAddr
= 0;
4134 unsigned int sig
= 0;
4136 /* making the offset sector aligned */
4137 uiSectAlignAddr
= uiOffset
& ~(Adapter
->uiSectorSize
- 1);
4139 if ((uiSectAlignAddr
== BcmGetSectionValEndOffset(Adapter
, DSD2
) - Adapter
->uiSectorSize
) ||
4140 (uiSectAlignAddr
== BcmGetSectionValEndOffset(Adapter
, DSD1
) - Adapter
->uiSectorSize
) ||
4141 (uiSectAlignAddr
== BcmGetSectionValEndOffset(Adapter
, DSD0
) - Adapter
->uiSectorSize
)) {
4142 /* offset from the sector boundary having the header map */
4143 offsetToProtect
= Adapter
->psFlash2xCSInfo
->OffsetFromDSDStartForDSDHeader
% Adapter
->uiSectorSize
;
4144 HeaderSizeToProtect
= sizeof(DSD_HEADER
);
4148 if (uiSectAlignAddr
== BcmGetSectionValStartOffset(Adapter
, ISO_IMAGE1
) ||
4149 uiSectAlignAddr
== BcmGetSectionValStartOffset(Adapter
, ISO_IMAGE2
)) {
4150 offsetToProtect
= 0;
4151 HeaderSizeToProtect
= sizeof(ISO_HEADER
);
4154 /* If Header is present overwrite passed buffer with this */
4155 if (bHasHeader
&& (Adapter
->bHeaderChangeAllowed
== FALSE
)) {
4156 pTempBuff
= (PUCHAR
)kzalloc(HeaderSizeToProtect
, GFP_KERNEL
);
4158 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Memory allocation failed");
4162 BeceemFlashBulkRead(Adapter
, (PUINT
)pTempBuff
, (uiSectAlignAddr
+ offsetToProtect
), HeaderSizeToProtect
);
4163 BCM_DEBUG_PRINT_BUFFER(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, pTempBuff
, HeaderSizeToProtect
);
4164 /* Replace Buffer content with Header */
4165 memcpy(pBuff
+ offsetToProtect
, pTempBuff
, HeaderSizeToProtect
);
4169 if (bHasHeader
&& Adapter
->bSigCorrupted
) {
4170 sig
= *((PUINT
)(pBuff
+ offsetToProtect
+ FIELD_OFFSET_IN_HEADER(PDSD_HEADER
, DSDImageMagicNumber
)));
4172 if ((sig
& 0xFF000000) != CORRUPTED_PATTERN
) {
4173 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "Desired pattern is not at sig offset. Hence won't restore");
4174 Adapter
->bSigCorrupted
= FALSE
;
4175 return STATUS_SUCCESS
;
4177 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, " Corrupted sig is :%X", sig
);
4178 *((PUINT
)(pBuff
+ offsetToProtect
+ FIELD_OFFSET_IN_HEADER(PDSD_HEADER
, DSDImageMagicNumber
))) = htonl(DSD_IMAGE_MAGIC_NUMBER
);
4179 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "Restoring the signature in Header Write only");
4180 Adapter
->bSigCorrupted
= FALSE
;
4183 return STATUS_SUCCESS
;
4187 * BcmDoChipSelect : This will selcet the appropriate chip for writing.
4188 * @Adapater :- Bcm Driver Private Data Structure
4191 * Select the Appropriate chip and retrn status Success
4193 static int BcmDoChipSelect(struct bcm_mini_adapter
*Adapter
, unsigned int offset
)
4195 unsigned int FlashConfig
= 0;
4197 unsigned int GPIOConfig
= 0;
4198 unsigned int PartNum
= 0;
4200 ChipNum
= offset
/ FLASH_PART_SIZE
;
4203 * Chip Select mapping to enable flash0.
4204 * To select flash 0, we have to OR with (0<<12).
4205 * ORing 0 will have no impact so not doing that part.
4206 * In future if Chip select value changes from 0 to non zero,
4207 * That needs be taken care with backward comaptibility. No worries for now.
4211 * SelectedChip Variable is the selection that the host is 100% Sure the same as what the register will hold. This can be ONLY ensured
4212 * if the Chip doesn't goes to low power mode while the flash operation is in progress (NVMRdmWrmLock is taken)
4213 * Before every new Flash Write operation, we reset the variable. This is to ensure that after any wake-up from
4214 * power down modes (Idle mode/shutdown mode), the values in the register will be different.
4217 if (Adapter
->SelectedChip
== ChipNum
)
4218 return STATUS_SUCCESS
;
4220 /* BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "Selected Chip :%x", ChipNum); */
4221 Adapter
->SelectedChip
= ChipNum
;
4223 /* bit[13..12] will select the appropriate chip */
4224 rdmalt(Adapter
, FLASH_CONFIG_REG
, &FlashConfig
, 4);
4225 rdmalt(Adapter
, FLASH_GPIO_CONFIG_REG
, &GPIOConfig
, 4);
4233 GPIOConfig
|= (0x4 << CHIP_SELECT_BIT12
);
4237 GPIOConfig
|= (0x1 << CHIP_SELECT_BIT12
);
4241 GPIOConfig
|= (0x2 << CHIP_SELECT_BIT12
);
4245 /* In case the bits already written in the FLASH_CONFIG_REG is same as what the user desired,
4246 * nothing to do... can return immediately.
4247 * ASSUMPTION: FLASH_GPIO_CONFIG_REG will be in sync with FLASH_CONFIG_REG.
4248 * Even if the chip goes to low power mode, it should wake with values in each register in sync with each other.
4249 * These values are not written by host other than during CHIP_SELECT.
4251 if (PartNum
== ((FlashConfig
>> CHIP_SELECT_BIT12
) & 0x3))
4252 return STATUS_SUCCESS
;
4254 /* clearing the bit[13..12] */
4255 FlashConfig
&= 0xFFFFCFFF;
4256 FlashConfig
= (FlashConfig
| (PartNum
<<CHIP_SELECT_BIT12
)); /* 00 */
4258 wrmalt(Adapter
, FLASH_GPIO_CONFIG_REG
, &GPIOConfig
, 4);
4261 wrmalt(Adapter
, FLASH_CONFIG_REG
, &FlashConfig
, 4);
4264 return STATUS_SUCCESS
;
4267 int ReadDSDSignature(struct bcm_mini_adapter
*Adapter
, FLASH2X_SECTION_VAL dsd
)
4269 unsigned int uiDSDsig
= 0;
4270 /* unsigned int sigoffsetInMap = 0;
4271 * DSD_HEADER dsdHeader = {0};
4274 /* sigoffsetInMap =(PUCHAR)&(dsdHeader.DSDImageMagicNumber) -(PUCHAR)&dsdHeader; */
4276 if (dsd
!= DSD0
&& dsd
!= DSD1
&& dsd
!= DSD2
) {
4277 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "passed section value is not for DSDs");
4278 return STATUS_FAILURE
;
4280 BcmFlash2xBulkRead(Adapter
,
4283 Adapter
->psFlash2xCSInfo
->OffsetFromDSDStartForDSDHeader
+ FIELD_OFFSET_IN_HEADER(PDSD_HEADER
, DSDImageMagicNumber
),
4286 uiDSDsig
= ntohl(uiDSDsig
);
4287 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "DSD SIG :%x", uiDSDsig
);
4292 int ReadDSDPriority(struct bcm_mini_adapter
*Adapter
, FLASH2X_SECTION_VAL dsd
)
4294 /* unsigned int priOffsetInMap = 0 ; */
4295 unsigned int uiDSDPri
= STATUS_FAILURE
;
4296 /* DSD_HEADER dsdHeader = {0};
4297 * priOffsetInMap = (PUCHAR)&(dsdHeader.DSDImagePriority) -(PUCHAR)&dsdHeader;
4299 if (IsSectionWritable(Adapter
, dsd
)) {
4300 if (ReadDSDSignature(Adapter
, dsd
) == DSD_IMAGE_MAGIC_NUMBER
) {
4301 BcmFlash2xBulkRead(Adapter
,
4304 Adapter
->psFlash2xCSInfo
->OffsetFromDSDStartForDSDHeader
+ FIELD_OFFSET_IN_HEADER(PDSD_HEADER
, DSDImagePriority
),
4307 uiDSDPri
= ntohl(uiDSDPri
);
4308 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "DSD<%x> Priority :%x", dsd
, uiDSDPri
);
4315 FLASH2X_SECTION_VAL
getHighestPriDSD(struct bcm_mini_adapter
*Adapter
)
4317 int DSDHighestPri
= STATUS_FAILURE
;
4319 FLASH2X_SECTION_VAL HighestPriDSD
= 0;
4321 if (IsSectionWritable(Adapter
, DSD2
)) {
4322 DSDHighestPri
= ReadDSDPriority(Adapter
, DSD2
);
4323 HighestPriDSD
= DSD2
;
4326 if (IsSectionWritable(Adapter
, DSD1
)) {
4327 DsdPri
= ReadDSDPriority(Adapter
, DSD1
);
4328 if (DSDHighestPri
< DsdPri
) {
4329 DSDHighestPri
= DsdPri
;
4330 HighestPriDSD
= DSD1
;
4334 if (IsSectionWritable(Adapter
, DSD0
)) {
4335 DsdPri
= ReadDSDPriority(Adapter
, DSD0
);
4336 if (DSDHighestPri
< DsdPri
) {
4337 DSDHighestPri
= DsdPri
;
4338 HighestPriDSD
= DSD0
;
4342 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "Highest DSD :%x , and its Pri :%x", HighestPriDSD
, DSDHighestPri
);
4344 return HighestPriDSD
;
4347 int ReadISOSignature(struct bcm_mini_adapter
*Adapter
, FLASH2X_SECTION_VAL iso
)
4349 unsigned int uiISOsig
= 0;
4350 /* unsigned int sigoffsetInMap = 0;
4351 * ISO_HEADER ISOHeader = {0};
4352 * sigoffsetInMap =(PUCHAR)&(ISOHeader.ISOImageMagicNumber) -(PUCHAR)&ISOHeader;
4354 if (iso
!= ISO_IMAGE1
&& iso
!= ISO_IMAGE2
) {
4355 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "passed section value is not for ISOs");
4356 return STATUS_FAILURE
;
4358 BcmFlash2xBulkRead(Adapter
,
4361 0 + FIELD_OFFSET_IN_HEADER(PISO_HEADER
, ISOImageMagicNumber
),
4364 uiISOsig
= ntohl(uiISOsig
);
4365 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "ISO SIG :%x", uiISOsig
);
4370 int ReadISOPriority(struct bcm_mini_adapter
*Adapter
, FLASH2X_SECTION_VAL iso
)
4372 unsigned int ISOPri
= STATUS_FAILURE
;
4373 if (IsSectionWritable(Adapter
, iso
)) {
4374 if (ReadISOSignature(Adapter
, iso
) == ISO_IMAGE_MAGIC_NUMBER
) {
4375 BcmFlash2xBulkRead(Adapter
,
4378 0 + FIELD_OFFSET_IN_HEADER(PISO_HEADER
, ISOImagePriority
),
4381 ISOPri
= ntohl(ISOPri
);
4382 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "ISO<%x> Priority :%x", iso
, ISOPri
);
4389 FLASH2X_SECTION_VAL
getHighestPriISO(struct bcm_mini_adapter
*Adapter
)
4391 int ISOHighestPri
= STATUS_FAILURE
;
4393 FLASH2X_SECTION_VAL HighestPriISO
= NO_SECTION_VAL
;
4395 if (IsSectionWritable(Adapter
, ISO_IMAGE2
)) {
4396 ISOHighestPri
= ReadISOPriority(Adapter
, ISO_IMAGE2
);
4397 HighestPriISO
= ISO_IMAGE2
;
4400 if (IsSectionWritable(Adapter
, ISO_IMAGE1
)) {
4401 ISOPri
= ReadISOPriority(Adapter
, ISO_IMAGE1
);
4402 if (ISOHighestPri
< ISOPri
) {
4403 ISOHighestPri
= ISOPri
;
4404 HighestPriISO
= ISO_IMAGE1
;
4408 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "Highest ISO :%x and its Pri :%x", HighestPriISO
, ISOHighestPri
);
4410 return HighestPriISO
;
4413 int WriteToFlashWithoutSectorErase(struct bcm_mini_adapter
*Adapter
,
4415 FLASH2X_SECTION_VAL eFlash2xSectionVal
,
4416 unsigned int uiOffset
,
4417 unsigned int uiNumBytes
)
4419 #if !defined(BCM_SHM_INTERFACE) || defined(FLASH_DIRECT_ACCESS)
4420 unsigned int uiTemp
= 0, value
= 0;
4422 unsigned int uiPartOffset
= 0;
4424 unsigned int uiStartOffset
= 0;
4425 /* Adding section start address */
4426 int Status
= STATUS_SUCCESS
;
4427 PUCHAR pcBuff
= (PUCHAR
)pBuff
;
4429 if (uiNumBytes
% Adapter
->ulFlashWriteSize
) {
4430 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Writing without Sector Erase for non-FlashWriteSize number of bytes 0x%x\n", uiNumBytes
);
4431 return STATUS_FAILURE
;
4434 uiStartOffset
= BcmGetSectionValStartOffset(Adapter
, eFlash2xSectionVal
);
4436 if (IsSectionExistInVendorInfo(Adapter
, eFlash2xSectionVal
))
4437 return vendorextnWriteSectionWithoutErase(Adapter
, pcBuff
, eFlash2xSectionVal
, uiOffset
, uiNumBytes
);
4439 uiOffset
= uiOffset
+ uiStartOffset
;
4441 #if defined(BCM_SHM_INTERFACE) && !defined(FLASH_DIRECT_ACCESS)
4442 Status
= bcmflash_raw_writenoerase((uiOffset
/ FLASH_PART_SIZE
), (uiOffset
% FLASH_PART_SIZE
), pcBuff
, uiNumBytes
);
4444 rdmalt(Adapter
, 0x0f000C80, &uiTemp
, sizeof(uiTemp
));
4446 wrmalt(Adapter
, 0x0f000C80, &value
, sizeof(value
));
4448 Adapter
->SelectedChip
= RESET_CHIP_SELECT
;
4449 BcmDoChipSelect(Adapter
, uiOffset
);
4450 uiPartOffset
= (uiOffset
& (FLASH_PART_SIZE
- 1)) + GetFlashBaseAddr(Adapter
);
4452 for (i
= 0 ; i
< uiNumBytes
; i
+= Adapter
->ulFlashWriteSize
) {
4453 if (Adapter
->ulFlashWriteSize
== BYTE_WRITE_SUPPORT
)
4454 Status
= flashByteWrite(Adapter
, uiPartOffset
, pcBuff
);
4456 Status
= flashWrite(Adapter
, uiPartOffset
, pcBuff
);
4458 if (Status
!= STATUS_SUCCESS
)
4461 pcBuff
= pcBuff
+ Adapter
->ulFlashWriteSize
;
4462 uiPartOffset
= uiPartOffset
+ Adapter
->ulFlashWriteSize
;
4464 wrmalt(Adapter
, 0x0f000C80, &uiTemp
, sizeof(uiTemp
));
4465 Adapter
->SelectedChip
= RESET_CHIP_SELECT
;
4471 BOOLEAN
IsSectionExistInFlash(struct bcm_mini_adapter
*Adapter
, FLASH2X_SECTION_VAL section
)
4473 BOOLEAN SectionPresent
= FALSE
;
4477 if ((Adapter
->psFlash2xCSInfo
->OffsetISOImage1Part1Start
!= UNINIT_PTR_IN_CS
) &&
4478 (IsNonCDLessDevice(Adapter
) == FALSE
))
4479 SectionPresent
= TRUE
;
4482 if ((Adapter
->psFlash2xCSInfo
->OffsetISOImage2Part1Start
!= UNINIT_PTR_IN_CS
) &&
4483 (IsNonCDLessDevice(Adapter
) == FALSE
))
4484 SectionPresent
= TRUE
;
4487 if (Adapter
->psFlash2xCSInfo
->OffsetFromZeroForDSDStart
!= UNINIT_PTR_IN_CS
)
4488 SectionPresent
= TRUE
;
4491 if (Adapter
->psFlash2xCSInfo
->OffsetFromZeroForDSD1Start
!= UNINIT_PTR_IN_CS
)
4492 SectionPresent
= TRUE
;
4495 if (Adapter
->psFlash2xCSInfo
->OffsetFromZeroForDSD2Start
!= UNINIT_PTR_IN_CS
)
4496 SectionPresent
= TRUE
;
4499 if (Adapter
->psFlash2xCSInfo
->OffsetFromZeroForVSAStart
!= UNINIT_PTR_IN_CS
)
4500 SectionPresent
= TRUE
;
4503 if (Adapter
->psFlash2xCSInfo
->OffsetFromZeroForVSA1Start
!= UNINIT_PTR_IN_CS
)
4504 SectionPresent
= TRUE
;
4507 if (Adapter
->psFlash2xCSInfo
->OffsetFromZeroForVSA2Start
!= UNINIT_PTR_IN_CS
)
4508 SectionPresent
= TRUE
;
4511 if (Adapter
->psFlash2xCSInfo
->OffsetFromZeroForScsiFirmware
!= UNINIT_PTR_IN_CS
)
4512 SectionPresent
= TRUE
;
4514 case CONTROL_SECTION
:
4515 if (Adapter
->psFlash2xCSInfo
->OffsetFromZeroForControlSectionStart
!= UNINIT_PTR_IN_CS
)
4516 SectionPresent
= TRUE
;
4519 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Section Does not exist in Flash 2.x");
4520 SectionPresent
= FALSE
;
4523 return SectionPresent
;
4526 int IsSectionWritable(struct bcm_mini_adapter
*Adapter
, FLASH2X_SECTION_VAL Section
)
4528 int offset
= STATUS_FAILURE
;
4531 if (IsSectionExistInFlash(Adapter
, Section
) == FALSE
) {
4532 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Section <%d> does not exixt", Section
);
4536 offset
= BcmGetSectionValStartOffset(Adapter
, Section
);
4537 if (offset
== INVALID_OFFSET
) {
4538 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Section<%d> does not exixt", Section
);
4542 if (IsSectionExistInVendorInfo(Adapter
, Section
))
4543 return !(Adapter
->psFlash2xVendorInfo
->VendorSection
[Section
].AccessFlags
& FLASH2X_SECTION_RO
);
4545 Status
= IsOffsetWritable(Adapter
, offset
);
4549 static int CorruptDSDSig(struct bcm_mini_adapter
*Adapter
, FLASH2X_SECTION_VAL eFlash2xSectionVal
)
4551 PUCHAR pBuff
= NULL
;
4552 unsigned int sig
= 0;
4553 unsigned int uiOffset
= 0;
4554 unsigned int BlockStatus
= 0;
4555 unsigned int uiSectAlignAddr
= 0;
4557 Adapter
->bSigCorrupted
= FALSE
;
4558 if (Adapter
->bAllDSDWriteAllow
== FALSE
) {
4559 if (IsSectionWritable(Adapter
, eFlash2xSectionVal
) != TRUE
) {
4560 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Section is not Writable...Hence can't Corrupt signature");
4561 return SECTOR_IS_NOT_WRITABLE
;
4565 pBuff
= (PUCHAR
)kzalloc(MAX_RW_SIZE
, GFP_KERNEL
);
4567 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Can't allocate memorey");
4571 uiOffset
= Adapter
->psFlash2xCSInfo
->OffsetFromDSDStartForDSDHeader
+ sizeof(DSD_HEADER
);
4572 uiOffset
-= MAX_RW_SIZE
;
4574 BcmFlash2xBulkRead(Adapter
, (PUINT
)pBuff
, eFlash2xSectionVal
, uiOffset
, MAX_RW_SIZE
);
4576 sig
= *((PUINT
)(pBuff
+ 12));
4578 BCM_DEBUG_PRINT_BUFFER(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, pBuff
, MAX_RW_SIZE
);
4579 /* Now corrupting the sig by corrupting 4th last Byte. */
4582 if (sig
== DSD_IMAGE_MAGIC_NUMBER
) {
4583 Adapter
->bSigCorrupted
= TRUE
;
4584 if (Adapter
->ulFlashWriteSize
== BYTE_WRITE_SUPPORT
) {
4585 uiSectAlignAddr
= uiOffset
& ~(Adapter
->uiSectorSize
- 1);
4586 BlockStatus
= BcmFlashUnProtectBlock(Adapter
, uiSectAlignAddr
, Adapter
->uiSectorSize
);
4588 WriteToFlashWithoutSectorErase(Adapter
, (PUINT
)(pBuff
+ 12), eFlash2xSectionVal
,
4589 (uiOffset
+ 12), BYTE_WRITE_SUPPORT
);
4591 BcmRestoreBlockProtectStatus(Adapter
, BlockStatus
);
4595 WriteToFlashWithoutSectorErase(Adapter
, (PUINT
)pBuff
, eFlash2xSectionVal
,
4596 uiOffset
, MAX_RW_SIZE
);
4599 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "BCM Signature is not present in header");
4602 return STATUS_FAILURE
;
4606 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "Corrupted the signature");
4608 return STATUS_SUCCESS
;
4611 static int CorruptISOSig(struct bcm_mini_adapter
*Adapter
, FLASH2X_SECTION_VAL eFlash2xSectionVal
)
4613 PUCHAR pBuff
= NULL
;
4614 unsigned int sig
= 0;
4615 unsigned int uiOffset
= 0;
4617 Adapter
->bSigCorrupted
= FALSE
;
4619 if (IsSectionWritable(Adapter
, eFlash2xSectionVal
) != TRUE
) {
4620 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Section is not Writable...Hence can't Corrupt signature");
4621 return SECTOR_IS_NOT_WRITABLE
;
4624 pBuff
= (PUCHAR
)kzalloc(MAX_RW_SIZE
, GFP_KERNEL
);
4626 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "Can't allocate memorey");
4632 BcmFlash2xBulkRead(Adapter
, (PUINT
)pBuff
, eFlash2xSectionVal
, uiOffset
, MAX_RW_SIZE
);
4634 sig
= *((PUINT
)pBuff
);
4637 /* corrupt signature */
4640 if (sig
== ISO_IMAGE_MAGIC_NUMBER
) {
4641 Adapter
->bSigCorrupted
= TRUE
;
4642 WriteToFlashWithoutSectorErase(Adapter
, (PUINT
)pBuff
, eFlash2xSectionVal
,
4643 uiOffset
, Adapter
->ulFlashWriteSize
);
4645 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_PRINTK
, 0, 0, "BCM Signature is not present in header");
4648 return STATUS_FAILURE
;
4651 BCM_DEBUG_PRINT(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, "Corrupted the signature");
4652 BCM_DEBUG_PRINT_BUFFER(Adapter
, DBG_TYPE_OTHERS
, NVM_RW
, DBG_LVL_ALL
, pBuff
, MAX_RW_SIZE
);
4655 return STATUS_SUCCESS
;
4658 BOOLEAN
IsNonCDLessDevice(struct bcm_mini_adapter
*Adapter
)
4660 if (Adapter
->psFlash2xCSInfo
->IsCDLessDeviceBootSig
== NON_CDLESS_DEVICE_BOOT_SIG
)