
#1樓主:znFAT--單片機上的FAT32文件系統 之研發手記文章發表于:2009-12-05 22:04
znFAT--單片機上的FAT32文件系統 之研發手記
兩年前,我開始學習DIY MP3,剛開始我只是直接把MP3文件的數據放在單片機的FLASH中,讀取播放。但這樣受限于單片機FLASH的容量,使得根本裝不下整首的MP3數據,頂多能播放7、8秒鐘。這就需要一種大容量的存儲器,你可能會說:“用大容量的FLASH ROM芯片就可以了”。不錯,用諸如K9F、45DB系列的FLASHROM芯片容量是夠大了,但此時也許你也跟我一樣碰到了一個問題,MP3文件怎么放入到FLASH芯片中?你可能會說“用燒錄器就可以了!”。我要問的話,你見過商場里哪款MP3播放器是需要燒錄器的?基本都是通過USB直接拷的,或者是可以擴展存儲卡,如SD卡、CF卡,甚至U盤。要用USB把FLASH芯片作成U盤,可以用PDIUSBD12來實現(如果您對這個感興趣可以看看computer00的USB),對USB有一定了解的,都會知道想把U盤作出來,還是非常復雜的。所以最簡單的方法就是使用存儲卡,一方面可以使用讀卡器,直接在操作系統中把MP3拷入其中,另一方面單片機驅動SD卡的相關資料也比較全,便于研究。
文件系統的引出就由此而生??!問題是這樣的,將MP3文件拷入到SD卡中以后,下面我們要作的就是用單片機來讀取SD卡上的數據,以便于播放,拷入的MP3文件數據在SD卡的哪里???到哪個扇區中去讀???我們使用U盤或SD卡等存儲設備拷貝電影啊,歌曲啊,都是最平常的事情,你想過沒有,這些文件的數據存在SD卡上的什么地方嗎?它為什么要存在那個地方?
為了找到SD卡上的MP3數據,我開始研究相關內容,這些就是FAT32文件系統。研究起來以后,發現已經有很多現成的在單片機上或在ARM等芯片上用的FAT文件系統方案,比如FATFS(這個是最為著名的一個,用得也最多)等等,國內也有幾個,比如沁恒的文件系統庫(不過他不開源,是商業的東西)、ZLG/FS(他提供的還是應用于ARM上的,在單片機應用的少)等。我也曾經向單片機(我剛開始用的是STC89C58,后來開始用STC12C5A60S2,不過這也是今年才開始用)上去移植這些現成的方案,但移植并不順利。最后我打算不再用任何現有方案,自己研究自己寫。
于是我開始動手寫了一個最原始的方案,這個最原始的方案僅僅可以實現讀取根目錄下的某個文件,還非常不成熟,同時我在網上發了一篇文章《FAT32文件系統的存儲機制及其在單片機上的實現》(感興趣的話可以在網上找一下,不過這篇文章里講的非常膚淺)。我將這個文件系統方案的雛形用于MP3播放實驗,實現了讀SD卡MP3文件播放的功能。與此同時,我錄制了《51單片機實現FAT32文件系統》視頻教程(長達500分鐘),希望通過通俗全面的講解,讓廣大電子愛好者對文件系統有一個初頻的了解(不過,現在回想起來,錄制視頻教程的時候對文件系統的研究仍然還不算深刻)。因為我發現很多人雖然每天在用電腦,每天在聽MP3,每天在看電子書,但從不知道有文件系統這種東西存在,從來不納悶存在扇區中的數據在我們面前怎么就成為了一個個的文件。
我的SD卡MP3的基本功能雖然實現了,但我又在想:“難道國內就不能有一款開源的,好用的FAT32文件系統的方案嗎?”。我在前期研究的基礎上,又開始進行更深入的研究。也許你可以在1個月內,甚至1個星期,把文件系統的相關技術手冊通讀N遍,也可能在理論上搞得很明白(當然需要較高的悟性),但這離最終的實現還相差甚遠,或者說只是剛剛起步。一些國外的研究文件系統的組織都是很多人一起傾注很大精力在作的,像EFSL(比利時的開源項目)、FATFS(上面已經提到,它是從大量的wince源代碼中剝離出的fat文件系統源代碼,微軟的代碼)等。它們會給我們使用,但不會講給我們他們是怎么實現的,更重要的一點是,它們一般用于AVR、ARM等芯片上,如果想要在51單片機上使用,不能說不能用,但因為硬件資源有限,所以用起來會有麻煩。所以,我才打算在RAM僅有1K字節的STC國產51單片機上真正作一套功能完備,方便移植的,性能較高,完全從0原創的文件系統方案。
應用說這項工作工作量很大,主要是我不想僅僅去實現基本的功能,還希望能有功能上的創新。要實現的基本功能有:1、文件系統初始化 2、打開文件 3、讀取數據 4、文件重命名 5、復制文件 6、創建文件 7、添加數據 8、創建目錄 9、關閉文件 10、獲取剩余容量 11、獲取總容量 獨特具有的功能:我稱之為“多設備”(所謂的多設備功能,就是可以在運行的過程中動態的切換存儲設備的驅動,說明了就是文件系統可以穿梭于多種存儲設備之間,你會問這有什么用?我要說,這里所實現的每一項功能都有非常實際的應用,多設備最典型的應用就是可以在多種設備間進行文件的拷貝,如將SD卡上的某一文件拷貝到CF卡、U盤或是另一張SD卡上)
最大的工作量并不在于寫代碼,而在于測試代碼和改代碼。就像讀數據的功能,讀從文件里讀1000個字節,沒有問題,讀10000字節呢?仍然不會出錯嗎?又如打開文件這一功能,如果目錄里有5個文件,要打開其中某個文件沒有問題,那能保證目錄里有10000個文件的時候,打開這個文件仍然沒有問題嗎?能打開根目錄下的文件沒有問題,打開\A\B\C\D\E\F\G\H\IJ\K\K\K\K\L\A.TXT這樣的深層目錄下的文件,也會沒問題嗎?寫入文件數據時,寫入1個字節沒問題,寫入10K的數據也照樣沒有問題嗎?............像這種類似的情況有很多。憑我一個人的力量是不夠的,我找了很多網友,給他用我的代碼,并將問題反饋給我,我再加以修改。還有一個很重要的途徑是通過一些公司實際的工程項目,因為他們會有專門測試的環境,比如頻繁讀數據、長時間的運行等等。很多問題會在此期間暴露出來。在修改代碼的過程中,時常還會發現一些以前沒有看到的FAT32更深層的東西。到現在為止,我的文件系統方案已經較為完備,在穩定性與正確性上得到了一定的保障。
要著重說明的是所實現的一切功能,僅僅用了大約900字節的RAM,其中包括512字節的扇區數據緩沖。
到后期,我的文件系統開始在網上開源,為了讓大家能記住它,我給它起名為znFAT(意為振南的FAT32文件系統方案)。僅僅有znFAT代碼是遠遠不夠的,大家感興趣還是使用znFAT來作的一些實驗,比如讀SD卡上的TXT文本文件,作電子書;讀SD卡上的MP3文件作播放器;讀SD卡上的BMP文件,作數碼相框;在SD卡與CF卡之間進行文件的互拷;甚至我自己用51的串口作了一個Shell命令接口,來通超級終端敲入命令來實現相應的文件操作(這就是我在網上起名為“仿DOS”的實驗)。令我欣慰的是,現在已經有人開始在用znFAT來作一些實驗了,說明znFAT真正被人們用起來了。雖然還沒有像FATFS等方案那樣流行,但它仍然是完全MIC(Made In China)的。
代碼公布出來,并不意味著代碼就很成熟,反而會暴露出一些問題。其實最典型的一個問題就是:我提供的znFAT的代碼是基于51單片機的KEIL工程,但很多網友并不用51,而用像AVR、STM32、DSP、NIOSII等等。反應一些功能異常。這是對可移植性的很大考驗,可移植性要求在不同的硬件條件下,在代碼修改量不大的情況下,可以在其上運行,并且功能良好。所以我中途又搞了一陣子STM32(它是一種ARM7核的MCU),最終發現是不同CPU的差異而造成的,說得更具體一些是因為不同CPU的大小端問題。最終成功移植到STM32上,并將代碼在網上公布出來。與此同時,一個網友用LM的控制器也跑通了znFAT,并應用于項目,運行良好。
znFAT從開始作,到現在已有1年多,這期間研究不斷深化,現在的znFAT與當初的雛形已有極大的發展。原來的視頻教程與文檔資料現在已經覺得比較膚淺,所以在打算錄制新的視頻教程,以求更多的人知道文件系統,知道它的重要。我要說,存儲設備的扇區讀寫好實現,而建立在扇區讀寫基礎上的文件系統的實現,才是思想真正的升華,對研發能力最大的考驗。
為了更廣泛的普及文件系統的相關知識,也為了滿足很多對文件系統的需求和好奇(您難道沒有發現國內,乃至國外,還沒有一本專門講在嵌入式中構建和使用文件系統的書嗎?),在努力撰寫《振南的znFAT--單片機上的FAT32文件系統》一書。不地寫書過程漫長而辛苦,努力早日出來。
振南贈語
振嚇四方博為旨,
南極北斗自來朝。
電摯山河獨標新,
子聚吾來弄天狼。
原點出發終有始,
創業何達必親為。
無盡峰端難攀登,
限在你我掌當中。