/*
 * NAND Flash Controller Device Driver
 * Copyright (c) 2009, Intel Corporation and its suppliers.
 *
 * This program is free software; you can redistribute it and/or modify it
 * under the terms and conditions of the GNU General Public License,
 * version 2, as published by the Free Software Foundation.
 *
 * This program is distributed in the hope it will be useful, but WITHOUT
 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
 * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
 * more details.
 *
 * You should have received a copy of the GNU General Public License along with
 * this program; if not, write to the Free Software Foundation, Inc.,
 * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
 *
 */

#include <linux/fs.h>
#include <linux/slab.h>

#include "flash.h"
#include "ffsdefs.h"
#include "lld.h"
#include "lld_nand.h"
#if CMD_DMA
#include "lld_cdma.h"
#endif

#define BLK_FROM_ADDR(addr)  ((u32)(addr >> DeviceInfo.nBitsInBlockDataSize))
#define PAGE_FROM_ADDR(addr, Block)  ((u16)((addr - (u64)Block * \
	DeviceInfo.wBlockDataSize) >> DeviceInfo.nBitsInPageDataSize))

#define IS_SPARE_BLOCK(blk)     (BAD_BLOCK != (pbt[blk] &\
	BAD_BLOCK) && SPARE_BLOCK == (pbt[blk] & SPARE_BLOCK))

#define IS_DATA_BLOCK(blk)      (0 == (pbt[blk] & BAD_BLOCK))

#define IS_DISCARDED_BLOCK(blk) (BAD_BLOCK != (pbt[blk] &\
	BAD_BLOCK) && DISCARD_BLOCK == (pbt[blk] & DISCARD_BLOCK))

#define IS_BAD_BLOCK(blk)       (BAD_BLOCK == (pbt[blk] & BAD_BLOCK))

#if DEBUG_BNDRY
void debug_boundary_lineno_error(int chnl, int limit, int no,
				int lineno, char *filename)
{
	if (chnl >= limit)
		printk(KERN_ERR "Boundary Check Fail value %d >= limit %d, "
		"at  %s:%d. Other info:%d. Aborting...\n",
		chnl, limit, filename, lineno, no);
}
/* static int globalmemsize; */
#endif

static u16 FTL_Cache_If_Hit(u64 dwPageAddr);
static int FTL_Cache_Read(u64 dwPageAddr);
static void FTL_Cache_Read_Page(u8 *pData, u64 dwPageAddr,
				u16 cache_blk);
static void FTL_Cache_Write_Page(u8 *pData, u64 dwPageAddr,
				 u8 cache_blk, u16 flag);
static int FTL_Cache_Write(void);
static void FTL_Calculate_LRU(void);
static u32 FTL_Get_Block_Index(u32 wBlockNum);

static int FTL_Search_Block_Table_IN_Block(u32 BT_Block,
					   u8 BT_Tag, u16 *Page);
static int FTL_Read_Block_Table(void);
static int FTL_Write_Block_Table(int wForce);
static int FTL_Write_Block_Table_Data(void);
static int FTL_Check_Block_Table(int wOldTable);
static int FTL_Static_Wear_Leveling(void);
static u32 FTL_Replace_Block_Table(void);
static int FTL_Write_IN_Progress_Block_Table_Page(void);

static u32 FTL_Get_Page_Num(u64 length);
static u64 FTL_Get_Physical_Block_Addr(u64 blk_addr);

static u32 FTL_Replace_OneBlock(u32 wBlockNum,
				      u32 wReplaceNum);
static u32 FTL_Replace_LWBlock(u32 wBlockNum,
				     int *pGarbageCollect);
static u32 FTL_Replace_MWBlock(void);
static int FTL_Replace_Block(u64 blk_addr);
static int FTL_Adjust_Relative_Erase_Count(u32 Index_of_MAX);

struct device_info_tag DeviceInfo;
struct flash_cache_tag Cache;
static struct spectra_l2_cache_info cache_l2;

static u8 *cache_l2_page_buf;
static u8 *cache_l2_blk_buf;

u8 *g_pBlockTable;
u8 *g_pWearCounter;
u16 *g_pReadCounter;
u32 *g_pBTBlocks;
static u16 g_wBlockTableOffset;
static u32 g_wBlockTableIndex;
static u8 g_cBlockTableStatus;

static u8 *g_pTempBuf;
static u8 *flag_check_blk_table;
static u8 *tmp_buf_search_bt_in_block;
static u8 *spare_buf_search_bt_in_block;
static u8 *spare_buf_bt_search_bt_in_block;
static u8 *tmp_buf1_read_blk_table;
static u8 *tmp_buf2_read_blk_table;
static u8 *flags_static_wear_leveling;
static u8 *tmp_buf_write_blk_table_data;
static u8 *tmp_buf_read_disturbance;

u8 *buf_read_page_main_spare;
u8 *buf_write_page_main_spare;
u8 *buf_read_page_spare;
u8 *buf_get_bad_block;

#if (RESTORE_CACHE_ON_CDMA_CHAIN_FAILURE && CMD_DMA)
struct flash_cache_delta_list_tag int_cache[MAX_CHANS + MAX_DESCS];
struct flash_cache_tag cache_start_copy;
#endif

int g_wNumFreeBlocks;
u8 g_SBDCmdIndex;

static u8 *g_pIPF;
static u8 bt_flag = FIRST_BT_ID;
static u8 bt_block_changed;

static u16 cache_block_to_write;
static u8 last_erased = FIRST_BT_ID;

static u8 GC_Called;
static u8 BT_GC_Called;

#if CMD_DMA
#define COPY_BACK_BUF_NUM 10

static u8 ftl_cmd_cnt;  /* Init value is 0 */
u8 *g_pBTDelta;
u8 *g_pBTDelta_Free;
u8 *g_pBTStartingCopy;
u8 *g_pWearCounterCopy;
u16 *g_pReadCounterCopy;
u8 *g_pBlockTableCopies;
u8 *g_pNextBlockTable;
static u8 *cp_back_buf_copies[COPY_BACK_BUF_NUM];
static int cp_back_buf_idx;

static u8 *g_temp_buf;

#pragma pack(push, 1)
#pragma pack(1)
struct BTableChangesDelta {
	u8 ftl_cmd_cnt;
	u8 ValidFields;
	u16 g_wBlockTableOffset;
	u32 g_wBlockTableIndex;
	u32 BT_Index;
	u32 BT_Entry_Value;
	u32 WC_Index;
	u8 WC_Entry_Value;
	u32 RC_Index;
	u16 RC_Entry_Value;
};

#pragma pack(pop)

struct BTableChangesDelta *p_BTableChangesDelta;
#endif


#define MARK_BLOCK_AS_BAD(blocknode)      (blocknode |= BAD_BLOCK)
#define MARK_BLK_AS_DISCARD(blk)  (blk = (blk & ~SPARE_BLOCK) | DISCARD_BLOCK)

#define FTL_Get_LBAPBA_Table_Mem_Size_Bytes() (DeviceInfo.wDataBlockNum *\
						sizeof(u32))
#define FTL_Get_WearCounter_Table_Mem_Size_Bytes() (DeviceInfo.wDataBlockNum *\
						sizeof(u8))
#define FTL_Get_ReadCounter_Table_Mem_Size_Bytes() (DeviceInfo.wDataBlockNum *\
						sizeof(u16))
#if SUPPORT_LARGE_BLOCKNUM
#define FTL_Get_LBAPBA_Table_Flash_Size_Bytes() (DeviceInfo.wDataBlockNum *\
						sizeof(u8) * 3)
#else
#define FTL_Get_LBAPBA_Table_Flash_Size_Bytes() (DeviceInfo.wDataBlockNum *\
						sizeof(u16))
#endif
#define FTL_Get_WearCounter_Table_Flash_Size_Bytes \
	FTL_Get_WearCounter_Table_Mem_Size_Bytes
#define FTL_Get_ReadCounter_Table_Flash_Size_Bytes \
	FTL_Get_ReadCounter_Table_Mem_Size_Bytes

static u32 FTL_Get_Block_Table_Flash_Size_Bytes(void)
{
	u32 byte_num;

	if (DeviceInfo.MLCDevice) {
		byte_num = FTL_Get_LBAPBA_Table_Flash_Size_Bytes() +
			DeviceInfo.wDataBlockNum * sizeof(u8) +
			DeviceInfo.wDataBlockNum * sizeof(u16);
	} else {
		byte_num = FTL_Get_LBAPBA_Table_Flash_Size_Bytes() +
			DeviceInfo.wDataBlockNum * sizeof(u8);
	}

	byte_num += 4 * sizeof(u8);

	return byte_num;
}

static u16  FTL_Get_Block_Table_Flash_Size_Pages(void)
{
	return (u16)FTL_Get_Page_Num(FTL_Get_Block_Table_Flash_Size_Bytes());
}

static int FTL_Copy_Block_Table_To_Flash(u8 *flashBuf, u32 sizeToTx,
					u32 sizeTxed)
{
	u32 wBytesCopied, blk_tbl_size, wBytes;
	u32 *pbt = (u32 *)g_pBlockTable;

	blk_tbl_size = FTL_Get_LBAPBA_Table_Flash_Size_Bytes();
	for (wBytes = 0;
	(wBytes < sizeToTx) && ((wBytes + sizeTxed) < blk_tbl_size);
	wBytes++) {
#if SUPPORT_LARGE_BLOCKNUM
		flashBuf[wBytes] = (u8)(pbt[(wBytes + sizeTxed) / 3]
		>> (((wBytes + sizeTxed) % 3) ?
		((((wBytes + sizeTxed) % 3) == 2) ? 0 : 8) : 16)) & 0xFF;
#else
		flashBuf[wBytes] = (u8)(pbt[(wBytes + sizeTxed) / 2]
		>> (((wBytes + sizeTxed) % 2) ? 0 : 8)) & 0xFF;
#endif
	}

	sizeTxed = (sizeTxed > blk_tbl_size) ? (sizeTxed - blk_tbl_size) : 0;
	blk_tbl_size = FTL_Get_WearCounter_Table_Flash_Size_Bytes();
	wBytesCopied = wBytes;
	wBytes = ((blk_tbl_size - sizeTxed) > (sizeToTx - wBytesCopied)) ?
		(sizeToTx - wBytesCopied) : (blk_tbl_size - sizeTxed);
	memcpy(flashBuf + wBytesCopied, g_pWearCounter + sizeTxed, wBytes);

	sizeTxed = (sizeTxed > blk_tbl_size) ? (sizeTxed - blk_tbl_size) : 0;

	if (DeviceInfo.MLCDevice) {
		blk_tbl_size = FTL_Get_ReadCounter_Table_Flash_Size_Bytes();
		wBytesCopied += wBytes;
		for (wBytes = 0; ((wBytes + wBytesCopied) < sizeToTx) &&
			((wBytes + sizeTxed) < blk_tbl_size); wBytes++)
			flashBuf[wBytes + wBytesCopied] =
			(g_pReadCounter[(wBytes + sizeTxed) / 2] >>
			(((wBytes + sizeTxed) % 2) ? 0 : 8)) & 0xFF;
	}

	return wBytesCopied + wBytes;
}

static int FTL_Copy_Block_Table_From_Flash(u8 *flashBuf,
				u32 sizeToTx, u32 sizeTxed)
{
	u32 wBytesCopied, blk_tbl_size, wBytes;
	u32 *pbt = (u32 *)g_pBlockTable;

	blk_tbl_size = FTL_Get_LBAPBA_Table_Flash_Size_Bytes();
	for (wBytes = 0; (wBytes < sizeToTx) &&
		((wBytes + sizeTxed) < blk_tbl_size); wBytes++) {
#if SUPPORT_LARGE_BLOCKNUM
		if (!((wBytes + sizeTxed) % 3))
			pbt[(wBytes + sizeTxed) / 3] = 0;
		pbt[(wBytes + sizeTxed) / 3] |=
			(flashBuf[wBytes] << (((wBytes + sizeTxed) % 3) ?
			((((wBytes + sizeTxed) % 3) == 2) ? 0 : 8) : 16));
#else
		if (!((wBytes + sizeTxed) % 2))
			pbt[(wBytes + sizeTxed) / 2] = 0;
		pbt[(wBytes + sizeTxed) / 2] |=
			(flashBuf[wBytes] << (((wBytes + sizeTxed) % 2) ?
			0 : 8));
#endif
	}

	sizeTxed = (sizeTxed > blk_tbl_size) ? (sizeTxed - blk_tbl_size) : 0;
	blk_tbl_size = FTL_Get_WearCounter_Table_Flash_Size_Bytes();
	wBytesCopied = wBytes;
	wBytes = ((blk_tbl_size - sizeTxed) > (sizeToTx - wBytesCopied)) ?
		(sizeToTx - wBytesCopied) : (blk_tbl_size - sizeTxed);
	memcpy(g_pWearCounter + sizeTxed, flashBuf + wBytesCopied, wBytes);
	sizeTxed = (sizeTxed > blk_tbl_size) ? (sizeTxed - blk_tbl_size) : 0;

	if (DeviceInfo.MLCDevice) {
		wBytesCopied += wBytes;
		blk_tbl_size = FTL_Get_ReadCounter_Table_Flash_Size_Bytes();
		for (wBytes = 0; ((wBytes + wBytesCopied) < sizeToTx) &&
			((wBytes + sizeTxed) < blk_tbl_size); wBytes++) {
			if (((wBytes + sizeTxed) % 2))
				g_pReadCounter[(wBytes + sizeTxed) / 2] = 0;
			g_pReadCounter[(wBytes + sizeTxed) / 2] |=
				(flashBuf[wBytes] <<
				(((wBytes + sizeTxed) % 2) ? 0 : 8));
		}
	}

	return wBytesCopied+wBytes;
}

static int FTL_Insert_Block_Table_Signature(u8 *buf, u8 tag)
{
	int i;

	for (i = 0; i < BTSIG_BYTES; i++)
		buf[BTSIG_OFFSET + i] =
		((tag + (i * BTSIG_DELTA) - FIRST_BT_ID) %
		(1 + LAST_BT_ID-FIRST_BT_ID)) + FIRST_BT_ID;

	return PASS;
}

static int FTL_Extract_Block_Table_Tag(u8 *buf, u8 **tagarray)
{
	static u8 tag[BTSIG_BYTES >> 1];
	int i, j, k, tagi, tagtemp, status;

	*tagarray = (u8 *)tag;
	tagi = 0;

	for (i = 0; i < (BTSIG_BYTES - 1); i++) {
		for (j = i + 1; (j < BTSIG_BYTES) &&
			(tagi < (BTSIG_BYTES >> 1)); j++) {
			tagtemp = buf[BTSIG_OFFSET + j] -
				buf[BTSIG_OFFSET + i];
			if (tagtemp && !(tagtemp % BTSIG_DELTA)) {
				tagtemp = (buf[BTSIG_OFFSET + i] +
					(1 + LAST_BT_ID - FIRST_BT_ID) -
					(i * BTSIG_DELTA)) %
					(1 + LAST_BT_ID - FIRST_BT_ID);
				status = FAIL;
				for (k = 0; k < tagi; k++) {
					if (tagtemp == tag[k])
						status = PASS;
				}

				if (status == FAIL) {
					tag[tagi++] = tagtemp;
					i = (j == (i + 1)) ? i + 1 : i;
					j = (j == (i + 1)) ? i + 1 : i;
				}
			}
		}
	}

	return tagi;
}


static int FTL_Execute_SPL_Recovery(void)
{
	u32 j, block, blks;
	u32 *pbt = (u32 *)g_pBlockTable;
	int ret;

	nand_dbg_print(NAND_DBG_TRACE, "%s, Line %d, Function: %s\n",
				__FILE__, __LINE__, __func__);

	blks = DeviceInfo.wSpectraEndBlock - DeviceInfo.wSpectraStartBlock;
	for (j = 0; j <= blks; j++) {
		block = (pbt[j]);
		if (((block & BAD_BLOCK) != BAD_BLOCK) &&
			((block & SPARE_BLOCK) == SPARE_BLOCK)) {
			ret =  GLOB_LLD_Erase_Block(block & ~BAD_BLOCK);
			if (FAIL == ret) {
				nand_dbg_print(NAND_DBG_WARN,
					"NAND Program fail in %s, Line %d, "
					"Function: %s, new Bad Block %d "
					"generated!\n",
					__FILE__, __LINE__, __func__,
					(int)(block & ~BAD_BLOCK));
				MARK_BLOCK_AS_BAD(pbt[j]);
			}
		}
	}

	return PASS;
}

/*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&
* Function:     GLOB_FTL_IdentifyDevice
* Inputs:       pointer to identify data structure
* Outputs:      PASS / FAIL
* Description:  the identify data structure is filled in with
*                   information for the block driver.
*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&*/
int GLOB_FTL_IdentifyDevice(struct spectra_indentfy_dev_tag *dev_data)
{
	nand_dbg_print(NAND_DBG_TRACE, "%s, Line %d, Function: %s\n",
				__FILE__, __LINE__, __func__);

	dev_data->NumBlocks = DeviceInfo.wTotalBlocks;
	dev_data->PagesPerBlock = DeviceInfo.wPagesPerBlock;
	dev_data->PageDataSize = DeviceInfo.wPageDataSize;
	dev_data->wECCBytesPerSector = DeviceInfo.wECCBytesPerSector;
	dev_data->wDataBlockNum = DeviceInfo.wDataBlockNum;

	return PASS;
}

/* ..... */
static int allocate_memory(void)
{
	u32 block_table_size, page_size, block_size, mem_size;
	u32 total_bytes = 0;
	int i;
#if CMD_DMA
	int j;
#endif

	nand_dbg_print(NAND_DBG_TRACE, "%s, Line %d, Function: %s\n",
		__FILE__, __LINE__, __func__);

	page_size = DeviceInfo.wPageSize;
	block_size = DeviceInfo.wPagesPerBlock * DeviceInfo.wPageDataSize;

	block_table_size = DeviceInfo.wDataBlockNum *
		(sizeof(u32) + sizeof(u8) + sizeof(u16));
	block_table_size += (DeviceInfo.wPageDataSize -
		(block_table_size % DeviceInfo.wPageDataSize)) %
		DeviceInfo.wPageDataSize;

	/* Malloc memory for block tables */
	g_pBlockTable = kmalloc(block_table_size, GFP_ATOMIC);
	if (!g_pBlockTable)
		goto block_table_fail;
	memset(g_pBlockTable, 0, block_table_size);
	total_bytes += block_table_size;

	g_pWearCounter = (u8 *)(g_pBlockTable +
		DeviceInfo.wDataBlockNum * sizeof(u32));

	if (DeviceInfo.MLCDevice)
		g_pReadCounter = (u16 *)(g_pBlockTable +
			DeviceInfo.wDataBlockNum *
			(sizeof(u32) + sizeof(u8)));

	/* Malloc memory and init for cache items */
	for (i = 0; i < CACHE_ITEM_NUM; i++) {
		Cache.array[i].address = NAND_CACHE_INIT_ADDR;
		Cache.array[i].use_cnt = 0;
		Cache.array[i].changed = CLEAR;
		Cache.array[i].buf = kmalloc(Cache.cache_item_size,
			GFP_ATOMIC);
		if (!Cache.array[i].buf)
			goto cache_item_fail;
		memset(Cache.array[i].buf, 0, Cache.cache_item_size);
		total_bytes += Cache.cache_item_size;
	}

	/* Malloc memory for IPF */
	g_pIPF = kmalloc(page_size, GFP_ATOMIC);
	if (!g_pIPF)
		goto ipf_fail;
	memset(g_pIPF, 0, page_size);
	total_bytes += page_size;

	/* Malloc memory for data merging during Level2 Cache flush */
	cache_l2_page_buf = kmalloc(page_size, GFP_ATOMIC);
	if (!cache_l2_page_buf)
		goto cache_l2_page_buf_fail;
	memset(cache_l2_page_buf, 0xff, page_size);
	total_bytes += page_size;

	cache_l2_blk_buf = kmalloc(block_size, GFP_ATOMIC);
	if (!cache_l2_blk_buf)
		goto cache_l2_blk_buf_fail;
	memset(cache_l2_blk_buf, 0xff, block_size);
	total_bytes += block_size;

	/* Malloc memory for temp buffer */
	g_pTempBuf = kmalloc(Cache.cache_item_size, GFP_ATOMIC);
	if (!g_pTempBuf)
		goto Temp_buf_fail;
	memset(g_pTempBuf, 0, Cache.cache_item_size);
	total_bytes += Cache.cache_item_size;

	/* Malloc memory for block table blocks */
	mem_size = (1 + LAST_BT_ID - FIRST_BT_ID) * sizeof(u32);
	g_pBTBlocks = kmalloc(mem_size, GFP_ATOMIC);
	if (!g_pBTBlocks)
		goto bt_blocks_fail;
	memset(g_pBTBlocks, 0xff, mem_size);
	total_bytes += mem_size;

	/* Malloc memory for function FTL_Check_Block_Table */
	flag_check_blk_table = kmalloc(DeviceInfo.wDataBlockNum, GFP_ATOMIC);
	if (!flag_check_blk_table)
		goto flag_check_blk_table_fail;
	total_bytes += DeviceInfo.wDataBlockNum;

	/* Malloc memory for function FTL_Search_Block_Table_IN_Block */
	tmp_buf_search_bt_in_block = kmalloc(page_size, GFP_ATOMIC);
	if (!tmp_buf_search_bt_in_block)
		goto tmp_buf_search_bt_in_block_fail;
	memset(tmp_buf_search_bt_in_block, 0xff, page_size);
	total_bytes += page_size;

	mem_size = DeviceInfo.wPageSize - DeviceInfo.wPageDataSize;
	spare_buf_search_bt_in_block = kmalloc(mem_size, GFP_ATOMIC);
	if (!spare_buf_search_bt_in_block)
		goto spare_buf_search_bt_in_block_fail;
	memset(spare_buf_search_bt_in_block, 0xff, mem_size);
	total_bytes += mem_size;

	spare_buf_bt_search_bt_in_block = kmalloc(mem_size, GFP_ATOMIC);
	if (!spare_buf_bt_search_bt_in_block)
		goto spare_buf_bt_search_bt_in_block_fail;
	memset(spare_buf_bt_search_bt_in_block, 0xff, mem_size);
	total_bytes += mem_size;

	/* Malloc memory for function FTL_Read_Block_Table */
	tmp_buf1_read_blk_table = kmalloc(page_size, GFP_ATOMIC);
	if (!tmp_buf1_read_blk_table)
		goto tmp_buf1_read_blk_table_fail;
	memset(tmp_buf1_read_blk_table, 0xff, page_size);
	total_bytes += page_size;

	tmp_buf2_read_blk_table = kmalloc(page_size, GFP_ATOMIC);
	if (!tmp_buf2_read_blk_table)
		goto tmp_buf2_read_blk_table_fail;
	memset(tmp_buf2_read_blk_table, 0xff, page_size);
	total_bytes += page_size;

	/* Malloc memory for function FTL_Static_Wear_Leveling */
	flags_static_wear_leveling = kmalloc(DeviceInfo.wDataBlockNum,
					GFP_ATOMIC);
	if (!flags_static_wear_leveling)
		goto flags_static_wear_leveling_fail;
	total_bytes += DeviceInfo.wDataBlockNum;

	/* Malloc memory for function FTL_Write_Block_Table_Data */
	if (FTL_Get_Block_Table_Flash_Size_Pages() > 3)
		mem_size = FTL_Get_Block_Table_Flash_Size_Bytes() -
				2 * DeviceInfo.wPageSize;
	else
		mem_size = DeviceInfo.wPageSize;
	tmp_buf_write_blk_table_data = kmalloc(mem_size, GFP_ATOMIC);
	if (!tmp_buf_write_blk_table_data)
		goto tmp_buf_write_blk_table_data_fail;
	memset(tmp_buf_write_blk_table_data, 0xff, mem_size);
	total_bytes += mem_size;

	/* Malloc memory for function FTL_Read_Disturbance */
	tmp_buf_read_disturbance = kmalloc(block_size, GFP_ATOMIC);
	if (!tmp_buf_read_disturbance)
		goto tmp_buf_read_disturbance_fail;
	memset(tmp_buf_read_disturbance, 0xff, block_size);
	total_bytes += block_size;

	/* Alloc mem for function NAND_Read_Page_Main_Spare of lld_nand.c */
	buf_read_page_main_spare = kmalloc(DeviceInfo.wPageSize, GFP_ATOMIC);
	if (!buf_read_page_main_spare)
		goto buf_read_page_main_spare_fail;
	total_bytes += DeviceInfo.wPageSize;

	/* Alloc mem for function NAND_Write_Page_Main_Spare of lld_nand.c */
	buf_write_page_main_spare = kmalloc(DeviceInfo.wPageSize, GFP_ATOMIC);
	if (!buf_write_page_main_spare)
		goto buf_write_page_main_spare_fail;
	total_bytes += DeviceInfo.wPageSize;

	/* Alloc mem for function NAND_Read_Page_Spare of lld_nand.c */
	buf_read_page_spare = kmalloc(DeviceInfo.wPageSpareSize, GFP_ATOMIC);
	if (!buf_read_page_spare)
		goto buf_read_page_spare_fail;
	memset(buf_read_page_spare, 0xff, DeviceInfo.wPageSpareSize);
	total_bytes += DeviceInfo.wPageSpareSize;

	/* Alloc mem for function NAND_Get_Bad_Block of lld_nand.c */
	buf_get_bad_block = kmalloc(DeviceInfo.wPageSpareSize, GFP_ATOMIC);
	if (!buf_get_bad_block)
		goto buf_get_bad_block_fail;
	memset(buf_get_bad_block, 0xff, DeviceInfo.wPageSpareSize);
	total_bytes += DeviceInfo.wPageSpareSize;

#if CMD_DMA
	g_temp_buf = kmalloc(block_size, GFP_ATOMIC);
	if (!g_temp_buf)
		goto temp_buf_fail;
	memset(g_temp_buf, 0xff, block_size);
	total_bytes += block_size;

	/* Malloc memory for copy of block table used in CDMA mode */
	g_pBTStartingCopy = kmalloc(block_table_size, GFP_ATOMIC);
	if (!g_pBTStartingCopy)
		goto bt_starting_copy;
	memset(g_pBTStartingCopy, 0, block_table_size);
	total_bytes += block_table_size;

	g_pWearCounterCopy = (u8 *)(g_pBTStartingCopy +
		DeviceInfo.wDataBlockNum * sizeof(u32));

	if (DeviceInfo.MLCDevice)
		g_pReadCounterCopy = (u16 *)(g_pBTStartingCopy +
			DeviceInfo.wDataBlockNum *
			(sizeof(u32) + sizeof(u8)));

	/* Malloc memory for block table copies */
	mem_size = 5 * DeviceInfo.wDataBlockNum * sizeof(u32) +
			5 * DeviceInfo.wDataBlockNum * sizeof(u8);
	if (DeviceInfo.MLCDevice)
		mem_size += 5 * DeviceInfo.wDataBlockNum * sizeof(u16);
	g_pBlockTableCopies = kmalloc(mem_size, GFP_ATOMIC);
	if (!g_pBlockTableCopies)
		goto blk_table_copies_fail;
	memset(g_pBlockTableCopies, 0, mem_size);
	total_bytes += mem_size;
	g_pNextBlockTable = g_pBlockTableCopies;

	/* Malloc memory for Block Table Delta */
	mem_size = MAX_DESCS * sizeof(struct BTableChangesDelta);
	g_pBTDelta = kmalloc(mem_size, GFP_ATOMIC);
	if (!g_pBTDelta)
		goto bt_delta_fail;
	memset(g_pBTDelta, 0, mem_size);
	total_bytes += mem_size;
	g_pBTDelta_Free = g_pBTDelta;

	/* Malloc memory for Copy Back Buffers */
	for (j = 0; j < COPY_BACK_BUF_NUM; j++) {
		cp_back_buf_copies[j] = kmalloc(block_size, GFP_ATOMIC);
		if (!cp_back_buf_copies[j])
			goto cp_back_buf_copies_fail;
		memset(cp_back_buf_copies[j], 0, block_size);
		total_bytes += block_size;
	}
	cp_back_buf_idx = 0;

	/* Malloc memory for pending commands list */
	mem_size = sizeof(struct pending_cmd) * MAX_DESCS;
	info.pcmds = kzalloc(mem_size, GFP_KERNEL);
	if (!info.pcmds)
		goto pending_cmds_buf_fail;
	total_bytes += mem_size;

	/* Malloc memory for CDMA descripter table */
	mem_size = sizeof(struct cdma_descriptor) * MAX_DESCS;
	info.cdma_desc_buf = kzalloc(mem_size, GFP_KERNEL);
	if (!info.cdma_desc_buf)
		goto cdma_desc_buf_fail;
	total_bytes += mem_size;

	/* Malloc memory for Memcpy descripter table */
	mem_size = sizeof(struct memcpy_descriptor) * MAX_DESCS;
	info.memcp_desc_buf = kzalloc(mem_size, GFP_KERNEL);
	if (!info.memcp_desc_buf)
		goto memcp_desc_buf_fail;
	total_bytes += mem_size;
#endif

	nand_dbg_print(NAND_DBG_WARN,
		"Total memory allocated in FTL layer: %d\n", total_bytes);

	return PASS;

#if CMD_DMA
memcp_desc_buf_fail:
	kfree(info.cdma_desc_buf);
cdma_desc_buf_fail:
	kfree(info.pcmds);
pending_cmds_buf_fail:
cp_back_buf_copies_fail:
	j--;
	for (; j >= 0; j--)
		kfree(cp_back_buf_copies[j]);
	kfree(g_pBTDelta);
bt_delta_fail:
	kfree(g_pBlockTableCopies);
blk_table_copies_fail:
	kfree(g_pBTStartingCopy);
bt_starting_copy:
	kfree(g_temp_buf);
temp_buf_fail:
	kfree(buf_get_bad_block);
#endif

buf_get_bad_block_fail:
	kfree(buf_read_page_spare);
buf_read_page_spare_fail:
	kfree(buf_write_page_main_spare);
buf_write_page_main_spare_fail:
	kfree(buf_read_page_main_spare);
buf_read_page_main_spare_fail:
	kfree(tmp_buf_read_disturbance);
tmp_buf_read_disturbance_fail:
	kfree(tmp_buf_write_blk_table_data);
tmp_buf_write_blk_table_data_fail:
	kfree(flags_static_wear_leveling);
flags_static_wear_leveling_fail:
	kfree(tmp_buf2_read_blk_table);
tmp_buf2_read_blk_table_fail:
	kfree(tmp_buf1_read_blk_table);
tmp_buf1_read_blk_table_fail:
	kfree(spare_buf_bt_search_bt_in_block);
spare_buf_bt_search_bt_in_block_fail:
	kfree(spare_buf_search_bt_in_block);
spare_buf_search_bt_in_block_fail:
	kfree(tmp_buf_search_bt_in_block);
tmp_buf_search_bt_in_block_fail:
	kfree(flag_check_blk_table);
flag_check_blk_table_fail:
	kfree(g_pBTBlocks);
bt_blocks_fail:
	kfree(g_pTempBuf);
Temp_buf_fail:
	kfree(cache_l2_blk_buf);
cache_l2_blk_buf_fail:
	kfree(cache_l2_page_buf);
cache_l2_page_buf_fail:
	kfree(g_pIPF);
ipf_fail:
cache_item_fail:
	i--;
	for (; i >= 0; i--)
		kfree(Cache.array[i].buf);
	kfree(g_pBlockTable);
block_table_fail:
	printk(KERN_ERR "Failed to kmalloc memory in %s Line %d.\n",
		__FILE__, __LINE__);

	return -ENOMEM;
}

/* .... */
static int free_memory(void)
{
	int i;

#if CMD_DMA
	kfree(info.memcp_desc_buf);
	kfree(info.cdma_desc_buf);
	kfree(info.pcmds);
	for (i = COPY_BACK_BUF_NUM - 1; i >= 0; i--)
		kfree(cp_back_buf_copies[i]);
	kfree(g_pBTDelta);
	kfree(g_pBlockTableCopies);
	kfree(g_pBTStartingCopy);
	kfree(g_temp_buf);
	kfree(buf_get_bad_block);
#endif
	kfree(buf_read_page_spare);
	kfree(buf_write_page_main_spare);
	kfree(buf_read_page_main_spare);
	kfree(tmp_buf_read_disturbance);
	kfree(tmp_buf_write_blk_table_data);
	kfree(flags_static_wear_leveling);
	kfree(tmp_buf2_read_blk_table);
	kfree(tmp_buf1_read_blk_table);
	kfree(spare_buf_bt_search_bt_in_block);
	kfree(spare_buf_search_bt_in_block);
	kfree(tmp_buf_search_bt_in_block);
	kfree(flag_check_blk_table);
	kfree(g_pBTBlocks);
	kfree(g_pTempBuf);
	kfree(g_pIPF);
	for (i = CACHE_ITEM_NUM - 1; i >= 0; i--)
		kfree(Cache.array[i].buf);
	kfree(g_pBlockTable);

	return 0;
}

static void dump_cache_l2_table(void)
{
	struct list_head *p;
	struct spectra_l2_cache_list *pnd;
	int n;

	n = 0;
	list_for_each(p, &cache_l2.table.list) {
		pnd = list_entry(p, struct spectra_l2_cache_list, list);
		nand_dbg_print(NAND_DBG_WARN, "dump_cache_l2_table node: %d, logical_blk_num: %d\n", n, pnd->logical_blk_num);
/*
		for (i = 0; i < DeviceInfo.wPagesPerBlock; i++) {
			if (pnd->pages_array[i] != MAX_U32_VALUE)
				nand_dbg_print(NAND_DBG_WARN, "    pages_array[%d]: 0x%x\n", i, pnd->pages_array[i]);
		}
*/
		n++;
	}
}

/*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&
* Function:     GLOB_FTL_Init
* Inputs:       none
* Outputs:      PASS=0 / FAIL=1
* Description:  allocates the memory for cache array,
*               important data structures
*               clears the cache array
*               reads the block table from flash into array
*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&*/
int GLOB_FTL_Init(void)
{
	int i;

	nand_dbg_print(NAND_DBG_TRACE, "%s, Line %d, Function: %s\n",
		__FILE__, __LINE__, __func__);

	Cache.pages_per_item = 1;
	Cache.cache_item_size = 1 * DeviceInfo.wPageDataSize;

	if (allocate_memory() != PASS)
		return FAIL;

#if CMD_DMA
#if RESTORE_CACHE_ON_CDMA_CHAIN_FAILURE
	memcpy((void *)&cache_start_copy, (void *)&Cache,
		sizeof(struct flash_cache_tag));
	memset((void *)&int_cache, -1,
		sizeof(struct flash_cache_delta_list_tag) *
		(MAX_CHANS + MAX_DESCS));
#endif
	ftl_cmd_cnt = 0;
#endif

	if (FTL_Read_Block_Table() != PASS)
		return FAIL;

	/* Init the Level2 Cache data structure */
	for (i = 0; i < BLK_NUM_FOR_L2_CACHE; i++)
		cache_l2.blk_array[i] = MAX_U32_VALUE;
	cache_l2.cur_blk_idx = 0;
	cache_l2.cur_page_num = 0;
	INIT_LIST_HEAD(&cache_l2.table.list);
	cache_l2.table.logical_blk_num = MAX_U32_VALUE;

	dump_cache_l2_table();

	return 0;
}


#if CMD_DMA
#if 0
static void save_blk_table_changes(u16 idx)
{
	u8 ftl_cmd;
	u32 *pbt = (u32 *)g_pBTStartingCopy;

#if RESTORE_CACHE_ON_CDMA_CHAIN_FAILURE
	u16 id;
	u8 cache_blks;

	id = idx - MAX_CHANS;
	if (int_cache[id].item != -1) {
		cache_blks = int_cache[id].item;
		cache_start_copy.array[cache_blks].address =
			int_cache[id].cache.address;
		cache_start_copy.array[cache_blks].changed =
			int_cache[id].cache.changed;
	}
#endif

	ftl_cmd = p_BTableChangesDelta->ftl_cmd_cnt;

	while (ftl_cmd <= PendingCMD[idx].Tag) {
		if (p_BTableChangesDelta->ValidFields == 0x01) {
			g_wBlockTableOffset =
				p_BTableChangesDelta->g_wBlockTableOffset;
		} else if (p_BTableChangesDelta->ValidFields == 0x0C) {
			pbt[p_BTableChangesDelta->BT_Index] =
				p_BTableChangesDelta->BT_Entry_Value;
			debug_boundary_error(((
				p_BTableChangesDelta->BT_Index)),
				DeviceInfo.wDataBlockNum, 0);
		} else if (p_BTableChangesDelta->ValidFields == 0x03) {
			g_wBlockTableOffset =
				p_BTableChangesDelta->g_wBlockTableOffset;
			g_wBlockTableIndex =
				p_BTableChangesDelta->g_wBlockTableIndex;
		} else if (p_BTableChangesDelta->ValidFields == 0x30) {
			g_pWearCounterCopy[p_BTableChangesDelta->WC_Index] =
				p_BTableChangesDelta->WC_Entry_Value;
		} else if ((DeviceInfo.MLCDevice) &&
			(p_BTableChangesDelta->ValidFields == 0xC0)) {
			g_pReadCounterCopy[p_BTableChangesDelta->RC_Index] =
				p_BTableChangesDelta->RC_Entry_Value;
			nand_dbg_print(NAND_DBG_DEBUG,
				"In event status setting read counter "
				"GLOB_ftl_cmd_cnt %u Count %u Index %u\n",
				ftl_cmd,
				p_BTableChangesDelta->RC_Entry_Value,
				(unsigned int)p_BTableChangesDelta->RC_Index);
		} else {
			nand_dbg_print(NAND_DBG_DEBUG,
				"This should never occur \n");
		}
		p_BTableChangesDelta += 1;
		ftl_cmd = p_BTableChangesDelta->ftl_cmd_cnt;
	}
}

static void discard_cmds(u16 n)
{
	u32 *pbt = (u32 *)g_pBTStartingCopy;
	u8 ftl_cmd;
	unsigned long k;
#if RESTORE_CACHE_ON_CDMA_CHAIN_FAILURE
	u8 cache_blks;
	u16 id;
#endif

	if ((PendingCMD[n].CMD == WRITE_MAIN_CMD) ||
		(PendingCMD[n].CMD == WRITE_MAIN_SPARE_CMD)) {
		for (k = 0; k < DeviceInfo.wDataBlockNum; k++) {
			if (PendingCMD[n].Block == (pbt[k] & (~BAD_BLOCK)))
				MARK_BLK_AS_DISCARD(pbt[k]);
		}
	}

	ftl_cmd = p_BTableChangesDelta->ftl_cmd_cnt;
	while (ftl_cmd <= PendingCMD[n].Tag) {
		p_BTableChangesDelta += 1;
		ftl_cmd = p_BTableChangesDelta->ftl_cmd_cnt;
	}

#if RESTORE_CACHE_ON_CDMA_CHAIN_FAILURE
	id = n - MAX_CHANS;

	if (int_cache[id].item != -1) {
		cache_blks = int_cache[id].item;
		if (PendingCMD[n].CMD == MEMCOPY_CMD) {
			if ((cache_start_copy.array[cache_blks].buf <=
				PendingCMD[n].DataDestAddr) &&
				((cache_start_copy.array[cache_blks].buf +
				Cache.cache_item_size) >
				PendingCMD[n].DataDestAddr)) {
				cache_start_copy.array[cache_blks].address =
						NAND_CACHE_INIT_ADDR;
				cache_start_copy.array[cache_blks].use_cnt =
								0;
				cache_start_copy.array[cache_blks].changed =
								CLEAR;
			}
		} else {
			cache_start_copy.array[cache_blks].address =
					int_cache[id].cache.address;
			cache_start_copy.array[cache_blks].changed =
					int_cache[id].cache.changed;
		}
	}
#endif
}

static void process_cmd_pass(int *first_failed_cmd, u16 idx)
{
	if (0 == *first_failed_cmd)
		save_blk_table_changes(idx);
	else
		discard_cmds(idx);
}

static void process_cmd_fail_abort(int *first_failed_cmd,
				u16 idx, int event)
{
	u32 *pbt = (u32 *)g_pBTStartingCopy;
	u8 ftl_cmd;
	unsigned long i;
	int erase_fail, program_fail;
#if RESTORE_CACHE_ON_CDMA_CHAIN_FAILURE
	u8 cache_blks;
	u16 id;
#endif

	if (0 == *first_failed_cmd)
		*first_failed_cmd = PendingCMD[idx].SBDCmdIndex;

	nand_dbg_print(NAND_DBG_DEBUG, "Uncorrectable error has occured "
		"while executing %u Command %u accesing Block %u\n",
		(unsigned int)p_BTableChangesDelta->ftl_cmd_cnt,
		PendingCMD[idx].CMD,
		(unsigned int)PendingCMD[idx].Block);

	ftl_cmd = p_BTableChangesDelta->ftl_cmd_cnt;
	while (ftl_cmd <= PendingCMD[idx].Tag) {
		p_BTableChangesDelta += 1;
		ftl_cmd = p_BTableChangesDelta->ftl_cmd_cnt;
	}

#if RESTORE_CACHE_ON_CDMA_CHAIN_FAILURE
	id = idx - MAX_CHANS;

	if (int_cache[id].item != -1) {
		cache_blks = int_cache[id].item;
		if ((PendingCMD[idx].CMD == WRITE_MAIN_CMD)) {
			cache_start_copy.array[cache_blks].address =
					int_cache[id].cache.address;
			cache_start_copy.array[cache_blks].changed = SET;
		} else if ((PendingCMD[idx].CMD == READ_MAIN_CMD)) {
			cache_start_copy.array[cache_blks].address =
				NAND_CACHE_INIT_ADDR;
			cache_start_copy.array[cache_blks].use_cnt = 0;
			cache_start_copy.array[cache_blks].changed =
							CLEAR;
		} else if (PendingCMD[idx].CMD == ERASE_CMD) {
			/* ? */
		} else if (PendingCMD[idx].CMD == MEMCOPY_CMD) {
			/* ? */
		}
	}
#endif

	erase_fail = (event == EVENT_ERASE_FAILURE) &&
			(PendingCMD[idx].CMD == ERASE_CMD);

	program_fail = (event == EVENT_PROGRAM_FAILURE) &&
			((PendingCMD[idx].CMD == WRITE_MAIN_CMD) ||
			(PendingCMD[idx].CMD == WRITE_MAIN_SPARE_CMD));

	if (erase_fail || program_fail) {
		for (i = 0; i < DeviceInfo.wDataBlockNum; i++) {
			if (PendingCMD[idx].Block ==
				(pbt[i] & (~BAD_BLOCK)))
				MARK_BLOCK_AS_BAD(pbt[i]);
		}
	}
}

static void process_cmd(int *first_failed_cmd, u16 idx, int event)
{
	u8 ftl_cmd;
	int cmd_match = 0;

	if (p_BTableChangesDelta->ftl_cmd_cnt == PendingCMD[idx].Tag)
		cmd_match = 1;

	if (PendingCMD[idx].Status == CMD_PASS) {
		process_cmd_pass(first_failed_cmd, idx);
	} else if ((PendingCMD[idx].Status == CMD_FAIL) ||
			(PendingCMD[idx].Status == CMD_ABORT)) {
		process_cmd_fail_abort(first_failed_cmd, idx, event);
	} else if ((PendingCMD[idx].Status == CMD_NOT_DONE) &&
					PendingCMD[idx].Tag) {
		nand_dbg_print(NAND_DBG_DEBUG,
			" Command no. %hu is not executed\n",
			(unsigned int)PendingCMD[idx].Tag);
		ftl_cmd = p_BTableChangesDelta->ftl_cmd_cnt;
		while (ftl_cmd <= PendingCMD[idx].Tag) {
			p_BTableChangesDelta += 1;
			ftl_cmd = p_BTableChangesDelta->ftl_cmd_cnt;
		}
	}
}
#endif

static void process_cmd(int *first_failed_cmd, u16 idx, int event)
{
	printk(KERN_ERR "temporary workaround function. "
		"Should not be called! \n");
}

/*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&
* Function:    	GLOB_FTL_Event_Status
* Inputs:       none
* Outputs:      Event Code
* Description:	It is called by SBD after hardware interrupt signalling
*               completion of commands chain
*               It does following things
*               get event status from LLD
*               analyze command chain status
*               determine last command executed
*               analyze results
*               rebuild the block table in case of uncorrectable error
*               return event code
*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&*/
int GLOB_FTL_Event_Status(int *first_failed_cmd)
{
	int event_code = PASS;
	u16 i_P;

	nand_dbg_print(NAND_DBG_TRACE, "%s, Line %d, Function: %s\n",
		__FILE__, __LINE__, __func__);

	*first_failed_cmd = 0;

	event_code = GLOB_LLD_Event_Status();

	switch (event_code) {
	case EVENT_PASS:
		nand_dbg_print(NAND_DBG_DEBUG, "Handling EVENT_PASS\n");
		break;
	case EVENT_UNCORRECTABLE_DATA_ERROR:
		nand_dbg_print(NAND_DBG_DEBUG, "Handling Uncorrectable ECC!\n");
		break;
	case EVENT_PROGRAM_FAILURE:
	case EVENT_ERASE_FAILURE:
		nand_dbg_print(NAND_DBG_WARN, "Handling Ugly case. "
			"Event code: 0x%x\n", event_code);
		p_BTableChangesDelta =
			(struct BTableChangesDelta *)g_pBTDelta;
		for (i_P = MAX_CHANS; i_P < (ftl_cmd_cnt + MAX_CHANS);
				i_P++)
			process_cmd(first_failed_cmd, i_P, event_code);
		memcpy(g_pBlockTable, g_pBTStartingCopy,
			DeviceInfo.wDataBlockNum * sizeof(u32));
		memcpy(g_pWearCounter, g_pWearCounterCopy,
			DeviceInfo.wDataBlockNum * sizeof(u8));
		if (DeviceInfo.MLCDevice)
			memcpy(g_pReadCounter, g_pReadCounterCopy,
				DeviceInfo.wDataBlockNum * sizeof(u16));

#if RESTORE_CACHE_ON_CDMA_CHAIN_FAILURE
		memcpy((void *)&Cache, (void *)&cache_start_copy,
			sizeof(struct flash_cache_tag));
		memset((void *)&int_cache, -1,
			sizeof(struct flash_cache_delta_list_tag) *
			(MAX_DESCS + MAX_CHANS));
#endif
		break;
	default:
		nand_dbg_print(NAND_DBG_WARN,
			"Handling unexpected event code - 0x%x\n",
			event_code);
		event_code = ERR;
		break;
	}

	memcpy(g_pBTStartingCopy, g_pBlockTable,
		DeviceInfo.wDataBlockNum * sizeof(u32));
	memcpy(g_pWearCounterCopy, g_pWearCounter,
		DeviceInfo.wDataBlockNum * sizeof(u8));
	if (DeviceInfo.MLCDevice)
		memcpy(g_pReadCounterCopy, g_pReadCounter,
			DeviceInfo.wDataBlockNum * sizeof(u16));

	g_pBTDelta_Free = g_pBTDelta;
	ftl_cmd_cnt = 0;
	g_pNextBlockTable = g_pBlockTableCopies;
	cp_back_buf_idx = 0;

#if RESTORE_CACHE_ON_CDMA_CHAIN_FAILURE
	memcpy((void *)&cache_start_copy, (void *)&Cache,
		sizeof(struct flash_cache_tag));
	memset((void *)&int_cache, -1,
		sizeof(struct flash_cache_delta_list_tag) *
		(MAX_DESCS + MAX_CHANS));
#endif

	return event_code;
}

/*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&
* Function:     glob_ftl_execute_cmds
* Inputs:       none
* Outputs:      none
* Description:  pass thru to LLD
***************************************************************/
u16 glob_ftl_execute_cmds(void)
{
	nand_dbg_print(NAND_DBG_TRACE,
		"glob_ftl_execute_cmds: ftl_cmd_cnt %u\n",
		(unsigned int)ftl_cmd_cnt);
	g_SBDCmdIndex = 0;
	return glob_lld_execute_cmds();
}

#endif

#if !CMD_DMA
/*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&
* Function:     GLOB_FTL_Read Immediate
* Inputs:         pointer to data
*                     address of data
* Outputs:      PASS / FAIL
* Description:  Reads one page of data into RAM directly from flash without
*       using or disturbing cache.It is assumed this function is called
*       with CMD-DMA disabled.
*****************************************************************/
int GLOB_FTL_Read_Immediate(u8 *read_data, u64 addr)
{
	int wResult = FAIL;
	u32 Block;
	u16 Page;
	u32 phy_blk;
	u32 *pbt = (u32 *)g_pBlockTable;

	nand_dbg_print(NAND_DBG_TRACE, "%s, Line %d, Function: %s\n",
		__FILE__, __LINE__, __func__);

	Block = BLK_FROM_ADDR(addr);
	Page = PAGE_FROM_ADDR(addr, Block);

	if (!IS_SPARE_BLOCK(Block))
		return FAIL;

	phy_blk = pbt[Block];
	wResult = GLOB_LLD_Read_Page_Main(read_data, phy_blk, Page, 1);

	if (DeviceInfo.MLCDevice) {
		g_pReadCounter[phy_blk - DeviceInfo.wSpectraStartBlock]++;
		if (g_pReadCounter[phy_blk - DeviceInfo.wSpectraStartBlock]
			>= MAX_READ_COUNTER)
			FTL_Read_Disturbance(phy_blk);
		if (g_cBlockTableStatus != IN_PROGRESS_BLOCK_TABLE) {
			g_cBlockTableStatus = IN_PROGRESS_BLOCK_TABLE;
			FTL_Write_IN_Progress_Block_Table_Page();
		}
	}

	return wResult;
}
#endif

#ifdef SUPPORT_BIG_ENDIAN
/*********************************************************************
* Function:     FTL_Invert_Block_Table
* Inputs:       none
* Outputs:      none
* Description:  Re-format the block table in ram based on BIG_ENDIAN and
*                     LARGE_BLOCKNUM if necessary
**********************************************************************/
static void FTL_Invert_Block_Table(void)
{
	u32 i;
	u32 *pbt = (u32 *)g_pBlockTable;

	nand_dbg_print(NAND_DBG_TRACE, "%s, Line %d, Function: %s\n",
		__FILE__, __LINE__, __func__);

#ifdef SUPPORT_LARGE_BLOCKNUM
	for (i = 0; i < DeviceInfo.wDataBlockNum; i++) {
		pbt[i] = INVERTUINT32(pbt[i]);
		g_pWearCounter[i] = INVERTUINT32(g_pWearCounter[i]);
	}
#else
	for (i = 0; i < DeviceInfo.wDataBlockNum; i++) {
		pbt[i] = INVERTUINT16(pbt[i]);
		g_pWearCounter[i] = INVERTUINT16(g_pWearCounter[i]);
	}
#endif
}
#endif

/*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&
* Function:     GLOB_FTL_Flash_Init
* Inputs:       none
* Outputs:      PASS=0 / FAIL=0x01 (based on read ID)
* Description:  The flash controller is initialized
*               The flash device is reset
*               Perform a flash READ ID command to confirm that a
*                   valid device is attached and active.
*                   The DeviceInfo structure gets filled in
*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&*/
int GLOB_FTL_Flash_Init(void)
{
	int status = FAIL;

	nand_dbg_print(NAND_DBG_TRACE, "%s, Line %d, Function: %s\n",
		__FILE__, __LINE__, __func__);

	g_SBDCmdIndex = 0;

	GLOB_LLD_Flash_Init();

	status = GLOB_LLD_Read_Device_ID();

	return status;
}

/*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&
* Inputs:       none
* Outputs:      PASS=0 / FAIL=0x01 (based on read ID)
* Description:  The flash controller is released
*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&*/
int GLOB_FTL_Flash_Release(void)
{
	nand_dbg_print(NAND_DBG_TRACE, "%s, Line %d, Function: %s\n",
		__FILE__, __LINE__, __func__);

	return GLOB_LLD_Flash_Release();
}


/*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&
* Function:     GLOB_FTL_Cache_Release
* Inputs:       none
* Outputs:      none
* Description:  release all allocated memory in GLOB_FTL_Init
*               (allocated in GLOB_FTL_Init)
*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&*/
void GLOB_FTL_Cache_Release(void)
{
	nand_dbg_print(NAND_DBG_TRACE, "%s, Line %d, Function: %s\n",
			       __FILE__, __LINE__, __func__);

	free_memory();
}

/*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&
* Function:     FTL_Cache_If_Hit
* Inputs:       Page Address
* Outputs:      Block number/UNHIT BLOCK
* Description:  Determines if the addressed page is in cache
*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&*/
static u16 FTL_Cache_If_Hit(u64 page_addr)
{
	u16 item;
	u64 addr;
	int i;

	nand_dbg_print(NAND_DBG_TRACE, "%s, Line %d, Function: %s\n",
		__FILE__, __LINE__, __func__);

	item = UNHIT_CACHE_ITEM;
	for (i = 0; i < CACHE_ITEM_NUM; i++) {
		addr = Cache.array[i].address;
		if ((page_addr >= addr) &&
			(page_addr < (addr + Cache.cache_item_size))) {
			item = i;
			break;
		}
	}

	return item;
}

/*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&
* Function:     FTL_Calculate_LRU
* Inputs:       None
* Outputs:      None
* Description:  Calculate the least recently block in a cache and record its
*               index in LRU field.
*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&*/
static void FTL_Calculate_LRU(void)
{
	u16 i, bCurrentLRU, bTempCount;

	nand_dbg_print(NAND_DBG_TRACE, "%s, Line %d, Function: %s\n",
		__FILE__, __LINE__, __func__);

	bCurrentLRU = 0;
	bTempCount = MAX_WORD_VALUE;

	for (i = 0; i < CACHE_ITEM_NUM; i++) {
		if (Cache.array[i].use_cnt < bTempCount) {
			bCurrentLRU = i;
			bTempCount = Cache.array[i].use_cnt;
		}
	}

	Cache.LRU = bCurrentLRU;
}

/*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&
* Function:     FTL_Cache_Read_Page
* Inputs:       pointer to read buffer, logical address and cache item number
* Outputs:      None
* Description:  Read the page from the cached block addressed by blocknumber
*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&*/
static void FTL_Cache_Read_Page(u8 *data_buf, u64 logic_addr, u16 cache_item)
{
	u8 *start_addr;

	nand_dbg_print(NAND_DBG_TRACE, "%s, Line %d, Function: %s\n",
		__FILE__, __LINE__, __func__);

	start_addr = Cache.array[cache_item].buf;
	start_addr += (u32)(((logic_addr - Cache.array[cache_item].address) >>
		DeviceInfo.nBitsInPageDataSize) * DeviceInfo.wPageDataSize);

#if CMD_DMA
	GLOB_LLD_MemCopy_CMD(data_buf, start_addr,
			DeviceInfo.wPageDataSize, 0);
	ftl_cmd_cnt++;
#else
	memcpy(data_buf, start_addr, DeviceInfo.wPageDataSize);
#endif

	if (Cache.array[cache_item].use_cnt < MAX_WORD_VALUE)
		Cache.array[cache_item].use_cnt++;
}

/*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&
* Function:     FTL_Cache_Read_All
* Inputs:       pointer to read buffer,block address
* Outputs:      PASS=0 / FAIL =1
* Description:  It reads pages in cache
*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&*/
static int FTL_Cache_Read_All(u8 *pData, u64 phy_addr)
{
	int wResult = PASS;
	u32 Block;
	u32 lba;
	u16 Page;
	u16 PageCount;
	u32 *pbt = (u32 *)g_pBlockTable;
	u32 i;

	Block = BLK_FROM_ADDR(phy_addr);
	Page = PAGE_FROM_ADDR(phy_addr, Block);
	PageCount = Cache.pages_per_item;

	nand_dbg_print(NAND_DBG_DEBUG,
			"%s, Line %d, Function: %s, Block: 0x%x\n",
			__FILE__, __LINE__, __func__, Block);

	lba = 0xffffffff;
	for (i = 0; i < DeviceInfo.wDataBlockNum; i++) {
		if ((pbt[i] & (~BAD_BLOCK)) == Block) {
			lba = i;
			if (IS_SPARE_BLOCK(i) || IS_BAD_BLOCK(i) ||
				IS_DISCARDED_BLOCK(i)) {
				/* Add by yunpeng -2008.12.3 */
#if CMD_DMA
				GLOB_LLD_MemCopy_CMD(pData, g_temp_buf,
				PageCount * DeviceInfo.wPageDataSize, 0);
				ftl_cmd_cnt++;
#else
				memset(pData, 0xFF,
					PageCount * DeviceInfo.wPageDataSize);
#endif
				return wResult;
			} else {
				continue; /* break ?? */
			}
		}
	}

	if (0xffffffff == lba)
		printk(KERN_ERR "FTL_Cache_Read_All: Block is not found in BT\n");

#if CMD_DMA
	wResult = GLOB_LLD_Read_Page_Main_cdma(pData, Block, Page,
			PageCount, LLD_CMD_FLAG_MODE_CDMA);
	if (DeviceInfo.MLCDevice) {
		g_pReadCounter[Block - DeviceInfo.wSpectraStartBlock]++;
		nand_dbg_print(NAND_DBG_DEBUG,
			       "Read Counter modified in ftl_cmd_cnt %u"
				" Block %u Counter%u\n",
			       ftl_cmd_cnt, (unsigned int)Block,
			       g_pReadCounter[Block -
			       DeviceInfo.wSpectraStartBlock]);

		p_BTableChangesDelta =
			(struct BTableChangesDelta *)g_pBTDelta_Free;
		g_pBTDelta_Free += sizeof(struct BTableChangesDelta);
		p_BTableChangesDelta->ftl_cmd_cnt = ftl_cmd_cnt;
		p_BTableChangesDelta->RC_Index =
			Block - DeviceInfo.wSpectraStartBlock;
		p_BTableChangesDelta->RC_Entry_Value =
			g_pReadCounter[Block - DeviceInfo.wSpectraStartBlock];
		p_BTableChangesDelta->ValidFields = 0xC0;

		ftl_cmd_cnt++;

		if (g_pReadCounter[Block - DeviceInfo.wSpectraStartBlock] >=
		    MAX_READ_COUNTER)
			FTL_Read_Disturbance(Block);
		if (g_cBlockTableStatus != IN_PROGRESS_BLOCK_TABLE) {
			g_cBlockTableStatus = IN_PROGRESS_BLOCK_TABLE;
			FTL_Write_IN_Progress_Block_Table_Page();
		}
	} else {
		ftl_cmd_cnt++;
	}
#else
	wResult = GLOB_LLD_Read_Page_Main(pData, Block, Page, PageCount);
	if (wResult == FAIL)
		return wResult;

	if (DeviceInfo.MLCDevice) {
		g_pReadCounter[Block - DeviceInfo.wSpectraStartBlock]++;
		if (g_pReadCounter[Block - DeviceInfo.wSpectraStartBlock] >=
						MAX_READ_COUNTER)
			FTL_Read_Disturbance(Block);
		if (g_cBlockTableStatus != IN_PROGRESS_BLOCK_TABLE) {
			g_cBlockTableStatus = IN_PROGRESS_BLOCK_TABLE;
			FTL_Write_IN_Progress_Block_Table_Page();
		}
	}
#endif
	return wResult;
}

/*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&
* Function:     FTL_Cache_Write_All
* Inputs:       pointer to cache in sys memory
*               address of free block in flash
* Outputs:      PASS=0 / FAIL=1
* Description:  writes all the pages of the block in cache to flash
*
*               NOTE:need to make sure this works ok when cache is limited
*               to a partial block. This is where copy-back would be
*               activated.  This would require knowing which pages in the
*               cached block are clean/dirty.Right now we only know if
*               the whole block is clean/dirty.
*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&*/
static int FTL_Cache_Write_All(u8 *pData, u64 blk_addr)
{
	u16 wResult = PASS;
	u32 Block;
	u16 Page;
	u16 PageCount;

	nand_dbg_print(NAND_DBG_TRACE, "%s, Line %d, Function: %s\n",
			       __FILE__, __LINE__, __func__);

	nand_dbg_print(NAND_DBG_DEBUG, "This block %d going to be written "
		"on %d\n", cache_block_to_write,
		(u32)(blk_addr >> DeviceInfo.nBitsInBlockDataSize));

	Block = BLK_FROM_ADDR(blk_addr);
	Page = PAGE_FROM_ADDR(blk_addr, Block);
	PageCount = Cache.pages_per_item;

#if CMD_DMA
	if (FAIL == GLOB_LLD_Write_Page_Main_cdma(pData,
					Block, Page, PageCount)) {
		nand_dbg_print(NAND_DBG_WARN,
			"NAND Program fail in %s, Line %d, "
			"Function: %s, new Bad Block %d generated! "
			"Need Bad Block replacing.\n",
			__FILE__, __LINE__, __func__, Block);
		wResult = FAIL;
	}
	ftl_cmd_cnt++;
#else
	if (FAIL == GLOB_LLD_Write_Page_Main(pData, Block, Page, PageCount)) {
		nand_dbg_print(NAND_DBG_WARN, "NAND Program fail in %s,"
			" Line %d, Function %s, new Bad Block %d generated!"
			"Need Bad Block replacing.\n",
			__FILE__, __LINE__, __func__, Block);
		wResult = FAIL;
	}
#endif
	return wResult;
}

/*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&
* Function:     FTL_Copy_Block
* Inputs:       source block address
*               Destination block address
* Outputs:      PASS=0 / FAIL=1
* Description:  used only for static wear leveling to move the block
*               containing static data to new blocks(more worn)
*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&*/
int FTL_Copy_Block(u64 old_blk_addr, u64 blk_addr)
{
	int i, r1, r2, wResult = PASS;

	nand_dbg_print(NAND_DBG_TRACE, "%s, Line %d, Function: %s\n",
		__FILE__, __LINE__, __func__);

	for (i = 0; i < DeviceInfo.wPagesPerBlock; i += Cache.pages_per_item) {
		r1 = FTL_Cache_Read_All(g_pTempBuf, old_blk_addr +
					i * DeviceInfo.wPageDataSize);
		r2 = FTL_Cache_Write_All(g_pTempBuf, blk_addr +
					i * DeviceInfo.wPageDataSize);
		if ((ERR == r1) || (FAIL == r2)) {
			wResult = FAIL;
			break;
		}
	}

	return wResult;
}

/* Search the block table to find out the least wear block and then return it */
static u32 find_least_worn_blk_for_l2_cache(void)
{
	int i;
	u32 *pbt = (u32 *)g_pBlockTable;
	u8 least_wear_cnt = MAX_BYTE_VALUE;
	u32 least_wear_blk_idx = MAX_U32_VALUE;
	u32 phy_idx;

	for (i = 0; i < DeviceInfo.wDataBlockNum; i++) {
		if (IS_SPARE_BLOCK(i)) {
			phy_idx = (u32)((~BAD_BLOCK) & pbt[i]);
			if (phy_idx > DeviceInfo.wSpectraEndBlock)
				printk(KERN_ERR "find_least_worn_blk_for_l2_cache: "
					"Too big phy block num (%d)\n", phy_idx);
			if (g_pWearCounter[phy_idx -DeviceInfo.wSpectraStartBlock] < least_wear_cnt) {
				least_wear_cnt = g_pWearCounter[phy_idx - DeviceInfo.wSpectraStartBlock];
				least_wear_blk_idx = i;
			}
		}
	}

	nand_dbg_print(NAND_DBG_WARN,
		"find_least_worn_blk_for_l2_cache: "
		"find block %d with least worn counter (%d)\n",
		least_wear_blk_idx, least_wear_cnt);

	return least_wear_blk_idx;
}



/* Get blocks for Level2 Cache */
static int get_l2_cache_blks(void)
{
	int n;
	u32 blk;
	u32 *pbt = (u32 *)g_pBlockTable;

	for (n = 0; n < BLK_NUM_FOR_L2_CACHE; n++) {
		blk = find_least_worn_blk_for_l2_cache();
		if (blk > DeviceInfo.wDataBlockNum) {
			nand_dbg_print(NAND_DBG_WARN,
				"find_least_worn_blk_for_l2_cache: "
				"No enough free NAND blocks (n: %d) for L2 Cache!\n", n);
			return FAIL;
		}
		/* Tag the free block as discard in block table */
		pbt[blk] = (pbt[blk] & (~BAD_BLOCK)) | DISCARD_BLOCK;
		/* Add the free block to the L2 Cache block array */
		cache_l2.blk_array[n] = pbt[blk] & (~BAD_BLOCK);
	}

	return PASS;
}

static int erase_l2_cache_blocks(void)
{
	int i, ret = PASS;
	u32 pblk, lblk = BAD_BLOCK;
	u64 addr;
	u32 *pbt = (u32 *)g_pBlockTable;

	nand_dbg_print(NAND_DBG_WARN, "%s, Line %d, Function: %s\n",
			       __FILE__, __LINE__, __func__);

	for (i = 0; i < BLK_NUM_FOR_L2_CACHE; i++) {
		pblk = cache_l2.blk_array[i];

		/* If the L2 cache block is invalid, then just skip it */
		if (MAX_U32_VALUE == pblk)
			continue;

		BUG_ON(pblk > DeviceInfo.wSpectraEndBlock);

		addr = (u64)pblk << DeviceInfo.nBitsInBlockDataSize;
		if (PASS == GLOB_FTL_Block_Erase(addr)) {
			/* Get logical block number of the erased block */
			lblk = FTL_Get_Block_Index(pblk);
			BUG_ON(BAD_BLOCK == lblk);
			/* Tag it as free in the block table */
			pbt[lblk] &= (u32)(~DISCARD_BLOCK);
			pbt[lblk] |= (u32)(SPARE_BLOCK);
		} else {
			MARK_BLOCK_AS_BAD(pbt[lblk]);
			ret = ERR;
		}
	}

	return ret;
}

/*
 * Merge the valid data page in the L2 cache blocks into NAND.
*/
static int flush_l2_cache(void)
{
	struct list_head *p;
	struct spectra_l2_cache_list *pnd, *tmp_pnd;
	u32 *pbt = (u32 *)g_pBlockTable;
	u32 phy_blk, l2_blk;
	u64 addr;
	u16 l2_page;
	int i, ret = PASS;

	nand_dbg_print(NAND_DBG_WARN, "%s, Line %d, Function: %s\n",
			       __FILE__, __LINE__, __func__);

	if (list_empty(&cache_l2.table.list)) /* No data to flush */
		return ret;

	//dump_cache_l2_table();

	if (IN_PROGRESS_BLOCK_TABLE != g_cBlockTableStatus) {
		g_cBlockTableStatus = IN_PROGRESS_BLOCK_TABLE;
		FTL_Write_IN_Progress_Block_Table_Page();
	}

	list_for_each(p, &cache_l2.table.list) {
		pnd = list_entry(p, struct spectra_l2_cache_list, list);
		if (IS_SPARE_BLOCK(pnd->logical_blk_num) ||
			IS_BAD_BLOCK(pnd->logical_blk_num) ||
			IS_DISCARDED_BLOCK(pnd->logical_blk_num)) {
			nand_dbg_print(NAND_DBG_WARN, "%s, Line %d\n", __FILE__, __LINE__);
			memset(cache_l2_blk_buf, 0xff, DeviceInfo.wPagesPerBlock * DeviceInfo.wPageDataSize);			
		} else {
			nand_dbg_print(NAND_DBG_WARN, "%s, Line %d\n", __FILE__, __LINE__);
			phy_blk = pbt[pnd->logical_blk_num] & (~BAD_BLOCK);
			ret = GLOB_LLD_Read_Page_Main(cache_l2_blk_buf,
				phy_blk, 0, DeviceInfo.wPagesPerBlock);
			if (ret == FAIL) {
				printk(KERN_ERR "Read NAND page fail in %s, Line %d\n", __FILE__, __LINE__);
			}
		}

		for (i = 0; i < DeviceInfo.wPagesPerBlock; i++) {
			if (pnd->pages_array[i] != MAX_U32_VALUE) {
				l2_blk = cache_l2.blk_array[(pnd->pages_array[i] >> 16) & 0xffff];
				l2_page = pnd->pages_array[i] & 0xffff;
				ret = GLOB_LLD_Read_Page_Main(cache_l2_page_buf, l2_blk, l2_page, 1);
				if (ret == FAIL) {
					printk(KERN_ERR "Read NAND page fail in %s, Line %d\n", __FILE__, __LINE__);
				}
				memcpy(cache_l2_blk_buf + i * DeviceInfo.wPageDataSize, cache_l2_page_buf, DeviceInfo.wPageDataSize);
			}
		}

		/* Find a free block and tag the original block as discarded */
		addr = (u64)pnd->logical_blk_num << DeviceInfo.nBitsInBlockDataSize;
		ret = FTL_Replace_Block(addr);
		if (ret == FAIL) {
			printk(KERN_ERR "FTL_Replace_Block fail in %s, Line %d\n", __FILE__, __LINE__);
		}

		/* Write back the updated data into NAND */
		phy_blk = pbt[pnd->logical_blk_num] & (~BAD_BLOCK);
		if (FAIL == GLOB_LLD_Write_Page_Main(cache_l2_blk_buf, phy_blk, 0, DeviceInfo.wPagesPerBlock)) {
			nand_dbg_print(NAND_DBG_WARN,
				"Program NAND block %d fail in %s, Line %d\n",
				phy_blk, __FILE__, __LINE__);
			/* This may not be really a bad block. So just tag it as discarded. */
			/* Then it has a chance to be erased when garbage collection. */
			/* If it is really bad, then the erase will fail and it will be marked */
			/* as bad then. Otherwise it will be marked as free and can be used again */
			MARK_BLK_AS_DISCARD(pbt[pnd->logical_blk_num]);
			/* Find another free block and write it again */
			FTL_Replace_Block(addr);
			phy_blk = pbt[pnd->logical_blk_num] & (~BAD_BLOCK);
			if (FAIL == GLOB_LLD_Write_Page_Main(cache_l2_blk_buf, phy_blk, 0, DeviceInfo.wPagesPerBlock)) {
				printk(KERN_ERR "Failed to write back block %d when flush L2 cache."
					"Some data will be lost!\n", phy_blk);
				MARK_BLOCK_AS_BAD(pbt[pnd->logical_blk_num]);
			}
		} else {
			/* tag the new free block as used block */
			pbt[pnd->logical_blk_num] &= (~SPARE_BLOCK);
		}
	}

	/* Destroy the L2 Cache table and free the memory of all nodes */
	list_for_each_entry_safe(pnd, tmp_pnd, &cache_l2.table.list, list) {
		list_del(&pnd->list);
		kfree(pnd);
	}

	/* Erase discard L2 cache blocks */
	if (erase_l2_cache_blocks() != PASS)
		nand_dbg_print(NAND_DBG_WARN,
			" Erase L2 cache blocks error in %s, Line %d\n",
			__FILE__, __LINE__);

	/* Init the Level2 Cache data structure */
	for (i = 0; i < BLK_NUM_FOR_L2_CACHE; i++)
		cache_l2.blk_array[i] = MAX_U32_VALUE;
	cache_l2.cur_blk_idx = 0;
	cache_l2.cur_page_num = 0;
	INIT_LIST_HEAD(&cache_l2.table.list);
	cache_l2.table.logical_blk_num = MAX_U32_VALUE;

	return ret;
}

/*
 * Write back a changed victim cache item to the Level2 Cache
 * and update the L2 Cache table to map the change.
 * If the L2 Cache is full, then start to do the L2 Cache flush.
*/
static int write_back_to_l2_cache(u8 *buf, u64 logical_addr)
{
	u32 logical_blk_num;
	u16 logical_page_num;
	struct list_head *p;
	struct spectra_l2_cache_list *pnd, *pnd_new;
	u32 node_size;
	int i, found;

	nand_dbg_print(NAND_DBG_DEBUG, "%s, Line %d, Function: %s\n",
			       __FILE__, __LINE__, __func__);

	/*
	 * If Level2 Cache table is empty, then it means either:
	 * 1. This is the first time that the function called after FTL_init
	 * or
	 * 2. The Level2 Cache has just been flushed
	 *
	 * So, 'steal' some free blocks from NAND for L2 Cache using
	 * by just mask them as discard in the block table
	*/
	if (list_empty(&cache_l2.table.list)) {
		BUG_ON(cache_l2.cur_blk_idx != 0);
		BUG_ON(cache_l2.cur_page_num!= 0);
		BUG_ON(cache_l2.table.logical_blk_num != MAX_U32_VALUE);
		if (FAIL == get_l2_cache_blks()) {
			GLOB_FTL_Garbage_Collection();
			if (FAIL == get_l2_cache_blks()) {
				printk(KERN_ALERT "Fail to get L2 cache blks!\n");
				return FAIL;
			}
		}
	}

	logical_blk_num = BLK_FROM_ADDR(logical_addr);
	logical_page_num = PAGE_FROM_ADDR(logical_addr, logical_blk_num);
	BUG_ON(logical_blk_num == MAX_U32_VALUE);

	/* Write the cache item data into the current position of L2 Cache */
#if CMD_DMA
	/*
	 * TODO
	 */
#else
	if (FAIL == GLOB_LLD_Write_Page_Main(buf,
		cache_l2.blk_array[cache_l2.cur_blk_idx],
		cache_l2.cur_page_num, 1)) {
		nand_dbg_print(NAND_DBG_WARN, "NAND Program fail in "
			"%s, Line %d, new Bad Block %d generated!\n",
			__FILE__, __LINE__,
			cache_l2.blk_array[cache_l2.cur_blk_idx]);

		/* TODO: tag the current block as bad and try again */

		return FAIL;
	}
#endif

	/* 
	 * Update the L2 Cache table.
	 *
	 * First seaching in the table to see whether the logical block
	 * has been mapped. If not, then kmalloc a new node for the
	 * logical block, fill data, and then insert it to the list.
	 * Otherwise, just update the mapped node directly.
	 */
	found = 0;
	list_for_each(p, &cache_l2.table.list) {
		pnd = list_entry(p, struct spectra_l2_cache_list, list);
		if (pnd->logical_blk_num == logical_blk_num) {
			pnd->pages_array[logical_page_num] =
				(cache_l2.cur_blk_idx << 16) |
				cache_l2.cur_page_num;
			found = 1;
			break;
		}
	}
	if (!found) { /* Create new node for the logical block here */

		/* The logical pages to physical pages map array is
		 * located at the end of struct spectra_l2_cache_list.
		 */ 
		node_size = sizeof(struct spectra_l2_cache_list) +
			sizeof(u32) * DeviceInfo.wPagesPerBlock;
		pnd_new = kmalloc(node_size, GFP_ATOMIC);
		if (!pnd_new) {
			printk(KERN_ERR "Failed to kmalloc in %s Line %d\n",
				__FILE__, __LINE__);
			/* 
			 * TODO: Need to flush all the L2 cache into NAND ASAP
			 * since no memory available here
			 */
		}
		pnd_new->logical_blk_num = logical_blk_num;
		for (i = 0; i < DeviceInfo.wPagesPerBlock; i++)
			pnd_new->pages_array[i] = MAX_U32_VALUE;
		pnd_new->pages_array[logical_page_num] =
			(cache_l2.cur_blk_idx << 16) | cache_l2.cur_page_num;
		list_add(&pnd_new->list, &cache_l2.table.list);
	}

	/* Increasing the current position pointer of the L2 Cache */
	cache_l2.cur_page_num++;
	if (cache_l2.cur_page_num >= DeviceInfo.wPagesPerBlock) {
		cache_l2.cur_blk_idx++;
		if (cache_l2.cur_blk_idx >= BLK_NUM_FOR_L2_CACHE) {
			/* The L2 Cache is full. Need to flush it now */
			nand_dbg_print(NAND_DBG_WARN,
				"L2 Cache is full, will start to flush it\n");
			flush_l2_cache();
		} else {
			cache_l2.cur_page_num = 0;
		}
	}

	return PASS;
}

/*
 * Seach in the Level2 Cache table to find the cache item.
 * If find, read the data from the NAND page of L2 Cache,
 * Otherwise, return FAIL.
 */
static int search_l2_cache(u8 *buf, u64 logical_addr)
{
	u32 logical_blk_num;
	u16 logical_page_num;
	struct list_head *p;
	struct spectra_l2_cache_list *pnd;
	u32 tmp = MAX_U32_VALUE;
	u32 phy_blk;
	u16 phy_page;
	int ret = FAIL;

	logical_blk_num = BLK_FROM_ADDR(logical_addr);
	logical_page_num = PAGE_FROM_ADDR(logical_addr, logical_blk_num);

	list_for_each(p, &cache_l2.table.list) {
		pnd = list_entry(p, struct spectra_l2_cache_list, list);
		if (pnd->logical_blk_num == logical_blk_num) {
			tmp = pnd->pages_array[logical_page_num];
			break;
		}
	}

	if (tmp != MAX_U32_VALUE) { /* Found valid map */
		phy_blk = cache_l2.blk_array[(tmp >> 16) & 0xFFFF];
		phy_page = tmp & 0xFFFF;
#if CMD_DMA
		/* TODO */
#else
		ret = GLOB_LLD_Read_Page_Main(buf, phy_blk, phy_page, 1);
#endif
	}

	return ret;
}

/*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&
* Function:     FTL_Cache_Write_Page
* Inputs:       Pointer to buffer, page address, cache block number
* Outputs:      PASS=0 / FAIL=1
* Description:  It writes the data in Cache Block
*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&*/
static void FTL_Cache_Write_Page(u8 *pData, u64 page_addr,
				u8 cache_blk, u16 flag)
{
	u8 *pDest;
	u64 addr;

	nand_dbg_print(NAND_DBG_TRACE, "%s, Line %d, Function: %s\n",
		__FILE__, __LINE__, __func__);

	addr = Cache.array[cache_blk].address;
	pDest = Cache.array[cache_blk].buf;

	pDest += (unsigned long)(page_addr - addr);
	Cache.array[cache_blk].changed = SET;
#if CMD_DMA
#if RESTORE_CACHE_ON_CDMA_CHAIN_FAILURE
	int_cache[ftl_cmd_cnt].item = cache_blk;
	int_cache[ftl_cmd_cnt].cache.address =
			Cache.array[cache_blk].address;
	int_cache[ftl_cmd_cnt].cache.changed =
			Cache.array[cache_blk].changed;
#endif
	GLOB_LLD_MemCopy_CMD(pDest, pData, DeviceInfo.wPageDataSize, flag);
	ftl_cmd_cnt++;
#else
	memcpy(pDest, pData, DeviceInfo.wPageDataSize);
#endif
	if (Cache.array[cache_blk].use_cnt < MAX_WORD_VALUE)
		Cache.array[cache_blk].use_cnt++;
}

/*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&
* Function:     FTL_Cache_Write
* Inputs:       none
* Outputs:      PASS=0 / FAIL=1
* Description:  It writes least frequently used Cache block to flash if it
*               has been changed
*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&*/
static int FTL_Cache_Write(void)
{
	int i, bResult = PASS;
	u16 bNO, least_count = 0xFFFF;

	nand_dbg_print(NAND_DBG_TRACE, "%s, Line %d, Function: %s\n",
		__FILE__, __LINE__, __func__);

	FTL_Calculate_LRU();

	bNO = Cache.LRU;
	nand_dbg_print(NAND_DBG_DEBUG, "FTL_Cache_Write: "
		"Least used cache block is %d\n", bNO);

	if (Cache.array[bNO].changed != SET)
		return bResult;

	nand_dbg_print(NAND_DBG_DEBUG, "FTL_Cache_Write: Cache"
		" Block %d containing logical block %d is dirty\n",
		bNO,
		(u32)(Cache.array[bNO].address >>
		DeviceInfo.nBitsInBlockDataSize));
#if CMD_DMA
#if RESTORE_CACHE_ON_CDMA_CHAIN_FAILURE
	int_cache[ftl_cmd_cnt].item = bNO;
	int_cache[ftl_cmd_cnt].cache.address =
				Cache.array[bNO].address;
	int_cache[ftl_cmd_cnt].cache.changed = CLEAR;
#endif
#endif
	bResult = write_back_to_l2_cache(Cache.array[bNO].buf,
			Cache.array[bNO].address);
	if (bResult != ERR)
		Cache.array[bNO].changed = CLEAR;

	least_count = Cache.array[bNO].use_cnt;

	for (i = 0; i < CACHE_ITEM_NUM; i++) {
		if (i == bNO)
			continue;
		if (Cache.array[i].use_cnt > 0)
			Cache.array[i].use_cnt -= least_count;
	}

	return bResult;
}

/*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&
* Function:     FTL_Cache_Read
* Inputs:       Page address
* Outputs:      PASS=0 / FAIL=1
* Description:  It reads the block from device in Cache Block
*               Set the LRU count to 1
*               Mark the Cache Block as clean
*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&*/
static int FTL_Cache_Read(u64 logical_addr)
{
	u64 item_addr, phy_addr;
	u16 num;
	int ret;

	nand_dbg_print(NAND_DBG_TRACE, "%s, Line %d, Function: %s\n",
		__FILE__, __LINE__, __func__);

	num = Cache.LRU; /* The LRU cache item will be overwritten */

	item_addr = (u64)GLOB_u64_Div(logical_addr, Cache.cache_item_size) *
		Cache.cache_item_size;
	Cache.array[num].address = item_addr;
	Cache.array[num].use_cnt = 1;
	Cache.array[num].changed = CLEAR;

#if CMD_DMA
#if RESTORE_CACHE_ON_CDMA_CHAIN_FAILURE
	int_cache[ftl_cmd_cnt].item = num;
	int_cache[ftl_cmd_cnt].cache.address =
			Cache.array[num].address;
	int_cache[ftl_cmd_cnt].cache.changed =
			Cache.array[num].changed;
#endif
#endif
	/*
	 * Search in L2 Cache. If hit, fill data into L1 Cache item buffer,
	 * Otherwise, read it from NAND
	 */
	ret = search_l2_cache(Cache.array[num].buf, logical_addr);
	if (PASS == ret) /* Hit in L2 Cache */
		return ret;

	/* Compute the physical start address of NAND device according to */
	/* the logical start address of the cache item (LRU cache item) */
	phy_addr = FTL_Get_Physical_Block_Addr(item_addr) +
		GLOB_u64_Remainder(item_addr, 2);

	return FTL_Cache_Read_All(Cache.array[num].buf, phy_addr);
}

/*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&
* Function:     FTL_Check_Block_Table
* Inputs:       ?
* Outputs:      PASS=0 / FAIL=1
* Description:  It checks the correctness of each block table entry
*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&*/
static int FTL_Check_Block_Table(int wOldTable)
{
	u32 i;
	int wResult = PASS;
	u32 blk_idx;
	u32 *pbt = (u32 *)g_pBlockTable;
	u8 *pFlag = flag_check_blk_table;

	nand_dbg_print(NAND_DBG_TRACE, "%s, Line %d, Function: %s\n",
		       __FILE__, __LINE__, __func__);

	if (NULL != pFlag) {
		memset(pFlag, FAIL, DeviceInfo.wDataBlockNum);
		for (i = 0; i < DeviceInfo.wDataBlockNum; i++) {
			blk_idx = (u32)(pbt[i] & (~BAD_BLOCK));

			/*
			 * 20081006/KBV - Changed to pFlag[i] reference
			 * to avoid buffer overflow
			 */

			/*
			 * 2008-10-20 Yunpeng Note: This change avoid
			 * buffer overflow, but changed function of
			 * the code, so it should be re-write later
			 */
			if ((blk_idx > DeviceInfo.wSpectraEndBlock) ||
				PASS == pFlag[i]) {
				wResult = FAIL;
				break;
			} else {
				pFlag[i] = PASS;
			}
		}
	}

	return wResult;
}


/*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&
* Function:     FTL_Write_Block_Table
* Inputs:       flasg
* Outputs:      0=Block Table was updated. No write done. 1=Block write needs to
* happen. -1 Error
* Description:  It writes the block table
*               Block table always mapped to LBA 0 which inturn mapped
*               to any physical block
*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&*/
static int FTL_Write_Block_Table(int wForce)
{
	u32 *pbt = (u32 *)g_pBlockTable;
	int wSuccess = PASS;
	u32 wTempBlockTableIndex;
	u16 bt_pages, new_bt_offset;
	u8 blockchangeoccured = 0;

	nand_dbg_print(NAND_DBG_TRACE, "%s, Line %d, Function: %s\n",
			       __FILE__, __LINE__, __func__);

	bt_pages = FTL_Get_Block_Table_Flash_Size_Pages();

	if (IN_PROGRESS_BLOCK_TABLE != g_cBlockTableStatus)
		return 0;

	if (PASS == wForce) {
		g_wBlockTableOffset =
			(u16)(DeviceInfo.wPagesPerBlock - bt_pages);
#if CMD_DMA
		p_BTableChangesDelta =
			(struct BTableChangesDelta *)g_pBTDelta_Free;
		g_pBTDelta_Free += sizeof(struct BTableChangesDelta);

		p_BTableChangesDelta->ftl_cmd_cnt = ftl_cmd_cnt;
		p_BTableChangesDelta->g_wBlockTableOffset =
			g_wBlockTableOffset;
		p_BTableChangesDelta->ValidFields = 0x01;
#endif
	}

	nand_dbg_print(NAND_DBG_DEBUG,
		"Inside FTL_Write_Block_Table: block %d Page:%d\n",
		g_wBlockTableIndex, g_wBlockTableOffset);

	do {
		new_bt_offset = g_wBlockTableOffset + bt_pages + 1;
		if ((0 == (new_bt_offset % DeviceInfo.wPagesPerBlock)) ||
			(new_bt_offset > DeviceInfo.wPagesPerBlock) ||
			(FAIL == wSuccess)) {
			wTempBlockTableIndex = FTL_Replace_Block_Table();
			if (BAD_BLOCK == wTempBlockTableIndex)
				return ERR;
			if (!blockchangeoccured) {
				bt_block_changed = 1;
				blockchangeoccured = 1;
			}

			g_wBlockTableIndex = wTempBlockTableIndex;
			g_wBlockTableOffset = 0;
			pbt[BLOCK_TABLE_INDEX] = g_wBlockTableIndex;
#if CMD_DMA
			p_BTableChangesDelta =
				(struct BTableChangesDelta *)g_pBTDelta_Free;
			g_pBTDelta_Free += sizeof(struct BTableChangesDelta);

			p_BTableChangesDelta->ftl_cmd_cnt =
				    ftl_cmd_cnt;
			p_BTableChangesDelta->g_wBlockTableOffset =
				    g_wBlockTableOffset;
			p_BTableChangesDelta->g_wBlockTableIndex =
				    g_wBlockTableIndex;
			p_BTableChangesDelta->ValidFields = 0x03;

			p_BTableChangesDelta =
				(struct BTableChangesDelta *)g_pBTDelta_Free;
			g_pBTDelta_Free +=
				sizeof(struct BTableChangesDelta);

			p_BTableChangesDelta->ftl_cmd_cnt =
				    ftl_cmd_cnt;
			p_BTableChangesDelta->BT_Index =
				    BLOCK_TABLE_INDEX;
			p_BTableChangesDelta->BT_Entry_Value =
				    pbt[BLOCK_TABLE_INDEX];
			p_BTableChangesDelta->ValidFields = 0x0C;
#endif
		}

		wSuccess = FTL_Write_Block_Table_Data();
		if (FAIL == wSuccess)
			MARK_BLOCK_AS_BAD(pbt[BLOCK_TABLE_INDEX]);
	} while (FAIL == wSuccess);

	g_cBlockTableStatus = CURRENT_BLOCK_TABLE;

	return 1;
}

static int  force_format_nand(void)
{
	u32 i;

	/* Force erase the whole unprotected physical partiton of NAND */
	printk(KERN_ALERT "Start to force erase whole NAND device ...\n");
	printk(KERN_ALERT "From phyical block %d to %d\n",
		DeviceInfo.wSpectraStartBlock, DeviceInfo.wSpectraEndBlock);
	for (i = DeviceInfo.wSpectraStartBlock; i <= DeviceInfo.wSpectraEndBlock; i++) {
		if (GLOB_LLD_Erase_Block(i))
			printk(KERN_ERR "Failed to force erase NAND block %d\n", i);
	}
	printk(KERN_ALERT "Force Erase ends. Please reboot the system ...\n");
	while(1);

	return PASS;
}

int GLOB_FTL_Flash_Format(void)
{
	//return FTL_Format_Flash(1);
	return force_format_nand();

}

/*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&
* Function:     FTL_Search_Block_Table_IN_Block
* Inputs:       Block Number
*               Pointer to page
* Outputs:      PASS / FAIL
*               Page contatining the block table
* Description:  It searches the block table in the block
*               passed as an argument.
*
*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&*/
static int FTL_Search_Block_Table_IN_Block(u32 BT_Block,
						u8 BT_Tag, u16 *Page)
{
	u16 i, j, k;
	u16 Result = PASS;
	u16 Last_IPF = 0;
	u8  BT_Found = 0;
	u8 *tagarray;
	u8 *tempbuf = tmp_buf_search_bt_in_block;
	u8 *pSpareBuf = spare_buf_search_bt_in_block;
	u8 *pSpareBufBTLastPage = spare_buf_bt_search_bt_in_block;
	u8 bt_flag_last_page = 0xFF;
	u8 search_in_previous_pages = 0;
	u16 bt_pages;

	nand_dbg_print(NAND_DBG_DEBUG, "%s, Line %d, Function: %s\n",
			       __FILE__, __LINE__, __func__);

	nand_dbg_print(NAND_DBG_DEBUG,
		       "Searching block table in %u block\n",
		       (unsigned int)BT_Block);

	bt_pages = FTL_Get_Block_Table_Flash_Size_Pages();

	for (i = bt_pages; i < DeviceInfo.wPagesPerBlock;
				i += (bt_pages + 1)) {
		nand_dbg_print(NAND_DBG_DEBUG,
			       "Searching last IPF: %d\n", i);
		Result = GLOB_LLD_Read_Page_Main_Polling(tempbuf,
							BT_Block, i, 1);

		if (0 == memcmp(tempbuf, g_pIPF, DeviceInfo.wPageDataSize)) {
			if ((i + bt_pages + 1) < DeviceInfo.wPagesPerBlock) {
				continue;
			} else {
				search_in_previous_pages = 1;
				Last_IPF = i;
			}
		}

		if (!search_in_previous_pages) {
			if (i != bt_pages) {
				i -= (bt_pages + 1);
				Last_IPF = i;
			}
		}

		if (0 == Last_IPF)
			break;

		if (!search_in_previous_pages) {
			i = i + 1;
			nand_dbg_print(NAND_DBG_DEBUG,
				"Reading the spare area of Block %u Page %u",
				(unsigned int)BT_Block, i);
			Result = GLOB_LLD_Read_Page_Spare(pSpareBuf,
							BT_Block, i, 1);
			nand_dbg_print(NAND_DBG_DEBUG,
				"Reading the spare area of Block %u Page %u",
				(unsigned int)BT_Block, i + bt_pages - 1);
			Result = GLOB_LLD_Read_Page_Spare(pSpareBufBTLastPage,
				BT_Block, i + bt_pages - 1, 1);

			k = 0;
			j = FTL_Extract_Block_Table_Tag(pSpareBuf, &tagarray);
			if (j) {
				for (; k < j; k++) {
					if (tagarray[k] == BT_Tag)
						break;
				}
			}

			if (k < j)
				bt_flag = tagarray[k];
			else
				Result = FAIL;

			if (Result == PASS) {
				k = 0;
				j = FTL_Extract_Block_Table_Tag(
					pSpareBufBTLastPage, &tagarray);
				if (j) {
					for (; k < j; k++) {
						if (tagarray[k] == BT_Tag)
							break;
					}
				}

				if (k < j)
					bt_flag_last_page = tagarray[k];
				else
					Result = FAIL;

				if (Result == PASS) {
					if (bt_flag == bt_flag_last_page) {
						nand_dbg_print(NAND_DBG_DEBUG,
							"Block table is found"
							" in page after IPF "
							"at block %d "
							"page %d\n",
							(int)BT_Block, i);
						BT_Found = 1;
						*Page  = i;
						g_cBlockTableStatus =
							CURRENT_BLOCK_TABLE;
						break;
					} else {
						Result = FAIL;
					}
				}
			}
		}

		if (search_in_previous_pages)
			i = i - bt_pages;
		else
			i = i - (bt_pages + 1);

		Result = PASS;

		nand_dbg_print(NAND_DBG_DEBUG,
			"Reading the spare area of Block %d Page %d",
			(int)BT_Block, i);

		Result = GLOB_LLD_Read_Page_Spare(pSpareBuf, BT_Block, i, 1);
		nand_dbg_print(NAND_DBG_DEBUG,
			"Reading the spare area of Block %u Page %u",
			(unsigned int)BT_Block, i + bt_pages - 1);

		Result = GLOB_LLD_Read_Page_Spare(pSpareBufBTLastPage,
					BT_Block, i + bt_pages - 1, 1);

		k = 0;
		j = FTL_Extract_Block_Table_Tag(pSpareBuf, &tagarray);
		if (j) {
			for (; k < j; k++) {
				if (tagarray[k] == BT_Tag)
					break;
			}
		}

		if (k < j)
			bt_flag = tagarray[k];
		else
			Result = FAIL;

		if (Result == PASS) {
			k = 0;
			j = FTL_Extract_Block_Table_Tag(pSpareBufBTLastPage,
						&tagarray);
			if (j) {
				for (; k < j; k++) {
					if (tagarray[k] == BT_Tag)
						break;
				}
			}

			if (k < j) {
				bt_flag_last_page = tagarray[k];
			} else {
				Result = FAIL;
				break;
			}

			if (Result == PASS) {
				if (bt_flag == bt_flag_last_page) {
					nand_dbg_print(NAND_DBG_DEBUG,
						"Block table is found "
						"in page prior to IPF "
						"at block %u page %d\n",
						(unsigned int)BT_Block, i);
					BT_Found = 1;
					*Page  = i;
					g_cBlockTableStatus =
						IN_PROGRESS_BLOCK_TABLE;
					break;
				} else {
					Result = FAIL;
					break;
				}
			}
		}
	}

	if (Result == FAIL) {
		if ((Last_IPF > bt_pages) && (i < Last_IPF) && (!BT_Found)) {
			BT_Found = 1;
			*Page = i - (bt_pages + 1);
		}
		if ((Last_IPF == bt_pages) && (i < Last_IPF) && (!BT_Found))
			goto func_return;
	}

	if (Last_IPF == 0) {
		i = 0;
		Result = PASS;
		nand_dbg_print(NAND_DBG_DEBUG, "Reading the spare area of "
			"Block %u Page %u", (unsigned int)BT_Block, i);

		Result = GLOB_LLD_Read_Page_Spare(pSpareBuf, BT_Block, i, 1);
		nand_dbg_print(NAND_DBG_DEBUG,
			"Reading the spare area of Block %u Page %u",
			(unsigned int)BT_Block, i + bt_pages - 1);
		Result = GLOB_LLD_Read_Page_Spare(pSpareBufBTLastPage,
					BT_Block, i + bt_pages - 1, 1);

		k = 0;
		j = FTL_Extract_Block_Table_Tag(pSpareBuf, &tagarray);
		if (j) {
			for (; k < j; k++) {
				if (tagarray[k] == BT_Tag)
					break;
			}
		}

		if (k < j)
			bt_flag = tagarray[k];
		else
			Result = FAIL;

		if (Result == PASS) {
			k = 0;
			j = FTL_Extract_Block_Table_Tag(pSpareBufBTLastPage,
							&tagarray);
			if (j) {
				for (; k < j; k++) {
					if (tagarray[k] == BT_Tag)
						break;
				}
			}

			if (k < j)
				bt_flag_last_page = tagarray[k];
			else
				Result = FAIL;

			if (Result == PASS) {
				if (bt_flag == bt_flag_last_page) {
					nand_dbg_print(NAND_DBG_DEBUG,
						"Block table is found "
						"in page after IPF at "
						"block %u page %u\n",
						(unsigned int)BT_Block,
						(unsigned int)i);
					BT_Found = 1;
					*Page  = i;
					g_cBlockTableStatus =
						CURRENT_BLOCK_TABLE;
					goto func_return;
				} else {
					Result = FAIL;
				}
			}
		}

		if (Result == FAIL)
			goto func_return;
	}
func_return:
	return Result;
}

u8 *get_blk_table_start_addr(void)
{
	return g_pBlockTable;
}

unsigned long get_blk_table_len(void)
{
	return DeviceInfo.wDataBlockNum * sizeof(u32);
}

u8 *get_wear_leveling_table_start_addr(void)
{
	return g_pWearCounter;
}

unsigned long get_wear_leveling_table_len(void)
{
	return DeviceInfo.wDataBlockNum * sizeof(u8);
}

/*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&
* Function:     FTL_Read_Block_Table
* Inputs:       none
* Outputs:      PASS / FAIL
* Description:  read the flash spare area and find a block containing the
*               most recent block table(having largest block_table_counter).
*               Find the last written Block table in this block.
*               Check the correctness of Block Table
*               If CDMA is enabled, this function is called in
*               polling mode.
*               We don't need to store changes in Block table in this
*               function as it is called only at initialization
*
*               Note: Currently this function is called at initialization
*               before any read/erase/write command issued to flash so,
*               there is no need to wait for CDMA list to complete as of now
*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&*/
static int FTL_Read_Block_Table(void)
{
	u16 i = 0;
	int k, j;
	u8 *tempBuf, *tagarray;
	int wResult = FAIL;
	int status = FAIL;
	u8 block_table_found = 0;
	int search_result;
	u32 Block;
	u16 Page = 0;
	u16 PageCount;
	u16 bt_pages;
	int wBytesCopied = 0, tempvar;

	nand_dbg_print(NAND_DBG_TRACE, "%s, Line %d, Function: %s\n",
			       __FILE__, __LINE__, __func__);

	tempBuf = tmp_buf1_read_blk_table;
	bt_pages = FTL_Get_Block_Table_Flash_Size_Pages();

	for (j = DeviceInfo.wSpectraStartBlock;
		j <= (int)DeviceInfo.wSpectraEndBlock;
			j++) {
		status = GLOB_LLD_Read_Page_Spare(tempBuf, j, 0, 1);
		k = 0;
		i = FTL_Extract_Block_Table_Tag(tempBuf, &tagarray);
		if (i) {
			status  = GLOB_LLD_Read_Page_Main_Polling(tempBuf,
								j, 0, 1);
			for (; k < i; k++) {
				if (tagarray[k] == tempBuf[3])
					break;
			}
		}

		if (k < i)
			k = tagarray[k];
		else
			continue;

		nand_dbg_print(NAND_DBG_DEBUG,
				"Block table is contained in Block %d %d\n",
				       (unsigned int)j, (unsigned int)k);

		if (g_pBTBlocks[k-FIRST_BT_ID] == BTBLOCK_INVAL) {
			g_pBTBlocks[k-FIRST_BT_ID] = j;
			block_table_found = 1;
		} else {
			printk(KERN_ERR "FTL_Read_Block_Table -"
				"This should never happens. "
				"Two block table have same counter %u!\n", k);
		}
	}

	if (block_table_found) {
		if (g_pBTBlocks[FIRST_BT_ID - FIRST_BT_ID] != BTBLOCK_INVAL &&
		g_pBTBlocks[LAST_BT_ID - FIRST_BT_ID] != BTBLOCK_INVAL) {
			j = LAST_BT_ID;
			while ((j > FIRST_BT_ID) &&
			(g_pBTBlocks[j - FIRST_BT_ID] != BTBLOCK_INVAL))
				j--;
			if (j == FIRST_BT_ID) {
				j = LAST_BT_ID;
				last_erased = LAST_BT_ID;
			} else {
				last_erased = (u8)j + 1;
				while ((j > FIRST_BT_ID) && (BTBLOCK_INVAL ==
					g_pBTBlocks[j - FIRST_BT_ID]))
					j--;
			}
		} else {
			j = FIRST_BT_ID;
			while (g_pBTBlocks[j - FIRST_BT_ID] == BTBLOCK_INVAL)
				j++;
			last_erased = (u8)j;
			while ((j < LAST_BT_ID) && (BTBLOCK_INVAL !=
				g_pBTBlocks[j - FIRST_BT_ID]))
				j++;
			if (g_pBTBlocks[j-FIRST_BT_ID] == BTBLOCK_INVAL)
				j--;
		}

		if (last_erased > j)
			j += (1 + LAST_BT_ID - FIRST_BT_ID);

		for (; (j >= last_erased) && (FAIL == wResult); j--) {
			i = (j - FIRST_BT_ID) %
				(1 + LAST_BT_ID - FIRST_BT_ID);
			search_result =
			FTL_Search_Block_Table_IN_Block(g_pBTBlocks[i],
						i + FIRST_BT_ID, &Page);
			if (g_cBlockTableStatus == IN_PROGRESS_BLOCK_TABLE)
				block_table_found = 0;

			while ((search_result == PASS) && (FAIL == wResult)) {
				nand_dbg_print(NAND_DBG_DEBUG,
					"FTL_Read_Block_Table:"
					"Block: %u Page: %u "
					"contains block table\n",
					(unsigned int)g_pBTBlocks[i],
					(unsigned int)Page);

				tempBuf = tmp_buf2_read_blk_table;

				for (k = 0; k < bt_pages; k++) {
					Block = g_pBTBlocks[i];
					PageCount = 1;

					status  =
					GLOB_LLD_Read_Page_Main_Polling(
					tempBuf, Block, Page, PageCount);

					tempvar = k ? 0 : 4;

					wBytesCopied +=
					FTL_Copy_Block_Table_From_Flash(
					tempBuf + tempvar,
					DeviceInfo.wPageDataSize - tempvar,
					wBytesCopied);

					Page++;
				}

				wResult = FTL_Check_Block_Table(FAIL);
				if (FAIL == wResult) {
					block_table_found = 0;
					if (Page > bt_pages)
						Page -= ((bt_pages<<1) + 1);
					else
						search_result = FAIL;
				}
			}
		}
	}

	if (PASS == wResult) {
		if (!block_table_found)
			FTL_Execute_SPL_Recovery();

		if (g_cBlockTableStatus == IN_PROGRESS_BLOCK_TABLE)
			g_wBlockTableOffset = (u16)Page + 1;
		else
			g_wBlockTableOffset = (u16)Page - bt_pages;

		g_wBlockTableIndex = (u32)g_pBTBlocks[i];

#if CMD_DMA
		if (DeviceInfo.MLCDevice)
			memcpy(g_pBTStartingCopy, g_pBlockTable,
				DeviceInfo.wDataBlockNum * sizeof(u32)
				+ DeviceInfo.wDataBlockNum * sizeof(u8)
				+ DeviceInfo.wDataBlockNum * sizeof(u16));
		else
			memcpy(g_pBTStartingCopy, g_pBlockTable,
				DeviceInfo.wDataBlockNum * sizeof(u32)
				+ DeviceInfo.wDataBlockNum * sizeof(u8));
#endif
	}

	if (FAIL == wResult)
		printk(KERN_ERR "Yunpeng - "
		"Can not find valid spectra block table!\n");

#if AUTO_FORMAT_FLASH
	if (FAIL == wResult) {
		nand_dbg_print(NAND_DBG_DEBUG, "doing auto-format\n");
		wResult = FTL_Format_Flash(0);
	}
#endif

	return wResult;
}

/*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&
* Function:     FTL_Get_Page_Num
* Inputs:       Size in bytes
* Outputs:      Size in pages
* Description:  It calculates the pages required for the length passed
*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&*/
static u32 FTL_Get_Page_Num(u64 length)
{
	return (u32)((length >> DeviceInfo.nBitsInPageDataSize) +
		(GLOB_u64_Remainder(length , 1) > 0 ? 1 : 0));
}

/*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&
* Function:     FTL_Get_Physical_Block_Addr
* Inputs:       Block Address (byte format)
* Outputs:      Physical address of the block.
* Description:  It translates LBA to PBA by returning address stored
*               at the LBA location in the block table
*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&*/
static u64 FTL_Get_Physical_Block_Addr(u64 logical_addr)
{
	u32 *pbt;
	u64 physical_addr;

	nand_dbg_print(NAND_DBG_TRACE, "%s, Line %d, Function: %s\n",
		__FILE__, __LINE__, __func__);

	pbt = (u32 *)g_pBlockTable;
	physical_addr = (u64) DeviceInfo.wBlockDataSize *
		(pbt[BLK_FROM_ADDR(logical_addr)] & (~BAD_BLOCK));

	return physical_addr;
}

/*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&
* Function:     FTL_Get_Block_Index
* Inputs:       Physical Block no.
* Outputs:      Logical block no. /BAD_BLOCK
* Description:  It returns the logical block no. for the PBA passed
*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&*/
static u32 FTL_Get_Block_Index(u32 wBlockNum)
{
	u32 *pbt = (u32 *)g_pBlockTable;
	u32 i;

	nand_dbg_print(NAND_DBG_TRACE, "%s, Line %d, Function: %s\n",
		       __FILE__, __LINE__, __func__);

	for (i = 0; i < DeviceInfo.wDataBlockNum; i++)
		if (wBlockNum == (pbt[i] & (~BAD_BLOCK)))
			return i;

	return BAD_BLOCK;
}

/*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&
* Function:     GLOB_FTL_Wear_Leveling
* Inputs:       none
* Outputs:      PASS=0
* Description:  This is static wear leveling (done by explicit call)
*               do complete static wear leveling
*               do complete garbage collection
*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&*/
int GLOB_FTL_Wear_Leveling(void)
{
	nand_dbg_print(NAND_DBG_WARN, "%s, Line %d, Function: %s\n",
		__FILE__, __LINE__, __func__);

	FTL_Static_Wear_Leveling();
	GLOB_FTL_Garbage_Collection();

	return PASS;
}

static void find_least_most_worn(u8 *chg,
	u32 *least_idx, u8 *least_cnt,
	u32 *most_idx, u8 *most_cnt)
{
	u32 *pbt = (u32 *)g_pBlockTable;
	u32 idx;
	u8 cnt;
	int i;

	for (i = BLOCK_TABLE_INDEX + 1; i < DeviceInfo.wDataBlockNum; i++) {
		if (IS_BAD_BLOCK(i) || PASS == chg[i])
			continue;

		idx = (u32) ((~BAD_BLOCK) & pbt[i]);
		cnt = g_pWearCounter[idx - DeviceInfo.wSpectraStartBlock];

		if (IS_SPARE_BLOCK(i)) {
			if (cnt > *most_cnt) {
				*most_cnt = cnt;
				*most_idx = idx;
			}
		}

		if (IS_DATA_BLOCK(i)) {
			if (cnt < *least_cnt) {
				*least_cnt = cnt;
				*least_idx = idx;
			}
		}

		if (PASS == chg[*most_idx] || PASS == chg[*least_idx]) {
			debug_boundary_error(*most_idx,
				DeviceInfo.wDataBlockNum, 0);
			debug_boundary_error(*least_idx,
				DeviceInfo.wDataBlockNum, 0);
			continue;
		}
	}
}

static int move_blks_for_wear_leveling(u8 *chg,
	u32 *least_idx, u32 *rep_blk_num, int *result)
{
	u32 *pbt = (u32 *)g_pBlockTable;
	u32 rep_blk;
	int j, ret_cp_blk, ret_erase;
	int ret = PASS;

	chg[*least_idx] = PASS;
	debug_boundary_error(*least_idx, DeviceInfo.wDataBlockNum, 0);

	rep_blk = FTL_Replace_MWBlock();
	if (rep_blk != BAD_BLOCK) {
		nand_dbg_print(NAND_DBG_DEBUG,
			"More than two spare blocks exist so do it\n");
		nand_dbg_print(NAND_DBG_DEBUG, "Block Replaced is %d\n",
				rep_blk);

		chg[rep_blk] = PASS;

		if (IN_PROGRESS_BLOCK_TABLE != g_cBlockTableStatus) {
			g_cBlockTableStatus = IN_PROGRESS_BLOCK_TABLE;
			FTL_Write_IN_Progress_Block_Table_Page();
		}

		for (j = 0; j < RETRY_TIMES; j++) {
			ret_cp_blk = FTL_Copy_Block((u64)(*least_idx) *
				DeviceInfo.wBlockDataSize,
				(u64)rep_blk * DeviceInfo.wBlockDataSize);
			if (FAIL == ret_cp_blk) {
				ret_erase = GLOB_FTL_Block_Erase((u64)rep_blk
					* DeviceInfo.wBlockDataSize);
				if (FAIL == ret_erase)
					MARK_BLOCK_AS_BAD(pbt[rep_blk]);
			} else {
				nand_dbg_print(NAND_DBG_DEBUG,
					"FTL_Copy_Block == OK\n");
				break;
			}
		}

		if (j < RETRY_TIMES) {
			u32 tmp;
			u32 old_idx = FTL_Get_Block_Index(*least_idx);
			u32 rep_idx = FTL_Get_Block_Index(rep_blk);
			tmp = (u32)(DISCARD_BLOCK | pbt[old_idx]);
			pbt[old_idx] = (u32)((~SPARE_BLOCK) &
							pbt[rep_idx]);
			pbt[rep_idx] = tmp;
#if CMD_DMA
			p_BTableChangesDelta = (struct BTableChangesDelta *)
						g_pBTDelta_Free;
			g_pBTDelta_Free += sizeof(struct BTableChangesDelta);
			p_BTableChangesDelta->ftl_cmd_cnt =
						ftl_cmd_cnt;
			p_BTableChangesDelta->BT_Index = old_idx;
			p_BTableChangesDelta->BT_Entry_Value = pbt[old_idx];
			p_BTableChangesDelta->ValidFields = 0x0C;

			p_BTableChangesDelta = (struct BTableChangesDelta *)
						g_pBTDelta_Free;
			g_pBTDelta_Free += sizeof(struct BTableChangesDelta);

			p_BTableChangesDelta->ftl_cmd_cnt =
						ftl_cmd_cnt;
			p_BTableChangesDelta->BT_Index = rep_idx;
			p_BTableChangesDelta->BT_Entry_Value = pbt[rep_idx];
			p_BTableChangesDelta->ValidFields = 0x0C;
#endif
		} else {
			pbt[FTL_Get_Block_Index(rep_blk)] |= BAD_BLOCK;
#if CMD_DMA
			p_BTableChangesDelta = (struct BTableChangesDelta *)
						g_pBTDelta_Free;
			g_pBTDelta_Free += sizeof(struct BTableChangesDelta);

			p_BTableChangesDelta->ftl_cmd_cnt =
						ftl_cmd_cnt;
			p_BTableChangesDelta->BT_Index =
					FTL_Get_Block_Index(rep_blk);
			p_BTableChangesDelta->BT_Entry_Value =
					pbt[FTL_Get_Block_Index(rep_blk)];
			p_BTableChangesDelta->ValidFields = 0x0C;
#endif
			*result = FAIL;
			ret = FAIL;
		}

		if (((*rep_blk_num)++) > WEAR_LEVELING_BLOCK_NUM)
			ret = FAIL;
	} else {
		printk(KERN_ERR "Less than 3 spare blocks exist so quit\n");
		ret = FAIL;
	}

	return ret;
}

/*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&
* Function:     FTL_Static_Wear_Leveling
* Inputs:       none
* Outputs:      PASS=0 / FAIL=1
* Description:  This is static wear leveling (done by explicit call)
*               search for most&least used
*               if difference < GATE:
*                   update the block table with exhange
*                   mark block table in flash as IN_PROGRESS
*                   copy flash block
*               the caller should handle GC clean up after calling this function
*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&*/
int FTL_Static_Wear_Leveling(void)
{
	u8 most_worn_cnt;
	u8 least_worn_cnt;
	u32 most_worn_idx;
	u32 least_worn_idx;
	int result = PASS;
	int go_on = PASS;
	u32 replaced_blks = 0;
	u8 *chang_flag = flags_static_wear_leveling;

	nand_dbg_print(NAND_DBG_WARN, "%s, Line %d, Function: %s\n",
		       __FILE__, __LINE__, __func__);

	if (!chang_flag)
		return FAIL;

	memset(chang_flag, FAIL, DeviceInfo.wDataBlockNum);
	while (go_on == PASS) {
		nand_dbg_print(NAND_DBG_DEBUG,
			"starting static wear leveling\n");
		most_worn_cnt = 0;
		least_worn_cnt = 0xFF;
		least_worn_idx = BLOCK_TABLE_INDEX;
		most_worn_idx = BLOCK_TABLE_INDEX;

		find_least_most_worn(chang_flag, &least_worn_idx,
			&least_worn_cnt, &most_worn_idx, &most_worn_cnt);

		nand_dbg_print(NAND_DBG_DEBUG,
			"Used and least worn is block %u, whos count is %u\n",
			(unsigned int)least_worn_idx,
			(unsigned int)least_worn_cnt);

		nand_dbg_print(NAND_DBG_DEBUG,
			"Free and  most worn is block %u, whos count is %u\n",
			(unsigned int)most_worn_idx,
			(unsigned int)most_worn_cnt);

		if ((most_worn_cnt > least_worn_cnt) &&
			(most_worn_cnt - least_worn_cnt > WEAR_LEVELING_GATE))
			go_on = move_blks_for_wear_leveling(chang_flag,
				&least_worn_idx, &replaced_blks, &result);
		else
			go_on = FAIL;
	}

	return result;
}

#if CMD_DMA
static int do_garbage_collection(u32 discard_cnt)
{
	u32 *pbt = (u32 *)g_pBlockTable;
	u32 pba;
	u8 bt_block_erased = 0;
	int i, cnt, ret = FAIL;
	u64 addr;

	i = 0;
	while ((i < DeviceInfo.wDataBlockNum) && (discard_cnt > 0) &&
			((ftl_cmd_cnt + 28) < 256)) {
		if (((pbt[i] & BAD_BLOCK) != BAD_BLOCK) &&
				(pbt[i] & DISCARD_BLOCK)) {
			if (IN_PROGRESS_BLOCK_TABLE != g_cBlockTableStatus) {
				g_cBlockTableStatus = IN_PROGRESS_BLOCK_TABLE;
				FTL_Write_IN_Progress_Block_Table_Page();
			}

			addr = FTL_Get_Physical_Block_Addr((u64)i *
						DeviceInfo.wBlockDataSize);
			pba = BLK_FROM_ADDR(addr);

			for (cnt = FIRST_BT_ID; cnt <= LAST_BT_ID; cnt++) {
				if (pba == g_pBTBlocks[cnt - FIRST_BT_ID]) {
					nand_dbg_print(NAND_DBG_DEBUG,
						"GC will erase BT block %u\n",
						(unsigned int)pba);
					discard_cnt--;
					i++;
					bt_block_erased = 1;
					break;
				}
			}

			if (bt_block_erased) {
				bt_block_erased = 0;
				continue;
			}

			addr = FTL_Get_Physical_Block_Addr((u64)i *
						DeviceInfo.wBlockDataSize);

			if (PASS == GLOB_FTL_Block_Erase(addr)) {
				pbt[i] &= (u32)(~DISCARD_BLOCK);
				pbt[i] |= (u32)(SPARE_BLOCK);
				p_BTableChangesDelta =
					(struct BTableChangesDelta *)
					g_pBTDelta_Free;
				g_pBTDelta_Free +=
					sizeof(struct BTableChangesDelta);
				p_BTableChangesDelta->ftl_cmd_cnt =
					ftl_cmd_cnt - 1;
				p_BTableChangesDelta->BT_Index = i;
				p_BTableChangesDelta->BT_Entry_Value = pbt[i];
				p_BTableChangesDelta->ValidFields = 0x0C;
				discard_cnt--;
				ret = PASS;
			} else {
				MARK_BLOCK_AS_BAD(pbt[i]);
			}
		}

		i++;
	}

	return ret;
}

#else
static int do_garbage_collection(u32 discard_cnt)
{
	u32 *pbt = (u32 *)g_pBlockTable;
	u32 pba;
	u8 bt_block_erased = 0;
	int i, cnt, ret = FAIL;
	u64 addr;

	i = 0;
	while ((i < DeviceInfo.wDataBlockNum) && (discard_cnt > 0)) {
		if (((pbt[i] & BAD_BLOCK) != BAD_BLOCK) &&
				(pbt[i] & DISCARD_BLOCK)) {
			if (IN_PROGRESS_BLOCK_TABLE != g_cBlockTableStatus) {
				g_cBlockTableStatus = IN_PROGRESS_BLOCK_TABLE;
				FTL_Write_IN_Progress_Block_Table_Page();
			}

			addr = FTL_Get_Physical_Block_Addr((u64)i *
						DeviceInfo.wBlockDataSize);
			pba = BLK_FROM_ADDR(addr);

			for (cnt = FIRST_BT_ID; cnt <= LAST_BT_ID; cnt++) {
				if (pba == g_pBTBlocks[cnt - FIRST_BT_ID]) {
					nand_dbg_print(NAND_DBG_DEBUG,
						"GC will erase BT block %d\n",
						pba);
					discard_cnt--;
					i++;
					bt_block_erased = 1;
					break;
				}
			}

			if (bt_block_erased) {
				bt_block_erased = 0;
				continue;
			}

			/* If the discard block is L2 cache block, then just skip it */
			for (cnt = 0; cnt < BLK_NUM_FOR_L2_CACHE; cnt++) {
				if (cache_l2.blk_array[cnt] == pba) {
					nand_dbg_print(NAND_DBG_DEBUG,
						"GC will erase L2 cache blk %d\n",
						pba);
					break;
				}
			}
			if (cnt < BLK_NUM_FOR_L2_CACHE) { /* Skip it */
				discard_cnt--;
				i++;
				continue;
			}

			addr = FTL_Get_Physical_Block_Addr((u64)i *
						DeviceInfo.wBlockDataSize);

			if (PASS == GLOB_FTL_Block_Erase(addr)) {
				pbt[i] &= (u32)(~DISCARD_BLOCK);
				pbt[i] |= (u32)(SPARE_BLOCK);
				discard_cnt--;
				ret = PASS;
			} else {
				MARK_BLOCK_AS_BAD(pbt[i]);
			}
		}

		i++;
	}

	return ret;
}
#endif

/*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&
* Function:     GLOB_FTL_Garbage_Collection
* Inputs:       none
* Outputs:      PASS / FAIL (returns the number of un-erased blocks
* Description:  search the block table for all discarded blocks to erase
*               for each discarded block:
*                   set the flash block to IN_PROGRESS
*                   erase the block
*                   update the block table
*                   write the block table to flash
*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&*/
int GLOB_FTL_Garbage_Collection(void)
{
	u32 i;
	u32 wDiscard = 0;
	int wResult = FAIL;
	u32 *pbt = (u32 *)g_pBlockTable;

	nand_dbg_print(NAND_DBG_WARN, "%s, Line %d, Function: %s\n",
			       __FILE__, __LINE__, __func__);

	if (GC_Called) {
		printk(KERN_ALERT "GLOB_FTL_Garbage_Collection() "
			"has been re-entered! Exit.\n");
		return PASS;
	}

	GC_Called = 1;

	GLOB_FTL_BT_Garbage_Collection();

	for (i = 0; i < DeviceInfo.wDataBlockNum; i++) {
		if (IS_DISCARDED_BLOCK(i))
			wDiscard++;
	}

	if (wDiscard <= 0) {
		GC_Called = 0;
		return wResult;
	}

	nand_dbg_print(NAND_DBG_DEBUG,
		"Found %d discarded blocks\n", wDiscard);

	FTL_Write_Block_Table(FAIL);

	wResult = do_garbage_collection(wDiscard);

	FTL_Write_Block_Table(FAIL);

	GC_Called = 0;

	return wResult;
}


#if CMD_DMA
static int do_bt_garbage_collection(void)
{
	u32 pba, lba;
	u32 *pbt = (u32 *)g_pBlockTable;
	u32 *pBTBlocksNode = (u32 *)g_pBTBlocks;
	u64 addr;
	int i, ret = FAIL;

	nand_dbg_print(NAND_DBG_TRACE, "%s, Line %d, Function: %s\n",
			       __FILE__, __LINE__, __func__);

	if (BT_GC_Called)
		return PASS;

	BT_GC_Called = 1;

	for (i = last_erased; (i <= LAST_BT_ID) &&
		(g_pBTBlocks[((i + 2) % (1 + LAST_BT_ID - FIRST_BT_ID)) +
		FIRST_BT_ID - FIRST_BT_ID] != BTBLOCK_INVAL) &&
		((ftl_cmd_cnt + 28)) < 256; i++) {
		pba = pBTBlocksNode[i - FIRST_BT_ID];
		lba = FTL_Get_Block_Index(pba);
		nand_dbg_print(NAND_DBG_DEBUG,
			"do_bt_garbage_collection: pba %d, lba %d\n",
			pba, lba);
		nand_dbg_print(NAND_DBG_DEBUG,
			"Block Table Entry: %d", pbt[lba]);

		if (((pbt[lba] & BAD_BLOCK) != BAD_BLOCK) &&
			(pbt[lba] & DISCARD_BLOCK)) {
			nand_dbg_print(NAND_DBG_DEBUG,
				"do_bt_garbage_collection_cdma: "
				"Erasing Block tables present in block %d\n",
				pba);
			addr = FTL_Get_Physical_Block_Addr((u64)lba *
						DeviceInfo.wBlockDataSize);
			if (PASS == GLOB_FTL_Block_Erase(addr)) {
				pbt[lba] &= (u32)(~DISCARD_BLOCK);
				pbt[lba] |= (u32)(SPARE_BLOCK);

				p_BTableChangesDelta =
					(struct BTableChangesDelta *)
					g_pBTDelta_Free;
				g_pBTDelta_Free +=
					sizeof(struct BTableChangesDelta);

				p_BTableChangesDelta->ftl_cmd_cnt =
					ftl_cmd_cnt - 1;
				p_BTableChangesDelta->BT_Index = lba;
				p_BTableChangesDelta->BT_Entry_Value =
								pbt[lba];

				p_BTableChangesDelta->ValidFields = 0x0C;

				ret = PASS;
				pBTBlocksNode[last_erased - FIRST_BT_ID] =
							BTBLOCK_INVAL;
				nand_dbg_print(NAND_DBG_DEBUG,
					"resetting bt entry at index %d "
					"value %d\n", i,
					pBTBlocksNode[i - FIRST_BT_ID]);
				if (last_erased == LAST_BT_ID)
					last_erased = FIRST_BT_ID;
				else
					last_erased++;
			} else {
				MARK_BLOCK_AS_BAD(pbt[lba]);
			}
		}
	}

	BT_GC_Called = 0;

	return ret;
}

#else
static int do_bt_garbage_collection(void)
{
	u32 pba, lba;
	u32 *pbt = (u32 *)g_pBlockTable;
	u32 *pBTBlocksNode = (u32 *)g_pBTBlocks;
	u64 addr;
	int i, ret = FAIL;

	nand_dbg_print(NAND_DBG_TRACE, "%s, Line %d, Function: %s\n",
			       __FILE__, __LINE__, __func__);

	if (BT_GC_Called)
		return PASS;

	BT_GC_Called = 1;

	for (i = last_erased; (i <= LAST_BT_ID) &&
		(g_pBTBlocks[((i + 2) % (1 + LAST_BT_ID - FIRST_BT_ID)) +
		FIRST_BT_ID - FIRST_BT_ID] != BTBLOCK_INVAL); i++) {
		pba = pBTBlocksNode[i - FIRST_BT_ID];
		lba = FTL_Get_Block_Index(pba);
		nand_dbg_print(NAND_DBG_DEBUG,
			"do_bt_garbage_collection_cdma: pba %d, lba %d\n",
			pba, lba);
		nand_dbg_print(NAND_DBG_DEBUG,
			"Block Table Entry: %d", pbt[lba]);

		if (((pbt[lba] & BAD_BLOCK) != BAD_BLOCK) &&
			(pbt[lba] & DISCARD_BLOCK)) {
			nand_dbg_print(NAND_DBG_DEBUG,
				"do_bt_garbage_collection: "
				"Erasing Block tables present in block %d\n",
				pba);
			addr = FTL_Get_Physical_Block_Addr((u64)lba *
						DeviceInfo.wBlockDataSize);
			if (PASS == GLOB_FTL_Block_Erase(addr)) {
				pbt[lba] &= (u32)(~DISCARD_BLOCK);
				pbt[lba] |= (u32)(SPARE_BLOCK);
				ret = PASS;
				pBTBlocksNode[last_erased - FIRST_BT_ID] =
							BTBLOCK_INVAL;
				nand_dbg_print(NAND_DBG_DEBUG,
					"resetting bt entry at index %d "
					"value %d\n", i,
					pBTBlocksNode[i - FIRST_BT_ID]);
				if (last_erased == LAST_BT_ID)
					last_erased = FIRST_BT_ID;
				else
					last_erased++;
			} else {
				MARK_BLOCK_AS_BAD(pbt[lba]);
			}
		}
	}

	BT_GC_Called = 0;

	return ret;
}

#endif

/*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&
* Function:     GLOB_FTL_BT_Garbage_Collection
* Inputs:       none
* Outputs:      PASS / FAIL (returns the number of un-erased blocks
* Description:  Erases discarded blocks containing Block table
*
*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&*/
int GLOB_FTL_BT_Garbage_Collection(void)
{
	return do_bt_garbage_collection();
}

/*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&
* Function:     FTL_Replace_OneBlock
* Inputs:       Block number 1
*               Block number 2
* Outputs:      Replaced Block Number
* Description:  Interchange block table entries at wBlockNum and wReplaceNum
*
*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&*/
static u32 FTL_Replace_OneBlock(u32 blk, u32 rep_blk)
{
	u32 tmp_blk;
	u32 replace_node = BAD_BLOCK;
	u32 *pbt = (u32 *)g_pBlockTable;

	nand_dbg_print(NAND_DBG_TRACE, "%s, Line %d, Function: %s\n",
		__FILE__, __LINE__, __func__);

	if (rep_blk != BAD_BLOCK) {
		if (IS_BAD_BLOCK(blk))
			tmp_blk = pbt[blk];
		else
			tmp_blk = DISCARD_BLOCK | (~SPARE_BLOCK & pbt[blk]);

		replace_node = (u32) ((~SPARE_BLOCK) & pbt[rep_blk]);
		pbt[blk] = replace_node;
		pbt[rep_blk] = tmp_blk;

#if CMD_DMA
		p_BTableChangesDelta =
			(struct BTableChangesDelta *)g_pBTDelta_Free;
		g_pBTDelta_Free += sizeof(struct BTableChangesDelta);

		p_BTableChangesDelta->ftl_cmd_cnt = ftl_cmd_cnt;
		p_BTableChangesDelta->BT_Index = blk;
		p_BTableChangesDelta->BT_Entry_Value = pbt[blk];

		p_BTableChangesDelta->ValidFields = 0x0C;

		p_BTableChangesDelta =
			(struct BTableChangesDelta *)g_pBTDelta_Free;
		g_pBTDelta_Free += sizeof(struct BTableChangesDelta);

		p_BTableChangesDelta->ftl_cmd_cnt = ftl_cmd_cnt;
		p_BTableChangesDelta->BT_Index = rep_blk;
		p_BTableChangesDelta->BT_Entry_Value = pbt[rep_blk];
		p_BTableChangesDelta->ValidFields = 0x0C;
#endif
	}

	return replace_node;
}

/*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&
* Function:     FTL_Write_Block_Table_Data
* Inputs:       Block table size in pages
* Outputs:      PASS=0 / FAIL=1
* Description:  Write block table data in flash
*               If first page and last page
*                  Write data+BT flag
*               else
*                  Write data
*               BT flag is a counter. Its value is incremented for block table
*               write in a new Block
*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&*/
static int FTL_Write_Block_Table_Data(void)
{
	u64 dwBlockTableAddr, pTempAddr;
	u32 Block;
	u16 Page, PageCount;
	u8 *tempBuf = tmp_buf_write_blk_table_data;
	int wBytesCopied;
	u16 bt_pages;

	nand_dbg_print(NAND_DBG_TRACE, "%s, Line %d, Function: %s\n",
			       __FILE__, __LINE__, __func__);

	dwBlockTableAddr =
		(u64)((u64)g_wBlockTableIndex * DeviceInfo.wBlockDataSize +
		(u64)g_wBlockTableOffset * DeviceInfo.wPageDataSize);
	pTempAddr = dwBlockTableAddr;

	bt_pages = FTL_Get_Block_Table_Flash_Size_Pages();

	nand_dbg_print(NAND_DBG_DEBUG, "FTL_Write_Block_Table_Data: "
			       "page= %d BlockTableIndex= %d "
			       "BlockTableOffset=%d\n", bt_pages,
			       g_wBlockTableIndex, g_wBlockTableOffset);

	Block = BLK_FROM_ADDR(pTempAddr);
	Page = PAGE_FROM_ADDR(pTempAddr, Block);
	PageCount = 1;

	if (bt_block_changed) {
		if (bt_flag == LAST_BT_ID) {
			bt_flag = FIRST_BT_ID;
			g_pBTBlocks[bt_flag - FIRST_BT_ID] = Block;
		} else if (bt_flag < LAST_BT_ID) {
			bt_flag++;
			g_pBTBlocks[bt_flag - FIRST_BT_ID] = Block;
		}

		if ((bt_flag > (LAST_BT_ID-4)) &&
			g_pBTBlocks[FIRST_BT_ID - FIRST_BT_ID] !=
						BTBLOCK_INVAL) {
			bt_block_changed = 0;
			GLOB_FTL_BT_Garbage_Collection();
		}

		bt_block_changed = 0;
		nand_dbg_print(NAND_DBG_DEBUG,
			"Block Table Counter is %u Block %u\n",
			bt_flag, (unsigned int)Block);
	}

	memset(tempBuf, 0, 3);
	tempBuf[3] = bt_flag;
	wBytesCopied = FTL_Copy_Block_Table_To_Flash(tempBuf + 4,
			DeviceInfo.wPageDataSize - 4, 0);
	memset(&tempBuf[wBytesCopied + 4], 0xff,
		DeviceInfo.wPageSize - (wBytesCopied + 4));
	FTL_Insert_Block_Table_Signature(&tempBuf[DeviceInfo.wPageDataSize],
					bt_flag);

#if CMD_DMA
	memcpy(g_pNextBlockTable, tempBuf,
		DeviceInfo.wPageSize * sizeof(u8));
	nand_dbg_print(NAND_DBG_DEBUG, "Writing First Page of Block Table "
		"Block %u Page %u\n", (unsigned int)Block, Page);
	if (FAIL == GLOB_LLD_Write_Page_Main_Spare_cdma(g_pNextBlockTable,
		Block, Page, 1,
		LLD_CMD_FLAG_MODE_CDMA | LLD_CMD_FLAG_ORDER_BEFORE_REST)) {
		nand_dbg_print(NAND_DBG_WARN, "NAND Program fail in "
			"%s, Line %d, Function: %s, "
			"new Bad Block %d generated!\n",
			__FILE__, __LINE__, __func__, Block);
		goto func_return;
	}

	ftl_cmd_cnt++;
	g_pNextBlockTable += ((DeviceInfo.wPageSize * sizeof(u8)));
#else
	if (FAIL == GLOB_LLD_Write_Page_Main_Spare(tempBuf, Block, Page, 1)) {
		nand_dbg_print(NAND_DBG_WARN,
			"NAND Program fail in %s, Line %d, Function: %s, "
			"new Bad Block %d generated!\n",
			__FILE__, __LINE__, __func__, Block);
		goto func_return;
	}
#endif

	if (bt_pages > 1) {
		PageCount = bt_pages - 1;
		if (PageCount > 1) {
			wBytesCopied += FTL_Copy_Block_Table_To_Flash(tempBuf,
				DeviceInfo.wPageDataSize * (PageCount - 1),
				wBytesCopied);

#if CMD_DMA
			memcpy(g_pNextBlockTable, tempBuf,
				(PageCount - 1) * DeviceInfo.wPageDataSize);
			if (FAIL == GLOB_LLD_Write_Page_Main_cdma(
				g_pNextBlockTable, Block, Page + 1,
				PageCount - 1)) {
				nand_dbg_print(NAND_DBG_WARN,
					"NAND Program fail in %s, Line %d, "
					"Function: %s, "
					"new Bad Block %d generated!\n",
					__FILE__, __LINE__, __func__,
					(int)Block);
				goto func_return;
			}

			ftl_cmd_cnt++;
			g_pNextBlockTable += (PageCount - 1) *
				DeviceInfo.wPageDataSize * sizeof(u8);
#else
			if (FAIL == GLOB_LLD_Write_Page_Main(tempBuf,
					Block, Page + 1, PageCount - 1)) {
				nand_dbg_print(NAND_DBG_WARN,
					"NAND Program fail in %s, Line %d, "
					"Function: %s, "
					"new Bad Block %d generated!\n",
					__FILE__, __LINE__, __func__,
					(int)Block);
				goto func_return;
			}
#endif
		}

		wBytesCopied = FTL_Copy_Block_Table_To_Flash(tempBuf,
				DeviceInfo.wPageDataSize, wBytesCopied);
		memset(&tempBuf[wBytesCopied], 0xff,
			DeviceInfo.wPageSize-wBytesCopied);
		FTL_Insert_Block_Table_Signature(
			&tempBuf[DeviceInfo.wPageDataSize], bt_flag);
#if CMD_DMA
		memcpy(g_pNextBlockTable, tempBuf,
				DeviceInfo.wPageSize * sizeof(u8));
		nand_dbg_print(NAND_DBG_DEBUG,
			"Writing the last Page of Block Table "
			"Block %u Page %u\n",
			(unsigned int)Block, Page + bt_pages - 1);
		if (FAIL == GLOB_LLD_Write_Page_Main_Spare_cdma(
			g_pNextBlockTable, Block, Page + bt_pages - 1, 1,
			LLD_CMD_FLAG_MODE_CDMA |
			LLD_CMD_FLAG_ORDER_BEFORE_REST)) {
			nand_dbg_print(NAND_DBG_WARN,
				"NAND Program fail in %s, Line %d, "
				"Function: %s, new Bad Block %d generated!\n",
				__FILE__, __LINE__, __func__, Block);
			goto func_return;
		}
		ftl_cmd_cnt++;
#else
		if (FAIL == GLOB_LLD_Write_Page_Main_Spare(tempBuf,
					Block, Page+bt_pages - 1, 1)) {
			nand_dbg_print(NAND_DBG_WARN,
				"NAND Program fail in %s, Line %d, "
				"Function: %s, "
				"new Bad Block %d generated!\n",
				__FILE__, __LINE__, __func__, Block);
			goto func_return;
		}
#endif
	}

	nand_dbg_print(NAND_DBG_DEBUG, "FTL_Write_Block_Table_Data: done\n");

func_return:
	return PASS;
}

/*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&
* Function:     FTL_Replace_Block_Table
* Inputs:       None
* Outputs:      PASS=0 / FAIL=1
* Description:  Get a new block to write block table
*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&*/
static u32 FTL_Replace_Block_Table(void)
{
	u32 blk;
	int gc;

	nand_dbg_print(NAND_DBG_TRACE, "%s, Line %d, Function: %s\n",
		__FILE__, __LINE__, __func__);

	blk = FTL_Replace_LWBlock(BLOCK_TABLE_INDEX, &gc);

	if ((BAD_BLOCK == blk) && (PASS == gc)) {
		GLOB_FTL_Garbage_Collection();
		blk = FTL_Replace_LWBlock(BLOCK_TABLE_INDEX, &gc);
	}
	if (BAD_BLOCK == blk)
		printk(KERN_ERR "%s, %s: There is no spare block. "
			"It should never happen\n",
			__FILE__, __func__);

	nand_dbg_print(NAND_DBG_DEBUG, "New Block table Block is %d\n", blk);

	return blk;
}

/*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&
* Function:     FTL_Replace_LWBlock
* Inputs:       Block number
*               Pointer to Garbage Collect flag
* Outputs:
* Description:  Determine the least weared block by traversing
*               block table
*               Set Garbage collection to be called if number of spare
*               block is less than Free Block Gate count
*               Change Block table entry to map least worn block for current
*               operation
*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&*/
static u32 FTL_Replace_LWBlock(u32 wBlockNum, int *pGarbageCollect)
{
	u32 i;
	u32 *pbt = (u32 *)g_pBlockTable;
	u8 wLeastWornCounter = 0xFF;
	u32 wLeastWornIndex = BAD_BLOCK;
	u32 wSpareBlockNum = 0;
	u32 wDiscardBlockNum = 0;

	nand_dbg_print(NAND_DBG_TRACE, "%s, Line %d, Function: %s\n",
		__FILE__, __LINE__, __func__);

	if (IS_SPARE_BLOCK(wBlockNum)) {
		*pGarbageCollect = FAIL;
		pbt[wBlockNum] = (u32)(pbt[wBlockNum] & (~SPARE_BLOCK));
#if CMD_DMA
		p_BTableChangesDelta =
			(struct BTableChangesDelta *)g_pBTDelta_Free;
		g_pBTDelta_Free += sizeof(struct BTableChangesDelta);
		p_BTableChangesDelta->ftl_cmd_cnt =
						ftl_cmd_cnt;
		p_BTableChangesDelta->BT_Index = (u32)(wBlockNum);
		p_BTableChangesDelta->BT_Entry_Value = pbt[wBlockNum];
		p_BTableChangesDelta->ValidFields = 0x0C;
#endif
		return pbt[wBlockNum];
	}

	for (i = 0; i < DeviceInfo.wDataBlockNum; i++) {
		if (IS_DISCARDED_BLOCK(i))
			wDiscardBlockNum++;

		if (IS_SPARE_BLOCK(i)) {
			u32 wPhysicalIndex = (u32)((~BAD_BLOCK) & pbt[i]);
			if (wPhysicalIndex > DeviceInfo.wSpectraEndBlock)
				printk(KERN_ERR "FTL_Replace_LWBlock: "
					"This should never occur!\n");
			if (g_pWearCounter[wPhysicalIndex -
				DeviceInfo.wSpectraStartBlock] <
				wLeastWornCounter) {
				wLeastWornCounter =
					g_pWearCounter[wPhysicalIndex -
					DeviceInfo.wSpectraStartBlock];
				wLeastWornIndex = i;
			}
			wSpareBlockNum++;
		}
	}

	nand_dbg_print(NAND_DBG_WARN,
		"FTL_Replace_LWBlock: Least Worn Counter %d\n",
		(int)wLeastWornCounter);

	if ((wDiscardBlockNum >= NUM_FREE_BLOCKS_GATE) ||
		(wSpareBlockNum <= NUM_FREE_BLOCKS_GATE))
		*pGarbageCollect = PASS;
	else
		*pGarbageCollect = FAIL;

	nand_dbg_print(NAND_DBG_DEBUG,
		"FTL_Replace_LWBlock: Discarded Blocks %u Spare"
		" Blocks %u\n",
		(unsigned int)wDiscardBlockNum,
		(unsigned int)wSpareBlockNum);

	return FTL_Replace_OneBlock(wBlockNum, wLeastWornIndex);
}

/*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&
* Function:     FTL_Replace_MWBlock
* Inputs:       None
* Outputs:      most worn spare block no./BAD_BLOCK
* Description:  It finds most worn spare block.
*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&*/
static u32 FTL_Replace_MWBlock(void)
{
	u32 i;
	u32 *pbt = (u32 *)g_pBlockTable;
	u8 wMostWornCounter = 0;
	u32 wMostWornIndex = BAD_BLOCK;
	u32 wSpareBlockNum = 0;

	nand_dbg_print(NAND_DBG_TRACE, "%s, Line %d, Function: %s\n",
		       __FILE__, __LINE__, __func__);

	for (i = 0; i < DeviceInfo.wDataBlockNum; i++) {
		if (IS_SPARE_BLOCK(i)) {
			u32 wPhysicalIndex = (u32)((~SPARE_BLOCK) & pbt[i]);
			if (g_pWearCounter[wPhysicalIndex -
			    DeviceInfo.wSpectraStartBlock] >
			    wMostWornCounter) {
				wMostWornCounter =
				    g_pWearCounter[wPhysicalIndex -
				    DeviceInfo.wSpectraStartBlock];
				wMostWornIndex = wPhysicalIndex;
			}
			wSpareBlockNum++;
		}
	}

	if (wSpareBlockNum <= 2)
		return BAD_BLOCK;

	return wMostWornIndex;
}

/*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&
* Function:     FTL_Replace_Block
* Inputs:       Block Address
* Outputs:      PASS=0 / FAIL=1
* Description:  If block specified by blk_addr parameter is not free,
*               replace it with the least worn block.
*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&*/
static int FTL_Replace_Block(u64 blk_addr)
{
	u32 current_blk = BLK_FROM_ADDR(blk_addr);
	u32 *pbt = (u32 *)g_pBlockTable;
	int wResult = PASS;
	int GarbageCollect = FAIL;

	nand_dbg_print(NAND_DBG_TRACE, "%s, Line %d, Function: %s\n",
		__FILE__, __LINE__, __func__);

	if (IS_SPARE_BLOCK(current_blk)) {
		pbt[current_blk] = (~SPARE_BLOCK) & pbt[current_blk];
#if CMD_DMA
		p_BTableChangesDelta =
			(struct BTableChangesDelta *)g_pBTDelta_Free;
		g_pBTDelta_Free += sizeof(struct BTableChangesDelta);
		p_BTableChangesDelta->ftl_cmd_cnt =
			ftl_cmd_cnt;
		p_BTableChangesDelta->BT_Index = current_blk;
		p_BTableChangesDelta->BT_Entry_Value = pbt[current_blk];
		p_BTableChangesDelta->ValidFields = 0x0C ;
#endif
		return wResult;
	}

	FTL_Replace_LWBlock(current_blk, &GarbageCollect);

	if (PASS == GarbageCollect)
		wResult = GLOB_FTL_Garbage_Collection();

	return wResult;
}

/*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&
* Function:     GLOB_FTL_Is_BadBlock
* Inputs:       block number to test
* Outputs:      PASS (block is BAD) / FAIL (block is not bad)
* Description:  test if this block number is flagged as bad
*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&*/
int GLOB_FTL_Is_BadBlock(u32 wBlockNum)
{
	u32 *pbt = (u32 *)g_pBlockTable;

	nand_dbg_print(NAND_DBG_TRACE, "%s, Line %d, Function: %s\n",
		__FILE__, __LINE__, __func__);

	if (wBlockNum >= DeviceInfo.wSpectraStartBlock
		&& BAD_BLOCK == (pbt[wBlockNum] & BAD_BLOCK))
		return PASS;
	else
		return FAIL;
}

/*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&
* Function:     GLOB_FTL_Flush_Cache
* Inputs:       none
* Outputs:      PASS=0 / FAIL=1
* Description:  flush all the cache blocks to flash
*               if a cache block is not dirty, don't do anything with it
*               else, write the block and update the block table
* Note:         This function should be called at shutdown/power down.
*               to write important data into device
*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&*/
int GLOB_FTL_Flush_Cache(void)
{
	int i, ret;

	nand_dbg_print(NAND_DBG_WARN, "%s, Line %d, Function: %s\n",
		       __FILE__, __LINE__, __func__);

	for (i = 0; i < CACHE_ITEM_NUM; i++) {
		if (SET == Cache.array[i].changed) {
#if CMD_DMA
#if RESTORE_CACHE_ON_CDMA_CHAIN_FAILURE
			int_cache[ftl_cmd_cnt].item = i;
			int_cache[ftl_cmd_cnt].cache.address =
					Cache.array[i].address;
			int_cache[ftl_cmd_cnt].cache.changed = CLEAR;
#endif
#endif
			ret = write_back_to_l2_cache(Cache.array[i].buf, Cache.array[i].address);
			if (PASS == ret) {
				Cache.array[i].changed = CLEAR;
			} else {
				printk(KERN_ALERT "Failed when write back to L2 cache!\n");
				/* TODO - How to handle this? */
			}
		}
	}

	flush_l2_cache();

	return FTL_Write_Block_Table(FAIL);
}

/*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&
* Function:     GLOB_FTL_Page_Read
* Inputs:       pointer to data
*                   logical address of data (u64 is LBA * Bytes/Page)
* Outputs:      PASS=0 / FAIL=1
* Description:  reads a page of data into RAM from the cache
*               if the data is not already in cache, read from flash to cache
*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&*/
int GLOB_FTL_Page_Read(u8 *data, u64 logical_addr)
{
	u16 cache_item;
	int res = PASS;

	nand_dbg_print(NAND_DBG_DEBUG, "GLOB_FTL_Page_Read - "
		"page_addr: %llu\n", logical_addr);

	cache_item = FTL_Cache_If_Hit(logical_addr);

	if (UNHIT_CACHE_ITEM == cache_item) {
		nand_dbg_print(NAND_DBG_DEBUG,
			       "GLOB_FTL_Page_Read: Cache not hit\n");
		res = FTL_Cache_Write();
		if (ERR == FTL_Cache_Read(logical_addr))
			res = ERR;
		cache_item = Cache.LRU;
	}

	FTL_Cache_Read_Page(data, logical_addr, cache_item);

	return res;
}

/*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&
* Function:     GLOB_FTL_Page_Write
* Inputs:       pointer to data
*               address of data (ADDRESSTYPE is LBA * Bytes/Page)
* Outputs:      PASS=0 / FAIL=1
* Description:  writes a page of data from RAM to the cache
*               if the data is not already in cache, write back the
*               least recently used block and read the addressed block
*               from flash to cache
*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&*/
int GLOB_FTL_Page_Write(u8 *pData, u64 dwPageAddr)
{
	u16 cache_blk;
	u32 *pbt = (u32 *)g_pBlockTable;
	int wResult = PASS;

	nand_dbg_print(NAND_DBG_TRACE, "GLOB_FTL_Page_Write - "
		"dwPageAddr: %llu\n", dwPageAddr);

	cache_blk = FTL_Cache_If_Hit(dwPageAddr);

	if (UNHIT_CACHE_ITEM == cache_blk) {
		wResult = FTL_Cache_Write();
		if (IS_BAD_BLOCK(BLK_FROM_ADDR(dwPageAddr))) {
			wResult = FTL_Replace_Block(dwPageAddr);
			pbt[BLK_FROM_ADDR(dwPageAddr)] |= SPARE_BLOCK;
			if (wResult == FAIL)
				return FAIL;
		}
		if (ERR == FTL_Cache_Read(dwPageAddr))
			wResult = ERR;
		cache_blk = Cache.LRU;
		FTL_Cache_Write_Page(pData, dwPageAddr, cache_blk, 0);
	} else {
#if CMD_DMA
		FTL_Cache_Write_Page(pData, dwPageAddr, cache_blk,
				LLD_CMD_FLAG_ORDER_BEFORE_REST);
#else
		FTL_Cache_Write_Page(pData, dwPageAddr, cache_blk, 0);
#endif
	}

	return wResult;
}

/*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&
* Function:     GLOB_FTL_Block_Erase
* Inputs:       address of block to erase (now in byte format, should change to
* block format)
* Outputs:      PASS=0 / FAIL=1
* Description:  erases the specified block
*               increments the erase count
*               If erase count reaches its upper limit,call function to
*               do the ajustment as per the relative erase count values
*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&*/
int GLOB_FTL_Block_Erase(u64 blk_addr)
{
	int status;
	u32 BlkIdx;

	nand_dbg_print(NAND_DBG_TRACE, "%s, Line %d, Function: %s\n",
			       __FILE__, __LINE__, __func__);

	BlkIdx = (u32)(blk_addr >> DeviceInfo.nBitsInBlockDataSize);

	if (BlkIdx < DeviceInfo.wSpectraStartBlock) {
		printk(KERN_ERR "GLOB_FTL_Block_Erase: "
			"This should never occur\n");
		return FAIL;
	}

#if CMD_DMA
	status = GLOB_LLD_Erase_Block_cdma(BlkIdx, LLD_CMD_FLAG_MODE_CDMA);
	if (status == FAIL)
		nand_dbg_print(NAND_DBG_WARN,
			       "NAND Program fail in %s, Line %d, "
			       "Function: %s, new Bad Block %d generated!\n",
			       __FILE__, __LINE__, __func__, BlkIdx);
#else
	status = GLOB_LLD_Erase_Block(BlkIdx);
	if (status == FAIL) {
		nand_dbg_print(NAND_DBG_WARN,
			       "NAND Program fail in %s, Line %d, "
			       "Function: %s, new Bad Block %d generated!\n",
			       __FILE__, __LINE__, __func__, BlkIdx);
		return status;
	}
#endif

	if (DeviceInfo.MLCDevice) {
		g_pReadCounter[BlkIdx - DeviceInfo.wSpectraStartBlock] = 0;
		if (g_cBlockTableStatus != IN_PROGRESS_BLOCK_TABLE) {
			g_cBlockTableStatus = IN_PROGRESS_BLOCK_TABLE;
			FTL_Write_IN_Progress_Block_Table_Page();
		}
	}

	g_pWearCounter[BlkIdx - DeviceInfo.wSpectraStartBlock]++;

#if CMD_DMA
	p_BTableChangesDelta =
		(struct BTableChangesDelta *)g_pBTDelta_Free;
	g_pBTDelta_Free += sizeof(struct BTableChangesDelta);
	p_BTableChangesDelta->ftl_cmd_cnt = ftl_cmd_cnt;
	p_BTableChangesDelta->WC_Index =
		BlkIdx - DeviceInfo.wSpectraStartBlock;
	p_BTableChangesDelta->WC_Entry_Value =
		g_pWearCounter[BlkIdx - DeviceInfo.wSpectraStartBlock];
	p_BTableChangesDelta->ValidFields = 0x30;

	if (DeviceInfo.MLCDevice) {
		p_BTableChangesDelta =
			(struct BTableChangesDelta *)g_pBTDelta_Free;
		g_pBTDelta_Free += sizeof(struct BTableChangesDelta);
		p_BTableChangesDelta->ftl_cmd_cnt =
			ftl_cmd_cnt;
		p_BTableChangesDelta->RC_Index =
			BlkIdx - DeviceInfo.wSpectraStartBlock;
		p_BTableChangesDelta->RC_Entry_Value =
			g_pReadCounter[BlkIdx -
				DeviceInfo.wSpectraStartBlock];
		p_BTableChangesDelta->ValidFields = 0xC0;
	}

	ftl_cmd_cnt++;
#endif

	if (g_pWearCounter[BlkIdx - DeviceInfo.wSpectraStartBlock] == 0xFE)
		FTL_Adjust_Relative_Erase_Count(BlkIdx);

	return status;
}


/*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&
* Function:     FTL_Adjust_Relative_Erase_Count
* Inputs:       index to block that was just incremented and is at the max
* Outputs:      PASS=0 / FAIL=1
* Description:  If any erase counts at MAX, adjusts erase count of every
*               block by substracting least worn
*               counter from counter value of every entry in wear table
*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&*/
static int FTL_Adjust_Relative_Erase_Count(u32 Index_of_MAX)
{
	u8 wLeastWornCounter = MAX_BYTE_VALUE;
	u8 wWearCounter;
	u32 i, wWearIndex;
	u32 *pbt = (u32 *)g_pBlockTable;
	int wResult = PASS;

	nand_dbg_print(NAND_DBG_TRACE, "%s, Line %d, Function: %s\n",
		__FILE__, __LINE__, __func__);

	for (i = 0; i < DeviceInfo.wDataBlockNum; i++) {
		if (IS_BAD_BLOCK(i))
			continue;
		wWearIndex = (u32)(pbt[i] & (~BAD_BLOCK));

		if ((wWearIndex - DeviceInfo.wSpectraStartBlock) < 0)
			printk(KERN_ERR "FTL_Adjust_Relative_Erase_Count:"
					"This should never occur\n");
		wWearCounter = g_pWearCounter[wWearIndex -
			DeviceInfo.wSpectraStartBlock];
		if (wWearCounter < wLeastWornCounter)
			wLeastWornCounter = wWearCounter;
	}

	if (wLeastWornCounter == 0) {
		nand_dbg_print(NAND_DBG_WARN,
			"Adjusting Wear Levelling Counters: Special Case\n");
		g_pWearCounter[Index_of_MAX -
			DeviceInfo.wSpectraStartBlock]--;
#if CMD_DMA
		p_BTableChangesDelta =
			(struct BTableChangesDelta *)g_pBTDelta_Free;
		g_pBTDelta_Free += sizeof(struct BTableChangesDelta);
		p_BTableChangesDelta->ftl_cmd_cnt = ftl_cmd_cnt;
		p_BTableChangesDelta->WC_Index =
			Index_of_MAX - DeviceInfo.wSpectraStartBlock;
		p_BTableChangesDelta->WC_Entry_Value =
			g_pWearCounter[Index_of_MAX -
				DeviceInfo.wSpectraStartBlock];
		p_BTableChangesDelta->ValidFields = 0x30;
#endif
		FTL_Static_Wear_Leveling();
	} else {
		for (i = 0; i < DeviceInfo.wDataBlockNum; i++)
			if (!IS_BAD_BLOCK(i)) {
				wWearIndex = (u32)(pbt[i] & (~BAD_BLOCK));
				g_pWearCounter[wWearIndex -
					DeviceInfo.wSpectraStartBlock] =
					(u8)(g_pWearCounter
					[wWearIndex -
					DeviceInfo.wSpectraStartBlock] -
					wLeastWornCounter);
#if CMD_DMA
				p_BTableChangesDelta =
				(struct BTableChangesDelta *)g_pBTDelta_Free;
				g_pBTDelta_Free +=
					sizeof(struct BTableChangesDelta);

				p_BTableChangesDelta->ftl_cmd_cnt =
					ftl_cmd_cnt;
				p_BTableChangesDelta->WC_Index = wWearIndex -
					DeviceInfo.wSpectraStartBlock;
				p_BTableChangesDelta->WC_Entry_Value =
					g_pWearCounter[wWearIndex -
					DeviceInfo.wSpectraStartBlock];
				p_BTableChangesDelta->ValidFields = 0x30;
#endif
			}
	}

	return wResult;
}

/*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&
* Function:     FTL_Write_IN_Progress_Block_Table_Page
* Inputs:       None
* Outputs:      None
* Description:  It writes in-progress flag page to the page next to
*               block table
***********************************************************************/
static int FTL_Write_IN_Progress_Block_Table_Page(void)
{
	int wResult = PASS;
	u16 bt_pages;
	u16 dwIPFPageAddr;
#if CMD_DMA
#else
	u32 *pbt = (u32 *)g_pBlockTable;
	u32 wTempBlockTableIndex;
#endif

	nand_dbg_print(NAND_DBG_WARN, "%s, Line %d, Function: %s\n",
			       __FILE__, __LINE__, __func__);

	bt_pages = FTL_Get_Block_Table_Flash_Size_Pages();

	dwIPFPageAddr = g_wBlockTableOffset + bt_pages;

	nand_dbg_print(NAND_DBG_DEBUG, "Writing IPF at "
			       "Block %d Page %d\n",
			       g_wBlockTableIndex, dwIPFPageAddr);

#if CMD_DMA
	wResult = GLOB_LLD_Write_Page_Main_Spare_cdma(g_pIPF,
		g_wBlockTableIndex, dwIPFPageAddr, 1,
		LLD_CMD_FLAG_MODE_CDMA | LLD_CMD_FLAG_ORDER_BEFORE_REST);
	if (wResult == FAIL) {
		nand_dbg_print(NAND_DBG_WARN,
			       "NAND Program fail in %s, Line %d, "
			       "Function: %s, new Bad Block %d generated!\n",
			       __FILE__, __LINE__, __func__,
			       g_wBlockTableIndex);
	}
	g_wBlockTableOffset = dwIPFPageAddr + 1;
	p_BTableChangesDelta = (struct BTableChangesDelta *)g_pBTDelta_Free;
	g_pBTDelta_Free += sizeof(struct BTableChangesDelta);
	p_BTableChangesDelta->ftl_cmd_cnt = ftl_cmd_cnt;
	p_BTableChangesDelta->g_wBlockTableOffset = g_wBlockTableOffset;
	p_BTableChangesDelta->ValidFields = 0x01;
	ftl_cmd_cnt++;
#else
	wResult = GLOB_LLD_Write_Page_Main_Spare(g_pIPF,
		g_wBlockTableIndex, dwIPFPageAddr, 1);
	if (wResult == FAIL) {
		nand_dbg_print(NAND_DBG_WARN,
			       "NAND Program fail in %s, Line %d, "
			       "Function: %s, new Bad Block %d generated!\n",
			       __FILE__, __LINE__, __func__,
			       (int)g_wBlockTableIndex);
		MARK_BLOCK_AS_BAD(pbt[BLOCK_TABLE_INDEX]);
		wTempBlockTableIndex = FTL_Replace_Block_Table();
		bt_block_changed = 1;
		if (BAD_BLOCK == wTempBlockTableIndex)
			return ERR;
		g_wBlockTableIndex = wTempBlockTableIndex;
		g_wBlockTableOffset = 0;
		/* Block table tag is '00'. Means it's used one */
		pbt[BLOCK_TABLE_INDEX] = g_wBlockTableIndex;
		return FAIL;
	}
	g_wBlockTableOffset = dwIPFPageAddr + 1;
#endif
	return wResult;
}

/*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&
* Function:     FTL_Read_Disturbance
* Inputs:       block address
* Outputs:      PASS=0 / FAIL=1
* Description:  used to handle read disturbance. Data in block that
*               reaches its read limit is moved to new block
*&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&*/
int FTL_Read_Disturbance(u32 blk_addr)
{
	int wResult = FAIL;
	u32 *pbt = (u32 *) g_pBlockTable;
	u32 dwOldBlockAddr = blk_addr;
	u32 wBlockNum;
	u32 i;
	u32 wLeastReadCounter = 0xFFFF;
	u32 wLeastReadIndex = BAD_BLOCK;
	u32 wSpareBlockNum = 0;
	u32 wTempNode;
	u32 wReplacedNode;
	u8 *g_pTempBuf;

	nand_dbg_print(NAND_DBG_DEBUG, "%s, Line %d, Function: %s\n",
			       __FILE__, __LINE__, __func__);

#if CMD_DMA
	g_pTempBuf = cp_back_buf_copies[cp_back_buf_idx];
	cp_back_buf_idx++;
	if (cp_back_buf_idx > COPY_BACK_BUF_NUM) {
		printk(KERN_ERR "cp_back_buf_copies overflow! Exit."
		"Maybe too many pending commands in your CDMA chain.\n");
		return FAIL;
	}
#else
	g_pTempBuf = tmp_buf_read_disturbance;
#endif

	wBlockNum = FTL_Get_Block_Index(blk_addr);

	do {
		/* This is a bug.Here 'i' should be logical block number
		 * and start from 1 (0 is reserved for block table).
		 * Have fixed it.        - Yunpeng 2008. 12. 19
		 */
		for (i = 1; i < DeviceInfo.wDataBlockNum; i++) {
			if (IS_SPARE_BLOCK(i)) {
				u32 wPhysicalIndex =
					(u32)((~SPARE_BLOCK) & pbt[i]);
				if (g_pReadCounter[wPhysicalIndex -
					DeviceInfo.wSpectraStartBlock] <
					wLeastReadCounter) {
					wLeastReadCounter =
						g_pReadCounter[wPhysicalIndex -
						DeviceInfo.wSpectraStartBlock];
					wLeastReadIndex = i;
				}
				wSpareBlockNum++;
			}
		}

		if (wSpareBlockNum <= NUM_FREE_BLOCKS_GATE) {
			wResult = GLOB_FTL_Garbage_Collection();
			if (PASS == wResult)
				continue;
			else
				break;
		} else {
			wTempNode = (u32)(DISCARD_BLOCK | pbt[wBlockNum]);
			wReplacedNode = (u32)((~SPARE_BLOCK) &
					pbt[wLeastReadIndex]);
#if CMD_DMA
			pbt[wBlockNum] = wReplacedNode;
			pbt[wLeastReadIndex] = wTempNode;
			p_BTableChangesDelta =
				(struct BTableChangesDelta *)g_pBTDelta_Free;
			g_pBTDelta_Free += sizeof(struct BTableChangesDelta);

			p_BTableChangesDelta->ftl_cmd_cnt =
					ftl_cmd_cnt;
			p_BTableChangesDelta->BT_Index = wBlockNum;
			p_BTableChangesDelta->BT_Entry_Value = pbt[wBlockNum];
			p_BTableChangesDelta->ValidFields = 0x0C;

			p_BTableChangesDelta =
				(struct BTableChangesDelta *)g_pBTDelta_Free;
			g_pBTDelta_Free += sizeof(struct BTableChangesDelta);

			p_BTableChangesDelta->ftl_cmd_cnt =
					ftl_cmd_cnt;
			p_BTableChangesDelta->BT_Index = wLeastReadIndex;
			p_BTableChangesDelta->BT_Entry_Value =
					pbt[wLeastReadIndex];
			p_BTableChangesDelta->ValidFields = 0x0C;

			wResult = GLOB_LLD_Read_Page_Main_cdma(g_pTempBuf,
				dwOldBlockAddr, 0, DeviceInfo.wPagesPerBlock,
				LLD_CMD_FLAG_MODE_CDMA);
			if (wResult == FAIL)
				return wResult;

			ftl_cmd_cnt++;

			if (wResult != FAIL) {
				if (FAIL == GLOB_LLD_Write_Page_Main_cdma(
					g_pTempBuf, pbt[wBlockNum], 0,
					DeviceInfo.wPagesPerBlock)) {
					nand_dbg_print(NAND_DBG_WARN,
						"NAND Program fail in "
						"%s, Line %d, Function: %s, "
						"new Bad Block %d "
						"generated!\n",
						__FILE__, __LINE__, __func__,
						(int)pbt[wBlockNum]);
					wResult = FAIL;
					MARK_BLOCK_AS_BAD(pbt[wBlockNum]);
				}
				ftl_cmd_cnt++;
			}
#else
			wResult = GLOB_LLD_Read_Page_Main(g_pTempBuf,
				dwOldBlockAddr, 0, DeviceInfo.wPagesPerBlock);
			if (wResult == FAIL)
				return wResult;

			if (wResult != FAIL) {
				/* This is a bug. At this time, pbt[wBlockNum]
				is still the physical address of
				discard block, and should not be write.
				Have fixed it as below.
					-- Yunpeng 2008.12.19
				*/
				wResult = GLOB_LLD_Write_Page_Main(g_pTempBuf,
					wReplacedNode, 0,
					DeviceInfo.wPagesPerBlock);
				if (wResult == FAIL) {
					nand_dbg_print(NAND_DBG_WARN,
						"NAND Program fail in "
						"%s, Line %d, Function: %s, "
						"new Bad Block %d "
						"generated!\n",
						__FILE__, __LINE__, __func__,
						(int)wReplacedNode);
					MARK_BLOCK_AS_BAD(wReplacedNode);
				} else {
					pbt[wBlockNum] = wReplacedNode;
					pbt[wLeastReadIndex] = wTempNode;
				}
			}

			if ((wResult == PASS) && (g_cBlockTableStatus !=
				IN_PROGRESS_BLOCK_TABLE)) {
				g_cBlockTableStatus = IN_PROGRESS_BLOCK_TABLE;
				FTL_Write_IN_Progress_Block_Table_Page();
			}
#endif
		}
	} while (wResult != PASS)
	;

#if CMD_DMA
	/* ... */
#endif

	return wResult;
}

