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

📄 s3c6410_fil.c

📁 6410BSP3
💻 C
📖 第 1 页 / 共 5 页
字号:
	}
	NF_CMD(CMD_READ_CONFIRM);

	if (bInternalInterleaving == TRUE32)
	{
#if	1
		_TRDelay(nPpn);
#else
		if (nVBank%2)
		{
			NF_CMD(CMD_READ_STATUS_CHIP1);
		}
		else
		{
			NF_CMD(CMD_READ_STATUS_CHIP0);
		}
		while(!(NF_DATA_R()&0x40));

		// Dummy Command to Set Proper Pointer to Read Position after NF_WAIT_RnB()
		NF_CMD(CMD_READ);
#endif
	}
	else
	{
		NF_WAIT_RnB(nBank);

		// Dummy Command to Set Proper Pointer to Read Position after NF_WAIT_RnB()
		NF_CMD(CMD_READ);
	}

	// Read Spare Area
	if (ECC_8BIT_SPPORT == TRUE32)
	{
        NF_SETREG_8BITECC();
		nRet = Read_Spare_8BitECC(nBank, nPpn, (UINT32*)pSBuf);		
	}
	else if (SECTORS_PER_PAGE == 8)
	{
        NF_SETREG_8BITECC();
		nRet = Read_Spare_Separate(nBank, nPpn, (UINT32*)pSBuf);
        NF_SETREG_4BITECC();
	}
	else
	{
		nRet = Read_Spare(nBank, nPpn, (UINT32*)pSBuf);
	}

	if ((nRet & ECC_UNCORRECTABLE_ERROR) == 0)
	{
		nPageReadStatus = (nRet<<16);

		if (WMR_GetChkSum(&pSBuf[1], 1) >= 4)
		{
			// Not Clean Page
			bPageClean = FALSE32;
		}

		// Read Main Area
		if(pDBuf != NULL)
		{
			for (nCnt=0; nCnt<nLoopCount; nCnt++)
			{
				if (nSctBitmap&(0x1<<nCnt))
				{
 					if (ECC_8BIT_SPPORT == TRUE32)
					{
                        NF_SETREG_8BITECC();
						nRet = Read_Sector_8BitECC(nBank, nPpn, nCnt, pDBuf, (UINT32*)pSBuf, bPageClean);						
					}
					else
					{
						nRet = Read_Sector(nBank, nPpn, nCnt, pDBuf, (UINT32*)pSBuf, bPageClean);
					}
					//nPageReadStatus |= (nRet<<(nCnt*4));  // if 2KByte/Page
					nPageReadStatus |= (nRet<<(nCnt*2));  // if both non-case for all-ff and 4KByte/Page
				}
			}
		}
	}
	else
	{
    	nPageReadStatus |= (nRet<<(8*2));  // The spare area position.
	}

	// Chip Unselect
	NF_CE_H(nBank);

#ifdef	USE_SETKMODE
	SetKMode(bLastMode);
#endif

	if(bSecondRead)
	{
		nPageReadStatus2nd = nPageReadStatus;
	}
	else
	{
		nPageReadStatus1st = nPageReadStatus;
	}

	if(bLoopNeed && !bSecondRead)
	{
		bSecondRead = TRUE32;
		goto _B_SecondRead;
	}

	if(nPageReadStatus1st&PAGE_UNCORRECTABLE_ERROR_MASK || nPageReadStatus2nd&PAGE_UNCORRECTABLE_ERROR_MASK)
	{
		// Uncorrectable ECC Error
		NAND_ERR((_T("[FIL:ERR]--NAND_Read() : Uncorrectable Error in Bank %d, Page %d [0x%08x] [0x%08x]\r\n"), nBank, nPpn, nPageReadStatus1st, nPageReadStatus));
		return FIL_U_ECC_ERROR;
	}
	else
	{

//        MLC_Print_Page_Data(pDBuf, pSBuf);

#if (WMR_READ_RECLAIM)
		if (nPageReadStatus1st&PAGE_CORRECTABLE_ERROR_MASK || nPageReadStatus2nd&PAGE_CORRECTABLE_ERROR_MASK)
		{
			READ_ERR_FLAG = TRUE32;
			NAND_ERR((_T("[FIL:INF] NAND_Read() : Correctable Error in Bank %d, Page %d [0x%08x] [0x%08x]\r\n"), nBank, nPpn, nPageReadStatus1st, nPageReadStatus2nd));
		}
#endif
		if (bCleanCheck&&bPageClean)
		{
			if (bIsSBufNull == FALSE32)
			{
				BOOL32 bClean;

				// Check 32 bytes is all 0xFF & don't care about ECC Value
				if ((pDBuf == NULL) && (bECCIn))
				{
					// When the pMBuf is NULL, read 128 bytes(twice read) in the spare area
					if (bSecondRead)
					{
						pSBuf -= BYTES_PER_SPARE_PAGE;
					}

					bClean = _IsAllFF(pSBuf, BYTES_PER_SPARE_SUPAGE);
				}
				else
				{
					// TODO: to be changed all FF check Size
					bClean = _IsAllFF(pSBuf, ((SECTORS_PER_PAGE == 8) ? NAND_MECC_OFFSET_4K : NAND_MECC_OFFSET));
				}

				if (bClean)
				{
					NAND_MSG((_T("[FIL]--NAND_Read() : FIL_SUCCESS_CLEAN\r\n")));
					return FIL_SUCCESS_CLEAN;
				}
				else
				{
					NAND_MSG((_T("[FIL]--NAND_Read()[bClean==FASLE32]\r\n")));
					return FIL_SUCCESS;
				}
			}
			else
			{
				NAND_MSG((_T("[FIL]--NAND_Read()[bIsSBufNull != FALSE32] : FIL_SUCCESS_CLEAN\r\n")));
				return FIL_SUCCESS_CLEAN;
			}
		}
		else
		{
			NAND_MSG((_T("[FIL]--NAND_Read()[bCleanCheck&&bPageClean == FASLE32]\r\n")));
			return FIL_SUCCESS;
		}
	}

}


/*****************************************************************************/
/*                                                                           */
/* NAME                                                                      */
/*      NAND_Write		                                                     */
/* DESCRIPTION                                                               */
/*      This function writes NAND page area							 		 */
/* PARAMETERS                                                                */
/*      nBank    	[IN] 	Physical device number			               	 */
/*      nPpn     	[IN] 	Physical page number				         	 */
/*      nSctBitmap 	[IN] 	The indicator for the sector to write         	 */
/*      nPlaneBitmap[IN]    The indicator of the plane  					 */
/*      pDBuf		[IN]	Buffer pointer of main area to write          	 */
/*      pSBuf		[IN]	Buffer pointer of spare area to write         	 */
/*																			 */
/* RETURN VALUES                                                             */
/*		None																 */
/* NOTES                                                                     */
/*                                                                           */
/*****************************************************************************/
VOID
NAND_Write(UINT32 nBank, UINT32 nPpn, UINT32 nSctBitmap,
			UINT32  nPlaneBitmap, UINT8* pDBuf, UINT8* pSBuf)
{
	UINT32 nCnt;
	UINT32 nPbn;
	UINT32 nPOffset;

	//BOOL32	bFirstWrite = TRUE32;
	BOOL32	bSecondWrite = FALSE32;
	BOOL32  bLoopNeed = FALSE32;

	pSECCCxt pSpareCxt = NULL;

#ifdef	USE_SETKMODE
	BOOL bLastMode;
#endif

	NAND_MSG((_T("[FIL] ++NAND_Write(%d, %d, 0x%02x, 0x%02x)\r\n"), nBank, nPpn, nSctBitmap, nPlaneBitmap));
	//NAND_ERR((_T("[FIL] ++NAND_Write(%d, %d, 0x%02x, 0x%02x)\r\n"), nBank, nPpn, nSctBitmap, nPlaneBitmap));  // ksk dbg

//    MLC_Print_Page_Data(pDBuf, pSBuf);

	if (nBank >= BANKS_TOTAL || nPpn >= PAGES_PER_BANK || (pDBuf == NULL && pSBuf == NULL))
	{
		NAND_ERR((_T("[FIL:ERR]--NAND_Write() : Parameter Overflow\r\n")));
		WMR_ASSERT(FALSE32);
		return;
	}

	// avoid r/b check error with internal interleaving
	if (bInternalInterleaving == TRUE32)
	{
		aNeedSync[nBank] = TRUE32;
	}

	/* 
	In case of Internal Interleaving, the first address of the second bank should be 
	the half of toal block number of NAND.
	For example, In 4Gbit DDP NAND, its total block number is 4096.
	So, the bank 0 has 2048 blocks (Physical number : 0 ~ 2047),
	the bank 1 has another 2048 blocks (Physical number : 2048 ~ 4095).
	therefore, first block address of Bank 1 could be the physically 2048th block.
	*/
	if (bInternalInterleaving == TRUE32)
	{
		if ((nBank & 0x1) == 1)
		{
			nPpn += PAGES_PER_BANK;
		}
		nBank /= 2;
	}

#if (WMR_STDLIB_SUPPORT)
	nPbn = nPpn / PAGES_PER_BLOCK;
	nPOffset = nPpn % PAGES_PER_BLOCK;
#else
	nPbn = DIV(nPpn, PAGES_PER_BLOCK_SHIFT);
	nPOffset = REM(nPpn, PAGES_PER_BLOCK_SHIFT);
#endif

	// In case of 2-Plane Program, re-calculate the page address
	if(TWO_PLANE_PROGRAM == TRUE32)
	{
		nPpn = nPbn * 2 * PAGES_PER_BLOCK + nPOffset;

		if (nPlaneBitmap == enuBOTH_PLANE_BITMAP)
		{
			bLoopNeed = TRUE32;
		}
		else if (nPlaneBitmap == enuRIGHT_PLANE_BITMAP)
		{
			nPpn += PAGES_PER_BLOCK;
			//nSctBitmap = nSctBitmap>>4;
		}
	}

	nSctBitmap &= FULL_SECTOR_BITMAP_PAGE;

#ifdef	USE_SETKMODE
	bLastMode = SetKMode(TRUE);
#endif

	// CE Select
	NF_CE_L(nBank);

_B_SecondWrite:

	// 2-Plane Program, page address is changed
	if (bSecondWrite)
	{
		nPpn += PAGES_PER_BLOCK;
		nSctBitmap = nSctBitmap >> SECTORS_PER_PAGE;
	}

	if(pSBuf == NULL)
	{
		pSBuf = aTempSBuf;
		WMR_MEMSET(pSBuf, 0xFF, BYTES_PER_SPARE_PAGE);		// Initialize the spare buffer
	}
	else
	{
		// Set 0xFF to ECC Area
		if (IS_CHECK_SPARE_ECC == TRUE32)
		{
			pSBuf[2] = 0xff;	// Reserved
			pSBuf[3] = 0xff;
			//WMR_MEMSET(pSBuf+2, 0xFF, 2);						// Clear Reserved area in Spare Buffer
			WMR_MEMSET(pSBuf+((SECTORS_PER_PAGE == 8) ? NAND_MECC_OFFSET_4K : NAND_MECC_OFFSET),
						0xFF,
						BYTES_PER_SPARE_PAGE-((SECTORS_PER_PAGE == 8) ? NAND_MECC_OFFSET_4K : NAND_MECC_OFFSET));		// Clear ECC area in Spare Buffer
		}
	}

	pSpareCxt = (pSECCCxt)pSBuf;
	pSpareCxt->cCleanMark = 0x0;	// Clean mark to 0. It means that page is written

	if (bSecondWrite)
	{
		NF_CMD(CMD_2PLANE_PROGRAM);
		NF_SET_ADDR(nPpn, 0);
	}
	else
	{
		NF_CMD(CMD_PROGRAM);
		NF_SET_ADDR(nPpn, 0);
	}

	// Write Main Sector
	if (pDBuf != NULL)
	{
		// In case of the second write, the position of buffer pointer is moved backward as much as 1 page size
		if (bSecondWrite)
		{
			pDBuf += BYTES_PER_MAIN_PAGE;
		}

		for (nCnt=0; nCnt<SECTORS_PER_PAGE; nCnt++)
		{
			if (nSctBitmap&(0x1<<nCnt))
			{
				if (ECC_8BIT_SPPORT == TRUE32)
				{
                    NF_SETREG_8BITECC();
					Write_Sector_8BitECC(nPpn, nCnt, pDBuf);
				}
				else
				{
					Write_Sector(nPpn, nCnt, pDBuf);					
				}

				if (IS_CHECK_SPARE_ECC == TRUE32)
				{
				    if ( ECC_8BIT_SPPORT != TRUE32 )
				    {
    					pSpareCxt->aMECC[nCnt*2] = NF_MECC0();
    					pSpareCxt->aMECC[nCnt*2+1] = NF_MECC1();
    				}
    				else
    				{
    					pSpareCxt->aMECC[nCnt*4] = NF_8MECC0();
    					pSpareCxt->aMECC[nCnt*4+1] = NF_8MECC1();
    					pSpareCxt->aMECC[nCnt*4+2] = NF_8MECC2();
    					pSpareCxt->aMECC[nCnt*4+3] = NF_8MECC3() & 0xff;	
    				}
				}
			}
			else
			{
				if (ECC_8BIT_SPPORT == TRUE32)
				{
					pSpareCxt->aMECC[nCnt*4] = ECCVAL_ALLFF0;
					pSpareCxt->aMECC[nCnt*4+1] = ECCVAL_ALLFF1;
					pSpareCxt->aMECC[nCnt*4+2] = ECCVAL_ALLFF2;
					pSpareCxt->aMECC[nCnt*4+3] = ECCVAL_ALLFF3 & 0xff;					
    			}
    			else
    			{
    				pSpareCxt->aMECC[nCnt*2] = ECCVAL_ALLFF0;	// All 0xFF ECC
    				pSpareCxt->aMECC[nCnt*2+1] = ECCVAL_ALLFF1;
    			}
    		}
		}
	}
	else if (IS_CHECK_SPARE_ECC == TRUE32)
	{
		if (ECC_8BIT_SPPORT == TRUE32)
		{
			for (nCnt=0; nCnt<SECTORS_PER_PAGE; nCnt++)
			{
				pSpareCxt->aMECC[nCnt*4] = ECCVAL_ALLFF0;
				pSpareCxt->aMECC[nCnt*4+1] = ECCVAL_ALLFF1;
				pSpareCxt->aMECC[nCnt*4+2] = ECCVAL_ALLFF2;
				pSpareCxt->aMECC[nCnt*4+3] = ECCVAL_ALLFF3 & 0xff;
			}
		}
		else
		{
			for (nCnt=0; nCnt<SECTORS_PER_PAGE; nCnt++)
			{
				pSpareCxt->aMECC[nCnt*2] = ECCVAL_ALLFF0;	// All 0xFF ECC
				pSpareCxt->aMECC[nCnt*2+1] = ECCVAL_ALLFF1;
			}
		}
	}

	// Write Spare
	if (ECC_8BIT_SPPORT == TRUE32)
	{
        NF_SETREG_8BITECC();
		Write_Spare_8BitECC(nBank, nPpn, pSpareCxt);		
	}
	else if (SECTORS_PER_PAGE == 8)

⌨️ 快捷键说明

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