GUI: Fix Tomato RAF theme for all builds. Compilation typo.
[tomato.git] / release / src-rt-6.x.4708 / linux / linux-2.6.36 / drivers / usb / Beceem_driver / src / Common / nvm.c
blobe0a696022d19f7aaa914eb416070d1d6799c8dff
1 /*
2 * nvm.c
4 *Copyright (C) 2010 Beceem Communications, Inc.
6 *This program is free software: you can redistribute it and/or modify
7 *it under the terms of the GNU General Public License version 2 as
8 *published by the Free Software Foundation.
10 *This program is distributed in the hope that it will be useful,but
11 *WITHOUT ANY WARRANTY; without even the implied warranty of
12 *MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
13 *See the GNU General Public License for more details.
15 *You should have received a copy of the GNU General Public License
16 *along with this program. If not, write to the Free Software Foundation, Inc.,
17 *51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
22 #include <headers.h>
24 #define DWORD unsigned int
25 // Procedure: ReadEEPROMStatusRegister
27 // Description: Reads the standard EEPROM Status Register.
29 // Arguments:
30 // Adapter - ptr to Adapter object instance
31 // Returns:
32 // OSAL_STATUS_CODE
34 //-----------------------------------------------------------------------------
36 UCHAR ReadEEPROMStatusRegister( PMINI_ADAPTER Adapter )
38 UCHAR uiData = 0;
39 DWORD dwRetries = MAX_EEPROM_RETRIES*RETRIES_PER_DELAY;
40 UINT uiStatus = 0;
41 UINT value = 0;
42 UINT value1 = 0;
44 /* Read the EEPROM status register */
45 value = EEPROM_READ_STATUS_REGISTER ;
46 wrmalt( Adapter, EEPROM_CMDQ_SPI_REG, &value, sizeof(value));
48 while ( dwRetries != 0 )
50 value=0;
51 uiStatus = 0 ;
52 rdmalt( Adapter, EEPROM_SPI_Q_STATUS1_REG,&uiStatus, sizeof(uiStatus));
53 if(Adapter->device_removed == TRUE)
55 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Modem has got removed hence exiting....");
56 break;
59 /* Wait for Avail bit to be set. */
60 if ( ( uiStatus & EEPROM_READ_DATA_AVAIL) != 0 )
62 /* Clear the Avail/Full bits - which ever is set. */
63 value = uiStatus & (EEPROM_READ_DATA_AVAIL | EEPROM_READ_DATA_FULL);
64 wrmalt( Adapter, EEPROM_SPI_Q_STATUS1_REG, &value, sizeof(value));
66 value =0;
67 rdmalt(Adapter, EEPROM_READ_DATAQ_REG,&value, sizeof(value));
68 uiData = (UCHAR)value;
70 break;
73 dwRetries-- ;
74 if ( dwRetries == 0 )
76 rdmalt(Adapter, EEPROM_SPI_Q_STATUS1_REG,&value, sizeof(value));
77 rdmalt(Adapter, EEPROM_SPI_Q_STATUS_REG,&value1, sizeof(value1));
78 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);
79 return uiData;
81 if( !(dwRetries%RETRIES_PER_DELAY) )
82 msleep(1);
83 uiStatus = 0 ;
85 return uiData;
86 } /* ReadEEPROMStatusRegister */
88 //-----------------------------------------------------------------------------
89 // Procedure: ReadBeceemEEPROMBulk
91 // Description: This routine reads 16Byte data from EEPROM
93 // Arguments:
94 // Adapter - ptr to Adapter object instance
95 // dwAddress - EEPROM Offset to read the data from.
96 // pdwData - Pointer to double word where data needs to be stored in. // dwNumWords - Number of words. Valid values are 4 ONLY.
98 // Returns:
99 // OSAL_STATUS_CODE:
100 //-----------------------------------------------------------------------------
102 INT ReadBeceemEEPROMBulk( PMINI_ADAPTER Adapter,
103 DWORD dwAddress,
104 DWORD *pdwData,
105 DWORD dwNumWords
108 DWORD dwIndex = 0;
109 DWORD dwRetries = MAX_EEPROM_RETRIES*RETRIES_PER_DELAY;
110 UINT uiStatus = 0;
111 UINT value= 0;
112 UINT value1 = 0;
113 UCHAR *pvalue;
115 /* Flush the read and cmd queue. */
116 value=( EEPROM_READ_QUEUE_FLUSH | EEPROM_CMD_QUEUE_FLUSH );
117 wrmalt( Adapter, SPI_FLUSH_REG, &value, sizeof(value) );
118 value=0;
119 wrmalt( Adapter, SPI_FLUSH_REG, &value, sizeof(value));
121 /* Clear the Avail/Full bits. */
122 value=( EEPROM_READ_DATA_AVAIL | EEPROM_READ_DATA_FULL );
123 wrmalt( Adapter, EEPROM_SPI_Q_STATUS1_REG,&value, sizeof(value));
125 value= dwAddress | ( (dwNumWords == 4) ? EEPROM_16_BYTE_PAGE_READ : EEPROM_4_BYTE_PAGE_READ );
126 wrmalt( Adapter, EEPROM_CMDQ_SPI_REG, &value, sizeof(value));
128 while ( dwRetries != 0 )
131 uiStatus = 0;
132 rdmalt( Adapter, EEPROM_SPI_Q_STATUS1_REG, &uiStatus, sizeof(uiStatus));
133 if(Adapter->device_removed == TRUE)
135 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Modem has got Removed.hence exiting from loop...");
136 return -ENODEV;
139 /* If we are reading 16 bytes we want to be sure that the queue
140 * is full before we read. In the other cases we are ok if the
141 * queue has data available */
142 if ( dwNumWords == 4 )
144 if ( ( uiStatus & EEPROM_READ_DATA_FULL ) != 0 )
146 /* Clear the Avail/Full bits - which ever is set. */
147 value = ( uiStatus & (EEPROM_READ_DATA_AVAIL | EEPROM_READ_DATA_FULL) ) ;
148 wrmalt( Adapter, EEPROM_SPI_Q_STATUS1_REG,&value, sizeof(value));
149 break;
152 else if ( dwNumWords == 1 )
155 if ( ( uiStatus & EEPROM_READ_DATA_AVAIL ) != 0 )
157 /* We just got Avail and we have to read 32bits so we
158 * need this sleep for Cardbus kind of devices. */
159 if (Adapter->chip_id == 0xBECE0210 )
160 udelay(800);
162 /* Clear the Avail/Full bits - which ever is set. */
163 value=( uiStatus & (EEPROM_READ_DATA_AVAIL | EEPROM_READ_DATA_FULL) );
164 wrmalt( Adapter, EEPROM_SPI_Q_STATUS1_REG,&value, sizeof(value));
165 break;
169 uiStatus = 0;
171 dwRetries--;
172 if(dwRetries == 0)
174 value=0;
175 value1=0;
176 rdmalt(Adapter, EEPROM_SPI_Q_STATUS1_REG,&value, sizeof(value));
177 rdmalt(Adapter, EEPROM_SPI_Q_STATUS_REG,&value1, sizeof(value1));
178 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "dwNumWords %d 0x3004 = %x 0x3008 = %x retries = %d failed.\n", dwNumWords, value, value1, MAX_EEPROM_RETRIES*RETRIES_PER_DELAY);
179 return STATUS_FAILURE;
181 if( !(dwRetries%RETRIES_PER_DELAY) )
182 msleep(1);
185 for ( dwIndex = 0; dwIndex < dwNumWords ; dwIndex++ )
187 /* We get only a byte at a time - from LSB to MSB. We shift it into an integer. */
188 pvalue = (PUCHAR)(pdwData + dwIndex);
190 value =0;
191 rdmalt(Adapter, EEPROM_READ_DATAQ_REG,&value, sizeof(value));
193 pvalue[0] = value;
195 value = 0;
196 rdmalt(Adapter, EEPROM_READ_DATAQ_REG,&value, sizeof(value));
198 pvalue[1] = value;
200 value =0;
201 rdmalt(Adapter, EEPROM_READ_DATAQ_REG,&value, sizeof(value));
203 pvalue[2] = value;
205 value = 0;
206 rdmalt(Adapter, EEPROM_READ_DATAQ_REG,&value, sizeof(value));
208 pvalue[3] = value;
211 return STATUS_SUCCESS;
212 } /* ReadBeceemEEPROMBulk() */
214 //-----------------------------------------------------------------------------
215 // Procedure: ReadBeceemEEPROM
217 // Description: This routine reads 4 data from EEPROM. It uses 1 or 2 page
218 // reads to do this operation.
220 // Arguments:
221 // Adapter - ptr to Adapter object instance
222 // uiOffset - EEPROM Offset to read the data from.
223 // pBuffer - Pointer to word where data needs to be stored in.
225 // Returns:
226 // OSAL_STATUS_CODE:
227 //-----------------------------------------------------------------------------
229 INT ReadBeceemEEPROM( PMINI_ADAPTER Adapter,
230 DWORD uiOffset,
231 DWORD *pBuffer
234 UINT uiData[8] = {0};
235 UINT uiByteOffset = 0;
236 UINT uiTempOffset = 0;
238 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL," ====> ");
240 uiTempOffset = uiOffset - (uiOffset % MAX_RW_SIZE);
241 uiByteOffset = uiOffset - uiTempOffset;
243 ReadBeceemEEPROMBulk(Adapter, uiTempOffset, (PUINT)&uiData[0], 4);
245 /* A word can overlap at most over 2 pages. In that case we read the
246 * next page too. */
247 if ( uiByteOffset > 12 )
249 ReadBeceemEEPROMBulk(Adapter, uiTempOffset + MAX_RW_SIZE, (PUINT)&uiData[4], 4);
252 OsalMemMove( (PUCHAR) pBuffer, ( ((PUCHAR)&uiData[0]) + uiByteOffset ), 4);
254 return STATUS_SUCCESS;
255 } /* ReadBeceemEEPROM() */
258 #if 0
259 //-----------------------------------------------------------------------------
260 // Procedure: IsEEPROMWriteDone
262 // Description: Reads the SPI status to see the status of previous write.
264 // Arguments:
265 // Adapter - ptr to Adapter object instance
267 // Returns:
268 // BOOLEAN - TRUE - write went through
269 // - FALSE - Write Failed.
270 //-----------------------------------------------------------------------------
272 BOOLEAN IsEEPROMWriteDone(PMINI_ADAPTER Adapter)
274 UINT uiRetries = 16;
275 //UINT uiStatus = 0;
276 UINT value;
278 //sleep for 1.2ms ..worst case EEPROM write can take up to 1.2ms.
279 mdelay(2);
281 value = 0;
282 rdmalt(Adapter, EEPROM_SPI_Q_STATUS1_REG, &value, sizeof(value));
284 while(((value >> 14) & 1) == 1)
286 // EEPROM_SPI_Q_STATUS1_REG will be cleared only if write back to that.
287 value = (0x1 << 14);
288 wrmalt(Adapter, EEPROM_SPI_Q_STATUS1_REG,&value, sizeof(value));
289 udelay(1000);
290 uiRetries--;
291 if(uiRetries == 0)
293 return FALSE;
295 value = 0;
296 rdmalt(Adapter, EEPROM_SPI_Q_STATUS1_REG, &value, sizeof(value));
298 return TRUE;
304 //-----------------------------------------------------------------------------
305 // Procedure: ReadBeceemEEPROMBulk
307 // Description: This routine reads 16Byte data from EEPROM
309 // Arguments:
310 // Adapter - ptr to Adapter object instance
311 // dwAddress - EEPROM Offset to read the data from.
312 // pdwData - Pointer to double word where data needs to be stored in.
314 // Returns:
315 // OSAL_STATUS_CODE:
316 //-----------------------------------------------------------------------------
318 INT ReadBeceemEEPROMBulk(PMINI_ADAPTER Adapter,DWORD dwAddress, DWORD *pdwData)
320 DWORD dwRetries = 16;
321 DWORD dwIndex = 0;
322 UINT value, tmpVal;
325 value = 0;
326 rdmalt (Adapter, 0x0f003008, &value, sizeof(value));
328 //read 0x0f003020 untill bit 1 of 0x0f003008 is set.
329 while(((value >> 1) & 1) == 0)
332 rdmalt (Adapter, 0x0f003020, &tmpVal, sizeof(tmpVal));
333 dwRetries--;
334 if(dwRetries == 0)
336 return -1;
338 value = 0;
339 rdmalt (Adapter, 0x0f003008, &value, sizeof(value));
342 value = dwAddress | 0xfb000000;
343 wrmalt (Adapter, 0x0f003018, &value, sizeof(value));
345 udelay(1000);
346 value = 0;
347 for(dwIndex = 0;dwIndex < 4 ; dwIndex++)
349 value = 0;
350 rdmalt (Adapter, 0x0f003020, &value, sizeof(value));
351 pdwData[dwIndex] = value;
353 value = 0;
354 rdmalt (Adapter, 0x0f003020, &value, sizeof(value));
355 pdwData[dwIndex] |= (value << 8);
357 value = 0;
358 rdmalt (Adapter, 0x0f003020, &value, sizeof(value));
359 pdwData[dwIndex] |= (value << 16);
361 value = 0;
362 rdmalt (Adapter, 0x0f003020, &value, sizeof(value));
363 pdwData[dwIndex] |= (value << 24);
366 return 0;
369 //-----------------------------------------------------------------------------
370 // Procedure: ReadBeceemEEPROM
372 // Description: This routine reads 4Byte data from EEPROM
374 // Arguments:
375 // Adapter - ptr to Adapter object instance
376 // dwAddress - EEPROM Offset to read the data from.
377 // pdwData - Pointer to double word where data needs to be stored in.
379 // Returns:
380 // OSAL_STATUS_CODE:
381 //-----------------------------------------------------------------------------
383 INT ReadBeceemEEPROM(PMINI_ADAPTER Adapter,DWORD dwAddress, DWORD *pdwData)
386 DWORD dwReadValue = 0;
387 DWORD dwRetries = 16, dwCompleteWord = 0;
388 UINT value, tmpVal;
390 rdmalt(Adapter, 0x0f003008, &value, sizeof(value));
391 while (((value >> 1) & 1) == 0) {
392 rdmalt(Adapter, 0x0f003020, &tmpVal, sizeof(tmpVal));
394 if (dwRetries == 0) {
395 return -1;
397 rdmalt(Adapter, 0x0f003008, &value, sizeof(value));
401 //wrm (0x0f003018, 0xNbXXXXXX) // N is the number of bytes u want to read (0 means 1, f means 16, b is the opcode for page read)
402 // Follow it up by N executions of rdm(0x0f003020) to read the rxed bytes from rx queue.
403 dwAddress |= 0x3b000000;
404 wrmalt(Adapter, 0x0f003018,&dwAddress,4);
405 mdelay(10);
406 rdmalt(Adapter, 0x0f003020,&dwReadValue,4);
407 dwCompleteWord=dwReadValue;
408 rdmalt(Adapter, 0x0f003020,&dwReadValue,4);
409 dwCompleteWord|=(dwReadValue<<8);
410 rdmalt(Adapter, 0x0f003020,&dwReadValue,4);
411 dwCompleteWord|=(dwReadValue<<16);
412 rdmalt(Adapter, 0x0f003020,&dwReadValue,4);
413 dwCompleteWord|=(dwReadValue<<24);
415 *pdwData = dwCompleteWord;
417 return 0;
419 #endif
421 INT ReadMacAddressFromNVM(PMINI_ADAPTER Adapter)
423 INT Status=0, i;
424 unsigned char puMacAddr[6] = {0};
425 INT AllZeroMac = 0;
426 INT AllFFMac = 0;
428 Status = BeceemNVMRead(Adapter,
429 (PUINT)&puMacAddr[0],
430 INIT_PARAMS_1_MACADDRESS_ADDRESS,
431 MAC_ADDRESS_SIZE);
433 if(Status != STATUS_SUCCESS)
435 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Error in Reading the mac Addres with status :%d", Status);
436 return Status;
439 memcpy(Adapter->dev->dev_addr, puMacAddr, MAC_ADDRESS_SIZE);
440 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"Modem MAC Addr :");
441 BCM_DEBUG_PRINT_BUFFER(Adapter,DBG_TYPE_PRINTK, 0, DBG_LVL_ALL,&Adapter->dev->dev_addr[0],MAC_ADDRESS_SIZE);
442 for(i=0;i<MAC_ADDRESS_SIZE;i++)
445 if(Adapter->dev->dev_addr[i] == 0x00)
446 AllZeroMac++;
447 if(Adapter->dev->dev_addr[i] == 0xFF)
448 AllFFMac++;
451 //BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "\n");
452 if(AllZeroMac == MAC_ADDRESS_SIZE)
453 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"Warning :: MAC Address has all 00's");
454 if(AllFFMac == MAC_ADDRESS_SIZE)
455 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"Warning :: MAC Address has all FF's");
457 return Status;
461 //-----------------------------------------------------------------------------
462 // Procedure: BeceemEEPROMBulkRead
464 // Description: Reads the EEPROM and returns the Data.
466 // Arguments:
467 // Adapter - ptr to Adapter object instance
468 // pBuffer - Buffer to store the data read from EEPROM
469 // uiOffset - Offset of EEPROM from where data should be read
470 // uiNumBytes - Number of bytes to be read from the EEPROM.
472 // Returns:
473 // OSAL_STATUS_SUCCESS - if EEPROM read is successfull.
474 // <FAILURE> - if failed.
475 //-----------------------------------------------------------------------------
477 INT BeceemEEPROMBulkRead(
478 PMINI_ADAPTER Adapter,
479 PUINT pBuffer,
480 UINT uiOffset,
481 UINT uiNumBytes)
483 UINT uiData[4] = {0};
484 //UINT uiAddress = 0;
485 UINT uiBytesRemaining = uiNumBytes;
486 UINT uiIndex = 0;
487 UINT uiTempOffset = 0;
488 UINT uiExtraBytes = 0;
489 UINT uiFailureRetries = 0;
490 PUCHAR pcBuff = (PUCHAR)pBuffer;
493 if(uiOffset%MAX_RW_SIZE&& uiBytesRemaining)
495 uiTempOffset = uiOffset - (uiOffset%MAX_RW_SIZE);
496 uiExtraBytes = uiOffset-uiTempOffset;
497 ReadBeceemEEPROMBulk(Adapter,uiTempOffset,(PUINT)&uiData[0],4);
498 if(uiBytesRemaining >= (MAX_RW_SIZE - uiExtraBytes))
500 OsalMemMove(pBuffer,(((PUCHAR)&uiData[0])+uiExtraBytes),MAX_RW_SIZE - uiExtraBytes);
502 uiBytesRemaining -= (MAX_RW_SIZE - uiExtraBytes);
503 uiIndex += (MAX_RW_SIZE - uiExtraBytes);
504 uiOffset += (MAX_RW_SIZE - uiExtraBytes);
506 else
508 OsalMemMove(pBuffer,(((PUCHAR)&uiData[0])+uiExtraBytes),uiBytesRemaining);
509 uiIndex += uiBytesRemaining;
510 uiOffset += uiBytesRemaining;
511 uiBytesRemaining = 0;
518 while(uiBytesRemaining && uiFailureRetries != 128)
520 if(Adapter->device_removed )
522 return -1;
525 if(uiBytesRemaining >= MAX_RW_SIZE)
527 /* For the requests more than or equal to 16 bytes, use bulk
528 * read function to make the access faster.
529 * We read 4 Dwords of data */
530 if(0 == ReadBeceemEEPROMBulk(Adapter,uiOffset,&uiData[0],4))
532 OsalMemMove(pcBuff+uiIndex,&uiData[0],MAX_RW_SIZE);
533 uiOffset += MAX_RW_SIZE;
534 uiBytesRemaining -= MAX_RW_SIZE;
535 uiIndex += MAX_RW_SIZE;
537 else
539 uiFailureRetries++;
540 mdelay(3);//sleep for a while before retry...
543 else if(uiBytesRemaining >= 4)
545 if(0 == ReadBeceemEEPROM(Adapter,uiOffset,&uiData[0]))
547 OsalMemMove(pcBuff+uiIndex,&uiData[0],4);
548 uiOffset += 4;
549 uiBytesRemaining -= 4;
550 uiIndex +=4;
552 else
554 uiFailureRetries++;
555 mdelay(3);//sleep for a while before retry...
558 else
559 { // Handle the reads less than 4 bytes...
560 PUCHAR pCharBuff = (PUCHAR)pBuffer;
561 pCharBuff += uiIndex;
562 if(0 == ReadBeceemEEPROM(Adapter,uiOffset,&uiData[0]))
564 OsalMemMove(pCharBuff,&uiData[0],uiBytesRemaining);//copy only bytes requested.
565 uiBytesRemaining = 0;
567 else
569 uiFailureRetries++;
570 mdelay(3);//sleep for a while before retry...
576 return 0;
579 //-----------------------------------------------------------------------------
580 // Procedure: BeceemFlashBulkRead
582 // Description: Reads the FLASH and returns the Data.
584 // Arguments:
585 // Adapter - ptr to Adapter object instance
586 // pBuffer - Buffer to store the data read from FLASH
587 // uiOffset - Offset of FLASH from where data should be read
588 // uiNumBytes - Number of bytes to be read from the FLASH.
590 // Returns:
591 // OSAL_STATUS_SUCCESS - if FLASH read is successfull.
592 // <FAILURE> - if failed.
593 //-----------------------------------------------------------------------------
595 INT BeceemFlashBulkRead(
596 PMINI_ADAPTER Adapter,
597 PUINT pBuffer,
598 UINT uiOffset,
599 UINT uiNumBytes)
601 UINT uiIndex = 0;
602 UINT uiBytesToRead = uiNumBytes;
603 INT Status = 0;
604 UINT uiPartOffset = 0;
606 if(Adapter->device_removed )
608 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "Device Got Removed ");
609 return -ENODEV;
612 //Adding flash Base address
613 // uiOffset = uiOffset + GetFlashBaseAddr(Adapter);
614 #if defined(BCM_SHM_INTERFACE) && !defined(FLASH_DIRECT_ACCESS)
615 Status = bcmflash_raw_read((uiOffset/FLASH_PART_SIZE),(uiOffset % FLASH_PART_SIZE),( unsigned char *)pBuffer,uiNumBytes);
616 return Status;
617 #endif
619 Adapter->SelectedChip = RESET_CHIP_SELECT;
621 if(uiOffset % MAX_RW_SIZE)
623 BcmDoChipSelect(Adapter,uiOffset);
624 uiPartOffset = (uiOffset & (FLASH_PART_SIZE - 1)) + GetFlashBaseAddr(Adapter);
626 uiBytesToRead = MAX_RW_SIZE - (uiOffset%MAX_RW_SIZE);
627 uiBytesToRead = MIN(uiNumBytes,uiBytesToRead);
629 if(rdm(Adapter,uiPartOffset, (PCHAR)pBuffer+uiIndex,uiBytesToRead))
631 Status = -1;
632 Adapter->SelectedChip = RESET_CHIP_SELECT;
633 return Status;
636 uiIndex += uiBytesToRead;
637 uiOffset += uiBytesToRead;
638 uiNumBytes -= uiBytesToRead;
641 while(uiNumBytes)
643 BcmDoChipSelect(Adapter,uiOffset);
644 uiPartOffset = (uiOffset & (FLASH_PART_SIZE - 1)) + GetFlashBaseAddr(Adapter);
646 uiBytesToRead = MIN(uiNumBytes,MAX_RW_SIZE);
648 if(rdm(Adapter,uiPartOffset, (PCHAR)pBuffer+uiIndex,uiBytesToRead))
650 Status = -1;
651 break;
655 uiIndex += uiBytesToRead;
656 uiOffset += uiBytesToRead;
657 uiNumBytes -= uiBytesToRead;
660 Adapter->SelectedChip = RESET_CHIP_SELECT;
661 return Status;
664 //-----------------------------------------------------------------------------
665 // Procedure: BcmGetFlashSize
667 // Description: Finds the size of FLASH.
669 // Arguments:
670 // Adapter - ptr to Adapter object instance
672 // Returns:
673 // UINT - size of the FLASH Storage.
675 //-----------------------------------------------------------------------------
677 UINT BcmGetFlashSize(PMINI_ADAPTER Adapter)
679 #if 0
680 if(Adapter->bDDRInitDone)
682 return rdm(Adapter,FLASH_CONTIGIOUS_START_ADDR_AFTER_INIT|FLASH_SIZE_ADDR);
685 return rdm(Adapter,FLASH_CONTIGIOUS_START_ADDR_BEFORE_INIT|FLASH_SIZE_ADDR);
686 #endif
687 if(IsFlash2x(Adapter))
688 return (Adapter->psFlash2xCSInfo->OffsetFromDSDStartForDSDHeader + sizeof(DSD_HEADER));
689 else
690 return 32*1024;
695 //-----------------------------------------------------------------------------
696 // Procedure: BcmGetEEPROMSize
698 // Description: Finds the size of EEPROM.
700 // Arguments:
701 // Adapter - ptr to Adapter object instance
703 // Returns:
704 // UINT - size of the EEPROM Storage.
706 //-----------------------------------------------------------------------------
708 UINT BcmGetEEPROMSize(PMINI_ADAPTER Adapter)
710 UINT uiData = 0;
711 UINT uiIndex = 0;
714 // if EEPROM is present and already Calibrated,it will have
715 // 'BECM' string at 0th offset.
716 // To find the EEPROM size read the possible boundaries of the
717 // EEPROM like 4K,8K etc..accessing the EEPROM beyond its size will
718 // result in wrap around. So when we get the End of the EEPROM we will
719 // get 'BECM' string which is indeed at offset 0.
721 BeceemEEPROMBulkRead(Adapter,&uiData,0x0,4);
722 if(uiData == BECM)
724 for(uiIndex = 2;uiIndex <=256; uiIndex*=2)
726 BeceemEEPROMBulkRead(Adapter,&uiData,uiIndex*1024,4);
727 if(uiData == BECM)
729 return uiIndex*1024;
733 else
736 // EEPROM may not be present or not programmed
739 uiData = 0xBABEFACE;
740 if(0 == BeceemEEPROMBulkWrite(Adapter,(PUCHAR)&uiData,0,4,TRUE))
742 uiData = 0;
743 for(uiIndex = 2;uiIndex <=256; uiIndex*=2)
745 BeceemEEPROMBulkRead(Adapter,&uiData,uiIndex*1024,4);
746 if(uiData == 0xBABEFACE)
748 return uiIndex*1024;
754 return 0;
757 #if 0
758 /***********************************************************************************/
760 // WriteBeceemEEPROM: Writes 4 byte data to EEPROM offset.
762 // uiEEPROMOffset - Offset to be written to.
763 // uiData - Data to be written.
765 /***********************************************************************************/
767 INT WriteBeceemEEPROM(PMINI_ADAPTER Adapter,UINT uiEEPROMOffset, UINT uiData)
769 INT Status = 0;
770 ULONG ulRdBk = 0;
771 ULONG ulRetryCount = 3;
772 UINT value;
774 if(uiEEPROMOffset > EEPROM_END)
777 return -1;
780 uiData = htonl(uiData);
781 while(ulRetryCount--)
783 value = 0x06000000;
784 wrmalt(Adapter, 0x0F003018,&value, sizeof(value));//flush the EEPROM FIFO.
785 wrmalt(Adapter, 0x0F00301C,&uiData, sizeof(uiData));
786 value = 0x3A000000 | uiEEPROMOffset;
787 wrmalt(Adapter, 0x0F003018,&value, sizeof(value));
788 __udelay(100000);
789 //read back and verify.
790 Status = ReadBeceemEEPROM(Adapter,uiEEPROMOffset,(UINT *)&ulRdBk);
791 if(Status == 0)
793 if(ulRdBk == uiData)
795 return Status;
797 else
799 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "WriteBeceemEEPROM: Readback does not match\n");
802 else
804 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "WriteBeceemEEPROM: Readback failed\n");
808 return 0;
810 #endif
812 //-----------------------------------------------------------------------------
813 // Procedure: FlashSectorErase
815 // Description: Finds the sector size of the FLASH.
817 // Arguments:
818 // Adapter - ptr to Adapter object instance
819 // addr - sector start address
820 // numOfSectors - number of sectors to be erased.
822 // Returns:
823 // OSAL_STATUS_CODE
825 //-----------------------------------------------------------------------------
828 INT FlashSectorErase(PMINI_ADAPTER Adapter,
829 UINT addr,
830 UINT numOfSectors)
832 UINT iIndex = 0, iRetries = 0;
833 UINT uiStatus = 0;
834 UINT value;
836 for(iIndex=0;iIndex<numOfSectors;iIndex++)
838 value = 0x06000000;
839 wrmalt(Adapter, FLASH_SPI_CMDQ_REG, &value, sizeof(value));
841 value = (0xd8000000 | (addr & 0xFFFFFF));
842 wrmalt(Adapter, FLASH_SPI_CMDQ_REG, &value, sizeof(value));
843 iRetries = 0;
847 value = (FLASH_CMD_STATUS_REG_READ << 24);
848 if(wrmalt(Adapter, FLASH_SPI_CMDQ_REG, &value, sizeof(value)) < 0)
850 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Programing of FLASH_SPI_CMDQ_REG fails");
851 return STATUS_FAILURE;
854 if(rdmalt(Adapter, FLASH_SPI_READQ_REG, &uiStatus, sizeof(uiStatus)) < 0 )
856 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Reading status of FLASH_SPI_READQ_REG fails");
857 return STATUS_FAILURE;
859 iRetries++;
860 //After every try lets make the CPU free for 10 ms. generally time taken by the
861 //the sector erase cycle is 500 ms to 40000 msec. hence sleeping 10 ms
862 //won't hamper performance in any case.
863 msleep(10);
864 }while((uiStatus & 0x1) && (iRetries < 400));
866 if(uiStatus & 0x1)
868 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"iRetries crossing the limit of 80000\n");
869 return STATUS_FAILURE;
872 addr += Adapter->uiSectorSize;
874 return 0;
876 //-----------------------------------------------------------------------------
877 // Procedure: flashByteWrite
879 // Description: Performs Byte by Byte write to flash
881 // Arguments:
882 // Adapter - ptr to Adapter object instance
883 // uiOffset - Offset of the flash where data needs to be written to.
884 // pData - Address of Data to be written.
885 // Returns:
886 // OSAL_STATUS_CODE
888 //-----------------------------------------------------------------------------
890 INT flashByteWrite(
891 PMINI_ADAPTER Adapter,
892 UINT uiOffset,
893 PVOID pData)
896 UINT uiStatus = 0;
897 INT iRetries = MAX_FLASH_RETRIES * FLASH_PER_RETRIES_DELAY; //3
899 UINT value;
900 ULONG ulData = *(PUCHAR)pData;
903 // need not write 0xFF because write requires an erase and erase will
904 // make whole sector 0xFF.
907 if(0xFF == ulData)
909 return STATUS_SUCCESS;
912 // DumpDebug(NVM_RW,("flashWrite ====>\n"));
913 value = (FLASH_CMD_WRITE_ENABLE << 24);
914 if(wrmalt(Adapter, FLASH_SPI_CMDQ_REG,&value, sizeof(value)) < 0)
916 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Write enable in FLASH_SPI_CMDQ_REG register fails");
917 return STATUS_FAILURE;
919 if(wrm(Adapter,FLASH_SPI_WRITEQ_REG, (PCHAR)&ulData, 4) < 0 )
921 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"DATA Write on FLASH_SPI_WRITEQ_REG fails");
922 return STATUS_FAILURE;
924 value = (0x02000000 | (uiOffset & 0xFFFFFF));
925 if(wrmalt(Adapter, FLASH_SPI_CMDQ_REG,&value, sizeof(value)) < 0 )
927 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Programming of FLASH_SPI_CMDQ_REG fails");
928 return STATUS_FAILURE;
931 //__udelay(950);
935 value = (FLASH_CMD_STATUS_REG_READ << 24);
936 if(wrmalt(Adapter, FLASH_SPI_CMDQ_REG, &value, sizeof(value)) < 0)
938 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Programing of FLASH_SPI_CMDQ_REG fails");
939 return STATUS_FAILURE;
941 //__udelay(1);
942 if(rdmalt(Adapter, FLASH_SPI_READQ_REG, &uiStatus, sizeof(uiStatus)) < 0)
944 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Reading status of FLASH_SPI_READQ_REG fails");
945 return STATUS_FAILURE;
947 iRetries--;
948 if( iRetries && ((iRetries % FLASH_PER_RETRIES_DELAY) == 0))
949 msleep(1);
951 }while((uiStatus & 0x1) && (iRetries >0) );
953 if(uiStatus & 0x1)
955 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Flash Write fails even after checking status for 200 times.");
956 return STATUS_FAILURE ;
959 return STATUS_SUCCESS;
964 //-----------------------------------------------------------------------------
965 // Procedure: flashWrite
967 // Description: Performs write to flash
969 // Arguments:
970 // Adapter - ptr to Adapter object instance
971 // uiOffset - Offset of the flash where data needs to be written to.
972 // pData - Address of Data to be written.
973 // Returns:
974 // OSAL_STATUS_CODE
976 //-----------------------------------------------------------------------------
978 INT flashWrite(
979 PMINI_ADAPTER Adapter,
980 UINT uiOffset,
981 PVOID pData)
984 //UINT uiStatus = 0;
985 //INT iRetries = 0;
986 //UINT uiReadBack = 0;
988 UINT uiStatus = 0;
989 INT iRetries = MAX_FLASH_RETRIES * FLASH_PER_RETRIES_DELAY; //3
991 UINT value;
992 UINT uiErasePattern[4] = {0xFFFFFFFF,0xFFFFFFFF,0xFFFFFFFF,0xFFFFFFFF};
994 // need not write 0xFFFFFFFF because write requires an erase and erase will
995 // make whole sector 0xFFFFFFFF.
997 if (!OsalMemCompare(pData, uiErasePattern, MAX_RW_SIZE))
999 return 0;
1002 value = (FLASH_CMD_WRITE_ENABLE << 24);
1004 if(wrmalt(Adapter, FLASH_SPI_CMDQ_REG,&value, sizeof(value)) < 0 )
1006 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Write Enable of FLASH_SPI_CMDQ_REG fails");
1007 return STATUS_FAILURE;
1009 if(wrm(Adapter, uiOffset, (PCHAR)pData, MAX_RW_SIZE) < 0)
1011 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Data write fails...");
1012 return STATUS_FAILURE;
1015 //__udelay(950);
1018 value = (FLASH_CMD_STATUS_REG_READ << 24);
1019 if(wrmalt(Adapter, FLASH_SPI_CMDQ_REG, &value, sizeof(value)) < 0)
1021 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Programing of FLASH_SPI_CMDQ_REG fails");
1022 return STATUS_FAILURE;
1024 //__udelay(1);
1025 if(rdmalt(Adapter, FLASH_SPI_READQ_REG, &uiStatus, sizeof(uiStatus)) < 0 )
1027 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Reading status of FLASH_SPI_READQ_REG fails");
1028 return STATUS_FAILURE;
1031 iRetries--;
1032 //this will ensure that in there will be no changes in the current path.
1033 //currently one rdm/wrm takes 125 us.
1034 //Hence 125 *2 * FLASH_PER_RETRIES_DELAY > 3 ms(worst case delay)
1035 //Hence current implementation cycle will intoduce no delay in current path
1036 if(iRetries && ((iRetries % FLASH_PER_RETRIES_DELAY) == 0))
1037 msleep(1);
1038 }while((uiStatus & 0x1) && (iRetries > 0));
1040 if(uiStatus & 0x1)
1042 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Flash Write fails even after checking status for 200 times.");
1043 return STATUS_FAILURE ;
1046 return STATUS_SUCCESS;
1049 //-----------------------------------------------------------------------------
1050 // Procedure: flashByteWriteStatus
1052 // Description: Performs byte by byte write to flash with write done status check
1054 // Arguments:
1055 // Adapter - ptr to Adapter object instance
1056 // uiOffset - Offset of the flash where data needs to be written to.
1057 // pData - Address of the Data to be written.
1058 // Returns:
1059 // OSAL_STATUS_CODE
1061 //-----------------------------------------------------------------------------
1062 INT flashByteWriteStatus(
1063 PMINI_ADAPTER Adapter,
1064 UINT uiOffset,
1065 PVOID pData)
1067 UINT uiStatus = 0;
1068 INT iRetries = MAX_FLASH_RETRIES * FLASH_PER_RETRIES_DELAY; //3
1069 ULONG ulData = *(PUCHAR)pData;
1070 UINT value;
1073 // need not write 0xFFFFFFFF because write requires an erase and erase will
1074 // make whole sector 0xFFFFFFFF.
1077 if(0xFF == ulData)
1079 return STATUS_SUCCESS;
1082 // DumpDebug(NVM_RW,("flashWrite ====>\n"));
1084 value = (FLASH_CMD_WRITE_ENABLE << 24);
1085 if(wrmalt(Adapter, FLASH_SPI_CMDQ_REG,&value, sizeof(value)) < 0)
1087 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Write enable in FLASH_SPI_CMDQ_REG register fails");
1088 return STATUS_SUCCESS;
1090 if(wrm(Adapter,FLASH_SPI_WRITEQ_REG, (PCHAR)&ulData, 4) < 0)
1092 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"DATA Write on FLASH_SPI_WRITEQ_REG fails");
1093 return STATUS_FAILURE;
1095 value = (0x02000000 | (uiOffset & 0xFFFFFF));
1096 if(wrmalt(Adapter, FLASH_SPI_CMDQ_REG,&value, sizeof(value)) < 0)
1098 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Programming of FLASH_SPI_CMDQ_REG fails");
1099 return STATUS_FAILURE;
1102 //msleep(1);
1106 value = (FLASH_CMD_STATUS_REG_READ << 24);
1107 if(wrmalt(Adapter, FLASH_SPI_CMDQ_REG, &value, sizeof(value)) < 0)
1109 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Programing of FLASH_SPI_CMDQ_REG fails");
1110 return STATUS_FAILURE;
1112 //__udelay(1);
1113 if(rdmalt(Adapter, FLASH_SPI_READQ_REG, &uiStatus, sizeof(uiStatus)) < 0)
1115 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Reading status of FLASH_SPI_READQ_REG fails");
1116 return STATUS_FAILURE;
1119 iRetries--;
1120 if( iRetries && ((iRetries % FLASH_PER_RETRIES_DELAY) == 0))
1121 msleep(1);
1122 }while((uiStatus & 0x1) && (iRetries > 0));
1124 if(uiStatus & 0x1)
1126 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Flash Write fails even after checking status for 200 times.");
1127 return STATUS_FAILURE ;
1130 return STATUS_SUCCESS;
1133 //-----------------------------------------------------------------------------
1134 // Procedure: flashWriteStatus
1136 // Description: Performs write to flash with write done status check
1138 // Arguments:
1139 // Adapter - ptr to Adapter object instance
1140 // uiOffset - Offset of the flash where data needs to be written to.
1141 // pData - Address of the Data to be written.
1142 // Returns:
1143 // OSAL_STATUS_CODE
1145 //-----------------------------------------------------------------------------
1147 INT flashWriteStatus(
1148 PMINI_ADAPTER Adapter,
1149 UINT uiOffset,
1150 PVOID pData)
1152 UINT uiStatus = 0;
1153 INT iRetries = MAX_FLASH_RETRIES * FLASH_PER_RETRIES_DELAY; //3
1154 //UINT uiReadBack = 0;
1155 UINT value;
1156 UINT uiErasePattern[4] = {0xFFFFFFFF,0xFFFFFFFF,0xFFFFFFFF,0xFFFFFFFF};
1159 // need not write 0xFFFFFFFF because write requires an erase and erase will
1160 // make whole sector 0xFFFFFFFF.
1162 if (!OsalMemCompare(pData,uiErasePattern,MAX_RW_SIZE))
1164 return 0;
1167 value = (FLASH_CMD_WRITE_ENABLE << 24);
1168 if(wrmalt(Adapter, FLASH_SPI_CMDQ_REG,&value, sizeof(value)) < 0)
1170 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Write Enable of FLASH_SPI_CMDQ_REG fails");
1171 return STATUS_FAILURE;
1173 if(wrm(Adapter, uiOffset, (PCHAR)pData, MAX_RW_SIZE) < 0)
1175 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Data write fails...");
1176 return STATUS_FAILURE;
1178 // __udelay(1);
1182 value = (FLASH_CMD_STATUS_REG_READ << 24);
1183 if(wrmalt(Adapter, FLASH_SPI_CMDQ_REG, &value, sizeof(value)) < 0)
1185 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Programing of FLASH_SPI_CMDQ_REG fails");
1186 return STATUS_FAILURE;
1188 //__udelay(1);
1189 if(rdmalt(Adapter, FLASH_SPI_READQ_REG, &uiStatus, sizeof(uiStatus)) < 0)
1191 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Reading status of FLASH_SPI_READQ_REG fails");
1192 return STATUS_FAILURE;
1194 iRetries--;
1195 //this will ensure that in there will be no changes in the current path.
1196 //currently one rdm/wrm takes 125 us.
1197 //Hence 125 *2 * FLASH_PER_RETRIES_DELAY >3 ms(worst case delay)
1198 //Hence current implementation cycle will intoduce no delay in current path
1199 if(iRetries && ((iRetries % FLASH_PER_RETRIES_DELAY) == 0))
1200 msleep(1);
1201 }while((uiStatus & 0x1) && (iRetries >0));
1203 if(uiStatus & 0x1)
1205 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Flash Write fails even after checking status for 200 times.");
1206 return STATUS_FAILURE ;
1209 return STATUS_SUCCESS;
1212 //-----------------------------------------------------------------------------
1213 // Procedure: BcmRestoreBlockProtectStatus
1215 // Description: Restores the original block protection status.
1217 // Arguments:
1218 // Adapter - ptr to Adapter object instance
1219 // ulWriteStatus -Original status
1220 // Returns:
1221 // <VOID>
1223 //-----------------------------------------------------------------------------
1225 VOID BcmRestoreBlockProtectStatus(PMINI_ADAPTER Adapter,ULONG ulWriteStatus)
1227 UINT value;
1228 value = (FLASH_CMD_WRITE_ENABLE<< 24);
1229 wrmalt(Adapter, FLASH_SPI_CMDQ_REG, &value, sizeof(value));
1231 udelay(20);
1232 value = (FLASH_CMD_STATUS_REG_WRITE<<24)|(ulWriteStatus << 16);
1233 wrmalt(Adapter, FLASH_SPI_CMDQ_REG, &value, sizeof(value));
1234 udelay(20);
1236 //-----------------------------------------------------------------------------
1237 // Procedure: BcmFlashUnProtectBlock
1239 // Description: UnProtects appropriate blocks for writing.
1241 // Arguments:
1242 // Adapter - ptr to Adapter object instance
1243 // uiOffset - Offset of the flash where data needs to be written to. This should be Sector aligned.
1244 // Returns:
1245 // ULONG - Status value before UnProtect.
1247 //-----------------------------------------------------------------------------
1248 ULONG BcmFlashUnProtectBlock(PMINI_ADAPTER Adapter,UINT uiOffset, UINT uiLength)
1250 ULONG ulStatus = 0;
1251 ULONG ulWriteStatus = 0;
1252 UINT value;
1253 uiOffset = uiOffset&0x000FFFFF;
1256 // Implemented only for 1MB Flash parts.
1258 if(FLASH_PART_SST25VF080B == Adapter->ulFlashID)
1261 // Get Current BP status.
1263 value = (FLASH_CMD_STATUS_REG_READ << 24);
1264 wrmalt(Adapter, FLASH_SPI_CMDQ_REG, &value, sizeof(value));
1265 udelay(10);
1267 // Read status will be WWXXYYZZ. We have to take only WW.
1269 rdmalt(Adapter, FLASH_SPI_READQ_REG, (PUINT)&ulStatus, sizeof(ulStatus));
1270 ulStatus >>= 24;
1271 ulWriteStatus = ulStatus;
1274 // Bits [5-2] give current block level protection status.
1275 // Bit5: BP3 - DONT CARE
1276 // BP2-BP0: 0 - NO PROTECTION, 1 - UPPER 1/16, 2 - UPPER 1/8, 3 - UPPER 1/4
1277 // 4 - UPPER 1/2. 5 to 7 - ALL BLOCKS
1280 if(ulStatus)
1282 if((uiOffset+uiLength) <= 0x80000)
1285 // Offset comes in lower half of 1MB. Protect the upper half.
1286 // Clear BP1 and BP0 and set BP2.
1288 ulWriteStatus |= (0x4<<2);
1289 ulWriteStatus &= ~(0x3<<2);
1291 else if((uiOffset+uiLength) <= 0xC0000)
1294 // Offset comes below Upper 1/4. Upper 1/4 can be protected.
1295 // Clear BP2 and set BP1 and BP0.
1297 ulWriteStatus |= (0x3<<2);
1298 ulWriteStatus &= ~(0x1<<4);
1300 else if((uiOffset+uiLength) <= 0xE0000)
1303 // Offset comes below Upper 1/8. Upper 1/8 can be protected.
1304 // Clear BP2 and BP0 and set BP1
1306 ulWriteStatus |= (0x1<<3);
1307 ulWriteStatus &= ~(0x5<<2);
1310 else if((uiOffset+uiLength) <= 0xF0000)
1313 // Offset comes below Upper 1/16. Only upper 1/16 can be protected.
1314 // Set BP0 and Clear BP2,BP1.
1316 ulWriteStatus |= (0x1<<2);
1317 ulWriteStatus &= ~(0x3<<3);
1319 else
1322 // Unblock all.
1323 // Clear BP2,BP1 and BP0.
1325 ulWriteStatus &= ~(0x7<<2);
1328 value = (FLASH_CMD_WRITE_ENABLE<< 24);
1329 wrmalt(Adapter, FLASH_SPI_CMDQ_REG, &value, sizeof(value));
1330 udelay(20);
1331 value = (FLASH_CMD_STATUS_REG_WRITE<<24)|(ulWriteStatus << 16);
1332 wrmalt(Adapter, FLASH_SPI_CMDQ_REG, &value, sizeof(value));
1333 udelay(20);
1338 return ulStatus;
1340 //-----------------------------------------------------------------------------
1341 // Procedure: BeceemFlashBulkWrite
1343 // Description: Performs write to the flash
1345 // Arguments:
1346 // Adapter - ptr to Adapter object instance
1347 // pBuffer - Data to be written.
1348 // uiOffset - Offset of the flash where data needs to be written to.
1349 // uiNumBytes - Number of bytes to be written.
1350 // bVerify - read verify flag.
1351 // Returns:
1352 // OSAL_STATUS_CODE
1354 //-----------------------------------------------------------------------------
1356 INT BeceemFlashBulkWrite(
1357 PMINI_ADAPTER Adapter,
1358 PUINT pBuffer,
1359 UINT uiOffset,
1360 UINT uiNumBytes,
1361 BOOLEAN bVerify)
1363 PCHAR pTempBuff = NULL;
1364 PUCHAR pcBuffer = (PUCHAR)pBuffer;
1365 UINT uiIndex = 0;
1366 UINT uiOffsetFromSectStart = 0;
1367 UINT uiSectAlignAddr = 0;
1368 UINT uiCurrSectOffsetAddr = 0;
1369 UINT uiSectBoundary = 0;
1370 UINT uiNumSectTobeRead = 0;
1371 UCHAR ucReadBk[16] = {0};
1372 ULONG ulStatus = 0;
1373 INT Status = STATUS_SUCCESS;
1374 UINT uiTemp = 0;
1375 UINT index = 0;
1376 UINT uiPartOffset = 0;
1377 #if 0
1378 struct timeval tv1 = {0};
1379 struct timeval tv2 = {0};
1381 struct timeval tr = {0};
1382 struct timeval te = {0};
1383 struct timeval tw = {0};
1384 struct timeval twv = {0};
1385 #endif
1387 #if defined(BCM_SHM_INTERFACE) && !defined(FLASH_DIRECT_ACCESS)
1388 Status = bcmflash_raw_write((uiOffset/FLASH_PART_SIZE),(uiOffset % FLASH_PART_SIZE),( unsigned char *)pBuffer,uiNumBytes);
1389 return Status;
1390 #endif
1392 uiOffsetFromSectStart = uiOffset & ~(Adapter->uiSectorSize - 1);
1394 //Adding flash Base address
1395 // uiOffset = uiOffset + GetFlashBaseAddr(Adapter);
1397 uiSectAlignAddr = uiOffset & ~(Adapter->uiSectorSize - 1);
1398 uiCurrSectOffsetAddr = uiOffset & (Adapter->uiSectorSize - 1);
1399 uiSectBoundary = uiSectAlignAddr + Adapter->uiSectorSize;
1401 //pTempBuff = OsalMemAlloc(MAX_SECTOR_SIZE,'!MVN');
1402 pTempBuff = OsalMemAlloc(Adapter->uiSectorSize ,'!MVN');
1403 if(NULL == pTempBuff)
1405 goto BeceemFlashBulkWrite_EXIT;
1408 // check if the data to be written is overlapped accross sectors
1410 if(uiOffset+uiNumBytes < uiSectBoundary)
1412 uiNumSectTobeRead = 1;
1414 else
1416 // Number of sectors = Last sector start address/First sector start address
1417 uiNumSectTobeRead = (uiCurrSectOffsetAddr+uiNumBytes)/Adapter->uiSectorSize;
1418 if((uiCurrSectOffsetAddr+uiNumBytes)%Adapter->uiSectorSize)
1420 uiNumSectTobeRead++;
1423 #if 1
1424 //Check whether Requested sector is writable or not in case of flash2x write. But if write call is
1425 // for DSD calibration, allow it without checking of sector permission
1427 if(IsFlash2x(Adapter) && (Adapter->bAllDSDWriteAllow == FALSE))
1429 index = 0;
1430 uiTemp = uiNumSectTobeRead ;
1431 while(uiTemp)
1433 if(IsOffsetWritable(Adapter, uiOffsetFromSectStart + index * Adapter->uiSectorSize ) == FALSE)
1435 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Sector Starting at offset <0X%X> is not writable",
1436 (uiOffsetFromSectStart + index * Adapter->uiSectorSize));
1437 Status = SECTOR_IS_NOT_WRITABLE;
1438 goto BeceemFlashBulkWrite_EXIT;
1440 uiTemp = uiTemp - 1;
1441 index = index + 1 ;
1444 #endif
1445 Adapter->SelectedChip = RESET_CHIP_SELECT;
1446 while(uiNumSectTobeRead)
1448 //do_gettimeofday(&tv1);
1449 //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));
1450 uiPartOffset = (uiSectAlignAddr & (FLASH_PART_SIZE - 1)) + GetFlashBaseAddr(Adapter);
1452 BcmDoChipSelect(Adapter,uiSectAlignAddr);
1454 if(0 != BeceemFlashBulkRead(Adapter,
1455 (PUINT)pTempBuff,
1456 uiOffsetFromSectStart,
1457 Adapter->uiSectorSize))
1459 Status = -1;
1460 goto BeceemFlashBulkWrite_EXIT;
1463 //do_gettimeofday(&tr);
1464 //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));
1466 ulStatus = BcmFlashUnProtectBlock(Adapter,uiSectAlignAddr,Adapter->uiSectorSize);
1469 if(uiNumSectTobeRead > 1)
1472 OsalMemMove(&pTempBuff[uiCurrSectOffsetAddr],pcBuffer,uiSectBoundary-(uiSectAlignAddr+uiCurrSectOffsetAddr));
1473 pcBuffer += ((uiSectBoundary-(uiSectAlignAddr+uiCurrSectOffsetAddr)));
1474 uiNumBytes -= (uiSectBoundary-(uiSectAlignAddr+uiCurrSectOffsetAddr));
1476 else
1478 OsalMemMove(&pTempBuff[uiCurrSectOffsetAddr],pcBuffer,uiNumBytes);
1481 if(IsFlash2x(Adapter))
1483 SaveHeaderIfPresent(Adapter,(PUCHAR)pTempBuff,uiOffsetFromSectStart);
1486 FlashSectorErase(Adapter,uiPartOffset,1);
1487 //do_gettimeofday(&te);
1488 //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));
1490 for(uiIndex = 0; uiIndex < Adapter->uiSectorSize; uiIndex +=Adapter->ulFlashWriteSize)
1492 if(Adapter->device_removed)
1494 Status = -1;
1495 goto BeceemFlashBulkWrite_EXIT;
1497 if(STATUS_SUCCESS != (*Adapter->fpFlashWrite)(Adapter,uiPartOffset+uiIndex,(&pTempBuff[uiIndex])))
1499 Status = -1;
1500 goto BeceemFlashBulkWrite_EXIT;
1504 //do_gettimeofday(&tw);
1505 //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));
1506 for(uiIndex = 0;uiIndex < Adapter->uiSectorSize;uiIndex += MAX_RW_SIZE)
1508 if(STATUS_SUCCESS == BeceemFlashBulkRead(Adapter,(PUINT)ucReadBk,uiOffsetFromSectStart+uiIndex,MAX_RW_SIZE))
1510 if(Adapter->ulFlashWriteSize == 1)
1512 UINT uiReadIndex = 0;
1513 for(uiReadIndex = 0; uiReadIndex < 16; uiReadIndex++)
1515 if(ucReadBk[uiReadIndex] != pTempBuff[uiIndex+uiReadIndex])
1517 if(STATUS_SUCCESS != (*Adapter->fpFlashWriteWithStatusCheck)(Adapter,uiPartOffset+uiIndex+uiReadIndex,&pTempBuff[uiIndex+uiReadIndex]))
1519 Status = STATUS_FAILURE;
1520 goto BeceemFlashBulkWrite_EXIT;
1525 else
1527 if(OsalMemCompare(ucReadBk,&pTempBuff[uiIndex],MAX_RW_SIZE))
1529 if(STATUS_SUCCESS != (*Adapter->fpFlashWriteWithStatusCheck)(Adapter,uiPartOffset+uiIndex,&pTempBuff[uiIndex]))
1531 Status = STATUS_FAILURE;
1532 goto BeceemFlashBulkWrite_EXIT;
1538 //do_gettimeofday(&twv);
1539 //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));
1542 if(ulStatus)
1544 BcmRestoreBlockProtectStatus(Adapter,ulStatus);
1545 ulStatus = 0;
1548 uiCurrSectOffsetAddr = 0;
1549 uiSectAlignAddr = uiSectBoundary;
1550 uiSectBoundary += Adapter->uiSectorSize;
1551 uiOffsetFromSectStart += Adapter->uiSectorSize;
1552 uiNumSectTobeRead--;
1554 //do_gettimeofday(&tv2);
1555 //BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "Time after Write :%ld ms\n",(tv2.tv_sec *1000 + tv2.tv_usec/1000));
1556 //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));
1558 // Cleanup.
1560 BeceemFlashBulkWrite_EXIT:
1561 if(ulStatus)
1563 BcmRestoreBlockProtectStatus(Adapter,ulStatus);
1565 if(pTempBuff)
1567 OsalMemFree(pTempBuff,Adapter->uiSectorSize);
1570 Adapter->SelectedChip = RESET_CHIP_SELECT;
1571 return Status;
1575 //-----------------------------------------------------------------------------
1576 // Procedure: BeceemFlashBulkWriteStatus
1578 // Description: Writes to Flash. Checks the SPI status after each write.
1580 // Arguments:
1581 // Adapter - ptr to Adapter object instance
1582 // pBuffer - Data to be written.
1583 // uiOffset - Offset of the flash where data needs to be written to.
1584 // uiNumBytes - Number of bytes to be written.
1585 // bVerify - read verify flag.
1586 // Returns:
1587 // OSAL_STATUS_CODE
1589 //-----------------------------------------------------------------------------
1591 INT BeceemFlashBulkWriteStatus(
1592 PMINI_ADAPTER Adapter,
1593 PUINT pBuffer,
1594 UINT uiOffset,
1595 UINT uiNumBytes,
1596 BOOLEAN bVerify)
1598 PCHAR pTempBuff = NULL;
1599 PUCHAR pcBuffer = (PUCHAR)pBuffer;
1600 UINT uiIndex = 0;
1601 UINT uiOffsetFromSectStart = 0;
1602 UINT uiSectAlignAddr = 0;
1603 UINT uiCurrSectOffsetAddr = 0;
1604 UINT uiSectBoundary = 0;
1605 UINT uiNumSectTobeRead = 0;
1606 UCHAR ucReadBk[16] = {0};
1607 ULONG ulStatus = 0;
1608 UINT Status = STATUS_SUCCESS;
1609 UINT uiTemp = 0;
1610 UINT index = 0;
1611 UINT uiPartOffset = 0;
1613 uiOffsetFromSectStart = uiOffset & ~(Adapter->uiSectorSize - 1);
1615 //uiOffset += Adapter->ulFlashCalStart;
1616 //Adding flash Base address
1617 // uiOffset = uiOffset + GetFlashBaseAddr(Adapter);
1619 uiSectAlignAddr = uiOffset & ~(Adapter->uiSectorSize - 1);
1620 uiCurrSectOffsetAddr = uiOffset & (Adapter->uiSectorSize - 1);
1621 uiSectBoundary = uiSectAlignAddr + Adapter->uiSectorSize;
1625 // pTempBuff = OsalMemAlloc(MAX_SECTOR_SIZE,'!MVN');
1626 pTempBuff = OsalMemAlloc(Adapter->uiSectorSize,'!MVN');
1627 if(NULL == pTempBuff)
1629 goto BeceemFlashBulkWriteStatus_EXIT;
1632 // check if the data to be written is overlapped accross sectors
1634 if(uiOffset+uiNumBytes < uiSectBoundary)
1636 uiNumSectTobeRead = 1;
1638 else
1640 // Number of sectors = Last sector start address/First sector start address
1641 uiNumSectTobeRead = (uiCurrSectOffsetAddr+uiNumBytes)/Adapter->uiSectorSize;
1642 if((uiCurrSectOffsetAddr+uiNumBytes)%Adapter->uiSectorSize)
1644 uiNumSectTobeRead++;
1648 if(IsFlash2x(Adapter) && (Adapter->bAllDSDWriteAllow == FALSE))
1650 index = 0;
1651 uiTemp = uiNumSectTobeRead ;
1652 while(uiTemp)
1654 if(IsOffsetWritable(Adapter,uiOffsetFromSectStart + index * Adapter->uiSectorSize ) == FALSE)
1656 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Sector Starting at offset <0X%x> is not writable",
1657 (uiOffsetFromSectStart + index * Adapter->uiSectorSize));
1658 Status = SECTOR_IS_NOT_WRITABLE;
1659 goto BeceemFlashBulkWriteStatus_EXIT;
1661 uiTemp = uiTemp - 1;
1662 index = index + 1 ;
1666 Adapter->SelectedChip = RESET_CHIP_SELECT;
1667 while(uiNumSectTobeRead)
1669 uiPartOffset = (uiSectAlignAddr & (FLASH_PART_SIZE - 1)) + GetFlashBaseAddr(Adapter);
1671 BcmDoChipSelect(Adapter,uiSectAlignAddr);
1672 if(0 != BeceemFlashBulkRead(Adapter,
1673 (PUINT)pTempBuff,
1674 uiOffsetFromSectStart,
1675 Adapter->uiSectorSize))
1677 Status = -1;
1678 goto BeceemFlashBulkWriteStatus_EXIT;
1681 ulStatus = BcmFlashUnProtectBlock(Adapter,uiOffsetFromSectStart,Adapter->uiSectorSize);
1683 if(uiNumSectTobeRead > 1)
1686 OsalMemMove(&pTempBuff[uiCurrSectOffsetAddr],pcBuffer,uiSectBoundary-(uiSectAlignAddr+uiCurrSectOffsetAddr));
1687 pcBuffer += ((uiSectBoundary-(uiSectAlignAddr+uiCurrSectOffsetAddr)));
1688 uiNumBytes -= (uiSectBoundary-(uiSectAlignAddr+uiCurrSectOffsetAddr));
1690 else
1692 OsalMemMove(&pTempBuff[uiCurrSectOffsetAddr],pcBuffer,uiNumBytes);
1695 if(IsFlash2x(Adapter))
1697 SaveHeaderIfPresent(Adapter,(PUCHAR)pTempBuff,uiOffsetFromSectStart);
1700 FlashSectorErase(Adapter,uiPartOffset,1);
1702 for(uiIndex = 0; uiIndex < Adapter->uiSectorSize; uiIndex +=Adapter->ulFlashWriteSize)
1705 if(Adapter->device_removed)
1707 Status = -1;
1708 goto BeceemFlashBulkWriteStatus_EXIT;
1711 if(STATUS_SUCCESS != (*Adapter->fpFlashWriteWithStatusCheck)(Adapter,uiPartOffset+uiIndex,&pTempBuff[uiIndex]))
1713 Status = -1;
1714 goto BeceemFlashBulkWriteStatus_EXIT;
1718 if(bVerify)
1720 for(uiIndex = 0;uiIndex < Adapter->uiSectorSize;uiIndex += MAX_RW_SIZE)
1722 #if 0
1723 if(0 == BeceemFlashBulkRead(Adapter,uiReadBk,uiOffsetFromSectStart+uiIndex + Adapter->ulFlashCalStart ,MAX_RW_SIZE))
1725 for(uiReadIndex = 0;uiReadIndex < 4; uiReadIndex++)
1727 if(*((PUINT)&pTempBuff[uiIndex+uiReadIndex*4]) != uiReadBk[uiReadIndex])
1729 Status = -1;
1730 goto BeceemFlashBulkWriteStatus_EXIT;
1736 #endif
1738 if(STATUS_SUCCESS == BeceemFlashBulkRead(Adapter,(PUINT)ucReadBk,uiOffsetFromSectStart+uiIndex,MAX_RW_SIZE))
1740 if(OsalMemCompare(ucReadBk,&pTempBuff[uiIndex],MAX_RW_SIZE))
1742 Status = STATUS_FAILURE;
1743 goto BeceemFlashBulkWriteStatus_EXIT;
1751 if(ulStatus)
1753 BcmRestoreBlockProtectStatus(Adapter,ulStatus);
1754 ulStatus = 0;
1757 uiCurrSectOffsetAddr = 0;
1758 uiSectAlignAddr = uiSectBoundary;
1759 uiSectBoundary += Adapter->uiSectorSize;
1760 uiOffsetFromSectStart += Adapter->uiSectorSize;
1761 uiNumSectTobeRead--;
1764 // Cleanup.
1766 BeceemFlashBulkWriteStatus_EXIT:
1767 if(ulStatus)
1769 BcmRestoreBlockProtectStatus(Adapter,ulStatus);
1771 if(pTempBuff)
1773 OsalMemFree(pTempBuff,Adapter->uiSectorSize);
1775 Adapter->SelectedChip = RESET_CHIP_SELECT;
1776 return Status;
1780 //-----------------------------------------------------------------------------
1781 // Procedure: PropagateCalParamsFromEEPROMToMemory
1783 // Description: Dumps the calibration section of EEPROM to DDR.
1785 // Arguments:
1786 // Adapter - ptr to Adapter object instance
1787 // Returns:
1788 // OSAL_STATUS_CODE
1790 //-----------------------------------------------------------------------------
1793 INT PropagateCalParamsFromEEPROMToMemory(PMINI_ADAPTER Adapter)
1795 PCHAR pBuff = OsalMemAlloc(BUFFER_4K,'3MVN');
1796 UINT uiEepromSize = 0;
1797 UINT uiIndex = 0;
1798 UINT uiBytesToCopy = 0;
1799 UINT uiCalStartAddr = EEPROM_CALPARAM_START;
1800 UINT uiMemoryLoc = EEPROM_CAL_DATA_INTERNAL_LOC;
1801 UINT value;
1802 INT Status = 0;
1803 if(pBuff == NULL)
1805 return -1;
1808 if(0 != BeceemEEPROMBulkRead(Adapter,&uiEepromSize,EEPROM_SIZE_OFFSET,4))
1811 OsalMemFree(pBuff,BUFFER_4K);
1812 return -1;
1815 uiEepromSize >>= 16;
1816 if(uiEepromSize > 1024*1024)
1818 OsalMemFree(pBuff,BUFFER_4K);
1819 return -1;
1823 uiBytesToCopy = MIN(BUFFER_4K,uiEepromSize);
1825 while(uiBytesToCopy)
1827 if(0 != BeceemEEPROMBulkRead(Adapter,(PUINT)pBuff,uiCalStartAddr,uiBytesToCopy))
1829 Status = -1;
1830 break;
1832 wrm(Adapter,uiMemoryLoc,(PCHAR)(((PULONG)pBuff)+uiIndex),uiBytesToCopy);
1833 uiMemoryLoc += uiBytesToCopy;
1834 uiEepromSize -= uiBytesToCopy;
1835 uiCalStartAddr += uiBytesToCopy;
1836 uiIndex += uiBytesToCopy/4;
1837 uiBytesToCopy = MIN(BUFFER_4K,uiEepromSize);
1840 value = 0xbeadbead;
1841 wrmalt(Adapter, EEPROM_CAL_DATA_INTERNAL_LOC-4,&value, sizeof(value));
1842 value = 0xbeadbead;
1843 wrmalt(Adapter, EEPROM_CAL_DATA_INTERNAL_LOC-8,&value, sizeof(value));
1844 OsalMemFree(pBuff,MAX_RW_SIZE);
1846 return Status;
1850 //-----------------------------------------------------------------------------
1851 // Procedure: PropagateCalParamsFromFlashToMemory
1853 // Description: Dumps the calibration section of EEPROM to DDR.
1855 // Arguments:
1856 // Adapter - ptr to Adapter object instance
1857 // Returns:
1858 // OSAL_STATUS_CODE
1860 //-----------------------------------------------------------------------------
1862 INT PropagateCalParamsFromFlashToMemory(PMINI_ADAPTER Adapter)
1864 PCHAR pBuff, pPtr;
1865 UINT uiEepromSize = 0;
1866 UINT uiBytesToCopy = 0;
1867 //UINT uiIndex = 0;
1868 UINT uiCalStartAddr = EEPROM_CALPARAM_START;
1869 UINT uiMemoryLoc = EEPROM_CAL_DATA_INTERNAL_LOC;
1870 UINT value;
1871 INT Status = 0;
1873 // Write the signature first. This will ensure firmware does not access EEPROM.
1875 value = 0xbeadbead;
1876 wrmalt(Adapter, EEPROM_CAL_DATA_INTERNAL_LOC - 4, &value, sizeof(value));
1877 value = 0xbeadbead;
1878 wrmalt(Adapter, EEPROM_CAL_DATA_INTERNAL_LOC - 8, &value, sizeof(value));
1880 if(0 != BeceemNVMRead(Adapter,&uiEepromSize,EEPROM_SIZE_OFFSET, 4))
1882 return -1;
1884 uiEepromSize = ntohl(uiEepromSize);
1885 uiEepromSize >>= 16;
1888 // subtract the auto init section size
1890 uiEepromSize -= EEPROM_CALPARAM_START;
1892 if(uiEepromSize > 1024*1024)
1894 return -1;
1897 pBuff = OsalMemAlloc(uiEepromSize, 0);
1899 if ( pBuff == NULL )
1901 return -1;
1904 if(0 != BeceemNVMRead(Adapter,(PUINT)pBuff,uiCalStartAddr, uiEepromSize))
1906 OsalMemFree(pBuff, 0);
1907 return -1;
1910 pPtr = pBuff;
1912 uiBytesToCopy = MIN(BUFFER_4K,uiEepromSize);
1914 while(uiBytesToCopy)
1916 Status = wrm(Adapter,uiMemoryLoc,(PCHAR)pPtr,uiBytesToCopy);
1917 if(Status)
1919 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"wrm failed with status :%d",Status);
1920 break;
1923 pPtr += uiBytesToCopy;
1924 uiEepromSize -= uiBytesToCopy;
1925 uiMemoryLoc += uiBytesToCopy;
1926 uiBytesToCopy = MIN(BUFFER_4K,uiEepromSize);
1929 OsalMemFree(pBuff, 0);
1930 return Status;
1934 //-----------------------------------------------------------------------------
1935 // Procedure: BeceemEEPROMReadBackandVerify
1937 // Description: Read back the data written and verifies.
1939 // Arguments:
1940 // Adapter - ptr to Adapter object instance
1941 // pBuffer - Data to be written.
1942 // uiOffset - Offset of the flash where data needs to be written to.
1943 // uiNumBytes - Number of bytes to be written.
1944 // Returns:
1945 // OSAL_STATUS_CODE
1947 //-----------------------------------------------------------------------------
1949 INT BeceemEEPROMReadBackandVerify(
1950 PMINI_ADAPTER Adapter,
1951 PUINT pBuffer,
1952 UINT uiOffset,
1953 UINT uiNumBytes)
1955 UINT uiRdbk = 0;
1956 UINT uiIndex = 0;
1957 UINT uiData = 0;
1958 UINT auiData[4] = {0};
1960 while(uiNumBytes)
1962 if(Adapter->device_removed )
1964 return -1;
1967 if(uiNumBytes >= MAX_RW_SIZE)
1968 {// for the requests more than or equal to MAX_RW_SIZE bytes, use bulk read function to make the access faster.
1969 BeceemEEPROMBulkRead(Adapter,&auiData[0],uiOffset,MAX_RW_SIZE);
1971 if(OsalMemCompare(&pBuffer[uiIndex],&auiData[0],MAX_RW_SIZE))
1973 // re-write
1974 BeceemEEPROMBulkWrite(Adapter,(PUCHAR)(pBuffer+uiIndex),uiOffset,MAX_RW_SIZE,FALSE);
1975 mdelay(3);
1976 BeceemEEPROMBulkRead(Adapter,&auiData[0],uiOffset,MAX_RW_SIZE);
1978 if(OsalMemCompare(&pBuffer[uiIndex],&auiData[0],MAX_RW_SIZE))
1980 return -1;
1983 uiOffset += MAX_RW_SIZE;
1984 uiNumBytes -= MAX_RW_SIZE;
1985 uiIndex += 4;
1988 else if(uiNumBytes >= 4)
1990 BeceemEEPROMBulkRead(Adapter,&uiData,uiOffset,4);
1991 if(uiData != pBuffer[uiIndex])
1993 //re-write
1994 BeceemEEPROMBulkWrite(Adapter,(PUCHAR)(pBuffer+uiIndex),uiOffset,4,FALSE);
1995 mdelay(3);
1996 BeceemEEPROMBulkRead(Adapter,&uiData,uiOffset,4);
1997 if(uiData != pBuffer[uiIndex])
1999 return -1;
2002 uiOffset += 4;
2003 uiNumBytes -= 4;
2004 uiIndex++;
2007 else
2008 { // Handle the reads less than 4 bytes...
2009 uiData = 0;
2010 OsalMemMove(&uiData,((PUCHAR)pBuffer)+(uiIndex*sizeof(UINT)),uiNumBytes);
2011 BeceemEEPROMBulkRead(Adapter,&uiRdbk,uiOffset,4);
2013 if(memcmp(&uiData, &uiRdbk, uiNumBytes))
2014 return -1;
2016 uiNumBytes = 0;
2021 return 0;
2024 VOID BcmSwapWord(UINT *ptr1) {
2026 UINT tempval = (UINT)*ptr1;
2027 char *ptr2 = (char *)&tempval;
2028 char *ptr = (char *)ptr1;
2030 ptr[0] = ptr2[3];
2031 ptr[1] = ptr2[2];
2032 ptr[2] = ptr2[1];
2033 ptr[3] = ptr2[0];
2036 //-----------------------------------------------------------------------------
2037 // Procedure: BeceemEEPROMWritePage
2039 // Description: Performs page write (16bytes) to the EEPROM
2041 // Arguments:
2042 // Adapter - ptr to Adapter object instance
2043 // uiData - Data to be written.
2044 // uiOffset - Offset of the EEPROM where data needs to be written to.
2045 // Returns:
2046 // OSAL_STATUS_CODE
2048 //-----------------------------------------------------------------------------
2049 INT BeceemEEPROMWritePage( PMINI_ADAPTER Adapter, UINT uiData[], UINT uiOffset )
2051 UINT uiRetries = MAX_EEPROM_RETRIES*RETRIES_PER_DELAY;
2052 UINT uiStatus = 0;
2053 UCHAR uiEpromStatus = 0;
2054 UINT value =0 ;
2056 /* Flush the Write/Read/Cmd queues. */
2057 value = ( EEPROM_WRITE_QUEUE_FLUSH | EEPROM_CMD_QUEUE_FLUSH | EEPROM_READ_QUEUE_FLUSH );
2058 wrmalt( Adapter, SPI_FLUSH_REG, &value, sizeof(value));
2059 value = 0 ;
2060 wrmalt( Adapter, SPI_FLUSH_REG, &value, sizeof(value) );
2062 /* Clear the Empty/Avail/Full bits. After this it has been confirmed
2063 * that the bit was cleared by reading back the register. See NOTE below.
2064 * We also clear the Read queues as we do a EEPROM status register read
2065 * later. */
2066 value = ( EEPROM_WRITE_QUEUE_EMPTY | EEPROM_WRITE_QUEUE_AVAIL | EEPROM_WRITE_QUEUE_FULL | EEPROM_READ_DATA_AVAIL | EEPROM_READ_DATA_FULL ) ;
2067 wrmalt( Adapter, EEPROM_SPI_Q_STATUS1_REG,&value, sizeof(value));
2069 /* Enable write */
2070 value = EEPROM_WRITE_ENABLE ;
2071 wrmalt( Adapter, EEPROM_CMDQ_SPI_REG,&value, sizeof(value) );
2073 /* We can write back to back 8bits * 16 into the queue and as we have
2074 * checked for the queue to be empty we can write in a burst. */
2076 value = uiData[0];
2077 BcmSwapWord(&value);
2078 wrm( Adapter, EEPROM_WRITE_DATAQ_REG, (PUCHAR)&value, 4);
2080 value = uiData[1];
2081 BcmSwapWord(&value);
2082 wrm( Adapter, EEPROM_WRITE_DATAQ_REG, (PUCHAR)&value, 4);
2084 value = uiData[2];
2085 BcmSwapWord(&value);
2086 wrm( Adapter, EEPROM_WRITE_DATAQ_REG, (PUCHAR)&value, 4);
2088 value = uiData[3];
2089 BcmSwapWord(&value);
2090 wrm( Adapter, EEPROM_WRITE_DATAQ_REG, (PUCHAR)&value, 4);
2092 /* NOTE : After this write, on readback of EEPROM_SPI_Q_STATUS1_REG
2093 * shows that we see 7 for the EEPROM data write. Which means that
2094 * queue got full, also space is available as well as the queue is empty.
2095 * This may happen in sequence. */
2096 value = EEPROM_16_BYTE_PAGE_WRITE | uiOffset ;
2097 wrmalt( Adapter, EEPROM_CMDQ_SPI_REG, &value, sizeof(value) );
2099 /* Ideally we should loop here without tries and eventually succeed.
2100 * What we are checking if the previous write has completed, and this
2101 * may take time. We should wait till the Empty bit is set. */
2102 uiStatus = 0;
2103 rdmalt( Adapter, EEPROM_SPI_Q_STATUS1_REG,&uiStatus, sizeof(uiStatus)) ;
2104 while ( ( uiStatus & EEPROM_WRITE_QUEUE_EMPTY ) == 0 )
2106 uiRetries--;
2107 if ( uiRetries == 0 )
2109 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "0x0f003004 = %x, %d retries failed.\n", uiStatus, MAX_EEPROM_RETRIES *RETRIES_PER_DELAY);
2110 return STATUS_FAILURE ;
2113 if( !(uiRetries%RETRIES_PER_DELAY) )
2114 msleep(1);
2116 uiStatus = 0;
2117 rdmalt( Adapter, EEPROM_SPI_Q_STATUS1_REG,&uiStatus, sizeof(uiStatus)) ;
2118 if(Adapter->device_removed == TRUE)
2120 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Modem got removed hence exiting from loop....");
2121 return -ENODEV;
2126 if ( uiRetries != 0 )
2128 /* Clear the ones that are set - either, Empty/Full/Avail bits */
2129 value = ( uiStatus & ( EEPROM_WRITE_QUEUE_EMPTY | EEPROM_WRITE_QUEUE_AVAIL | EEPROM_WRITE_QUEUE_FULL ) );
2130 wrmalt( Adapter, EEPROM_SPI_Q_STATUS1_REG, &value, sizeof(value));
2133 /* Here we should check if the EEPROM status register is correct before
2134 * proceeding. Bit 0 in the EEPROM Status register should be 0 before
2135 * we proceed further. A 1 at Bit 0 indicates that the EEPROM is busy
2136 * with the previous write. Note also that issuing this read finally
2137 * means the previous write to the EEPROM has completed. */
2138 uiRetries = MAX_EEPROM_RETRIES*RETRIES_PER_DELAY;
2139 uiEpromStatus = 0;
2140 while ( uiRetries != 0 )
2142 uiEpromStatus = ReadEEPROMStatusRegister( Adapter) ;
2143 if(Adapter->device_removed == TRUE)
2145 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "Modem has got removed hence exiting from loop...");
2146 return -ENODEV;
2148 if ( ( EEPROM_STATUS_REG_WRITE_BUSY & uiEpromStatus ) == 0 )
2150 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "EEPROM status register = %x tries = %d\n", uiEpromStatus, (MAX_EEPROM_RETRIES * RETRIES_PER_DELAY- uiRetries) );
2151 return STATUS_SUCCESS ;
2153 uiRetries--;
2154 if ( uiRetries == 0 )
2156 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);
2157 return STATUS_FAILURE ;
2159 uiEpromStatus = 0;
2160 if( !(uiRetries%RETRIES_PER_DELAY) )
2161 msleep(1);
2164 return STATUS_SUCCESS ;
2165 } /* BeceemEEPROMWritePage */
2168 //-----------------------------------------------------------------------------
2169 // Procedure: BeceemEEPROMBulkWrite
2171 // Description: Performs write to the EEPROM
2173 // Arguments:
2174 // Adapter - ptr to Adapter object instance
2175 // pBuffer - Data to be written.
2176 // uiOffset - Offset of the EEPROM where data needs to be written to.
2177 // uiNumBytes - Number of bytes to be written.
2178 // bVerify - read verify flag.
2179 // Returns:
2180 // OSAL_STATUS_CODE
2182 //-----------------------------------------------------------------------------
2184 INT BeceemEEPROMBulkWrite(
2185 PMINI_ADAPTER Adapter,
2186 PUCHAR pBuffer,
2187 UINT uiOffset,
2188 UINT uiNumBytes,
2189 BOOLEAN bVerify)
2191 UINT uiBytesToCopy = uiNumBytes;
2192 //UINT uiRdbk = 0;
2193 UINT uiData[4] = {0};
2194 UINT uiIndex = 0;
2195 UINT uiTempOffset = 0;
2196 UINT uiExtraBytes = 0;
2197 //PUINT puiBuffer = (PUINT)pBuffer;
2198 //INT value;
2200 if(uiOffset%MAX_RW_SIZE && uiBytesToCopy)
2202 uiTempOffset = uiOffset - (uiOffset%MAX_RW_SIZE);
2203 uiExtraBytes = uiOffset-uiTempOffset;
2206 BeceemEEPROMBulkRead(Adapter,&uiData[0],uiTempOffset,MAX_RW_SIZE);
2208 if(uiBytesToCopy >= (16 -uiExtraBytes))
2210 OsalMemMove((((PUCHAR)&uiData[0])+uiExtraBytes),pBuffer,MAX_RW_SIZE- uiExtraBytes);
2212 if ( STATUS_FAILURE == BeceemEEPROMWritePage( Adapter, uiData, uiTempOffset ) )
2213 return STATUS_FAILURE;
2215 uiBytesToCopy -= (MAX_RW_SIZE - uiExtraBytes);
2216 uiIndex += (MAX_RW_SIZE - uiExtraBytes);
2217 uiOffset += (MAX_RW_SIZE - uiExtraBytes);
2219 else
2221 OsalMemMove((((PUCHAR)&uiData[0])+uiExtraBytes),pBuffer,uiBytesToCopy);
2223 if ( STATUS_FAILURE == BeceemEEPROMWritePage( Adapter, uiData, uiTempOffset ) )
2224 return STATUS_FAILURE;
2226 uiIndex += uiBytesToCopy;
2227 uiOffset += uiBytesToCopy;
2228 uiBytesToCopy = 0;
2234 while(uiBytesToCopy)
2236 if(Adapter->device_removed)
2238 return -1;
2241 if(uiBytesToCopy >= MAX_RW_SIZE)
2244 if (STATUS_FAILURE == BeceemEEPROMWritePage( Adapter, (PUINT) &pBuffer[uiIndex], uiOffset ) )
2245 return STATUS_FAILURE;
2247 uiIndex += MAX_RW_SIZE;
2248 uiOffset += MAX_RW_SIZE;
2249 uiBytesToCopy -= MAX_RW_SIZE;
2251 else
2254 // To program non 16byte aligned data, read 16byte and then update.
2256 BeceemEEPROMBulkRead(Adapter,&uiData[0],uiOffset,16);
2257 OsalMemMove(&uiData[0],pBuffer+uiIndex,uiBytesToCopy);
2260 if ( STATUS_FAILURE == BeceemEEPROMWritePage( Adapter, uiData, uiOffset ) )
2261 return STATUS_FAILURE;
2262 uiBytesToCopy = 0;
2267 return 0;
2270 //-----------------------------------------------------------------------------
2271 // Procedure: BeceemNVMRead
2273 // Description: Reads n number of bytes from NVM.
2275 // Arguments:
2276 // Adapter - ptr to Adapter object instance
2277 // pBuffer - Buffer to store the data read from NVM
2278 // uiOffset - Offset of NVM from where data should be read
2279 // uiNumBytes - Number of bytes to be read from the NVM.
2281 // Returns:
2282 // OSAL_STATUS_SUCCESS - if NVM read is successfull.
2283 // <FAILURE> - if failed.
2284 //-----------------------------------------------------------------------------
2286 INT BeceemNVMRead(
2287 PMINI_ADAPTER Adapter,
2288 PUINT pBuffer,
2289 UINT uiOffset,
2290 UINT uiNumBytes)
2292 INT Status = 0;
2293 #if !defined(BCM_SHM_INTERFACE) || defined(FLASH_DIRECT_ACCESS)
2294 UINT uiTemp = 0, value;
2295 #endif
2297 if(Adapter->eNVMType == NVM_FLASH)
2299 if(Adapter->bFlashRawRead == FALSE)
2301 if (IsSectionExistInVendorInfo(Adapter,Adapter->eActiveDSD))
2302 return vendorextnReadSection(Adapter,(PUCHAR)pBuffer,Adapter->eActiveDSD,uiOffset,uiNumBytes);
2303 uiOffset = uiOffset+ Adapter->ulFlashCalStart ;
2305 #if defined(BCM_SHM_INTERFACE) && !defined(FLASH_DIRECT_ACCESS)
2306 Status = bcmflash_raw_read((uiOffset/FLASH_PART_SIZE),(uiOffset % FLASH_PART_SIZE),( unsigned char *)pBuffer,uiNumBytes);
2307 #else
2309 rdmalt(Adapter, 0x0f000C80, &uiTemp, sizeof(uiTemp));
2310 value = 0;
2311 wrmalt(Adapter, 0x0f000C80,&value, sizeof(value));
2312 Status = BeceemFlashBulkRead(Adapter,
2313 pBuffer,
2314 uiOffset,
2315 uiNumBytes);
2316 wrmalt(Adapter, 0x0f000C80, &uiTemp, sizeof(uiTemp));
2317 #endif
2319 else if(Adapter->eNVMType == NVM_EEPROM)
2321 Status = BeceemEEPROMBulkRead(Adapter,
2322 pBuffer,
2323 uiOffset,
2324 uiNumBytes);
2326 else
2328 Status = -1;
2330 return Status;
2333 //-----------------------------------------------------------------------------
2334 // Procedure: BeceemNVMWrite
2336 // Description: Writes n number of bytes to NVM.
2338 // Arguments:
2339 // Adapter - ptr to Adapter object instance
2340 // pBuffer - Buffer contains the data to be written.
2341 // uiOffset - Offset of NVM where data to be written to.
2342 // uiNumBytes - Number of bytes to be written..
2344 // Returns:
2345 // OSAL_STATUS_SUCCESS - if NVM write is successfull.
2346 // <FAILURE> - if failed.
2347 //-----------------------------------------------------------------------------
2349 INT BeceemNVMWrite(
2350 PMINI_ADAPTER Adapter,
2351 PUINT pBuffer,
2352 UINT uiOffset,
2353 UINT uiNumBytes,
2354 BOOLEAN bVerify)
2356 INT Status = 0;
2357 UINT uiTemp = 0;
2358 UINT uiMemoryLoc = EEPROM_CAL_DATA_INTERNAL_LOC;
2359 UINT uiIndex = 0;
2360 #if !defined(BCM_SHM_INTERFACE) || defined(FLASH_DIRECT_ACCESS)
2361 UINT value;
2362 #endif
2363 UINT uiFlashOffset = 0;
2365 if(Adapter->eNVMType == NVM_FLASH)
2367 if (IsSectionExistInVendorInfo(Adapter,Adapter->eActiveDSD))
2368 Status = vendorextnWriteSection(Adapter,(PUCHAR)pBuffer,Adapter->eActiveDSD,uiOffset,uiNumBytes,bVerify);
2369 else
2371 uiFlashOffset = uiOffset + Adapter->ulFlashCalStart;
2373 #if defined(BCM_SHM_INTERFACE) && !defined(FLASH_DIRECT_ACCESS)
2374 Status = bcmflash_raw_write((uiFlashOffset/FLASH_PART_SIZE), (uiFlashOffset % FLASH_PART_SIZE), (unsigned char *)pBuffer,uiNumBytes);
2375 #else
2376 rdmalt(Adapter, 0x0f000C80, &uiTemp, sizeof(uiTemp));
2377 value = 0;
2378 wrmalt(Adapter, 0x0f000C80, &value, sizeof(value));
2380 if(Adapter->bStatusWrite == TRUE)
2382 Status = BeceemFlashBulkWriteStatus(Adapter,
2383 pBuffer,
2384 uiFlashOffset,
2385 uiNumBytes ,
2386 bVerify);
2388 else
2391 Status = BeceemFlashBulkWrite(Adapter,
2392 pBuffer,
2393 uiFlashOffset,
2394 uiNumBytes,
2395 bVerify);
2397 #endif
2401 if(uiOffset >= EEPROM_CALPARAM_START)
2403 uiMemoryLoc += (uiOffset - EEPROM_CALPARAM_START);
2404 while(uiNumBytes)
2406 if(uiNumBytes > BUFFER_4K)
2408 wrm(Adapter,(uiMemoryLoc+uiIndex),(PCHAR)(pBuffer+(uiIndex/4)),BUFFER_4K);
2409 uiNumBytes -= BUFFER_4K;
2410 uiIndex += BUFFER_4K;
2412 else
2414 wrm(Adapter,uiMemoryLoc+uiIndex,(PCHAR)(pBuffer+(uiIndex/4)),uiNumBytes);
2415 uiNumBytes = 0;
2416 break;
2420 else
2422 if((uiOffset+uiNumBytes) > EEPROM_CALPARAM_START)
2424 ULONG ulBytesTobeSkipped = 0;
2425 PUCHAR pcBuffer = (PUCHAR)pBuffer;// char pointer to take care of odd byte cases.
2426 uiNumBytes -= (EEPROM_CALPARAM_START - uiOffset);
2427 ulBytesTobeSkipped += (EEPROM_CALPARAM_START - uiOffset);
2428 uiOffset += (EEPROM_CALPARAM_START - uiOffset);
2429 while(uiNumBytes)
2431 if(uiNumBytes > BUFFER_4K)
2433 wrm(Adapter,uiMemoryLoc+uiIndex,(PCHAR )&pcBuffer[ulBytesTobeSkipped+uiIndex],BUFFER_4K);
2434 uiNumBytes -= BUFFER_4K;
2435 uiIndex += BUFFER_4K;
2437 else
2439 wrm(Adapter,uiMemoryLoc+uiIndex,(PCHAR)&pcBuffer[ulBytesTobeSkipped+uiIndex],uiNumBytes);
2440 uiNumBytes = 0;
2441 break;
2448 // restore the values.
2449 wrmalt(Adapter,0x0f000C80,&uiTemp, sizeof(uiTemp));
2451 else if(Adapter->eNVMType == NVM_EEPROM)
2453 Status = BeceemEEPROMBulkWrite(Adapter,
2454 (PUCHAR)pBuffer,
2455 uiOffset,
2456 uiNumBytes,
2457 bVerify);
2458 if(bVerify)
2460 Status = BeceemEEPROMReadBackandVerify(Adapter,(PUINT)pBuffer,uiOffset,uiNumBytes);
2463 else
2465 Status = -1;
2467 return Status;
2470 //-----------------------------------------------------------------------------
2471 // Procedure: BcmUpdateSectorSize
2473 // Description: Updates the sector size to FLASH.
2475 // Arguments:
2476 // Adapter - ptr to Adapter object instance
2477 // uiSectorSize - sector size
2479 // Returns:
2480 // OSAL_STATUS_SUCCESS - if NVM write is successfull.
2481 // <FAILURE> - if failed.
2482 //-----------------------------------------------------------------------------
2484 INT BcmUpdateSectorSize(PMINI_ADAPTER Adapter,UINT uiSectorSize)
2486 INT Status = -1;
2487 FLASH_CS_INFO sFlashCsInfo = {0};
2488 UINT uiTemp = 0;
2490 UINT uiSectorSig = 0;
2491 UINT uiCurrentSectorSize = 0;
2493 UINT value;
2497 rdmalt(Adapter, 0x0f000C80, &uiTemp, sizeof(uiTemp));
2498 value = 0;
2499 wrmalt(Adapter, 0x0f000C80,&value, sizeof(value));
2502 // Before updating the sector size in the reserved area, check if already present.
2504 BeceemFlashBulkRead(Adapter,(PUINT)&sFlashCsInfo,Adapter->ulFlashControlSectionStart,sizeof(sFlashCsInfo));
2505 uiSectorSig = ntohl(sFlashCsInfo.FlashSectorSizeSig);
2506 uiCurrentSectorSize = ntohl(sFlashCsInfo.FlashSectorSize);
2508 if(uiSectorSig == FLASH_SECTOR_SIZE_SIG)
2511 if((uiCurrentSectorSize <= MAX_SECTOR_SIZE) && (uiCurrentSectorSize >= MIN_SECTOR_SIZE))
2513 if(uiSectorSize == uiCurrentSectorSize)
2515 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"Provided sector size is same as programmed in Flash");
2516 Status = STATUS_SUCCESS;
2517 goto Restore ;
2522 if((uiSectorSize <= MAX_SECTOR_SIZE) && (uiSectorSize >= MIN_SECTOR_SIZE))
2525 sFlashCsInfo.FlashSectorSize = htonl(uiSectorSize);
2526 sFlashCsInfo.FlashSectorSizeSig = htonl(FLASH_SECTOR_SIZE_SIG);
2528 Status = BeceemFlashBulkWrite(Adapter,
2529 (PUINT)&sFlashCsInfo,
2530 Adapter->ulFlashControlSectionStart,
2531 sizeof(sFlashCsInfo),
2532 TRUE);
2537 Restore :
2538 // restore the values.
2539 wrmalt(Adapter, 0x0f000C80,&uiTemp, sizeof(uiTemp));
2542 return Status;
2546 //-----------------------------------------------------------------------------
2547 // Procedure: BcmGetFlashSectorSize
2549 // Description: Finds the sector size of the FLASH.
2551 // Arguments:
2552 // Adapter - ptr to Adapter object instance
2554 // Returns:
2555 // UINT - sector size.
2557 //-----------------------------------------------------------------------------
2559 UINT BcmGetFlashSectorSize(PMINI_ADAPTER Adapter, UINT FlashSectorSizeSig, UINT FlashSectorSize)
2561 UINT uiSectorSize = 0;
2562 UINT uiSectorSig = 0;
2564 if(Adapter->bSectorSizeOverride &&
2565 (Adapter->uiSectorSizeInCFG <= MAX_SECTOR_SIZE &&
2566 Adapter->uiSectorSizeInCFG >= MIN_SECTOR_SIZE))
2568 Adapter->uiSectorSize = Adapter->uiSectorSizeInCFG;
2570 else
2573 uiSectorSig = FlashSectorSizeSig;
2575 if(uiSectorSig == FLASH_SECTOR_SIZE_SIG)
2577 uiSectorSize = FlashSectorSize;
2579 // If the sector size stored in the FLASH makes sense then use it.
2581 if(uiSectorSize <= MAX_SECTOR_SIZE && uiSectorSize >= MIN_SECTOR_SIZE)
2583 Adapter->uiSectorSize = uiSectorSize;
2585 //No valid size in FLASH, check if Config file has it.
2586 else if(Adapter->uiSectorSizeInCFG <= MAX_SECTOR_SIZE &&
2587 Adapter->uiSectorSizeInCFG >= MIN_SECTOR_SIZE)
2589 Adapter->uiSectorSize = Adapter->uiSectorSizeInCFG;
2591 // Init to Default, if none of the above works.
2592 else
2594 Adapter->uiSectorSize = DEFAULT_SECTOR_SIZE;
2598 else
2600 if(Adapter->uiSectorSizeInCFG <= MAX_SECTOR_SIZE &&
2601 Adapter->uiSectorSizeInCFG >= MIN_SECTOR_SIZE)
2603 Adapter->uiSectorSize = Adapter->uiSectorSizeInCFG;
2605 else
2607 Adapter->uiSectorSize = DEFAULT_SECTOR_SIZE;
2612 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "Sector size :%x \n", Adapter->uiSectorSize);
2613 return Adapter->uiSectorSize;
2616 //-----------------------------------------------------------------------------
2617 // Procedure: BcmInitEEPROMQueues
2619 // Description: Initialization of EEPROM queues.
2621 // Arguments:
2622 // Adapter - ptr to Adapter object instance
2624 // Returns:
2625 // <OSAL_STATUS_CODE>
2626 //-----------------------------------------------------------------------------
2628 INT BcmInitEEPROMQueues(PMINI_ADAPTER Adapter)
2630 UINT value = 0;
2631 /* CHIP Bug : Clear the Avail bits on the Read queue. The default
2632 * value on this register is supposed to be 0x00001102.
2633 * But we get 0x00001122. */
2634 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"Fixing reset value on 0x0f003004 register\n" );
2635 value = EEPROM_READ_DATA_AVAIL;
2636 wrmalt( Adapter, EEPROM_SPI_Q_STATUS1_REG, &value, sizeof(value));
2638 /* Flush the all the EEPROM queues. */
2639 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, " Flushing the queues\n");
2640 value =EEPROM_ALL_QUEUE_FLUSH ;
2641 wrmalt( Adapter, SPI_FLUSH_REG, &value, sizeof(value));
2643 value = 0;
2644 wrmalt( Adapter, SPI_FLUSH_REG, &value, sizeof(value) );
2646 /* Read the EEPROM Status Register. Just to see, no real purpose. */
2647 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "EEPROM Status register value = %x\n", ReadEEPROMStatusRegister(Adapter) );
2649 return STATUS_SUCCESS;
2650 } /* BcmInitEEPROMQueues() */
2652 //-----------------------------------------------------------------------------
2653 // Procedure: BcmInitNVM
2655 // Description: Initialization of NVM, EEPROM size,FLASH size, sector size etc.
2657 // Arguments:
2658 // Adapter - ptr to Adapter object instance
2660 // Returns:
2661 // <OSAL_STATUS_CODE>
2662 //-----------------------------------------------------------------------------
2664 INT BcmInitNVM(PMINI_ADAPTER ps_adapter)
2666 #ifdef BCM_SHM_INTERFACE
2667 #ifdef FLASH_DIRECT_ACCESS
2668 unsigned int data,data1,data2 = 1;
2669 wrm(ps_adapter, PAD_SELECT_REGISTER, &data2, 4);
2670 data1 = rdm(ps_adapter,SYS_CFG,&data,4);
2671 data1 = rdm(ps_adapter,SYS_CFG,&data,4);
2672 data2 = (data | 0x80 | 0x8000);
2673 wrm(ps_adapter,SYS_CFG, &data2,4); // over-write as Flash boot mode
2674 #endif
2675 ps_adapter->eNVMType = NVM_FLASH;
2676 #else
2677 BcmValidateNvmType(ps_adapter);
2678 BcmInitEEPROMQueues(ps_adapter);
2679 #endif
2681 if(ps_adapter->eNVMType == NVM_AUTODETECT)
2683 ps_adapter->eNVMType = BcmGetNvmType(ps_adapter);
2684 if(ps_adapter->eNVMType == NVM_UNKNOWN)
2686 BCM_DEBUG_PRINT(ps_adapter,DBG_TYPE_PRINTK, 0, 0, "NVM Type is unknown!!\n");
2689 else if(ps_adapter->eNVMType == NVM_FLASH)
2691 BcmGetFlashCSInfo(ps_adapter);
2694 BcmGetNvmSize(ps_adapter);
2696 return STATUS_SUCCESS;
2698 /***************************************************************************/
2699 /*BcmGetNvmSize : set the EEPROM or flash size in Adapter.
2701 *Input Parameter:
2702 * Adapter data structure
2703 *Return Value :
2704 * 0. means sucess;
2706 /***************************************************************************/
2708 INT BcmGetNvmSize(PMINI_ADAPTER Adapter)
2710 if(Adapter->eNVMType == NVM_EEPROM)
2712 Adapter->uiNVMDSDSize = BcmGetEEPROMSize(Adapter);
2714 else if(Adapter->eNVMType == NVM_FLASH)
2716 Adapter->uiNVMDSDSize = BcmGetFlashSize(Adapter);
2718 return 0;
2721 //-----------------------------------------------------------------------------
2722 // Procedure: BcmValidateNvm
2724 // Description: Validates the NVM Type option selected against the device
2726 // Arguments:
2727 // Adapter - ptr to Adapter object instance
2729 // Returns:
2730 // <VOID>
2731 //-----------------------------------------------------------------------------
2732 VOID BcmValidateNvmType(PMINI_ADAPTER Adapter)
2736 // if forcing the FLASH through CFG file, we should ensure device really has a FLASH.
2737 // Accessing the FLASH address without the FLASH being present can cause hang/freeze etc.
2738 // So if NVM_FLASH is selected for older chipsets, change it to AUTODETECT where EEPROM is 1st choice.
2741 if(Adapter->eNVMType == NVM_FLASH &&
2742 Adapter->chip_id < 0xBECE3300)
2744 Adapter->eNVMType = NVM_AUTODETECT;
2747 //-----------------------------------------------------------------------------
2748 // Procedure: BcmReadFlashRDID
2750 // Description: Reads ID from Serial Flash
2752 // Arguments:
2753 // Adapter - ptr to Adapter object instance
2755 // Returns:
2756 // Flash ID
2757 //-----------------------------------------------------------------------------
2758 ULONG BcmReadFlashRDID(PMINI_ADAPTER Adapter)
2760 ULONG ulRDID = 0;
2761 UINT value;
2763 // Read ID Instruction.
2765 value = (FLASH_CMD_READ_ID<<24);
2766 wrmalt(Adapter, FLASH_SPI_CMDQ_REG,&value, sizeof(value));
2768 //Delay
2769 udelay(10);
2771 // Read SPI READQ REG. The output will be WWXXYYZZ.
2772 // The ID is 3Bytes long and is WWXXYY. ZZ needs to be Ignored.
2774 rdmalt(Adapter, FLASH_SPI_READQ_REG,(PUINT)&ulRDID, sizeof(ulRDID));
2776 return (ulRDID >>8);
2781 INT BcmAllocFlashCSStructure(PMINI_ADAPTER psAdapter)
2783 if(psAdapter == NULL)
2785 BCM_DEBUG_PRINT(psAdapter,DBG_TYPE_PRINTK, 0, 0, "Adapter structure point is NULL");
2786 return -EINVAL;
2788 psAdapter->psFlashCSInfo = (PFLASH_CS_INFO)kzalloc(sizeof(FLASH_CS_INFO), GFP_KERNEL);
2789 if(psAdapter->psFlashCSInfo == NULL)
2791 BCM_DEBUG_PRINT(psAdapter,DBG_TYPE_PRINTK, 0, 0,"Can't Allocate memory for Flash 1.x");
2792 return -ENOMEM;
2795 psAdapter->psFlash2xCSInfo = (PFLASH2X_CS_INFO)kzalloc(sizeof(FLASH2X_CS_INFO), GFP_KERNEL);
2796 if(psAdapter->psFlash2xCSInfo == NULL)
2798 BCM_DEBUG_PRINT(psAdapter,DBG_TYPE_PRINTK, 0, 0,"Can't Allocate memory for Flash 2.x");
2799 bcm_kfree(psAdapter->psFlashCSInfo);
2800 return -ENOMEM;
2803 psAdapter->psFlash2xVendorInfo = (PFLASH2X_VENDORSPECIFIC_INFO)kzalloc(sizeof(FLASH2X_VENDORSPECIFIC_INFO), GFP_KERNEL);
2804 if(psAdapter->psFlash2xVendorInfo == NULL)
2806 BCM_DEBUG_PRINT(psAdapter,DBG_TYPE_PRINTK, 0, 0,"Can't Allocate Vendor Info Memory for Flash 2.x");
2807 bcm_kfree(psAdapter->psFlashCSInfo);
2808 bcm_kfree(psAdapter->psFlash2xCSInfo);
2809 return -ENOMEM;
2812 return STATUS_SUCCESS;
2815 INT BcmDeAllocFlashCSStructure(PMINI_ADAPTER psAdapter)
2817 if(psAdapter == NULL)
2819 BCM_DEBUG_PRINT(psAdapter,DBG_TYPE_PRINTK, 0, 0," Adapter structure point is NULL");
2820 return -EINVAL;
2822 bcm_kfree(psAdapter->psFlashCSInfo);
2823 bcm_kfree(psAdapter->psFlash2xCSInfo);
2824 bcm_kfree(psAdapter->psFlash2xVendorInfo);
2825 return STATUS_SUCCESS ;
2828 INT BcmDumpFlash2XCSStructure(PFLASH2X_CS_INFO psFlash2xCSInfo,PMINI_ADAPTER Adapter)
2830 UINT Index = 0;
2831 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "**********************FLASH2X CS Structure *******************");
2832 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "Signature is :%x", (psFlash2xCSInfo->MagicNumber));
2833 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "Flash Major Version :%d", MAJOR_VERSION(psFlash2xCSInfo->FlashLayoutVersion));
2834 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "Flash Minor Version :%d", MINOR_VERSION(psFlash2xCSInfo->FlashLayoutVersion));
2835 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, " ISOImageMajorVersion:0x%x", (psFlash2xCSInfo->ISOImageVersion));
2836 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "SCSIFirmwareMajorVersion :0x%x", (psFlash2xCSInfo->SCSIFirmwareVersion));
2837 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetFromZeroForPart1ISOImage :0x%x", (psFlash2xCSInfo->OffsetFromZeroForPart1ISOImage));
2838 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetFromZeroForScsiFirmware :0x%x", (psFlash2xCSInfo->OffsetFromZeroForScsiFirmware));
2839 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "SizeOfScsiFirmware :0x%x", (psFlash2xCSInfo->SizeOfScsiFirmware ));
2840 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetFromZeroForPart2ISOImage :0x%x", (psFlash2xCSInfo->OffsetFromZeroForPart2ISOImage));
2841 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetFromZeroForDSDStart :0x%x", (psFlash2xCSInfo->OffsetFromZeroForDSDStart));
2842 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetFromZeroForDSDEnd :0x%x", (psFlash2xCSInfo->OffsetFromZeroForDSDEnd));
2843 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetFromZeroForVSAStart :0x%x", (psFlash2xCSInfo->OffsetFromZeroForVSAStart));
2844 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetFromZeroForVSAEnd :0x%x", (psFlash2xCSInfo->OffsetFromZeroForVSAEnd));
2845 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetFromZeroForControlSectionStart :0x%x", (psFlash2xCSInfo->OffsetFromZeroForControlSectionStart));
2846 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetFromZeroForControlSectionData :0x%x", (psFlash2xCSInfo->OffsetFromZeroForControlSectionData));
2847 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "CDLessInactivityTimeout :0x%x", (psFlash2xCSInfo->CDLessInactivityTimeout));
2848 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "NewImageSignature :0x%x", (psFlash2xCSInfo->NewImageSignature));
2849 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "FlashSectorSizeSig :0x%x", (psFlash2xCSInfo->FlashSectorSizeSig));
2850 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "FlashSectorSize :0x%x", (psFlash2xCSInfo->FlashSectorSize));
2851 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "FlashWriteSupportSize :0x%x", (psFlash2xCSInfo->FlashWriteSupportSize));
2852 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "TotalFlashSize :0x%X", (psFlash2xCSInfo->TotalFlashSize));
2853 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "FlashBaseAddr :0x%x", (psFlash2xCSInfo->FlashBaseAddr));
2854 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "FlashPartMaxSize :0x%x", (psFlash2xCSInfo->FlashPartMaxSize));
2855 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "IsCDLessDeviceBootSig :0x%x", (psFlash2xCSInfo->IsCDLessDeviceBootSig));
2856 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "MassStorageTimeout :0x%x", (psFlash2xCSInfo->MassStorageTimeout));
2857 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetISOImage1Part1Start :0x%x", (psFlash2xCSInfo->OffsetISOImage1Part1Start));
2858 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetISOImage1Part1End :0x%x", (psFlash2xCSInfo->OffsetISOImage1Part1End));
2859 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetISOImage1Part2Start :0x%x", (psFlash2xCSInfo->OffsetISOImage1Part2Start));
2860 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetISOImage1Part2End :0x%x", (psFlash2xCSInfo->OffsetISOImage1Part2End));
2861 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetISOImage1Part3Start :0x%x", (psFlash2xCSInfo->OffsetISOImage1Part3Start));
2862 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetISOImage1Part3End :0x%x", (psFlash2xCSInfo->OffsetISOImage1Part3End));
2863 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetISOImage2Part1Start :0x%x", (psFlash2xCSInfo->OffsetISOImage2Part1Start));
2864 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetISOImage2Part1End :0x%x", (psFlash2xCSInfo->OffsetISOImage2Part1End));
2865 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetISOImage2Part2Start :0x%x", (psFlash2xCSInfo->OffsetISOImage2Part2Start));
2866 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetISOImage2Part2End :0x%x", (psFlash2xCSInfo->OffsetISOImage2Part2End));
2867 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetISOImage2Part3Start :0x%x", (psFlash2xCSInfo->OffsetISOImage2Part3Start));
2868 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetISOImage2Part3End :0x%x", (psFlash2xCSInfo->OffsetISOImage2Part3End));
2869 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetFromDSDStartForDSDHeader :0x%x", (psFlash2xCSInfo->OffsetFromDSDStartForDSDHeader));
2870 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetFromZeroForDSD1Start :0x%x", (psFlash2xCSInfo->OffsetFromZeroForDSD1Start));
2871 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetFromZeroForDSD1End :0x%x", (psFlash2xCSInfo->OffsetFromZeroForDSD1End));
2872 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetFromZeroForDSD2Start :0x%x", (psFlash2xCSInfo->OffsetFromZeroForDSD2Start));
2873 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetFromZeroForDSD2End :0x%x", (psFlash2xCSInfo->OffsetFromZeroForDSD2End));
2874 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetFromZeroForVSA1Start :0x%x", (psFlash2xCSInfo->OffsetFromZeroForVSA1Start));
2875 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetFromZeroForVSA1End :0x%x", (psFlash2xCSInfo->OffsetFromZeroForVSA1End));
2876 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetFromZeroForVSA2Start :0x%x", (psFlash2xCSInfo->OffsetFromZeroForVSA2Start));
2877 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetFromZeroForVSA2End :0x%x", (psFlash2xCSInfo->OffsetFromZeroForVSA2End));
2878 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "Sector Access Bit Map is Defined as :");
2879 for(Index =0; Index <(FLASH2X_TOTAL_SIZE/(DEFAULT_SECTOR_SIZE *16)); Index++)
2881 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "SectorAccessBitMap[%d] :0x%x", Index,
2882 (psFlash2xCSInfo->SectorAccessBitMap[Index]));
2885 return STATUS_SUCCESS;
2889 INT ConvertEndianOf2XCSStructure(PFLASH2X_CS_INFO psFlash2xCSInfo)
2891 UINT Index = 0;
2892 psFlash2xCSInfo->MagicNumber = ntohl(psFlash2xCSInfo->MagicNumber);
2893 psFlash2xCSInfo->FlashLayoutVersion= ntohl(psFlash2xCSInfo->FlashLayoutVersion);
2894 //psFlash2xCSInfo->FlashLayoutMinorVersion = ntohs(psFlash2xCSInfo->FlashLayoutMinorVersion);
2895 psFlash2xCSInfo->ISOImageVersion = ntohl(psFlash2xCSInfo->ISOImageVersion);
2896 psFlash2xCSInfo->SCSIFirmwareVersion =ntohl(psFlash2xCSInfo->SCSIFirmwareVersion);
2897 psFlash2xCSInfo->OffsetFromZeroForPart1ISOImage = ntohl(psFlash2xCSInfo->OffsetFromZeroForPart1ISOImage);
2898 psFlash2xCSInfo->OffsetFromZeroForScsiFirmware = ntohl(psFlash2xCSInfo->OffsetFromZeroForScsiFirmware);
2899 psFlash2xCSInfo->SizeOfScsiFirmware = ntohl(psFlash2xCSInfo->SizeOfScsiFirmware );
2900 psFlash2xCSInfo->OffsetFromZeroForPart2ISOImage = ntohl(psFlash2xCSInfo->OffsetFromZeroForPart2ISOImage);
2901 psFlash2xCSInfo->OffsetFromZeroForDSDStart = ntohl(psFlash2xCSInfo->OffsetFromZeroForDSDStart);
2902 psFlash2xCSInfo->OffsetFromZeroForDSDEnd = ntohl(psFlash2xCSInfo->OffsetFromZeroForDSDEnd);
2903 psFlash2xCSInfo->OffsetFromZeroForVSAStart = ntohl(psFlash2xCSInfo->OffsetFromZeroForVSAStart);
2904 psFlash2xCSInfo->OffsetFromZeroForVSAEnd = ntohl(psFlash2xCSInfo->OffsetFromZeroForVSAEnd);
2905 psFlash2xCSInfo->OffsetFromZeroForControlSectionStart = ntohl(psFlash2xCSInfo->OffsetFromZeroForControlSectionStart);
2906 psFlash2xCSInfo->OffsetFromZeroForControlSectionData = ntohl(psFlash2xCSInfo->OffsetFromZeroForControlSectionData);
2907 psFlash2xCSInfo->CDLessInactivityTimeout = ntohl(psFlash2xCSInfo->CDLessInactivityTimeout);
2908 psFlash2xCSInfo->NewImageSignature = ntohl(psFlash2xCSInfo->NewImageSignature);
2909 psFlash2xCSInfo->FlashSectorSizeSig = ntohl(psFlash2xCSInfo->FlashSectorSizeSig);
2910 psFlash2xCSInfo->FlashSectorSize = ntohl(psFlash2xCSInfo->FlashSectorSize);
2911 psFlash2xCSInfo->FlashWriteSupportSize = ntohl(psFlash2xCSInfo->FlashWriteSupportSize);
2912 psFlash2xCSInfo->TotalFlashSize = ntohl(psFlash2xCSInfo->TotalFlashSize);
2913 psFlash2xCSInfo->FlashBaseAddr = ntohl(psFlash2xCSInfo->FlashBaseAddr);
2914 psFlash2xCSInfo->FlashPartMaxSize = ntohl(psFlash2xCSInfo->FlashPartMaxSize);
2915 psFlash2xCSInfo->IsCDLessDeviceBootSig = ntohl(psFlash2xCSInfo->IsCDLessDeviceBootSig);
2916 psFlash2xCSInfo->MassStorageTimeout = ntohl(psFlash2xCSInfo->MassStorageTimeout);
2917 psFlash2xCSInfo->OffsetISOImage1Part1Start = ntohl(psFlash2xCSInfo->OffsetISOImage1Part1Start);
2918 psFlash2xCSInfo->OffsetISOImage1Part1End = ntohl(psFlash2xCSInfo->OffsetISOImage1Part1End);
2919 psFlash2xCSInfo->OffsetISOImage1Part2Start = ntohl(psFlash2xCSInfo->OffsetISOImage1Part2Start);
2920 psFlash2xCSInfo->OffsetISOImage1Part2End = ntohl(psFlash2xCSInfo->OffsetISOImage1Part2End);
2921 psFlash2xCSInfo->OffsetISOImage1Part3Start = ntohl(psFlash2xCSInfo->OffsetISOImage1Part3Start);
2922 psFlash2xCSInfo->OffsetISOImage1Part3End = ntohl(psFlash2xCSInfo->OffsetISOImage1Part3End);
2923 psFlash2xCSInfo->OffsetISOImage2Part1Start = ntohl(psFlash2xCSInfo->OffsetISOImage2Part1Start);
2924 psFlash2xCSInfo->OffsetISOImage2Part1End = ntohl(psFlash2xCSInfo->OffsetISOImage2Part1End);
2925 psFlash2xCSInfo->OffsetISOImage2Part2Start = ntohl(psFlash2xCSInfo->OffsetISOImage2Part2Start);
2926 psFlash2xCSInfo->OffsetISOImage2Part2End = ntohl(psFlash2xCSInfo->OffsetISOImage2Part2End);
2927 psFlash2xCSInfo->OffsetISOImage2Part3Start = ntohl(psFlash2xCSInfo->OffsetISOImage2Part3Start);
2928 psFlash2xCSInfo->OffsetISOImage2Part3End = ntohl(psFlash2xCSInfo->OffsetISOImage2Part3End);
2929 psFlash2xCSInfo->OffsetFromDSDStartForDSDHeader = ntohl(psFlash2xCSInfo->OffsetFromDSDStartForDSDHeader);
2930 psFlash2xCSInfo->OffsetFromZeroForDSD1Start = ntohl(psFlash2xCSInfo->OffsetFromZeroForDSD1Start);
2931 psFlash2xCSInfo->OffsetFromZeroForDSD1End = ntohl(psFlash2xCSInfo->OffsetFromZeroForDSD1End);
2932 psFlash2xCSInfo->OffsetFromZeroForDSD2Start = ntohl(psFlash2xCSInfo->OffsetFromZeroForDSD2Start);
2933 psFlash2xCSInfo->OffsetFromZeroForDSD2End = ntohl(psFlash2xCSInfo->OffsetFromZeroForDSD2End);
2934 psFlash2xCSInfo->OffsetFromZeroForVSA1Start = ntohl(psFlash2xCSInfo->OffsetFromZeroForVSA1Start);
2935 psFlash2xCSInfo->OffsetFromZeroForVSA1End = ntohl(psFlash2xCSInfo->OffsetFromZeroForVSA1End);
2936 psFlash2xCSInfo->OffsetFromZeroForVSA2Start = ntohl(psFlash2xCSInfo->OffsetFromZeroForVSA2Start);
2937 psFlash2xCSInfo->OffsetFromZeroForVSA2End = ntohl(psFlash2xCSInfo->OffsetFromZeroForVSA2End);
2938 for(Index =0; Index <(FLASH2X_TOTAL_SIZE/(DEFAULT_SECTOR_SIZE *16)); Index++)
2940 psFlash2xCSInfo->SectorAccessBitMap[Index] = ntohl(psFlash2xCSInfo->SectorAccessBitMap[Index]);
2942 return STATUS_SUCCESS;
2945 INT ConvertEndianOfCSStructure(PFLASH_CS_INFO psFlashCSInfo)
2947 //UINT Index = 0;
2948 psFlashCSInfo->MagicNumber =ntohl(psFlashCSInfo->MagicNumber);
2949 psFlashCSInfo->FlashLayoutVersion =ntohl(psFlashCSInfo->FlashLayoutVersion);
2950 psFlashCSInfo->ISOImageVersion = ntohl(psFlashCSInfo->ISOImageVersion);
2951 //won't convert according to old assumption
2952 psFlashCSInfo->SCSIFirmwareVersion =(psFlashCSInfo->SCSIFirmwareVersion);
2954 psFlashCSInfo->OffsetFromZeroForPart1ISOImage = ntohl(psFlashCSInfo->OffsetFromZeroForPart1ISOImage);
2955 psFlashCSInfo->OffsetFromZeroForScsiFirmware = ntohl(psFlashCSInfo->OffsetFromZeroForScsiFirmware);
2956 psFlashCSInfo->SizeOfScsiFirmware = ntohl(psFlashCSInfo->SizeOfScsiFirmware );
2957 psFlashCSInfo->OffsetFromZeroForPart2ISOImage = ntohl(psFlashCSInfo->OffsetFromZeroForPart2ISOImage);
2958 psFlashCSInfo->OffsetFromZeroForCalibrationStart = ntohl(psFlashCSInfo->OffsetFromZeroForCalibrationStart);
2959 psFlashCSInfo->OffsetFromZeroForCalibrationEnd = ntohl(psFlashCSInfo->OffsetFromZeroForCalibrationEnd);
2960 psFlashCSInfo->OffsetFromZeroForVSAStart = ntohl(psFlashCSInfo->OffsetFromZeroForVSAStart);
2961 psFlashCSInfo->OffsetFromZeroForVSAEnd = ntohl(psFlashCSInfo->OffsetFromZeroForVSAEnd);
2962 psFlashCSInfo->OffsetFromZeroForControlSectionStart = ntohl(psFlashCSInfo->OffsetFromZeroForControlSectionStart);
2963 psFlashCSInfo->OffsetFromZeroForControlSectionData = ntohl(psFlashCSInfo->OffsetFromZeroForControlSectionData);
2964 psFlashCSInfo->CDLessInactivityTimeout = ntohl(psFlashCSInfo->CDLessInactivityTimeout);
2965 psFlashCSInfo->NewImageSignature = ntohl(psFlashCSInfo->NewImageSignature);
2966 psFlashCSInfo->FlashSectorSizeSig = ntohl(psFlashCSInfo->FlashSectorSizeSig);
2967 psFlashCSInfo->FlashSectorSize = ntohl(psFlashCSInfo->FlashSectorSize);
2968 psFlashCSInfo->FlashWriteSupportSize = ntohl(psFlashCSInfo->FlashWriteSupportSize);
2969 psFlashCSInfo->TotalFlashSize = ntohl(psFlashCSInfo->TotalFlashSize);
2970 psFlashCSInfo->FlashBaseAddr = ntohl(psFlashCSInfo->FlashBaseAddr);
2971 psFlashCSInfo->FlashPartMaxSize = ntohl(psFlashCSInfo->FlashPartMaxSize);
2972 psFlashCSInfo->IsCDLessDeviceBootSig = ntohl(psFlashCSInfo->IsCDLessDeviceBootSig);
2973 psFlashCSInfo->MassStorageTimeout = ntohl(psFlashCSInfo->MassStorageTimeout);
2975 return STATUS_SUCCESS;
2978 INT IsSectionExistInVendorInfo(PMINI_ADAPTER Adapter, FLASH2X_SECTION_VAL section)
2980 return ( Adapter->uiVendorExtnFlag &&
2981 (Adapter->psFlash2xVendorInfo->VendorSection[section].AccessFlags & FLASH2X_SECTION_PRESENT) &&
2982 (Adapter->psFlash2xVendorInfo->VendorSection[section].OffsetFromZeroForSectionStart != UNINIT_PTR_IN_CS) );
2985 VOID UpdateVendorInfo(PMINI_ADAPTER Adapter)
2987 B_UINT32 i = 0;
2988 UINT uiSizeSection = 0;
2990 Adapter->uiVendorExtnFlag = FALSE;
2992 for(i = 0;i < TOTAL_SECTIONS;i++)
2993 Adapter->psFlash2xVendorInfo->VendorSection[i].OffsetFromZeroForSectionStart = UNINIT_PTR_IN_CS;
2995 if(STATUS_SUCCESS != vendorextnGetSectionInfo(Adapter, Adapter->psFlash2xVendorInfo))
2996 return;
2998 i = 0;
2999 while(i < TOTAL_SECTIONS)
3001 if(!(Adapter->psFlash2xVendorInfo->VendorSection[i].AccessFlags & FLASH2X_SECTION_PRESENT))
3003 i++;
3004 continue;
3007 Adapter->uiVendorExtnFlag = TRUE;
3008 uiSizeSection = (Adapter->psFlash2xVendorInfo->VendorSection[i].OffsetFromZeroForSectionEnd -
3009 Adapter->psFlash2xVendorInfo->VendorSection[i].OffsetFromZeroForSectionStart);
3011 switch(i)
3013 case DSD0:
3014 if(( uiSizeSection >= (Adapter->psFlash2xCSInfo->OffsetFromDSDStartForDSDHeader + sizeof(DSD_HEADER))) &&
3015 (UNINIT_PTR_IN_CS != Adapter->psFlash2xVendorInfo->VendorSection[i].OffsetFromZeroForSectionStart))
3016 Adapter->psFlash2xCSInfo->OffsetFromZeroForDSDStart = Adapter->psFlash2xCSInfo->OffsetFromZeroForDSDEnd = VENDOR_PTR_IN_CS;
3017 else
3018 Adapter->psFlash2xCSInfo->OffsetFromZeroForDSDStart = Adapter->psFlash2xCSInfo->OffsetFromZeroForDSDEnd = UNINIT_PTR_IN_CS;
3019 break;
3021 case DSD1:
3022 if(( uiSizeSection >= (Adapter->psFlash2xCSInfo->OffsetFromDSDStartForDSDHeader + sizeof(DSD_HEADER))) &&
3023 (UNINIT_PTR_IN_CS != Adapter->psFlash2xVendorInfo->VendorSection[i].OffsetFromZeroForSectionStart))
3024 Adapter->psFlash2xCSInfo->OffsetFromZeroForDSD1Start = Adapter->psFlash2xCSInfo->OffsetFromZeroForDSD1End = VENDOR_PTR_IN_CS;
3025 else
3026 Adapter->psFlash2xCSInfo->OffsetFromZeroForDSD1Start = Adapter->psFlash2xCSInfo->OffsetFromZeroForDSD1End = UNINIT_PTR_IN_CS;
3027 break;
3029 case DSD2:
3030 if(( uiSizeSection >= (Adapter->psFlash2xCSInfo->OffsetFromDSDStartForDSDHeader + sizeof(DSD_HEADER))) &&
3031 (UNINIT_PTR_IN_CS != Adapter->psFlash2xVendorInfo->VendorSection[i].OffsetFromZeroForSectionStart))
3032 Adapter->psFlash2xCSInfo->OffsetFromZeroForDSD2Start = Adapter->psFlash2xCSInfo->OffsetFromZeroForDSD2End = VENDOR_PTR_IN_CS;
3033 else
3034 Adapter->psFlash2xCSInfo->OffsetFromZeroForDSD2Start = Adapter->psFlash2xCSInfo->OffsetFromZeroForDSD2End = UNINIT_PTR_IN_CS;
3035 break;
3036 case VSA0:
3037 if(UNINIT_PTR_IN_CS != Adapter->psFlash2xVendorInfo->VendorSection[i].OffsetFromZeroForSectionStart)
3038 Adapter->psFlash2xCSInfo->OffsetFromZeroForVSAStart = Adapter->psFlash2xCSInfo->OffsetFromZeroForVSAEnd = VENDOR_PTR_IN_CS;
3039 else
3040 Adapter->psFlash2xCSInfo->OffsetFromZeroForVSAStart = Adapter->psFlash2xCSInfo->OffsetFromZeroForVSAEnd = UNINIT_PTR_IN_CS;
3041 break;
3043 case VSA1:
3044 if(UNINIT_PTR_IN_CS != Adapter->psFlash2xVendorInfo->VendorSection[i].OffsetFromZeroForSectionStart)
3045 Adapter->psFlash2xCSInfo->OffsetFromZeroForVSA1Start = Adapter->psFlash2xCSInfo->OffsetFromZeroForVSA1End = VENDOR_PTR_IN_CS;
3046 else
3047 Adapter->psFlash2xCSInfo->OffsetFromZeroForVSA1Start = Adapter->psFlash2xCSInfo->OffsetFromZeroForVSA1End = UNINIT_PTR_IN_CS;
3048 break;
3049 case VSA2:
3050 if(UNINIT_PTR_IN_CS != Adapter->psFlash2xVendorInfo->VendorSection[i].OffsetFromZeroForSectionStart)
3051 Adapter->psFlash2xCSInfo->OffsetFromZeroForVSA2Start = Adapter->psFlash2xCSInfo->OffsetFromZeroForVSA2End = VENDOR_PTR_IN_CS;
3052 else
3053 Adapter->psFlash2xCSInfo->OffsetFromZeroForVSA2Start = Adapter->psFlash2xCSInfo->OffsetFromZeroForVSA2End = UNINIT_PTR_IN_CS;
3054 break;
3056 default:
3057 break;
3059 i++;
3064 //-----------------------------------------------------------------------------
3065 // Procedure: BcmGetFlashCSInfo
3067 // Description: Reads control structure and gets Cal section addresses.
3069 // Arguments:
3070 // Adapter - ptr to Adapter object instance
3072 // Returns:
3073 // <VOID>
3074 //-----------------------------------------------------------------------------
3076 INT BcmGetFlashCSInfo(PMINI_ADAPTER Adapter)
3078 //FLASH_CS_INFO sFlashCsInfo = {0};
3080 #if !defined(BCM_SHM_INTERFACE) || defined(FLASH_DIRECT_ACCESS)
3081 UINT value;
3082 #endif
3083 UINT uiFlashLayoutMajorVersion;
3084 Adapter->uiFlashLayoutMinorVersion = 0;
3085 Adapter->uiFlashLayoutMajorVersion = 0;
3086 Adapter->ulFlashControlSectionStart = FLASH_CS_INFO_START_ADDR;
3089 Adapter->uiFlashBaseAdd = 0;
3090 Adapter->ulFlashCalStart = 0;
3091 memset(Adapter->psFlashCSInfo, 0 ,sizeof(FLASH_CS_INFO));
3092 memset(Adapter->psFlash2xCSInfo, 0 ,sizeof(FLASH2X_CS_INFO));
3094 #ifndef BCM_SHM_INTERFACE
3095 if(!Adapter->bDDRInitDone)
3098 value = FLASH_CONTIGIOUS_START_ADDR_BEFORE_INIT;
3099 wrmalt(Adapter, 0xAF00A080, &value, sizeof(value));
3103 #endif
3105 // Reading first 8 Bytes to get the Flash Layout
3106 // MagicNumber(4 bytes) +FlashLayoutMinorVersion(2 Bytes) +FlashLayoutMajorVersion(2 Bytes)
3107 BeceemFlashBulkRead(Adapter,(PUINT)Adapter->psFlashCSInfo,Adapter->ulFlashControlSectionStart,8);
3109 Adapter->psFlashCSInfo->FlashLayoutVersion = ntohl(Adapter->psFlashCSInfo->FlashLayoutVersion);
3110 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "Flash Layout Version :%X", (Adapter->psFlashCSInfo->FlashLayoutVersion));
3111 //BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "Flash Layout Minor Version :%d\n", ntohs(sFlashCsInfo.FlashLayoutMinorVersion));
3112 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "Signature is :%x\n", ntohl(Adapter->psFlashCSInfo->MagicNumber));
3114 if(FLASH_CONTROL_STRUCT_SIGNATURE == ntohl(Adapter->psFlashCSInfo->MagicNumber))
3116 uiFlashLayoutMajorVersion = MAJOR_VERSION((Adapter->psFlashCSInfo->FlashLayoutVersion));
3117 Adapter->uiFlashLayoutMinorVersion = MINOR_VERSION((Adapter->psFlashCSInfo->FlashLayoutVersion));
3119 else
3121 Adapter->uiFlashLayoutMinorVersion = 0;
3122 uiFlashLayoutMajorVersion = 0;
3125 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"FLASH LAYOUT MAJOR VERSION :%X", uiFlashLayoutMajorVersion);
3127 if(uiFlashLayoutMajorVersion < FLASH_2X_MAJOR_NUMBER)
3129 BeceemFlashBulkRead(Adapter,(PUINT)Adapter->psFlashCSInfo,Adapter->ulFlashControlSectionStart,sizeof(FLASH_CS_INFO));
3130 ConvertEndianOfCSStructure(Adapter->psFlashCSInfo);
3131 Adapter->ulFlashCalStart = (Adapter->psFlashCSInfo->OffsetFromZeroForCalibrationStart);
3133 if(!((Adapter->uiFlashLayoutMajorVersion == 1) && (Adapter->uiFlashLayoutMinorVersion == 1)))
3135 Adapter->ulFlashControlSectionStart = Adapter->psFlashCSInfo->OffsetFromZeroForControlSectionStart;
3138 if((FLASH_CONTROL_STRUCT_SIGNATURE == (Adapter->psFlashCSInfo->MagicNumber)) &&
3139 (SCSI_FIRMWARE_MINOR_VERSION <= MINOR_VERSION(Adapter->psFlashCSInfo->SCSIFirmwareVersion)) &&
3140 (FLASH_SECTOR_SIZE_SIG == (Adapter->psFlashCSInfo->FlashSectorSizeSig)) &&
3141 (BYTE_WRITE_SUPPORT == (Adapter->psFlashCSInfo->FlashWriteSupportSize)))
3143 Adapter->ulFlashWriteSize = (Adapter->psFlashCSInfo->FlashWriteSupportSize);
3144 Adapter->fpFlashWrite = flashByteWrite;
3145 Adapter->fpFlashWriteWithStatusCheck = flashByteWriteStatus;
3147 else
3149 Adapter->ulFlashWriteSize = MAX_RW_SIZE;
3150 Adapter->fpFlashWrite = flashWrite;
3151 Adapter->fpFlashWriteWithStatusCheck = flashWriteStatus;
3154 BcmGetFlashSectorSize(Adapter, (Adapter->psFlashCSInfo->FlashSectorSizeSig),
3155 (Adapter->psFlashCSInfo->FlashSectorSize));
3158 Adapter->uiFlashBaseAdd = Adapter->psFlashCSInfo->FlashBaseAddr & 0xFCFFFFFF;
3162 else
3164 if(BcmFlash2xBulkRead(Adapter,(PUINT)Adapter->psFlash2xCSInfo,NO_SECTION_VAL,
3165 Adapter->ulFlashControlSectionStart,sizeof(FLASH2X_CS_INFO)))
3167 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "Unable to read CS structure \n");
3168 return STATUS_FAILURE;
3170 ConvertEndianOf2XCSStructure(Adapter->psFlash2xCSInfo);
3171 #ifndef BCM_SHM_INTERFACE
3172 BcmDumpFlash2XCSStructure(Adapter->psFlash2xCSInfo,Adapter);
3173 #endif
3174 if((FLASH_CONTROL_STRUCT_SIGNATURE == Adapter->psFlash2xCSInfo->MagicNumber) &&
3175 (SCSI_FIRMWARE_MINOR_VERSION <= MINOR_VERSION(Adapter->psFlash2xCSInfo->SCSIFirmwareVersion)) &&
3176 (FLASH_SECTOR_SIZE_SIG == Adapter->psFlash2xCSInfo->FlashSectorSizeSig) &&
3177 (BYTE_WRITE_SUPPORT == Adapter->psFlash2xCSInfo->FlashWriteSupportSize))
3179 Adapter->ulFlashWriteSize = Adapter->psFlash2xCSInfo->FlashWriteSupportSize;
3180 Adapter->fpFlashWrite = flashByteWrite;
3181 Adapter->fpFlashWriteWithStatusCheck = flashByteWriteStatus;
3183 else
3185 Adapter->ulFlashWriteSize = MAX_RW_SIZE;
3186 Adapter->fpFlashWrite = flashWrite;
3187 Adapter->fpFlashWriteWithStatusCheck = flashWriteStatus;
3190 BcmGetFlashSectorSize(Adapter, Adapter->psFlash2xCSInfo->FlashSectorSizeSig,
3191 Adapter->psFlash2xCSInfo->FlashSectorSize);
3193 UpdateVendorInfo(Adapter);
3195 BcmGetActiveDSD(Adapter);
3196 BcmGetActiveISO(Adapter);
3197 Adapter->uiFlashBaseAdd = Adapter->psFlash2xCSInfo->FlashBaseAddr & 0xFCFFFFFF;
3198 Adapter->ulFlashControlSectionStart = Adapter->psFlash2xCSInfo->OffsetFromZeroForControlSectionStart;
3202 Concerns: what if CS sector size does not match with this sector size ???
3203 what is the indication of AccessBitMap in CS in flash 2.x ????
3205 #ifndef BCM_SHM_INTERFACE
3206 Adapter->ulFlashID = BcmReadFlashRDID(Adapter);
3207 #endif
3209 Adapter->uiFlashLayoutMajorVersion = uiFlashLayoutMajorVersion;
3211 #if 0
3212 if(FLASH_PART_SST25VF080B == Adapter->ulFlashID)
3215 // 1MB flash has been selected. we have to use 64K as sector size no matter what is kept in FLASH_CS.
3217 Adapter->uiSectorSize = 0x10000;
3219 #endif
3221 return STATUS_SUCCESS ;
3225 //-----------------------------------------------------------------------------
3226 // Procedure: BcmGetNvmType
3228 // Description: Finds the type of NVM used.
3230 // Arguments:
3231 // Adapter - ptr to Adapter object instance
3233 // Returns:
3234 // NVM_TYPE
3236 //-----------------------------------------------------------------------------
3238 NVM_TYPE BcmGetNvmType(PMINI_ADAPTER Adapter)
3240 UINT uiData = 0;
3242 BeceemEEPROMBulkRead(Adapter,&uiData,0x0,4);
3243 if(uiData == BECM)
3245 return NVM_EEPROM;
3248 // Read control struct and get cal addresses before accessing the flash
3250 BcmGetFlashCSInfo(Adapter);
3252 BeceemFlashBulkRead(Adapter,&uiData,0x0 + Adapter->ulFlashCalStart,4);
3253 if(uiData == BECM)
3255 return NVM_FLASH;
3258 // even if there is no valid signature on EEPROM/FLASH find out if they really exist.
3259 // if exist select it.
3261 if(BcmGetEEPROMSize(Adapter))
3263 return NVM_EEPROM;
3266 //TBD for Flash.
3269 return NVM_UNKNOWN;
3273 * BcmGetSectionValStartOffset - this will calculate the section's starting offset if section val is given
3274 * @Adapter : Drivers Private Data structure
3275 * @eFlashSectionVal : Flash secion value defined in enum FLASH2X_SECTION_VAL
3277 * Return value:-
3278 * On success it return the start offset of the provided section val
3279 * On Failure -returns STATUS_FAILURE
3282 INT BcmGetSectionValStartOffset(PMINI_ADAPTER Adapter, FLASH2X_SECTION_VAL eFlashSectionVal)
3285 * Considering all the section for which end offset can be calculated or directly given
3286 * in CS Structure. if matching case does not exist, return STATUS_FAILURE indicating section
3287 * endoffset can't be calculated or given in CS Stucture.
3290 INT SectStartOffset = 0 ;
3292 SectStartOffset = INVALID_OFFSET ;
3294 if(IsSectionExistInVendorInfo(Adapter,eFlashSectionVal))
3296 return Adapter->psFlash2xVendorInfo->VendorSection[eFlashSectionVal].OffsetFromZeroForSectionStart;
3299 switch(eFlashSectionVal)
3301 case ISO_IMAGE1 :
3302 if((Adapter->psFlash2xCSInfo->OffsetISOImage1Part1Start != UNINIT_PTR_IN_CS) &&
3303 (IsNonCDLessDevice(Adapter) == FALSE))
3304 SectStartOffset = (Adapter->psFlash2xCSInfo->OffsetISOImage1Part1Start);
3305 break;
3306 case ISO_IMAGE2 :
3307 if((Adapter->psFlash2xCSInfo->OffsetISOImage2Part1Start != UNINIT_PTR_IN_CS) &&
3308 (IsNonCDLessDevice(Adapter) == FALSE))
3309 SectStartOffset = (Adapter->psFlash2xCSInfo->OffsetISOImage2Part1Start);
3310 break;
3311 case DSD0 :
3312 if(Adapter->psFlash2xCSInfo->OffsetFromZeroForDSDStart != UNINIT_PTR_IN_CS)
3313 SectStartOffset = (Adapter->psFlash2xCSInfo->OffsetFromZeroForDSDStart);
3314 break;
3315 case DSD1 :
3316 if(Adapter->psFlash2xCSInfo->OffsetFromZeroForDSD1Start != UNINIT_PTR_IN_CS)
3317 SectStartOffset = (Adapter->psFlash2xCSInfo->OffsetFromZeroForDSD1Start);
3318 break;
3319 case DSD2 :
3320 if(Adapter->psFlash2xCSInfo->OffsetFromZeroForDSD2Start != UNINIT_PTR_IN_CS)
3321 SectStartOffset = (Adapter->psFlash2xCSInfo->OffsetFromZeroForDSD2Start);
3322 break;
3323 case VSA0 :
3324 if(Adapter->psFlash2xCSInfo->OffsetFromZeroForVSAStart != UNINIT_PTR_IN_CS)
3325 SectStartOffset = (Adapter->psFlash2xCSInfo->OffsetFromZeroForVSAStart);
3326 break;
3327 case VSA1 :
3328 if(Adapter->psFlash2xCSInfo->OffsetFromZeroForVSA1Start != UNINIT_PTR_IN_CS)
3329 SectStartOffset = (Adapter->psFlash2xCSInfo->OffsetFromZeroForVSA1Start);
3330 break;
3331 case VSA2 :
3332 if(Adapter->psFlash2xCSInfo->OffsetFromZeroForVSA2Start != UNINIT_PTR_IN_CS)
3333 SectStartOffset = (Adapter->psFlash2xCSInfo->OffsetFromZeroForVSA2Start);
3334 break;
3335 case SCSI :
3336 if(Adapter->psFlash2xCSInfo->OffsetFromZeroForScsiFirmware != UNINIT_PTR_IN_CS)
3337 SectStartOffset = (Adapter->psFlash2xCSInfo->OffsetFromZeroForScsiFirmware);
3338 break;
3339 case CONTROL_SECTION :
3340 if(Adapter->psFlash2xCSInfo->OffsetFromZeroForControlSectionStart != UNINIT_PTR_IN_CS)
3341 SectStartOffset = (Adapter->psFlash2xCSInfo->OffsetFromZeroForControlSectionStart);
3342 break;
3343 case ISO_IMAGE1_PART2 :
3344 if(Adapter->psFlash2xCSInfo->OffsetISOImage1Part2Start != UNINIT_PTR_IN_CS)
3345 SectStartOffset = (Adapter->psFlash2xCSInfo->OffsetISOImage1Part2Start);
3346 break;
3347 case ISO_IMAGE1_PART3 :
3348 if(Adapter->psFlash2xCSInfo->OffsetISOImage1Part3Start != UNINIT_PTR_IN_CS)
3349 SectStartOffset = (Adapter->psFlash2xCSInfo->OffsetISOImage1Part3Start);
3350 break;
3351 case ISO_IMAGE2_PART2 :
3352 if(Adapter->psFlash2xCSInfo->OffsetISOImage2Part2Start != UNINIT_PTR_IN_CS)
3353 SectStartOffset = (Adapter->psFlash2xCSInfo->OffsetISOImage2Part2Start);
3354 break;
3355 case ISO_IMAGE2_PART3 :
3356 if(Adapter->psFlash2xCSInfo->OffsetISOImage2Part3Start != UNINIT_PTR_IN_CS)
3357 SectStartOffset = (Adapter->psFlash2xCSInfo->OffsetISOImage2Part3Start);
3358 break;
3359 default :
3360 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Section Does not exist in Flash 2.x");
3361 SectStartOffset = INVALID_OFFSET;
3363 return SectStartOffset;
3367 * BcmGetSectionValEndOffset - this will calculate the section's Ending offset if section val is given
3368 * @Adapter : Drivers Private Data structure
3369 * @eFlashSectionVal : Flash secion value defined in enum FLASH2X_SECTION_VAL
3371 * Return value:-
3372 * On success it return the end offset of the provided section val
3373 * On Failure -returns STATUS_FAILURE
3376 INT BcmGetSectionValEndOffset(PMINI_ADAPTER Adapter, FLASH2X_SECTION_VAL eFlash2xSectionVal)
3378 INT SectEndOffset = 0 ;
3379 SectEndOffset = INVALID_OFFSET;
3381 if(IsSectionExistInVendorInfo(Adapter,eFlash2xSectionVal))
3383 return Adapter->psFlash2xVendorInfo->VendorSection[eFlash2xSectionVal].OffsetFromZeroForSectionEnd;
3386 switch(eFlash2xSectionVal)
3388 case ISO_IMAGE1 :
3389 if((Adapter->psFlash2xCSInfo->OffsetISOImage1Part1End!= UNINIT_PTR_IN_CS) &&
3390 (IsNonCDLessDevice(Adapter) == FALSE))
3391 SectEndOffset = (Adapter->psFlash2xCSInfo->OffsetISOImage1Part1End);
3392 break;
3393 case ISO_IMAGE2 :
3394 if((Adapter->psFlash2xCSInfo->OffsetISOImage2Part1End!= UNINIT_PTR_IN_CS) &&
3395 (IsNonCDLessDevice(Adapter) == FALSE))
3396 SectEndOffset = (Adapter->psFlash2xCSInfo->OffsetISOImage2Part1End);
3397 break;
3398 case DSD0 :
3399 if(Adapter->psFlash2xCSInfo->OffsetFromZeroForDSDEnd != UNINIT_PTR_IN_CS)
3400 SectEndOffset = (Adapter->psFlash2xCSInfo->OffsetFromZeroForDSDEnd);
3401 break;
3402 case DSD1 :
3403 if(Adapter->psFlash2xCSInfo->OffsetFromZeroForDSD1End != UNINIT_PTR_IN_CS)
3404 SectEndOffset = (Adapter->psFlash2xCSInfo->OffsetFromZeroForDSD1End);
3405 break;
3406 case DSD2 :
3407 if(Adapter->psFlash2xCSInfo->OffsetFromZeroForDSD2End != UNINIT_PTR_IN_CS)
3408 SectEndOffset = (Adapter->psFlash2xCSInfo->OffsetFromZeroForDSD2End);
3409 break;
3410 case VSA0 :
3411 if(Adapter->psFlash2xCSInfo->OffsetFromZeroForVSAEnd != UNINIT_PTR_IN_CS)
3412 SectEndOffset = (Adapter->psFlash2xCSInfo->OffsetFromZeroForVSAEnd);
3413 break;
3414 case VSA1 :
3415 if(Adapter->psFlash2xCSInfo->OffsetFromZeroForVSA1End != UNINIT_PTR_IN_CS)
3416 SectEndOffset = (Adapter->psFlash2xCSInfo->OffsetFromZeroForVSA1End);
3417 break;
3418 case VSA2 :
3419 if(Adapter->psFlash2xCSInfo->OffsetFromZeroForVSA2End != UNINIT_PTR_IN_CS)
3420 SectEndOffset = (Adapter->psFlash2xCSInfo->OffsetFromZeroForVSA2End);
3421 break;
3422 case SCSI :
3423 if(Adapter->psFlash2xCSInfo->OffsetFromZeroForScsiFirmware != UNINIT_PTR_IN_CS)
3424 SectEndOffset = ((Adapter->psFlash2xCSInfo->OffsetFromZeroForScsiFirmware) +
3425 (Adapter->psFlash2xCSInfo->SizeOfScsiFirmware));
3426 break;
3427 case CONTROL_SECTION :
3428 //Not Clear So Putting failure. confirm and fix it.
3429 SectEndOffset = STATUS_FAILURE;
3430 case ISO_IMAGE1_PART2 :
3431 if(Adapter->psFlash2xCSInfo->OffsetISOImage1Part2End!= UNINIT_PTR_IN_CS)
3432 SectEndOffset = (Adapter->psFlash2xCSInfo->OffsetISOImage1Part2End);
3433 break;
3434 case ISO_IMAGE1_PART3 :
3435 if(Adapter->psFlash2xCSInfo->OffsetISOImage1Part3End!= UNINIT_PTR_IN_CS)
3436 SectEndOffset = (Adapter->psFlash2xCSInfo->OffsetISOImage1Part3End);
3437 break;
3438 case ISO_IMAGE2_PART2 :
3439 if(Adapter->psFlash2xCSInfo->OffsetISOImage2Part2End != UNINIT_PTR_IN_CS)
3440 SectEndOffset = (Adapter->psFlash2xCSInfo->OffsetISOImage2Part2End);
3441 break;
3442 case ISO_IMAGE2_PART3 :
3443 if(Adapter->psFlash2xCSInfo->OffsetISOImage2Part3End!= UNINIT_PTR_IN_CS)
3444 SectEndOffset = (Adapter->psFlash2xCSInfo->OffsetISOImage2Part3End);
3445 break;
3447 default :
3448 SectEndOffset = INVALID_OFFSET;
3450 return SectEndOffset ;
3454 * BcmFlash2xBulkRead:- Read API for Flash Map 2.x .
3455 * @Adapter :Driver Private Data Structure
3456 * @pBuffer : Buffer where data has to be put after reading
3457 * @eFlashSectionVal :Flash Section Val defined in FLASH2X_SECTION_VAL
3458 * @uiOffsetWithinSectionVal :- Offset with in provided section
3459 * @uiNumBytes : Number of Bytes for Read
3461 * Return value:-
3462 * return true on sucess and STATUS_FAILURE on fail.
3465 INT BcmFlash2xBulkRead(
3466 PMINI_ADAPTER Adapter,
3467 PUINT pBuffer,
3468 FLASH2X_SECTION_VAL eFlash2xSectionVal,
3469 UINT uiOffsetWithinSectionVal,
3470 UINT uiNumBytes)
3473 INT Status = STATUS_SUCCESS;
3474 INT SectionStartOffset = 0;
3475 UINT uiAbsoluteOffset = 0 ;
3476 UINT uiTemp =0, value =0 ;
3477 if(Adapter == NULL)
3479 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "Adapter structure is NULL");
3480 return -EINVAL;
3482 if(Adapter->device_removed )
3484 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "Device has been removed");
3485 return -ENODEV;
3488 //NO_SECTION_VAL means absolute offset is given.
3489 if(eFlash2xSectionVal == NO_SECTION_VAL)
3490 SectionStartOffset = 0;
3491 else
3492 SectionStartOffset = BcmGetSectionValStartOffset(Adapter,eFlash2xSectionVal);
3494 if(SectionStartOffset == STATUS_FAILURE )
3496 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"This Section<%d> does not exixt in Flash 2.x Map ",eFlash2xSectionVal);
3497 return -EINVAL;
3500 if(IsSectionExistInVendorInfo(Adapter,eFlash2xSectionVal))
3501 return vendorextnReadSection(Adapter,(PUCHAR)pBuffer, eFlash2xSectionVal, uiOffsetWithinSectionVal, uiNumBytes);
3503 //calculating the absolute offset from FLASH;
3504 uiAbsoluteOffset = uiOffsetWithinSectionVal + SectionStartOffset;
3505 rdmalt(Adapter, 0x0f000C80, &uiTemp, sizeof(uiTemp));
3506 value = 0;
3507 wrmalt(Adapter, 0x0f000C80,&value, sizeof(value));
3509 Status= BeceemFlashBulkRead(Adapter, pBuffer,uiAbsoluteOffset,uiNumBytes) ;
3511 wrmalt(Adapter, 0x0f000C80, &uiTemp, sizeof(uiTemp));
3512 if(Status)
3514 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "Flash Read Failed with Status :%d", Status);
3515 return Status ;
3518 return Status;
3522 * BcmFlash2xBulkWrite :-API for Writing on the Flash Map 2.x.
3523 * @Adapter :Driver Private Data Structure
3524 * @pBuffer : Buffer From where data has to taken for writing
3525 * @eFlashSectionVal :Flash Section Val defined in FLASH2X_SECTION_VAL
3526 * @uiOffsetWithinSectionVal :- Offset with in provided section
3527 * @uiNumBytes : Number of Bytes for Write
3529 * Return value:-
3530 * return true on sucess and STATUS_FAILURE on fail.
3534 INT BcmFlash2xBulkWrite(
3535 PMINI_ADAPTER Adapter,
3536 PUINT pBuffer,
3537 FLASH2X_SECTION_VAL eFlash2xSectVal,
3538 UINT uiOffset,
3539 UINT uiNumBytes,
3540 UINT bVerify)
3543 INT Status = STATUS_SUCCESS;
3544 UINT FlashSectValStartOffset = 0;
3545 UINT uiTemp = 0, value = 0;
3546 if(Adapter == NULL)
3548 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "Adapter structure is NULL");
3549 return -EINVAL;
3551 if(Adapter->device_removed )
3553 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "Device has been removed");
3554 return -ENODEV;
3557 //NO_SECTION_VAL means absolute offset is given.
3558 if(eFlash2xSectVal == NO_SECTION_VAL)
3559 FlashSectValStartOffset = 0;
3560 else
3561 FlashSectValStartOffset = BcmGetSectionValStartOffset(Adapter,eFlash2xSectVal);
3563 if(FlashSectValStartOffset == STATUS_FAILURE )
3565 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"This Section<%d> does not exixt in Flash Map 2.x",eFlash2xSectVal);
3566 return -EINVAL;
3569 if(IsSectionExistInVendorInfo(Adapter,eFlash2xSectVal))
3570 return vendorextnWriteSection(Adapter, (PUCHAR)pBuffer, eFlash2xSectVal, uiOffset, uiNumBytes, bVerify);
3572 //calculating the absolute offset from FLASH;
3573 uiOffset = uiOffset + FlashSectValStartOffset;
3575 rdmalt(Adapter, 0x0f000C80, &uiTemp, sizeof(uiTemp));
3576 value = 0;
3577 wrmalt(Adapter, 0x0f000C80,&value, sizeof(value));
3579 Status = BeceemFlashBulkWrite(Adapter, pBuffer,uiOffset,uiNumBytes,bVerify);
3581 wrmalt(Adapter, 0x0f000C80, &uiTemp, sizeof(uiTemp));
3582 if(Status)
3584 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "Flash Write failed with Status :%d", Status);
3585 return Status ;
3588 return Status;
3593 * ReadDSDHeader : Read the DSD map for the DSD Section val provided in Argument.
3594 * @Adapter : Beceem Private Data Structure
3595 * @psDSDHeader :Pointer of the buffer where header has to be read
3596 * @dsd :value of the Dyanmic DSD like DSD0 of DSD1 or DSD2
3598 * Return Value:-
3599 * if suceeds return STATUS_SUCCESS or negative error code.
3601 INT ReadDSDHeader(PMINI_ADAPTER Adapter, PDSD_HEADER psDSDHeader, FLASH2X_SECTION_VAL dsd)
3603 INT Status = STATUS_SUCCESS;
3605 Status =BcmFlash2xBulkRead(Adapter,
3606 (PUINT)psDSDHeader,
3607 dsd,
3608 Adapter->psFlash2xCSInfo->OffsetFromDSDStartForDSDHeader,
3609 sizeof(DSD_HEADER));
3610 if(Status == STATUS_SUCCESS)
3612 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "DSDImageMagicNumber :0X%x", ntohl(psDSDHeader->DSDImageMagicNumber));
3613 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "DSDImageSize :0X%x ",ntohl(psDSDHeader->DSDImageSize));
3614 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "DSDImageCRC :0X%x",ntohl(psDSDHeader->DSDImageCRC));
3615 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "DSDImagePriority :0X%x",ntohl(psDSDHeader->DSDImagePriority));
3617 else
3619 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"DSD Header read is failed with status :%d", Status);
3622 return Status;
3626 * BcmGetActiveDSD : Set the Active DSD in Adapter Structure which has to be dumped in DDR
3627 * @Adapter :-Drivers private Data Structure
3629 * Return Value:-
3630 * Return STATUS_SUCESS if get sucess in setting the right DSD else negaive error code
3633 INT BcmGetActiveDSD(PMINI_ADAPTER Adapter)
3635 FLASH2X_SECTION_VAL uiHighestPriDSD = 0 ;
3637 uiHighestPriDSD = getHighestPriDSD(Adapter);
3638 Adapter->eActiveDSD = uiHighestPriDSD;
3640 if(DSD0 == uiHighestPriDSD)
3641 Adapter->ulFlashCalStart = Adapter->psFlash2xCSInfo->OffsetFromZeroForDSDStart;
3642 if(DSD1 == uiHighestPriDSD)
3643 Adapter->ulFlashCalStart = Adapter->psFlash2xCSInfo->OffsetFromZeroForDSD1Start;
3644 if(DSD2 == uiHighestPriDSD)
3645 Adapter->ulFlashCalStart = Adapter->psFlash2xCSInfo->OffsetFromZeroForDSD2Start;
3646 if(Adapter->eActiveDSD)
3647 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "Active DSD :%d", Adapter->eActiveDSD);
3648 if(Adapter->eActiveDSD == 0)
3650 //if No DSD gets Active, Make Active the DSD with WR permission
3651 if(IsSectionWritable(Adapter,DSD2))
3653 Adapter->eActiveDSD = DSD2;
3654 Adapter->ulFlashCalStart = Adapter->psFlash2xCSInfo->OffsetFromZeroForDSD2Start;
3656 else if(IsSectionWritable(Adapter,DSD1))
3658 Adapter->eActiveDSD = DSD1;
3659 Adapter->ulFlashCalStart = Adapter->psFlash2xCSInfo->OffsetFromZeroForDSD1Start;
3661 else if(IsSectionWritable(Adapter,DSD0))
3663 Adapter->eActiveDSD = DSD0;
3664 Adapter->ulFlashCalStart = Adapter->psFlash2xCSInfo->OffsetFromZeroForDSDStart;
3668 return STATUS_SUCCESS;
3672 * ReadISOUnReservedBytes : Read the ISO map for the ISO Section val provided in Argument.
3673 * @Adapter : Driver Private Data Structure
3674 * @psISOHeader :Pointer of the location where header has to be read
3675 * @IsoImage :value of the Dyanmic ISO like ISO_IMAGE1 of ISO_IMAGE2
3677 * Return Value:-
3678 * if suceeds return STATUS_SUCCESS or negative error code.
3681 INT ReadISOHeader(PMINI_ADAPTER Adapter, PISO_HEADER psISOHeader, FLASH2X_SECTION_VAL IsoImage)
3683 INT Status = STATUS_SUCCESS;
3685 Status = BcmFlash2xBulkRead(Adapter,
3686 (PUINT)psISOHeader,
3687 IsoImage,
3689 sizeof(ISO_HEADER));
3691 if(Status == STATUS_SUCCESS)
3693 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "ISOImageMagicNumber :0X%x", ntohl(psISOHeader->ISOImageMagicNumber));
3694 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "ISOImageSize :0X%x ",ntohl(psISOHeader->ISOImageSize));
3695 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "ISOImageCRC :0X%x",ntohl(psISOHeader->ISOImageCRC));
3696 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "ISOImagePriority :0X%x",ntohl(psISOHeader->ISOImagePriority));
3698 else
3700 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "ISO Header Read failed");
3702 return Status;
3706 * BcmGetActiveISO :- Set the Active ISO in Adapter Data Structue
3707 * @Adapter : Driver private Data Structure
3709 * Return Value:-
3710 * Sucsess:- STATUS_SUCESS
3711 * Failure- : negative erro code
3715 INT BcmGetActiveISO(PMINI_ADAPTER Adapter)
3718 INT HighestPriISO = 0 ;
3719 HighestPriISO = getHighestPriISO(Adapter);
3721 Adapter->eActiveISO = HighestPriISO ;
3722 if(Adapter->eActiveISO == ISO_IMAGE2)
3723 Adapter->uiActiveISOOffset = (Adapter->psFlash2xCSInfo->OffsetISOImage2Part1Start);
3724 else if(Adapter->eActiveISO == ISO_IMAGE1)
3725 Adapter->uiActiveISOOffset = (Adapter->psFlash2xCSInfo->OffsetISOImage1Part1Start);
3727 if(Adapter->eActiveISO)
3728 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"Active ISO :%x", Adapter->eActiveISO);
3730 return STATUS_SUCCESS;
3734 * IsOffsetWritable :- it will tell the access permission of the sector having passed offset
3735 * @Adapter : Drivers Private Data Structure
3736 * @uiOffset : Offset provided in the Flash
3738 * Return Value:-
3739 * Sucess:-TRUE , offset is writable
3740 * Failure:-FALSE, offset is RO
3743 B_UINT8 IsOffsetWritable(PMINI_ADAPTER Adapter, UINT uiOffset)
3745 UINT uiSectorNum = 0;
3746 UINT uiWordOfSectorPermission =0;
3747 UINT uiBitofSectorePermission = 0;
3748 B_UINT32 permissionBits = 0;
3749 uiSectorNum = uiOffset/Adapter->uiSectorSize;
3751 //calculating the word having this Sector Access permission from SectorAccessBitMap Array
3752 uiWordOfSectorPermission = Adapter->psFlash2xCSInfo->SectorAccessBitMap[uiSectorNum /16];
3754 //calculating the bit index inside the word for this sector
3755 uiBitofSectorePermission = 2*(15 - uiSectorNum %16);
3757 //Setting Access permission
3758 permissionBits = uiWordOfSectorPermission & (0x3 << uiBitofSectorePermission) ;
3759 permissionBits = (permissionBits >> uiBitofSectorePermission) & 0x3;
3760 if(permissionBits == SECTOR_READWRITE_PERMISSION)
3761 return TRUE;
3762 else
3763 return FALSE;
3766 INT BcmDumpFlash2xSectionBitMap(PFLASH2X_BITMAP psFlash2xBitMap)
3768 PMINI_ADAPTER Adapter = GET_BCM_ADAPTER(gblpnetdev);
3769 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "***************Flash 2.x Section Bitmap***************");
3770 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"ISO_IMAGE1 :0X%x", psFlash2xBitMap->ISO_IMAGE1);
3771 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"ISO_IMAGE2 :0X%x", psFlash2xBitMap->ISO_IMAGE2);
3772 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"DSD0 :0X%x", psFlash2xBitMap->DSD0);
3773 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"DSD1 :0X%x", psFlash2xBitMap->DSD1);
3774 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"DSD2 :0X%x", psFlash2xBitMap->DSD2);
3775 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"VSA0 :0X%x", psFlash2xBitMap->VSA0);
3776 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"VSA1 :0X%x", psFlash2xBitMap->VSA1);
3777 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"VSA2 :0X%x", psFlash2xBitMap->VSA2);
3778 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"SCSI :0X%x", psFlash2xBitMap->SCSI);
3779 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"CONTROL_SECTION :0X%x", psFlash2xBitMap->CONTROL_SECTION);
3781 return STATUS_SUCCESS;
3785 * BcmGetFlash2xSectionalBitMap :- It will provide the bit map of all the section present in Flash
3786 * 8bit has been assigned to every section.
3787 bit[0] :Section present or not
3788 bit[1] :section is valid or not
3789 bit[2] : Secton is read only or has write permission too.
3790 bit[3] : Active Section -
3791 bit[7...4] = Reserved .
3793 @Adapter:-Driver private Data Structure
3795 * Return value:-
3796 * Sucess:- STATUS_SUCESS
3797 * Failure:- negative error code
3800 INT BcmGetFlash2xSectionalBitMap(PMINI_ADAPTER Adapter, PFLASH2X_BITMAP psFlash2xBitMap)
3804 PFLASH2X_CS_INFO psFlash2xCSInfo = Adapter->psFlash2xCSInfo;
3805 FLASH2X_SECTION_VAL uiHighestPriDSD = 0 ;
3806 FLASH2X_SECTION_VAL uiHighestPriISO= 0 ;
3807 BOOLEAN SetActiveDSDDone = FALSE ;
3808 BOOLEAN SetActiveISODone = FALSE ;
3810 //For 1.x map all the section except DSD0 will be shown as not present
3811 //This part will be used by calibration tool to detect the number of DSD present in Flash.
3812 if(IsFlash2x(Adapter) == FALSE)
3814 psFlash2xBitMap->ISO_IMAGE2 = 0;
3815 psFlash2xBitMap->ISO_IMAGE1 = 0;
3816 psFlash2xBitMap->DSD0 = FLASH2X_SECTION_VALID | FLASH2X_SECTION_ACT | FLASH2X_SECTION_PRESENT; //0xF; //0000(Reseved)1(Active)0(RW)1(valid)1(present)
3817 psFlash2xBitMap->DSD1 = 0 ;
3818 psFlash2xBitMap->DSD2 = 0 ;
3819 psFlash2xBitMap->VSA0 = 0 ;
3820 psFlash2xBitMap->VSA1 = 0 ;
3821 psFlash2xBitMap->VSA2 = 0 ;
3822 psFlash2xBitMap->CONTROL_SECTION = 0 ;
3823 psFlash2xBitMap->SCSI= 0 ;
3824 psFlash2xBitMap->Reserved0 = 0 ;
3825 psFlash2xBitMap->Reserved1 = 0 ;
3826 psFlash2xBitMap->Reserved2 = 0 ;
3827 return STATUS_SUCCESS ;
3831 uiHighestPriDSD = getHighestPriDSD(Adapter);
3832 uiHighestPriISO = getHighestPriISO(Adapter);
3835 // IS0 IMAGE 2
3837 if((psFlash2xCSInfo->OffsetISOImage2Part1Start) != UNINIT_PTR_IN_CS)
3839 //Setting the 0th Bit representing the Section is present or not.
3840 psFlash2xBitMap->ISO_IMAGE2= psFlash2xBitMap->ISO_IMAGE2 | FLASH2X_SECTION_PRESENT;
3843 if(ReadISOSignature(Adapter,ISO_IMAGE2)== ISO_IMAGE_MAGIC_NUMBER)
3844 psFlash2xBitMap->ISO_IMAGE2 |= FLASH2X_SECTION_VALID;
3847 //Calculation for extrating the Access permission
3848 if(IsSectionWritable(Adapter, ISO_IMAGE2) == FALSE)
3849 psFlash2xBitMap->ISO_IMAGE2 |= FLASH2X_SECTION_RO;
3851 if(SetActiveISODone == FALSE && uiHighestPriISO == ISO_IMAGE2)
3853 psFlash2xBitMap->ISO_IMAGE2 |= FLASH2X_SECTION_ACT ;
3854 SetActiveISODone = TRUE;
3860 // IS0 IMAGE 1
3862 if((psFlash2xCSInfo->OffsetISOImage1Part1Start) != UNINIT_PTR_IN_CS)
3864 //Setting the 0th Bit representing the Section is present or not.
3865 psFlash2xBitMap->ISO_IMAGE1 = psFlash2xBitMap->ISO_IMAGE1 | FLASH2X_SECTION_PRESENT;
3867 if(ReadISOSignature(Adapter,ISO_IMAGE1) == ISO_IMAGE_MAGIC_NUMBER)
3868 psFlash2xBitMap->ISO_IMAGE1 |= FLASH2X_SECTION_VALID;
3870 // Calculation for extrating the Access permission
3871 if(IsSectionWritable(Adapter, ISO_IMAGE1) == FALSE)
3872 psFlash2xBitMap->ISO_IMAGE1 |= FLASH2X_SECTION_RO;
3874 if(SetActiveISODone == FALSE && uiHighestPriISO == ISO_IMAGE1)
3876 psFlash2xBitMap->ISO_IMAGE1 |= FLASH2X_SECTION_ACT ;
3877 SetActiveISODone = TRUE;
3884 // DSD2
3886 if((psFlash2xCSInfo->OffsetFromZeroForDSD2Start) != UNINIT_PTR_IN_CS)
3888 //Setting the 0th Bit representing the Section is present or not.
3889 psFlash2xBitMap->DSD2= psFlash2xBitMap->DSD2 | FLASH2X_SECTION_PRESENT;
3891 if(ReadDSDSignature(Adapter,DSD2)== DSD_IMAGE_MAGIC_NUMBER)
3892 psFlash2xBitMap->DSD2 |= FLASH2X_SECTION_VALID;
3894 //Calculation for extrating the Access permission
3895 if(IsSectionWritable(Adapter, DSD2) == FALSE)
3897 psFlash2xBitMap->DSD2 |= FLASH2X_SECTION_RO;
3900 else
3902 //Means section is writable
3903 if((SetActiveDSDDone == FALSE) && (uiHighestPriDSD == DSD2))
3905 psFlash2xBitMap->DSD2 |= FLASH2X_SECTION_ACT ;
3906 SetActiveDSDDone =TRUE ;
3912 // DSD 1
3914 if((psFlash2xCSInfo->OffsetFromZeroForDSD1Start) != UNINIT_PTR_IN_CS)
3916 //Setting the 0th Bit representing the Section is present or not.
3917 psFlash2xBitMap->DSD1= psFlash2xBitMap->DSD1 | FLASH2X_SECTION_PRESENT;
3920 if(ReadDSDSignature(Adapter,DSD1)== DSD_IMAGE_MAGIC_NUMBER)
3921 psFlash2xBitMap->DSD1 |= FLASH2X_SECTION_VALID;
3923 //Calculation for extrating the Access permission
3924 if(IsSectionWritable(Adapter, DSD1) == FALSE)
3926 psFlash2xBitMap->DSD1 |= FLASH2X_SECTION_RO;
3928 else
3930 //Means section is writable
3931 if((SetActiveDSDDone == FALSE) && (uiHighestPriDSD == DSD1))
3933 psFlash2xBitMap->DSD1 |= FLASH2X_SECTION_ACT ;
3934 SetActiveDSDDone =TRUE ;
3941 //For DSD 0
3943 if((psFlash2xCSInfo->OffsetFromZeroForDSDStart) != UNINIT_PTR_IN_CS)
3945 //Setting the 0th Bit representing the Section is present or not.
3946 psFlash2xBitMap->DSD0 = psFlash2xBitMap->DSD0 | FLASH2X_SECTION_PRESENT;
3948 if(ReadDSDSignature(Adapter,DSD0) == DSD_IMAGE_MAGIC_NUMBER)
3949 psFlash2xBitMap->DSD0 |= FLASH2X_SECTION_VALID;
3951 //Setting Access permission
3952 if(IsSectionWritable(Adapter, DSD0) == FALSE)
3954 psFlash2xBitMap->DSD0 |= FLASH2X_SECTION_RO;
3956 else
3958 //Means section is writable
3959 if((SetActiveDSDDone == FALSE) &&(uiHighestPriDSD == DSD0))
3961 psFlash2xBitMap->DSD0 |= FLASH2X_SECTION_ACT ;
3962 SetActiveDSDDone =TRUE ;
3968 // VSA 0
3970 if((psFlash2xCSInfo->OffsetFromZeroForVSAStart) != UNINIT_PTR_IN_CS)
3972 //Setting the 0th Bit representing the Section is present or not.
3973 psFlash2xBitMap->VSA0= psFlash2xBitMap->VSA0 | FLASH2X_SECTION_PRESENT;
3975 //Setting the Access Bit. Map is not defined hece setting it always valid
3976 psFlash2xBitMap->VSA0 |= FLASH2X_SECTION_VALID;
3978 //Calculation for extrating the Access permission
3979 if(IsSectionWritable(Adapter, VSA0) == FALSE)
3980 psFlash2xBitMap->VSA0 |= FLASH2X_SECTION_RO;
3982 //By Default section is Active
3983 psFlash2xBitMap->VSA0 |= FLASH2X_SECTION_ACT ;
3989 // VSA 1
3992 if((psFlash2xCSInfo->OffsetFromZeroForVSA1Start) != UNINIT_PTR_IN_CS)
3994 //Setting the 0th Bit representing the Section is present or not.
3995 psFlash2xBitMap->VSA1= psFlash2xBitMap->VSA1 | FLASH2X_SECTION_PRESENT;
3997 //Setting the Access Bit. Map is not defined hece setting it always valid
3998 psFlash2xBitMap->VSA1|= FLASH2X_SECTION_VALID;
4000 //Checking For Access permission
4001 if(IsSectionWritable(Adapter, VSA1) == FALSE)
4002 psFlash2xBitMap->VSA1 |= FLASH2X_SECTION_RO;
4004 //By Default section is Active
4005 psFlash2xBitMap->VSA1 |= FLASH2X_SECTION_ACT ;
4011 // VSA 2
4014 if((psFlash2xCSInfo->OffsetFromZeroForVSA2Start) != UNINIT_PTR_IN_CS)
4016 //Setting the 0th Bit representing the Section is present or not.
4017 psFlash2xBitMap->VSA2= psFlash2xBitMap->VSA2 | FLASH2X_SECTION_PRESENT;
4020 //Setting the Access Bit. Map is not defined hece setting it always valid
4021 psFlash2xBitMap->VSA2 |= FLASH2X_SECTION_VALID;
4023 //Checking For Access permission
4024 if(IsSectionWritable(Adapter, VSA2) == FALSE)
4025 psFlash2xBitMap->VSA2 |= FLASH2X_SECTION_RO;
4027 //By Default section is Active
4028 psFlash2xBitMap->VSA2 |= FLASH2X_SECTION_ACT ;
4032 // SCSI Section
4034 if((psFlash2xCSInfo->OffsetFromZeroForScsiFirmware) != UNINIT_PTR_IN_CS)
4036 //Setting the 0th Bit representing the Section is present or not.
4037 psFlash2xBitMap->SCSI= psFlash2xBitMap->SCSI | FLASH2X_SECTION_PRESENT;
4040 //Setting the Access Bit. Map is not defined hece setting it always valid
4041 psFlash2xBitMap->SCSI|= FLASH2X_SECTION_VALID;
4043 //Checking For Access permission
4044 if(IsSectionWritable(Adapter, SCSI) == FALSE)
4045 psFlash2xBitMap->SCSI |= FLASH2X_SECTION_RO;
4047 //By Default section is Active
4048 psFlash2xBitMap->SCSI |= FLASH2X_SECTION_ACT ;
4054 // Control Section
4056 if((psFlash2xCSInfo->OffsetFromZeroForControlSectionStart) != UNINIT_PTR_IN_CS)
4058 //Setting the 0th Bit representing the Section is present or not.
4059 psFlash2xBitMap->CONTROL_SECTION = psFlash2xBitMap->CONTROL_SECTION | (FLASH2X_SECTION_PRESENT);
4062 //Setting the Access Bit. Map is not defined hece setting it always valid
4063 psFlash2xBitMap->CONTROL_SECTION |= FLASH2X_SECTION_VALID;
4065 //Checking For Access permission
4066 if(IsSectionWritable(Adapter, CONTROL_SECTION) == FALSE)
4067 psFlash2xBitMap->CONTROL_SECTION |= FLASH2X_SECTION_RO;
4069 //By Default section is Active
4070 psFlash2xBitMap->CONTROL_SECTION |= FLASH2X_SECTION_ACT ;
4075 // For Reserved Sections
4077 psFlash2xBitMap->Reserved0 = 0;
4078 psFlash2xBitMap->Reserved0 = 0;
4079 psFlash2xBitMap->Reserved0 = 0;
4081 BcmDumpFlash2xSectionBitMap(psFlash2xBitMap);
4083 return STATUS_SUCCESS ;
4087 BcmSetActiveSection :- Set Active section is used to make priority field highest over other
4088 section of same type.
4090 @Adapater :- Bcm Driver Private Data Structure
4091 @eFlash2xSectionVal :- Flash section val whose priority has to be made highest.
4093 Return Value:- Make the priorit highest else return erorr code
4096 INT BcmSetActiveSection(PMINI_ADAPTER Adapter, FLASH2X_SECTION_VAL eFlash2xSectVal)
4098 INT SectImagePriority = 0;
4099 INT Status =STATUS_SUCCESS;
4101 //DSD_HEADER sDSD = {0};
4102 //ISO_HEADER sISO = {0};
4103 INT HighestPriDSD = 0 ;
4104 INT HighestPriISO = 0;
4108 Status = IsSectionWritable(Adapter,eFlash2xSectVal) ;
4109 if(Status != TRUE )
4111 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Provided Section <%d> is not writable",eFlash2xSectVal);
4112 return STATUS_FAILURE;
4115 Adapter->bHeaderChangeAllowed = TRUE ;
4116 switch(eFlash2xSectVal)
4118 case ISO_IMAGE1 :
4119 case ISO_IMAGE2 :
4120 if(ReadISOSignature(Adapter,eFlash2xSectVal)== ISO_IMAGE_MAGIC_NUMBER )
4122 HighestPriISO = getHighestPriISO(Adapter);
4124 if(HighestPriISO == eFlash2xSectVal )
4126 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"Given ISO<%x> already has highest priority",eFlash2xSectVal );
4127 Status = STATUS_SUCCESS ;
4128 break;
4131 SectImagePriority = ReadISOPriority(Adapter, HighestPriISO) + 1;
4133 if((SectImagePriority <= 0) && IsSectionWritable(Adapter,HighestPriISO))
4135 // This is a SPECIAL Case which will only happen if the current highest priority ISO has priority value = 0x7FFFFFFF.
4136 // We will write 1 to the current Highest priority ISO And then shall increase the priority of the requested ISO
4137 // by user
4138 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "SectImagePriority wraparound happend, eFlash2xSectVal: 0x%x\n",eFlash2xSectVal);
4139 SectImagePriority = htonl(0x1);
4140 Status = BcmFlash2xBulkWrite(Adapter,
4141 &SectImagePriority,
4142 HighestPriISO,
4143 0 + FIELD_OFFSET_IN_HEADER(PISO_HEADER, ISOImagePriority),
4144 SIGNATURE_SIZE,
4145 TRUE);
4147 if(Status)
4149 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Priority has not been written properly");
4150 Status = STATUS_FAILURE;
4151 break ;
4154 HighestPriISO = getHighestPriISO(Adapter);
4156 if(HighestPriISO == eFlash2xSectVal )
4158 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"Given ISO<%x> already has highest priority",eFlash2xSectVal );
4159 Status = STATUS_SUCCESS ;
4160 break;
4163 SectImagePriority = 2;
4167 SectImagePriority = htonl(SectImagePriority);
4169 Status = BcmFlash2xBulkWrite(Adapter,
4170 &SectImagePriority,
4171 eFlash2xSectVal,
4172 0 + FIELD_OFFSET_IN_HEADER(PISO_HEADER, ISOImagePriority),
4173 SIGNATURE_SIZE,
4174 TRUE);
4175 if(Status)
4177 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Priority has not been written properly");
4178 break ;
4181 else
4183 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "Signature is currupted. Hence can't increase the priority");
4184 Status = STATUS_FAILURE ;
4185 break;
4187 break;
4188 case DSD0 :
4189 case DSD1 :
4190 case DSD2 :
4191 if(ReadDSDSignature(Adapter,eFlash2xSectVal)== DSD_IMAGE_MAGIC_NUMBER)
4193 HighestPriDSD = getHighestPriDSD(Adapter);
4195 if((HighestPriDSD == eFlash2xSectVal))
4197 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"Given DSD<%x> already has highest priority", eFlash2xSectVal);
4198 Status = STATUS_SUCCESS ;
4199 break;
4202 SectImagePriority = ReadDSDPriority(Adapter, HighestPriDSD) + 1 ;
4203 if(SectImagePriority <= 0)
4205 // This is a SPECIAL Case which will only happen if the current highest priority DSD has priority value = 0x7FFFFFFF.
4206 // We will write 1 to the current Highest priority DSD And then shall increase the priority of the requested DSD
4207 // by user
4208 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, NVM_RW, DBG_LVL_ALL, "SectImagePriority wraparound happend, eFlash2xSectVal: 0x%x\n",eFlash2xSectVal);
4209 SectImagePriority = htonl(0x1);
4211 Status = BcmFlash2xBulkWrite(Adapter,
4212 &SectImagePriority,
4213 HighestPriDSD,
4214 Adapter->psFlash2xCSInfo->OffsetFromDSDStartForDSDHeader + FIELD_OFFSET_IN_HEADER(PDSD_HEADER, DSDImagePriority),
4215 SIGNATURE_SIZE,
4216 TRUE);
4218 if(Status)
4220 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "Priority has not been written properly");
4221 break ;
4224 HighestPriDSD = getHighestPriDSD(Adapter);
4226 if((HighestPriDSD == eFlash2xSectVal))
4228 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"Made the DSD: %x highest by reducing priority of other\n", eFlash2xSectVal);
4229 Status = STATUS_SUCCESS ;
4230 break;
4233 SectImagePriority = htonl(0x2);
4234 Status = BcmFlash2xBulkWrite(Adapter,
4235 &SectImagePriority,
4236 HighestPriDSD,
4237 Adapter->psFlash2xCSInfo->OffsetFromDSDStartForDSDHeader + FIELD_OFFSET_IN_HEADER(PDSD_HEADER, DSDImagePriority),
4238 SIGNATURE_SIZE,
4239 TRUE);
4241 if(Status)
4243 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "Priority has not been written properly");
4244 break ;
4247 HighestPriDSD = getHighestPriDSD(Adapter);
4249 if((HighestPriDSD == eFlash2xSectVal))
4251 Status = STATUS_SUCCESS ;
4252 break;
4254 SectImagePriority = 3 ;
4257 SectImagePriority = htonl(SectImagePriority);
4258 Status = BcmFlash2xBulkWrite(Adapter,
4259 &SectImagePriority,
4260 eFlash2xSectVal,
4261 Adapter->psFlash2xCSInfo->OffsetFromDSDStartForDSDHeader + FIELD_OFFSET_IN_HEADER(PDSD_HEADER, DSDImagePriority),
4262 SIGNATURE_SIZE ,
4263 TRUE);
4264 if(Status)
4266 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Priority has not been written properly");
4267 Status = STATUS_FAILURE ;
4268 break ;
4271 else
4273 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "Signature is currupted. Hence can't increase the priority");
4274 Status = STATUS_FAILURE ;
4275 break;
4277 break;
4278 case VSA0 :
4279 case VSA1 :
4280 case VSA2 :
4281 //Has to be decided
4282 break ;
4283 default :
4284 Status = STATUS_FAILURE ;
4285 break;
4289 Adapter->bHeaderChangeAllowed = FALSE ;
4290 return Status;
4295 BcmCopyISO - Used only for copying the ISO section
4296 @Adapater :- Bcm Driver Private Data Structure
4297 @sCopySectStrut :- Section copy structure
4299 Return value:- SUCCESS if copies successfully else negative error code
4302 INT BcmCopyISO(PMINI_ADAPTER Adapter, FLASH2X_COPY_SECTION sCopySectStrut)
4305 PCHAR Buff = NULL;
4306 FLASH2X_SECTION_VAL eISOReadPart = 0,eISOWritePart = 0;
4307 UINT uiReadOffsetWithinPart = 0, uiWriteOffsetWithinPart = 0;
4308 UINT uiTotalDataToCopy = 0;
4309 BOOLEAN IsThisHeaderSector = FALSE ;
4310 UINT sigOffset = 0;
4311 UINT ISOLength = 0;
4312 UINT Status = STATUS_SUCCESS;
4313 UINT SigBuff[MAX_RW_SIZE];
4314 UINT i = 0;
4316 if(ReadISOSignature(Adapter,sCopySectStrut.SrcSection) != ISO_IMAGE_MAGIC_NUMBER)
4318 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "error as Source ISO Section does not have valid signature");
4319 return STATUS_FAILURE;
4322 Status = BcmFlash2xBulkRead(Adapter,
4323 &ISOLength,
4324 sCopySectStrut.SrcSection,
4325 0 + FIELD_OFFSET_IN_HEADER(PISO_HEADER,ISOImageSize),
4328 if(Status)
4330 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "Read failed while copying ISO\n");
4331 return Status;
4334 ISOLength = htonl(ISOLength);
4336 if(ISOLength % Adapter->uiSectorSize)
4338 ISOLength = Adapter->uiSectorSize*(1 + ISOLength/Adapter->uiSectorSize);
4341 sigOffset = FIELD_OFFSET_IN_HEADER(PISO_HEADER, ISOImageMagicNumber);
4343 Buff = kzalloc(Adapter->uiSectorSize, GFP_KERNEL);
4345 if(Buff == NULL)
4347 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Memory allocation failed for section size");
4348 return -ENOMEM;
4351 if(sCopySectStrut.SrcSection ==ISO_IMAGE1 && sCopySectStrut.DstSection ==ISO_IMAGE2)
4353 eISOReadPart = ISO_IMAGE1 ;
4354 eISOWritePart = ISO_IMAGE2 ;
4355 uiReadOffsetWithinPart = 0;
4356 uiWriteOffsetWithinPart = 0 ;
4358 uiTotalDataToCopy =(Adapter->psFlash2xCSInfo->OffsetISOImage1Part1End) -
4359 (Adapter->psFlash2xCSInfo->OffsetISOImage1Part1Start)+
4360 (Adapter->psFlash2xCSInfo->OffsetISOImage1Part2End) -
4361 (Adapter->psFlash2xCSInfo->OffsetISOImage1Part2Start)+
4362 (Adapter->psFlash2xCSInfo->OffsetISOImage1Part3End) -
4363 (Adapter->psFlash2xCSInfo->OffsetISOImage1Part3Start);
4365 if(uiTotalDataToCopy < ISOLength)
4367 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"error as Source ISO Section does not have valid signature");
4368 return STATUS_FAILURE;
4371 uiTotalDataToCopy =(Adapter->psFlash2xCSInfo->OffsetISOImage2Part1End) -
4372 (Adapter->psFlash2xCSInfo->OffsetISOImage2Part1Start)+
4373 (Adapter->psFlash2xCSInfo->OffsetISOImage2Part2End) -
4374 (Adapter->psFlash2xCSInfo->OffsetISOImage2Part2Start)+
4375 (Adapter->psFlash2xCSInfo->OffsetISOImage2Part3End) -
4376 (Adapter->psFlash2xCSInfo->OffsetISOImage2Part3Start);
4378 if(uiTotalDataToCopy < ISOLength)
4380 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"error as Dest ISO Section does not have enough section size");
4381 return STATUS_FAILURE;
4384 uiTotalDataToCopy = ISOLength;
4386 CorruptISOSig(Adapter,ISO_IMAGE2);
4388 while(uiTotalDataToCopy)
4390 if(uiTotalDataToCopy == Adapter->uiSectorSize)
4392 //Setting for write of first sector. First sector is assumed to be written in last
4393 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"Writing the signature sector");
4394 eISOReadPart = ISO_IMAGE1 ;
4395 uiReadOffsetWithinPart = 0;
4396 eISOWritePart = ISO_IMAGE2;
4397 uiWriteOffsetWithinPart = 0 ;
4398 IsThisHeaderSector = TRUE ;
4401 else
4403 uiReadOffsetWithinPart = uiReadOffsetWithinPart + Adapter->uiSectorSize ;
4404 uiWriteOffsetWithinPart = uiWriteOffsetWithinPart + Adapter->uiSectorSize ;
4406 if((eISOReadPart == ISO_IMAGE1) && (uiReadOffsetWithinPart == (Adapter->psFlash2xCSInfo->OffsetISOImage1Part1End - Adapter->psFlash2xCSInfo->OffsetISOImage1Part1Start) ))
4408 eISOReadPart = ISO_IMAGE1_PART2 ;
4409 uiReadOffsetWithinPart = 0;
4411 if((eISOReadPart == ISO_IMAGE1_PART2) && (uiReadOffsetWithinPart == (Adapter->psFlash2xCSInfo->OffsetISOImage1Part2End - Adapter->psFlash2xCSInfo->OffsetISOImage1Part2Start)))
4413 eISOReadPart = ISO_IMAGE1_PART3 ;
4414 uiReadOffsetWithinPart = 0;
4416 if((eISOWritePart == ISO_IMAGE2) && (uiWriteOffsetWithinPart == (Adapter->psFlash2xCSInfo->OffsetISOImage2Part1End - Adapter->psFlash2xCSInfo->OffsetISOImage2Part1Start)))
4418 eISOWritePart = ISO_IMAGE2_PART2 ;
4419 uiWriteOffsetWithinPart = 0;
4421 if((eISOWritePart == ISO_IMAGE2_PART2) && (uiWriteOffsetWithinPart == (Adapter->psFlash2xCSInfo->OffsetISOImage2Part2End - Adapter->psFlash2xCSInfo->OffsetISOImage2Part2Start)))
4423 eISOWritePart = ISO_IMAGE2_PART3 ;
4424 uiWriteOffsetWithinPart = 0;
4428 Status = BcmFlash2xBulkRead(Adapter,
4429 (PUINT)Buff,
4430 eISOReadPart,
4431 uiReadOffsetWithinPart,
4432 Adapter->uiSectorSize
4435 if(Status)
4437 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "Read failed while copying ISO: Part: %x, OffsetWithinPart: %x\n", eISOReadPart, uiReadOffsetWithinPart);
4438 break;
4441 if(IsThisHeaderSector == TRUE)
4443 //If this is header sector write 0xFFFFFFFF at the sig time and in last write sig
4444 memcpy(SigBuff, Buff + sigOffset, MAX_RW_SIZE);
4446 for(i = 0; i < MAX_RW_SIZE;i++)
4447 *(Buff + sigOffset + i) = 0xFF;
4449 Adapter->bHeaderChangeAllowed = TRUE ;
4451 Status = BcmFlash2xBulkWrite(Adapter,
4452 (PUINT)Buff,
4453 eISOWritePart,
4454 uiWriteOffsetWithinPart,
4455 Adapter->uiSectorSize,
4456 TRUE);
4457 if(Status)
4459 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "Write failed while copying ISO: Part: %x, OffsetWithinPart: %x\n", eISOWritePart, uiWriteOffsetWithinPart);
4460 break;
4463 Adapter->bHeaderChangeAllowed = FALSE;
4465 if(IsThisHeaderSector == TRUE)
4467 WriteToFlashWithoutSectorErase(Adapter,
4468 SigBuff,
4469 eISOWritePart,
4470 sigOffset,
4471 MAX_RW_SIZE);
4472 IsThisHeaderSector = FALSE ;
4474 //substracting the written Data
4475 uiTotalDataToCopy = uiTotalDataToCopy - Adapter->uiSectorSize ;
4481 if(sCopySectStrut.SrcSection ==ISO_IMAGE2 && sCopySectStrut.DstSection ==ISO_IMAGE1)
4483 eISOReadPart = ISO_IMAGE2 ;
4484 eISOWritePart = ISO_IMAGE1 ;
4485 uiReadOffsetWithinPart = 0;
4486 uiWriteOffsetWithinPart = 0 ;
4488 uiTotalDataToCopy =(Adapter->psFlash2xCSInfo->OffsetISOImage2Part1End) -
4489 (Adapter->psFlash2xCSInfo->OffsetISOImage2Part1Start)+
4490 (Adapter->psFlash2xCSInfo->OffsetISOImage2Part2End) -
4491 (Adapter->psFlash2xCSInfo->OffsetISOImage2Part2Start)+
4492 (Adapter->psFlash2xCSInfo->OffsetISOImage2Part3End) -
4493 (Adapter->psFlash2xCSInfo->OffsetISOImage2Part3Start);
4495 if(uiTotalDataToCopy < ISOLength)
4497 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"error as Source ISO Section does not have valid signature");
4498 return STATUS_FAILURE;
4501 uiTotalDataToCopy =(Adapter->psFlash2xCSInfo->OffsetISOImage1Part1End) -
4502 (Adapter->psFlash2xCSInfo->OffsetISOImage1Part1Start)+
4503 (Adapter->psFlash2xCSInfo->OffsetISOImage1Part2End) -
4504 (Adapter->psFlash2xCSInfo->OffsetISOImage1Part2Start)+
4505 (Adapter->psFlash2xCSInfo->OffsetISOImage1Part3End) -
4506 (Adapter->psFlash2xCSInfo->OffsetISOImage1Part3Start);
4508 if(uiTotalDataToCopy < ISOLength)
4510 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"error as Dest ISO Section does not have enough section size");
4511 return STATUS_FAILURE;
4514 uiTotalDataToCopy = ISOLength;
4516 CorruptISOSig(Adapter,ISO_IMAGE1);
4518 while(uiTotalDataToCopy)
4520 if(uiTotalDataToCopy == Adapter->uiSectorSize)
4522 //Setting for write of first sector. First sector is assumed to be written in last
4523 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"Writing the signature sector");
4524 eISOReadPart = ISO_IMAGE2 ;
4525 uiReadOffsetWithinPart = 0;
4526 eISOWritePart = ISO_IMAGE1;
4527 uiWriteOffsetWithinPart = 0 ;
4528 IsThisHeaderSector = TRUE;
4531 else
4533 uiReadOffsetWithinPart = uiReadOffsetWithinPart + Adapter->uiSectorSize ;
4534 uiWriteOffsetWithinPart = uiWriteOffsetWithinPart + Adapter->uiSectorSize ;
4536 if((eISOReadPart == ISO_IMAGE2) && (uiReadOffsetWithinPart == (Adapter->psFlash2xCSInfo->OffsetISOImage2Part1End - Adapter->psFlash2xCSInfo->OffsetISOImage2Part1Start) ))
4538 eISOReadPart = ISO_IMAGE2_PART2 ;
4539 uiReadOffsetWithinPart = 0;
4541 if((eISOReadPart == ISO_IMAGE2_PART2) && (uiReadOffsetWithinPart == (Adapter->psFlash2xCSInfo->OffsetISOImage2Part2End - Adapter->psFlash2xCSInfo->OffsetISOImage2Part2Start)))
4543 eISOReadPart = ISO_IMAGE2_PART3 ;
4544 uiReadOffsetWithinPart = 0;
4546 if((eISOWritePart == ISO_IMAGE1) && (uiWriteOffsetWithinPart == (Adapter->psFlash2xCSInfo->OffsetISOImage1Part1End - Adapter->psFlash2xCSInfo->OffsetISOImage1Part1Start)))
4548 eISOWritePart = ISO_IMAGE1_PART2 ;
4549 uiWriteOffsetWithinPart = 0;
4551 if((eISOWritePart == ISO_IMAGE1_PART2) && (uiWriteOffsetWithinPart == (Adapter->psFlash2xCSInfo->OffsetISOImage1Part2End - Adapter->psFlash2xCSInfo->OffsetISOImage1Part2Start)))
4553 eISOWritePart = ISO_IMAGE1_PART3 ;
4554 uiWriteOffsetWithinPart = 0;
4558 Status = BcmFlash2xBulkRead(Adapter,
4559 (PUINT)Buff,
4560 eISOReadPart,
4561 uiReadOffsetWithinPart,
4562 Adapter->uiSectorSize
4564 if(Status)
4566 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "Read failed while copying ISO: Part: %x, OffsetWithinPart: %x\n", eISOReadPart, uiReadOffsetWithinPart);
4567 break;
4570 if(IsThisHeaderSector == TRUE)
4572 //If this is header sector write 0xFFFFFFFF at the sig time and in last write sig
4573 memcpy(SigBuff, Buff + sigOffset, MAX_RW_SIZE);
4575 for(i = 0; i < MAX_RW_SIZE;i++)
4576 *(Buff + sigOffset + i) = 0xFF;
4579 Adapter->bHeaderChangeAllowed = TRUE ;
4580 Status = BcmFlash2xBulkWrite(Adapter,
4581 (PUINT)Buff,
4582 eISOWritePart,
4583 uiWriteOffsetWithinPart,
4584 Adapter->uiSectorSize,
4585 TRUE);
4587 if(Status)
4589 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "Write failed while copying ISO: Part: %x, OffsetWithinPart: %x\n", eISOWritePart, uiWriteOffsetWithinPart);
4590 break;
4593 Adapter->bHeaderChangeAllowed = FALSE ;
4595 if(IsThisHeaderSector == TRUE)
4597 WriteToFlashWithoutSectorErase(Adapter,
4598 SigBuff,
4599 eISOWritePart,
4600 sigOffset,
4601 MAX_RW_SIZE);
4602 IsThisHeaderSector = FALSE ;
4605 //substracting the written Data
4606 uiTotalDataToCopy = uiTotalDataToCopy - Adapter->uiSectorSize ;
4612 bcm_kfree(Buff);
4614 return Status;
4617 BcmFlash2xCorruptSig : this API is used to corrupt the written sig in Bcm Header present in flash section.
4618 It will corrupt the sig, if Section is writable, by making first bytes as zero.
4619 @Adapater :- Bcm Driver Private Data Structure
4620 @eFlash2xSectionVal :- Flash section val which has header
4622 Return Value :-
4623 Sucess :- If Section is present and writable, corrupt the sig and return STATUS_SUCCESS
4624 Failure :-Return negative error code
4628 INT BcmFlash2xCorruptSig(PMINI_ADAPTER Adapter, FLASH2X_SECTION_VAL eFlash2xSectionVal)
4631 INT Status = STATUS_SUCCESS ;
4632 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "Section Value :%x \n", eFlash2xSectionVal);
4634 if((eFlash2xSectionVal == DSD0) || (eFlash2xSectionVal == DSD1) || (eFlash2xSectionVal == DSD2))
4636 Status = CorruptDSDSig(Adapter, eFlash2xSectionVal);
4638 else if(eFlash2xSectionVal == ISO_IMAGE1 || eFlash2xSectionVal == ISO_IMAGE2)
4640 Status = CorruptISOSig(Adapter, eFlash2xSectionVal);
4642 else
4644 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"Given Section <%d>does not have Header",eFlash2xSectionVal);
4645 return STATUS_SUCCESS;
4647 return Status;
4650 BcmFlash2xWriteSig :-this API is used to Write the sig if requested Section has
4651 header and Write Permission.
4652 @Adapater :- Bcm Driver Private Data Structure
4653 @eFlashSectionVal :- Flash section val which has header
4655 Return Value :-
4656 Sucess :- If Section is present and writable write the sig and return STATUS_SUCCESS
4657 Failure :-Return negative error code
4660 INT BcmFlash2xWriteSig(PMINI_ADAPTER Adapter, FLASH2X_SECTION_VAL eFlashSectionVal)
4663 UINT uiSignature = 0 ;
4664 UINT uiOffset = 0;
4665 //DSD_HEADER dsdHeader = {0};
4667 if(Adapter->bSigCorrupted == FALSE)
4669 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"Signature is not corrupted by driver, hence not restoring\n");
4670 return STATUS_SUCCESS;
4672 if(Adapter->bAllDSDWriteAllow == FALSE)
4674 if(IsSectionWritable(Adapter,eFlashSectionVal) == FALSE)
4676 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Section is not Writable...Hence can't Write signature");
4677 return SECTOR_IS_NOT_WRITABLE;
4680 if((eFlashSectionVal == DSD0) ||(eFlashSectionVal == DSD1) || (eFlashSectionVal == DSD2))
4682 uiSignature = htonl(DSD_IMAGE_MAGIC_NUMBER) ;
4683 uiOffset = Adapter->psFlash2xCSInfo->OffsetFromDSDStartForDSDHeader ;
4685 uiOffset += FIELD_OFFSET_IN_HEADER(PDSD_HEADER,DSDImageMagicNumber);
4687 if((ReadDSDSignature(Adapter,eFlashSectionVal) & 0xFF000000) != CORRUPTED_PATTERN)
4689 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Corrupted Pattern is not there. Hence won't write sig");
4690 return STATUS_FAILURE;
4694 else if((eFlashSectionVal == ISO_IMAGE1) || (eFlashSectionVal == ISO_IMAGE2))
4696 uiSignature = htonl(ISO_IMAGE_MAGIC_NUMBER);
4697 //uiOffset = 0;
4698 uiOffset = FIELD_OFFSET_IN_HEADER(PISO_HEADER,ISOImageMagicNumber);
4699 if((ReadISOSignature(Adapter,eFlashSectionVal) & 0xFF000000) != CORRUPTED_PATTERN)
4701 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Currupted Pattern is not there. Hence won't write sig");
4702 return STATUS_FAILURE;
4705 else
4707 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"GIVEN SECTION< %d > IS NOT VALID FOR SIG WRITE...", eFlashSectionVal);
4708 return STATUS_FAILURE;
4711 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"Restoring the signature");
4714 Adapter->bHeaderChangeAllowed = TRUE;
4715 Adapter->bSigCorrupted = FALSE;
4716 BcmFlash2xBulkWrite(Adapter, &uiSignature,eFlashSectionVal,uiOffset,SIGNATURE_SIZE,TRUE);
4717 Adapter->bHeaderChangeAllowed = FALSE;
4721 return STATUS_SUCCESS;
4724 validateFlash2xReadWrite :- This API is used to validate the user request for Read/Write.
4725 if requested Bytes goes beyond the Requested section, it reports error.
4726 @Adapater :- Bcm Driver Private Data Structure
4727 @psFlash2xReadWrite :-Flash2x Read/write structure pointer
4729 Return values:-Return TRUE is request is valid else FALSE.
4733 INT validateFlash2xReadWrite(PMINI_ADAPTER Adapter, PFLASH2X_READWRITE psFlash2xReadWrite)
4735 UINT uiNumOfBytes = 0 ;
4736 UINT uiSectStartOffset = 0 ;
4737 UINT uiSectEndOffset = 0;
4738 uiNumOfBytes = psFlash2xReadWrite->numOfBytes;
4740 if(IsSectionExistInFlash(Adapter,psFlash2xReadWrite->Section) != TRUE)
4742 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Section<%x> does not exixt in Flash",psFlash2xReadWrite->Section);
4743 return FALSE;
4745 uiSectStartOffset = BcmGetSectionValStartOffset(Adapter,psFlash2xReadWrite->Section);
4746 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "Start offset :%x ,section :%d\n",uiSectStartOffset,psFlash2xReadWrite->Section);
4747 if((psFlash2xReadWrite->Section == ISO_IMAGE1) ||(psFlash2xReadWrite->Section == ISO_IMAGE2))
4749 if(psFlash2xReadWrite->Section == ISO_IMAGE1)
4751 uiSectEndOffset = BcmGetSectionValEndOffset(Adapter,ISO_IMAGE1) -
4752 BcmGetSectionValStartOffset(Adapter,ISO_IMAGE1)+
4753 BcmGetSectionValEndOffset(Adapter,ISO_IMAGE1_PART2) -
4754 BcmGetSectionValStartOffset(Adapter,ISO_IMAGE1_PART2)+
4755 BcmGetSectionValEndOffset(Adapter,ISO_IMAGE1_PART3) -
4756 BcmGetSectionValStartOffset(Adapter,ISO_IMAGE1_PART3);
4758 else if(psFlash2xReadWrite->Section == ISO_IMAGE2)
4760 uiSectEndOffset = BcmGetSectionValEndOffset(Adapter,ISO_IMAGE2) -
4761 BcmGetSectionValStartOffset(Adapter,ISO_IMAGE2)+
4762 BcmGetSectionValEndOffset(Adapter,ISO_IMAGE2_PART2) -
4763 BcmGetSectionValStartOffset(Adapter,ISO_IMAGE2_PART2)+
4764 BcmGetSectionValEndOffset(Adapter,ISO_IMAGE2_PART3) -
4765 BcmGetSectionValStartOffset(Adapter,ISO_IMAGE2_PART3);
4769 //since this uiSectEndoffset is the size of iso Image. hence for calculating the vitual endoffset
4770 //it should be added in startoffset. so that check done in last of this function can be valued.
4771 uiSectEndOffset = uiSectStartOffset + uiSectEndOffset ;
4773 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"Total size of the ISO Image :%x",uiSectEndOffset);
4775 else
4776 uiSectEndOffset = BcmGetSectionValEndOffset(Adapter,psFlash2xReadWrite->Section);
4777 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "End offset :%x \n",uiSectEndOffset);
4779 //Checking the boundary condition
4780 if((uiSectStartOffset + psFlash2xReadWrite->offset + uiNumOfBytes) <= uiSectEndOffset)
4781 return TRUE;
4782 else
4784 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Invalid Request....");
4785 return FALSE;
4791 IsFlash2x :- check for Flash 2.x
4792 @Adapater :- Bcm Driver Private Data Structure
4794 Return value:-
4795 return TRUE if flah2.x of hgher version else return false.
4798 INT IsFlash2x(PMINI_ADAPTER Adapter)
4800 if(Adapter->uiFlashLayoutMajorVersion >= FLASH_2X_MAJOR_NUMBER)
4801 return TRUE ;
4802 else
4803 return FALSE;
4806 GetFlashBaseAddr :- Calculate the Flash Base address
4807 @Adapater :- Bcm Driver Private Data Structure
4809 Return Value:-
4810 Success :- Base Address of the Flash
4813 INT GetFlashBaseAddr(PMINI_ADAPTER Adapter)
4816 UINT uiBaseAddr = 0;
4818 if(Adapter->bDDRInitDone)
4821 For All Valid Flash Versions... except 1.1, take the value from FlashBaseAddr
4822 In case of Raw Read... use the default value
4824 if(Adapter->uiFlashLayoutMajorVersion && (Adapter->bFlashRawRead == FALSE) &&
4825 !((Adapter->uiFlashLayoutMajorVersion == 1) && (Adapter->uiFlashLayoutMinorVersion == 1))
4827 uiBaseAddr = Adapter->uiFlashBaseAdd ;
4828 else
4829 uiBaseAddr = FLASH_CONTIGIOUS_START_ADDR_AFTER_INIT;
4831 else
4834 For All Valid Flash Versions... except 1.1, take the value from FlashBaseAddr
4835 In case of Raw Read... use the default value
4837 if(Adapter->uiFlashLayoutMajorVersion && (Adapter->bFlashRawRead == FALSE) &&
4838 !((Adapter->uiFlashLayoutMajorVersion == 1) && (Adapter->uiFlashLayoutMinorVersion == 1))
4840 uiBaseAddr = Adapter->uiFlashBaseAdd | FLASH_CONTIGIOUS_START_ADDR_BEFORE_INIT;
4841 else
4842 uiBaseAddr = FLASH_CONTIGIOUS_START_ADDR_BEFORE_INIT;
4845 return uiBaseAddr ;
4848 BcmCopySection :- This API is used to copy the One section in another. Both section should
4849 be contiuous and of same size. Hence this Will not be applicabe to copy ISO.
4851 @Adapater :- Bcm Driver Private Data Structure
4852 @SrcSection :- Source section From where data has to be copied
4853 @DstSection :- Destination section to which data has to be copied
4854 @offset :- Offset from/to where data has to be copied from one section to another.
4855 @numOfBytes :- number of byes that has to be copyed from one section to another at given offset.
4856 in case of numofBytes equal zero complete section will be copied.
4858 Return Values-
4859 Sucess : Return STATUS_SUCCESS
4860 Faillure :- return negative error code
4864 INT BcmCopySection(PMINI_ADAPTER Adapter,
4865 FLASH2X_SECTION_VAL SrcSection,
4866 FLASH2X_SECTION_VAL DstSection,
4867 UINT offset,
4868 UINT numOfBytes)
4870 UINT BuffSize = 0 ;
4871 UINT BytesToBeCopied = 0;
4872 PUCHAR pBuff = NULL ;
4873 INT Status = STATUS_SUCCESS ;
4874 if(SrcSection == DstSection)
4876 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Source and Destination should be different ...try again");
4877 return -EINVAL;
4879 if((SrcSection != DSD0) && (SrcSection != DSD1) && (SrcSection != DSD2))
4881 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Source should be DSD subsection");
4882 return -EINVAL;
4884 if((DstSection != DSD0) && (DstSection != DSD1) && (DstSection != DSD2))
4886 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Destination should be DSD subsection");
4887 return -EINVAL;
4890 #if 0
4891 else
4893 if((SrcSection == VSA0) || (SrcSection == VSA1) || (SrcSection == VSA2))
4895 if((DstSection != VSA0) && (DstSection != VSA1) && (DstSection != VSA2))
4897 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"Source and Destion secton is not of same type");
4898 return -EINVAL;
4903 #endif
4904 //if offset zero means have to copy complete secton
4906 if(numOfBytes == 0)
4908 numOfBytes = BcmGetSectionValEndOffset(Adapter,SrcSection)
4909 - BcmGetSectionValStartOffset(Adapter,SrcSection);
4911 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL," Section Size :0x%x",numOfBytes);
4914 if((offset + numOfBytes) > BcmGetSectionValEndOffset(Adapter,SrcSection)
4915 - BcmGetSectionValStartOffset(Adapter,SrcSection))
4917 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0," Input parameters going beyond the section offS: %x numB: %x of Source Section\n",
4918 offset, numOfBytes);
4919 return -EINVAL;
4922 if((offset + numOfBytes) > BcmGetSectionValEndOffset(Adapter,DstSection)
4923 - BcmGetSectionValStartOffset(Adapter,DstSection))
4925 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0," Input parameters going beyond the section offS: %x numB: %x of Destination Section\n",
4926 offset, numOfBytes);
4927 return -EINVAL;
4931 if(numOfBytes > Adapter->uiSectorSize )
4932 BuffSize = Adapter->uiSectorSize;
4933 else
4934 BuffSize = numOfBytes ;
4936 pBuff = (PCHAR)kzalloc(BuffSize, GFP_KERNEL);
4937 if(pBuff == NULL)
4939 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Memory allocation failed.. ");
4940 return -ENOMEM;
4944 BytesToBeCopied = Adapter->uiSectorSize ;
4945 if(offset % Adapter->uiSectorSize)
4946 BytesToBeCopied = Adapter->uiSectorSize - (offset % Adapter->uiSectorSize);
4947 if(BytesToBeCopied > numOfBytes)
4948 BytesToBeCopied = numOfBytes ;
4952 Adapter->bHeaderChangeAllowed = TRUE;
4956 Status = BcmFlash2xBulkRead(Adapter, (PUINT)pBuff, SrcSection , offset,BytesToBeCopied);
4957 if(Status)
4959 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "Read failed at offset :%d for NOB :%d", SrcSection,BytesToBeCopied);
4960 break;
4962 Status = BcmFlash2xBulkWrite(Adapter,(PUINT)pBuff,DstSection,offset,BytesToBeCopied,FALSE);
4963 if(Status)
4965 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "Write failed at offset :%d for NOB :%d", DstSection,BytesToBeCopied);
4966 break;
4968 offset = offset + BytesToBeCopied;
4969 numOfBytes = numOfBytes - BytesToBeCopied ;
4970 if(numOfBytes)
4972 if(numOfBytes > Adapter->uiSectorSize )
4973 BytesToBeCopied = Adapter->uiSectorSize;
4974 else
4975 BytesToBeCopied = numOfBytes;
4977 }while(numOfBytes > 0) ;
4978 bcm_kfree(pBuff);
4979 Adapter->bHeaderChangeAllowed = FALSE ;
4980 return Status;
4984 SaveHeaderIfPresent :- This API is use to Protect the Header in case of Header Sector write
4985 @Adapater :- Bcm Driver Private Data Structure
4986 @pBuff :- Data buffer that has to be written in sector having the header map.
4987 @uiOffset :- Flash offset that has to be written.
4989 Return value :-
4990 Sucess :- On sucess return STATUS_SUCCESS
4991 Faillure :- Return negative error code
4995 INT SaveHeaderIfPresent(PMINI_ADAPTER Adapter, PUCHAR pBuff, UINT uiOffset)
4997 UINT offsetToProtect = 0,HeaderSizeToProtect =0;
4998 BOOLEAN bHasHeader = FALSE ;
4999 PUCHAR pTempBuff =NULL;
5000 UINT uiSectAlignAddr = 0;
5001 UINT sig = 0;
5003 #if 0
5004 //if Chenges in Header is allowed, Return back
5005 if(Adapter->bHeaderChangeAllowed == TRUE)
5007 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "Header Change is allowed");
5008 return STATUS_SUCCESS ;
5010 #endif
5011 //making the offset sector alligned
5012 uiSectAlignAddr = uiOffset & ~(Adapter->uiSectorSize - 1);
5015 if((uiSectAlignAddr == BcmGetSectionValEndOffset(Adapter,DSD2)- Adapter->uiSectorSize)||
5016 (uiSectAlignAddr == BcmGetSectionValEndOffset(Adapter,DSD1)- Adapter->uiSectorSize)||
5017 (uiSectAlignAddr == BcmGetSectionValEndOffset(Adapter,DSD0)- Adapter->uiSectorSize))
5020 //offset from the sector boundry having the header map
5021 offsetToProtect = Adapter->psFlash2xCSInfo->OffsetFromDSDStartForDSDHeader % Adapter->uiSectorSize;
5022 HeaderSizeToProtect = sizeof(DSD_HEADER);
5023 bHasHeader = TRUE ;
5026 if(uiSectAlignAddr == BcmGetSectionValStartOffset(Adapter,ISO_IMAGE1) ||
5027 uiSectAlignAddr == BcmGetSectionValStartOffset(Adapter,ISO_IMAGE2))
5029 offsetToProtect = 0;
5030 HeaderSizeToProtect = sizeof(ISO_HEADER);
5031 bHasHeader = TRUE;
5033 //If Header is present overwrite passed buffer with this
5034 if(bHasHeader && (Adapter->bHeaderChangeAllowed == FALSE))
5036 pTempBuff = (PUCHAR)kzalloc(HeaderSizeToProtect, GFP_KERNEL);
5037 if(pTempBuff == NULL)
5039 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Memory allocation failed ");
5040 return -ENOMEM;
5042 //Read header
5043 BeceemFlashBulkRead(Adapter,(PUINT)pTempBuff,(uiSectAlignAddr + offsetToProtect),HeaderSizeToProtect);
5044 BCM_DEBUG_PRINT_BUFFER(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,pTempBuff ,HeaderSizeToProtect);
5045 //Replace Buffer content with Header
5046 memcpy(pBuff +offsetToProtect,pTempBuff,HeaderSizeToProtect);
5048 bcm_kfree(pTempBuff);
5050 if(bHasHeader && Adapter->bSigCorrupted)
5052 sig = *((PUINT)(pBuff + offsetToProtect + FIELD_OFFSET_IN_HEADER(PDSD_HEADER,DSDImageMagicNumber)));
5053 sig = ntohl(sig);
5054 if((sig & 0xFF000000) != CORRUPTED_PATTERN)
5056 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"Desired pattern is not at sig offset. Hence won't restore");
5057 Adapter->bSigCorrupted = FALSE;
5058 return STATUS_SUCCESS;
5060 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL," Corrupted sig is :%X", sig);
5061 *((PUINT)(pBuff + offsetToProtect + FIELD_OFFSET_IN_HEADER(PDSD_HEADER,DSDImageMagicNumber)))= htonl(DSD_IMAGE_MAGIC_NUMBER);
5062 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"Restoring the signature in Header Write only");
5063 Adapter->bSigCorrupted = FALSE;
5066 return STATUS_SUCCESS ;
5068 INT BcmMakeFlashCSActive(PMINI_ADAPTER Adapter, UINT offset)
5070 UINT GPIOConfig = 0 ;
5073 if(Adapter->bFlashRawRead == FALSE)
5075 //Applicable for Flash2.x
5076 if(IsFlash2x(Adapter) == FALSE)
5077 return STATUS_SUCCESS;
5080 if(offset/FLASH_PART_SIZE)
5082 //bit[14..12] -> will select make Active CS1, CS2 or CS3
5083 // Select CS1, CS2 and CS3 (CS0 is dedicated pin)
5084 rdmalt(Adapter,FLASH_GPIO_CONFIG_REG, &GPIOConfig, 4);
5085 GPIOConfig |= (7 << 12);
5086 wrmalt(Adapter,FLASH_GPIO_CONFIG_REG, &GPIOConfig, 4);
5089 return STATUS_SUCCESS ;
5092 BcmDoChipSelect : This will selcet the appropriate chip for writing.
5093 @Adapater :- Bcm Driver Private Data Structure
5095 OutPut:-
5096 Select the Appropriate chip and retrn status Sucess
5098 INT BcmDoChipSelect(PMINI_ADAPTER Adapter, UINT offset)
5100 UINT FlashConfig = 0;
5101 INT ChipNum = 0;
5102 UINT GPIOConfig = 0;
5103 UINT PartNum = 0;
5105 ChipNum = offset / FLASH_PART_SIZE ;
5108 // Chip Select mapping to enable flash0.
5109 // To select flash 0, we have to OR with (0<<12).
5110 // ORing 0 will have no impact so not doing that part.
5111 // In future if Chip select value changes from 0 to non zero,
5112 // That needs be taken care with backward comaptibility. No worries for now.
5116 SelectedChip Variable is the selection that the host is 100% Sure the same as what the register will hold. This can be ONLY ensured
5117 if the Chip doesn't goes to low power mode while the flash operation is in progress (NVMRdmWrmLock is taken)
5118 Before every new Flash Write operation, we reset the variable. This is to ensure that after any wake-up from
5119 power down modes (Idle mode/shutdown mode), the values in the register will be different.
5122 if(Adapter->SelectedChip == ChipNum)
5123 return STATUS_SUCCESS;
5125 //BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "Selected Chip :%x", ChipNum);
5126 Adapter->SelectedChip = ChipNum ;
5128 //bit[13..12] will select the appropriate chip
5129 rdmalt(Adapter,FLASH_CONFIG_REG, &FlashConfig, 4);
5130 rdmalt(Adapter,FLASH_GPIO_CONFIG_REG, &GPIOConfig, 4);
5133 switch(ChipNum)
5135 case 0:
5136 PartNum = 0;
5137 break;
5138 case 1:
5139 PartNum = 3;
5140 GPIOConfig |= (0x4 << CHIP_SELECT_BIT12);
5141 break;
5142 case 2:
5143 PartNum = 1;
5144 GPIOConfig |= (0x1 << CHIP_SELECT_BIT12);
5145 break;
5146 case 3:
5147 PartNum = 2;
5148 GPIOConfig |= (0x2 << CHIP_SELECT_BIT12);
5149 break;
5152 /* In case the bits already written in the FLASH_CONFIG_REG is same as what the user desired,
5153 nothing to do... can return immediately.
5154 ASSUMPTION: FLASH_GPIO_CONFIG_REG will be in sync with FLASH_CONFIG_REG.
5155 Even if the chip goes to low power mode, it should wake with values in each register in sync with each other.
5156 These values are not written by host other than during CHIP_SELECT.
5158 if(PartNum == ((FlashConfig >> CHIP_SELECT_BIT12) & 0x3))
5159 return STATUS_SUCCESS;
5161 //clearing the bit[13..12]
5162 FlashConfig &= 0xFFFFCFFF;
5163 FlashConfig = (FlashConfig | (PartNum<<CHIP_SELECT_BIT12)); //00
5165 wrmalt(Adapter,FLASH_GPIO_CONFIG_REG, &GPIOConfig, 4);
5166 udelay(100);
5168 wrmalt(Adapter,FLASH_CONFIG_REG, &FlashConfig, 4);
5169 udelay(100);
5171 return STATUS_SUCCESS;
5174 INT ReadDSDSignature(PMINI_ADAPTER Adapter, FLASH2X_SECTION_VAL dsd)
5176 UINT uiDSDsig = 0;
5177 //UINT sigoffsetInMap = 0;
5178 //DSD_HEADER dsdHeader = {0};
5181 //sigoffsetInMap =(PUCHAR)&(dsdHeader.DSDImageMagicNumber) -(PUCHAR)&dsdHeader;
5183 if(dsd != DSD0 && dsd != DSD1 && dsd != DSD2)
5185 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"passed section value is not for DSDs");
5186 return STATUS_FAILURE;
5188 BcmFlash2xBulkRead(Adapter,
5189 &uiDSDsig,
5190 dsd,
5191 Adapter->psFlash2xCSInfo->OffsetFromDSDStartForDSDHeader + FIELD_OFFSET_IN_HEADER(PDSD_HEADER,DSDImageMagicNumber),
5192 SIGNATURE_SIZE);
5194 uiDSDsig = ntohl(uiDSDsig);
5195 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"DSD SIG :%x", uiDSDsig);
5197 return uiDSDsig ;
5199 INT ReadDSDPriority(PMINI_ADAPTER Adapter, FLASH2X_SECTION_VAL dsd)
5201 //UINT priOffsetInMap = 0 ;
5202 INT uiDSDPri = STATUS_FAILURE;
5203 //DSD_HEADER dsdHeader = {0};
5204 //priOffsetInMap = (PUCHAR)&(dsdHeader.DSDImagePriority) -(PUCHAR)&dsdHeader;
5205 if(IsSectionWritable(Adapter,dsd))
5207 if(ReadDSDSignature(Adapter,dsd)== DSD_IMAGE_MAGIC_NUMBER)
5209 BcmFlash2xBulkRead(Adapter,
5210 &uiDSDPri,
5211 dsd,
5212 Adapter->psFlash2xCSInfo->OffsetFromDSDStartForDSDHeader +FIELD_OFFSET_IN_HEADER(PDSD_HEADER, DSDImagePriority),
5215 uiDSDPri = ntohl(uiDSDPri);
5216 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"DSD<%x> Priority :%x", dsd, uiDSDPri);
5220 return uiDSDPri;
5222 FLASH2X_SECTION_VAL getHighestPriDSD(PMINI_ADAPTER Adapter)
5224 INT DSDHighestPri = STATUS_FAILURE;
5225 INT DsdPri= 0 ;
5226 FLASH2X_SECTION_VAL HighestPriDSD = 0 ;
5228 if(IsSectionWritable(Adapter,DSD2))
5230 DSDHighestPri = ReadDSDPriority(Adapter,DSD2);
5231 HighestPriDSD = DSD2 ;
5233 if(IsSectionWritable(Adapter,DSD1))
5235 DsdPri = ReadDSDPriority(Adapter,DSD1);
5236 if(DSDHighestPri < DsdPri)
5238 DSDHighestPri = DsdPri ;
5239 HighestPriDSD = DSD1;
5242 if(IsSectionWritable(Adapter,DSD0))
5244 DsdPri = ReadDSDPriority(Adapter,DSD0);
5245 if(DSDHighestPri < DsdPri)
5247 DSDHighestPri = DsdPri ;
5248 HighestPriDSD = DSD0;
5251 if(HighestPriDSD)
5252 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"Highest DSD :%x , and its Pri :%x", HighestPriDSD, DSDHighestPri);
5253 return HighestPriDSD ;
5256 INT ReadISOSignature(PMINI_ADAPTER Adapter, FLASH2X_SECTION_VAL iso)
5258 UINT uiISOsig = 0;
5259 //UINT sigoffsetInMap = 0;
5260 //ISO_HEADER ISOHeader = {0};
5263 //sigoffsetInMap =(PUCHAR)&(ISOHeader.ISOImageMagicNumber) -(PUCHAR)&ISOHeader;
5265 if(iso != ISO_IMAGE1 && iso != ISO_IMAGE2)
5267 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"passed section value is not for ISOs");
5268 return STATUS_FAILURE;
5270 BcmFlash2xBulkRead(Adapter,
5271 &uiISOsig,
5272 iso,
5273 0 + FIELD_OFFSET_IN_HEADER(PISO_HEADER,ISOImageMagicNumber),
5274 SIGNATURE_SIZE);
5276 uiISOsig = ntohl(uiISOsig);
5277 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"ISO SIG :%x", uiISOsig);
5279 return uiISOsig ;
5281 INT ReadISOPriority(PMINI_ADAPTER Adapter, FLASH2X_SECTION_VAL iso)
5284 INT ISOPri = STATUS_FAILURE;
5285 if(IsSectionWritable(Adapter,iso))
5287 if(ReadISOSignature(Adapter,iso)== ISO_IMAGE_MAGIC_NUMBER)
5289 BcmFlash2xBulkRead(Adapter,
5290 &ISOPri,
5291 iso,
5292 0 + FIELD_OFFSET_IN_HEADER(PISO_HEADER, ISOImagePriority),
5295 ISOPri = ntohl(ISOPri);
5296 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"ISO<%x> Priority :%x", iso, ISOPri);
5300 return ISOPri;
5302 FLASH2X_SECTION_VAL getHighestPriISO(PMINI_ADAPTER Adapter)
5304 INT ISOHighestPri = STATUS_FAILURE;
5305 INT ISOPri= 0 ;
5306 FLASH2X_SECTION_VAL HighestPriISO = NO_SECTION_VAL ;
5308 if(IsSectionWritable(Adapter,ISO_IMAGE2))
5310 ISOHighestPri = ReadISOPriority(Adapter,ISO_IMAGE2);
5311 HighestPriISO = ISO_IMAGE2 ;
5313 if(IsSectionWritable(Adapter,ISO_IMAGE1))
5315 ISOPri = ReadISOPriority(Adapter,ISO_IMAGE1);
5316 if(ISOHighestPri < ISOPri)
5318 ISOHighestPri = ISOPri ;
5319 HighestPriISO = ISO_IMAGE1;
5322 if(HighestPriISO)
5323 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"Highest ISO :%x and its Pri :%x",HighestPriISO,ISOHighestPri);
5324 return HighestPriISO ;
5326 INT WriteToFlashWithoutSectorErase(PMINI_ADAPTER Adapter,
5327 PUINT pBuff,
5328 FLASH2X_SECTION_VAL eFlash2xSectionVal,
5329 UINT uiOffset,
5330 UINT uiNumBytes
5333 #if !defined(BCM_SHM_INTERFACE) || defined(FLASH_DIRECT_ACCESS)
5334 UINT uiTemp = 0, value = 0 ;
5335 UINT i = 0;
5336 UINT uiPartOffset = 0;
5337 #endif
5338 UINT uiStartOffset = 0;
5339 //Adding section start address
5340 INT Status = STATUS_SUCCESS;
5341 PUCHAR pcBuff = (PUCHAR)pBuff;
5343 if(uiNumBytes % Adapter->ulFlashWriteSize)
5345 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Writing without Sector Erase for non-FlashWriteSize number of bytes 0x%x\n", uiNumBytes);
5346 return STATUS_FAILURE;
5349 uiStartOffset = BcmGetSectionValStartOffset(Adapter,eFlash2xSectionVal);
5351 if(IsSectionExistInVendorInfo(Adapter,eFlash2xSectionVal))
5353 return vendorextnWriteSectionWithoutErase(Adapter, pcBuff, eFlash2xSectionVal, uiOffset, uiNumBytes);
5356 uiOffset = uiOffset + uiStartOffset;
5358 #if defined(BCM_SHM_INTERFACE) && !defined(FLASH_DIRECT_ACCESS)
5359 Status = bcmflash_raw_writenoerase((uiOffset/FLASH_PART_SIZE),(uiOffset % FLASH_PART_SIZE), pcBuff,uiNumBytes);
5360 #else
5361 rdmalt(Adapter, 0x0f000C80, &uiTemp, sizeof(uiTemp));
5362 value = 0;
5363 wrmalt(Adapter, 0x0f000C80,&value, sizeof(value));
5365 Adapter->SelectedChip = RESET_CHIP_SELECT;
5366 BcmDoChipSelect(Adapter,uiOffset);
5367 uiPartOffset = (uiOffset & (FLASH_PART_SIZE - 1)) + GetFlashBaseAddr(Adapter);
5369 for(i = 0 ; i< uiNumBytes; i += Adapter->ulFlashWriteSize)
5371 if(Adapter->ulFlashWriteSize == BYTE_WRITE_SUPPORT)
5372 Status = flashByteWrite(Adapter,uiPartOffset, pcBuff);
5373 else
5374 Status = flashWrite(Adapter,uiPartOffset, pcBuff);
5376 if(Status != STATUS_SUCCESS)
5377 break;
5379 pcBuff = pcBuff + Adapter->ulFlashWriteSize;
5380 uiPartOffset = uiPartOffset + Adapter->ulFlashWriteSize;
5382 wrmalt(Adapter, 0x0f000C80, &uiTemp, sizeof(uiTemp));
5383 Adapter->SelectedChip = RESET_CHIP_SELECT;
5384 #endif
5386 return Status;
5389 #if 0
5390 UINT getNumOfSubSectionWithWRPermisson(PMINI_ADAPTER Adapter, SECTION_TYPE secType)
5393 UINT numOfWRSubSec = 0;
5394 switch(secType)
5396 case ISO :
5397 if(IsSectionWritable(Adapter,ISO_IMAGE1))
5398 numOfWRSubSec = numOfWRSubSec + 1;
5399 if(IsSectionWritable(Adapter,ISO_IMAGE2))
5400 numOfWRSubSec = numOfWRSubSec + 1;
5401 break;
5403 case DSD :
5404 if(IsSectionWritable(Adapter,DSD2))
5405 numOfWRSubSec = numOfWRSubSec + 1;
5406 if(IsSectionWritable(Adapter,DSD1))
5407 numOfWRSubSec = numOfWRSubSec + 1;
5408 if(IsSectionWritable(Adapter,DSD0))
5409 numOfWRSubSec = numOfWRSubSec + 1;
5410 break ;
5412 case VSA :
5413 //for VSA Add code Here
5414 default :
5415 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"Invalid secton<%d> is passed", secType);\
5416 numOfWRSubSec = 0;
5419 return numOfWRSubSec;
5421 #endif
5422 BOOLEAN IsSectionExistInFlash(PMINI_ADAPTER Adapter, FLASH2X_SECTION_VAL section)
5425 BOOLEAN SectionPresent = FALSE ;
5427 switch(section)
5430 case ISO_IMAGE1 :
5431 if((Adapter->psFlash2xCSInfo->OffsetISOImage1Part1Start != UNINIT_PTR_IN_CS) &&
5432 (IsNonCDLessDevice(Adapter) == FALSE))
5433 SectionPresent = TRUE ;
5434 break;
5435 case ISO_IMAGE2 :
5436 if((Adapter->psFlash2xCSInfo->OffsetISOImage2Part1Start != UNINIT_PTR_IN_CS) &&
5437 (IsNonCDLessDevice(Adapter) == FALSE))
5438 SectionPresent = TRUE ;
5439 break;
5440 case DSD0 :
5441 if(Adapter->psFlash2xCSInfo->OffsetFromZeroForDSDStart != UNINIT_PTR_IN_CS)
5442 SectionPresent = TRUE ;
5443 break;
5444 case DSD1 :
5445 if(Adapter->psFlash2xCSInfo->OffsetFromZeroForDSD1Start != UNINIT_PTR_IN_CS)
5446 SectionPresent = TRUE ;
5447 break;
5448 case DSD2 :
5449 if(Adapter->psFlash2xCSInfo->OffsetFromZeroForDSD2Start != UNINIT_PTR_IN_CS)
5450 SectionPresent = TRUE ;
5451 break;
5452 case VSA0 :
5453 if(Adapter->psFlash2xCSInfo->OffsetFromZeroForVSAStart != UNINIT_PTR_IN_CS)
5454 SectionPresent = TRUE ;
5455 break;
5456 case VSA1 :
5457 if(Adapter->psFlash2xCSInfo->OffsetFromZeroForVSA1Start != UNINIT_PTR_IN_CS)
5458 SectionPresent = TRUE ;
5459 break;
5460 case VSA2 :
5461 if(Adapter->psFlash2xCSInfo->OffsetFromZeroForVSA2Start != UNINIT_PTR_IN_CS)
5462 SectionPresent = TRUE ;
5463 break;
5464 case SCSI :
5465 if(Adapter->psFlash2xCSInfo->OffsetFromZeroForScsiFirmware != UNINIT_PTR_IN_CS)
5466 SectionPresent = TRUE ;
5467 break;
5468 case CONTROL_SECTION :
5469 if(Adapter->psFlash2xCSInfo->OffsetFromZeroForControlSectionStart != UNINIT_PTR_IN_CS)
5470 SectionPresent = TRUE ;
5471 break;
5472 default :
5473 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Section Does not exist in Flash 2.x");
5474 SectionPresent = FALSE;
5476 return SectionPresent ;
5478 INT IsSectionWritable(PMINI_ADAPTER Adapter, FLASH2X_SECTION_VAL Section)
5480 INT offset = STATUS_FAILURE;
5481 INT Status = FALSE;
5482 if(IsSectionExistInFlash(Adapter,Section) == FALSE)
5484 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Section <%d> does not exixt", Section);
5485 return FALSE;
5487 offset = BcmGetSectionValStartOffset(Adapter,Section);
5488 if(offset == INVALID_OFFSET)
5490 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Section<%d> does not exixt", Section);
5491 return FALSE;
5494 if(IsSectionExistInVendorInfo(Adapter,Section))
5496 return !(Adapter->psFlash2xVendorInfo->VendorSection[Section].AccessFlags & FLASH2X_SECTION_RO);
5499 Status = IsOffsetWritable(Adapter,offset);
5500 return Status ;
5503 INT CorruptDSDSig(PMINI_ADAPTER Adapter, FLASH2X_SECTION_VAL eFlash2xSectionVal)
5506 PUCHAR pBuff = 0 ;
5507 UINT sig = 0;
5508 UINT uiOffset = 0;
5509 UINT BlockStatus = 0;
5510 UINT uiSectAlignAddr = 0;
5512 Adapter->bSigCorrupted = FALSE;
5514 if(Adapter->bAllDSDWriteAllow == FALSE)
5516 if(IsSectionWritable(Adapter,eFlash2xSectionVal) != TRUE)
5518 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Section is not Writable...Hence cant Corrupt signature");
5519 return SECTOR_IS_NOT_WRITABLE;
5523 pBuff = (PUCHAR)kzalloc(MAX_RW_SIZE, GFP_KERNEL);
5524 if(pBuff == NULL)
5526 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "Can't allocate memorey");
5527 return -ENOMEM ;
5530 uiOffset = Adapter->psFlash2xCSInfo->OffsetFromDSDStartForDSDHeader + sizeof(DSD_HEADER);
5531 uiOffset -= MAX_RW_SIZE ;
5533 BcmFlash2xBulkRead(Adapter, (PUINT)pBuff,eFlash2xSectionVal,uiOffset,MAX_RW_SIZE);
5536 sig = *((PUINT)(pBuff +12));
5537 sig =ntohl(sig);
5538 BCM_DEBUG_PRINT_BUFFER(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,pBuff,MAX_RW_SIZE);
5539 //Now corrupting the sig by corrupting 4th last Byte.
5540 *(pBuff + 12) = 0;
5542 if(sig == DSD_IMAGE_MAGIC_NUMBER)
5544 Adapter->bSigCorrupted = TRUE;
5545 if(Adapter->ulFlashWriteSize == BYTE_WRITE_SUPPORT)
5547 uiSectAlignAddr = uiOffset & ~(Adapter->uiSectorSize -1);
5548 BlockStatus = BcmFlashUnProtectBlock(Adapter,uiSectAlignAddr,Adapter->uiSectorSize);
5550 WriteToFlashWithoutSectorErase(Adapter,(PUINT)(pBuff + 12),eFlash2xSectionVal,
5551 (uiOffset + 12),BYTE_WRITE_SUPPORT);
5552 if(BlockStatus)
5554 BcmRestoreBlockProtectStatus(Adapter,BlockStatus);
5555 BlockStatus = 0;
5558 else
5560 WriteToFlashWithoutSectorErase(Adapter,(PUINT)pBuff,eFlash2xSectionVal,
5561 uiOffset ,MAX_RW_SIZE);
5564 else
5566 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"BCM Signature is not present in header");
5567 bcm_kfree(pBuff);
5568 return STATUS_FAILURE;
5571 bcm_kfree(pBuff);
5572 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"Corrupted the signature");
5573 return STATUS_SUCCESS ;
5576 INT CorruptISOSig(PMINI_ADAPTER Adapter, FLASH2X_SECTION_VAL eFlash2xSectionVal)
5579 PUCHAR pBuff = 0 ;
5580 UINT sig = 0;
5581 UINT uiOffset = 0;
5583 Adapter->bSigCorrupted = FALSE;
5585 if(IsSectionWritable(Adapter,eFlash2xSectionVal) != TRUE)
5587 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Section is not Writable...Hence cant Corrupt signature");
5588 return SECTOR_IS_NOT_WRITABLE;
5591 pBuff = (PUCHAR)kzalloc(MAX_RW_SIZE, GFP_KERNEL);
5592 if(pBuff == NULL)
5594 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Can't allocate memorey");
5595 return -ENOMEM ;
5598 uiOffset = 0;
5600 BcmFlash2xBulkRead(Adapter, (PUINT)pBuff,eFlash2xSectionVal,uiOffset, MAX_RW_SIZE);
5602 sig = *((PUINT)pBuff);
5603 sig =ntohl(sig);
5605 //corrupt signature
5606 *pBuff = 0;
5608 if(sig == ISO_IMAGE_MAGIC_NUMBER)
5610 Adapter->bSigCorrupted = TRUE;
5611 WriteToFlashWithoutSectorErase(Adapter,(PUINT)pBuff,eFlash2xSectionVal,
5612 uiOffset ,Adapter->ulFlashWriteSize);
5614 else
5616 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"BCM Signature is not present in header");
5617 bcm_kfree(pBuff);
5618 return STATUS_FAILURE;
5621 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"Corrupted the signature");
5622 BCM_DEBUG_PRINT_BUFFER(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,pBuff,MAX_RW_SIZE);
5624 bcm_kfree(pBuff);
5625 return STATUS_SUCCESS ;
5628 BOOLEAN IsNonCDLessDevice(PMINI_ADAPTER Adapter)
5630 if(Adapter->psFlash2xCSInfo->IsCDLessDeviceBootSig == NON_CDLESS_DEVICE_BOOT_SIG)
5631 return TRUE;
5632 else
5633 return FALSE ;