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

📄 fmd.cpp

📁 wince5.0 bsp 下K9F2G08Flash的驱动源代码
💻 CPP
📖 第 1 页 / 共 3 页
字号:
    {
	    RETAILMSG(1, (TEXT("FMD:FMD_EraseBlock:This error block=%d!!\r\n"),blockID));
    }
//    RETAILMSG(1, (TEXT("FMD:FMD_EraseBlock:This  block=%d!!\r\n"),blockID));
    /*added  20080414 end*/
    if(g_pNandFlashChip)
    {
              Return_Status = g_pNandFlashChip->pEraseBlock(blockID);
	       return Return_Status;
    }
    return FALSE;
}


/*
    @func   BOOL | FMD_WriteSector | Writes the specified data to the specified NAND flash sector/page.
    @rdesc  TRUE = Success, FALSE = Failure.
    @comm    
    @xref   
*/
BOOL FMD_WriteSector(SECTOR_ADDR startSectorAddr, LPBYTE pSectorBuff, PSectorInfo pSectorInfoBuff, DWORD dwNumSectors)
{
       /*added by yangrui 20080414*/
       BOOL Return_Status=FALSE;
	startSectorAddr = startSectorAddr + (NandPartitionInfo.PartitionStartSector); 
//Added by Sky Xu to Control Shut down WinCE on Jan 15.2009 - Start
#if 1
	PELITE_GLOBALS peliteGlobal=NULL;
	peliteGlobal = (PELITE_GLOBALS)(DRIVER_GLOBALS_PHYSICAL_MEMORY_START+ (DWORD)(&((PDRIVER_GLOBALS)0)->elite));

	if(FALSE == peliteGlobal->Control_ShutDown_WinCE)
	{
		RETAILMSG(1, (TEXT("<<<Sky Xu>>>FMD_WriteSector:::Control_ShutDown_WinCE was setted as FALSE!!!\r\n")));
		return FALSE;
	}
#endif
//Added by Sky Xu to Control Shut down WinCE on Jan 15.2009 - Start

	if(startSectorAddr/64 > 2047)
	{
		RETAILMSG(1, (TEXT("FMD:FMD_WriteSector:This error block=%d!!\r\n"),startSectorAddr/64));
		RETAILMSG(1, (TEXT("FMD:FMD_WriteSector:This error SectorAddr=%d!!\r\n"),startSectorAddr));
	}
	//RETAILMSG(1, (TEXT("FMD:FMD_WriteSector:This  SectorAddr=%d!!\r\n"),startSectorAddr));
         /*added  20080414 end*/
    	if(g_pNandFlashChip)
    	{
    	       Return_Status = g_pNandFlashChip->pWriteSector(startSectorAddr,pSectorBuff,pSectorInfoBuff,dwNumSectors);
		return Return_Status;
    	}
	return FALSE;
}

VOID FMD_PowerUp(VOID)
{

}


VOID FMD_PowerDown(VOID)
{

}

BOOL FMD_OEMIoControl(DWORD dwIoControlCode, PBYTE pInBuf, DWORD nInBufSize, PBYTE pOutBuf, DWORD nOutBufSize, PDWORD pBytesReturned)
{
    return(TRUE);
}

BOOL FMD_Deinit(PVOID hFMD)
{
	// destroy the mutex
	if (g_hMutex)
	{
            CloseHandle(g_hMutex);
	}
       return(TRUE);
}


/*
    @func   BOOL | FMD_GetInfo | Provides information on the NAND flash.
    @rdesc  TRUE = Success, FALSE = Failure.
    @comm    
    @xref   
*/
BOOL FMD_GetInfo(PFlashInfo pFlashInfo)
{
    RETAILMSG(0, (TEXT("FMD_GetInfo\r\n")));
    if (!pFlashInfo)
    {
        return(FALSE);
    }
    pFlashInfo->flashType           = NAND;
    pFlashInfo->wDataBytesPerSector = (WORD)NandPartitionInfo.wDataBytesPerSector;
    pFlashInfo->dwNumBlocks         = NandPartitionInfo.TotalPartitionBlocks * 1;
    pFlashInfo->wSectorsPerBlock    = (WORD)NandPartitionInfo.SectorsPerBlock;
    pFlashInfo->dwBytesPerBlock     = (pFlashInfo->wSectorsPerBlock * pFlashInfo->wDataBytesPerSector);
    RETAILMSG(0,(TEXT("FMD_GetInfo:pFlashInfo->dwNumBlocks = %d!!\r\n"),pFlashInfo->dwNumBlocks));
    RETAILMSG(0,(TEXT("FMD_GetInfo:pFlashInfo->wSectorsPerBlock = %d!!\r\n"),pFlashInfo->wSectorsPerBlock));   
    RETAILMSG(0,(TEXT("FMD_GetInfo:the whole sector = %d!!\r\n"),(pFlashInfo->wSectorsPerBlock)*(pFlashInfo->dwNumBlocks)));   
    return(TRUE);
}


BOOL IsBlockBad(BLOCK_ID blockID)
{
    /*added by yangrui 20080414*/	
    BOOL Return_Status=FALSE;
    blockID = blockID + (NandPartitionInfo.PartitionStartBlock);
    if(blockID > 2047)
    {
	    RETAILMSG(1, (TEXT("FMD:IsBlockBad:This error block=%d!!\r\n"),blockID));
    }
    /*added  20080414 end*/
    if(g_pNandFlashChip)
    {
         Return_Status = g_pNandFlashChip->pIsBlockBad(blockID);
         return Return_Status;
    }
    return FALSE;
}


/*
    @func   DWORD | FMD_GetBlockStatus | Returns the status of the specified block.
    @rdesc  Block status (see fmd.h).
    @comm    
    @xref   
*/
DWORD FMD_GetBlockStatus(BLOCK_ID blockID)
{
    SECTOR_ADDR Sector = (blockID * NAND_PAGE_CNT);
    SectorInfo SI;
    DWORD dwResult = 0;


    if (IsBlockBad(blockID))
//20080223 eboot test
        return BLOCK_STATUS_BAD;
       //dwResult |=BLOCK_STATUS_BAD;
//20080223 by yqx

    if (!FMD_ReadSector(Sector, NULL, &SI, 1)) 
        return BLOCK_STATUS_UNKNOWN;

    if (!(SI.bOEMReserved & OEM_BLOCK_READONLY))  
        dwResult |= BLOCK_STATUS_READONLY;

    if (!(SI.bOEMReserved & OEM_BLOCK_RESERVED))  
        dwResult |= BLOCK_STATUS_RESERVED;

    return(dwResult);
}


/*
    @func   BOOL | MarkBlockBad | Marks the specified block as bad.
    @rdesc  TRUE = Success, FALSE = Failure.
    @comm    
    @xref   
*/
static BOOL MarkBlockBad(BLOCK_ID blockID)
{
    /*added by yangrui 20080414*/
    BOOL Return_Status=FALSE;
    blockID = blockID + (NandPartitionInfo.PartitionStartBlock);
    if(blockID > 2047)
    {
	    RETAILMSG(1, (TEXT("FMD:IsBlockBad:This error block=%d!!\r\n"),blockID));
    }
    /*added  20080414 end*/
    if(g_pNandFlashChip)
    {
         Return_Status = g_pNandFlashChip->pMarkBlockBad(blockID);
	  return Return_Status;
    }
    return FALSE;
}

/*
    @func   BOOL | FMD_SetBlockStatus | Marks the block with the specified block status.
    @rdesc  TRUE = Success, FALSE = Failure.
    @comm    
    @xref   
*/
BOOL FMD_SetBlockStatus(BLOCK_ID blockID, DWORD dwStatus)
{

	RETAILMSG(1,(TEXT("FMD_SetBlockStatus:block:%d,status:%d \r\n"),blockID,dwStatus));

//Added by Sky Xu to Control Shut down WinCE on Jan 15.2009 - Start
	PELITE_GLOBALS peliteGlobal=NULL;
	peliteGlobal = (PELITE_GLOBALS)(DRIVER_GLOBALS_PHYSICAL_MEMORY_START+ (DWORD)(&((PDRIVER_GLOBALS)0)->elite));

	if(FALSE == peliteGlobal->Control_ShutDown_WinCE)
	{
		RETAILMSG(0, (TEXT("<<<Sky Xu>>>FMD_SetBlockStatus:::Control_ShutDown_WinCE was setted as FALSE!!!\r\n")));
		return FALSE;
	}
//Added by Sky Xu to Control Shut down WinCE on Jan 15.2009 - Start

	
    if (dwStatus & BLOCK_STATUS_BAD)
    {
        if (!MarkBlockBad(blockID))
            return(FALSE);
    }

    if (dwStatus & (BLOCK_STATUS_READONLY | BLOCK_STATUS_RESERVED)) {
        
        SECTOR_ADDR Sector = blockID * NAND_PAGE_CNT;
        SectorInfo SI;

        if (!FMD_ReadSector(Sector, NULL, &SI, 1)) {
            return FALSE;
        }

        if (dwStatus & BLOCK_STATUS_READONLY) {
            SI.bOEMReserved &= ~OEM_BLOCK_READONLY;
        }
        
        if (dwStatus & BLOCK_STATUS_RESERVED) {
            SI.bOEMReserved &= ~OEM_BLOCK_RESERVED;
        }

        if (!FMD_WriteSector (Sector, NULL, &SI, 1)) {
            return FALSE;
        }

    }    
    
    return(TRUE);
}


BOOL FMD_ReadSector1G08(SECTOR_ADDR startSectorAddr, LPBYTE pSectorBuff, PSectorInfo pSectorInfoBuff, DWORD dwNumSectors)
{
  	ULONG SectorAddr = (ULONG)startSectorAddr;
	int i;
    	BOOL  bRet = TRUE;

  	//20080229 ADD ECC 2048
  	BYTE ECCBuf[4];
  	BYTE ECCBufN[4];
  	DWORD ECCRegVal;
  	BYTE temp;
	DWORD ecc_state;
    	DWORD byteLocation;
    	DWORD bitLocation; 
  	//20080229 by yqx
	
//	RETAILMSG(1,(TEXT("FMD_ReadSector1G08,startSectorAddr=%d,pSectorBuff=0x%x,pSectorInfoBuff=0x%x,dwNumSectors=%d\r\n"),startSectorAddr,pSectorBuff,pSectorInfoBuff,dwNumSectors));
//	EdbgOutputDebugString("FMD_ReadSector1G08(%d,%p,%p,%d)\n",startSectorAddr,pSectorBuff,pSectorInfoBuff,dwNumSectors);

    	if (!pSectorBuff && !pSectorInfoBuff || dwNumSectors > 1) 
     	{
        	RETAILMSG(1, (TEXT("Invalid parameters!\n")));
        	return FALSE;
    	}
		
	GRABMUTEX();          //we should MUTEX first
		
  	NF_nFCE_L();                            // Select the flash chip.
	NF_WAITRnB();
  	//delete at 20080919
//	NF_CLEAR_RB();
//  	NF_CMD(CMD_RESET);                        // Send reset command.
//	for(i=0;i<10;i++); 
//    	NF_DETECT_RB();
  	//delete at 20080919

    	ULONG blockPage = SectorAddr;//(((SectorAddr / NAND_PAGE_CNT) * NAND_PAGE_CNT) | (SectorAddr % NAND_PAGE_CNT));
 
	if(pSectorBuff)
	{			
		//20080229 ADD 2048 BYTE ECC   
      		NF_RSTECC();                            // Initialize ECC.
      		NF_MECC_UnLock();
		//20080229 by yqx
		   
		NF_CLEAR_RB();
		NF_CMD(CMD_READ);                    // Send read command.
      		NF_ADDR(0); 	// Column (A[7:0]) = 0
		NF_ADDR(0); 	// A[11:8]
      		NF_ADDR((blockPage)&0xff);	// A[19:12]
      		NF_ADDR((blockPage>>8)&0xff);	// A[27:20]
#if (K9F2G08_SUPPORT||K9F4G08_SUPPORT||K9F8G08_SUPPORT)
		if((g_pNandFlashChip->FlashID!=0xECF1)&&(g_pNandFlashChip->FlashID!=0xECA1))
		NF_ADDR((blockPage>>16)&0xff);
#endif
      
     		NF_CLEAR_RB();
      		NF_CMD(0x30);	// 2'nd command
     		NF_DETECT_RB();

   	
		 if((DWORD) pSectorBuff&0x3)
		 {
			 RdPage2048Unalign (pSectorBuff,(PULONG)&s2440NAND->rNFDATA);
     		 }
     		 else 
     		 {
#if (TRANS_MODE == C_LANG)  
       		RdPage2048(pSectorBuff,(PULONG)&s2440NAND->rNFDATA);                // Read page/sector data. 
#elif (TRANS_MODE == DMA)		
		// Nand to memory dma setting
		s2440INT->rSRCPND=BIT_DMA0;	// Init DMA src pending.
		s2440DMAregs->rDISRC0=(unsigned int)NFDATA; 	// Nand flash data register
		s2440DMAregs->rDISRCC0=(0<<1) | (1<<0); //arc=AHB,src_addr=fix
		s2440DMAregs->rDIDST0=(unsigned int)pPhyDMAbuffer;
		s2440DMAregs->rDIDSTC0=(0<<1) | (0<<0); //dst=AHB,dst_addr=inc;
		s2440DMAregs->rDCON0=(1<<31)|(1<<30)|(1<<29)|(1<<28)|(1<<27)|(0<<23)|(1<<22)|(2<<20)|(2048/4/4);
		//Handshake,AHB,interrupt,(4-burst),whole,S/W,no_autoreload,word,count=128;
	
		// DMA on and start.
		s2440DMAregs->rDMASKTRIG0=(1<<1)|(1<<0);
	
		while(!((s2440INT->rSRCPND) & BIT_DMA0));	// Wait until Dma transfer is done.			
		s2440INT->rSRCPND=BIT_DMA0;
		memcpy(pSectorBuff, pVirDMAbuf, 2048);
#endif
       		
		 }


//20080229 add 2048 byte ecc
     		NF_MECC_Lock();
     		ECCRegVal=NF_ECC();
     		//RETAILMSG(1,(TEXT("FMD_ReadSector1G08(11startSectorAddr %d) ECCNEW =0x%x\r\n"),startSectorAddr,ECCRegVal));
     		ECCBufN[0]= (BYTE)(ECCRegVal &0xff);
     		ECCBufN[1]= (BYTE)((ECCRegVal>>8) &0xff);
     		ECCBufN[2]= (BYTE)((ECCRegVal>>16) &0xff);
     		ECCBufN[3]= (BYTE)((ECCRegVal>>24) &0xff);
//20080229 BY YQx		
   	}//end if pSectorBuff
   
   
	if(pSectorInfoBuff) 
  	{
		if(!pSectorBuff)
    		{
       		NF_CLEAR_RB();
       		NF_CMD(0x00);	// Read command
       		NF_ADDR((2048+0)&0xff);			// 2060 = 0x080c
		   	NF_ADDR(((2048+0)>>8)&0xff);
       		NF_ADDR((blockPage)&0xff);	// A[19:12]
       		NF_ADDR((blockPage>>8)&0xff);	// A[27:20]     
#if (K9F2G08_SUPPORT||K9F4G08_SUPPORT||K9F8G08_SUPPORT)
		     if((g_pNandFlashChip->FlashID!=0xECF1)&&(g_pNandFlashChip->FlashID!=0xECA1))
			NF_ADDR((blockPage>>16)&0xff);
#endif
       		NF_CLEAR_RB();
       		NF_CMD(0x30);	// 2'nd command
       		NF_DETECT_RB();	
	       }//end if (!pSectorBuff)
		 
  		//  Read the bad block mark
    		pSectorInfoBuff->bBadBlock = (BYTE) NF_RDDATA();
	 	//  Read the SectorInfo data (we only need to read first 8 bytes)
    		pSectorInfoBuff->dwReserved1  = NF_DATA_R4();
    		//  OEM byte
    		pSectorInfoBuff->bOEMReserved = (BYTE) NF_RDDATA();  
    		//  Second reserved field (WORD)
    		pSectorInfoBuff->wReserved2 = ((BYTE) NF_RDDATA() << 8);
    		pSectorInfoBuff->wReserved2 |= ((BYTE) NF_RDDATA());
  	}//end if(pSectorInfoBuff)    
 	//20080229 ADD 2048 BYTE ECC
 	else
 	{
    		for(i=0; i<sizeof(SectorInfo); i++) 
    		{
        		temp = (BYTE)NF_RDDATA();
    		}
 	}//end else
 
 	if (pSectorBuff)
 	{
	  //Verify the ECC values
    	//  Read the ECC buffer
    		for(i=0; i<4; i++)
    		{
       		ECCBuf[i] = (BYTE) NF_RDDATA();

⌨️ 快捷键说明

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