mini2440硬件篇之Nand Flash
1.硬件原理
NandFlash在對大容量的數(shù)據(jù)存儲中發(fā)揮著重要的作用。相對于NorFlash,它具有一些優(yōu)勢,但它的一個(gè)劣勢是很容易產(chǎn)生壞塊,因此在使用NandFlash時(shí),往往要利用校驗(yàn)算法發(fā)現(xiàn)壞塊并標(biāo)注出來,以便以后不再使用該壞塊。NandFlash沒有地址或數(shù)據(jù)總線,如果是8位NandFlash,那么它只有8個(gè)IO口,這8個(gè)IO口用于傳輸命令、地址和數(shù)據(jù)。NandFlash主要以page(頁)為單位進(jìn)行讀寫,以block(塊)為單位進(jìn)行擦除。每一頁中又分為main區(qū)和spare區(qū),main區(qū)用于正常數(shù)據(jù)的存儲,spare區(qū)用于存儲一些附加信息,如塊好壞的標(biāo)記、塊的邏輯地址、頁內(nèi)數(shù)據(jù)的ECC校驗(yàn)和等。
1.1.壞塊管理
由于NANDFlash的工藝不能保證NAND的MemoryArray在其生命周期中保持性能的可靠,因此,在NAND的生產(chǎn)中及使用過程中會(huì)產(chǎn)生壞塊。壞塊的特性是:當(dāng)編程/擦除這個(gè)塊時(shí),不能將某些位拉高,這會(huì)造成PageProgram和BlockErase操作時(shí)的錯(cuò)誤,相應(yīng)地反映到StatusRegister的相應(yīng)位。
(1)固有壞塊,這是生產(chǎn)過程中產(chǎn)生的壞塊,一般芯片原廠都會(huì)在出廠時(shí)都會(huì)將壞塊第一個(gè)page的sparearea的第6個(gè)bit標(biāo)記為不等于0xff的值。
(2)使用壞塊,這是在NANDFlash使用過程中,如果BlockErase或者PageProgram錯(cuò)誤,就可以簡單地將這個(gè)塊作為壞塊來處理,這個(gè)時(shí)候需要把壞塊標(biāo)記起來。為了和固有壞塊信息保持一致,將新發(fā)現(xiàn)的壞塊的第一個(gè)page的sparearea的第6個(gè)Bit標(biāo)記為非0xff的值。
(3)壞塊管理
根據(jù)上面的這些敘述,可以了解NANDFlash出廠時(shí)在sparearea中已經(jīng)反映出了壞塊信息,因此,如果在擦除一個(gè)塊之前,一定要先check一下sparearea的第6個(gè)bit(512)或第1個(gè)bit(2k)是否是0xff,如果是就證明這是一個(gè)好塊,可以擦除;如果是非0xff,那么就不能擦除。
當(dāng)然,這樣處理可能會(huì)犯一個(gè)錯(cuò)誤―――“錯(cuò)殺偽壞塊”,因?yàn)樵谛酒僮鬟^程中可能由于電壓不穩(wěn)定等偶然因素會(huì)造成NAND操作的錯(cuò)誤。但是,為了數(shù)據(jù)的可靠性及軟件設(shè)計(jì)的簡單化,我們就要奉行“蔣委員長”的“寧可錯(cuò)殺一千,也決不放過一個(gè)”的宗旨。
(4)需要對前面由于PageProgram錯(cuò)誤發(fā)現(xiàn)的壞塊進(jìn)行一下特別說明。如果在對一個(gè)塊的某個(gè)page進(jìn)行編程的時(shí)候發(fā)生了錯(cuò)誤就要把這個(gè)塊標(biāo)記為壞塊,首先就要把其他好的page里面的內(nèi)容備份到另外一個(gè)空的好塊里面,然后,把這個(gè)塊標(biāo)記為壞塊。
當(dāng)然,這可能會(huì)犯“錯(cuò)殺”之誤,一個(gè)補(bǔ)救的辦法,就是在進(jìn)行完頁備份之后,再將這個(gè)塊擦除一遍,如果BlockErase發(fā)生錯(cuò)誤,那就證明這個(gè)塊是個(gè)真正的壞塊,那就毫不猶豫地將它打個(gè)“戳”吧!
(2)可能有人會(huì)問,為什么要使用sparearea的第六個(gè)bit作為壞塊標(biāo)記。這是NANDFlash生產(chǎn)商的默認(rèn)約定。
2.芯片手冊
K9F2G08U0B
2.1.特性
容量256MB
一頁2k+64;一塊128k+4k;
2.2.引腳描述
見手冊
2.3.指令集
2.4.讀
2.5.編程
2.6.擦除
2.7.讀ID
3.mini2440電路圖
4.S3C2440寄存器
4.1.控制器特性
1、支持讀/寫/編程N(yùn)ANDFLASH內(nèi)存
2、系統(tǒng)復(fù)位后nandflash的前4k代碼自動(dòng)copy到內(nèi)部sram,copy完成后從sram啟動(dòng),此時(shí)內(nèi)部sram被映射為nGCS0。(當(dāng)OM[1:0]=00時(shí)使能NANDFLASH啟動(dòng)模式)
3、支持硬件ECC校驗(yàn)
4、系統(tǒng)啟動(dòng)后內(nèi)部ram可以用做其他的用途。
4.2.操作Nand方法
1、設(shè)置nandflash配置寄存器NFCONF
2、向命令寄存器NFCMD寫入操作命令
3、向地址寄存器NFADDR寫入地址
4、讀/寫數(shù)據(jù)前要讀取狀態(tài)寄存器NFSTAT來判斷nandflash是否處于忙狀態(tài)。
4.3.ECC奇偶校驗(yàn)
S3C2440在讀/寫操作時(shí),自動(dòng)生成2048字節(jié)的奇偶校驗(yàn)碼。
NandFlash的頁為2048B。在讀寫的時(shí)候每頁會(huì)產(chǎn)生4個(gè)bit大小的ECC校驗(yàn)碼。
28bitECC校驗(yàn)碼=22bit線校驗(yàn)碼+6bit列校驗(yàn)碼
ECC產(chǎn)生模塊執(zhí)行以下步驟:
1:當(dāng)MCU寫數(shù)據(jù)到NAND時(shí),ECC產(chǎn)生模塊生成ECC碼。
2:當(dāng)MCU從NAND讀數(shù)據(jù)時(shí),ECC產(chǎn)生模塊生成ECC碼同時(shí)用戶程序?qū)⑺c先前寫入時(shí)產(chǎn)生的ECC碼作比較。
在自動(dòng)引導(dǎo)模式下,不進(jìn)行ECC檢測。因此,NANDFLASH的前4KB應(yīng)確保不能有位錯(cuò)誤(一般NANDFLASH廠家都確保)。
nand.h
/*******************************************************************
*Copyright(C),2011-2012,XXX.
*FileName:nand.h
*Author:HuangYinqing
*Version:1.0
*Date::2012-04-22
*Description:nandflash驅(qū)動(dòng).
*FunctionList:
*History:
******************************************************************/
#ifndef__NAND_H__
#define__NAND_H__
/*nandflash調(diào)試等級*/
#defineDBG_NAND_LEVEL1
/*nandflash信息*/
#defineNAND_PAGE_SIZE(2*1024)//==1頁2k
#defineNAND_BLOCK_SIZE(NAND_PAGE_SIZE*64)//==1塊128k
#defineNAND_SIZE(256*1024*1024)//==容量256M
/*操作命令*/
#defineCMD_READ10x00//頁讀命令周期1
#defineCMD_READ20x30//頁讀命令周期2
#defineCMD_READID0x90//讀ID命令
#defineCMD_WRITE10x80//頁寫命令周期1
#defineCMD_WRITE20x10//頁寫命令周期2
#defineCMD_ERASE10x60//塊擦除命令周期1
#defineCMD_ERASE20xd0//塊擦除命令周期2
#defineCMD_STATUS0x70//讀狀態(tài)命令
#defineCMD_RESET0xff//復(fù)位
#defineCMD_RANDOMREAD10x05//隨意讀命令周期1
#defineCMD_RANDOMREAD20xE0//隨意讀命令周期2
#defineCMD_RANDOMWRITE0x85//隨意寫命令
/*NFCONF設(shè)置時(shí)序*/
#defineTACLS1
#defineTWRPH02
#defineTWRPH10
/*NFCONT片選*/
#defineNF_nFCE_L(){rNFCONT&=~(1<<1);}//==打開片選
#defineNF_nFCE_H(){rNFCONT|=(1<<1);}//==關(guān)閉片選
/*讀寫數(shù)據(jù)*/
#defineNF_CMD(data){rNFCMD=(data);}//傳輸命令
#define NF_ADDR(addr) {rNFADDR = (addr);} //傳輸?shù)刂?