WinCE中nandflash驅動開發介紹

2021-05-08 02:11:36 字數 3835 閱讀 1649

這裡介紹nandflash驅動,在wince中,有專門針對flash儲存裝置驅動的支援,一般傳統採用fal+fmd的架構。在wince最新的版本中,也就是windows ce6.0 r2中,還支援mdd+pdd的架構。在fal+fmd架構中,fal層由微軟來實現,我們需要實現fmd層的相關介面函式。在mdd+pdd的架構中,mdd替換了原來架構中的fal,而pdd相當於原來的fmd,只要實現pdd層就可以了。如果你的系統已經公升級到wince6.0 r2,那麼你應該可以在/wince600/public/common/oak/drivers目錄下面找到這兩種架構驅動的源**。 由於mdd+pdd的架構在wince6.0 r2中才有支援,本人也沒有實現過。所以這裡只介紹基於fal+fmd架構下,nandflash驅動的開發,這也是目前大家都採用的開發flash驅動的架構。

如上面所說,我們需要實現fmd層的相關介面,下面來介紹一下各個介面函式:

1. pvoid fmd_init(lpctstr lpactivereg, ppci_reg_info pregin, ppci_reg_info pregout): 這個是flash裝置的初始化函式。在wince啟動的時候,要載入flash驅動時,首先呼叫這個函式對flash裝置進行初始化。如果你的系統中有nandflash的controller,那麼你需要在這裡對你的nandflash controller進行初始化。如果沒有的話,你需要針對你的硬體設計進行相關的片選,時序等進行配置。返回乙個handle表示成功,這個handle將被fmd_deinit(..)函式用到,如果返回null表示失敗。

2. bool fmd_deinit(pvoid hfmd): 這個函式在nandflash驅動解除安裝的時候被呼叫,引數就是fmd_init函式返回的handle.一般在這個函式裡面,你可以釋放一些用到的資源,然後關閉nandflash controller。

3. bool fmd_readsector(sector_addr startsectoraddr, lpbyte psectorbuff, psectorinfo psectorinfobuff, dword dwnumsectors): 這個函式用於讀nandflash的乙個扇區。對於nandflash來說,分大page和小page,大page是2048個bytes一頁,小page是512個bytes一頁。所以大page每個扇區有2048 bytes,小page每個扇區有512 bytes。

startsectoraddr: nandflash物理扇區的起始位址,對於nandflash來說,就是nandflash中從哪個page開始。

psectorbuff:扇區資料buffer,從nandflash中讀出的每乙個扇區的資料都存放在這個buffer中。

psectorinfobuff:扇區資訊buffer,一般每個扇區的資訊會被儲存在nandflash的帶外資料中,針對小page,帶外資料有16 bytes,大page有64 bytes。從nandflash的帶外資料將該扇區的相關資訊讀出來,存放在這個buffer中。

dwnumsectors:讀取多少個扇區,對於nandflash來說相當於讀取多少個page。

4. bool fmd_writesector(sector_addr startsectoraddr, lpbyte psectorbuff, psectorinfo psectorinfobuff, dword dwnumsectors): 該函式用於寫nandflash的乙個扇區。引數和上面的fmd_readsector的引數意思一樣,就不多說了。

5. bool fmd_eraseblock(block_id blockid): 該函式用於擦出nandflash的乙個block,引數為要擦除nandflash的block位址,也就是第幾個block。

6. dword fmd_getblockstatus(block_id blockid): 該函式獲得nandflash中某乙個block的狀態。引數為nandflash的block位址。由於nandflash中可能有壞塊,所以針對nandflash,這個函式首先會檢查當前塊是否是壞塊,這個一般通過讀取當前block的第0個page和第1個page的帶外資料。對於小page nandflash一般是讀取第5個byte,對於大page nandflash一般讀取第0個byte,如果不為0xff表示該塊是壞塊。當然,至於具體該讀哪個byte,最好還是看一下所用nandflash的datasheet,確認一下,不同的廠家可能有所不同。如果發現該塊是壞塊,應該返回block_status_bad。如果不是壞塊,需要讀取這個塊的起始扇區的扇區資訊。如果讀該扇區資訊出錯,應該返回block_status_unknown,否則,判斷獨到的資訊,返回相應結果。

7. bool fmd_setblockstatus(block_id blockid, dword dwstatus): 該函式設定nandflash某個block的狀態,第乙個引數是nandflash的block位址,第二個是要設定的狀態。在這個函式中,首先檢查dwstatus是不是block_status_bad,如果是就對nandflash作壞塊標記,然後返回false。如果不是,就將dwstatus寫到該block的第0個page的扇區info中。這個函式和上面的函式正好是相反的。

8. bool fmd_getinfo(pflashinfo pflashinfo): 該函式用於返回flash的資訊。其中pflashinfo是乙個包含flash資訊的結構。

pflashinfo->flashtype:flash的型別,對於nandflash來說,應該是nand。

pflashinfo->wdatabytespersector:乙個扇區多少個bytes,對於大page是2048,對於小page是512。

pflashinfo->dwnumblocks:flash中總共有多少個block,查一下所用的nandflash的datasheet就知道了。

pflashinfo->wsectorsperblock:每個block中包含多少個扇區。

pflashinfo->dwbytesperblock:每個block中包含多少個bytes。

9. void fmd_powerdown()和void fmd_powerup(): 這兩個函式用於電源管理。fmd_powerdown()用於關閉flash裝置電源,fmd_powerup()用於恢復flash裝置電源。根據你所用處理器和相關硬體環境,去實現這兩個函式。不實現也不會影響nandflash的使用。

10. bool fmd_oemiocontrol(..): 就像很多的iocontrol函式一樣,根據不同的case,實現相應的功能。針對nandflash來說,這裡面的case不一定都需要實現。事實上,如果什麼都沒有實現,也不影響nandflash的使用。在wince的文件中,定義了一些需要實現的case,你可以實現,也可以不去實現。

對於nandflash來說,實現上述函式就可以了。在nandflash出廠的時候,廠家已經對nandflash中的壞塊進行了標記。所以第一次對nandflash操作的時候,不要隨便擦除nandflash,因為這樣可能會把壞塊標記擦掉,這樣你就判斷不出哪個塊是壞塊了。

關於ecc校驗,目前很多處理帶有nandflash controller,而且nandflash controller帶有硬體ecc功能。如果沒有硬體ecc,也可以使用軟體ecc,軟ecc的**可以在/wince600/public/common/oak/drivers/block/msflashfmd/ecc下找到。一般來說,ecc校驗會對512個byte產生3個位元組的校驗碼,也就是說對小page來說,每個page有3個位元組的ecc校驗碼;對於大page來說,有12個位元組。這些校驗碼應該在寫扇區資料的時候,被寫在扇區的帶外資料裡面。當讀扇區資料時,會先把資料讀出來,然後根據這些資料計算ecc,再和讀出來的ecc進行比較,如果一致,則表示正確。

WinCE中nandflash驅動開發介紹

這裡介紹nandflash驅動,在wince中,有專門針對flash儲存裝置驅動的支援,一般傳統採用fal fmd的架構。在wince最新的版本中,也就是windows ce6.0 r2中,還支援mdd pdd的架構。在fal fmd架構中,fal層由微軟來實現,我們需要實現fmd層的相關介面函式。...

WinCE中nandflash驅動開發介紹

先來談一下flash,flash是一種非易失儲存器,一般flash儲存裝置分為nandflash和norflash。這兩種flash各有優缺點。在讀寫速度上,norflash的讀速度快一些,nandflash的寫速度會快一些。nandflash的容量一般都比norflash大很多,而且相比 比較便宜...

NANDFLASH 中的Bad Block管理

1.skip block method 跳過壞塊方式 這種方法通俗易懂。這個演算法開始之前先讀取儲存器內的所有備用區域。那些被標 識成 bad block 的位址都被收集起來。接下來,資料被連續的寫入目標 flash 器件。當 目標位址與先前收集的 bad block 位址一致時,跳過壞塊,資料被寫...