亚洲欧美第一页_禁久久精品乱码_粉嫩av一区二区三区免费野_久草精品视频

? 歡迎來到蟲蟲下載站! | ?? 資源下載 ?? 資源專輯 ?? 關于我們
? 蟲蟲下載站

?? nflash_1.c

?? ARM
?? C
?? 第 1 頁 / 共 2 頁
字號:

#include "k9f1208uom.h"

#include "SysConfig.h"

#ifdef _DEBUG_
#include "Uart1.h"
#endif

/*************************全局變量定義************************************************/

	
	union _K9fUnion DEV[2]; //支持0/1兩個設備
/*************************底層讀寫和延時定義************************************************/	
#define NFLASH_DELAY(count)   { volatile int i; for(i=0;i<count;i++);}

#define NFLASH_CMD_LATCH_WAIT   NFLASH_DELAY(10)
#define NFLASH_ADDR_LATCH_WAIT   NFLASH_DELAY(10)
#define NFLASH_READ_ID_WAIT      NFLASH_DELAY(10)
#define NFLASH_READ_STATUS_WAIT      NFLASH_DELAY(100)
#define NFLASH_INPUT_DATA_WAIT      NFLASH_DELAY(350)
#define NFLASH_RB_WAIT             NFLASH_DELAY(500)  //  NFLASH_DELAY(100)


void __inline K9F_WriteCommand(unsigned char dev,unsigned char comm)
{
	if(dev==0)
  		DEV0_K9F_COMMAND=comm; 	//發送命令
  	else
  		DEV1_K9F_COMMAND=comm; 
}
void __inline K9F_WriteData(unsigned char dev,unsigned char d) 
{
	if(dev==0)
  		DEV0_K9F_DATA=d; 	//發送數據
  	else
  		DEV1_K9F_DATA=d; 	
}
unsigned char __inline K9F_ReadData(unsigned char dev)
{
	if(dev==0)
  		return	DEV0_K9F_DATA; 	//接收數據
  	else
  		return	DEV1_K9F_DATA; 	 
}
void __inline  K9F_Enable(unsigned char dev)
{
	if(dev==0)
	{
		DEV0_K9F_ENABLE;
	}
	else
	{
		DEV1_K9F_ENABLE;
	}
}

void __inline  K9F_Disable(unsigned char dev)
{
	if(dev==0)
	{
		DEV0_K9F_DISABLE;
	}
	else
	{
		DEV1_K9F_DISABLE;
	}
}
/*******************************中間層讀寫操作函數××××××××××××××××××××××********************/

void K9F_WriteAddr(unsigned char dev,unsigned int block,unsigned int page) //發送地址block-4096,page-32
{
	unsigned int addr[4];
	addr[3]=(block>>11)&0x0001;
	addr[2]=(block&0x07f8)>>3;
	addr[1]=((block&0x0007)<<5)|page;
	addr[0]=0x00;  	//從第0地址開始
	if(dev==0)
	{
		DEV0_K9F_ADDR=addr[0];
		DEV0_K9F_ADDR=addr[1];
		DEV0_K9F_ADDR=addr[2];
		DEV0_K9F_ADDR=addr[3];//從低到高發送地址
	}
	else
	{
		DEV1_K9F_ADDR=addr[0];
		DEV1_K9F_ADDR=addr[1];
		DEV1_K9F_ADDR=addr[2];
		DEV1_K9F_ADDR=addr[3];
	}
}
void K9F_WriteCheckAddr(unsigned char dev,unsigned int block,unsigned int page) //發送地址block-4096,page-32
{
	unsigned int addr[4];
	addr[3]=(block>>11)&0x0001;
	addr[2]=(block&0x07f8)>>3;
	addr[1]=((block&0x0007)<<5)|page;
	addr[0]=0x05;  	//從第517地址開始C區
	
	if(dev==0)
	{
		DEV0_K9F_ADDR=addr[0];
		DEV0_K9F_ADDR=addr[1];
		DEV0_K9F_ADDR=addr[2];
		DEV0_K9F_ADDR=addr[3];//從低到高發送地址
	}
	else
	{
		DEV1_K9F_ADDR=addr[0];
		DEV1_K9F_ADDR=addr[1];
		DEV1_K9F_ADDR=addr[2];
		DEV1_K9F_ADDR=addr[3];
	}
	
}

void K9F_WriteBlockAddr(unsigned char dev,unsigned int block)	//檫除使用
{
	unsigned int addr[3];
	addr[2]=(block>>11)&0x0001;
	addr[1]=(block&0x07f8)>>3;
	addr[0]=((block&0x0007)<<5)&0x00e0;
	
	if(dev==0)
	{
		DEV0_K9F_ADDR=addr[0];
		DEV0_K9F_ADDR=addr[1];
		DEV0_K9F_ADDR=addr[2];//從低到高發送地址
	}
	else
	{
		DEV1_K9F_ADDR=addr[0];
		DEV1_K9F_ADDR=addr[1];
		DEV1_K9F_ADDR=addr[2];
	}
}
//復位*********************************************
//可以不用
  void K9F_Reset(unsigned char dev)//flash reset
 {
 	K9F_WriteCommand(dev,K9F_RESET);
 }
//讀ID**********************************************
unsigned int K9F_Read_Flash_Id(unsigned char dev)
{
	unsigned int i,j,k,l;
	K9F_Enable(dev);
	K9F_WriteCommand(dev,READ_K9F_ID);
	if(dev==0)
		DEV0_K9F_ADDR=0x00;
	else
		DEV1_K9F_ADDR=0x00;
	NFLASH_READ_ID_WAIT;
	i=K9F_ReadData(dev);//返回ID
	j=K9F_ReadData(dev);//返回ID
	k=K9F_ReadData(dev);//返回ID
	l=K9F_ReadData(dev);//返回ID
	K9F_Disable(dev);
	return (i<<24)|(j<<16)|(k<<8)|l;
}
//等待與成功失敗*********************************************
unsigned char K9F_Read_Status(unsigned char dev) //io6為1表示準備好io0為0表示成功
{
	unsigned char j=0x00;
	K9F_Enable(dev);
	K9F_WriteCommand(dev,READ_STATUS);
	j=K9F_ReadData(dev);//K9F_ReadData();
	while((j&0x40)==0) //如果I/O6為0就一直等待
	{
		NFLASH_READ_STATUS_WAIT;
		j=K9F_ReadData(dev);
	}
	K9F_Disable(dev);
	return j;  //準備好
	
}

//***************************************************************************************//
//FLASH上層操作函數
//***************************************************************************************//
//dev=0,板上FLASH,dev=1,卡上FLASH
void K9F_Init(unsigned char dev)
{
	
	 SMC_SMCBCR3         =  0x0000ffef  ; 
	 SET_K9F_ENABLE; //卡上nand_FLASH的E引腳設置為輸出
	 
	 if(K9F_ReadInfo(dev)==1)
	 {
		#ifdef _DEBUG_
			PutStr("  Have Creat info."); 
			PutNextLine();    
		#endif
	 	//已經建立信息
	 }
	 else
	 {
	 	#ifdef _DEBUG_
			PutStr("  Start to creat the info.");    
			PutNextLine();   
		#endif
	  	K9F_CreatInfo(dev);
	 }

}

//檫除塊*********************************************
unsigned char K9F_Erase_Block(unsigned char dev,unsigned int block)
{
		unsigned int j;
			
			block=K9F_GetBlock(dev,block);
			
			K9F_Enable(dev);
			K9F_WriteCommand(dev,ERASE_START);
			K9F_WriteBlockAddr(dev,block);  //寫地址
			K9F_WriteCommand(dev,ERASE_END);
			
			K9F_Disable(dev);
			
			NFLASH_RB_WAIT;
//			while(*PEDATDIR&0x0004==0);
			
			j=K9F_Read_Status(dev);
			if(j&0x01)
			{
			// 	AddBadBlock(block);
			 	return 0; //失敗
			}
			else 
			 return 1;//成功
	  
}
//讀一頁*********************************************
void K9F_ReadPage(unsigned char dev,unsigned int block,unsigned int page,unsigned char *pData)
{
	
	unsigned int i=0, k=512;//每個扇區有528個字節讀528字節  
	unsigned char *p=pData;
	        
	block=K9F_GetBlock(dev,block);
	        
	K9F_Read_Status(dev); 	
	K9F_Enable(dev);
	K9F_WriteCommand(dev,0);//從A-ARRAY開始
	K9F_WriteAddr(dev,block,page);  //寫地址
		
	NFLASH_INPUT_DATA_WAIT;   
	
	do {       
		*p=K9F_ReadData(dev);     //讀數據 
		i++;
		p++;
	}while(i<k);

	K9F_Disable(dev);
	
	NFLASH_DELAY(100000); //等待讀完成,后來添加。
}
//寫一頁*********************************************
unsigned char K9F_WritePage(unsigned char dev,unsigned int block,unsigned int page,unsigned char *pData)
{
	
	unsigned int i,j,k=512;
	unsigned char *p=pData;
       
//	Read_Status();    	
	block=K9F_GetBlock(dev,block);
	
	K9F_Enable(dev);
	K9F_WriteCommand(dev,0x00);
	K9F_WriteCommand(dev,0x80);   //寫開始
	K9F_WriteAddr(dev,block,page);  //寫地址
	
	NFLASH_RB_WAIT;   
	
	for(i=0;i<k;i++) //當k不為0時,就繼讀;否則就停止讀                                     
	{                                          
	 	K9F_WriteData(dev,*p);     //寫數據 
		p++;
		NFLASH_DELAY(10); //等待寫完成,后來添加。
	}
	K9F_WriteCommand(dev,0x10);//寫結束	
	
	NFLASH_DELAY(1000); //等待寫完成,后來添加。
	K9F_Disable(dev);
	
	NFLASH_DELAY(10000); //等待寫完成,后來添加。
//	while(*PEDATDIR&0x0004==0); //硬件判忙
	j=K9F_Read_Status(dev);
	if(j&0x01)
	{
//		AddBadBlock(block);
		return 0; //失敗表示為壞塊了
	}
	else 
		return 1;//成功
}

//*********************文件管理函數***************************//???稍后做處理

//讀取NAND-FLASH信息存到DEV0_K9fInfo結構中*********************************************
//return 1:已經處理的NAND
//return 0:沒有處理的NAND
unsigned char K9F_ReadInfo(unsigned char dev)
{
	 
	K9F_ReadPage(dev,0,0,DEV[dev].Dbuf);
	if((DEV[dev].Dbuf[0]==0x0aa)&&(DEV[dev].Dbuf[1]==0x55))
	{ //表示已經建立壞塊表
		return 1;
	}
	else
		return 0;

}

//把NAND-FLASH信息存到DEV0_K9fInfo結構中*********************************************
//return 1:
//return 0:
unsigned char K9F_WriteInfo(unsigned char dev)
{
 	unsigned int i,j;
 	unsigned char pDataCheck[512];
	//先擦除再寫入
	K9F_Erase_Block(dev,0);
	NFLASH_DELAY(1000);
	K9F_WritePage(dev,0,0,DEV[dev].Dbuf);
	//check
	K9F_ReadPage(dev,0,0,pDataCheck);
	for(i=0;i<512;i++)
	{
		if(pDataCheck[i]!=DEV[dev].Dbuf[i])
		{
			#ifdef _DEBUG_
				 PutStr("Write Info Error!");
		 	     PutNextLine();
			#endif
			return 0;	
		/**/
		}
	}
	return 1;
}
//獲得當前塊的映射塊地址***********************/
unsigned int K9F_GetBlock(unsigned char dev,unsigned int block)// 與記錄壞塊的表相對照的子程序
{
		unsigned int i;
		for(i=0;i<DEV[dev].K9fInfo.BlockTableNum;i++)
		{
			if(block==DEV[dev].K9fInfo.BlockTable[2*i])
				return DEV[dev].K9fInfo.BlockTable[2*i+1];//返回映射塊
			 //每項占用兩個單元
		}		
		return block;	//沒有查找到,就是當前塊。
}

//建立NAND信息表*********************************************
//包括容量大小,壞塊映射表等等
void K9F_CreatInfo(unsigned char dev)
{
	unsigned int block,page;
	volatile unsigned int i,j,k;
	unsigned int bStop;
	unsigned int bad1,bad2;
	unsigned int blockAmount;
	unsigned int DevCode;
	 
	//建立容量大小等信息 
	 DevCode=K9F_Read_Flash_Id(dev);
      switch(DevCode)
      {
      	case K9F1208_ID :
      		DEV[dev].K9fInfo.BlockAmount=4096;
      		DEV[dev].K9fInfo.BlockUsed=4016;
      		break;
      	case K9F5608_ID :
      		DEV[dev].K9fInfo.BlockAmount=2048;
      		DEV[dev].K9fInfo.BlockUsed=2008;	
      		break;
      	default:
      		break;
      }      
      
	//初始化壞塊結構
		DEV[dev].K9fInfo.BadBlockAmount=0; //初始壞塊總數為0
		DEV[dev].K9fInfo.BlockTableNum=0; //初始壞塊映射表項目為0
		DEV[dev].K9fInfo.BlockNextMux=DEV[dev].K9fInfo.BlockUsed;
		blockAmount=DEV[dev].K9fInfo.BlockAmount;

	//開始讀取壞塊
	for(block=0;block<blockAmount;block++)
	{
	
		for(page=0;page<2;page++)
		{
			K9F_Read_Status(dev); 
			K9F_Enable(dev);
			K9F_WriteCommand(dev,0x50);//從SPARE-ARRAY開始
			K9F_WriteCheckAddr(dev,block,page);  //寫地址
	
			NFLASH_INPUT_DATA_WAIT;   			  
	 		j=K9F_ReadData(dev);     //讀數據 
	 		NFLASH_READ_STATUS_WAIT;
			K9F_Disable(dev);
			
			if((j!=0xff)&&(page==0))
				bad1=1;
			if((j!=0xff)&&(page==1))
				bad2=1;
		}
		if((bad1==1)||(bad2==1))//壞的塊,添加
		{
				bad1=0;bad2=0;
				DEV[dev].K9fInfo.BadBlockNum[DEV[dev].K9fInfo.BadBlockAmount]=block;
				DEV[dev].K9fInfo.BadBlockAmount++;
				if(DEV[dev].K9fInfo.BadBlockAmount>=80)
				{
					#ifdef _DEBUG_
    					 PutStr("Bad block exceed 80.program halted!");
    			 	     PutNextLine();
  					#endif
				}
		}	
	}
	
	//建立壞塊映射表
	for(i=0;i<DEV[dev].K9fInfo.BlockUsed;i++)
	{
		for(j=0;j<DEV[dev].K9fInfo.BadBlockAmount;j++)
		{
			if(i==DEV[dev].K9fInfo.BadBlockNum[j])
			{
				
			   while(bStop==0) //找到一個不是壞塊為止,DEV0_K9fInfo.BlockNextMux
			  	{
			  		bStop=1; //先假設是好的
			  		for(k=0;k<DEV[dev].K9fInfo.BadBlockAmount;k++)
					{
						if(DEV[dev].K9fInfo.BlockNextMux==DEV[dev].K9fInfo.BadBlockNum[k])
						{
							//如果替換塊也是壞的,繼續往下找
							DEV[dev].K9fInfo.BlockNextMux++;
							bStop=0;
							break; //一發現是壞的就不再繼續判斷
						}	
					}
				}		
				DEV[dev].K9fInfo.BlockTable[2*DEV[dev].K9fInfo.BlockTableNum]=i; //前一項為壞塊
				DEV[dev].K9fInfo.BlockTable[2*DEV[dev].K9fInfo.BlockTableNum+1]=DEV[dev].K9fInfo.BlockNextMux;//后一項為替換好塊
				DEV[dev].K9fInfo.BlockTableNum++;   //壞塊替換表項數
				DEV[dev].K9fInfo.BlockNextMux++;
			}	
		}
	}
	//設置已經建立標志
	DEV[dev].K9fInfo.AppLen =255;
	DEV[dev].K9fInfo.IsCreat=0x55aa;
	//把NANDFLASH信息和壞塊映射表寫入BLOCK0-PAGE4
	K9F_WriteInfo(dev);
	
}
//添加壞塊到信息表中*********************************************
void AddToBadBlock(unsigned char dev,unsigned int block)
{
	unsigned int k;
	unsigned int bStop=0;
	DEV[dev].K9fInfo.BadBlockNum[DEV[dev].K9fInfo.BadBlockAmount]=block;
	DEV[dev].K9fInfo.BadBlockAmount++;
	
	while(bStop==0) //找到一個不是壞塊為止,DEV0_K9fInfo.BlockNextMux
  	{
  		bStop=1; //先假設是好的
  		for(k=0;k<DEV[dev].K9fInfo.BadBlockAmount;k++)
		{
			if(DEV[dev].K9fInfo.BlockNextMux==DEV[dev].K9fInfo.BadBlockNum[k])
			{
				//如果替換塊也是壞的,繼續往下找
				DEV[dev].K9fInfo.BlockNextMux++;
				bStop=0;
				break; //一發現是壞的就不再繼續判斷
			}	
		}
	}		
	DEV[dev].K9fInfo.BlockTable[2*DEV[dev].K9fInfo.BlockTableNum]=block; //前一項為壞塊
	DEV[dev].K9fInfo.BlockTable[2*DEV[dev].K9fInfo.BlockTableNum+1]=DEV[dev].K9fInfo.BlockNextMux;//后一項為替換好塊
	DEV[dev].K9fInfo.BlockTableNum++;   //壞塊替換表項數
	DEV[dev].K9fInfo.BlockNextMux++;	
}
//測試模塊*********************************************
void TestNandFlash(unsigned char dev)
{
	unsigned int i;
	unsigned char WriterBuf[512];
	unsigned char  ReadBuf[512];
	
	K9F_Init(dev);
	#ifdef _DEBUG_
      PutStr("  The nand flash is:");

?? 快捷鍵說明

復制代碼 Ctrl + C
搜索代碼 Ctrl + F
全屏模式 F11
切換主題 Ctrl + Shift + D
顯示快捷鍵 ?
增大字號 Ctrl + =
減小字號 Ctrl + -
亚洲欧美第一页_禁久久精品乱码_粉嫩av一区二区三区免费野_久草精品视频
亚洲日韩欧美一区二区在线| 国产亚洲精品超碰| 久久影视一区二区| 亚洲午夜久久久| 成人精品鲁一区一区二区| 欧美肥大bbwbbw高潮| 亚洲女同女同女同女同女同69| 久久精品国产精品亚洲红杏| 欧美视频三区在线播放| 亚洲欧美日韩国产另类专区| 国产黄色精品网站| 亚洲精品一区二区三区香蕉| 偷偷要91色婷婷| 欧美少妇一区二区| 亚洲激情一二三区| 一本久久综合亚洲鲁鲁五月天 | 亚洲va欧美va天堂v国产综合| 成人精品免费看| 中文字幕第一区二区| 精品一区二区三区香蕉蜜桃 | 欧美一区二区免费| 亚欧色一区w666天堂| 欧美偷拍一区二区| 一级精品视频在线观看宜春院 | 91国产福利在线| 亚洲色图欧洲色图| 色哟哟精品一区| 一色屋精品亚洲香蕉网站| 成人黄色小视频| 中日韩av电影| 不卡高清视频专区| 亚洲视频在线一区| 91福利精品第一导航| 亚洲一区二区影院| 日本一区二区三区免费乱视频| 国产99一区视频免费| 26uuu另类欧美亚洲曰本| 精品影视av免费| 久久久电影一区二区三区| 国产·精品毛片| 亚洲视频1区2区| 欧美色图激情小说| 麻豆精品一区二区综合av| 亚洲精品一区二区三区蜜桃下载| 国产综合色精品一区二区三区| 国产日韩欧美在线一区| 成人av电影免费观看| 亚洲综合激情小说| 日韩视频免费观看高清完整版| 韩国精品免费视频| 国产精品久久精品日日| 色综合天天综合| 视频一区在线视频| 国产欧美日韩精品一区| 一本大道久久a久久精二百 | 色av综合在线| 91视频www| 亚洲国产综合色| 日韩三级视频在线观看| 成人精品鲁一区一区二区| 一区二区三区中文在线观看| 欧美一级精品在线| 99re热视频精品| 免费成人美女在线观看.| 国产喂奶挤奶一区二区三区| 欧洲视频一区二区| 国产一区二区在线观看视频| 亚洲女人****多毛耸耸8| 日韩一区二区三区视频| 91碰在线视频| 国产在线精品国自产拍免费| 亚洲综合在线免费观看| 久久久久久久久免费| 欧美亚洲禁片免费| 成人app软件下载大全免费| 免费成人在线网站| 亚洲欧美激情一区二区| 久久综合九色综合欧美就去吻| 欧美午夜不卡在线观看免费| 亚洲欧美日韩在线播放| 91精品国产一区二区三区香蕉| 国产成人av电影免费在线观看| 午夜国产精品影院在线观看| 国产精品另类一区| 日韩天堂在线观看| 色呦呦一区二区三区| 国产乱码精品一品二品| 日本女人一区二区三区| 亚洲一区二区三区视频在线| 免费三级欧美电影| 亚洲欧洲av在线| 亚洲精品一线二线三线无人区| 欧美日韩精品三区| 不卡欧美aaaaa| 国产盗摄一区二区| 久久精品理论片| 免费观看一级欧美片| 五月婷婷综合在线| 亚洲国产裸拍裸体视频在线观看乱了| 国产精品久久久久7777按摩| 亚洲国产精品影院| 久久国产视频网| 亚洲一区在线视频| 国产精品久久久久影视| 久久综合999| 日韩欧美国产一区在线观看| 欧美人动与zoxxxx乱| 欧美日韩另类一区| 欧美精品久久99| 欧美丰满一区二区免费视频 | 精品一区二区三区在线观看国产 | 成人免费视频视频| 国产黄色成人av| 国产高清在线观看免费不卡| 国产九九视频一区二区三区| 国产精品一二三四五| 成熟亚洲日本毛茸茸凸凹| 成人高清av在线| 99精品国产91久久久久久| 一本色道久久加勒比精品| 亚洲精品国产一区二区精华液| 黄色精品一二区| 韩国午夜理伦三级不卡影院| 麻豆国产一区二区| 国产成人精品一区二区三区网站观看| 韩国三级中文字幕hd久久精品| 国产精品一级在线| 91麻豆视频网站| 欧美老肥妇做.爰bbww| 精品粉嫩超白一线天av| 久久人人97超碰com| 国产精品乱人伦中文| 日韩毛片精品高清免费| 午夜激情综合网| 久久99精品久久只有精品| 国产丶欧美丶日本不卡视频| 色综合色综合色综合色综合色综合| 在线观看亚洲精品| 精品国产乱码久久久久久久久| 国产蜜臀97一区二区三区| 亚洲国产精品久久人人爱| 精品一区二区三区在线观看国产| 国产盗摄一区二区| 欧美日产国产精品| 亚洲国产精品黑人久久久| 亚洲午夜av在线| 99视频一区二区| 欧美日韩一级片在线观看| 精品国产麻豆免费人成网站| 亚洲欧美自拍偷拍色图| 理论电影国产精品| www.久久精品| 欧美一级免费大片| 国产亚洲污的网站| 亚洲va欧美va国产va天堂影院| 国产精品影音先锋| 欧美色电影在线| 亚洲国产精品传媒在线观看| 亚洲成a人v欧美综合天堂| 从欧美一区二区三区| 91精品国产一区二区三区蜜臀| 亚洲天堂av一区| 国产精品18久久久久久久久 | 久久你懂得1024| 一区二区免费看| 国产成人免费视频精品含羞草妖精 | 精品少妇一区二区三区免费观看| 精品处破学生在线二十三| 亚洲精品你懂的| 国产成人免费av在线| 日韩精品资源二区在线| 一区二区三区在线视频观看| 国产美女一区二区三区| 欧美亚日韩国产aⅴ精品中极品| 中文无字幕一区二区三区| 美女mm1313爽爽久久久蜜臀| 91黄色激情网站| **网站欧美大片在线观看| 国产精品一卡二卡| 26uuu亚洲婷婷狠狠天堂| 日韩精品一二三| 欧美日韩mp4| 亚洲bt欧美bt精品| 欧美系列日韩一区| 亚洲视频网在线直播| 国产成人精品在线看| 精品日韩99亚洲| 蜜桃视频一区二区| 精品视频在线免费| 污片在线观看一区二区| 欧美日韩中字一区| 欧美性三三影院| 国产精品乱人伦中文| 国产在线精品不卡| www久久久久| 蜜桃久久av一区| 欧美成人伊人久久综合网| 麻豆精品视频在线观看| 精品国产乱码久久| 成人一区二区三区视频在线观看|