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

📄 nandfblk.c

📁 PDA上的CF CARD 文件系统的建立程式
💻 C
📖 第 1 页 / 共 3 页
字号:
		return -1;
	}
  #else
	// no cache present, write to flash
	if (NAND_FFS_eraseFlashBlock(block) == -1)
	{
		// errno set by NAND_FFS_eraseFlashBlock()
		return -1;
	}

	if (NAND_FFS_programFlashBlock(block, pData) == -1)
	{
		// errno set by NAND_FFS_programFlashBlock()
		return -1;
	}

	return 0;
  #endif
}



/*************************************************************
Function: NAND_FFS_findLeastErasedNonFullBlock
Description:
	find a least erased non full block
Input:
	nThLumpEntry -- this one would be the lump entry used
			by NAND_findFreeLump();
Output:
	block number of the least erased free block
	-1 if there is no free block (disk full)
**************************************************************/

/**** modified by chilong 01/17/2002 ****/
int NAND_FFS_findLeastErasedNonFullBlock(int *pNthLumpEntry)
{
  unsigned long minCount = 0xFFFFFFFF;
  int i;
  int resultBlock = -1;

  #ifdef NAND_FFS_DEBUG
	sprintf(NAND_FFS_DebugString, "[NAND_FFS_findLeastErasedNonFullBlock]");
	SprintStringLn(NAND_FFS_DebugString);
  #endif

  // check the erase count of every flash block

  for (i = 0; i < NAND_FFS_BLOCK_NUM; i++)
  {
	if (NAND_FFS_Block[i] == NAND_FB_UNUSED)
	{
		continue;
	}

	// if the block full bit is 1, the block is full
//	if ((NAND_FFS_EraseCount[i] & NAND_BLOCK_FULL_BIT_MASK) != 0)
	if (NAND_FFS_Block[i] == NAND_FB_FULL)
		continue;

//	if ((NAND_FFS_EraseCount[i] & (~NAND_BLOCK_FULL_BIT_MASK)) < minCount)
	if (NAND_FFS_EraseCount[i] < minCount)
	{
		// the erase count of block i is less than the current smallest count
		// check if block i has any unoccupied lump
		
		/**** added by chilong 01/18/2002 ****/
		*pNthLumpEntry = NAND_END_LUMP;
		/**** added by chilong 01/18/2002 ****/
		
		if (NAND_countFreeLumpsInBlock(i, pNthLumpEntry) > 0)
		{
			// block i has free lumps, update the temporary smallest count
//			minCount = (NAND_FFS_EraseCount[i] & (~NAND_BLOCK_FULL_BIT_MASK));
			minCount = NAND_FFS_EraseCount[i];
			resultBlock = i;
		}
	}
  }

  #ifdef NAND_FFS_DEBUG
	sprintf(NAND_FFS_DebugString, "    result block: %d", resultBlock);
	SprintStringLn(NAND_FFS_DebugString);
  #endif

  return resultBlock;
}
/**** modified by chilong 01/17/2002 ****/

/*************************************************************
Function: NAND_FFS_block2Offset
Description:
	get the address offset of the target flash block
Input:
	block - the block number
Output:
	the address offset of the block
	-1	error block number
**************************************************************/
/*
long NAND_FFS_block2Offset(int block)
{
  // check if the block is out of bound
  if (block < 0 || block >= NAND_FFS_BLOCK_NUM)
	return -1;

  // check if the block is valid
  if (NAND_FFS_Block[block] == NAND_FB_UNUSED)
	return -1;

  return ((NAND_FFS_START_BLOCK + block) * NAND_FLASH_BLOCK_SIZE);
}
*/


/*************************************************************
Function: NAND_FFS_offset2Block
Description:
	get the block number of the target flash block from offset
Input:
	offset - the address offset
	block - the resulting block number (-1 if failed)
	lump - the resulting lump number within the block (-1 if failed)
Output:
	NONE
**************************************************************/
/*
void NAND_FFS_offset2Block(long offset, int *block, int *lump)
{
  *block = (offset / NAND_FLASH_BLOCK_SIZE) - NAND_FFS_START_BLOCK;
  *lump = (offset & (NAND_FLASH_BLOCK_SIZE - 1)) / NAND_LUMP_SIZE;

  if (*block < 0 || *block >= NAND_FFS_BLOCK_NUM || NAND_FFS_Block[*block] == NAND_FB_UNUSED)
  {
	// the block is invalid
	*block = -1;
	*lump = -1;
  }

  return;
}
*/


/*************************************************************
Function: NAND_FFS_block2Address
Description:
	get the address of the target flash block
Input:
	block - the block number
Output:
	the address of the block
	-1	error block number
**************************************************************/
/*
void *NAND_FFS_block2Address(int block)
{
  long offset;

  // check if the block is out of bound
  if (block < 0 || block >= NAND_FFS_BLOCK_NUM)
	return NULL;

  // check if the block is valid
  if (NAND_FFS_Block[block] == NAND_FB_UNUSED)
	return NULL;

  offset =  (NAND_FFS_START_BLOCK + block) * NAND_FLASH_BLOCK_SIZE;

  return((void *)(offset + NAND_FFS_FLASH_BASE_ADDR));
}
*/


/*************************************************************
Function: NAND_FFS_address2Block
Description:
	get the block number of the target flash block from address
Input:
	address - the starting address of a flash block or lump
	block - the resulting block number (-1 if failed)
	lump - the resulting lump number within the block (-1 if failed)
Output:
	NONE
**************************************************************/
/*
void NAND_FFS_address2Block(void *address, int *block, int *lump)
{
  if ((unsigned long)address < NAND_FFS_FLASH_BASE_ADDR)
  {
	*block = -1;
	*lump = -1;

	return;
  }

  *block = (((unsigned long)address - NAND_FFS_FLASH_BASE_ADDR) / NAND_FLASH_BLOCK_SIZE) - NAND_FFS_START_BLOCK;
  *lump = (((unsigned long)address - NAND_FFS_FLASH_BASE_ADDR) & (NAND_FLASH_BLOCK_SIZE - 1)) / NAND_LUMP_SIZE;

  if (*block < 0 || *block >= NAND_FFS_BLOCK_NUM || NAND_FFS_Block[*block] == NAND_FB_UNUSED)
  {
	// the block is invalid
	*block = -1;
	*lump = -1;
  }

  return;
}
*/


/*************************************************************
Function: NAND_FFS_checkBlock
Description:
	check if the target block is valid
Input:
	block - the target block
Output:
	 0 - block is ok
	-1 - block is invalid
**************************************************************/
int NAND_FFS_checkBlock(int block)
{
  // check if the block is out of bound

  if (block < 0 || block >= NAND_FFS_BLOCK_NUM)
  {
	NAND_FFS_Errno = ERROR_INVALID_BLOCK;
	return -1;
  }

  // check if the block is valid
  if (NAND_FFS_Block[block] == NAND_FB_UNUSED)
  {
  	NAND_FFS_Errno = ERROR_INVALID_BLOCK;
	return -1;
  }

  return 0;
}



#ifdef NAND_FFS_USE_CACHE

/*************************************************************
Function: NAND_FFS_clearCache
Description:
	clear the NAND_FFS block cache
Input:
	cacheNum - the cache number
Output:
	none
Note:
	Called only when the cache is corrupted.
**************************************************************/
void NAND_FFS_clearCache(int cacheNum)
{
  int i;
  int *src;

  #ifdef NAND_FFS_DEBUG
	sprintf(NAND_FFS_DebugString, "[NAND_FFS_clearCache] cache = %d", cacheNum);
	SprintStringLn(NAND_FFS_DebugString);
  #endif

  // check if the cache number is out of bound
  if (cacheNum < 0 || cacheNum >= NAND_FFS_CACHE_BLOCK_NUM)
	return;

  NAND_FFS_CacheStatus[cacheNum]->block = -1;
  NAND_FFS_CacheStatus[cacheNum]->handle = -1;
  NAND_FFS_CacheStatus[cacheNum]->checksum = 0L;
  NAND_FFS_CacheStatus[cacheNum]->lastModTime = 0;
  NAND_FFS_CacheStatus[cacheNum]->flag = 0;

  src = (int *)NAND_FFS_BlockCache[cacheNum];

  for (i = 0; i < NAND_FLASH_BLOCK_SIZE; i += sizeof(int))
	*src++ = 0;

  #ifdef NAND_FFS_DEBUG
	sprintf(NAND_FFS_DebugString, "    DONE");
	SprintStringLn(NAND_FFS_DebugString);
  #endif

  return;
}



/*************************************************************
Function: NAND_FFS_clearAllCache
Description:
	clear all FFS block cache
Input:
	none
Output:
	none
Note:
**************************************************************/
void NAND_FFS_clearAllCache(void)
{
  int i;

  for (i = 0; i < NAND_FFS_CACHE_BLOCK_NUM; i++)
	NAND_FFS_clearCache(i);

  return;
}



/*************************************************************
Function: NAND_FFS_vertifyCache
Description:
	vertify the cache content
Input:
	cacheNum - the cache number
Output:
	0	valid cache content
	-1	invalid cache content
**************************************************************/
int NAND_FFS_vertifyCache(int cacheNum)
{
  unsigned long checksum;

  #ifdef NAND_FFS_DEBUG
	sprintf(NAND_FFS_DebugString, "[NAND_FFS_vertifyCache] cache = %d", cacheNum);
	SprintStringLn(NAND_FFS_DebugString);
  #endif

  // check if the cache is all zeros
  if (NAND_FFS_CacheStatus[cacheNum]->block == 0 && NAND_FFS_CacheStatus[cacheNum]->handle == 0 && NAND_FFS_CacheStatus[cacheNum]->checksum == 0)
  {
	// cache content all zeros, invalid
	#ifdef NAND_FFS_DEBUG
		sprintf(NAND_FFS_DebugString, "    ERR: all zeros");
		SprintStringLn(NAND_FFS_DebugString);
	#endif

	NAND_FFS_Errno = ERROR_INVALID_CACHE;
	return -1;
  }

  // check if the cache number is out of bound
  if (cacheNum < 0 || cacheNum >= NAND_FFS_CACHE_BLOCK_NUM)
  {
	#ifdef NAND_FFS_DEBUG
		sprintf(NAND_FFS_DebugString, "    ERR: invalid cache number");
		SprintStringLn(NAND_FFS_DebugString);
	#endif

	NAND_FFS_Errno = ERROR_INVALID_CACHE;
	return -1;
  }

  // check if the cache block is free
  if (NAND_FFS_CacheStatus[cacheNum]->block == -1)
  {
	#ifdef NAND_FFS_DEBUG
		sprintf(NAND_FFS_DebugString, "    OK: unused cache block");
		SprintStringLn(NAND_FFS_DebugString);
	#endif

	return 0;
  }

  // check if the block is valid
  if (NAND_FFS_checkBlock(NAND_FFS_CacheStatus[cacheNum]->block) == -1)
  {
	#ifdef NAND_FFS_DEBUG
		sprintf(NAND_FFS_DebugString, "    ERR: invalid block %d", NAND_FFS_CacheStatus[cacheNum]->block);
		SprintStringLn(NAND_FFS_DebugString);
	#endif

	// errno set by NAND_FFS_checkBlock()
	return -1;
  }

  // get CRC of the cache block
//  checksum = calcrc32(NAND_FFS_BlockCache[cacheNum], NAND_FLASH_BLOCK_SIZE);
  // modified by chilong 01/24/2002
  checksum = calcrc32(NAND_FFS_BlockCache[cacheNum], NFLASH_FRAME_SIZE);
  checksum = cacheNum;
  if (checksum == NAND_FFS_CacheStatus[cacheNum]->checksum)
  {
	#ifdef NAND_FFS_DEBUG
		sprintf(NAND_FFS_DebugString, "    OK: CRC good 0x%x 0x%x", checksum, NAND_FFS_CacheStatus[cacheNum]->checksum);
		SprintStringLn(NAND_FFS_DebugString);
	#endif

	return 0;
  }
  else
  {
	#ifdef NAND_FFS_DEBUG
		sprintf(NAND_FFS_DebugString, "    ERR: CRC bad 0x%x 0x%x", checksum, NAND_FFS_CacheStatus[cacheNum]->checksum);
		SprintStringLn(NAND_FFS_DebugString);
	#endif

	NAND_FFS_Errno = ERROR_INVALID_CACHE;
	return -1;
  }
}



/*************************************************************
Function: NAND_FFS_flushCache

⌨️ 快捷键说明

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