如何使用Flash模擬EEPROM
在講解這篇博文前,首先要明白為什么使用Flash存儲來模擬EEPROM?
主要有以下幾個原因:
成本效益:許多微控制器(MCU)和系統(tǒng)芯片(SoC)內(nèi)置有Flash存儲,但沒有專門的EEPROM。使用已有的Flash存儲模擬EEPROM可以減少額外硬件成本。
更大的存儲容量:通常,F(xiàn)lash存儲提供比EEPROM更大的存儲容量。這使得在沒有犧牲太多物理空間的情況下可以存儲更多數(shù)據(jù)。
靈活性和可擴展性:通過軟件,可以靈活地設(shè)計和調(diào)整EEPROM模擬的大小和結(jié)構(gòu),以適應不同的應用需求。這種方法比使用固定大小的物理EEPROM更具可擴展性。
數(shù)據(jù)持久性:盡管Flash存儲的寫入次數(shù)有限,但它仍然能夠提供足夠的耐用性來滿足大多數(shù)應用的需要。通過適當?shù)臄?shù)據(jù)管理,可以最大限度地延長Flash存儲的壽命。
數(shù)據(jù)保護和安全性:許多現(xiàn)代微控制器提供了Flash存儲的安全功能,如寫入保護、加密等,這有助于保護存儲在Flash中的數(shù)據(jù)不被未經(jīng)授權(quán)訪問。
易于編程和集成:使用Flash存儲來模擬EEPROM可以充分利用現(xiàn)有的Flash編程工具和技術(shù),同時也簡化了硬件設(shè)計。
在使用Arduino開發(fā)時,有個內(nèi)置庫可以使用Flash模擬EEPROM,極大方便了嵌入式數(shù)據(jù)存儲的開發(fā)。
如果使用庫函數(shù),只是知道調(diào)用API,很難理解Flash模擬EEPROM的原理和方法,本篇博文將以AT32F413(flash:256KB)這款MCU為例,詳細介紹如何使用Flash模擬EEPROM。
實現(xiàn)代碼:https://download.csdn.net/download/m0_38106923/88717668
1
FLASH與EEPROM簡介
FLASH和EEPROM都為非易失性存儲器,在斷電后數(shù)據(jù)仍然可以長期保存,這為FLASH模擬 EEPROM提供了條件,F(xiàn)LASH與EEPROM特點對比如下表所示:
FLASH模擬EEPROM優(yōu)點:
低成本:可節(jié)約一顆EEPROM芯片;
存儲、讀取速度快:通訊速度快于使用I2C或者SPI通訊的EEPROM元件;
抗干擾能力強:由于FLASH在單片機內(nèi)部,不會存在通訊總線被外部干擾的問題;
容量可調(diào):可根據(jù)實際使用,靈活調(diào)整存儲空間大小。
2
FLASH模擬EEPROM原理
2.1、EERPOM數(shù)據(jù)結(jié)構(gòu)
由于FLASH在寫入數(shù)據(jù)前,需要將FLASH數(shù)據(jù)先擦除為0xFF,而FLASH擦除時通常為扇區(qū)擦除,例如AT32F403A的扇區(qū)大小為2K字節(jié),這個特性決定了不能簡單將舊數(shù)據(jù)擦除然后寫新數(shù) 據(jù),因為這樣會導致存儲在這個扇區(qū)內(nèi)的其他數(shù)據(jù)也被擦除,并且也會導致FLASH頻繁擦除而降低 其使用壽命。
所以FLASH模擬EEPROM的思路是:
新數(shù)據(jù)存儲不影響舊數(shù)據(jù);
盡量減少FLASH擦除次數(shù),延長FLASH使用壽命。
基于以上的考慮,我們設(shè)計了以下存儲結(jié)構(gòu):
EERPOM結(jié)構(gòu)
EEPROM由兩個頁組成:頁0和頁1,在使用的時候,1個頁處于有效狀態(tài),另外一個頁處于擦除 狀態(tài),讀取或者寫入數(shù)據(jù)都在有效狀態(tài)的頁進行。
數(shù)據(jù)格式
存儲的數(shù)據(jù)格式為數(shù)據(jù) + 數(shù)據(jù)地址,地址和數(shù)據(jù)都是16位方式存儲,每一次存儲占用32位也就是 4個字節(jié)。圖中data列為數(shù)據(jù),data address列為數(shù)據(jù)地址,flash address列為數(shù)據(jù)存儲的實際 flash地址偏移量。例如上圖中頁0的flash address=12處,數(shù)據(jù)為0x3003,數(shù)據(jù)地址為0x0002。
頁狀態(tài)標志
在第一個數(shù)據(jù)存儲區(qū),存儲頁狀態(tài)標志status,頁狀態(tài)標志有3種:
有效狀態(tài):EE_PAGE_VALID,status = 0x0000,讀取和寫數(shù)據(jù)在此頁進行;
數(shù)據(jù)轉(zhuǎn)移狀態(tài):EE_PAGE_TRANSFER,status = 0xCCCC,另外一頁滿了,正在傳輸有效數(shù) 據(jù)到本頁;
擦除狀態(tài):EE_PAGE_ERASED,status = 0xFFFF。 數(shù)據(jù)寫入 每一次寫入數(shù)據(jù)前,都會從頁起始地址開始尋找第一個未存儲數(shù)據(jù)的區(qū)域(值為0xFFFFFFFF),然后將待寫入的數(shù)據(jù)和數(shù)據(jù)地址寫到未存儲數(shù)據(jù)的區(qū)域。例如上圖中頁0的flash address = 20處,值 為0xFFFFFFFF,就是第一個未存儲數(shù)據(jù)的區(qū)域。
當知道了頁的大小后,就可以算出最大的變量存儲個數(shù):頁容量/4-1。例如當頁大小為1K時,最大 可存儲的變量數(shù)量為1024/4-1=255。需要注意的是,在實際使用中,應該盡量留出較多的空閑容 量,這樣可以減小FLASH擦除次數(shù),提高FLASH壽命。
另外數(shù)據(jù)地址不可以超過最大能存儲的變量數(shù)量,例如當頁大小為1K時,最大可存儲的變量數(shù)量為 1024/4-1=255,那么數(shù)據(jù)地址data address不可以大于255。
數(shù)據(jù)讀取
每一次讀取數(shù)據(jù)都會從頁結(jié)束地址開始向前尋找最后一個存儲的有效數(shù)據(jù),例如現(xiàn)在要讀取地址為 0x0000的數(shù)據(jù)。從上圖中看到flash address = 4和flash address = 16都是地址為0x0000的數(shù) 據(jù),因為最后一次存儲的數(shù)據(jù)為flash address = 16處的數(shù)據(jù),所以此時讀取地址0x0000的數(shù)據(jù)為 0x1234。
數(shù)據(jù)轉(zhuǎn)移
當一頁數(shù)據(jù)存滿了之后,會將數(shù)據(jù)傳輸?shù)娇臻e頁,將會執(zhí)行以下操作(以頁0滿,頁1空為例):
將頁1狀態(tài)標記為數(shù)據(jù)傳輸狀態(tài)(EE_PAGE_TRANSFER);
將所有有效數(shù)據(jù)復制到頁1;
擦除頁0;
將頁1狀態(tài)標記為有效狀態(tài)(EE_PAGE_VALID)。
EEPROM寫入流程如下所示:
2.2、EERPOM物理結(jié)構(gòu)
實現(xiàn)的EEPROM結(jié)構(gòu)如下圖所示,一個頁可以由1個或者多個扇區(qū)組成,可以根據(jù)實際應 用靈活的選擇扇區(qū)數(shù)量,扇區(qū)數(shù)量越多,可以存儲的數(shù)據(jù)量就越多。通常EEPROM存儲區(qū)定義在整 個FLASH末尾,這樣程序的燒錄、執(zhí)行和EEPROM區(qū)域互不影響。
*博客內(nèi)容為網(wǎng)友個人發(fā)布,僅代表博主個人觀點,如有侵權(quán)請聯(lián)系工作人員刪除。