⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 c1667.c

📁 Flash芯片的CFI驱动c语言源代码,对自升级的系统有帮助。
💻 C
📖 第 1 页 / 共 3 页
字号:
   Step 6: If DQ6 did not toggle between the last two reads then return Flash_Success   Step 7: Error: return Flash_ToggleFailed*******************************************************************************/ReturnType FlashDataToggle( void ){   uCPUBusType ucVal1, ucVal2; /* Hold Status Register values */   FlashTimeOut(0); /* Initialize TimeOut Counter */        while(FlashTimeOut(200) != Flash_OperationTimeOut) {                     /* Step 1: Read Status Register  */      ucVal2 = FlashRead( ANY_ADDR );                /* Step 2: Read Status Register again */      ucVal1 = FlashRead( ANY_ADDR );            /* Step 3: If DQ6 did not toggle between the two reads                  then return Flash_Success */      if( (ucVal1&CMD(0x0040)) == (ucVal2&CMD(0x0040)) ) /* No Toggling */            return Flash_Success;      /* Step 4: DQ6 Toggling: If DQ5 is zero then operation                  is not yet complete */      if( (ucVal2&CMD(0x0020)) != CMD(0x0020) )         continue;      /* Step 5: DQ5 is zero: check DQ6 again  */      ucVal1 = FlashRead( ANY_ADDR ); /* Read Status Register two times */      ucVal2 = FlashRead( ANY_ADDR );       /* Step 6: If DQ6 did not toggle between the two reads                  then return Flash_Success */      if( (ucVal2&CMD(0x0040)) == (ucVal1&CMD(0x0040)) ) /* No Toggling */         return Flash_Success;      /* Step 7: Error: return Flash_ToggleFailed */      else {          eiErrorInfo.sprRetVal=FlashSpec_ToggleFailed;         return Flash_SpecificError;      } /* EndInf */   } /* EndWhile */       return Flash_OperationTimeOut; /* Time out exceeded */    } /*EndFunction FlashDataToggle */   #ifdef VERBOSE/******************************************************************************* Function:     byte *FlashErrorStr( ReturnType rErrNum ); Arguments:    rErrNum is the error number returned from other Flash Routines Return Value: A pointer to a string with the error message.Description:  This function is used to generate a text string describing the    error from the flash. Call with the return value from other flash routines.  Pseudo Code:    Step 1: Return the correct string. *******************************************************************************/ byte *FlashErrorStr( ReturnType rErrNum ) {    switch(rErrNum) {          case Flash_AddressInvalid:               return "Flash - Address is out of Range";          case Flash_BlockEraseFailed:               return "Flash - Block Erase failed";          case Flash_BlockNrInvalid:               return "Flash - Block Number is out of Range";          case Flash_ChipEraseFailed:               return "Flash - Chip Erase failed";          case Flash_FunctionNotSupported:               return "Flash - Function not supported";          case Flash_NoInformationAvailable:               return "Flash - No Additional Information Available";          case Flash_OperationOngoing:               return "Flash - Operation ongoing";          case Flash_OperationTimeOut:               return "Flash - Operation TimeOut";          case Flash_ProgramFailed:               return "Flash - Program failed";         case Flash_ResponseUnclear:              return "Flash - Response unclear";          case Flash_SpecificError:               switch (eiErrorInfo.sprRetVal) {                  case FlashSpec_MwpSetupFailed:                       return "Flash - Multiple Word Program Setup Failed";                  case FlashSpec_ToggleFailed:                       return "Flash - Data Toggle Failure";                  default:                        return "Flash - Undefined Error Value";              } /* End Switch */         case Flash_Success:               return "Flash - Success";          case Flash_VppInvalid:               return "Flash - Program/Erase Voltage (VPP) unsufficient";          case Flash_WrongType:               return "Flash - Wrong Type";          default:               return "Flash - Undefined Error Value";    } /* EndSwitch */ } /* EndFunction FlashErrorString */#endif /* VERBOSE Definition */   /*******************************************************************************Function:     ReturnType FlashMWProgram( udword udMode, udword udAddrOff,   udword udNrOfElementsInArray, udword udSaveState, void *pArray )Arguments:    udMode changes between programming modes   udAddrOff is the address offset into the flash to be programmed   udNrOfElementsInArray holds the number of (double)words in the array.   udSaveState zero if the function must update the eiErrorInfo.udGeneralInfo[0]   field.   pArray is a void pointer to the array with the contents to be programmed.Return Value: The function returns the following conditions:   Flash_Success                    Flash_AddressInvalid             Flash_FunctionNotSupported      Flash_OperationTimeOut    Flash_ProgramFailed              Flash_SpecificError with       eiErrorInfo.sprRetVal=FlashSpec_MwpSetupFailed   Flash_VppInvalidDescription: This function is used to program an array into the flash. It does   not erase the flash first and will not produce proper results, if the block(s)   are not erased first.   Any errors are returned without any further attempts to program other addresses   of the device. The function returns Flash_Success when all addresses have   successfully been programmed.Notes:1) Two program modes are available:   - udMode = 0, Normal Program Mode   The number of elements (udNumberOfElementsInArray) contained in pArray   are programmed directly to the flash starting with udAddrOff.       - udMode = 1, Single Value Program Mode   Only the first value of the pArray will be programmed to the flash   starting from udAddrOff.2) This function, if needed, should be rewritten for the specific environment.   Infact, to enhance performance, this function DOESN'T USE FlashRead and FlashWrite,   but read/write directly from the flash like an array, and DOESN'T follow exactly    the Multiple Word Program FlowChart of the data-sheet.   Moreover, to obtain the full performance mentioned in the data-sheet the procedure   should be rewritten in Assembler, to avoid any delays introduced by the C-language,    and to deploy the characteristics of your CPU, like pipelining or multiple execution    units.   Pseudo Code:   Step  1:  Check whether the data to be programmed are within the Flash memory    Step  2:  MWP Setup Phase (55 us)   Step  3:  Wait until Setup Phase is ready   Step  4:  MWP Program Phase   Step  5:  MWP Program Phase End   Step  6:  MWP Verify Phase       Step  7:  Check for errors   Step  8:  MWP Verify Phase End   Step  9:  Wait until Program/Erase Controller is ready   Step 10:  Multiple Word Program completed with success*******************************************************************************/ReturnType FlashMWProgram(udword udMode, udword udAddrOff, udword udNrOfElementsInArray, void *pArray ) {   uCPUBusType *ucpArrayPointer; /* Use an uCPUBusType to access the array */   uCPUBusType ucStatusBit6_1, ucStatusBit6_2, ucStatusBit0; /* Holds the Status Register reads */   uCPUBusType ucValueBit0 = CMD(1);   uCPUBusType ucValueBit6 = CMD(64);   udword udCurElement, udLastOff, udAddrOffOutsideOfCurrentBlock;   volatile udword *udpPrgAddr;   if (udMode > 1)      return Flash_FunctionNotSupported;   udpPrgAddr = (uCPUBusType*)&BASE_ADDR[udAddrOff];   /* Step 1: Check whether the data to be programmed are within               the Flash memory */   udLastOff = udAddrOff + udNrOfElementsInArray - 1;   if ( (udAddrOff>= FLASH_SIZE) || ( udNrOfElementsInArray > (FLASH_SIZE-udAddrOff) ) )      return Flash_AddressInvalid;            ucpArrayPointer = (uCPUBusType *)pArray;         /* Save Address Offset out of the current Block */   if (udAddrOff >= BlockOffset[1]) {      udAddrOffOutsideOfCurrentBlock = BlockOffset[0];   } else {      udAddrOffOutsideOfCurrentBlock = BlockOffset[1];   } /* EndIf */   /* Step 2: MWP Setup Phase (55 us) */   BASE_ADDR[0x555] = (uCPUBusType)CMD(0xAA);   BASE_ADDR[0x2AA] = (uCPUBusType)CMD(0x55);   BASE_ADDR[0x555] = (uCPUBusType)CMD(0x20);   /* Step 3: Wait until Setup  Phase is ready */   FlashTimeOut(0); /* Initialize TimeOut Counter */      /* Check the toggling of DQ6 */   ucStatusBit6_1 = BASE_ADDR[ANY_ADDR] & ucValueBit6;    ucStatusBit6_2 = BASE_ADDR[ANY_ADDR+1] & ucValueBit6;    while ( (ucStatusBit6_1 ^ ucStatusBit6_2) != ucValueBit6 ) {      /* Wait until StatusRegister Bit6 is toggling */      ucStatusBit6_1 = BASE_ADDR[ANY_ADDR] & ucValueBit6;       ucStatusBit6_2 = BASE_ADDR[ANY_ADDR+1] & ucValueBit6;       if (FlashTimeOut(1) == Flash_OperationTimeOut) {         FlashReset();         eiErrorInfo.sprRetVal = FlashSpec_MwpSetupFailed;         return Flash_SpecificError;       } /* EndIf */   } /* EndWhile */      ucStatusBit0 = BASE_ADDR[ANY_ADDR] & ucValueBit0;   if (ucStatusBit0 != 0) {      FlashReset();      eiErrorInfo.sprRetVal = FlashSpec_MwpSetupFailed;      return Flash_SpecificError;    } /* EndIf */      /* Step 4: MWP Program Phase */   if (udMode == 0) {      for (udCurElement = 0; udCurElement < udNrOfElementsInArray; ++udCurElement) {         *udpPrgAddr = ucpArrayPointer[udCurElement];         /* If DQ0 = 0, Program Process completed */          while( (*udpPrgAddr & ucValueBit0) != 0 );                                 } /* Next udCurElement */   } else { /* udMode = 1 */      for (udCurElement = 0; udCurElement < udNrOfElementsInArray; ++udCurElement) {         *udpPrgAddr = ucpArrayPointer[0];         /* If DQ0 = 0, Program Process completed */          while( (*udpPrgAddr & ucValueBit0) != 0 );      } /* Next udCurElement */   } /* EndIf */    /* Step 5: MWP Program Phase End */   BASE_ADDR[udAddrOffOutsideOfCurrentBlock] = ANY_VALUE; /* Program End Command */   /* Step 6: MWP Verify Phase */     /* If DQ0 = 0, Program Process completed */    while((BASE_ADDR[ANY_ADDR] & ucValueBit0) != 0);    if (udMode == 0) {      for (udCurElement = 0; udCurElement < udNrOfElementsInArray; ++udCurElement) {         *udpPrgAddr = ucpArrayPointer[udCurElement];         /* If DQ0 = 0, Program Process completed */          while( (*udpPrgAddr & ucValueBit0) != 0);      } /* Next udCurElement */   } else { /* udMode = 1 */      for (udCurElement = 0; udCurElement < udNrOfElementsInArray; ++udCurElement) {         *udpPrgAddr = ucpArrayPointer[0];         /* If DQ0 = 0, Program Process completed */          while( (*udpPrgAddr & ucValueBit0) != 0 );      } /* Next udCurElement */   } /* EndIf */    /* Step 8: MWP Verify Phase End */   BASE_ADDR[udAddrOffOutsideOfCurrentBlock] = ANY_VALUE; /* Verify End Command */   /* Step 9: Wait until Program/Erase Controller is ready */   do {      ucStatusBit6_1 = BASE_ADDR[ANY_ADDR]   & ucValueBit6; /* Read Bit6 of Status Register */       ucStatusBit6_2 = BASE_ADDR[ANY_ADDR+1] & ucValueBit6; /* Read Bit6 of Status Register */   /* Wait until every Action is finished (StatusRegister Bit6 is not toggling anymore) */   } while( ucStatusBit6_1 != ucStatusBit6_2 );    /* Step 10: Multiple Word Program completed with success */   return Flash_Success;} /* EndFunction FlashMWProgram */    /*******************************************************************************Function:     ReturnType FlashProgram( udword udMode, udword udAddrOff,   udword udNrOfElementsInArray, void *pArray )Arguments:    udMode changes between programming modes   udAddrOff is the address offset into the flash to be programmed   udNrOfElementsInArray holds the number of (double)words in the array.   pArray is a void pointer to the array with the contents to be programmed.Return Value: The function returns the following conditions:   Flash_Success                    Flash_AddressInvalid             Flash_FunctionNotSupported      Flash_OperationTimeOut    Flash_ProgramFailed              Flash_SpecificError with eiErrorInfo.sprRetVal=FlashSpec_MwpSetupFailed   Flash_VppInvalid       Description: This function is used to program an array into the flash. It does   not erase the flash first and will not produce proper results, if the block(s)   are not erased first.   Any errors are returned without any further attempts to program other addresses   of the device. The function returns Flash_Success when all addresses have   successfully been programmed.   Note: Two program modes are available:   - udMode = 0, Normal Program Mode   The number of elements (udNumberOfElementsInArray) contained in pArray   are programmed directly to the flash starting with udAddrOff.       - udMode = 1, Single Value Program Mode   Only the first value of the pArray will be programmed to the flash   starting from udAddrOff. Pseudo Code:    Step 1:  Check whether the data to be programmed are within the Flash memory    Step 2:  Send Word Program Command Sequence    Step 3:  Wait until Program/Erase Controller has completed   Step 4:  Return to Read mode (if an error occurred)   Step 5:  Return the error condition*******************************************************************************/ReturnType FlashProgram(udword udMode, udword udAddrOff, udword udNrOfElementsInArray, void *pArray ) {   uCPUBusType *ucpArrayPointer; /* Use an uCPUBusType to access the array */   udword udCounter; /* Counts number of programmed locations */   udword udLastOff;   ReturnType rRetVal=Flash_Success, rRetVal2;   if (udMode > 1)      return Flash_FunctionNotSupported;      /*Step 1: Check whether the data to be programmed are within the Flash memory space */   udLastOff = udAddrOff + udNrOfElementsInArray - 1;   if( udLastOff >= FLASH_SIZE )      return Flash_AddressInvalid;      if( udAddrOff >= FLASH_SIZE )         return Flash_AddressInvalid;   ucpArrayPointer = (uCPUBusType *)pArray;   for (udCounter =0; udCounter < udNrOfElementsInArray; udCounter++) {      /* Step 2: Send Word Program Command Sequence */      FlashWrite( 0x555, CMD(0xAA) );       FlashWrite( 0x2AA, CMD(0x55) );       FlashWrite( 0x555, CMD(0xA0) );       FlashWrite( udAddrOff+udCounter, *ucpArrayPointer );       /* Step 3: Wait until Program/Erase Controller has completed */      rRetVal2 = FlashDataToggle();      if( rRetVal2 !=  Flash_Success ) {             /* Step 4: Return to Read mode (if an error occurred) */         FlashWrite( ANY_ADDR, (uCPUBusType)CMD(0x00F0) ); /* Use single instruction cycle method */         eiErrorInfo.udGeneralInfo[0] = udAddrOff+udCounter;         rRetVal=Flash_ProgramFailed;      } /* EndIf */      if (udMode == 0)          ucpArrayPointer++;   } /* Next */   /* Step 5: Return the error condition */   return rRetVal;} /* EndFunction FlashProgram */ 

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -