Staging: bcm: hostmibs: Added temporary variable to shorten lines
[deliverable/linux.git] / drivers / staging / bcm / nvm.c
CommitLineData
f8942e07
SH
1#include "headers.h"
2
3#define DWORD unsigned int
9dd47ee7
SH
4
5static INT BcmDoChipSelect(PMINI_ADAPTER Adapter, UINT offset);
6static INT BcmGetActiveDSD(PMINI_ADAPTER Adapter);
7static INT BcmGetActiveISO(PMINI_ADAPTER Adapter);
8static UINT BcmGetEEPROMSize(PMINI_ADAPTER Adapter);
9static INT BcmGetFlashCSInfo(PMINI_ADAPTER Adapter);
10static UINT BcmGetFlashSectorSize(PMINI_ADAPTER Adapter, UINT FlashSectorSizeSig, UINT FlashSectorSize);
11
12static VOID BcmValidateNvmType(PMINI_ADAPTER Adapter);
13static INT BcmGetNvmSize(PMINI_ADAPTER Adapter);
14static UINT BcmGetFlashSize(PMINI_ADAPTER Adapter);
15static NVM_TYPE BcmGetNvmType(PMINI_ADAPTER Adapter);
16
17static INT BcmGetSectionValEndOffset(PMINI_ADAPTER Adapter, FLASH2X_SECTION_VAL eFlash2xSectionVal);
18
19static B_UINT8 IsOffsetWritable(PMINI_ADAPTER Adapter, UINT uiOffset);
20static INT IsSectionWritable(PMINI_ADAPTER Adapter, FLASH2X_SECTION_VAL Section);
21static INT IsSectionExistInVendorInfo(PMINI_ADAPTER Adapter, FLASH2X_SECTION_VAL section);
22
23static INT ReadDSDPriority(PMINI_ADAPTER Adapter, FLASH2X_SECTION_VAL dsd);
24static INT ReadDSDSignature(PMINI_ADAPTER Adapter, FLASH2X_SECTION_VAL dsd);
25static INT ReadISOPriority(PMINI_ADAPTER Adapter, FLASH2X_SECTION_VAL iso);
26static INT ReadISOSignature(PMINI_ADAPTER Adapter, FLASH2X_SECTION_VAL iso);
27
28static INT CorruptDSDSig(PMINI_ADAPTER Adapter, FLASH2X_SECTION_VAL eFlash2xSectionVal);
29static INT CorruptISOSig(PMINI_ADAPTER Adapter, FLASH2X_SECTION_VAL eFlash2xSectionVal);
30static INT SaveHeaderIfPresent(PMINI_ADAPTER Adapter, PUCHAR pBuff, UINT uiSectAlignAddr);
31static INT WriteToFlashWithoutSectorErase(PMINI_ADAPTER Adapter, PUINT pBuff,
32 FLASH2X_SECTION_VAL eFlash2xSectionVal,
33 UINT uiOffset, UINT uiNumBytes);
34static FLASH2X_SECTION_VAL getHighestPriDSD(PMINI_ADAPTER Adapter);
35static FLASH2X_SECTION_VAL getHighestPriISO(PMINI_ADAPTER Adapter);
36
37static INT BeceemFlashBulkRead(
38 PMINI_ADAPTER Adapter,
39 PUINT pBuffer,
40 UINT uiOffset,
41 UINT uiNumBytes);
42
43static INT BeceemFlashBulkWrite(
44 PMINI_ADAPTER Adapter,
45 PUINT pBuffer,
46 UINT uiOffset,
47 UINT uiNumBytes,
48 BOOLEAN bVerify);
49
50static INT GetFlashBaseAddr(PMINI_ADAPTER Adapter);
51
52static INT ReadBeceemEEPROMBulk(PMINI_ADAPTER Adapter,UINT dwAddress, UINT *pdwData, UINT dwNumData);
53
f8942e07
SH
54// Procedure: ReadEEPROMStatusRegister
55//
56// Description: Reads the standard EEPROM Status Register.
57//
58// Arguments:
59// Adapter - ptr to Adapter object instance
60// Returns:
61// OSAL_STATUS_CODE
62//
63//-----------------------------------------------------------------------------
64
44a17eff 65static UCHAR ReadEEPROMStatusRegister( PMINI_ADAPTER Adapter )
f8942e07
SH
66{
67 UCHAR uiData = 0;
68 DWORD dwRetries = MAX_EEPROM_RETRIES*RETRIES_PER_DELAY;
69 UINT uiStatus = 0;
70 UINT value = 0;
71 UINT value1 = 0;
72
73 /* Read the EEPROM status register */
74 value = EEPROM_READ_STATUS_REGISTER ;
75 wrmalt( Adapter, EEPROM_CMDQ_SPI_REG, &value, sizeof(value));
76
77 while ( dwRetries != 0 )
78 {
79 value=0;
80 uiStatus = 0 ;
81 rdmalt( Adapter, EEPROM_SPI_Q_STATUS1_REG,&uiStatus, sizeof(uiStatus));
82 if(Adapter->device_removed == TRUE)
83 {
84 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Modem has got removed hence exiting....");
85 break;
86 }
87
88 /* Wait for Avail bit to be set. */
89 if ( ( uiStatus & EEPROM_READ_DATA_AVAIL) != 0 )
90 {
91 /* Clear the Avail/Full bits - which ever is set. */
92 value = uiStatus & (EEPROM_READ_DATA_AVAIL | EEPROM_READ_DATA_FULL);
93 wrmalt( Adapter, EEPROM_SPI_Q_STATUS1_REG, &value, sizeof(value));
94
95 value =0;
96 rdmalt(Adapter, EEPROM_READ_DATAQ_REG,&value, sizeof(value));
97 uiData = (UCHAR)value;
98
99 break;
100 }
101
102 dwRetries-- ;
103 if ( dwRetries == 0 )
104 {
105 rdmalt(Adapter, EEPROM_SPI_Q_STATUS1_REG,&value, sizeof(value));
106 rdmalt(Adapter, EEPROM_SPI_Q_STATUS_REG,&value1, sizeof(value1));
107 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);
108 return uiData;
109 }
110 if( !(dwRetries%RETRIES_PER_DELAY) )
111 msleep(1);
112 uiStatus = 0 ;
113 }
114 return uiData;
115} /* ReadEEPROMStatusRegister */
116
117//-----------------------------------------------------------------------------
118// Procedure: ReadBeceemEEPROMBulk
119//
120// Description: This routine reads 16Byte data from EEPROM
121//
122// Arguments:
123// Adapter - ptr to Adapter object instance
124// dwAddress - EEPROM Offset to read the data from.
125// pdwData - Pointer to double word where data needs to be stored in. // dwNumWords - Number of words. Valid values are 4 ONLY.
126//
127// Returns:
128// OSAL_STATUS_CODE:
129//-----------------------------------------------------------------------------
130
131INT ReadBeceemEEPROMBulk( PMINI_ADAPTER Adapter,
132 DWORD dwAddress,
133 DWORD *pdwData,
134 DWORD dwNumWords
135 )
136{
137 DWORD dwIndex = 0;
138 DWORD dwRetries = MAX_EEPROM_RETRIES*RETRIES_PER_DELAY;
139 UINT uiStatus = 0;
140 UINT value= 0;
141 UINT value1 = 0;
142 UCHAR *pvalue;
143
144 /* Flush the read and cmd queue. */
145 value=( EEPROM_READ_QUEUE_FLUSH | EEPROM_CMD_QUEUE_FLUSH );
146 wrmalt( Adapter, SPI_FLUSH_REG, &value, sizeof(value) );
147 value=0;
148 wrmalt( Adapter, SPI_FLUSH_REG, &value, sizeof(value));
149
150 /* Clear the Avail/Full bits. */
151 value=( EEPROM_READ_DATA_AVAIL | EEPROM_READ_DATA_FULL );
152 wrmalt( Adapter, EEPROM_SPI_Q_STATUS1_REG,&value, sizeof(value));
153
154 value= dwAddress | ( (dwNumWords == 4) ? EEPROM_16_BYTE_PAGE_READ : EEPROM_4_BYTE_PAGE_READ );
155 wrmalt( Adapter, EEPROM_CMDQ_SPI_REG, &value, sizeof(value));
156
157 while ( dwRetries != 0 )
158 {
159
160 uiStatus = 0;
161 rdmalt( Adapter, EEPROM_SPI_Q_STATUS1_REG, &uiStatus, sizeof(uiStatus));
162 if(Adapter->device_removed == TRUE)
163 {
164 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Modem has got Removed.hence exiting from loop...");
165 return -ENODEV;
166 }
167
168 /* If we are reading 16 bytes we want to be sure that the queue
169 * is full before we read. In the other cases we are ok if the
170 * queue has data available */
171 if ( dwNumWords == 4 )
172 {
173 if ( ( uiStatus & EEPROM_READ_DATA_FULL ) != 0 )
174 {
175 /* Clear the Avail/Full bits - which ever is set. */
176 value = ( uiStatus & (EEPROM_READ_DATA_AVAIL | EEPROM_READ_DATA_FULL) ) ;
177 wrmalt( Adapter, EEPROM_SPI_Q_STATUS1_REG,&value, sizeof(value));
178 break;
179 }
180 }
181 else if ( dwNumWords == 1 )
182 {
183
184 if ( ( uiStatus & EEPROM_READ_DATA_AVAIL ) != 0 )
185 {
186 /* We just got Avail and we have to read 32bits so we
187 * need this sleep for Cardbus kind of devices. */
188 if (Adapter->chip_id == 0xBECE0210 )
189 udelay(800);
190
191 /* Clear the Avail/Full bits - which ever is set. */
192 value=( uiStatus & (EEPROM_READ_DATA_AVAIL | EEPROM_READ_DATA_FULL) );
193 wrmalt( Adapter, EEPROM_SPI_Q_STATUS1_REG,&value, sizeof(value));
194 break;
195 }
196 }
197
198 uiStatus = 0;
199
200 dwRetries--;
201 if(dwRetries == 0)
202 {
203 value=0;
204 value1=0;
205 rdmalt(Adapter, EEPROM_SPI_Q_STATUS1_REG,&value, sizeof(value));
206 rdmalt(Adapter, EEPROM_SPI_Q_STATUS_REG,&value1, sizeof(value1));
207 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);
208 return STATUS_FAILURE;
209 }
210 if( !(dwRetries%RETRIES_PER_DELAY) )
211 msleep(1);
212 }
213
214 for ( dwIndex = 0; dwIndex < dwNumWords ; dwIndex++ )
215 {
216 /* We get only a byte at a time - from LSB to MSB. We shift it into an integer. */
217 pvalue = (PUCHAR)(pdwData + dwIndex);
218
219 value =0;
220 rdmalt(Adapter, EEPROM_READ_DATAQ_REG,&value, sizeof(value));
221
222 pvalue[0] = value;
223
224 value = 0;
225 rdmalt(Adapter, EEPROM_READ_DATAQ_REG,&value, sizeof(value));
226
227 pvalue[1] = value;
228
229 value =0;
230 rdmalt(Adapter, EEPROM_READ_DATAQ_REG,&value, sizeof(value));
231
232 pvalue[2] = value;
233
234 value = 0;
235 rdmalt(Adapter, EEPROM_READ_DATAQ_REG,&value, sizeof(value));
236
237 pvalue[3] = value;
238 }
239
240 return STATUS_SUCCESS;
241} /* ReadBeceemEEPROMBulk() */
242
243//-----------------------------------------------------------------------------
244// Procedure: ReadBeceemEEPROM
245//
246// Description: This routine reads 4 data from EEPROM. It uses 1 or 2 page
247// reads to do this operation.
248//
249// Arguments:
250// Adapter - ptr to Adapter object instance
251// uiOffset - EEPROM Offset to read the data from.
252// pBuffer - Pointer to word where data needs to be stored in.
253//
254// Returns:
255// OSAL_STATUS_CODE:
256//-----------------------------------------------------------------------------
257
258INT ReadBeceemEEPROM( PMINI_ADAPTER Adapter,
259 DWORD uiOffset,
260 DWORD *pBuffer
261 )
262{
263 UINT uiData[8] = {0};
264 UINT uiByteOffset = 0;
265 UINT uiTempOffset = 0;
266
267 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL," ====> ");
268
269 uiTempOffset = uiOffset - (uiOffset % MAX_RW_SIZE);
270 uiByteOffset = uiOffset - uiTempOffset;
271
272 ReadBeceemEEPROMBulk(Adapter, uiTempOffset, (PUINT)&uiData[0], 4);
273
274 /* A word can overlap at most over 2 pages. In that case we read the
275 * next page too. */
276 if ( uiByteOffset > 12 )
277 {
278 ReadBeceemEEPROMBulk(Adapter, uiTempOffset + MAX_RW_SIZE, (PUINT)&uiData[4], 4);
279 }
280
082e889b 281 memcpy( (PUCHAR) pBuffer, ( ((PUCHAR)&uiData[0]) + uiByteOffset ), 4);
f8942e07
SH
282
283 return STATUS_SUCCESS;
284} /* ReadBeceemEEPROM() */
285
286
f8942e07
SH
287
288INT ReadMacAddressFromNVM(PMINI_ADAPTER Adapter)
289{
4ea4f7a0
SH
290 INT Status;
291 unsigned char puMacAddr[6];
f8942e07
SH
292
293 Status = BeceemNVMRead(Adapter,
294 (PUINT)&puMacAddr[0],
295 INIT_PARAMS_1_MACADDRESS_ADDRESS,
296 MAC_ADDRESS_SIZE);
297
4ea4f7a0
SH
298 if(Status == STATUS_SUCCESS)
299 memcpy(Adapter->dev->dev_addr, puMacAddr, MAC_ADDRESS_SIZE);
f8942e07
SH
300
301 return Status;
f8942e07
SH
302}
303
304//-----------------------------------------------------------------------------
305// Procedure: BeceemEEPROMBulkRead
306//
307// Description: Reads the EEPROM and returns the Data.
308//
309// Arguments:
310// Adapter - ptr to Adapter object instance
311// pBuffer - Buffer to store the data read from EEPROM
312// uiOffset - Offset of EEPROM from where data should be read
313// uiNumBytes - Number of bytes to be read from the EEPROM.
314//
315// Returns:
25985edc 316// OSAL_STATUS_SUCCESS - if EEPROM read is successful.
f8942e07
SH
317// <FAILURE> - if failed.
318//-----------------------------------------------------------------------------
319
320INT BeceemEEPROMBulkRead(
321 PMINI_ADAPTER Adapter,
322 PUINT pBuffer,
323 UINT uiOffset,
324 UINT uiNumBytes)
325{
326 UINT uiData[4] = {0};
327 //UINT uiAddress = 0;
328 UINT uiBytesRemaining = uiNumBytes;
329 UINT uiIndex = 0;
330 UINT uiTempOffset = 0;
331 UINT uiExtraBytes = 0;
332 UINT uiFailureRetries = 0;
333 PUCHAR pcBuff = (PUCHAR)pBuffer;
334
335
336 if(uiOffset%MAX_RW_SIZE&& uiBytesRemaining)
337 {
338 uiTempOffset = uiOffset - (uiOffset%MAX_RW_SIZE);
339 uiExtraBytes = uiOffset-uiTempOffset;
340 ReadBeceemEEPROMBulk(Adapter,uiTempOffset,(PUINT)&uiData[0],4);
341 if(uiBytesRemaining >= (MAX_RW_SIZE - uiExtraBytes))
342 {
082e889b 343 memcpy(pBuffer,(((PUCHAR)&uiData[0])+uiExtraBytes),MAX_RW_SIZE - uiExtraBytes);
f8942e07
SH
344
345 uiBytesRemaining -= (MAX_RW_SIZE - uiExtraBytes);
346 uiIndex += (MAX_RW_SIZE - uiExtraBytes);
347 uiOffset += (MAX_RW_SIZE - uiExtraBytes);
348 }
349 else
350 {
082e889b 351 memcpy(pBuffer,(((PUCHAR)&uiData[0])+uiExtraBytes),uiBytesRemaining);
f8942e07
SH
352 uiIndex += uiBytesRemaining;
353 uiOffset += uiBytesRemaining;
354 uiBytesRemaining = 0;
355 }
356
357
358 }
359
360
361 while(uiBytesRemaining && uiFailureRetries != 128)
362 {
363 if(Adapter->device_removed )
364 {
365 return -1;
366 }
367
368 if(uiBytesRemaining >= MAX_RW_SIZE)
369 {
370 /* For the requests more than or equal to 16 bytes, use bulk
371 * read function to make the access faster.
372 * We read 4 Dwords of data */
373 if(0 == ReadBeceemEEPROMBulk(Adapter,uiOffset,&uiData[0],4))
374 {
082e889b 375 memcpy(pcBuff+uiIndex,&uiData[0],MAX_RW_SIZE);
f8942e07
SH
376 uiOffset += MAX_RW_SIZE;
377 uiBytesRemaining -= MAX_RW_SIZE;
378 uiIndex += MAX_RW_SIZE;
379 }
380 else
381 {
382 uiFailureRetries++;
383 mdelay(3);//sleep for a while before retry...
384 }
385 }
386 else if(uiBytesRemaining >= 4)
387 {
388 if(0 == ReadBeceemEEPROM(Adapter,uiOffset,&uiData[0]))
389 {
082e889b 390 memcpy(pcBuff+uiIndex,&uiData[0],4);
f8942e07
SH
391 uiOffset += 4;
392 uiBytesRemaining -= 4;
393 uiIndex +=4;
394 }
395 else
396 {
397 uiFailureRetries++;
398 mdelay(3);//sleep for a while before retry...
399 }
400 }
401 else
402 { // Handle the reads less than 4 bytes...
403 PUCHAR pCharBuff = (PUCHAR)pBuffer;
404 pCharBuff += uiIndex;
405 if(0 == ReadBeceemEEPROM(Adapter,uiOffset,&uiData[0]))
406 {
082e889b 407 memcpy(pCharBuff,&uiData[0],uiBytesRemaining);//copy only bytes requested.
f8942e07
SH
408 uiBytesRemaining = 0;
409 }
410 else
411 {
412 uiFailureRetries++;
413 mdelay(3);//sleep for a while before retry...
414 }
415 }
416
417 }
418
419 return 0;
420}
421
422//-----------------------------------------------------------------------------
423// Procedure: BeceemFlashBulkRead
424//
425// Description: Reads the FLASH and returns the Data.
426//
427// Arguments:
428// Adapter - ptr to Adapter object instance
429// pBuffer - Buffer to store the data read from FLASH
430// uiOffset - Offset of FLASH from where data should be read
431// uiNumBytes - Number of bytes to be read from the FLASH.
432//
433// Returns:
25985edc 434// OSAL_STATUS_SUCCESS - if FLASH read is successful.
f8942e07
SH
435// <FAILURE> - if failed.
436//-----------------------------------------------------------------------------
437
9dd47ee7 438static INT BeceemFlashBulkRead(
f8942e07
SH
439 PMINI_ADAPTER Adapter,
440 PUINT pBuffer,
441 UINT uiOffset,
442 UINT uiNumBytes)
443{
444 UINT uiIndex = 0;
445 UINT uiBytesToRead = uiNumBytes;
446 INT Status = 0;
447 UINT uiPartOffset = 0;
448
449 if(Adapter->device_removed )
450 {
451 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "Device Got Removed ");
452 return -ENODEV;
453 }
454
455 //Adding flash Base address
456// uiOffset = uiOffset + GetFlashBaseAddr(Adapter);
457#if defined(BCM_SHM_INTERFACE) && !defined(FLASH_DIRECT_ACCESS)
458 Status = bcmflash_raw_read((uiOffset/FLASH_PART_SIZE),(uiOffset % FLASH_PART_SIZE),( unsigned char *)pBuffer,uiNumBytes);
459 return Status;
460#endif
461
462 Adapter->SelectedChip = RESET_CHIP_SELECT;
463
464 if(uiOffset % MAX_RW_SIZE)
465 {
466 BcmDoChipSelect(Adapter,uiOffset);
467 uiPartOffset = (uiOffset & (FLASH_PART_SIZE - 1)) + GetFlashBaseAddr(Adapter);
468
469 uiBytesToRead = MAX_RW_SIZE - (uiOffset%MAX_RW_SIZE);
470 uiBytesToRead = MIN(uiNumBytes,uiBytesToRead);
471
472 if(rdm(Adapter,uiPartOffset, (PCHAR)pBuffer+uiIndex,uiBytesToRead))
473 {
474 Status = -1;
475 Adapter->SelectedChip = RESET_CHIP_SELECT;
476 return Status;
477 }
478
479 uiIndex += uiBytesToRead;
480 uiOffset += uiBytesToRead;
481 uiNumBytes -= uiBytesToRead;
482 }
483
484 while(uiNumBytes)
485 {
486 BcmDoChipSelect(Adapter,uiOffset);
487 uiPartOffset = (uiOffset & (FLASH_PART_SIZE - 1)) + GetFlashBaseAddr(Adapter);
488
489 uiBytesToRead = MIN(uiNumBytes,MAX_RW_SIZE);
490
491 if(rdm(Adapter,uiPartOffset, (PCHAR)pBuffer+uiIndex,uiBytesToRead))
492 {
493 Status = -1;
494 break;
495 }
496
497
498 uiIndex += uiBytesToRead;
499 uiOffset += uiBytesToRead;
500 uiNumBytes -= uiBytesToRead;
501
502 }
503 Adapter->SelectedChip = RESET_CHIP_SELECT;
504 return Status;
505}
506
507//-----------------------------------------------------------------------------
508// Procedure: BcmGetFlashSize
509//
510// Description: Finds the size of FLASH.
511//
512// Arguments:
513// Adapter - ptr to Adapter object instance
514//
515// Returns:
516// UINT - size of the FLASH Storage.
517//
518//-----------------------------------------------------------------------------
519
9dd47ee7 520static UINT BcmGetFlashSize(PMINI_ADAPTER Adapter)
f8942e07 521{
f8942e07
SH
522 if(IsFlash2x(Adapter))
523 return (Adapter->psFlash2xCSInfo->OffsetFromDSDStartForDSDHeader + sizeof(DSD_HEADER));
524 else
525 return 32*1024;
526
527
528}
529
530//-----------------------------------------------------------------------------
531// Procedure: BcmGetEEPROMSize
532//
533// Description: Finds the size of EEPROM.
534//
535// Arguments:
536// Adapter - ptr to Adapter object instance
537//
538// Returns:
539// UINT - size of the EEPROM Storage.
540//
541//-----------------------------------------------------------------------------
542
9dd47ee7 543static UINT BcmGetEEPROMSize(PMINI_ADAPTER Adapter)
f8942e07
SH
544{
545 UINT uiData = 0;
546 UINT uiIndex = 0;
547
548//
549// if EEPROM is present and already Calibrated,it will have
550// 'BECM' string at 0th offset.
551// To find the EEPROM size read the possible boundaries of the
552// EEPROM like 4K,8K etc..accessing the EEPROM beyond its size will
553// result in wrap around. So when we get the End of the EEPROM we will
554// get 'BECM' string which is indeed at offset 0.
555//
556 BeceemEEPROMBulkRead(Adapter,&uiData,0x0,4);
557 if(uiData == BECM)
558 {
559 for(uiIndex = 2;uiIndex <=256; uiIndex*=2)
560 {
561 BeceemEEPROMBulkRead(Adapter,&uiData,uiIndex*1024,4);
562 if(uiData == BECM)
563 {
564 return uiIndex*1024;
565 }
566 }
567 }
568 else
569 {
570//
571// EEPROM may not be present or not programmed
572//
573
574 uiData = 0xBABEFACE;
575 if(0 == BeceemEEPROMBulkWrite(Adapter,(PUCHAR)&uiData,0,4,TRUE))
576 {
577 uiData = 0;
578 for(uiIndex = 2;uiIndex <=256; uiIndex*=2)
579 {
580 BeceemEEPROMBulkRead(Adapter,&uiData,uiIndex*1024,4);
581 if(uiData == 0xBABEFACE)
582 {
583 return uiIndex*1024;
584 }
585 }
586 }
587
588 }
589 return 0;
590}
591
f8942e07
SH
592
593//-----------------------------------------------------------------------------
594// Procedure: FlashSectorErase
595//
596// Description: Finds the sector size of the FLASH.
597//
598// Arguments:
599// Adapter - ptr to Adapter object instance
600// addr - sector start address
601// numOfSectors - number of sectors to be erased.
602//
603// Returns:
604// OSAL_STATUS_CODE
605//
606//-----------------------------------------------------------------------------
607
608
44a17eff 609static INT FlashSectorErase(PMINI_ADAPTER Adapter,
f8942e07
SH
610 UINT addr,
611 UINT numOfSectors)
612{
613 UINT iIndex = 0, iRetries = 0;
614 UINT uiStatus = 0;
615 UINT value;
616
617 for(iIndex=0;iIndex<numOfSectors;iIndex++)
618 {
619 value = 0x06000000;
620 wrmalt(Adapter, FLASH_SPI_CMDQ_REG, &value, sizeof(value));
621
622 value = (0xd8000000 | (addr & 0xFFFFFF));
623 wrmalt(Adapter, FLASH_SPI_CMDQ_REG, &value, sizeof(value));
624 iRetries = 0;
625
626 do
627 {
628 value = (FLASH_CMD_STATUS_REG_READ << 24);
629 if(wrmalt(Adapter, FLASH_SPI_CMDQ_REG, &value, sizeof(value)) < 0)
630 {
631 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Programing of FLASH_SPI_CMDQ_REG fails");
632 return STATUS_FAILURE;
633 }
634
635 if(rdmalt(Adapter, FLASH_SPI_READQ_REG, &uiStatus, sizeof(uiStatus)) < 0 )
636 {
637 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Reading status of FLASH_SPI_READQ_REG fails");
638 return STATUS_FAILURE;
639 }
640 iRetries++;
641 //After every try lets make the CPU free for 10 ms. generally time taken by the
642 //the sector erase cycle is 500 ms to 40000 msec. hence sleeping 10 ms
643 //won't hamper performance in any case.
644 msleep(10);
645 }while((uiStatus & 0x1) && (iRetries < 400));
646
647 if(uiStatus & 0x1)
648 {
649 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"iRetries crossing the limit of 80000\n");
650 return STATUS_FAILURE;
651 }
652
653 addr += Adapter->uiSectorSize;
654 }
655 return 0;
656}
657//-----------------------------------------------------------------------------
658// Procedure: flashByteWrite
659//
660// Description: Performs Byte by Byte write to flash
661//
662// Arguments:
663// Adapter - ptr to Adapter object instance
664// uiOffset - Offset of the flash where data needs to be written to.
665// pData - Address of Data to be written.
666// Returns:
667// OSAL_STATUS_CODE
668//
669//-----------------------------------------------------------------------------
670
44a17eff 671static INT flashByteWrite(
f8942e07
SH
672 PMINI_ADAPTER Adapter,
673 UINT uiOffset,
674 PVOID pData)
675{
676
677 UINT uiStatus = 0;
678 INT iRetries = MAX_FLASH_RETRIES * FLASH_PER_RETRIES_DELAY; //3
679
680 UINT value;
681 ULONG ulData = *(PUCHAR)pData;
682
683//
684// need not write 0xFF because write requires an erase and erase will
685// make whole sector 0xFF.
686//
687
688 if(0xFF == ulData)
689 {
690 return STATUS_SUCCESS;
691 }
692
693// DumpDebug(NVM_RW,("flashWrite ====>\n"));
694 value = (FLASH_CMD_WRITE_ENABLE << 24);
695 if(wrmalt(Adapter, FLASH_SPI_CMDQ_REG,&value, sizeof(value)) < 0)
696 {
697 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Write enable in FLASH_SPI_CMDQ_REG register fails");
698 return STATUS_FAILURE;
699 }
700 if(wrm(Adapter,FLASH_SPI_WRITEQ_REG, (PCHAR)&ulData, 4) < 0 )
701 {
702 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"DATA Write on FLASH_SPI_WRITEQ_REG fails");
703 return STATUS_FAILURE;
704 }
705 value = (0x02000000 | (uiOffset & 0xFFFFFF));
706 if(wrmalt(Adapter, FLASH_SPI_CMDQ_REG,&value, sizeof(value)) < 0 )
707 {
708 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Programming of FLASH_SPI_CMDQ_REG fails");
709 return STATUS_FAILURE;
710 }
711
712 //__udelay(950);
713
714 do
715 {
716 value = (FLASH_CMD_STATUS_REG_READ << 24);
717 if(wrmalt(Adapter, FLASH_SPI_CMDQ_REG, &value, sizeof(value)) < 0)
718 {
719 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Programing of FLASH_SPI_CMDQ_REG fails");
720 return STATUS_FAILURE;
721 }
722 //__udelay(1);
723 if(rdmalt(Adapter, FLASH_SPI_READQ_REG, &uiStatus, sizeof(uiStatus)) < 0)
724 {
725 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Reading status of FLASH_SPI_READQ_REG fails");
726 return STATUS_FAILURE;
727 }
728 iRetries--;
729 if( iRetries && ((iRetries % FLASH_PER_RETRIES_DELAY) == 0))
730 msleep(1);
731
732 }while((uiStatus & 0x1) && (iRetries >0) );
733
734 if(uiStatus & 0x1)
735 {
736 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Flash Write fails even after checking status for 200 times.");
737 return STATUS_FAILURE ;
738 }
739
740 return STATUS_SUCCESS;
741}
742
743
744
745//-----------------------------------------------------------------------------
746// Procedure: flashWrite
747//
748// Description: Performs write to flash
749//
750// Arguments:
751// Adapter - ptr to Adapter object instance
752// uiOffset - Offset of the flash where data needs to be written to.
753// pData - Address of Data to be written.
754// Returns:
755// OSAL_STATUS_CODE
756//
757//-----------------------------------------------------------------------------
758
44a17eff 759static INT flashWrite(
f8942e07
SH
760 PMINI_ADAPTER Adapter,
761 UINT uiOffset,
762 PVOID pData)
763
764{
765 //UINT uiStatus = 0;
766 //INT iRetries = 0;
767 //UINT uiReadBack = 0;
768
769 UINT uiStatus = 0;
770 INT iRetries = MAX_FLASH_RETRIES * FLASH_PER_RETRIES_DELAY; //3
771
772 UINT value;
773 UINT uiErasePattern[4] = {0xFFFFFFFF,0xFFFFFFFF,0xFFFFFFFF,0xFFFFFFFF};
774//
775// need not write 0xFFFFFFFF because write requires an erase and erase will
776// make whole sector 0xFFFFFFFF.
777//
082e889b 778 if (!memcmp(pData, uiErasePattern, MAX_RW_SIZE))
f8942e07
SH
779 {
780 return 0;
781 }
782
783 value = (FLASH_CMD_WRITE_ENABLE << 24);
784
785 if(wrmalt(Adapter, FLASH_SPI_CMDQ_REG,&value, sizeof(value)) < 0 )
786 {
787 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Write Enable of FLASH_SPI_CMDQ_REG fails");
788 return STATUS_FAILURE;
789 }
790 if(wrm(Adapter, uiOffset, (PCHAR)pData, MAX_RW_SIZE) < 0)
791 {
792 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Data write fails...");
793 return STATUS_FAILURE;
794 }
795
796 //__udelay(950);
797 do
798 {
799 value = (FLASH_CMD_STATUS_REG_READ << 24);
800 if(wrmalt(Adapter, FLASH_SPI_CMDQ_REG, &value, sizeof(value)) < 0)
801 {
802 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Programing of FLASH_SPI_CMDQ_REG fails");
803 return STATUS_FAILURE;
804 }
805 //__udelay(1);
806 if(rdmalt(Adapter, FLASH_SPI_READQ_REG, &uiStatus, sizeof(uiStatus)) < 0 )
807 {
808 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Reading status of FLASH_SPI_READQ_REG fails");
809 return STATUS_FAILURE;
810 }
811
812 iRetries--;
813 //this will ensure that in there will be no changes in the current path.
814 //currently one rdm/wrm takes 125 us.
815 //Hence 125 *2 * FLASH_PER_RETRIES_DELAY > 3 ms(worst case delay)
816 //Hence current implementation cycle will intoduce no delay in current path
817 if(iRetries && ((iRetries % FLASH_PER_RETRIES_DELAY) == 0))
818 msleep(1);
819 }while((uiStatus & 0x1) && (iRetries > 0));
820
821 if(uiStatus & 0x1)
822 {
823 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Flash Write fails even after checking status for 200 times.");
824 return STATUS_FAILURE ;
825 }
826
827 return STATUS_SUCCESS;
828}
829
830//-----------------------------------------------------------------------------
831// Procedure: flashByteWriteStatus
832//
833// Description: Performs byte by byte write to flash with write done status check
834//
835// Arguments:
836// Adapter - ptr to Adapter object instance
837// uiOffset - Offset of the flash where data needs to be written to.
838// pData - Address of the Data to be written.
839// Returns:
840// OSAL_STATUS_CODE
841//
842//-----------------------------------------------------------------------------
44a17eff 843static INT flashByteWriteStatus(
f8942e07
SH
844 PMINI_ADAPTER Adapter,
845 UINT uiOffset,
846 PVOID pData)
847{
848 UINT uiStatus = 0;
849 INT iRetries = MAX_FLASH_RETRIES * FLASH_PER_RETRIES_DELAY; //3
850 ULONG ulData = *(PUCHAR)pData;
851 UINT value;
852
853//
854// need not write 0xFFFFFFFF because write requires an erase and erase will
855// make whole sector 0xFFFFFFFF.
856//
857
858 if(0xFF == ulData)
859 {
860 return STATUS_SUCCESS;
861 }
862
863 // DumpDebug(NVM_RW,("flashWrite ====>\n"));
864
865 value = (FLASH_CMD_WRITE_ENABLE << 24);
866 if(wrmalt(Adapter, FLASH_SPI_CMDQ_REG,&value, sizeof(value)) < 0)
867 {
868 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Write enable in FLASH_SPI_CMDQ_REG register fails");
869 return STATUS_SUCCESS;
870 }
871 if(wrm(Adapter,FLASH_SPI_WRITEQ_REG, (PCHAR)&ulData, 4) < 0)
872 {
873 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"DATA Write on FLASH_SPI_WRITEQ_REG fails");
874 return STATUS_FAILURE;
875 }
876 value = (0x02000000 | (uiOffset & 0xFFFFFF));
877 if(wrmalt(Adapter, FLASH_SPI_CMDQ_REG,&value, sizeof(value)) < 0)
878 {
879 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Programming of FLASH_SPI_CMDQ_REG fails");
880 return STATUS_FAILURE;
881 }
882
883 //msleep(1);
884
885 do
886 {
887 value = (FLASH_CMD_STATUS_REG_READ << 24);
888 if(wrmalt(Adapter, FLASH_SPI_CMDQ_REG, &value, sizeof(value)) < 0)
889 {
890 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Programing of FLASH_SPI_CMDQ_REG fails");
891 return STATUS_FAILURE;
892 }
893 //__udelay(1);
894 if(rdmalt(Adapter, FLASH_SPI_READQ_REG, &uiStatus, sizeof(uiStatus)) < 0)
895 {
896 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Reading status of FLASH_SPI_READQ_REG fails");
897 return STATUS_FAILURE;
898 }
899
900 iRetries--;
901 if( iRetries && ((iRetries % FLASH_PER_RETRIES_DELAY) == 0))
902 msleep(1);
903 }while((uiStatus & 0x1) && (iRetries > 0));
904
905 if(uiStatus & 0x1)
906 {
907 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Flash Write fails even after checking status for 200 times.");
908 return STATUS_FAILURE ;
909 }
910
911 return STATUS_SUCCESS;
912
913}
914//-----------------------------------------------------------------------------
915// Procedure: flashWriteStatus
916//
917// Description: Performs write to flash with write done status check
918//
919// Arguments:
920// Adapter - ptr to Adapter object instance
921// uiOffset - Offset of the flash where data needs to be written to.
922// pData - Address of the Data to be written.
923// Returns:
924// OSAL_STATUS_CODE
925//
926//-----------------------------------------------------------------------------
927
44a17eff 928static INT flashWriteStatus(
f8942e07
SH
929 PMINI_ADAPTER Adapter,
930 UINT uiOffset,
931 PVOID pData)
932{
933 UINT uiStatus = 0;
934 INT iRetries = MAX_FLASH_RETRIES * FLASH_PER_RETRIES_DELAY; //3
935 //UINT uiReadBack = 0;
936 UINT value;
937 UINT uiErasePattern[4] = {0xFFFFFFFF,0xFFFFFFFF,0xFFFFFFFF,0xFFFFFFFF};
938
939//
940// need not write 0xFFFFFFFF because write requires an erase and erase will
941// make whole sector 0xFFFFFFFF.
942//
082e889b 943 if (!memcmp(pData,uiErasePattern,MAX_RW_SIZE))
f8942e07
SH
944 {
945 return 0;
946 }
947
948 value = (FLASH_CMD_WRITE_ENABLE << 24);
949 if(wrmalt(Adapter, FLASH_SPI_CMDQ_REG,&value, sizeof(value)) < 0)
950 {
951 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Write Enable of FLASH_SPI_CMDQ_REG fails");
952 return STATUS_FAILURE;
953 }
954 if(wrm(Adapter, uiOffset, (PCHAR)pData, MAX_RW_SIZE) < 0)
955 {
956 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Data write fails...");
957 return STATUS_FAILURE;
958 }
959 // __udelay(1);
960
961 do
962 {
963 value = (FLASH_CMD_STATUS_REG_READ << 24);
964 if(wrmalt(Adapter, FLASH_SPI_CMDQ_REG, &value, sizeof(value)) < 0)
965 {
966 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Programing of FLASH_SPI_CMDQ_REG fails");
967 return STATUS_FAILURE;
968 }
969 //__udelay(1);
970 if(rdmalt(Adapter, FLASH_SPI_READQ_REG, &uiStatus, sizeof(uiStatus)) < 0)
971 {
972 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Reading status of FLASH_SPI_READQ_REG fails");
973 return STATUS_FAILURE;
974 }
975 iRetries--;
976 //this will ensure that in there will be no changes in the current path.
977 //currently one rdm/wrm takes 125 us.
978 //Hence 125 *2 * FLASH_PER_RETRIES_DELAY >3 ms(worst case delay)
979 //Hence current implementation cycle will intoduce no delay in current path
980 if(iRetries && ((iRetries % FLASH_PER_RETRIES_DELAY) == 0))
981 msleep(1);
982 }while((uiStatus & 0x1) && (iRetries >0));
983
984 if(uiStatus & 0x1)
985 {
986 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Flash Write fails even after checking status for 200 times.");
987 return STATUS_FAILURE ;
988 }
989
990 return STATUS_SUCCESS;
991}
992
993//-----------------------------------------------------------------------------
994// Procedure: BcmRestoreBlockProtectStatus
995//
996// Description: Restores the original block protection status.
997//
998// Arguments:
999// Adapter - ptr to Adapter object instance
1000// ulWriteStatus -Original status
1001// Returns:
1002// <VOID>
1003//
1004//-----------------------------------------------------------------------------
1005
44a17eff 1006static VOID BcmRestoreBlockProtectStatus(PMINI_ADAPTER Adapter,ULONG ulWriteStatus)
f8942e07
SH
1007{
1008 UINT value;
1009 value = (FLASH_CMD_WRITE_ENABLE<< 24);
1010 wrmalt(Adapter, FLASH_SPI_CMDQ_REG, &value, sizeof(value));
1011
1012 udelay(20);
1013 value = (FLASH_CMD_STATUS_REG_WRITE<<24)|(ulWriteStatus << 16);
1014 wrmalt(Adapter, FLASH_SPI_CMDQ_REG, &value, sizeof(value));
1015 udelay(20);
1016}
1017//-----------------------------------------------------------------------------
1018// Procedure: BcmFlashUnProtectBlock
1019//
1020// Description: UnProtects appropriate blocks for writing.
1021//
1022// Arguments:
1023// Adapter - ptr to Adapter object instance
1024// uiOffset - Offset of the flash where data needs to be written to. This should be Sector aligned.
1025// Returns:
1026// ULONG - Status value before UnProtect.
1027//
1028//-----------------------------------------------------------------------------
44a17eff 1029static ULONG BcmFlashUnProtectBlock(PMINI_ADAPTER Adapter,UINT uiOffset, UINT uiLength)
f8942e07
SH
1030{
1031 ULONG ulStatus = 0;
1032 ULONG ulWriteStatus = 0;
1033 UINT value;
1034 uiOffset = uiOffset&0x000FFFFF;
1035
1036//
1037// Implemented only for 1MB Flash parts.
1038//
1039 if(FLASH_PART_SST25VF080B == Adapter->ulFlashID)
1040 {
1041 //
1042 // Get Current BP status.
1043 //
1044 value = (FLASH_CMD_STATUS_REG_READ << 24);
1045 wrmalt(Adapter, FLASH_SPI_CMDQ_REG, &value, sizeof(value));
1046 udelay(10);
1047 //
1048 // Read status will be WWXXYYZZ. We have to take only WW.
1049 //
1050 rdmalt(Adapter, FLASH_SPI_READQ_REG, (PUINT)&ulStatus, sizeof(ulStatus));
1051 ulStatus >>= 24;
1052 ulWriteStatus = ulStatus;
1053
1054 //
1055 // Bits [5-2] give current block level protection status.
1056 // Bit5: BP3 - DONT CARE
1057 // BP2-BP0: 0 - NO PROTECTION, 1 - UPPER 1/16, 2 - UPPER 1/8, 3 - UPPER 1/4
1058 // 4 - UPPER 1/2. 5 to 7 - ALL BLOCKS
1059 //
1060
1061 if(ulStatus)
1062 {
1063 if((uiOffset+uiLength) <= 0x80000)
1064 {
1065 //
1066 // Offset comes in lower half of 1MB. Protect the upper half.
1067 // Clear BP1 and BP0 and set BP2.
1068 //
1069 ulWriteStatus |= (0x4<<2);
1070 ulWriteStatus &= ~(0x3<<2);
1071 }
1072 else if((uiOffset+uiLength) <= 0xC0000)
1073 {
1074 //
1075 // Offset comes below Upper 1/4. Upper 1/4 can be protected.
1076 // Clear BP2 and set BP1 and BP0.
1077 //
1078 ulWriteStatus |= (0x3<<2);
1079 ulWriteStatus &= ~(0x1<<4);
1080 }
1081 else if((uiOffset+uiLength) <= 0xE0000)
1082 {
1083 //
1084 // Offset comes below Upper 1/8. Upper 1/8 can be protected.
1085 // Clear BP2 and BP0 and set BP1
1086 //
1087 ulWriteStatus |= (0x1<<3);
1088 ulWriteStatus &= ~(0x5<<2);
1089
1090 }
1091 else if((uiOffset+uiLength) <= 0xF0000)
1092 {
1093 //
1094 // Offset comes below Upper 1/16. Only upper 1/16 can be protected.
1095 // Set BP0 and Clear BP2,BP1.
1096 //
1097 ulWriteStatus |= (0x1<<2);
1098 ulWriteStatus &= ~(0x3<<3);
1099 }
1100 else
1101 {
1102 //
1103 // Unblock all.
1104 // Clear BP2,BP1 and BP0.
1105 //
1106 ulWriteStatus &= ~(0x7<<2);
1107 }
1108
1109 value = (FLASH_CMD_WRITE_ENABLE<< 24);
1110 wrmalt(Adapter, FLASH_SPI_CMDQ_REG, &value, sizeof(value));
1111 udelay(20);
1112 value = (FLASH_CMD_STATUS_REG_WRITE<<24)|(ulWriteStatus << 16);
1113 wrmalt(Adapter, FLASH_SPI_CMDQ_REG, &value, sizeof(value));
1114 udelay(20);
1115
1116 }
1117
1118 }
1119 return ulStatus;
1120}
1121//-----------------------------------------------------------------------------
1122// Procedure: BeceemFlashBulkWrite
1123//
1124// Description: Performs write to the flash
1125//
1126// Arguments:
1127// Adapter - ptr to Adapter object instance
1128// pBuffer - Data to be written.
1129// uiOffset - Offset of the flash where data needs to be written to.
1130// uiNumBytes - Number of bytes to be written.
1131// bVerify - read verify flag.
1132// Returns:
1133// OSAL_STATUS_CODE
1134//
1135//-----------------------------------------------------------------------------
1136
9dd47ee7 1137static INT BeceemFlashBulkWrite(
f8942e07
SH
1138 PMINI_ADAPTER Adapter,
1139 PUINT pBuffer,
1140 UINT uiOffset,
1141 UINT uiNumBytes,
1142 BOOLEAN bVerify)
1143{
1144 PCHAR pTempBuff = NULL;
1145 PUCHAR pcBuffer = (PUCHAR)pBuffer;
1146 UINT uiIndex = 0;
1147 UINT uiOffsetFromSectStart = 0;
1148 UINT uiSectAlignAddr = 0;
1149 UINT uiCurrSectOffsetAddr = 0;
1150 UINT uiSectBoundary = 0;
1151 UINT uiNumSectTobeRead = 0;
1152 UCHAR ucReadBk[16] = {0};
1153 ULONG ulStatus = 0;
1154 INT Status = STATUS_SUCCESS;
1155 UINT uiTemp = 0;
1156 UINT index = 0;
1157 UINT uiPartOffset = 0;
f8942e07
SH
1158
1159#if defined(BCM_SHM_INTERFACE) && !defined(FLASH_DIRECT_ACCESS)
1160 Status = bcmflash_raw_write((uiOffset/FLASH_PART_SIZE),(uiOffset % FLASH_PART_SIZE),( unsigned char *)pBuffer,uiNumBytes);
1161 return Status;
1162#endif
1163
1164 uiOffsetFromSectStart = uiOffset & ~(Adapter->uiSectorSize - 1);
1165
1166 //Adding flash Base address
1167// uiOffset = uiOffset + GetFlashBaseAddr(Adapter);
1168
1169 uiSectAlignAddr = uiOffset & ~(Adapter->uiSectorSize - 1);
1170 uiCurrSectOffsetAddr = uiOffset & (Adapter->uiSectorSize - 1);
1171 uiSectBoundary = uiSectAlignAddr + Adapter->uiSectorSize;
1172
082e889b 1173 pTempBuff = kmalloc(Adapter->uiSectorSize, GFP_KERNEL);
f8942e07 1174 if(NULL == pTempBuff)
f8942e07 1175 goto BeceemFlashBulkWrite_EXIT;
f8942e07 1176//
25985edc 1177// check if the data to be written is overlapped across sectors
f8942e07
SH
1178//
1179 if(uiOffset+uiNumBytes < uiSectBoundary)
1180 {
1181 uiNumSectTobeRead = 1;
1182 }
1183 else
1184 {
1185 // Number of sectors = Last sector start address/First sector start address
1186 uiNumSectTobeRead = (uiCurrSectOffsetAddr+uiNumBytes)/Adapter->uiSectorSize;
1187 if((uiCurrSectOffsetAddr+uiNumBytes)%Adapter->uiSectorSize)
1188 {
1189 uiNumSectTobeRead++;
1190 }
1191 }
f8942e07
SH
1192 //Check whether Requested sector is writable or not in case of flash2x write. But if write call is
1193 // for DSD calibration, allow it without checking of sector permission
1194
1195 if(IsFlash2x(Adapter) && (Adapter->bAllDSDWriteAllow == FALSE))
1196 {
1197 index = 0;
1198 uiTemp = uiNumSectTobeRead ;
1199 while(uiTemp)
1200 {
1201 if(IsOffsetWritable(Adapter, uiOffsetFromSectStart + index * Adapter->uiSectorSize ) == FALSE)
1202 {
1203 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Sector Starting at offset <0X%X> is not writable",
1204 (uiOffsetFromSectStart + index * Adapter->uiSectorSize));
1205 Status = SECTOR_IS_NOT_WRITABLE;
1206 goto BeceemFlashBulkWrite_EXIT;
1207 }
1208 uiTemp = uiTemp - 1;
1209 index = index + 1 ;
1210 }
1211 }
f8942e07
SH
1212 Adapter->SelectedChip = RESET_CHIP_SELECT;
1213 while(uiNumSectTobeRead)
1214 {
1215 //do_gettimeofday(&tv1);
1216 //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));
1217 uiPartOffset = (uiSectAlignAddr & (FLASH_PART_SIZE - 1)) + GetFlashBaseAddr(Adapter);
1218
1219 BcmDoChipSelect(Adapter,uiSectAlignAddr);
1220
1221 if(0 != BeceemFlashBulkRead(Adapter,
1222 (PUINT)pTempBuff,
1223 uiOffsetFromSectStart,
1224 Adapter->uiSectorSize))
1225 {
1226 Status = -1;
1227 goto BeceemFlashBulkWrite_EXIT;
1228 }
1229
1230 //do_gettimeofday(&tr);
1231 //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));
1232
1233 ulStatus = BcmFlashUnProtectBlock(Adapter,uiSectAlignAddr,Adapter->uiSectorSize);
1234
1235
1236 if(uiNumSectTobeRead > 1)
1237 {
1238
082e889b 1239 memcpy(&pTempBuff[uiCurrSectOffsetAddr],pcBuffer,uiSectBoundary-(uiSectAlignAddr+uiCurrSectOffsetAddr));
f8942e07
SH
1240 pcBuffer += ((uiSectBoundary-(uiSectAlignAddr+uiCurrSectOffsetAddr)));
1241 uiNumBytes -= (uiSectBoundary-(uiSectAlignAddr+uiCurrSectOffsetAddr));
1242 }
1243 else
1244 {
082e889b 1245 memcpy(&pTempBuff[uiCurrSectOffsetAddr],pcBuffer,uiNumBytes);
f8942e07
SH
1246 }
1247
1248 if(IsFlash2x(Adapter))
1249 {
1250 SaveHeaderIfPresent(Adapter,(PUCHAR)pTempBuff,uiOffsetFromSectStart);
1251 }
1252
1253 FlashSectorErase(Adapter,uiPartOffset,1);
1254 //do_gettimeofday(&te);
1255 //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));
1256
1257 for(uiIndex = 0; uiIndex < Adapter->uiSectorSize; uiIndex +=Adapter->ulFlashWriteSize)
1258 {
1259 if(Adapter->device_removed)
1260 {
1261 Status = -1;
1262 goto BeceemFlashBulkWrite_EXIT;
1263 }
1264 if(STATUS_SUCCESS != (*Adapter->fpFlashWrite)(Adapter,uiPartOffset+uiIndex,(&pTempBuff[uiIndex])))
1265 {
1266 Status = -1;
1267 goto BeceemFlashBulkWrite_EXIT;
1268 }
1269 }
1270
1271 //do_gettimeofday(&tw);
1272 //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));
1273 for(uiIndex = 0;uiIndex < Adapter->uiSectorSize;uiIndex += MAX_RW_SIZE)
1274 {
1275 if(STATUS_SUCCESS == BeceemFlashBulkRead(Adapter,(PUINT)ucReadBk,uiOffsetFromSectStart+uiIndex,MAX_RW_SIZE))
1276 {
1277 if(Adapter->ulFlashWriteSize == 1)
1278 {
1279 UINT uiReadIndex = 0;
1280 for(uiReadIndex = 0; uiReadIndex < 16; uiReadIndex++)
1281 {
1282 if(ucReadBk[uiReadIndex] != pTempBuff[uiIndex+uiReadIndex])
1283 {
1284 if(STATUS_SUCCESS != (*Adapter->fpFlashWriteWithStatusCheck)(Adapter,uiPartOffset+uiIndex+uiReadIndex,&pTempBuff[uiIndex+uiReadIndex]))
1285 {
1286 Status = STATUS_FAILURE;
1287 goto BeceemFlashBulkWrite_EXIT;
1288 }
1289 }
1290 }
1291 }
1292 else
1293 {
082e889b 1294 if(memcmp(ucReadBk,&pTempBuff[uiIndex],MAX_RW_SIZE))
f8942e07
SH
1295 {
1296 if(STATUS_SUCCESS != (*Adapter->fpFlashWriteWithStatusCheck)(Adapter,uiPartOffset+uiIndex,&pTempBuff[uiIndex]))
1297 {
1298 Status = STATUS_FAILURE;
1299 goto BeceemFlashBulkWrite_EXIT;
1300 }
1301 }
1302 }
1303 }
1304 }
1305 //do_gettimeofday(&twv);
1306 //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));
1307
1308
1309 if(ulStatus)
1310 {
1311 BcmRestoreBlockProtectStatus(Adapter,ulStatus);
1312 ulStatus = 0;
1313 }
1314
1315 uiCurrSectOffsetAddr = 0;
1316 uiSectAlignAddr = uiSectBoundary;
1317 uiSectBoundary += Adapter->uiSectorSize;
1318 uiOffsetFromSectStart += Adapter->uiSectorSize;
1319 uiNumSectTobeRead--;
1320 }
1321 //do_gettimeofday(&tv2);
1322 //BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "Time after Write :%ld ms\n",(tv2.tv_sec *1000 + tv2.tv_usec/1000));
1323 //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));
1324//
1325// Cleanup.
1326//
1327BeceemFlashBulkWrite_EXIT:
1328 if(ulStatus)
1329 {
1330 BcmRestoreBlockProtectStatus(Adapter,ulStatus);
1331 }
082e889b
SH
1332
1333 kfree(pTempBuff);
f8942e07
SH
1334
1335 Adapter->SelectedChip = RESET_CHIP_SELECT;
1336 return Status;
1337}
1338
1339
1340//-----------------------------------------------------------------------------
1341// Procedure: BeceemFlashBulkWriteStatus
1342//
1343// Description: Writes to Flash. Checks the SPI status after each write.
1344//
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
1353//
1354//-----------------------------------------------------------------------------
1355
44a17eff 1356static INT BeceemFlashBulkWriteStatus(
f8942e07
SH
1357 PMINI_ADAPTER Adapter,
1358 PUINT pBuffer,
1359 UINT uiOffset,
1360 UINT uiNumBytes,
1361 BOOLEAN bVerify)
1362{
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 UINT Status = STATUS_SUCCESS;
1374 UINT uiTemp = 0;
1375 UINT index = 0;
1376 UINT uiPartOffset = 0;
1377
1378 uiOffsetFromSectStart = uiOffset & ~(Adapter->uiSectorSize - 1);
1379
1380 //uiOffset += Adapter->ulFlashCalStart;
1381 //Adding flash Base address
1382// uiOffset = uiOffset + GetFlashBaseAddr(Adapter);
1383
1384 uiSectAlignAddr = uiOffset & ~(Adapter->uiSectorSize - 1);
1385 uiCurrSectOffsetAddr = uiOffset & (Adapter->uiSectorSize - 1);
1386 uiSectBoundary = uiSectAlignAddr + Adapter->uiSectorSize;
1387
082e889b 1388 pTempBuff = kmalloc(Adapter->uiSectorSize, GFP_KERNEL);
f8942e07 1389 if(NULL == pTempBuff)
f8942e07 1390 goto BeceemFlashBulkWriteStatus_EXIT;
082e889b 1391
f8942e07 1392//
25985edc 1393// check if the data to be written is overlapped across sectors
f8942e07
SH
1394//
1395 if(uiOffset+uiNumBytes < uiSectBoundary)
1396 {
1397 uiNumSectTobeRead = 1;
1398 }
1399 else
1400 {
1401// Number of sectors = Last sector start address/First sector start address
1402 uiNumSectTobeRead = (uiCurrSectOffsetAddr+uiNumBytes)/Adapter->uiSectorSize;
1403 if((uiCurrSectOffsetAddr+uiNumBytes)%Adapter->uiSectorSize)
1404 {
1405 uiNumSectTobeRead++;
1406 }
1407 }
1408
1409 if(IsFlash2x(Adapter) && (Adapter->bAllDSDWriteAllow == FALSE))
1410 {
1411 index = 0;
1412 uiTemp = uiNumSectTobeRead ;
1413 while(uiTemp)
1414 {
1415 if(IsOffsetWritable(Adapter,uiOffsetFromSectStart + index * Adapter->uiSectorSize ) == FALSE)
1416 {
1417 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Sector Starting at offset <0X%x> is not writable",
1418 (uiOffsetFromSectStart + index * Adapter->uiSectorSize));
1419 Status = SECTOR_IS_NOT_WRITABLE;
1420 goto BeceemFlashBulkWriteStatus_EXIT;
1421 }
1422 uiTemp = uiTemp - 1;
1423 index = index + 1 ;
1424 }
1425 }
1426
1427 Adapter->SelectedChip = RESET_CHIP_SELECT;
1428 while(uiNumSectTobeRead)
1429 {
1430 uiPartOffset = (uiSectAlignAddr & (FLASH_PART_SIZE - 1)) + GetFlashBaseAddr(Adapter);
1431
1432 BcmDoChipSelect(Adapter,uiSectAlignAddr);
1433 if(0 != BeceemFlashBulkRead(Adapter,
1434 (PUINT)pTempBuff,
1435 uiOffsetFromSectStart,
1436 Adapter->uiSectorSize))
1437 {
1438 Status = -1;
1439 goto BeceemFlashBulkWriteStatus_EXIT;
1440 }
1441
1442 ulStatus = BcmFlashUnProtectBlock(Adapter,uiOffsetFromSectStart,Adapter->uiSectorSize);
1443
1444 if(uiNumSectTobeRead > 1)
1445 {
1446
082e889b 1447 memcpy(&pTempBuff[uiCurrSectOffsetAddr],pcBuffer,uiSectBoundary-(uiSectAlignAddr+uiCurrSectOffsetAddr));
f8942e07
SH
1448 pcBuffer += ((uiSectBoundary-(uiSectAlignAddr+uiCurrSectOffsetAddr)));
1449 uiNumBytes -= (uiSectBoundary-(uiSectAlignAddr+uiCurrSectOffsetAddr));
1450 }
1451 else
1452 {
082e889b 1453 memcpy(&pTempBuff[uiCurrSectOffsetAddr],pcBuffer,uiNumBytes);
f8942e07
SH
1454 }
1455
1456 if(IsFlash2x(Adapter))
1457 {
1458 SaveHeaderIfPresent(Adapter,(PUCHAR)pTempBuff,uiOffsetFromSectStart);
1459 }
1460
1461 FlashSectorErase(Adapter,uiPartOffset,1);
1462
1463 for(uiIndex = 0; uiIndex < Adapter->uiSectorSize; uiIndex +=Adapter->ulFlashWriteSize)
1464
1465 {
1466 if(Adapter->device_removed)
1467 {
1468 Status = -1;
1469 goto BeceemFlashBulkWriteStatus_EXIT;
1470 }
1471
1472 if(STATUS_SUCCESS != (*Adapter->fpFlashWriteWithStatusCheck)(Adapter,uiPartOffset+uiIndex,&pTempBuff[uiIndex]))
1473 {
1474 Status = -1;
1475 goto BeceemFlashBulkWriteStatus_EXIT;
1476 }
1477 }
1478
1479 if(bVerify)
1480 {
1481 for(uiIndex = 0;uiIndex < Adapter->uiSectorSize;uiIndex += MAX_RW_SIZE)
1482 {
f8942e07
SH
1483
1484 if(STATUS_SUCCESS == BeceemFlashBulkRead(Adapter,(PUINT)ucReadBk,uiOffsetFromSectStart+uiIndex,MAX_RW_SIZE))
1485 {
082e889b 1486 if(memcmp(ucReadBk,&pTempBuff[uiIndex],MAX_RW_SIZE))
f8942e07
SH
1487 {
1488 Status = STATUS_FAILURE;
1489 goto BeceemFlashBulkWriteStatus_EXIT;
1490 }
1491
1492 }
1493
1494 }
1495 }
1496
1497 if(ulStatus)
1498 {
1499 BcmRestoreBlockProtectStatus(Adapter,ulStatus);
1500 ulStatus = 0;
1501 }
1502
1503 uiCurrSectOffsetAddr = 0;
1504 uiSectAlignAddr = uiSectBoundary;
1505 uiSectBoundary += Adapter->uiSectorSize;
1506 uiOffsetFromSectStart += Adapter->uiSectorSize;
1507 uiNumSectTobeRead--;
1508 }
1509//
1510// Cleanup.
1511//
1512BeceemFlashBulkWriteStatus_EXIT:
1513 if(ulStatus)
1514 {
1515 BcmRestoreBlockProtectStatus(Adapter,ulStatus);
1516 }
082e889b
SH
1517
1518 kfree(pTempBuff);
f8942e07
SH
1519 Adapter->SelectedChip = RESET_CHIP_SELECT;
1520 return Status;
1521
1522}
1523
1524//-----------------------------------------------------------------------------
1525// Procedure: PropagateCalParamsFromEEPROMToMemory
1526//
1527// Description: Dumps the calibration section of EEPROM to DDR.
1528//
1529// Arguments:
1530// Adapter - ptr to Adapter object instance
1531// Returns:
1532// OSAL_STATUS_CODE
1533//
1534//-----------------------------------------------------------------------------
1535
1536
1537INT PropagateCalParamsFromEEPROMToMemory(PMINI_ADAPTER Adapter)
1538{
082e889b 1539 PCHAR pBuff = kmalloc(BUFFER_4K, GFP_KERNEL);
f8942e07
SH
1540 UINT uiEepromSize = 0;
1541 UINT uiIndex = 0;
1542 UINT uiBytesToCopy = 0;
1543 UINT uiCalStartAddr = EEPROM_CALPARAM_START;
1544 UINT uiMemoryLoc = EEPROM_CAL_DATA_INTERNAL_LOC;
1545 UINT value;
1546 INT Status = 0;
1547 if(pBuff == NULL)
1548 {
1549 return -1;
1550 }
1551
1552 if(0 != BeceemEEPROMBulkRead(Adapter,&uiEepromSize,EEPROM_SIZE_OFFSET,4))
1553 {
1554
082e889b 1555 kfree(pBuff);
f8942e07
SH
1556 return -1;
1557 }
1558
1559 uiEepromSize >>= 16;
1560 if(uiEepromSize > 1024*1024)
1561 {
082e889b 1562 kfree(pBuff);
f8942e07
SH
1563 return -1;
1564 }
1565
1566
1567 uiBytesToCopy = MIN(BUFFER_4K,uiEepromSize);
1568
1569 while(uiBytesToCopy)
1570 {
1571 if(0 != BeceemEEPROMBulkRead(Adapter,(PUINT)pBuff,uiCalStartAddr,uiBytesToCopy))
1572 {
1573 Status = -1;
1574 break;
1575 }
1576 wrm(Adapter,uiMemoryLoc,(PCHAR)(((PULONG)pBuff)+uiIndex),uiBytesToCopy);
1577 uiMemoryLoc += uiBytesToCopy;
1578 uiEepromSize -= uiBytesToCopy;
1579 uiCalStartAddr += uiBytesToCopy;
1580 uiIndex += uiBytesToCopy/4;
1581 uiBytesToCopy = MIN(BUFFER_4K,uiEepromSize);
1582
1583 }
1584 value = 0xbeadbead;
1585 wrmalt(Adapter, EEPROM_CAL_DATA_INTERNAL_LOC-4,&value, sizeof(value));
1586 value = 0xbeadbead;
1587 wrmalt(Adapter, EEPROM_CAL_DATA_INTERNAL_LOC-8,&value, sizeof(value));
082e889b 1588 kfree(pBuff);
f8942e07
SH
1589
1590 return Status;
1591
1592}
1593
1594//-----------------------------------------------------------------------------
1595// Procedure: PropagateCalParamsFromFlashToMemory
1596//
1597// Description: Dumps the calibration section of EEPROM to DDR.
1598//
1599// Arguments:
1600// Adapter - ptr to Adapter object instance
1601// Returns:
1602// OSAL_STATUS_CODE
1603//
1604//-----------------------------------------------------------------------------
1605
1606INT PropagateCalParamsFromFlashToMemory(PMINI_ADAPTER Adapter)
1607{
1608 PCHAR pBuff, pPtr;
1609 UINT uiEepromSize = 0;
1610 UINT uiBytesToCopy = 0;
1611 //UINT uiIndex = 0;
1612 UINT uiCalStartAddr = EEPROM_CALPARAM_START;
1613 UINT uiMemoryLoc = EEPROM_CAL_DATA_INTERNAL_LOC;
1614 UINT value;
1615 INT Status = 0;
1616//
1617// Write the signature first. This will ensure firmware does not access EEPROM.
1618//
1619 value = 0xbeadbead;
1620 wrmalt(Adapter, EEPROM_CAL_DATA_INTERNAL_LOC - 4, &value, sizeof(value));
1621 value = 0xbeadbead;
1622 wrmalt(Adapter, EEPROM_CAL_DATA_INTERNAL_LOC - 8, &value, sizeof(value));
1623
1624 if(0 != BeceemNVMRead(Adapter,&uiEepromSize,EEPROM_SIZE_OFFSET, 4))
1625 {
1626 return -1;
1627 }
1628 uiEepromSize = ntohl(uiEepromSize);
1629 uiEepromSize >>= 16;
1630
1631//
1632// subtract the auto init section size
1633//
1634 uiEepromSize -= EEPROM_CALPARAM_START;
1635
1636 if(uiEepromSize > 1024*1024)
1637 {
1638 return -1;
1639 }
1640
082e889b 1641 pBuff = kmalloc(uiEepromSize, GFP_KERNEL);
f8942e07 1642 if ( pBuff == NULL )
f8942e07 1643 return -1;
f8942e07
SH
1644
1645 if(0 != BeceemNVMRead(Adapter,(PUINT)pBuff,uiCalStartAddr, uiEepromSize))
1646 {
082e889b 1647 kfree(pBuff);
f8942e07
SH
1648 return -1;
1649 }
1650
1651 pPtr = pBuff;
1652
1653 uiBytesToCopy = MIN(BUFFER_4K,uiEepromSize);
1654
1655 while(uiBytesToCopy)
1656 {
1657 Status = wrm(Adapter,uiMemoryLoc,(PCHAR)pPtr,uiBytesToCopy);
1658 if(Status)
1659 {
1660 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"wrm failed with status :%d",Status);
1661 break;
1662 }
1663
1664 pPtr += uiBytesToCopy;
1665 uiEepromSize -= uiBytesToCopy;
1666 uiMemoryLoc += uiBytesToCopy;
1667 uiBytesToCopy = MIN(BUFFER_4K,uiEepromSize);
1668 }
1669
082e889b 1670 kfree(pBuff);
f8942e07
SH
1671 return Status;
1672
1673}
1674
1675//-----------------------------------------------------------------------------
1676// Procedure: BeceemEEPROMReadBackandVerify
1677//
1678// Description: Read back the data written and verifies.
1679//
1680// Arguments:
1681// Adapter - ptr to Adapter object instance
1682// pBuffer - Data to be written.
1683// uiOffset - Offset of the flash where data needs to be written to.
1684// uiNumBytes - Number of bytes to be written.
1685// Returns:
1686// OSAL_STATUS_CODE
1687//
1688//-----------------------------------------------------------------------------
1689
44a17eff 1690static INT BeceemEEPROMReadBackandVerify(
f8942e07
SH
1691 PMINI_ADAPTER Adapter,
1692 PUINT pBuffer,
1693 UINT uiOffset,
1694 UINT uiNumBytes)
1695{
1696 UINT uiRdbk = 0;
1697 UINT uiIndex = 0;
1698 UINT uiData = 0;
1699 UINT auiData[4] = {0};
1700
1701 while(uiNumBytes)
1702 {
1703 if(Adapter->device_removed )
1704 {
1705 return -1;
1706 }
1707
1708 if(uiNumBytes >= MAX_RW_SIZE)
1709 {// for the requests more than or equal to MAX_RW_SIZE bytes, use bulk read function to make the access faster.
1710 BeceemEEPROMBulkRead(Adapter,&auiData[0],uiOffset,MAX_RW_SIZE);
1711
082e889b 1712 if(memcmp(&pBuffer[uiIndex],&auiData[0],MAX_RW_SIZE))
f8942e07
SH
1713 {
1714 // re-write
1715 BeceemEEPROMBulkWrite(Adapter,(PUCHAR)(pBuffer+uiIndex),uiOffset,MAX_RW_SIZE,FALSE);
1716 mdelay(3);
1717 BeceemEEPROMBulkRead(Adapter,&auiData[0],uiOffset,MAX_RW_SIZE);
1718
082e889b 1719 if(memcmp(&pBuffer[uiIndex],&auiData[0],MAX_RW_SIZE))
f8942e07
SH
1720 {
1721 return -1;
1722 }
1723 }
1724 uiOffset += MAX_RW_SIZE;
1725 uiNumBytes -= MAX_RW_SIZE;
1726 uiIndex += 4;
1727
1728 }
1729 else if(uiNumBytes >= 4)
1730 {
1731 BeceemEEPROMBulkRead(Adapter,&uiData,uiOffset,4);
1732 if(uiData != pBuffer[uiIndex])
1733 {
1734 //re-write
1735 BeceemEEPROMBulkWrite(Adapter,(PUCHAR)(pBuffer+uiIndex),uiOffset,4,FALSE);
1736 mdelay(3);
1737 BeceemEEPROMBulkRead(Adapter,&uiData,uiOffset,4);
1738 if(uiData != pBuffer[uiIndex])
1739 {
1740 return -1;
1741 }
1742 }
1743 uiOffset += 4;
1744 uiNumBytes -= 4;
1745 uiIndex++;
1746
1747 }
1748 else
1749 { // Handle the reads less than 4 bytes...
1750 uiData = 0;
082e889b 1751 memcpy(&uiData,((PUCHAR)pBuffer)+(uiIndex*sizeof(UINT)),uiNumBytes);
f8942e07
SH
1752 BeceemEEPROMBulkRead(Adapter,&uiRdbk,uiOffset,4);
1753
1754 if(memcmp(&uiData, &uiRdbk, uiNumBytes))
1755 return -1;
1756
1757 uiNumBytes = 0;
1758 }
1759
1760 }
1761
1762 return 0;
1763}
1764
44a17eff 1765static VOID BcmSwapWord(UINT *ptr1) {
f8942e07
SH
1766
1767 UINT tempval = (UINT)*ptr1;
1768 char *ptr2 = (char *)&tempval;
1769 char *ptr = (char *)ptr1;
1770
1771 ptr[0] = ptr2[3];
1772 ptr[1] = ptr2[2];
1773 ptr[2] = ptr2[1];
1774 ptr[3] = ptr2[0];
1775}
1776
1777//-----------------------------------------------------------------------------
1778// Procedure: BeceemEEPROMWritePage
1779//
1780// Description: Performs page write (16bytes) to the EEPROM
1781//
1782// Arguments:
1783// Adapter - ptr to Adapter object instance
1784// uiData - Data to be written.
1785// uiOffset - Offset of the EEPROM where data needs to be written to.
1786// Returns:
1787// OSAL_STATUS_CODE
1788//
1789//-----------------------------------------------------------------------------
44a17eff 1790static INT BeceemEEPROMWritePage( PMINI_ADAPTER Adapter, UINT uiData[], UINT uiOffset )
f8942e07
SH
1791{
1792 UINT uiRetries = MAX_EEPROM_RETRIES*RETRIES_PER_DELAY;
1793 UINT uiStatus = 0;
1794 UCHAR uiEpromStatus = 0;
1795 UINT value =0 ;
1796
1797 /* Flush the Write/Read/Cmd queues. */
1798 value = ( EEPROM_WRITE_QUEUE_FLUSH | EEPROM_CMD_QUEUE_FLUSH | EEPROM_READ_QUEUE_FLUSH );
1799 wrmalt( Adapter, SPI_FLUSH_REG, &value, sizeof(value));
1800 value = 0 ;
1801 wrmalt( Adapter, SPI_FLUSH_REG, &value, sizeof(value) );
1802
1803 /* Clear the Empty/Avail/Full bits. After this it has been confirmed
1804 * that the bit was cleared by reading back the register. See NOTE below.
1805 * We also clear the Read queues as we do a EEPROM status register read
1806 * later. */
1807 value = ( EEPROM_WRITE_QUEUE_EMPTY | EEPROM_WRITE_QUEUE_AVAIL | EEPROM_WRITE_QUEUE_FULL | EEPROM_READ_DATA_AVAIL | EEPROM_READ_DATA_FULL ) ;
1808 wrmalt( Adapter, EEPROM_SPI_Q_STATUS1_REG,&value, sizeof(value));
1809
1810 /* Enable write */
1811 value = EEPROM_WRITE_ENABLE ;
1812 wrmalt( Adapter, EEPROM_CMDQ_SPI_REG,&value, sizeof(value) );
1813
1814 /* We can write back to back 8bits * 16 into the queue and as we have
1815 * checked for the queue to be empty we can write in a burst. */
1816
1817 value = uiData[0];
1818 BcmSwapWord(&value);
1819 wrm( Adapter, EEPROM_WRITE_DATAQ_REG, (PUCHAR)&value, 4);
1820
1821 value = uiData[1];
1822 BcmSwapWord(&value);
1823 wrm( Adapter, EEPROM_WRITE_DATAQ_REG, (PUCHAR)&value, 4);
1824
1825 value = uiData[2];
1826 BcmSwapWord(&value);
1827 wrm( Adapter, EEPROM_WRITE_DATAQ_REG, (PUCHAR)&value, 4);
1828
1829 value = uiData[3];
1830 BcmSwapWord(&value);
1831 wrm( Adapter, EEPROM_WRITE_DATAQ_REG, (PUCHAR)&value, 4);
1832
1833 /* NOTE : After this write, on readback of EEPROM_SPI_Q_STATUS1_REG
1834 * shows that we see 7 for the EEPROM data write. Which means that
1835 * queue got full, also space is available as well as the queue is empty.
1836 * This may happen in sequence. */
1837 value = EEPROM_16_BYTE_PAGE_WRITE | uiOffset ;
1838 wrmalt( Adapter, EEPROM_CMDQ_SPI_REG, &value, sizeof(value) );
1839
1840 /* Ideally we should loop here without tries and eventually succeed.
1841 * What we are checking if the previous write has completed, and this
1842 * may take time. We should wait till the Empty bit is set. */
1843 uiStatus = 0;
1844 rdmalt( Adapter, EEPROM_SPI_Q_STATUS1_REG,&uiStatus, sizeof(uiStatus)) ;
1845 while ( ( uiStatus & EEPROM_WRITE_QUEUE_EMPTY ) == 0 )
1846 {
1847 uiRetries--;
1848 if ( uiRetries == 0 )
1849 {
1850 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "0x0f003004 = %x, %d retries failed.\n", uiStatus, MAX_EEPROM_RETRIES *RETRIES_PER_DELAY);
1851 return STATUS_FAILURE ;
1852 }
1853
1854 if( !(uiRetries%RETRIES_PER_DELAY) )
1855 msleep(1);
1856
1857 uiStatus = 0;
1858 rdmalt( Adapter, EEPROM_SPI_Q_STATUS1_REG,&uiStatus, sizeof(uiStatus)) ;
1859 if(Adapter->device_removed == TRUE)
1860 {
1861 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Modem got removed hence exiting from loop....");
1862 return -ENODEV;
1863 }
1864
1865 }
1866
1867 if ( uiRetries != 0 )
1868 {
1869 /* Clear the ones that are set - either, Empty/Full/Avail bits */
1870 value = ( uiStatus & ( EEPROM_WRITE_QUEUE_EMPTY | EEPROM_WRITE_QUEUE_AVAIL | EEPROM_WRITE_QUEUE_FULL ) );
1871 wrmalt( Adapter, EEPROM_SPI_Q_STATUS1_REG, &value, sizeof(value));
1872 }
1873
1874 /* Here we should check if the EEPROM status register is correct before
1875 * proceeding. Bit 0 in the EEPROM Status register should be 0 before
1876 * we proceed further. A 1 at Bit 0 indicates that the EEPROM is busy
1877 * with the previous write. Note also that issuing this read finally
1878 * means the previous write to the EEPROM has completed. */
1879 uiRetries = MAX_EEPROM_RETRIES*RETRIES_PER_DELAY;
1880 uiEpromStatus = 0;
1881 while ( uiRetries != 0 )
1882 {
1883 uiEpromStatus = ReadEEPROMStatusRegister( Adapter) ;
1884 if(Adapter->device_removed == TRUE)
1885 {
1886 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "Modem has got removed hence exiting from loop...");
1887 return -ENODEV;
1888 }
1889 if ( ( EEPROM_STATUS_REG_WRITE_BUSY & uiEpromStatus ) == 0 )
1890 {
1891 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "EEPROM status register = %x tries = %d\n", uiEpromStatus, (MAX_EEPROM_RETRIES * RETRIES_PER_DELAY- uiRetries) );
1892 return STATUS_SUCCESS ;
1893 }
1894 uiRetries--;
1895 if ( uiRetries == 0 )
1896 {
1897 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);
1898 return STATUS_FAILURE ;
1899 }
1900 uiEpromStatus = 0;
1901 if( !(uiRetries%RETRIES_PER_DELAY) )
1902 msleep(1);
1903 }
1904
1905 return STATUS_SUCCESS ;
1906} /* BeceemEEPROMWritePage */
1907
1908
1909//-----------------------------------------------------------------------------
1910// Procedure: BeceemEEPROMBulkWrite
1911//
1912// Description: Performs write to the EEPROM
1913//
1914// Arguments:
1915// Adapter - ptr to Adapter object instance
1916// pBuffer - Data to be written.
1917// uiOffset - Offset of the EEPROM where data needs to be written to.
1918// uiNumBytes - Number of bytes to be written.
1919// bVerify - read verify flag.
1920// Returns:
1921// OSAL_STATUS_CODE
1922//
1923//-----------------------------------------------------------------------------
1924
1925INT BeceemEEPROMBulkWrite(
1926 PMINI_ADAPTER Adapter,
1927 PUCHAR pBuffer,
1928 UINT uiOffset,
1929 UINT uiNumBytes,
1930 BOOLEAN bVerify)
1931{
1932 UINT uiBytesToCopy = uiNumBytes;
1933 //UINT uiRdbk = 0;
1934 UINT uiData[4] = {0};
1935 UINT uiIndex = 0;
1936 UINT uiTempOffset = 0;
1937 UINT uiExtraBytes = 0;
1938 //PUINT puiBuffer = (PUINT)pBuffer;
1939 //INT value;
1940
1941 if(uiOffset%MAX_RW_SIZE && uiBytesToCopy)
1942 {
1943 uiTempOffset = uiOffset - (uiOffset%MAX_RW_SIZE);
1944 uiExtraBytes = uiOffset-uiTempOffset;
1945
1946
1947 BeceemEEPROMBulkRead(Adapter,&uiData[0],uiTempOffset,MAX_RW_SIZE);
1948
1949 if(uiBytesToCopy >= (16 -uiExtraBytes))
1950 {
082e889b 1951 memcpy((((PUCHAR)&uiData[0])+uiExtraBytes),pBuffer,MAX_RW_SIZE- uiExtraBytes);
f8942e07
SH
1952
1953 if ( STATUS_FAILURE == BeceemEEPROMWritePage( Adapter, uiData, uiTempOffset ) )
1954 return STATUS_FAILURE;
1955
1956 uiBytesToCopy -= (MAX_RW_SIZE - uiExtraBytes);
1957 uiIndex += (MAX_RW_SIZE - uiExtraBytes);
1958 uiOffset += (MAX_RW_SIZE - uiExtraBytes);
1959 }
1960 else
1961 {
082e889b 1962 memcpy((((PUCHAR)&uiData[0])+uiExtraBytes),pBuffer,uiBytesToCopy);
f8942e07
SH
1963
1964 if ( STATUS_FAILURE == BeceemEEPROMWritePage( Adapter, uiData, uiTempOffset ) )
1965 return STATUS_FAILURE;
1966
1967 uiIndex += uiBytesToCopy;
1968 uiOffset += uiBytesToCopy;
1969 uiBytesToCopy = 0;
1970 }
1971
1972
1973 }
1974
1975 while(uiBytesToCopy)
1976 {
1977 if(Adapter->device_removed)
1978 {
1979 return -1;
1980 }
1981
1982 if(uiBytesToCopy >= MAX_RW_SIZE)
1983 {
1984
1985 if (STATUS_FAILURE == BeceemEEPROMWritePage( Adapter, (PUINT) &pBuffer[uiIndex], uiOffset ) )
1986 return STATUS_FAILURE;
1987
1988 uiIndex += MAX_RW_SIZE;
1989 uiOffset += MAX_RW_SIZE;
1990 uiBytesToCopy -= MAX_RW_SIZE;
1991 }
1992 else
1993 {
1994 //
1995 // To program non 16byte aligned data, read 16byte and then update.
1996 //
1997 BeceemEEPROMBulkRead(Adapter,&uiData[0],uiOffset,16);
082e889b 1998 memcpy(&uiData[0],pBuffer+uiIndex,uiBytesToCopy);
f8942e07
SH
1999
2000
2001 if ( STATUS_FAILURE == BeceemEEPROMWritePage( Adapter, uiData, uiOffset ) )
2002 return STATUS_FAILURE;
2003 uiBytesToCopy = 0;
2004 }
2005
2006 }
2007
2008 return 0;
2009}
2010
2011//-----------------------------------------------------------------------------
2012// Procedure: BeceemNVMRead
2013//
2014// Description: Reads n number of bytes from NVM.
2015//
2016// Arguments:
2017// Adapter - ptr to Adapter object instance
2018// pBuffer - Buffer to store the data read from NVM
2019// uiOffset - Offset of NVM from where data should be read
2020// uiNumBytes - Number of bytes to be read from the NVM.
2021//
2022// Returns:
25985edc 2023// OSAL_STATUS_SUCCESS - if NVM read is successful.
f8942e07
SH
2024// <FAILURE> - if failed.
2025//-----------------------------------------------------------------------------
2026
2027INT BeceemNVMRead(
2028 PMINI_ADAPTER Adapter,
2029 PUINT pBuffer,
2030 UINT uiOffset,
2031 UINT uiNumBytes)
2032{
2033 INT Status = 0;
2034#if !defined(BCM_SHM_INTERFACE) || defined(FLASH_DIRECT_ACCESS)
2035 UINT uiTemp = 0, value;
2036#endif
2037
2038 if(Adapter->eNVMType == NVM_FLASH)
2039 {
2040 if(Adapter->bFlashRawRead == FALSE)
2041 {
2042 if (IsSectionExistInVendorInfo(Adapter,Adapter->eActiveDSD))
2043 return vendorextnReadSection(Adapter,(PUCHAR)pBuffer,Adapter->eActiveDSD,uiOffset,uiNumBytes);
2044 uiOffset = uiOffset+ Adapter->ulFlashCalStart ;
2045 }
2046#if defined(BCM_SHM_INTERFACE) && !defined(FLASH_DIRECT_ACCESS)
2047 Status = bcmflash_raw_read((uiOffset/FLASH_PART_SIZE),(uiOffset % FLASH_PART_SIZE),( unsigned char *)pBuffer,uiNumBytes);
2048#else
2049
2050 rdmalt(Adapter, 0x0f000C80, &uiTemp, sizeof(uiTemp));
2051 value = 0;
2052 wrmalt(Adapter, 0x0f000C80,&value, sizeof(value));
2053 Status = BeceemFlashBulkRead(Adapter,
2054 pBuffer,
2055 uiOffset,
2056 uiNumBytes);
2057 wrmalt(Adapter, 0x0f000C80, &uiTemp, sizeof(uiTemp));
2058#endif
2059 }
2060 else if(Adapter->eNVMType == NVM_EEPROM)
2061 {
2062 Status = BeceemEEPROMBulkRead(Adapter,
2063 pBuffer,
2064 uiOffset,
2065 uiNumBytes);
2066 }
2067 else
2068 {
2069 Status = -1;
2070 }
2071 return Status;
2072}
2073
2074//-----------------------------------------------------------------------------
2075// Procedure: BeceemNVMWrite
2076//
2077// Description: Writes n number of bytes to NVM.
2078//
2079// Arguments:
2080// Adapter - ptr to Adapter object instance
2081// pBuffer - Buffer contains the data to be written.
2082// uiOffset - Offset of NVM where data to be written to.
2083// uiNumBytes - Number of bytes to be written..
2084//
2085// Returns:
25985edc 2086// OSAL_STATUS_SUCCESS - if NVM write is successful.
f8942e07
SH
2087// <FAILURE> - if failed.
2088//-----------------------------------------------------------------------------
2089
2090INT BeceemNVMWrite(
2091 PMINI_ADAPTER Adapter,
2092 PUINT pBuffer,
2093 UINT uiOffset,
2094 UINT uiNumBytes,
2095 BOOLEAN bVerify)
2096{
2097 INT Status = 0;
2098 UINT uiTemp = 0;
2099 UINT uiMemoryLoc = EEPROM_CAL_DATA_INTERNAL_LOC;
2100 UINT uiIndex = 0;
2101#if !defined(BCM_SHM_INTERFACE) || defined(FLASH_DIRECT_ACCESS)
2102 UINT value;
2103#endif
2104 UINT uiFlashOffset = 0;
2105
2106 if(Adapter->eNVMType == NVM_FLASH)
2107 {
2108 if (IsSectionExistInVendorInfo(Adapter,Adapter->eActiveDSD))
2109 Status = vendorextnWriteSection(Adapter,(PUCHAR)pBuffer,Adapter->eActiveDSD,uiOffset,uiNumBytes,bVerify);
2110 else
2111 {
2112 uiFlashOffset = uiOffset + Adapter->ulFlashCalStart;
2113
2114#if defined(BCM_SHM_INTERFACE) && !defined(FLASH_DIRECT_ACCESS)
2115 Status = bcmflash_raw_write((uiFlashOffset/FLASH_PART_SIZE), (uiFlashOffset % FLASH_PART_SIZE), (unsigned char *)pBuffer,uiNumBytes);
2116#else
2117 rdmalt(Adapter, 0x0f000C80, &uiTemp, sizeof(uiTemp));
2118 value = 0;
2119 wrmalt(Adapter, 0x0f000C80, &value, sizeof(value));
2120
2121 if(Adapter->bStatusWrite == TRUE)
2122 {
2123 Status = BeceemFlashBulkWriteStatus(Adapter,
2124 pBuffer,
2125 uiFlashOffset,
2126 uiNumBytes ,
2127 bVerify);
2128 }
2129 else
2130 {
2131
2132 Status = BeceemFlashBulkWrite(Adapter,
2133 pBuffer,
2134 uiFlashOffset,
2135 uiNumBytes,
2136 bVerify);
2137 }
2138#endif
2139 }
2140
2141
2142 if(uiOffset >= EEPROM_CALPARAM_START)
2143 {
2144 uiMemoryLoc += (uiOffset - EEPROM_CALPARAM_START);
2145 while(uiNumBytes)
2146 {
2147 if(uiNumBytes > BUFFER_4K)
2148 {
2149 wrm(Adapter,(uiMemoryLoc+uiIndex),(PCHAR)(pBuffer+(uiIndex/4)),BUFFER_4K);
2150 uiNumBytes -= BUFFER_4K;
2151 uiIndex += BUFFER_4K;
2152 }
2153 else
2154 {
2155 wrm(Adapter,uiMemoryLoc+uiIndex,(PCHAR)(pBuffer+(uiIndex/4)),uiNumBytes);
2156 uiNumBytes = 0;
2157 break;
2158 }
2159 }
2160 }
2161 else
2162 {
2163 if((uiOffset+uiNumBytes) > EEPROM_CALPARAM_START)
2164 {
2165 ULONG ulBytesTobeSkipped = 0;
2166 PUCHAR pcBuffer = (PUCHAR)pBuffer;// char pointer to take care of odd byte cases.
2167 uiNumBytes -= (EEPROM_CALPARAM_START - uiOffset);
2168 ulBytesTobeSkipped += (EEPROM_CALPARAM_START - uiOffset);
2169 uiOffset += (EEPROM_CALPARAM_START - uiOffset);
2170 while(uiNumBytes)
2171 {
2172 if(uiNumBytes > BUFFER_4K)
2173 {
2174 wrm(Adapter,uiMemoryLoc+uiIndex,(PCHAR )&pcBuffer[ulBytesTobeSkipped+uiIndex],BUFFER_4K);
2175 uiNumBytes -= BUFFER_4K;
2176 uiIndex += BUFFER_4K;
2177 }
2178 else
2179 {
2180 wrm(Adapter,uiMemoryLoc+uiIndex,(PCHAR)&pcBuffer[ulBytesTobeSkipped+uiIndex],uiNumBytes);
2181 uiNumBytes = 0;
2182 break;
2183 }
2184 }
2185
2186 }
2187 }
2188
2189 // restore the values.
2190 wrmalt(Adapter,0x0f000C80,&uiTemp, sizeof(uiTemp));
2191 }
2192 else if(Adapter->eNVMType == NVM_EEPROM)
2193 {
2194 Status = BeceemEEPROMBulkWrite(Adapter,
2195 (PUCHAR)pBuffer,
2196 uiOffset,
2197 uiNumBytes,
2198 bVerify);
2199 if(bVerify)
2200 {
2201 Status = BeceemEEPROMReadBackandVerify(Adapter,(PUINT)pBuffer,uiOffset,uiNumBytes);
2202 }
2203 }
2204 else
2205 {
2206 Status = -1;
2207 }
2208 return Status;
2209}
2210
2211//-----------------------------------------------------------------------------
2212// Procedure: BcmUpdateSectorSize
2213//
2214// Description: Updates the sector size to FLASH.
2215//
2216// Arguments:
2217// Adapter - ptr to Adapter object instance
2218// uiSectorSize - sector size
2219//
2220// Returns:
25985edc 2221// OSAL_STATUS_SUCCESS - if NVM write is successful.
f8942e07
SH
2222// <FAILURE> - if failed.
2223//-----------------------------------------------------------------------------
2224
2225INT BcmUpdateSectorSize(PMINI_ADAPTER Adapter,UINT uiSectorSize)
2226{
2227 INT Status = -1;
2228 FLASH_CS_INFO sFlashCsInfo = {0};
2229 UINT uiTemp = 0;
2230
2231 UINT uiSectorSig = 0;
2232 UINT uiCurrentSectorSize = 0;
2233
2234 UINT value;
2235
2236
2237
2238 rdmalt(Adapter, 0x0f000C80, &uiTemp, sizeof(uiTemp));
2239 value = 0;
2240 wrmalt(Adapter, 0x0f000C80,&value, sizeof(value));
2241
2242//
2243// Before updating the sector size in the reserved area, check if already present.
2244//
2245 BeceemFlashBulkRead(Adapter,(PUINT)&sFlashCsInfo,Adapter->ulFlashControlSectionStart,sizeof(sFlashCsInfo));
2246 uiSectorSig = ntohl(sFlashCsInfo.FlashSectorSizeSig);
2247 uiCurrentSectorSize = ntohl(sFlashCsInfo.FlashSectorSize);
2248
2249 if(uiSectorSig == FLASH_SECTOR_SIZE_SIG)
2250 {
2251
2252 if((uiCurrentSectorSize <= MAX_SECTOR_SIZE) && (uiCurrentSectorSize >= MIN_SECTOR_SIZE))
2253 {
2254 if(uiSectorSize == uiCurrentSectorSize)
2255 {
2256 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"Provided sector size is same as programmed in Flash");
2257 Status = STATUS_SUCCESS;
2258 goto Restore ;
2259 }
2260 }
2261 }
2262
2263 if((uiSectorSize <= MAX_SECTOR_SIZE) && (uiSectorSize >= MIN_SECTOR_SIZE))
2264 {
2265
2266 sFlashCsInfo.FlashSectorSize = htonl(uiSectorSize);
2267 sFlashCsInfo.FlashSectorSizeSig = htonl(FLASH_SECTOR_SIZE_SIG);
2268
2269 Status = BeceemFlashBulkWrite(Adapter,
2270 (PUINT)&sFlashCsInfo,
2271 Adapter->ulFlashControlSectionStart,
2272 sizeof(sFlashCsInfo),
2273 TRUE);
2274
2275
2276 }
2277
2278 Restore :
2279 // restore the values.
2280 wrmalt(Adapter, 0x0f000C80,&uiTemp, sizeof(uiTemp));
2281
2282
2283 return Status;
2284
2285}
2286
2287//-----------------------------------------------------------------------------
2288// Procedure: BcmGetFlashSectorSize
2289//
2290// Description: Finds the sector size of the FLASH.
2291//
2292// Arguments:
2293// Adapter - ptr to Adapter object instance
2294//
2295// Returns:
2296// UINT - sector size.
2297//
2298//-----------------------------------------------------------------------------
2299
9dd47ee7 2300static UINT BcmGetFlashSectorSize(PMINI_ADAPTER Adapter, UINT FlashSectorSizeSig, UINT FlashSectorSize)
f8942e07
SH
2301{
2302 UINT uiSectorSize = 0;
2303 UINT uiSectorSig = 0;
2304
2305 if(Adapter->bSectorSizeOverride &&
2306 (Adapter->uiSectorSizeInCFG <= MAX_SECTOR_SIZE &&
2307 Adapter->uiSectorSizeInCFG >= MIN_SECTOR_SIZE))
2308 {
2309 Adapter->uiSectorSize = Adapter->uiSectorSizeInCFG;
2310 }
2311 else
2312 {
2313
2314 uiSectorSig = FlashSectorSizeSig;
2315
2316 if(uiSectorSig == FLASH_SECTOR_SIZE_SIG)
2317 {
2318 uiSectorSize = FlashSectorSize;
2319 //
2320 // If the sector size stored in the FLASH makes sense then use it.
2321 //
2322 if(uiSectorSize <= MAX_SECTOR_SIZE && uiSectorSize >= MIN_SECTOR_SIZE)
2323 {
2324 Adapter->uiSectorSize = uiSectorSize;
2325 }
2326 //No valid size in FLASH, check if Config file has it.
2327 else if(Adapter->uiSectorSizeInCFG <= MAX_SECTOR_SIZE &&
2328 Adapter->uiSectorSizeInCFG >= MIN_SECTOR_SIZE)
2329 {
2330 Adapter->uiSectorSize = Adapter->uiSectorSizeInCFG;
2331 }
2332 // Init to Default, if none of the above works.
2333 else
2334 {
2335 Adapter->uiSectorSize = DEFAULT_SECTOR_SIZE;
2336 }
2337
2338 }
2339 else
2340 {
2341 if(Adapter->uiSectorSizeInCFG <= MAX_SECTOR_SIZE &&
2342 Adapter->uiSectorSizeInCFG >= MIN_SECTOR_SIZE)
2343 {
2344 Adapter->uiSectorSize = Adapter->uiSectorSizeInCFG;
2345 }
2346 else
2347 {
2348 Adapter->uiSectorSize = DEFAULT_SECTOR_SIZE;
2349 }
2350 }
2351 }
2352
2353 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "Sector size :%x \n", Adapter->uiSectorSize);
2354 return Adapter->uiSectorSize;
2355}
2356
2357//-----------------------------------------------------------------------------
2358// Procedure: BcmInitEEPROMQueues
2359//
2360// Description: Initialization of EEPROM queues.
2361//
2362// Arguments:
2363// Adapter - ptr to Adapter object instance
2364//
2365// Returns:
2366// <OSAL_STATUS_CODE>
2367//-----------------------------------------------------------------------------
2368
44a17eff 2369static INT BcmInitEEPROMQueues(PMINI_ADAPTER Adapter)
f8942e07
SH
2370{
2371 UINT value = 0;
2372 /* CHIP Bug : Clear the Avail bits on the Read queue. The default
2373 * value on this register is supposed to be 0x00001102.
2374 * But we get 0x00001122. */
2375 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"Fixing reset value on 0x0f003004 register\n" );
2376 value = EEPROM_READ_DATA_AVAIL;
2377 wrmalt( Adapter, EEPROM_SPI_Q_STATUS1_REG, &value, sizeof(value));
2378
2379 /* Flush the all the EEPROM queues. */
2380 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, " Flushing the queues\n");
2381 value =EEPROM_ALL_QUEUE_FLUSH ;
2382 wrmalt( Adapter, SPI_FLUSH_REG, &value, sizeof(value));
2383
2384 value = 0;
2385 wrmalt( Adapter, SPI_FLUSH_REG, &value, sizeof(value) );
2386
2387 /* Read the EEPROM Status Register. Just to see, no real purpose. */
2388 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "EEPROM Status register value = %x\n", ReadEEPROMStatusRegister(Adapter) );
2389
2390 return STATUS_SUCCESS;
2391} /* BcmInitEEPROMQueues() */
2392
2393//-----------------------------------------------------------------------------
2394// Procedure: BcmInitNVM
2395//
2396// Description: Initialization of NVM, EEPROM size,FLASH size, sector size etc.
2397//
2398// Arguments:
2399// Adapter - ptr to Adapter object instance
2400//
2401// Returns:
2402// <OSAL_STATUS_CODE>
2403//-----------------------------------------------------------------------------
2404
2405INT BcmInitNVM(PMINI_ADAPTER ps_adapter)
2406{
f8942e07
SH
2407 BcmValidateNvmType(ps_adapter);
2408 BcmInitEEPROMQueues(ps_adapter);
f8942e07
SH
2409
2410 if(ps_adapter->eNVMType == NVM_AUTODETECT)
2411 {
2412 ps_adapter->eNVMType = BcmGetNvmType(ps_adapter);
2413 if(ps_adapter->eNVMType == NVM_UNKNOWN)
2414 {
2415 BCM_DEBUG_PRINT(ps_adapter,DBG_TYPE_PRINTK, 0, 0, "NVM Type is unknown!!\n");
2416 }
2417 }
2418 else if(ps_adapter->eNVMType == NVM_FLASH)
2419 {
2420 BcmGetFlashCSInfo(ps_adapter);
2421 }
2422
2423 BcmGetNvmSize(ps_adapter);
2424
2425 return STATUS_SUCCESS;
2426}
2427/***************************************************************************/
2428/*BcmGetNvmSize : set the EEPROM or flash size in Adapter.
2429*
2430*Input Parameter:
2431* Adapter data structure
2432*Return Value :
25985edc 2433* 0. means success;
f8942e07
SH
2434*/
2435/***************************************************************************/
2436
9dd47ee7 2437static INT BcmGetNvmSize(PMINI_ADAPTER Adapter)
f8942e07
SH
2438{
2439 if(Adapter->eNVMType == NVM_EEPROM)
2440 {
2441 Adapter->uiNVMDSDSize = BcmGetEEPROMSize(Adapter);
2442 }
2443 else if(Adapter->eNVMType == NVM_FLASH)
2444 {
2445 Adapter->uiNVMDSDSize = BcmGetFlashSize(Adapter);
2446 }
2447 return 0;
2448}
2449
2450//-----------------------------------------------------------------------------
2451// Procedure: BcmValidateNvm
2452//
2453// Description: Validates the NVM Type option selected against the device
2454//
2455// Arguments:
2456// Adapter - ptr to Adapter object instance
2457//
2458// Returns:
2459// <VOID>
2460//-----------------------------------------------------------------------------
9dd47ee7 2461static VOID BcmValidateNvmType(PMINI_ADAPTER Adapter)
f8942e07
SH
2462{
2463
2464 //
2465 // if forcing the FLASH through CFG file, we should ensure device really has a FLASH.
2466 // Accessing the FLASH address without the FLASH being present can cause hang/freeze etc.
2467 // So if NVM_FLASH is selected for older chipsets, change it to AUTODETECT where EEPROM is 1st choice.
2468 //
2469
2470 if(Adapter->eNVMType == NVM_FLASH &&
2471 Adapter->chip_id < 0xBECE3300)
2472 {
2473 Adapter->eNVMType = NVM_AUTODETECT;
2474 }
2475}
2476//-----------------------------------------------------------------------------
2477// Procedure: BcmReadFlashRDID
2478//
2479// Description: Reads ID from Serial Flash
2480//
2481// Arguments:
2482// Adapter - ptr to Adapter object instance
2483//
2484// Returns:
2485// Flash ID
2486//-----------------------------------------------------------------------------
44a17eff 2487static ULONG BcmReadFlashRDID(PMINI_ADAPTER Adapter)
f8942e07
SH
2488{
2489 ULONG ulRDID = 0;
2490 UINT value;
2491//
2492// Read ID Instruction.
2493//
2494 value = (FLASH_CMD_READ_ID<<24);
2495 wrmalt(Adapter, FLASH_SPI_CMDQ_REG,&value, sizeof(value));
2496
2497//Delay
2498 udelay(10);
2499//
2500// Read SPI READQ REG. The output will be WWXXYYZZ.
2501// The ID is 3Bytes long and is WWXXYY. ZZ needs to be Ignored.
2502//
2503 rdmalt(Adapter, FLASH_SPI_READQ_REG,(PUINT)&ulRDID, sizeof(ulRDID));
2504
2505 return (ulRDID >>8);
2506
2507
2508}
2509
2510INT BcmAllocFlashCSStructure(PMINI_ADAPTER psAdapter)
2511{
2512 if(psAdapter == NULL)
2513 {
2514 BCM_DEBUG_PRINT(psAdapter,DBG_TYPE_PRINTK, 0, 0, "Adapter structure point is NULL");
2515 return -EINVAL;
2516 }
2517 psAdapter->psFlashCSInfo = (PFLASH_CS_INFO)kzalloc(sizeof(FLASH_CS_INFO), GFP_KERNEL);
2518 if(psAdapter->psFlashCSInfo == NULL)
2519 {
2520 BCM_DEBUG_PRINT(psAdapter,DBG_TYPE_PRINTK, 0, 0,"Can't Allocate memory for Flash 1.x");
2521 return -ENOMEM;
2522 }
2523
2524 psAdapter->psFlash2xCSInfo = (PFLASH2X_CS_INFO)kzalloc(sizeof(FLASH2X_CS_INFO), GFP_KERNEL);
2525 if(psAdapter->psFlash2xCSInfo == NULL)
2526 {
2527 BCM_DEBUG_PRINT(psAdapter,DBG_TYPE_PRINTK, 0, 0,"Can't Allocate memory for Flash 2.x");
082e889b 2528 kfree(psAdapter->psFlashCSInfo);
f8942e07
SH
2529 return -ENOMEM;
2530 }
2531
2532 psAdapter->psFlash2xVendorInfo = (PFLASH2X_VENDORSPECIFIC_INFO)kzalloc(sizeof(FLASH2X_VENDORSPECIFIC_INFO), GFP_KERNEL);
2533 if(psAdapter->psFlash2xVendorInfo == NULL)
2534 {
2535 BCM_DEBUG_PRINT(psAdapter,DBG_TYPE_PRINTK, 0, 0,"Can't Allocate Vendor Info Memory for Flash 2.x");
082e889b
SH
2536 kfree(psAdapter->psFlashCSInfo);
2537 kfree(psAdapter->psFlash2xCSInfo);
f8942e07
SH
2538 return -ENOMEM;
2539 }
2540
2541 return STATUS_SUCCESS;
2542}
2543
2544INT BcmDeAllocFlashCSStructure(PMINI_ADAPTER psAdapter)
2545{
2546 if(psAdapter == NULL)
2547 {
2548 BCM_DEBUG_PRINT(psAdapter,DBG_TYPE_PRINTK, 0, 0," Adapter structure point is NULL");
2549 return -EINVAL;
2550 }
082e889b
SH
2551 kfree(psAdapter->psFlashCSInfo);
2552 kfree(psAdapter->psFlash2xCSInfo);
2553 kfree(psAdapter->psFlash2xVendorInfo);
f8942e07
SH
2554 return STATUS_SUCCESS ;
2555}
2556
44a17eff 2557static INT BcmDumpFlash2XCSStructure(PFLASH2X_CS_INFO psFlash2xCSInfo,PMINI_ADAPTER Adapter)
f8942e07
SH
2558{
2559 UINT Index = 0;
2560 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "**********************FLASH2X CS Structure *******************");
2561 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "Signature is :%x", (psFlash2xCSInfo->MagicNumber));
2562 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "Flash Major Version :%d", MAJOR_VERSION(psFlash2xCSInfo->FlashLayoutVersion));
2563 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "Flash Minor Version :%d", MINOR_VERSION(psFlash2xCSInfo->FlashLayoutVersion));
2564 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, " ISOImageMajorVersion:0x%x", (psFlash2xCSInfo->ISOImageVersion));
2565 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "SCSIFirmwareMajorVersion :0x%x", (psFlash2xCSInfo->SCSIFirmwareVersion));
2566 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetFromZeroForPart1ISOImage :0x%x", (psFlash2xCSInfo->OffsetFromZeroForPart1ISOImage));
2567 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetFromZeroForScsiFirmware :0x%x", (psFlash2xCSInfo->OffsetFromZeroForScsiFirmware));
2568 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "SizeOfScsiFirmware :0x%x", (psFlash2xCSInfo->SizeOfScsiFirmware ));
2569 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetFromZeroForPart2ISOImage :0x%x", (psFlash2xCSInfo->OffsetFromZeroForPart2ISOImage));
2570 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetFromZeroForDSDStart :0x%x", (psFlash2xCSInfo->OffsetFromZeroForDSDStart));
2571 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetFromZeroForDSDEnd :0x%x", (psFlash2xCSInfo->OffsetFromZeroForDSDEnd));
2572 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetFromZeroForVSAStart :0x%x", (psFlash2xCSInfo->OffsetFromZeroForVSAStart));
2573 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetFromZeroForVSAEnd :0x%x", (psFlash2xCSInfo->OffsetFromZeroForVSAEnd));
2574 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetFromZeroForControlSectionStart :0x%x", (psFlash2xCSInfo->OffsetFromZeroForControlSectionStart));
2575 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetFromZeroForControlSectionData :0x%x", (psFlash2xCSInfo->OffsetFromZeroForControlSectionData));
2576 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "CDLessInactivityTimeout :0x%x", (psFlash2xCSInfo->CDLessInactivityTimeout));
2577 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "NewImageSignature :0x%x", (psFlash2xCSInfo->NewImageSignature));
2578 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "FlashSectorSizeSig :0x%x", (psFlash2xCSInfo->FlashSectorSizeSig));
2579 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "FlashSectorSize :0x%x", (psFlash2xCSInfo->FlashSectorSize));
2580 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "FlashWriteSupportSize :0x%x", (psFlash2xCSInfo->FlashWriteSupportSize));
2581 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "TotalFlashSize :0x%X", (psFlash2xCSInfo->TotalFlashSize));
2582 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "FlashBaseAddr :0x%x", (psFlash2xCSInfo->FlashBaseAddr));
2583 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "FlashPartMaxSize :0x%x", (psFlash2xCSInfo->FlashPartMaxSize));
2584 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "IsCDLessDeviceBootSig :0x%x", (psFlash2xCSInfo->IsCDLessDeviceBootSig));
2585 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "MassStorageTimeout :0x%x", (psFlash2xCSInfo->MassStorageTimeout));
2586 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetISOImage1Part1Start :0x%x", (psFlash2xCSInfo->OffsetISOImage1Part1Start));
2587 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetISOImage1Part1End :0x%x", (psFlash2xCSInfo->OffsetISOImage1Part1End));
2588 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetISOImage1Part2Start :0x%x", (psFlash2xCSInfo->OffsetISOImage1Part2Start));
2589 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetISOImage1Part2End :0x%x", (psFlash2xCSInfo->OffsetISOImage1Part2End));
2590 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetISOImage1Part3Start :0x%x", (psFlash2xCSInfo->OffsetISOImage1Part3Start));
2591 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetISOImage1Part3End :0x%x", (psFlash2xCSInfo->OffsetISOImage1Part3End));
2592 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetISOImage2Part1Start :0x%x", (psFlash2xCSInfo->OffsetISOImage2Part1Start));
2593 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetISOImage2Part1End :0x%x", (psFlash2xCSInfo->OffsetISOImage2Part1End));
2594 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetISOImage2Part2Start :0x%x", (psFlash2xCSInfo->OffsetISOImage2Part2Start));
2595 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetISOImage2Part2End :0x%x", (psFlash2xCSInfo->OffsetISOImage2Part2End));
2596 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetISOImage2Part3Start :0x%x", (psFlash2xCSInfo->OffsetISOImage2Part3Start));
2597 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetISOImage2Part3End :0x%x", (psFlash2xCSInfo->OffsetISOImage2Part3End));
2598 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetFromDSDStartForDSDHeader :0x%x", (psFlash2xCSInfo->OffsetFromDSDStartForDSDHeader));
2599 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetFromZeroForDSD1Start :0x%x", (psFlash2xCSInfo->OffsetFromZeroForDSD1Start));
2600 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetFromZeroForDSD1End :0x%x", (psFlash2xCSInfo->OffsetFromZeroForDSD1End));
2601 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetFromZeroForDSD2Start :0x%x", (psFlash2xCSInfo->OffsetFromZeroForDSD2Start));
2602 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetFromZeroForDSD2End :0x%x", (psFlash2xCSInfo->OffsetFromZeroForDSD2End));
2603 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetFromZeroForVSA1Start :0x%x", (psFlash2xCSInfo->OffsetFromZeroForVSA1Start));
2604 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetFromZeroForVSA1End :0x%x", (psFlash2xCSInfo->OffsetFromZeroForVSA1End));
2605 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetFromZeroForVSA2Start :0x%x", (psFlash2xCSInfo->OffsetFromZeroForVSA2Start));
2606 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "OffsetFromZeroForVSA2End :0x%x", (psFlash2xCSInfo->OffsetFromZeroForVSA2End));
2607 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "Sector Access Bit Map is Defined as :");
2608 for(Index =0; Index <(FLASH2X_TOTAL_SIZE/(DEFAULT_SECTOR_SIZE *16)); Index++)
2609 {
2610 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "SectorAccessBitMap[%d] :0x%x", Index,
2611 (psFlash2xCSInfo->SectorAccessBitMap[Index]));
2612 }
2613
2614 return STATUS_SUCCESS;
2615}
2616
2617
44a17eff 2618static INT ConvertEndianOf2XCSStructure(PFLASH2X_CS_INFO psFlash2xCSInfo)
f8942e07
SH
2619{
2620 UINT Index = 0;
2621 psFlash2xCSInfo->MagicNumber = ntohl(psFlash2xCSInfo->MagicNumber);
2622 psFlash2xCSInfo->FlashLayoutVersion= ntohl(psFlash2xCSInfo->FlashLayoutVersion);
2623 //psFlash2xCSInfo->FlashLayoutMinorVersion = ntohs(psFlash2xCSInfo->FlashLayoutMinorVersion);
2624 psFlash2xCSInfo->ISOImageVersion = ntohl(psFlash2xCSInfo->ISOImageVersion);
2625 psFlash2xCSInfo->SCSIFirmwareVersion =ntohl(psFlash2xCSInfo->SCSIFirmwareVersion);
2626 psFlash2xCSInfo->OffsetFromZeroForPart1ISOImage = ntohl(psFlash2xCSInfo->OffsetFromZeroForPart1ISOImage);
2627 psFlash2xCSInfo->OffsetFromZeroForScsiFirmware = ntohl(psFlash2xCSInfo->OffsetFromZeroForScsiFirmware);
2628 psFlash2xCSInfo->SizeOfScsiFirmware = ntohl(psFlash2xCSInfo->SizeOfScsiFirmware );
2629 psFlash2xCSInfo->OffsetFromZeroForPart2ISOImage = ntohl(psFlash2xCSInfo->OffsetFromZeroForPart2ISOImage);
2630 psFlash2xCSInfo->OffsetFromZeroForDSDStart = ntohl(psFlash2xCSInfo->OffsetFromZeroForDSDStart);
2631 psFlash2xCSInfo->OffsetFromZeroForDSDEnd = ntohl(psFlash2xCSInfo->OffsetFromZeroForDSDEnd);
2632 psFlash2xCSInfo->OffsetFromZeroForVSAStart = ntohl(psFlash2xCSInfo->OffsetFromZeroForVSAStart);
2633 psFlash2xCSInfo->OffsetFromZeroForVSAEnd = ntohl(psFlash2xCSInfo->OffsetFromZeroForVSAEnd);
2634 psFlash2xCSInfo->OffsetFromZeroForControlSectionStart = ntohl(psFlash2xCSInfo->OffsetFromZeroForControlSectionStart);
2635 psFlash2xCSInfo->OffsetFromZeroForControlSectionData = ntohl(psFlash2xCSInfo->OffsetFromZeroForControlSectionData);
2636 psFlash2xCSInfo->CDLessInactivityTimeout = ntohl(psFlash2xCSInfo->CDLessInactivityTimeout);
2637 psFlash2xCSInfo->NewImageSignature = ntohl(psFlash2xCSInfo->NewImageSignature);
2638 psFlash2xCSInfo->FlashSectorSizeSig = ntohl(psFlash2xCSInfo->FlashSectorSizeSig);
2639 psFlash2xCSInfo->FlashSectorSize = ntohl(psFlash2xCSInfo->FlashSectorSize);
2640 psFlash2xCSInfo->FlashWriteSupportSize = ntohl(psFlash2xCSInfo->FlashWriteSupportSize);
2641 psFlash2xCSInfo->TotalFlashSize = ntohl(psFlash2xCSInfo->TotalFlashSize);
2642 psFlash2xCSInfo->FlashBaseAddr = ntohl(psFlash2xCSInfo->FlashBaseAddr);
2643 psFlash2xCSInfo->FlashPartMaxSize = ntohl(psFlash2xCSInfo->FlashPartMaxSize);
2644 psFlash2xCSInfo->IsCDLessDeviceBootSig = ntohl(psFlash2xCSInfo->IsCDLessDeviceBootSig);
2645 psFlash2xCSInfo->MassStorageTimeout = ntohl(psFlash2xCSInfo->MassStorageTimeout);
2646 psFlash2xCSInfo->OffsetISOImage1Part1Start = ntohl(psFlash2xCSInfo->OffsetISOImage1Part1Start);
2647 psFlash2xCSInfo->OffsetISOImage1Part1End = ntohl(psFlash2xCSInfo->OffsetISOImage1Part1End);
2648 psFlash2xCSInfo->OffsetISOImage1Part2Start = ntohl(psFlash2xCSInfo->OffsetISOImage1Part2Start);
2649 psFlash2xCSInfo->OffsetISOImage1Part2End = ntohl(psFlash2xCSInfo->OffsetISOImage1Part2End);
2650 psFlash2xCSInfo->OffsetISOImage1Part3Start = ntohl(psFlash2xCSInfo->OffsetISOImage1Part3Start);
2651 psFlash2xCSInfo->OffsetISOImage1Part3End = ntohl(psFlash2xCSInfo->OffsetISOImage1Part3End);
2652 psFlash2xCSInfo->OffsetISOImage2Part1Start = ntohl(psFlash2xCSInfo->OffsetISOImage2Part1Start);
2653 psFlash2xCSInfo->OffsetISOImage2Part1End = ntohl(psFlash2xCSInfo->OffsetISOImage2Part1End);
2654 psFlash2xCSInfo->OffsetISOImage2Part2Start = ntohl(psFlash2xCSInfo->OffsetISOImage2Part2Start);
2655 psFlash2xCSInfo->OffsetISOImage2Part2End = ntohl(psFlash2xCSInfo->OffsetISOImage2Part2End);
2656 psFlash2xCSInfo->OffsetISOImage2Part3Start = ntohl(psFlash2xCSInfo->OffsetISOImage2Part3Start);
2657 psFlash2xCSInfo->OffsetISOImage2Part3End = ntohl(psFlash2xCSInfo->OffsetISOImage2Part3End);
2658 psFlash2xCSInfo->OffsetFromDSDStartForDSDHeader = ntohl(psFlash2xCSInfo->OffsetFromDSDStartForDSDHeader);
2659 psFlash2xCSInfo->OffsetFromZeroForDSD1Start = ntohl(psFlash2xCSInfo->OffsetFromZeroForDSD1Start);
2660 psFlash2xCSInfo->OffsetFromZeroForDSD1End = ntohl(psFlash2xCSInfo->OffsetFromZeroForDSD1End);
2661 psFlash2xCSInfo->OffsetFromZeroForDSD2Start = ntohl(psFlash2xCSInfo->OffsetFromZeroForDSD2Start);
2662 psFlash2xCSInfo->OffsetFromZeroForDSD2End = ntohl(psFlash2xCSInfo->OffsetFromZeroForDSD2End);
2663 psFlash2xCSInfo->OffsetFromZeroForVSA1Start = ntohl(psFlash2xCSInfo->OffsetFromZeroForVSA1Start);
2664 psFlash2xCSInfo->OffsetFromZeroForVSA1End = ntohl(psFlash2xCSInfo->OffsetFromZeroForVSA1End);
2665 psFlash2xCSInfo->OffsetFromZeroForVSA2Start = ntohl(psFlash2xCSInfo->OffsetFromZeroForVSA2Start);
2666 psFlash2xCSInfo->OffsetFromZeroForVSA2End = ntohl(psFlash2xCSInfo->OffsetFromZeroForVSA2End);
2667 for(Index =0; Index <(FLASH2X_TOTAL_SIZE/(DEFAULT_SECTOR_SIZE *16)); Index++)
2668 {
2669 psFlash2xCSInfo->SectorAccessBitMap[Index] = ntohl(psFlash2xCSInfo->SectorAccessBitMap[Index]);
2670 }
2671 return STATUS_SUCCESS;
2672}
2673
44a17eff 2674static INT ConvertEndianOfCSStructure(PFLASH_CS_INFO psFlashCSInfo)
f8942e07
SH
2675{
2676 //UINT Index = 0;
2677 psFlashCSInfo->MagicNumber =ntohl(psFlashCSInfo->MagicNumber);
2678 psFlashCSInfo->FlashLayoutVersion =ntohl(psFlashCSInfo->FlashLayoutVersion);
2679 psFlashCSInfo->ISOImageVersion = ntohl(psFlashCSInfo->ISOImageVersion);
2680 //won't convert according to old assumption
2681 psFlashCSInfo->SCSIFirmwareVersion =(psFlashCSInfo->SCSIFirmwareVersion);
2682
2683 psFlashCSInfo->OffsetFromZeroForPart1ISOImage = ntohl(psFlashCSInfo->OffsetFromZeroForPart1ISOImage);
2684 psFlashCSInfo->OffsetFromZeroForScsiFirmware = ntohl(psFlashCSInfo->OffsetFromZeroForScsiFirmware);
2685 psFlashCSInfo->SizeOfScsiFirmware = ntohl(psFlashCSInfo->SizeOfScsiFirmware );
2686 psFlashCSInfo->OffsetFromZeroForPart2ISOImage = ntohl(psFlashCSInfo->OffsetFromZeroForPart2ISOImage);
2687 psFlashCSInfo->OffsetFromZeroForCalibrationStart = ntohl(psFlashCSInfo->OffsetFromZeroForCalibrationStart);
2688 psFlashCSInfo->OffsetFromZeroForCalibrationEnd = ntohl(psFlashCSInfo->OffsetFromZeroForCalibrationEnd);
2689 psFlashCSInfo->OffsetFromZeroForVSAStart = ntohl(psFlashCSInfo->OffsetFromZeroForVSAStart);
2690 psFlashCSInfo->OffsetFromZeroForVSAEnd = ntohl(psFlashCSInfo->OffsetFromZeroForVSAEnd);
2691 psFlashCSInfo->OffsetFromZeroForControlSectionStart = ntohl(psFlashCSInfo->OffsetFromZeroForControlSectionStart);
2692 psFlashCSInfo->OffsetFromZeroForControlSectionData = ntohl(psFlashCSInfo->OffsetFromZeroForControlSectionData);
2693 psFlashCSInfo->CDLessInactivityTimeout = ntohl(psFlashCSInfo->CDLessInactivityTimeout);
2694 psFlashCSInfo->NewImageSignature = ntohl(psFlashCSInfo->NewImageSignature);
2695 psFlashCSInfo->FlashSectorSizeSig = ntohl(psFlashCSInfo->FlashSectorSizeSig);
2696 psFlashCSInfo->FlashSectorSize = ntohl(psFlashCSInfo->FlashSectorSize);
2697 psFlashCSInfo->FlashWriteSupportSize = ntohl(psFlashCSInfo->FlashWriteSupportSize);
2698 psFlashCSInfo->TotalFlashSize = ntohl(psFlashCSInfo->TotalFlashSize);
2699 psFlashCSInfo->FlashBaseAddr = ntohl(psFlashCSInfo->FlashBaseAddr);
2700 psFlashCSInfo->FlashPartMaxSize = ntohl(psFlashCSInfo->FlashPartMaxSize);
2701 psFlashCSInfo->IsCDLessDeviceBootSig = ntohl(psFlashCSInfo->IsCDLessDeviceBootSig);
2702 psFlashCSInfo->MassStorageTimeout = ntohl(psFlashCSInfo->MassStorageTimeout);
2703
2704 return STATUS_SUCCESS;
2705}
2706
9dd47ee7 2707static INT IsSectionExistInVendorInfo(PMINI_ADAPTER Adapter, FLASH2X_SECTION_VAL section)
f8942e07
SH
2708{
2709 return ( Adapter->uiVendorExtnFlag &&
2710 (Adapter->psFlash2xVendorInfo->VendorSection[section].AccessFlags & FLASH2X_SECTION_PRESENT) &&
2711 (Adapter->psFlash2xVendorInfo->VendorSection[section].OffsetFromZeroForSectionStart != UNINIT_PTR_IN_CS) );
2712}
2713
44a17eff 2714static VOID UpdateVendorInfo(PMINI_ADAPTER Adapter)
f8942e07
SH
2715{
2716 B_UINT32 i = 0;
2717 UINT uiSizeSection = 0;
2718
2719 Adapter->uiVendorExtnFlag = FALSE;
2720
2721 for(i = 0;i < TOTAL_SECTIONS;i++)
2722 Adapter->psFlash2xVendorInfo->VendorSection[i].OffsetFromZeroForSectionStart = UNINIT_PTR_IN_CS;
2723
2724 if(STATUS_SUCCESS != vendorextnGetSectionInfo(Adapter, Adapter->psFlash2xVendorInfo))
2725 return;
2726
2727 i = 0;
2728 while(i < TOTAL_SECTIONS)
2729 {
2730 if(!(Adapter->psFlash2xVendorInfo->VendorSection[i].AccessFlags & FLASH2X_SECTION_PRESENT))
2731 {
2732 i++;
2733 continue;
2734 }
2735
2736 Adapter->uiVendorExtnFlag = TRUE;
2737 uiSizeSection = (Adapter->psFlash2xVendorInfo->VendorSection[i].OffsetFromZeroForSectionEnd -
2738 Adapter->psFlash2xVendorInfo->VendorSection[i].OffsetFromZeroForSectionStart);
2739
2740 switch(i)
2741 {
2742 case DSD0:
2743 if(( uiSizeSection >= (Adapter->psFlash2xCSInfo->OffsetFromDSDStartForDSDHeader + sizeof(DSD_HEADER))) &&
2744 (UNINIT_PTR_IN_CS != Adapter->psFlash2xVendorInfo->VendorSection[i].OffsetFromZeroForSectionStart))
2745 Adapter->psFlash2xCSInfo->OffsetFromZeroForDSDStart = Adapter->psFlash2xCSInfo->OffsetFromZeroForDSDEnd = VENDOR_PTR_IN_CS;
2746 else
2747 Adapter->psFlash2xCSInfo->OffsetFromZeroForDSDStart = Adapter->psFlash2xCSInfo->OffsetFromZeroForDSDEnd = UNINIT_PTR_IN_CS;
2748 break;
2749
2750 case DSD1:
2751 if(( uiSizeSection >= (Adapter->psFlash2xCSInfo->OffsetFromDSDStartForDSDHeader + sizeof(DSD_HEADER))) &&
2752 (UNINIT_PTR_IN_CS != Adapter->psFlash2xVendorInfo->VendorSection[i].OffsetFromZeroForSectionStart))
2753 Adapter->psFlash2xCSInfo->OffsetFromZeroForDSD1Start = Adapter->psFlash2xCSInfo->OffsetFromZeroForDSD1End = VENDOR_PTR_IN_CS;
2754 else
2755 Adapter->psFlash2xCSInfo->OffsetFromZeroForDSD1Start = Adapter->psFlash2xCSInfo->OffsetFromZeroForDSD1End = UNINIT_PTR_IN_CS;
2756 break;
2757
2758 case DSD2:
2759 if(( uiSizeSection >= (Adapter->psFlash2xCSInfo->OffsetFromDSDStartForDSDHeader + sizeof(DSD_HEADER))) &&
2760 (UNINIT_PTR_IN_CS != Adapter->psFlash2xVendorInfo->VendorSection[i].OffsetFromZeroForSectionStart))
2761 Adapter->psFlash2xCSInfo->OffsetFromZeroForDSD2Start = Adapter->psFlash2xCSInfo->OffsetFromZeroForDSD2End = VENDOR_PTR_IN_CS;
2762 else
2763 Adapter->psFlash2xCSInfo->OffsetFromZeroForDSD2Start = Adapter->psFlash2xCSInfo->OffsetFromZeroForDSD2End = UNINIT_PTR_IN_CS;
2764 break;
2765 case VSA0:
2766 if(UNINIT_PTR_IN_CS != Adapter->psFlash2xVendorInfo->VendorSection[i].OffsetFromZeroForSectionStart)
2767 Adapter->psFlash2xCSInfo->OffsetFromZeroForVSAStart = Adapter->psFlash2xCSInfo->OffsetFromZeroForVSAEnd = VENDOR_PTR_IN_CS;
2768 else
2769 Adapter->psFlash2xCSInfo->OffsetFromZeroForVSAStart = Adapter->psFlash2xCSInfo->OffsetFromZeroForVSAEnd = UNINIT_PTR_IN_CS;
2770 break;
2771
2772 case VSA1:
2773 if(UNINIT_PTR_IN_CS != Adapter->psFlash2xVendorInfo->VendorSection[i].OffsetFromZeroForSectionStart)
2774 Adapter->psFlash2xCSInfo->OffsetFromZeroForVSA1Start = Adapter->psFlash2xCSInfo->OffsetFromZeroForVSA1End = VENDOR_PTR_IN_CS;
2775 else
2776 Adapter->psFlash2xCSInfo->OffsetFromZeroForVSA1Start = Adapter->psFlash2xCSInfo->OffsetFromZeroForVSA1End = UNINIT_PTR_IN_CS;
2777 break;
2778 case VSA2:
2779 if(UNINIT_PTR_IN_CS != Adapter->psFlash2xVendorInfo->VendorSection[i].OffsetFromZeroForSectionStart)
2780 Adapter->psFlash2xCSInfo->OffsetFromZeroForVSA2Start = Adapter->psFlash2xCSInfo->OffsetFromZeroForVSA2End = VENDOR_PTR_IN_CS;
2781 else
2782 Adapter->psFlash2xCSInfo->OffsetFromZeroForVSA2Start = Adapter->psFlash2xCSInfo->OffsetFromZeroForVSA2End = UNINIT_PTR_IN_CS;
2783 break;
2784
2785 default:
2786 break;
2787 }
2788 i++;
2789 }
2790
2791}
2792
2793//-----------------------------------------------------------------------------
2794// Procedure: BcmGetFlashCSInfo
2795//
2796// Description: Reads control structure and gets Cal section addresses.
2797//
2798// Arguments:
2799// Adapter - ptr to Adapter object instance
2800//
2801// Returns:
2802// <VOID>
2803//-----------------------------------------------------------------------------
2804
9dd47ee7 2805static INT BcmGetFlashCSInfo(PMINI_ADAPTER Adapter)
f8942e07
SH
2806{
2807 //FLASH_CS_INFO sFlashCsInfo = {0};
2808
2809#if !defined(BCM_SHM_INTERFACE) || defined(FLASH_DIRECT_ACCESS)
2810 UINT value;
2811#endif
2812 UINT uiFlashLayoutMajorVersion;
2813 Adapter->uiFlashLayoutMinorVersion = 0;
2814 Adapter->uiFlashLayoutMajorVersion = 0;
2815 Adapter->ulFlashControlSectionStart = FLASH_CS_INFO_START_ADDR;
2816
2817
2818 Adapter->uiFlashBaseAdd = 0;
2819 Adapter->ulFlashCalStart = 0;
2820 memset(Adapter->psFlashCSInfo, 0 ,sizeof(FLASH_CS_INFO));
2821 memset(Adapter->psFlash2xCSInfo, 0 ,sizeof(FLASH2X_CS_INFO));
2822
f8942e07
SH
2823 if(!Adapter->bDDRInitDone)
2824 {
2825 {
2826 value = FLASH_CONTIGIOUS_START_ADDR_BEFORE_INIT;
2827 wrmalt(Adapter, 0xAF00A080, &value, sizeof(value));
2828 }
2829 }
2830
f8942e07
SH
2831
2832 // Reading first 8 Bytes to get the Flash Layout
2833 // MagicNumber(4 bytes) +FlashLayoutMinorVersion(2 Bytes) +FlashLayoutMajorVersion(2 Bytes)
2834 BeceemFlashBulkRead(Adapter,(PUINT)Adapter->psFlashCSInfo,Adapter->ulFlashControlSectionStart,8);
2835
2836 Adapter->psFlashCSInfo->FlashLayoutVersion = ntohl(Adapter->psFlashCSInfo->FlashLayoutVersion);
2837 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "Flash Layout Version :%X", (Adapter->psFlashCSInfo->FlashLayoutVersion));
2838 //BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "Flash Layout Minor Version :%d\n", ntohs(sFlashCsInfo.FlashLayoutMinorVersion));
2839 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "Signature is :%x\n", ntohl(Adapter->psFlashCSInfo->MagicNumber));
2840
2841 if(FLASH_CONTROL_STRUCT_SIGNATURE == ntohl(Adapter->psFlashCSInfo->MagicNumber))
2842 {
2843 uiFlashLayoutMajorVersion = MAJOR_VERSION((Adapter->psFlashCSInfo->FlashLayoutVersion));
2844 Adapter->uiFlashLayoutMinorVersion = MINOR_VERSION((Adapter->psFlashCSInfo->FlashLayoutVersion));
2845 }
2846 else
2847 {
2848 Adapter->uiFlashLayoutMinorVersion = 0;
2849 uiFlashLayoutMajorVersion = 0;
2850 }
2851
2852 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"FLASH LAYOUT MAJOR VERSION :%X", uiFlashLayoutMajorVersion);
2853
2854 if(uiFlashLayoutMajorVersion < FLASH_2X_MAJOR_NUMBER)
2855 {
2856 BeceemFlashBulkRead(Adapter,(PUINT)Adapter->psFlashCSInfo,Adapter->ulFlashControlSectionStart,sizeof(FLASH_CS_INFO));
2857 ConvertEndianOfCSStructure(Adapter->psFlashCSInfo);
2858 Adapter->ulFlashCalStart = (Adapter->psFlashCSInfo->OffsetFromZeroForCalibrationStart);
2859
2860 if(!((Adapter->uiFlashLayoutMajorVersion == 1) && (Adapter->uiFlashLayoutMinorVersion == 1)))
2861 {
2862 Adapter->ulFlashControlSectionStart = Adapter->psFlashCSInfo->OffsetFromZeroForControlSectionStart;
2863 }
2864
2865 if((FLASH_CONTROL_STRUCT_SIGNATURE == (Adapter->psFlashCSInfo->MagicNumber)) &&
2866 (SCSI_FIRMWARE_MINOR_VERSION <= MINOR_VERSION(Adapter->psFlashCSInfo->SCSIFirmwareVersion)) &&
2867 (FLASH_SECTOR_SIZE_SIG == (Adapter->psFlashCSInfo->FlashSectorSizeSig)) &&
2868 (BYTE_WRITE_SUPPORT == (Adapter->psFlashCSInfo->FlashWriteSupportSize)))
2869 {
2870 Adapter->ulFlashWriteSize = (Adapter->psFlashCSInfo->FlashWriteSupportSize);
2871 Adapter->fpFlashWrite = flashByteWrite;
2872 Adapter->fpFlashWriteWithStatusCheck = flashByteWriteStatus;
2873 }
2874 else
2875 {
2876 Adapter->ulFlashWriteSize = MAX_RW_SIZE;
2877 Adapter->fpFlashWrite = flashWrite;
2878 Adapter->fpFlashWriteWithStatusCheck = flashWriteStatus;
2879 }
2880
2881 BcmGetFlashSectorSize(Adapter, (Adapter->psFlashCSInfo->FlashSectorSizeSig),
2882 (Adapter->psFlashCSInfo->FlashSectorSize));
2883
2884
2885 Adapter->uiFlashBaseAdd = Adapter->psFlashCSInfo->FlashBaseAddr & 0xFCFFFFFF;
2886
2887
2888 }
2889 else
2890 {
2891 if(BcmFlash2xBulkRead(Adapter,(PUINT)Adapter->psFlash2xCSInfo,NO_SECTION_VAL,
2892 Adapter->ulFlashControlSectionStart,sizeof(FLASH2X_CS_INFO)))
2893 {
2894 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "Unable to read CS structure \n");
2895 return STATUS_FAILURE;
2896 }
2897 ConvertEndianOf2XCSStructure(Adapter->psFlash2xCSInfo);
f8942e07 2898 BcmDumpFlash2XCSStructure(Adapter->psFlash2xCSInfo,Adapter);
f8942e07
SH
2899 if((FLASH_CONTROL_STRUCT_SIGNATURE == Adapter->psFlash2xCSInfo->MagicNumber) &&
2900 (SCSI_FIRMWARE_MINOR_VERSION <= MINOR_VERSION(Adapter->psFlash2xCSInfo->SCSIFirmwareVersion)) &&
2901 (FLASH_SECTOR_SIZE_SIG == Adapter->psFlash2xCSInfo->FlashSectorSizeSig) &&
2902 (BYTE_WRITE_SUPPORT == Adapter->psFlash2xCSInfo->FlashWriteSupportSize))
2903 {
2904 Adapter->ulFlashWriteSize = Adapter->psFlash2xCSInfo->FlashWriteSupportSize;
2905 Adapter->fpFlashWrite = flashByteWrite;
2906 Adapter->fpFlashWriteWithStatusCheck = flashByteWriteStatus;
2907 }
2908 else
2909 {
2910 Adapter->ulFlashWriteSize = MAX_RW_SIZE;
2911 Adapter->fpFlashWrite = flashWrite;
2912 Adapter->fpFlashWriteWithStatusCheck = flashWriteStatus;
2913 }
2914
2915 BcmGetFlashSectorSize(Adapter, Adapter->psFlash2xCSInfo->FlashSectorSizeSig,
2916 Adapter->psFlash2xCSInfo->FlashSectorSize);
2917
2918 UpdateVendorInfo(Adapter);
2919
2920 BcmGetActiveDSD(Adapter);
2921 BcmGetActiveISO(Adapter);
2922 Adapter->uiFlashBaseAdd = Adapter->psFlash2xCSInfo->FlashBaseAddr & 0xFCFFFFFF;
2923 Adapter->ulFlashControlSectionStart = Adapter->psFlash2xCSInfo->OffsetFromZeroForControlSectionStart;
2924
2925 }
2926 /*
2927 Concerns: what if CS sector size does not match with this sector size ???
2928 what is the indication of AccessBitMap in CS in flash 2.x ????
2929 */
f8942e07 2930 Adapter->ulFlashID = BcmReadFlashRDID(Adapter);
f8942e07
SH
2931
2932 Adapter->uiFlashLayoutMajorVersion = uiFlashLayoutMajorVersion;
2933
f8942e07
SH
2934
2935 return STATUS_SUCCESS ;
2936}
2937
2938
2939//-----------------------------------------------------------------------------
2940// Procedure: BcmGetNvmType
2941//
2942// Description: Finds the type of NVM used.
2943//
2944// Arguments:
2945// Adapter - ptr to Adapter object instance
2946//
2947// Returns:
2948// NVM_TYPE
2949//
2950//-----------------------------------------------------------------------------
2951
9dd47ee7 2952static NVM_TYPE BcmGetNvmType(PMINI_ADAPTER Adapter)
f8942e07
SH
2953{
2954 UINT uiData = 0;
2955
2956 BeceemEEPROMBulkRead(Adapter,&uiData,0x0,4);
2957 if(uiData == BECM)
2958 {
2959 return NVM_EEPROM;
2960 }
2961 //
2962 // Read control struct and get cal addresses before accessing the flash
2963 //
2964 BcmGetFlashCSInfo(Adapter);
2965
2966 BeceemFlashBulkRead(Adapter,&uiData,0x0 + Adapter->ulFlashCalStart,4);
2967 if(uiData == BECM)
2968 {
2969 return NVM_FLASH;
2970 }
2971//
2972// even if there is no valid signature on EEPROM/FLASH find out if they really exist.
2973// if exist select it.
2974//
2975 if(BcmGetEEPROMSize(Adapter))
2976 {
2977 return NVM_EEPROM;
2978 }
2979
2980//TBD for Flash.
2981
2982
2983 return NVM_UNKNOWN;
2984}
2985
2986/**
2987* BcmGetSectionValStartOffset - this will calculate the section's starting offset if section val is given
2988* @Adapter : Drivers Private Data structure
2989* @eFlashSectionVal : Flash secion value defined in enum FLASH2X_SECTION_VAL
2990*
2991* Return value:-
2992* On success it return the start offset of the provided section val
2993* On Failure -returns STATUS_FAILURE
2994**/
2995
2996INT BcmGetSectionValStartOffset(PMINI_ADAPTER Adapter, FLASH2X_SECTION_VAL eFlashSectionVal)
2997{
2998 /*
2999 * Considering all the section for which end offset can be calculated or directly given
3000 * in CS Structure. if matching case does not exist, return STATUS_FAILURE indicating section
25985edc 3001 * endoffset can't be calculated or given in CS Structure.
f8942e07
SH
3002 */
3003
3004 INT SectStartOffset = 0 ;
3005
3006 SectStartOffset = INVALID_OFFSET ;
3007
3008 if(IsSectionExistInVendorInfo(Adapter,eFlashSectionVal))
3009 {
3010 return Adapter->psFlash2xVendorInfo->VendorSection[eFlashSectionVal].OffsetFromZeroForSectionStart;
3011 }
3012
3013 switch(eFlashSectionVal)
3014 {
3015 case ISO_IMAGE1 :
3016 if((Adapter->psFlash2xCSInfo->OffsetISOImage1Part1Start != UNINIT_PTR_IN_CS) &&
3017 (IsNonCDLessDevice(Adapter) == FALSE))
3018 SectStartOffset = (Adapter->psFlash2xCSInfo->OffsetISOImage1Part1Start);
3019 break;
3020 case ISO_IMAGE2 :
3021 if((Adapter->psFlash2xCSInfo->OffsetISOImage2Part1Start != UNINIT_PTR_IN_CS) &&
3022 (IsNonCDLessDevice(Adapter) == FALSE))
3023 SectStartOffset = (Adapter->psFlash2xCSInfo->OffsetISOImage2Part1Start);
3024 break;
3025 case DSD0 :
3026 if(Adapter->psFlash2xCSInfo->OffsetFromZeroForDSDStart != UNINIT_PTR_IN_CS)
3027 SectStartOffset = (Adapter->psFlash2xCSInfo->OffsetFromZeroForDSDStart);
3028 break;
3029 case DSD1 :
3030 if(Adapter->psFlash2xCSInfo->OffsetFromZeroForDSD1Start != UNINIT_PTR_IN_CS)
3031 SectStartOffset = (Adapter->psFlash2xCSInfo->OffsetFromZeroForDSD1Start);
3032 break;
3033 case DSD2 :
3034 if(Adapter->psFlash2xCSInfo->OffsetFromZeroForDSD2Start != UNINIT_PTR_IN_CS)
3035 SectStartOffset = (Adapter->psFlash2xCSInfo->OffsetFromZeroForDSD2Start);
3036 break;
3037 case VSA0 :
3038 if(Adapter->psFlash2xCSInfo->OffsetFromZeroForVSAStart != UNINIT_PTR_IN_CS)
3039 SectStartOffset = (Adapter->psFlash2xCSInfo->OffsetFromZeroForVSAStart);
3040 break;
3041 case VSA1 :
3042 if(Adapter->psFlash2xCSInfo->OffsetFromZeroForVSA1Start != UNINIT_PTR_IN_CS)
3043 SectStartOffset = (Adapter->psFlash2xCSInfo->OffsetFromZeroForVSA1Start);
3044 break;
3045 case VSA2 :
3046 if(Adapter->psFlash2xCSInfo->OffsetFromZeroForVSA2Start != UNINIT_PTR_IN_CS)
3047 SectStartOffset = (Adapter->psFlash2xCSInfo->OffsetFromZeroForVSA2Start);
3048 break;
3049 case SCSI :
3050 if(Adapter->psFlash2xCSInfo->OffsetFromZeroForScsiFirmware != UNINIT_PTR_IN_CS)
3051 SectStartOffset = (Adapter->psFlash2xCSInfo->OffsetFromZeroForScsiFirmware);
3052 break;
3053 case CONTROL_SECTION :
3054 if(Adapter->psFlash2xCSInfo->OffsetFromZeroForControlSectionStart != UNINIT_PTR_IN_CS)
3055 SectStartOffset = (Adapter->psFlash2xCSInfo->OffsetFromZeroForControlSectionStart);
3056 break;
3057 case ISO_IMAGE1_PART2 :
3058 if(Adapter->psFlash2xCSInfo->OffsetISOImage1Part2Start != UNINIT_PTR_IN_CS)
3059 SectStartOffset = (Adapter->psFlash2xCSInfo->OffsetISOImage1Part2Start);
3060 break;
3061 case ISO_IMAGE1_PART3 :
3062 if(Adapter->psFlash2xCSInfo->OffsetISOImage1Part3Start != UNINIT_PTR_IN_CS)
3063 SectStartOffset = (Adapter->psFlash2xCSInfo->OffsetISOImage1Part3Start);
3064 break;
3065 case ISO_IMAGE2_PART2 :
3066 if(Adapter->psFlash2xCSInfo->OffsetISOImage2Part2Start != UNINIT_PTR_IN_CS)
3067 SectStartOffset = (Adapter->psFlash2xCSInfo->OffsetISOImage2Part2Start);
3068 break;
3069 case ISO_IMAGE2_PART3 :
3070 if(Adapter->psFlash2xCSInfo->OffsetISOImage2Part3Start != UNINIT_PTR_IN_CS)
3071 SectStartOffset = (Adapter->psFlash2xCSInfo->OffsetISOImage2Part3Start);
3072 break;
3073 default :
3074 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Section Does not exist in Flash 2.x");
3075 SectStartOffset = INVALID_OFFSET;
3076 }
3077 return SectStartOffset;
3078}
3079
3080/**
3081* BcmGetSectionValEndOffset - this will calculate the section's Ending offset if section val is given
3082* @Adapter : Drivers Private Data structure
3083* @eFlashSectionVal : Flash secion value defined in enum FLASH2X_SECTION_VAL
3084*
3085* Return value:-
3086* On success it return the end offset of the provided section val
3087* On Failure -returns STATUS_FAILURE
3088**/
3089
3090INT BcmGetSectionValEndOffset(PMINI_ADAPTER Adapter, FLASH2X_SECTION_VAL eFlash2xSectionVal)
3091{
3092 INT SectEndOffset = 0 ;
3093 SectEndOffset = INVALID_OFFSET;
3094
3095 if(IsSectionExistInVendorInfo(Adapter,eFlash2xSectionVal))
3096 {
3097 return Adapter->psFlash2xVendorInfo->VendorSection[eFlash2xSectionVal].OffsetFromZeroForSectionEnd;
3098 }
3099
3100 switch(eFlash2xSectionVal)
3101 {
3102 case ISO_IMAGE1 :
3103 if((Adapter->psFlash2xCSInfo->OffsetISOImage1Part1End!= UNINIT_PTR_IN_CS) &&
3104 (IsNonCDLessDevice(Adapter) == FALSE))
3105 SectEndOffset = (Adapter->psFlash2xCSInfo->OffsetISOImage1Part1End);
3106 break;
3107 case ISO_IMAGE2 :
3108 if((Adapter->psFlash2xCSInfo->OffsetISOImage2Part1End!= UNINIT_PTR_IN_CS) &&
3109 (IsNonCDLessDevice(Adapter) == FALSE))
3110 SectEndOffset = (Adapter->psFlash2xCSInfo->OffsetISOImage2Part1End);
3111 break;
3112 case DSD0 :
3113 if(Adapter->psFlash2xCSInfo->OffsetFromZeroForDSDEnd != UNINIT_PTR_IN_CS)
3114 SectEndOffset = (Adapter->psFlash2xCSInfo->OffsetFromZeroForDSDEnd);
3115 break;
3116 case DSD1 :
3117 if(Adapter->psFlash2xCSInfo->OffsetFromZeroForDSD1End != UNINIT_PTR_IN_CS)
3118 SectEndOffset = (Adapter->psFlash2xCSInfo->OffsetFromZeroForDSD1End);
3119 break;
3120 case DSD2 :
3121 if(Adapter->psFlash2xCSInfo->OffsetFromZeroForDSD2End != UNINIT_PTR_IN_CS)
3122 SectEndOffset = (Adapter->psFlash2xCSInfo->OffsetFromZeroForDSD2End);
3123 break;
3124 case VSA0 :
3125 if(Adapter->psFlash2xCSInfo->OffsetFromZeroForVSAEnd != UNINIT_PTR_IN_CS)
3126 SectEndOffset = (Adapter->psFlash2xCSInfo->OffsetFromZeroForVSAEnd);
3127 break;
3128 case VSA1 :
3129 if(Adapter->psFlash2xCSInfo->OffsetFromZeroForVSA1End != UNINIT_PTR_IN_CS)
3130 SectEndOffset = (Adapter->psFlash2xCSInfo->OffsetFromZeroForVSA1End);
3131 break;
3132 case VSA2 :
3133 if(Adapter->psFlash2xCSInfo->OffsetFromZeroForVSA2End != UNINIT_PTR_IN_CS)
3134 SectEndOffset = (Adapter->psFlash2xCSInfo->OffsetFromZeroForVSA2End);
3135 break;
3136 case SCSI :
3137 if(Adapter->psFlash2xCSInfo->OffsetFromZeroForScsiFirmware != UNINIT_PTR_IN_CS)
3138 SectEndOffset = ((Adapter->psFlash2xCSInfo->OffsetFromZeroForScsiFirmware) +
3139 (Adapter->psFlash2xCSInfo->SizeOfScsiFirmware));
3140 break;
3141 case CONTROL_SECTION :
3142 //Not Clear So Putting failure. confirm and fix it.
3143 SectEndOffset = STATUS_FAILURE;
3144 case ISO_IMAGE1_PART2 :
3145 if(Adapter->psFlash2xCSInfo->OffsetISOImage1Part2End!= UNINIT_PTR_IN_CS)
3146 SectEndOffset = (Adapter->psFlash2xCSInfo->OffsetISOImage1Part2End);
3147 break;
3148 case ISO_IMAGE1_PART3 :
3149 if(Adapter->psFlash2xCSInfo->OffsetISOImage1Part3End!= UNINIT_PTR_IN_CS)
3150 SectEndOffset = (Adapter->psFlash2xCSInfo->OffsetISOImage1Part3End);
3151 break;
3152 case ISO_IMAGE2_PART2 :
3153 if(Adapter->psFlash2xCSInfo->OffsetISOImage2Part2End != UNINIT_PTR_IN_CS)
3154 SectEndOffset = (Adapter->psFlash2xCSInfo->OffsetISOImage2Part2End);
3155 break;
3156 case ISO_IMAGE2_PART3 :
3157 if(Adapter->psFlash2xCSInfo->OffsetISOImage2Part3End!= UNINIT_PTR_IN_CS)
3158 SectEndOffset = (Adapter->psFlash2xCSInfo->OffsetISOImage2Part3End);
3159 break;
3160
3161 default :
3162 SectEndOffset = INVALID_OFFSET;
3163 }
3164 return SectEndOffset ;
3165}
3166
3167/*
3168* BcmFlash2xBulkRead:- Read API for Flash Map 2.x .
3169* @Adapter :Driver Private Data Structure
3170* @pBuffer : Buffer where data has to be put after reading
3171* @eFlashSectionVal :Flash Section Val defined in FLASH2X_SECTION_VAL
3172* @uiOffsetWithinSectionVal :- Offset with in provided section
3173* @uiNumBytes : Number of Bytes for Read
3174*
3175* Return value:-
25985edc 3176* return true on success and STATUS_FAILURE on fail.
f8942e07
SH
3177*/
3178
3179INT BcmFlash2xBulkRead(
3180 PMINI_ADAPTER Adapter,
3181 PUINT pBuffer,
3182 FLASH2X_SECTION_VAL eFlash2xSectionVal,
3183 UINT uiOffsetWithinSectionVal,
3184 UINT uiNumBytes)
3185{
3186
3187 INT Status = STATUS_SUCCESS;
3188 INT SectionStartOffset = 0;
3189 UINT uiAbsoluteOffset = 0 ;
3190 UINT uiTemp =0, value =0 ;
3191 if(Adapter == NULL)
3192 {
3193 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "Adapter structure is NULL");
3194 return -EINVAL;
3195 }
3196 if(Adapter->device_removed )
3197 {
3198 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "Device has been removed");
3199 return -ENODEV;
3200 }
3201
3202 //NO_SECTION_VAL means absolute offset is given.
3203 if(eFlash2xSectionVal == NO_SECTION_VAL)
3204 SectionStartOffset = 0;
3205 else
3206 SectionStartOffset = BcmGetSectionValStartOffset(Adapter,eFlash2xSectionVal);
3207
3208 if(SectionStartOffset == STATUS_FAILURE )
3209 {
3210 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"This Section<%d> does not exixt in Flash 2.x Map ",eFlash2xSectionVal);
3211 return -EINVAL;
3212 }
3213
3214 if(IsSectionExistInVendorInfo(Adapter,eFlash2xSectionVal))
3215 return vendorextnReadSection(Adapter,(PUCHAR)pBuffer, eFlash2xSectionVal, uiOffsetWithinSectionVal, uiNumBytes);
3216
3217 //calculating the absolute offset from FLASH;
3218 uiAbsoluteOffset = uiOffsetWithinSectionVal + SectionStartOffset;
3219 rdmalt(Adapter, 0x0f000C80, &uiTemp, sizeof(uiTemp));
3220 value = 0;
3221 wrmalt(Adapter, 0x0f000C80,&value, sizeof(value));
3222
3223 Status= BeceemFlashBulkRead(Adapter, pBuffer,uiAbsoluteOffset,uiNumBytes) ;
3224
3225 wrmalt(Adapter, 0x0f000C80, &uiTemp, sizeof(uiTemp));
3226 if(Status)
3227 {
3228 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "Flash Read Failed with Status :%d", Status);
3229 return Status ;
3230 }
3231
3232 return Status;
3233}
3234
3235/*
3236* BcmFlash2xBulkWrite :-API for Writing on the Flash Map 2.x.
3237* @Adapter :Driver Private Data Structure
3238* @pBuffer : Buffer From where data has to taken for writing
3239* @eFlashSectionVal :Flash Section Val defined in FLASH2X_SECTION_VAL
3240* @uiOffsetWithinSectionVal :- Offset with in provided section
3241* @uiNumBytes : Number of Bytes for Write
3242*
3243* Return value:-
25985edc 3244* return true on success and STATUS_FAILURE on fail.
f8942e07
SH
3245*
3246*/
3247
3248INT BcmFlash2xBulkWrite(
3249 PMINI_ADAPTER Adapter,
3250 PUINT pBuffer,
3251 FLASH2X_SECTION_VAL eFlash2xSectVal,
3252 UINT uiOffset,
3253 UINT uiNumBytes,
3254 UINT bVerify)
3255{
3256
3257 INT Status = STATUS_SUCCESS;
3258 UINT FlashSectValStartOffset = 0;
3259 UINT uiTemp = 0, value = 0;
3260 if(Adapter == NULL)
3261 {
3262 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "Adapter structure is NULL");
3263 return -EINVAL;
3264 }
3265 if(Adapter->device_removed )
3266 {
3267 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "Device has been removed");
3268 return -ENODEV;
3269 }
3270
3271 //NO_SECTION_VAL means absolute offset is given.
3272 if(eFlash2xSectVal == NO_SECTION_VAL)
3273 FlashSectValStartOffset = 0;
3274 else
3275 FlashSectValStartOffset = BcmGetSectionValStartOffset(Adapter,eFlash2xSectVal);
3276
3277 if(FlashSectValStartOffset == STATUS_FAILURE )
3278 {
3279 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"This Section<%d> does not exixt in Flash Map 2.x",eFlash2xSectVal);
3280 return -EINVAL;
3281 }
3282
3283 if(IsSectionExistInVendorInfo(Adapter,eFlash2xSectVal))
3284 return vendorextnWriteSection(Adapter, (PUCHAR)pBuffer, eFlash2xSectVal, uiOffset, uiNumBytes, bVerify);
3285
3286 //calculating the absolute offset from FLASH;
3287 uiOffset = uiOffset + FlashSectValStartOffset;
3288
3289 rdmalt(Adapter, 0x0f000C80, &uiTemp, sizeof(uiTemp));
3290 value = 0;
3291 wrmalt(Adapter, 0x0f000C80,&value, sizeof(value));
3292
3293 Status = BeceemFlashBulkWrite(Adapter, pBuffer,uiOffset,uiNumBytes,bVerify);
3294
3295 wrmalt(Adapter, 0x0f000C80, &uiTemp, sizeof(uiTemp));
3296 if(Status)
3297 {
3298 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "Flash Write failed with Status :%d", Status);
3299 return Status ;
3300 }
3301
3302 return Status;
3303
3304}
3305
f8942e07
SH
3306/**
3307* BcmGetActiveDSD : Set the Active DSD in Adapter Structure which has to be dumped in DDR
3308* @Adapter :-Drivers private Data Structure
3309*
3310* Return Value:-
25985edc 3311* Return STATUS_SUCESS if get success in setting the right DSD else negaive error code
f8942e07
SH
3312*
3313**/
9dd47ee7 3314static INT BcmGetActiveDSD(PMINI_ADAPTER Adapter)
f8942e07
SH
3315{
3316 FLASH2X_SECTION_VAL uiHighestPriDSD = 0 ;
3317
3318 uiHighestPriDSD = getHighestPriDSD(Adapter);
3319 Adapter->eActiveDSD = uiHighestPriDSD;
3320
3321 if(DSD0 == uiHighestPriDSD)
3322 Adapter->ulFlashCalStart = Adapter->psFlash2xCSInfo->OffsetFromZeroForDSDStart;
3323 if(DSD1 == uiHighestPriDSD)
3324 Adapter->ulFlashCalStart = Adapter->psFlash2xCSInfo->OffsetFromZeroForDSD1Start;
3325 if(DSD2 == uiHighestPriDSD)
3326 Adapter->ulFlashCalStart = Adapter->psFlash2xCSInfo->OffsetFromZeroForDSD2Start;
3327 if(Adapter->eActiveDSD)
3328 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "Active DSD :%d", Adapter->eActiveDSD);
3329 if(Adapter->eActiveDSD == 0)
3330 {
3331 //if No DSD gets Active, Make Active the DSD with WR permission
3332 if(IsSectionWritable(Adapter,DSD2))
3333 {
3334 Adapter->eActiveDSD = DSD2;
3335 Adapter->ulFlashCalStart = Adapter->psFlash2xCSInfo->OffsetFromZeroForDSD2Start;
3336 }
3337 else if(IsSectionWritable(Adapter,DSD1))
3338 {
3339 Adapter->eActiveDSD = DSD1;
3340 Adapter->ulFlashCalStart = Adapter->psFlash2xCSInfo->OffsetFromZeroForDSD1Start;
3341 }
3342 else if(IsSectionWritable(Adapter,DSD0))
3343 {
3344 Adapter->eActiveDSD = DSD0;
3345 Adapter->ulFlashCalStart = Adapter->psFlash2xCSInfo->OffsetFromZeroForDSDStart;
3346 }
3347 }
3348
3349 return STATUS_SUCCESS;
3350}
3351
f8942e07
SH
3352
3353/**
3354* BcmGetActiveISO :- Set the Active ISO in Adapter Data Structue
3355* @Adapter : Driver private Data Structure
3356*
3357* Return Value:-
3358* Sucsess:- STATUS_SUCESS
3359* Failure- : negative erro code
3360*
3361**/
3362
9dd47ee7 3363static INT BcmGetActiveISO(PMINI_ADAPTER Adapter)
f8942e07
SH
3364{
3365
3366 INT HighestPriISO = 0 ;
3367 HighestPriISO = getHighestPriISO(Adapter);
3368
3369 Adapter->eActiveISO = HighestPriISO ;
3370 if(Adapter->eActiveISO == ISO_IMAGE2)
3371 Adapter->uiActiveISOOffset = (Adapter->psFlash2xCSInfo->OffsetISOImage2Part1Start);
3372 else if(Adapter->eActiveISO == ISO_IMAGE1)
3373 Adapter->uiActiveISOOffset = (Adapter->psFlash2xCSInfo->OffsetISOImage1Part1Start);
3374
3375 if(Adapter->eActiveISO)
3376 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"Active ISO :%x", Adapter->eActiveISO);
3377
3378 return STATUS_SUCCESS;
3379}
3380
3381/**
3382* IsOffsetWritable :- it will tell the access permission of the sector having passed offset
3383* @Adapter : Drivers Private Data Structure
3384* @uiOffset : Offset provided in the Flash
3385*
3386* Return Value:-
25985edc 3387* Success:-TRUE , offset is writable
f8942e07
SH
3388* Failure:-FALSE, offset is RO
3389*
3390**/
3391B_UINT8 IsOffsetWritable(PMINI_ADAPTER Adapter, UINT uiOffset)
3392{
3393 UINT uiSectorNum = 0;
3394 UINT uiWordOfSectorPermission =0;
3395 UINT uiBitofSectorePermission = 0;
3396 B_UINT32 permissionBits = 0;
3397 uiSectorNum = uiOffset/Adapter->uiSectorSize;
3398
3399 //calculating the word having this Sector Access permission from SectorAccessBitMap Array
3400 uiWordOfSectorPermission = Adapter->psFlash2xCSInfo->SectorAccessBitMap[uiSectorNum /16];
3401
3402 //calculating the bit index inside the word for this sector
3403 uiBitofSectorePermission = 2*(15 - uiSectorNum %16);
3404
3405 //Setting Access permission
3406 permissionBits = uiWordOfSectorPermission & (0x3 << uiBitofSectorePermission) ;
3407 permissionBits = (permissionBits >> uiBitofSectorePermission) & 0x3;
3408 if(permissionBits == SECTOR_READWRITE_PERMISSION)
3409 return TRUE;
3410 else
3411 return FALSE;
3412}
3413
44a17eff 3414static INT BcmDumpFlash2xSectionBitMap(PFLASH2X_BITMAP psFlash2xBitMap)
f8942e07
SH
3415{
3416 PMINI_ADAPTER Adapter = GET_BCM_ADAPTER(gblpnetdev);
3417 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "***************Flash 2.x Section Bitmap***************");
3418 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"ISO_IMAGE1 :0X%x", psFlash2xBitMap->ISO_IMAGE1);
3419 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"ISO_IMAGE2 :0X%x", psFlash2xBitMap->ISO_IMAGE2);
3420 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"DSD0 :0X%x", psFlash2xBitMap->DSD0);
3421 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"DSD1 :0X%x", psFlash2xBitMap->DSD1);
3422 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"DSD2 :0X%x", psFlash2xBitMap->DSD2);
3423 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"VSA0 :0X%x", psFlash2xBitMap->VSA0);
3424 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"VSA1 :0X%x", psFlash2xBitMap->VSA1);
3425 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"VSA2 :0X%x", psFlash2xBitMap->VSA2);
3426 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"SCSI :0X%x", psFlash2xBitMap->SCSI);
3427 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"CONTROL_SECTION :0X%x", psFlash2xBitMap->CONTROL_SECTION);
3428
3429 return STATUS_SUCCESS;
3430}
3431
3432/**
3433* BcmGetFlash2xSectionalBitMap :- It will provide the bit map of all the section present in Flash
3434* 8bit has been assigned to every section.
3435 bit[0] :Section present or not
3436 bit[1] :section is valid or not
3437 bit[2] : Secton is read only or has write permission too.
3438 bit[3] : Active Section -
3439 bit[7...4] = Reserved .
3440
3441 @Adapter:-Driver private Data Structure
3442*
3443* Return value:-
25985edc 3444* Success:- STATUS_SUCESS
f8942e07
SH
3445* Failure:- negative error code
3446**/
3447
3448INT BcmGetFlash2xSectionalBitMap(PMINI_ADAPTER Adapter, PFLASH2X_BITMAP psFlash2xBitMap)
3449{
3450
3451
3452 PFLASH2X_CS_INFO psFlash2xCSInfo = Adapter->psFlash2xCSInfo;
3453 FLASH2X_SECTION_VAL uiHighestPriDSD = 0 ;
3454 FLASH2X_SECTION_VAL uiHighestPriISO= 0 ;
3455 BOOLEAN SetActiveDSDDone = FALSE ;
3456 BOOLEAN SetActiveISODone = FALSE ;
3457
3458 //For 1.x map all the section except DSD0 will be shown as not present
3459 //This part will be used by calibration tool to detect the number of DSD present in Flash.
3460 if(IsFlash2x(Adapter) == FALSE)
3461 {
3462 psFlash2xBitMap->ISO_IMAGE2 = 0;
3463 psFlash2xBitMap->ISO_IMAGE1 = 0;
3464 psFlash2xBitMap->DSD0 = FLASH2X_SECTION_VALID | FLASH2X_SECTION_ACT | FLASH2X_SECTION_PRESENT; //0xF; //0000(Reseved)1(Active)0(RW)1(valid)1(present)
3465 psFlash2xBitMap->DSD1 = 0 ;
3466 psFlash2xBitMap->DSD2 = 0 ;
3467 psFlash2xBitMap->VSA0 = 0 ;
3468 psFlash2xBitMap->VSA1 = 0 ;
3469 psFlash2xBitMap->VSA2 = 0 ;
3470 psFlash2xBitMap->CONTROL_SECTION = 0 ;
3471 psFlash2xBitMap->SCSI= 0 ;
3472 psFlash2xBitMap->Reserved0 = 0 ;
3473 psFlash2xBitMap->Reserved1 = 0 ;
3474 psFlash2xBitMap->Reserved2 = 0 ;
3475 return STATUS_SUCCESS ;
3476
3477 }
3478
3479 uiHighestPriDSD = getHighestPriDSD(Adapter);
3480 uiHighestPriISO = getHighestPriISO(Adapter);
3481
3482 ///
3483 // IS0 IMAGE 2
3484 ///
3485 if((psFlash2xCSInfo->OffsetISOImage2Part1Start) != UNINIT_PTR_IN_CS)
3486 {
3487 //Setting the 0th Bit representing the Section is present or not.
3488 psFlash2xBitMap->ISO_IMAGE2= psFlash2xBitMap->ISO_IMAGE2 | FLASH2X_SECTION_PRESENT;
3489
3490
3491 if(ReadISOSignature(Adapter,ISO_IMAGE2)== ISO_IMAGE_MAGIC_NUMBER)
3492 psFlash2xBitMap->ISO_IMAGE2 |= FLASH2X_SECTION_VALID;
3493
3494
3495 //Calculation for extrating the Access permission
3496 if(IsSectionWritable(Adapter, ISO_IMAGE2) == FALSE)
3497 psFlash2xBitMap->ISO_IMAGE2 |= FLASH2X_SECTION_RO;
3498
3499 if(SetActiveISODone == FALSE && uiHighestPriISO == ISO_IMAGE2)
3500 {
3501 psFlash2xBitMap->ISO_IMAGE2 |= FLASH2X_SECTION_ACT ;
3502 SetActiveISODone = TRUE;
3503 }
3504
3505 }
3506
3507 ///
3508 // IS0 IMAGE 1
3509 ///
3510 if((psFlash2xCSInfo->OffsetISOImage1Part1Start) != UNINIT_PTR_IN_CS)
3511 {
3512 //Setting the 0th Bit representing the Section is present or not.
3513 psFlash2xBitMap->ISO_IMAGE1 = psFlash2xBitMap->ISO_IMAGE1 | FLASH2X_SECTION_PRESENT;
3514
3515 if(ReadISOSignature(Adapter,ISO_IMAGE1) == ISO_IMAGE_MAGIC_NUMBER)
3516 psFlash2xBitMap->ISO_IMAGE1 |= FLASH2X_SECTION_VALID;
3517
3518 // Calculation for extrating the Access permission
3519 if(IsSectionWritable(Adapter, ISO_IMAGE1) == FALSE)
3520 psFlash2xBitMap->ISO_IMAGE1 |= FLASH2X_SECTION_RO;
3521
3522 if(SetActiveISODone == FALSE && uiHighestPriISO == ISO_IMAGE1)
3523 {
3524 psFlash2xBitMap->ISO_IMAGE1 |= FLASH2X_SECTION_ACT ;
3525 SetActiveISODone = TRUE;
3526 }
3527 }
3528
3529
3530
3531 ///
3532 // DSD2
3533 ///
3534 if((psFlash2xCSInfo->OffsetFromZeroForDSD2Start) != UNINIT_PTR_IN_CS)
3535 {
3536 //Setting the 0th Bit representing the Section is present or not.
3537 psFlash2xBitMap->DSD2= psFlash2xBitMap->DSD2 | FLASH2X_SECTION_PRESENT;
3538
3539 if(ReadDSDSignature(Adapter,DSD2)== DSD_IMAGE_MAGIC_NUMBER)
3540 psFlash2xBitMap->DSD2 |= FLASH2X_SECTION_VALID;
3541
3542 //Calculation for extrating the Access permission
3543 if(IsSectionWritable(Adapter, DSD2) == FALSE)
3544 {
3545 psFlash2xBitMap->DSD2 |= FLASH2X_SECTION_RO;
3546
3547 }
3548 else
3549 {
3550 //Means section is writable
3551 if((SetActiveDSDDone == FALSE) && (uiHighestPriDSD == DSD2))
3552 {
3553 psFlash2xBitMap->DSD2 |= FLASH2X_SECTION_ACT ;
3554 SetActiveDSDDone =TRUE ;
3555 }
3556 }
3557 }
3558
3559 ///
3560 // DSD 1
3561 ///
3562 if((psFlash2xCSInfo->OffsetFromZeroForDSD1Start) != UNINIT_PTR_IN_CS)
3563 {
3564 //Setting the 0th Bit representing the Section is present or not.
3565 psFlash2xBitMap->DSD1= psFlash2xBitMap->DSD1 | FLASH2X_SECTION_PRESENT;
3566
3567
3568 if(ReadDSDSignature(Adapter,DSD1)== DSD_IMAGE_MAGIC_NUMBER)
3569 psFlash2xBitMap->DSD1 |= FLASH2X_SECTION_VALID;
3570
3571 //Calculation for extrating the Access permission
3572 if(IsSectionWritable(Adapter, DSD1) == FALSE)
3573 {
3574 psFlash2xBitMap->DSD1 |= FLASH2X_SECTION_RO;
3575 }
3576 else
3577 {
3578 //Means section is writable
3579 if((SetActiveDSDDone == FALSE) && (uiHighestPriDSD == DSD1))
3580 {
3581 psFlash2xBitMap->DSD1 |= FLASH2X_SECTION_ACT ;
3582 SetActiveDSDDone =TRUE ;
3583 }
3584 }
3585
3586 }
3587
3588 ///
3589 //For DSD 0
3590 //
3591 if((psFlash2xCSInfo->OffsetFromZeroForDSDStart) != UNINIT_PTR_IN_CS)
3592 {
3593 //Setting the 0th Bit representing the Section is present or not.
3594 psFlash2xBitMap->DSD0 = psFlash2xBitMap->DSD0 | FLASH2X_SECTION_PRESENT;
3595
3596 if(ReadDSDSignature(Adapter,DSD0) == DSD_IMAGE_MAGIC_NUMBER)
3597 psFlash2xBitMap->DSD0 |= FLASH2X_SECTION_VALID;
3598
3599 //Setting Access permission
3600 if(IsSectionWritable(Adapter, DSD0) == FALSE)
3601 {
3602 psFlash2xBitMap->DSD0 |= FLASH2X_SECTION_RO;
3603 }
3604 else
3605 {
3606 //Means section is writable
3607 if((SetActiveDSDDone == FALSE) &&(uiHighestPriDSD == DSD0))
3608 {
3609 psFlash2xBitMap->DSD0 |= FLASH2X_SECTION_ACT ;
3610 SetActiveDSDDone =TRUE ;
3611 }
3612 }
3613 }
3614
3615 ///
3616 // VSA 0
3617 ///
3618 if((psFlash2xCSInfo->OffsetFromZeroForVSAStart) != UNINIT_PTR_IN_CS)
3619 {
3620 //Setting the 0th Bit representing the Section is present or not.
3621 psFlash2xBitMap->VSA0= psFlash2xBitMap->VSA0 | FLASH2X_SECTION_PRESENT;
3622
3623 //Setting the Access Bit. Map is not defined hece setting it always valid
3624 psFlash2xBitMap->VSA0 |= FLASH2X_SECTION_VALID;
3625
3626 //Calculation for extrating the Access permission
3627 if(IsSectionWritable(Adapter, VSA0) == FALSE)
3628 psFlash2xBitMap->VSA0 |= FLASH2X_SECTION_RO;
3629
3630 //By Default section is Active
3631 psFlash2xBitMap->VSA0 |= FLASH2X_SECTION_ACT ;
3632
3633 }
3634
3635
3636 ///
3637 // VSA 1
3638 ///
3639
3640 if((psFlash2xCSInfo->OffsetFromZeroForVSA1Start) != UNINIT_PTR_IN_CS)
3641 {
3642 //Setting the 0th Bit representing the Section is present or not.
3643 psFlash2xBitMap->VSA1= psFlash2xBitMap->VSA1 | FLASH2X_SECTION_PRESENT;
3644
3645 //Setting the Access Bit. Map is not defined hece setting it always valid
3646 psFlash2xBitMap->VSA1|= FLASH2X_SECTION_VALID;
3647
3648 //Checking For Access permission
3649 if(IsSectionWritable(Adapter, VSA1) == FALSE)
3650 psFlash2xBitMap->VSA1 |= FLASH2X_SECTION_RO;
3651
3652 //By Default section is Active
3653 psFlash2xBitMap->VSA1 |= FLASH2X_SECTION_ACT ;
3654
3655 }
3656
3657
3658 ///
3659 // VSA 2
3660 ///
3661
3662 if((psFlash2xCSInfo->OffsetFromZeroForVSA2Start) != UNINIT_PTR_IN_CS)
3663 {
3664 //Setting the 0th Bit representing the Section is present or not.
3665 psFlash2xBitMap->VSA2= psFlash2xBitMap->VSA2 | FLASH2X_SECTION_PRESENT;
3666
3667
3668 //Setting the Access Bit. Map is not defined hece setting it always valid
3669 psFlash2xBitMap->VSA2 |= FLASH2X_SECTION_VALID;
3670
3671 //Checking For Access permission
3672 if(IsSectionWritable(Adapter, VSA2) == FALSE)
3673 psFlash2xBitMap->VSA2 |= FLASH2X_SECTION_RO;
3674
3675 //By Default section is Active
3676 psFlash2xBitMap->VSA2 |= FLASH2X_SECTION_ACT ;
3677 }
3678
3679 ///
3680 // SCSI Section
3681 ///
3682 if((psFlash2xCSInfo->OffsetFromZeroForScsiFirmware) != UNINIT_PTR_IN_CS)
3683 {
3684 //Setting the 0th Bit representing the Section is present or not.
3685 psFlash2xBitMap->SCSI= psFlash2xBitMap->SCSI | FLASH2X_SECTION_PRESENT;
3686
3687
3688 //Setting the Access Bit. Map is not defined hece setting it always valid
3689 psFlash2xBitMap->SCSI|= FLASH2X_SECTION_VALID;
3690
3691 //Checking For Access permission
3692 if(IsSectionWritable(Adapter, SCSI) == FALSE)
3693 psFlash2xBitMap->SCSI |= FLASH2X_SECTION_RO;
3694
3695 //By Default section is Active
3696 psFlash2xBitMap->SCSI |= FLASH2X_SECTION_ACT ;
3697
3698 }
3699
3700
3701 ///
3702 // Control Section
3703 ///
3704 if((psFlash2xCSInfo->OffsetFromZeroForControlSectionStart) != UNINIT_PTR_IN_CS)
3705 {
3706 //Setting the 0th Bit representing the Section is present or not.
3707 psFlash2xBitMap->CONTROL_SECTION = psFlash2xBitMap->CONTROL_SECTION | (FLASH2X_SECTION_PRESENT);
3708
3709
3710 //Setting the Access Bit. Map is not defined hece setting it always valid
3711 psFlash2xBitMap->CONTROL_SECTION |= FLASH2X_SECTION_VALID;
3712
3713 //Checking For Access permission
3714 if(IsSectionWritable(Adapter, CONTROL_SECTION) == FALSE)
3715 psFlash2xBitMap->CONTROL_SECTION |= FLASH2X_SECTION_RO;
3716
3717 //By Default section is Active
3718 psFlash2xBitMap->CONTROL_SECTION |= FLASH2X_SECTION_ACT ;
3719
3720 }
3721
3722 ///
3723 // For Reserved Sections
3724 ///
3725 psFlash2xBitMap->Reserved0 = 0;
3726 psFlash2xBitMap->Reserved0 = 0;
3727 psFlash2xBitMap->Reserved0 = 0;
3728
3729 BcmDumpFlash2xSectionBitMap(psFlash2xBitMap);
3730
3731 return STATUS_SUCCESS ;
3732
3733}
3734/**
3735BcmSetActiveSection :- Set Active section is used to make priority field highest over other
3736 section of same type.
3737
3738@Adapater :- Bcm Driver Private Data Structure
3739@eFlash2xSectionVal :- Flash section val whose priority has to be made highest.
3740
3741Return Value:- Make the priorit highest else return erorr code
3742
3743**/
3744INT BcmSetActiveSection(PMINI_ADAPTER Adapter, FLASH2X_SECTION_VAL eFlash2xSectVal)
3745{
44a17eff 3746 unsigned int SectImagePriority = 0;
f8942e07
SH
3747 INT Status =STATUS_SUCCESS;
3748
3749 //DSD_HEADER sDSD = {0};
3750 //ISO_HEADER sISO = {0};
3751 INT HighestPriDSD = 0 ;
3752 INT HighestPriISO = 0;
3753
3754
3755
3756 Status = IsSectionWritable(Adapter,eFlash2xSectVal) ;
3757 if(Status != TRUE )
3758 {
3759 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Provided Section <%d> is not writable",eFlash2xSectVal);
3760 return STATUS_FAILURE;
3761 }
3762
3763 Adapter->bHeaderChangeAllowed = TRUE ;
3764 switch(eFlash2xSectVal)
3765 {
3766 case ISO_IMAGE1 :
3767 case ISO_IMAGE2 :
3768 if(ReadISOSignature(Adapter,eFlash2xSectVal)== ISO_IMAGE_MAGIC_NUMBER )
3769 {
3770 HighestPriISO = getHighestPriISO(Adapter);
3771
3772 if(HighestPriISO == eFlash2xSectVal )
3773 {
3774 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"Given ISO<%x> already has highest priority",eFlash2xSectVal );
3775 Status = STATUS_SUCCESS ;
3776 break;
3777 }
3778
3779 SectImagePriority = ReadISOPriority(Adapter, HighestPriISO) + 1;
3780
3781 if((SectImagePriority <= 0) && IsSectionWritable(Adapter,HighestPriISO))
3782 {
3783 // This is a SPECIAL Case which will only happen if the current highest priority ISO has priority value = 0x7FFFFFFF.
3784 // We will write 1 to the current Highest priority ISO And then shall increase the priority of the requested ISO
3785 // by user
25985edc 3786 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "SectImagePriority wraparound happened, eFlash2xSectVal: 0x%x\n",eFlash2xSectVal);
f8942e07
SH
3787 SectImagePriority = htonl(0x1);
3788 Status = BcmFlash2xBulkWrite(Adapter,
3789 &SectImagePriority,
3790 HighestPriISO,
3791 0 + FIELD_OFFSET_IN_HEADER(PISO_HEADER, ISOImagePriority),
3792 SIGNATURE_SIZE,
3793 TRUE);
3794
3795 if(Status)
3796 {
3797 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Priority has not been written properly");
3798 Status = STATUS_FAILURE;
3799 break ;
3800 }
3801
3802 HighestPriISO = getHighestPriISO(Adapter);
3803
3804 if(HighestPriISO == eFlash2xSectVal )
3805 {
3806 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"Given ISO<%x> already has highest priority",eFlash2xSectVal );
3807 Status = STATUS_SUCCESS ;
3808 break;
3809 }
3810
3811 SectImagePriority = 2;
3812 }
3813
3814
3815 SectImagePriority = htonl(SectImagePriority);
3816
3817 Status = BcmFlash2xBulkWrite(Adapter,
3818 &SectImagePriority,
3819 eFlash2xSectVal,
3820 0 + FIELD_OFFSET_IN_HEADER(PISO_HEADER, ISOImagePriority),
3821 SIGNATURE_SIZE,
3822 TRUE);
3823 if(Status)
3824 {
3825 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Priority has not been written properly");
3826 break ;
3827 }
3828 }
3829 else
3830 {
3831 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "Signature is currupted. Hence can't increase the priority");
3832 Status = STATUS_FAILURE ;
3833 break;
3834 }
3835 break;
3836 case DSD0 :
3837 case DSD1 :
3838 case DSD2 :
3839 if(ReadDSDSignature(Adapter,eFlash2xSectVal)== DSD_IMAGE_MAGIC_NUMBER)
3840 {
3841 HighestPriDSD = getHighestPriDSD(Adapter);
3842
3843 if((HighestPriDSD == eFlash2xSectVal))
3844 {
3845 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"Given DSD<%x> already has highest priority", eFlash2xSectVal);
3846 Status = STATUS_SUCCESS ;
3847 break;
3848 }
3849
3850 SectImagePriority = ReadDSDPriority(Adapter, HighestPriDSD) + 1 ;
3851 if(SectImagePriority <= 0)
3852 {
3853 // This is a SPECIAL Case which will only happen if the current highest priority DSD has priority value = 0x7FFFFFFF.
3854 // We will write 1 to the current Highest priority DSD And then shall increase the priority of the requested DSD
3855 // by user
25985edc 3856 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, NVM_RW, DBG_LVL_ALL, "SectImagePriority wraparound happened, eFlash2xSectVal: 0x%x\n",eFlash2xSectVal);
f8942e07
SH
3857 SectImagePriority = htonl(0x1);
3858
3859 Status = BcmFlash2xBulkWrite(Adapter,
3860 &SectImagePriority,
3861 HighestPriDSD,
3862 Adapter->psFlash2xCSInfo->OffsetFromDSDStartForDSDHeader + FIELD_OFFSET_IN_HEADER(PDSD_HEADER, DSDImagePriority),
3863 SIGNATURE_SIZE,
3864 TRUE);
3865
3866 if(Status)
3867 {
3868 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "Priority has not been written properly");
3869 break ;
3870 }
3871
3872 HighestPriDSD = getHighestPriDSD(Adapter);
3873
3874 if((HighestPriDSD == eFlash2xSectVal))
3875 {
3876 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"Made the DSD: %x highest by reducing priority of other\n", eFlash2xSectVal);
3877 Status = STATUS_SUCCESS ;
3878 break;
3879 }
3880
3881 SectImagePriority = htonl(0x2);
3882 Status = BcmFlash2xBulkWrite(Adapter,
3883 &SectImagePriority,
3884 HighestPriDSD,
3885 Adapter->psFlash2xCSInfo->OffsetFromDSDStartForDSDHeader + FIELD_OFFSET_IN_HEADER(PDSD_HEADER, DSDImagePriority),
3886 SIGNATURE_SIZE,
3887 TRUE);
3888
3889 if(Status)
3890 {
3891 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "Priority has not been written properly");
3892 break ;
3893 }
3894
3895 HighestPriDSD = getHighestPriDSD(Adapter);
3896
3897 if((HighestPriDSD == eFlash2xSectVal))
3898 {
3899 Status = STATUS_SUCCESS ;
3900 break;
3901 }
3902 SectImagePriority = 3 ;
3903
3904 }
3905 SectImagePriority = htonl(SectImagePriority);
3906 Status = BcmFlash2xBulkWrite(Adapter,
3907 &SectImagePriority,
3908 eFlash2xSectVal,
3909 Adapter->psFlash2xCSInfo->OffsetFromDSDStartForDSDHeader + FIELD_OFFSET_IN_HEADER(PDSD_HEADER, DSDImagePriority),
3910 SIGNATURE_SIZE ,
3911 TRUE);
3912 if(Status)
3913 {
3914 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Priority has not been written properly");
3915 Status = STATUS_FAILURE ;
3916 break ;
3917 }
3918 }
3919 else
3920 {
3921 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "Signature is currupted. Hence can't increase the priority");
3922 Status = STATUS_FAILURE ;
3923 break;
3924 }
3925 break;
3926 case VSA0 :
3927 case VSA1 :
3928 case VSA2 :
3929 //Has to be decided
3930 break ;
3931 default :
3932 Status = STATUS_FAILURE ;
3933 break;
3934
3935 }
3936
3937 Adapter->bHeaderChangeAllowed = FALSE ;
3938 return Status;
3939
3940}
3941
3942/**
3943BcmCopyISO - Used only for copying the ISO section
3944@Adapater :- Bcm Driver Private Data Structure
3945@sCopySectStrut :- Section copy structure
3946
3947Return value:- SUCCESS if copies successfully else negative error code
3948
3949**/
3950INT BcmCopyISO(PMINI_ADAPTER Adapter, FLASH2X_COPY_SECTION sCopySectStrut)
3951{
3952
3953 PCHAR Buff = NULL;
3954 FLASH2X_SECTION_VAL eISOReadPart = 0,eISOWritePart = 0;
3955 UINT uiReadOffsetWithinPart = 0, uiWriteOffsetWithinPart = 0;
3956 UINT uiTotalDataToCopy = 0;
3957 BOOLEAN IsThisHeaderSector = FALSE ;
3958 UINT sigOffset = 0;
3959 UINT ISOLength = 0;
3960 UINT Status = STATUS_SUCCESS;
3961 UINT SigBuff[MAX_RW_SIZE];
3962 UINT i = 0;
3963
3964 if(ReadISOSignature(Adapter,sCopySectStrut.SrcSection) != ISO_IMAGE_MAGIC_NUMBER)
3965 {
3966 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "error as Source ISO Section does not have valid signature");
3967 return STATUS_FAILURE;
3968 }
3969
3970 Status = BcmFlash2xBulkRead(Adapter,
3971 &ISOLength,
3972 sCopySectStrut.SrcSection,
3973 0 + FIELD_OFFSET_IN_HEADER(PISO_HEADER,ISOImageSize),
3974 4);
3975
3976 if(Status)
3977 {
3978 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "Read failed while copying ISO\n");
3979 return Status;
3980 }
3981
3982 ISOLength = htonl(ISOLength);
3983
3984 if(ISOLength % Adapter->uiSectorSize)
3985 {
3986 ISOLength = Adapter->uiSectorSize*(1 + ISOLength/Adapter->uiSectorSize);
3987 }
3988
3989 sigOffset = FIELD_OFFSET_IN_HEADER(PISO_HEADER, ISOImageMagicNumber);
3990
3991 Buff = kzalloc(Adapter->uiSectorSize, GFP_KERNEL);
3992
3993 if(Buff == NULL)
3994 {
3995 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Memory allocation failed for section size");
3996 return -ENOMEM;
3997 }
3998
3999 if(sCopySectStrut.SrcSection ==ISO_IMAGE1 && sCopySectStrut.DstSection ==ISO_IMAGE2)
4000 {
4001 eISOReadPart = ISO_IMAGE1 ;
4002 eISOWritePart = ISO_IMAGE2 ;
4003 uiReadOffsetWithinPart = 0;
4004 uiWriteOffsetWithinPart = 0 ;
4005
4006 uiTotalDataToCopy =(Adapter->psFlash2xCSInfo->OffsetISOImage1Part1End) -
4007 (Adapter->psFlash2xCSInfo->OffsetISOImage1Part1Start)+
4008 (Adapter->psFlash2xCSInfo->OffsetISOImage1Part2End) -
4009 (Adapter->psFlash2xCSInfo->OffsetISOImage1Part2Start)+
4010 (Adapter->psFlash2xCSInfo->OffsetISOImage1Part3End) -
4011 (Adapter->psFlash2xCSInfo->OffsetISOImage1Part3Start);
4012
4013 if(uiTotalDataToCopy < ISOLength)
4014 {
4015 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"error as Source ISO Section does not have valid signature");
e5969d55
JL
4016 Status = STATUS_FAILURE;
4017 goto out;
f8942e07
SH
4018 }
4019
4020 uiTotalDataToCopy =(Adapter->psFlash2xCSInfo->OffsetISOImage2Part1End) -
4021 (Adapter->psFlash2xCSInfo->OffsetISOImage2Part1Start)+
4022 (Adapter->psFlash2xCSInfo->OffsetISOImage2Part2End) -
4023 (Adapter->psFlash2xCSInfo->OffsetISOImage2Part2Start)+
4024 (Adapter->psFlash2xCSInfo->OffsetISOImage2Part3End) -
4025 (Adapter->psFlash2xCSInfo->OffsetISOImage2Part3Start);
4026
4027 if(uiTotalDataToCopy < ISOLength)
4028 {
4029 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"error as Dest ISO Section does not have enough section size");
e5969d55
JL
4030 Status = STATUS_FAILURE;
4031 goto out;
f8942e07
SH
4032 }
4033
4034 uiTotalDataToCopy = ISOLength;
4035
4036 CorruptISOSig(Adapter,ISO_IMAGE2);
4037
4038 while(uiTotalDataToCopy)
4039 {
4040 if(uiTotalDataToCopy == Adapter->uiSectorSize)
4041 {
4042 //Setting for write of first sector. First sector is assumed to be written in last
4043 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"Writing the signature sector");
4044 eISOReadPart = ISO_IMAGE1 ;
4045 uiReadOffsetWithinPart = 0;
4046 eISOWritePart = ISO_IMAGE2;
4047 uiWriteOffsetWithinPart = 0 ;
4048 IsThisHeaderSector = TRUE ;
4049
4050 }
4051 else
4052 {
4053 uiReadOffsetWithinPart = uiReadOffsetWithinPart + Adapter->uiSectorSize ;
4054 uiWriteOffsetWithinPart = uiWriteOffsetWithinPart + Adapter->uiSectorSize ;
4055
4056 if((eISOReadPart == ISO_IMAGE1) && (uiReadOffsetWithinPart == (Adapter->psFlash2xCSInfo->OffsetISOImage1Part1End - Adapter->psFlash2xCSInfo->OffsetISOImage1Part1Start) ))
4057 {
4058 eISOReadPart = ISO_IMAGE1_PART2 ;
4059 uiReadOffsetWithinPart = 0;
4060 }
4061 if((eISOReadPart == ISO_IMAGE1_PART2) && (uiReadOffsetWithinPart == (Adapter->psFlash2xCSInfo->OffsetISOImage1Part2End - Adapter->psFlash2xCSInfo->OffsetISOImage1Part2Start)))
4062 {
4063 eISOReadPart = ISO_IMAGE1_PART3 ;
4064 uiReadOffsetWithinPart = 0;
4065 }
4066 if((eISOWritePart == ISO_IMAGE2) && (uiWriteOffsetWithinPart == (Adapter->psFlash2xCSInfo->OffsetISOImage2Part1End - Adapter->psFlash2xCSInfo->OffsetISOImage2Part1Start)))
4067 {
4068 eISOWritePart = ISO_IMAGE2_PART2 ;
4069 uiWriteOffsetWithinPart = 0;
4070 }
4071 if((eISOWritePart == ISO_IMAGE2_PART2) && (uiWriteOffsetWithinPart == (Adapter->psFlash2xCSInfo->OffsetISOImage2Part2End - Adapter->psFlash2xCSInfo->OffsetISOImage2Part2Start)))
4072 {
4073 eISOWritePart = ISO_IMAGE2_PART3 ;
4074 uiWriteOffsetWithinPart = 0;
4075 }
4076 }
4077
4078 Status = BcmFlash2xBulkRead(Adapter,
4079 (PUINT)Buff,
4080 eISOReadPart,
4081 uiReadOffsetWithinPart,
4082 Adapter->uiSectorSize
4083 );
4084
4085 if(Status)
4086 {
4087 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "Read failed while copying ISO: Part: %x, OffsetWithinPart: %x\n", eISOReadPart, uiReadOffsetWithinPart);
4088 break;
4089 }
4090
4091 if(IsThisHeaderSector == TRUE)
4092 {
4093 //If this is header sector write 0xFFFFFFFF at the sig time and in last write sig
4094 memcpy(SigBuff, Buff + sigOffset, MAX_RW_SIZE);
4095
4096 for(i = 0; i < MAX_RW_SIZE;i++)
4097 *(Buff + sigOffset + i) = 0xFF;
4098 }
4099 Adapter->bHeaderChangeAllowed = TRUE ;
4100
4101 Status = BcmFlash2xBulkWrite(Adapter,
4102 (PUINT)Buff,
4103 eISOWritePart,
4104 uiWriteOffsetWithinPart,
4105 Adapter->uiSectorSize,
4106 TRUE);
4107 if(Status)
4108 {
4109 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "Write failed while copying ISO: Part: %x, OffsetWithinPart: %x\n", eISOWritePart, uiWriteOffsetWithinPart);
4110 break;
4111 }
4112
4113 Adapter->bHeaderChangeAllowed = FALSE;
4114
4115 if(IsThisHeaderSector == TRUE)
4116 {
4117 WriteToFlashWithoutSectorErase(Adapter,
4118 SigBuff,
4119 eISOWritePart,
4120 sigOffset,
4121 MAX_RW_SIZE);
4122 IsThisHeaderSector = FALSE ;
4123 }
25985edc 4124 //subtracting the written Data
f8942e07
SH
4125 uiTotalDataToCopy = uiTotalDataToCopy - Adapter->uiSectorSize ;
4126 }
4127
4128
4129 }
4130
4131 if(sCopySectStrut.SrcSection ==ISO_IMAGE2 && sCopySectStrut.DstSection ==ISO_IMAGE1)
4132 {
4133 eISOReadPart = ISO_IMAGE2 ;
4134 eISOWritePart = ISO_IMAGE1 ;
4135 uiReadOffsetWithinPart = 0;
4136 uiWriteOffsetWithinPart = 0 ;
4137
4138 uiTotalDataToCopy =(Adapter->psFlash2xCSInfo->OffsetISOImage2Part1End) -
4139 (Adapter->psFlash2xCSInfo->OffsetISOImage2Part1Start)+
4140 (Adapter->psFlash2xCSInfo->OffsetISOImage2Part2End) -
4141 (Adapter->psFlash2xCSInfo->OffsetISOImage2Part2Start)+
4142 (Adapter->psFlash2xCSInfo->OffsetISOImage2Part3End) -
4143 (Adapter->psFlash2xCSInfo->OffsetISOImage2Part3Start);
4144
4145 if(uiTotalDataToCopy < ISOLength)
4146 {
4147 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"error as Source ISO Section does not have valid signature");
e5969d55
JL
4148 Status = STATUS_FAILURE;
4149 goto out;
f8942e07
SH
4150 }
4151
4152 uiTotalDataToCopy =(Adapter->psFlash2xCSInfo->OffsetISOImage1Part1End) -
4153 (Adapter->psFlash2xCSInfo->OffsetISOImage1Part1Start)+
4154 (Adapter->psFlash2xCSInfo->OffsetISOImage1Part2End) -
4155 (Adapter->psFlash2xCSInfo->OffsetISOImage1Part2Start)+
4156 (Adapter->psFlash2xCSInfo->OffsetISOImage1Part3End) -
4157 (Adapter->psFlash2xCSInfo->OffsetISOImage1Part3Start);
4158
4159 if(uiTotalDataToCopy < ISOLength)
4160 {
4161 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"error as Dest ISO Section does not have enough section size");
e5969d55
JL
4162 Status = STATUS_FAILURE;
4163 goto out;
f8942e07
SH
4164 }
4165
4166 uiTotalDataToCopy = ISOLength;
4167
4168 CorruptISOSig(Adapter,ISO_IMAGE1);
4169
4170 while(uiTotalDataToCopy)
4171 {
4172 if(uiTotalDataToCopy == Adapter->uiSectorSize)
4173 {
4174 //Setting for write of first sector. First sector is assumed to be written in last
4175 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"Writing the signature sector");
4176 eISOReadPart = ISO_IMAGE2 ;
4177 uiReadOffsetWithinPart = 0;
4178 eISOWritePart = ISO_IMAGE1;
4179 uiWriteOffsetWithinPart = 0 ;
4180 IsThisHeaderSector = TRUE;
4181
4182 }
4183 else
4184 {
4185 uiReadOffsetWithinPart = uiReadOffsetWithinPart + Adapter->uiSectorSize ;
4186 uiWriteOffsetWithinPart = uiWriteOffsetWithinPart + Adapter->uiSectorSize ;
4187
4188 if((eISOReadPart == ISO_IMAGE2) && (uiReadOffsetWithinPart == (Adapter->psFlash2xCSInfo->OffsetISOImage2Part1End - Adapter->psFlash2xCSInfo->OffsetISOImage2Part1Start) ))
4189 {
4190 eISOReadPart = ISO_IMAGE2_PART2 ;
4191 uiReadOffsetWithinPart = 0;
4192 }
4193 if((eISOReadPart == ISO_IMAGE2_PART2) && (uiReadOffsetWithinPart == (Adapter->psFlash2xCSInfo->OffsetISOImage2Part2End - Adapter->psFlash2xCSInfo->OffsetISOImage2Part2Start)))
4194 {
4195 eISOReadPart = ISO_IMAGE2_PART3 ;
4196 uiReadOffsetWithinPart = 0;
4197 }
4198 if((eISOWritePart == ISO_IMAGE1) && (uiWriteOffsetWithinPart == (Adapter->psFlash2xCSInfo->OffsetISOImage1Part1End - Adapter->psFlash2xCSInfo->OffsetISOImage1Part1Start)))
4199 {
4200 eISOWritePart = ISO_IMAGE1_PART2 ;
4201 uiWriteOffsetWithinPart = 0;
4202 }
4203 if((eISOWritePart == ISO_IMAGE1_PART2) && (uiWriteOffsetWithinPart == (Adapter->psFlash2xCSInfo->OffsetISOImage1Part2End - Adapter->psFlash2xCSInfo->OffsetISOImage1Part2Start)))
4204 {
4205 eISOWritePart = ISO_IMAGE1_PART3 ;
4206 uiWriteOffsetWithinPart = 0;
4207 }
4208 }
4209
4210 Status = BcmFlash2xBulkRead(Adapter,
4211 (PUINT)Buff,
4212 eISOReadPart,
4213 uiReadOffsetWithinPart,
4214 Adapter->uiSectorSize
4215 );
4216 if(Status)
4217 {
4218 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "Read failed while copying ISO: Part: %x, OffsetWithinPart: %x\n", eISOReadPart, uiReadOffsetWithinPart);
4219 break;
4220 }
4221
4222 if(IsThisHeaderSector == TRUE)
4223 {
4224 //If this is header sector write 0xFFFFFFFF at the sig time and in last write sig
4225 memcpy(SigBuff, Buff + sigOffset, MAX_RW_SIZE);
4226
4227 for(i = 0; i < MAX_RW_SIZE;i++)
4228 *(Buff + sigOffset + i) = 0xFF;
4229
4230 }
4231 Adapter->bHeaderChangeAllowed = TRUE ;
4232 Status = BcmFlash2xBulkWrite(Adapter,
4233 (PUINT)Buff,
4234 eISOWritePart,
4235 uiWriteOffsetWithinPart,
4236 Adapter->uiSectorSize,
4237 TRUE);
4238
4239 if(Status)
4240 {
4241 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "Write failed while copying ISO: Part: %x, OffsetWithinPart: %x\n", eISOWritePart, uiWriteOffsetWithinPart);
4242 break;
4243 }
4244
4245 Adapter->bHeaderChangeAllowed = FALSE ;
4246
4247 if(IsThisHeaderSector == TRUE)
4248 {
4249 WriteToFlashWithoutSectorErase(Adapter,
4250 SigBuff,
4251 eISOWritePart,
4252 sigOffset,
4253 MAX_RW_SIZE);
4254 IsThisHeaderSector = FALSE ;
4255 }
4256
25985edc 4257 //subtracting the written Data
f8942e07
SH
4258 uiTotalDataToCopy = uiTotalDataToCopy - Adapter->uiSectorSize ;
4259 }
4260
4261
4262 }
4263
e5969d55 4264out:
082e889b 4265 kfree(Buff);
f8942e07
SH
4266
4267 return Status;
4268}
4269/**
4270BcmFlash2xCorruptSig : this API is used to corrupt the written sig in Bcm Header present in flash section.
4271 It will corrupt the sig, if Section is writable, by making first bytes as zero.
4272@Adapater :- Bcm Driver Private Data Structure
4273@eFlash2xSectionVal :- Flash section val which has header
4274
4275Return Value :-
25985edc 4276 Success :- If Section is present and writable, corrupt the sig and return STATUS_SUCCESS
f8942e07
SH
4277 Failure :-Return negative error code
4278
4279
4280**/
4281INT BcmFlash2xCorruptSig(PMINI_ADAPTER Adapter, FLASH2X_SECTION_VAL eFlash2xSectionVal)
4282{
4283
4284 INT Status = STATUS_SUCCESS ;
4285 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "Section Value :%x \n", eFlash2xSectionVal);
4286
4287 if((eFlash2xSectionVal == DSD0) || (eFlash2xSectionVal == DSD1) || (eFlash2xSectionVal == DSD2))
4288 {
4289 Status = CorruptDSDSig(Adapter, eFlash2xSectionVal);
4290 }
4291 else if(eFlash2xSectionVal == ISO_IMAGE1 || eFlash2xSectionVal == ISO_IMAGE2)
4292 {
4293 Status = CorruptISOSig(Adapter, eFlash2xSectionVal);
4294 }
4295 else
4296 {
4297 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"Given Section <%d>does not have Header",eFlash2xSectionVal);
4298 return STATUS_SUCCESS;
4299 }
4300 return Status;
4301}
4302/**
4303BcmFlash2xWriteSig :-this API is used to Write the sig if requested Section has
4304 header and Write Permission.
4305@Adapater :- Bcm Driver Private Data Structure
4306@eFlashSectionVal :- Flash section val which has header
4307
4308Return Value :-
25985edc 4309 Success :- If Section is present and writable write the sig and return STATUS_SUCCESS
f8942e07
SH
4310 Failure :-Return negative error code
4311
4312**/
4313INT BcmFlash2xWriteSig(PMINI_ADAPTER Adapter, FLASH2X_SECTION_VAL eFlashSectionVal)
4314{
4315
4316 UINT uiSignature = 0 ;
4317 UINT uiOffset = 0;
4318 //DSD_HEADER dsdHeader = {0};
4319
4320 if(Adapter->bSigCorrupted == FALSE)
4321 {
4322 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"Signature is not corrupted by driver, hence not restoring\n");
4323 return STATUS_SUCCESS;
4324 }
4325 if(Adapter->bAllDSDWriteAllow == FALSE)
4326 {
4327 if(IsSectionWritable(Adapter,eFlashSectionVal) == FALSE)
4328 {
4329 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Section is not Writable...Hence can't Write signature");
4330 return SECTOR_IS_NOT_WRITABLE;
4331 }
4332 }
4333 if((eFlashSectionVal == DSD0) ||(eFlashSectionVal == DSD1) || (eFlashSectionVal == DSD2))
4334 {
4335 uiSignature = htonl(DSD_IMAGE_MAGIC_NUMBER) ;
4336 uiOffset = Adapter->psFlash2xCSInfo->OffsetFromDSDStartForDSDHeader ;
4337
4338 uiOffset += FIELD_OFFSET_IN_HEADER(PDSD_HEADER,DSDImageMagicNumber);
4339
4340 if((ReadDSDSignature(Adapter,eFlashSectionVal) & 0xFF000000) != CORRUPTED_PATTERN)
4341 {
4342 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Corrupted Pattern is not there. Hence won't write sig");
4343 return STATUS_FAILURE;
4344 }
4345
4346 }
4347 else if((eFlashSectionVal == ISO_IMAGE1) || (eFlashSectionVal == ISO_IMAGE2))
4348 {
4349 uiSignature = htonl(ISO_IMAGE_MAGIC_NUMBER);
4350 //uiOffset = 0;
4351 uiOffset = FIELD_OFFSET_IN_HEADER(PISO_HEADER,ISOImageMagicNumber);
4352 if((ReadISOSignature(Adapter,eFlashSectionVal) & 0xFF000000) != CORRUPTED_PATTERN)
4353 {
4354 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Currupted Pattern is not there. Hence won't write sig");
4355 return STATUS_FAILURE;
4356 }
4357 }
4358 else
4359 {
4360 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"GIVEN SECTION< %d > IS NOT VALID FOR SIG WRITE...", eFlashSectionVal);
4361 return STATUS_FAILURE;
4362 }
4363
4364 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"Restoring the signature");
4365
4366
4367 Adapter->bHeaderChangeAllowed = TRUE;
4368 Adapter->bSigCorrupted = FALSE;
4369 BcmFlash2xBulkWrite(Adapter, &uiSignature,eFlashSectionVal,uiOffset,SIGNATURE_SIZE,TRUE);
4370 Adapter->bHeaderChangeAllowed = FALSE;
4371
4372
4373
4374 return STATUS_SUCCESS;
4375}
4376/**
4377validateFlash2xReadWrite :- This API is used to validate the user request for Read/Write.
4378 if requested Bytes goes beyond the Requested section, it reports error.
4379@Adapater :- Bcm Driver Private Data Structure
4380@psFlash2xReadWrite :-Flash2x Read/write structure pointer
4381
4382Return values:-Return TRUE is request is valid else FALSE.
4383
4384
4385**/
4386INT validateFlash2xReadWrite(PMINI_ADAPTER Adapter, PFLASH2X_READWRITE psFlash2xReadWrite)
4387{
4388 UINT uiNumOfBytes = 0 ;
4389 UINT uiSectStartOffset = 0 ;
4390 UINT uiSectEndOffset = 0;
4391 uiNumOfBytes = psFlash2xReadWrite->numOfBytes;
4392
4393 if(IsSectionExistInFlash(Adapter,psFlash2xReadWrite->Section) != TRUE)
4394 {
4395 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Section<%x> does not exixt in Flash",psFlash2xReadWrite->Section);
4396 return FALSE;
4397 }
4398 uiSectStartOffset = BcmGetSectionValStartOffset(Adapter,psFlash2xReadWrite->Section);
4399 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "Start offset :%x ,section :%d\n",uiSectStartOffset,psFlash2xReadWrite->Section);
4400 if((psFlash2xReadWrite->Section == ISO_IMAGE1) ||(psFlash2xReadWrite->Section == ISO_IMAGE2))
4401 {
4402 if(psFlash2xReadWrite->Section == ISO_IMAGE1)
4403 {
4404 uiSectEndOffset = BcmGetSectionValEndOffset(Adapter,ISO_IMAGE1) -
4405 BcmGetSectionValStartOffset(Adapter,ISO_IMAGE1)+
4406 BcmGetSectionValEndOffset(Adapter,ISO_IMAGE1_PART2) -
4407 BcmGetSectionValStartOffset(Adapter,ISO_IMAGE1_PART2)+
4408 BcmGetSectionValEndOffset(Adapter,ISO_IMAGE1_PART3) -
4409 BcmGetSectionValStartOffset(Adapter,ISO_IMAGE1_PART3);
4410 }
4411 else if(psFlash2xReadWrite->Section == ISO_IMAGE2)
4412 {
4413 uiSectEndOffset = BcmGetSectionValEndOffset(Adapter,ISO_IMAGE2) -
4414 BcmGetSectionValStartOffset(Adapter,ISO_IMAGE2)+
4415 BcmGetSectionValEndOffset(Adapter,ISO_IMAGE2_PART2) -
4416 BcmGetSectionValStartOffset(Adapter,ISO_IMAGE2_PART2)+
4417 BcmGetSectionValEndOffset(Adapter,ISO_IMAGE2_PART3) -
4418 BcmGetSectionValStartOffset(Adapter,ISO_IMAGE2_PART3);
4419
4420 }
4421
4422 //since this uiSectEndoffset is the size of iso Image. hence for calculating the vitual endoffset
4423 //it should be added in startoffset. so that check done in last of this function can be valued.
4424 uiSectEndOffset = uiSectStartOffset + uiSectEndOffset ;
4425
4426 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"Total size of the ISO Image :%x",uiSectEndOffset);
4427 }
4428 else
4429 uiSectEndOffset = BcmGetSectionValEndOffset(Adapter,psFlash2xReadWrite->Section);
4430 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "End offset :%x \n",uiSectEndOffset);
4431
4432 //Checking the boundary condition
4433 if((uiSectStartOffset + psFlash2xReadWrite->offset + uiNumOfBytes) <= uiSectEndOffset)
4434 return TRUE;
4435 else
4436 {
4437 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Invalid Request....");
4438 return FALSE;
4439 }
4440
4441}
4442
4443/**
4444IsFlash2x :- check for Flash 2.x
4445@Adapater :- Bcm Driver Private Data Structure
4446
4447Return value:-
4448 return TRUE if flah2.x of hgher version else return false.
4449**/
4450
4451INT IsFlash2x(PMINI_ADAPTER Adapter)
4452{
4453 if(Adapter->uiFlashLayoutMajorVersion >= FLASH_2X_MAJOR_NUMBER)
4454 return TRUE ;
4455 else
4456 return FALSE;
4457}
4458/**
4459GetFlashBaseAddr :- Calculate the Flash Base address
4460@Adapater :- Bcm Driver Private Data Structure
4461
4462Return Value:-
4463 Success :- Base Address of the Flash
4464**/
4465
9dd47ee7 4466static INT GetFlashBaseAddr(PMINI_ADAPTER Adapter)
f8942e07
SH
4467{
4468
4469 UINT uiBaseAddr = 0;
4470
4471 if(Adapter->bDDRInitDone)
4472 {
4473 /*
4474 For All Valid Flash Versions... except 1.1, take the value from FlashBaseAddr
4475 In case of Raw Read... use the default value
4476 */
4477 if(Adapter->uiFlashLayoutMajorVersion && (Adapter->bFlashRawRead == FALSE) &&
4478 !((Adapter->uiFlashLayoutMajorVersion == 1) && (Adapter->uiFlashLayoutMinorVersion == 1))
4479 )
4480 uiBaseAddr = Adapter->uiFlashBaseAdd ;
4481 else
4482 uiBaseAddr = FLASH_CONTIGIOUS_START_ADDR_AFTER_INIT;
4483 }
4484 else
4485 {
4486 /*
4487 For All Valid Flash Versions... except 1.1, take the value from FlashBaseAddr
4488 In case of Raw Read... use the default value
4489 */
4490 if(Adapter->uiFlashLayoutMajorVersion && (Adapter->bFlashRawRead == FALSE) &&
4491 !((Adapter->uiFlashLayoutMajorVersion == 1) && (Adapter->uiFlashLayoutMinorVersion == 1))
4492 )
4493 uiBaseAddr = Adapter->uiFlashBaseAdd | FLASH_CONTIGIOUS_START_ADDR_BEFORE_INIT;
4494 else
4495 uiBaseAddr = FLASH_CONTIGIOUS_START_ADDR_BEFORE_INIT;
4496 }
4497
4498 return uiBaseAddr ;
4499}
4500/**
4501BcmCopySection :- This API is used to copy the One section in another. Both section should
4502 be contiuous and of same size. Hence this Will not be applicabe to copy ISO.
4503
4504@Adapater :- Bcm Driver Private Data Structure
4505@SrcSection :- Source section From where data has to be copied
4506@DstSection :- Destination section to which data has to be copied
4507@offset :- Offset from/to where data has to be copied from one section to another.
4508@numOfBytes :- number of byes that has to be copyed from one section to another at given offset.
4509 in case of numofBytes equal zero complete section will be copied.
4510
4511Return Values-
25985edc 4512 Success : Return STATUS_SUCCESS
f8942e07
SH
4513 Faillure :- return negative error code
4514
4515**/
4516
4517INT BcmCopySection(PMINI_ADAPTER Adapter,
4518 FLASH2X_SECTION_VAL SrcSection,
4519 FLASH2X_SECTION_VAL DstSection,
4520 UINT offset,
4521 UINT numOfBytes)
4522{
4523 UINT BuffSize = 0 ;
4524 UINT BytesToBeCopied = 0;
4525 PUCHAR pBuff = NULL ;
4526 INT Status = STATUS_SUCCESS ;
4527 if(SrcSection == DstSection)
4528 {
4529 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Source and Destination should be different ...try again");
4530 return -EINVAL;
4531 }
4532 if((SrcSection != DSD0) && (SrcSection != DSD1) && (SrcSection != DSD2))
4533 {
4534 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Source should be DSD subsection");
4535 return -EINVAL;
4536 }
4537 if((DstSection != DSD0) && (DstSection != DSD1) && (DstSection != DSD2))
4538 {
4539 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Destination should be DSD subsection");
4540 return -EINVAL;
4541 }
4542
f8942e07
SH
4543 //if offset zero means have to copy complete secton
4544
4545 if(numOfBytes == 0)
4546 {
4547 numOfBytes = BcmGetSectionValEndOffset(Adapter,SrcSection)
4548 - BcmGetSectionValStartOffset(Adapter,SrcSection);
4549
4550 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL," Section Size :0x%x",numOfBytes);
4551 }
4552
4553 if((offset + numOfBytes) > BcmGetSectionValEndOffset(Adapter,SrcSection)
4554 - BcmGetSectionValStartOffset(Adapter,SrcSection))
4555 {
4556 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0," Input parameters going beyond the section offS: %x numB: %x of Source Section\n",
4557 offset, numOfBytes);
4558 return -EINVAL;
4559 }
4560
4561 if((offset + numOfBytes) > BcmGetSectionValEndOffset(Adapter,DstSection)
4562 - BcmGetSectionValStartOffset(Adapter,DstSection))
4563 {
4564 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0," Input parameters going beyond the section offS: %x numB: %x of Destination Section\n",
4565 offset, numOfBytes);
4566 return -EINVAL;
4567 }
4568
4569
4570 if(numOfBytes > Adapter->uiSectorSize )
4571 BuffSize = Adapter->uiSectorSize;
4572 else
4573 BuffSize = numOfBytes ;
4574
4575 pBuff = (PCHAR)kzalloc(BuffSize, GFP_KERNEL);
4576 if(pBuff == NULL)
4577 {
4578 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Memory allocation failed.. ");
4579 return -ENOMEM;
4580 }
4581
4582
4583 BytesToBeCopied = Adapter->uiSectorSize ;
4584 if(offset % Adapter->uiSectorSize)
4585 BytesToBeCopied = Adapter->uiSectorSize - (offset % Adapter->uiSectorSize);
4586 if(BytesToBeCopied > numOfBytes)
4587 BytesToBeCopied = numOfBytes ;
4588
4589
4590
4591 Adapter->bHeaderChangeAllowed = TRUE;
4592
4593 do
4594 {
4595 Status = BcmFlash2xBulkRead(Adapter, (PUINT)pBuff, SrcSection , offset,BytesToBeCopied);
4596 if(Status)
4597 {
4598 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "Read failed at offset :%d for NOB :%d", SrcSection,BytesToBeCopied);
4599 break;
4600 }
4601 Status = BcmFlash2xBulkWrite(Adapter,(PUINT)pBuff,DstSection,offset,BytesToBeCopied,FALSE);
4602 if(Status)
4603 {
4604 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "Write failed at offset :%d for NOB :%d", DstSection,BytesToBeCopied);
4605 break;
4606 }
4607 offset = offset + BytesToBeCopied;
4608 numOfBytes = numOfBytes - BytesToBeCopied ;
4609 if(numOfBytes)
4610 {
4611 if(numOfBytes > Adapter->uiSectorSize )
4612 BytesToBeCopied = Adapter->uiSectorSize;
4613 else
4614 BytesToBeCopied = numOfBytes;
4615 }
4616 }while(numOfBytes > 0) ;
082e889b 4617 kfree(pBuff);
f8942e07
SH
4618 Adapter->bHeaderChangeAllowed = FALSE ;
4619 return Status;
4620}
4621
4622/**
4623SaveHeaderIfPresent :- This API is use to Protect the Header in case of Header Sector write
4624@Adapater :- Bcm Driver Private Data Structure
4625@pBuff :- Data buffer that has to be written in sector having the header map.
4626@uiOffset :- Flash offset that has to be written.
4627
4628Return value :-
25985edc 4629 Success :- On success return STATUS_SUCCESS
f8942e07
SH
4630 Faillure :- Return negative error code
4631
4632**/
4633
4634INT SaveHeaderIfPresent(PMINI_ADAPTER Adapter, PUCHAR pBuff, UINT uiOffset)
4635{
4636 UINT offsetToProtect = 0,HeaderSizeToProtect =0;
4637 BOOLEAN bHasHeader = FALSE ;
4638 PUCHAR pTempBuff =NULL;
4639 UINT uiSectAlignAddr = 0;
4640 UINT sig = 0;
4641
25985edc 4642 //making the offset sector aligned
f8942e07
SH
4643 uiSectAlignAddr = uiOffset & ~(Adapter->uiSectorSize - 1);
4644
4645
4646 if((uiSectAlignAddr == BcmGetSectionValEndOffset(Adapter,DSD2)- Adapter->uiSectorSize)||
4647 (uiSectAlignAddr == BcmGetSectionValEndOffset(Adapter,DSD1)- Adapter->uiSectorSize)||
4648 (uiSectAlignAddr == BcmGetSectionValEndOffset(Adapter,DSD0)- Adapter->uiSectorSize))
4649 {
4650
25985edc 4651 //offset from the sector boundary having the header map
f8942e07
SH
4652 offsetToProtect = Adapter->psFlash2xCSInfo->OffsetFromDSDStartForDSDHeader % Adapter->uiSectorSize;
4653 HeaderSizeToProtect = sizeof(DSD_HEADER);
4654 bHasHeader = TRUE ;
4655 }
4656
4657 if(uiSectAlignAddr == BcmGetSectionValStartOffset(Adapter,ISO_IMAGE1) ||
4658 uiSectAlignAddr == BcmGetSectionValStartOffset(Adapter,ISO_IMAGE2))
4659 {
4660 offsetToProtect = 0;
4661 HeaderSizeToProtect = sizeof(ISO_HEADER);
4662 bHasHeader = TRUE;
4663 }
4664 //If Header is present overwrite passed buffer with this
4665 if(bHasHeader && (Adapter->bHeaderChangeAllowed == FALSE))
4666 {
4667 pTempBuff = (PUCHAR)kzalloc(HeaderSizeToProtect, GFP_KERNEL);
4668 if(pTempBuff == NULL)
4669 {
4670 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Memory allocation failed ");
4671 return -ENOMEM;
4672 }
4673 //Read header
4674 BeceemFlashBulkRead(Adapter,(PUINT)pTempBuff,(uiSectAlignAddr + offsetToProtect),HeaderSizeToProtect);
4675 BCM_DEBUG_PRINT_BUFFER(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,pTempBuff ,HeaderSizeToProtect);
4676 //Replace Buffer content with Header
4677 memcpy(pBuff +offsetToProtect,pTempBuff,HeaderSizeToProtect);
4678
082e889b 4679 kfree(pTempBuff);
f8942e07
SH
4680 }
4681 if(bHasHeader && Adapter->bSigCorrupted)
4682 {
4683 sig = *((PUINT)(pBuff + offsetToProtect + FIELD_OFFSET_IN_HEADER(PDSD_HEADER,DSDImageMagicNumber)));
4684 sig = ntohl(sig);
4685 if((sig & 0xFF000000) != CORRUPTED_PATTERN)
4686 {
4687 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"Desired pattern is not at sig offset. Hence won't restore");
4688 Adapter->bSigCorrupted = FALSE;
4689 return STATUS_SUCCESS;
4690 }
4691 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL," Corrupted sig is :%X", sig);
4692 *((PUINT)(pBuff + offsetToProtect + FIELD_OFFSET_IN_HEADER(PDSD_HEADER,DSDImageMagicNumber)))= htonl(DSD_IMAGE_MAGIC_NUMBER);
4693 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"Restoring the signature in Header Write only");
4694 Adapter->bSigCorrupted = FALSE;
4695 }
4696
4697 return STATUS_SUCCESS ;
4698}
f8942e07 4699
f8942e07
SH
4700/**
4701BcmDoChipSelect : This will selcet the appropriate chip for writing.
4702@Adapater :- Bcm Driver Private Data Structure
4703
4704OutPut:-
25985edc 4705 Select the Appropriate chip and retrn status Success
f8942e07 4706**/
9dd47ee7 4707static INT BcmDoChipSelect(PMINI_ADAPTER Adapter, UINT offset)
f8942e07
SH
4708{
4709 UINT FlashConfig = 0;
4710 INT ChipNum = 0;
4711 UINT GPIOConfig = 0;
4712 UINT PartNum = 0;
4713
4714 ChipNum = offset / FLASH_PART_SIZE ;
4715
4716 //
4717 // Chip Select mapping to enable flash0.
4718 // To select flash 0, we have to OR with (0<<12).
4719 // ORing 0 will have no impact so not doing that part.
4720 // In future if Chip select value changes from 0 to non zero,
4721 // That needs be taken care with backward comaptibility. No worries for now.
4722 //
4723
4724 /*
4725 SelectedChip Variable is the selection that the host is 100% Sure the same as what the register will hold. This can be ONLY ensured
4726 if the Chip doesn't goes to low power mode while the flash operation is in progress (NVMRdmWrmLock is taken)
4727 Before every new Flash Write operation, we reset the variable. This is to ensure that after any wake-up from
4728 power down modes (Idle mode/shutdown mode), the values in the register will be different.
4729 */
4730
4731 if(Adapter->SelectedChip == ChipNum)
4732 return STATUS_SUCCESS;
4733
4734 //BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL, "Selected Chip :%x", ChipNum);
4735 Adapter->SelectedChip = ChipNum ;
4736
4737 //bit[13..12] will select the appropriate chip
4738 rdmalt(Adapter,FLASH_CONFIG_REG, &FlashConfig, 4);
4739 rdmalt(Adapter,FLASH_GPIO_CONFIG_REG, &GPIOConfig, 4);
4740
4741 {
4742 switch(ChipNum)
4743 {
4744 case 0:
4745 PartNum = 0;
4746 break;
4747 case 1:
4748 PartNum = 3;
4749 GPIOConfig |= (0x4 << CHIP_SELECT_BIT12);
4750 break;
4751 case 2:
4752 PartNum = 1;
4753 GPIOConfig |= (0x1 << CHIP_SELECT_BIT12);
4754 break;
4755 case 3:
4756 PartNum = 2;
4757 GPIOConfig |= (0x2 << CHIP_SELECT_BIT12);
4758 break;
4759 }
4760 }
4761 /* In case the bits already written in the FLASH_CONFIG_REG is same as what the user desired,
4762 nothing to do... can return immediately.
4763 ASSUMPTION: FLASH_GPIO_CONFIG_REG will be in sync with FLASH_CONFIG_REG.
4764 Even if the chip goes to low power mode, it should wake with values in each register in sync with each other.
4765 These values are not written by host other than during CHIP_SELECT.
4766 */
4767 if(PartNum == ((FlashConfig >> CHIP_SELECT_BIT12) & 0x3))
4768 return STATUS_SUCCESS;
4769
4770 //clearing the bit[13..12]
4771 FlashConfig &= 0xFFFFCFFF;
4772 FlashConfig = (FlashConfig | (PartNum<<CHIP_SELECT_BIT12)); //00
4773
4774 wrmalt(Adapter,FLASH_GPIO_CONFIG_REG, &GPIOConfig, 4);
4775 udelay(100);
4776
4777 wrmalt(Adapter,FLASH_CONFIG_REG, &FlashConfig, 4);
4778 udelay(100);
4779
4780 return STATUS_SUCCESS;
4781
4782}
4783INT ReadDSDSignature(PMINI_ADAPTER Adapter, FLASH2X_SECTION_VAL dsd)
4784{
4785 UINT uiDSDsig = 0;
4786 //UINT sigoffsetInMap = 0;
4787 //DSD_HEADER dsdHeader = {0};
4788
4789
4790 //sigoffsetInMap =(PUCHAR)&(dsdHeader.DSDImageMagicNumber) -(PUCHAR)&dsdHeader;
4791
4792 if(dsd != DSD0 && dsd != DSD1 && dsd != DSD2)
4793 {
4794 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"passed section value is not for DSDs");
4795 return STATUS_FAILURE;
4796 }
4797 BcmFlash2xBulkRead(Adapter,
4798 &uiDSDsig,
4799 dsd,
4800 Adapter->psFlash2xCSInfo->OffsetFromDSDStartForDSDHeader + FIELD_OFFSET_IN_HEADER(PDSD_HEADER,DSDImageMagicNumber),
4801 SIGNATURE_SIZE);
4802
4803 uiDSDsig = ntohl(uiDSDsig);
4804 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"DSD SIG :%x", uiDSDsig);
4805
4806 return uiDSDsig ;
4807}
4808INT ReadDSDPriority(PMINI_ADAPTER Adapter, FLASH2X_SECTION_VAL dsd)
4809{
4810 //UINT priOffsetInMap = 0 ;
44a17eff 4811 unsigned int uiDSDPri = STATUS_FAILURE;
f8942e07
SH
4812 //DSD_HEADER dsdHeader = {0};
4813 //priOffsetInMap = (PUCHAR)&(dsdHeader.DSDImagePriority) -(PUCHAR)&dsdHeader;
4814 if(IsSectionWritable(Adapter,dsd))
4815 {
4816 if(ReadDSDSignature(Adapter,dsd)== DSD_IMAGE_MAGIC_NUMBER)
4817 {
4818 BcmFlash2xBulkRead(Adapter,
4819 &uiDSDPri,
4820 dsd,
4821 Adapter->psFlash2xCSInfo->OffsetFromDSDStartForDSDHeader +FIELD_OFFSET_IN_HEADER(PDSD_HEADER, DSDImagePriority),
4822 4);
4823
4824 uiDSDPri = ntohl(uiDSDPri);
4825 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"DSD<%x> Priority :%x", dsd, uiDSDPri);
4826
4827 }
4828 }
4829 return uiDSDPri;
4830}
4831FLASH2X_SECTION_VAL getHighestPriDSD(PMINI_ADAPTER Adapter)
4832{
4833 INT DSDHighestPri = STATUS_FAILURE;
4834 INT DsdPri= 0 ;
4835 FLASH2X_SECTION_VAL HighestPriDSD = 0 ;
4836
4837 if(IsSectionWritable(Adapter,DSD2))
4838 {
4839 DSDHighestPri = ReadDSDPriority(Adapter,DSD2);
4840 HighestPriDSD = DSD2 ;
4841 }
4842 if(IsSectionWritable(Adapter,DSD1))
4843 {
4844 DsdPri = ReadDSDPriority(Adapter,DSD1);
4845 if(DSDHighestPri < DsdPri)
4846 {
4847 DSDHighestPri = DsdPri ;
4848 HighestPriDSD = DSD1;
4849 }
4850 }
4851 if(IsSectionWritable(Adapter,DSD0))
4852 {
4853 DsdPri = ReadDSDPriority(Adapter,DSD0);
4854 if(DSDHighestPri < DsdPri)
4855 {
4856 DSDHighestPri = DsdPri ;
4857 HighestPriDSD = DSD0;
4858 }
4859 }
4860 if(HighestPriDSD)
4861 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"Highest DSD :%x , and its Pri :%x", HighestPriDSD, DSDHighestPri);
4862 return HighestPriDSD ;
4863}
4864
4865INT ReadISOSignature(PMINI_ADAPTER Adapter, FLASH2X_SECTION_VAL iso)
4866{
4867 UINT uiISOsig = 0;
4868 //UINT sigoffsetInMap = 0;
4869 //ISO_HEADER ISOHeader = {0};
4870
4871
4872 //sigoffsetInMap =(PUCHAR)&(ISOHeader.ISOImageMagicNumber) -(PUCHAR)&ISOHeader;
4873
4874 if(iso != ISO_IMAGE1 && iso != ISO_IMAGE2)
4875 {
4876 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"passed section value is not for ISOs");
4877 return STATUS_FAILURE;
4878 }
4879 BcmFlash2xBulkRead(Adapter,
4880 &uiISOsig,
4881 iso,
4882 0 + FIELD_OFFSET_IN_HEADER(PISO_HEADER,ISOImageMagicNumber),
4883 SIGNATURE_SIZE);
4884
4885 uiISOsig = ntohl(uiISOsig);
4886 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"ISO SIG :%x", uiISOsig);
4887
4888 return uiISOsig ;
4889}
4890INT ReadISOPriority(PMINI_ADAPTER Adapter, FLASH2X_SECTION_VAL iso)
4891{
4892
44a17eff 4893 unsigned int ISOPri = STATUS_FAILURE;
f8942e07
SH
4894 if(IsSectionWritable(Adapter,iso))
4895 {
4896 if(ReadISOSignature(Adapter,iso)== ISO_IMAGE_MAGIC_NUMBER)
4897 {
4898 BcmFlash2xBulkRead(Adapter,
4899 &ISOPri,
4900 iso,
4901 0 + FIELD_OFFSET_IN_HEADER(PISO_HEADER, ISOImagePriority),
4902 4);
4903
4904 ISOPri = ntohl(ISOPri);
4905 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"ISO<%x> Priority :%x", iso, ISOPri);
4906
4907 }
4908 }
4909 return ISOPri;
4910}
4911FLASH2X_SECTION_VAL getHighestPriISO(PMINI_ADAPTER Adapter)
4912{
4913 INT ISOHighestPri = STATUS_FAILURE;
4914 INT ISOPri= 0 ;
4915 FLASH2X_SECTION_VAL HighestPriISO = NO_SECTION_VAL ;
4916
4917 if(IsSectionWritable(Adapter,ISO_IMAGE2))
4918 {
4919 ISOHighestPri = ReadISOPriority(Adapter,ISO_IMAGE2);
4920 HighestPriISO = ISO_IMAGE2 ;
4921 }
4922 if(IsSectionWritable(Adapter,ISO_IMAGE1))
4923 {
4924 ISOPri = ReadISOPriority(Adapter,ISO_IMAGE1);
4925 if(ISOHighestPri < ISOPri)
4926 {
4927 ISOHighestPri = ISOPri ;
4928 HighestPriISO = ISO_IMAGE1;
4929 }
4930 }
4931 if(HighestPriISO)
4932 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"Highest ISO :%x and its Pri :%x",HighestPriISO,ISOHighestPri);
4933 return HighestPriISO ;
4934}
4935INT WriteToFlashWithoutSectorErase(PMINI_ADAPTER Adapter,
4936 PUINT pBuff,
4937 FLASH2X_SECTION_VAL eFlash2xSectionVal,
4938 UINT uiOffset,
4939 UINT uiNumBytes
4940 )
4941{
4942#if !defined(BCM_SHM_INTERFACE) || defined(FLASH_DIRECT_ACCESS)
4943 UINT uiTemp = 0, value = 0 ;
4944 UINT i = 0;
4945 UINT uiPartOffset = 0;
4946#endif
4947 UINT uiStartOffset = 0;
4948 //Adding section start address
4949 INT Status = STATUS_SUCCESS;
4950 PUCHAR pcBuff = (PUCHAR)pBuff;
4951
4952 if(uiNumBytes % Adapter->ulFlashWriteSize)
4953 {
4954 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Writing without Sector Erase for non-FlashWriteSize number of bytes 0x%x\n", uiNumBytes);
4955 return STATUS_FAILURE;
4956 }
4957
4958 uiStartOffset = BcmGetSectionValStartOffset(Adapter,eFlash2xSectionVal);
4959
4960 if(IsSectionExistInVendorInfo(Adapter,eFlash2xSectionVal))
4961 {
4962 return vendorextnWriteSectionWithoutErase(Adapter, pcBuff, eFlash2xSectionVal, uiOffset, uiNumBytes);
4963 }
4964
4965 uiOffset = uiOffset + uiStartOffset;
4966
4967#if defined(BCM_SHM_INTERFACE) && !defined(FLASH_DIRECT_ACCESS)
4968 Status = bcmflash_raw_writenoerase((uiOffset/FLASH_PART_SIZE),(uiOffset % FLASH_PART_SIZE), pcBuff,uiNumBytes);
4969#else
4970 rdmalt(Adapter, 0x0f000C80, &uiTemp, sizeof(uiTemp));
4971 value = 0;
4972 wrmalt(Adapter, 0x0f000C80,&value, sizeof(value));
4973
4974 Adapter->SelectedChip = RESET_CHIP_SELECT;
4975 BcmDoChipSelect(Adapter,uiOffset);
4976 uiPartOffset = (uiOffset & (FLASH_PART_SIZE - 1)) + GetFlashBaseAddr(Adapter);
4977
4978 for(i = 0 ; i< uiNumBytes; i += Adapter->ulFlashWriteSize)
4979 {
4980 if(Adapter->ulFlashWriteSize == BYTE_WRITE_SUPPORT)
4981 Status = flashByteWrite(Adapter,uiPartOffset, pcBuff);
4982 else
4983 Status = flashWrite(Adapter,uiPartOffset, pcBuff);
4984
4985 if(Status != STATUS_SUCCESS)
4986 break;
4987
4988 pcBuff = pcBuff + Adapter->ulFlashWriteSize;
4989 uiPartOffset = uiPartOffset + Adapter->ulFlashWriteSize;
4990 }
4991 wrmalt(Adapter, 0x0f000C80, &uiTemp, sizeof(uiTemp));
4992 Adapter->SelectedChip = RESET_CHIP_SELECT;
4993#endif
4994
4995 return Status;
4996}
4997
f8942e07
SH
4998BOOLEAN IsSectionExistInFlash(PMINI_ADAPTER Adapter, FLASH2X_SECTION_VAL section)
4999{
5000
5001 BOOLEAN SectionPresent = FALSE ;
5002
5003 switch(section)
5004 {
5005
5006 case ISO_IMAGE1 :
5007 if((Adapter->psFlash2xCSInfo->OffsetISOImage1Part1Start != UNINIT_PTR_IN_CS) &&
5008 (IsNonCDLessDevice(Adapter) == FALSE))
5009 SectionPresent = TRUE ;
5010 break;
5011 case ISO_IMAGE2 :
5012 if((Adapter->psFlash2xCSInfo->OffsetISOImage2Part1Start != UNINIT_PTR_IN_CS) &&
5013 (IsNonCDLessDevice(Adapter) == FALSE))
5014 SectionPresent = TRUE ;
5015 break;
5016 case DSD0 :
5017 if(Adapter->psFlash2xCSInfo->OffsetFromZeroForDSDStart != UNINIT_PTR_IN_CS)
5018 SectionPresent = TRUE ;
5019 break;
5020 case DSD1 :
5021 if(Adapter->psFlash2xCSInfo->OffsetFromZeroForDSD1Start != UNINIT_PTR_IN_CS)
5022 SectionPresent = TRUE ;
5023 break;
5024 case DSD2 :
5025 if(Adapter->psFlash2xCSInfo->OffsetFromZeroForDSD2Start != UNINIT_PTR_IN_CS)
5026 SectionPresent = TRUE ;
5027 break;
5028 case VSA0 :
5029 if(Adapter->psFlash2xCSInfo->OffsetFromZeroForVSAStart != UNINIT_PTR_IN_CS)
5030 SectionPresent = TRUE ;
5031 break;
5032 case VSA1 :
5033 if(Adapter->psFlash2xCSInfo->OffsetFromZeroForVSA1Start != UNINIT_PTR_IN_CS)
5034 SectionPresent = TRUE ;
5035 break;
5036 case VSA2 :
5037 if(Adapter->psFlash2xCSInfo->OffsetFromZeroForVSA2Start != UNINIT_PTR_IN_CS)
5038 SectionPresent = TRUE ;
5039 break;
5040 case SCSI :
5041 if(Adapter->psFlash2xCSInfo->OffsetFromZeroForScsiFirmware != UNINIT_PTR_IN_CS)
5042 SectionPresent = TRUE ;
5043 break;
5044 case CONTROL_SECTION :
5045 if(Adapter->psFlash2xCSInfo->OffsetFromZeroForControlSectionStart != UNINIT_PTR_IN_CS)
5046 SectionPresent = TRUE ;
5047 break;
5048 default :
5049 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Section Does not exist in Flash 2.x");
5050 SectionPresent = FALSE;
5051 }
5052 return SectionPresent ;
5053}
5054INT IsSectionWritable(PMINI_ADAPTER Adapter, FLASH2X_SECTION_VAL Section)
5055{
5056 INT offset = STATUS_FAILURE;
5057 INT Status = FALSE;
5058 if(IsSectionExistInFlash(Adapter,Section) == FALSE)
5059 {
5060 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Section <%d> does not exixt", Section);
5061 return FALSE;
5062 }
5063 offset = BcmGetSectionValStartOffset(Adapter,Section);
5064 if(offset == INVALID_OFFSET)
5065 {
5066 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Section<%d> does not exixt", Section);
5067 return FALSE;
5068 }
5069
5070 if(IsSectionExistInVendorInfo(Adapter,Section))
5071 {
5072 return !(Adapter->psFlash2xVendorInfo->VendorSection[Section].AccessFlags & FLASH2X_SECTION_RO);
5073 }
5074
5075 Status = IsOffsetWritable(Adapter,offset);
5076 return Status ;
5077}
5078
9dd47ee7 5079static INT CorruptDSDSig(PMINI_ADAPTER Adapter, FLASH2X_SECTION_VAL eFlash2xSectionVal)
f8942e07
SH
5080{
5081
44a17eff 5082 PUCHAR pBuff = NULL;
f8942e07
SH
5083 UINT sig = 0;
5084 UINT uiOffset = 0;
5085 UINT BlockStatus = 0;
5086 UINT uiSectAlignAddr = 0;
5087
5088 Adapter->bSigCorrupted = FALSE;
5089
5090 if(Adapter->bAllDSDWriteAllow == FALSE)
5091 {
5092 if(IsSectionWritable(Adapter,eFlash2xSectionVal) != TRUE)
5093 {
25985edc 5094 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Section is not Writable...Hence can't Corrupt signature");
f8942e07
SH
5095 return SECTOR_IS_NOT_WRITABLE;
5096 }
5097 }
5098
5099 pBuff = (PUCHAR)kzalloc(MAX_RW_SIZE, GFP_KERNEL);
5100 if(pBuff == NULL)
5101 {
5102 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0, "Can't allocate memorey");
5103 return -ENOMEM ;
5104 }
5105
5106 uiOffset = Adapter->psFlash2xCSInfo->OffsetFromDSDStartForDSDHeader + sizeof(DSD_HEADER);
5107 uiOffset -= MAX_RW_SIZE ;
5108
5109 BcmFlash2xBulkRead(Adapter, (PUINT)pBuff,eFlash2xSectionVal,uiOffset,MAX_RW_SIZE);
5110
5111
5112 sig = *((PUINT)(pBuff +12));
5113 sig =ntohl(sig);
5114 BCM_DEBUG_PRINT_BUFFER(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,pBuff,MAX_RW_SIZE);
5115 //Now corrupting the sig by corrupting 4th last Byte.
5116 *(pBuff + 12) = 0;
5117
5118 if(sig == DSD_IMAGE_MAGIC_NUMBER)
5119 {
5120 Adapter->bSigCorrupted = TRUE;
5121 if(Adapter->ulFlashWriteSize == BYTE_WRITE_SUPPORT)
5122 {
5123 uiSectAlignAddr = uiOffset & ~(Adapter->uiSectorSize -1);
5124 BlockStatus = BcmFlashUnProtectBlock(Adapter,uiSectAlignAddr,Adapter->uiSectorSize);
5125
5126 WriteToFlashWithoutSectorErase(Adapter,(PUINT)(pBuff + 12),eFlash2xSectionVal,
5127 (uiOffset + 12),BYTE_WRITE_SUPPORT);
5128 if(BlockStatus)
5129 {
5130 BcmRestoreBlockProtectStatus(Adapter,BlockStatus);
5131 BlockStatus = 0;
5132 }
5133 }
5134 else
5135 {
5136 WriteToFlashWithoutSectorErase(Adapter,(PUINT)pBuff,eFlash2xSectionVal,
5137 uiOffset ,MAX_RW_SIZE);
5138 }
5139 }
5140 else
5141 {
5142 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"BCM Signature is not present in header");
082e889b 5143 kfree(pBuff);
f8942e07
SH
5144 return STATUS_FAILURE;
5145 }
5146
082e889b 5147 kfree(pBuff);
f8942e07
SH
5148 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"Corrupted the signature");
5149 return STATUS_SUCCESS ;
5150}
5151
9dd47ee7 5152static INT CorruptISOSig(PMINI_ADAPTER Adapter, FLASH2X_SECTION_VAL eFlash2xSectionVal)
f8942e07
SH
5153{
5154
44a17eff 5155 PUCHAR pBuff = NULL;
f8942e07
SH
5156 UINT sig = 0;
5157 UINT uiOffset = 0;
5158
5159 Adapter->bSigCorrupted = FALSE;
5160
5161 if(IsSectionWritable(Adapter,eFlash2xSectionVal) != TRUE)
5162 {
25985edc 5163 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Section is not Writable...Hence can't Corrupt signature");
f8942e07
SH
5164 return SECTOR_IS_NOT_WRITABLE;
5165 }
5166
5167 pBuff = (PUCHAR)kzalloc(MAX_RW_SIZE, GFP_KERNEL);
5168 if(pBuff == NULL)
5169 {
5170 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"Can't allocate memorey");
5171 return -ENOMEM ;
5172 }
5173
5174 uiOffset = 0;
5175
5176 BcmFlash2xBulkRead(Adapter, (PUINT)pBuff,eFlash2xSectionVal,uiOffset, MAX_RW_SIZE);
5177
5178 sig = *((PUINT)pBuff);
5179 sig =ntohl(sig);
5180
5181 //corrupt signature
5182 *pBuff = 0;
5183
5184 if(sig == ISO_IMAGE_MAGIC_NUMBER)
5185 {
5186 Adapter->bSigCorrupted = TRUE;
5187 WriteToFlashWithoutSectorErase(Adapter,(PUINT)pBuff,eFlash2xSectionVal,
5188 uiOffset ,Adapter->ulFlashWriteSize);
5189 }
5190 else
5191 {
5192 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_PRINTK, 0, 0,"BCM Signature is not present in header");
082e889b 5193 kfree(pBuff);
f8942e07
SH
5194 return STATUS_FAILURE;
5195 }
5196
5197 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,"Corrupted the signature");
5198 BCM_DEBUG_PRINT_BUFFER(Adapter,DBG_TYPE_OTHERS, NVM_RW, DBG_LVL_ALL,pBuff,MAX_RW_SIZE);
5199
082e889b 5200 kfree(pBuff);
f8942e07
SH
5201 return STATUS_SUCCESS ;
5202}
5203
5204BOOLEAN IsNonCDLessDevice(PMINI_ADAPTER Adapter)
5205{
5206 if(Adapter->psFlash2xCSInfo->IsCDLessDeviceBootSig == NON_CDLESS_DEVICE_BOOT_SIG)
5207 return TRUE;
5208 else
5209 return FALSE ;
5210}
5211
This page took 0.341218 seconds and 5 git commands to generate.