[nRF51822] 六、基于nRF51822平台的flash读写研究

 

前言

本文重点介绍flash的数据存取特性、flash的内存划分、一个简单的存取图片的内存管理方式,以及对flash写前删的时间、删后读的时间、写后读的时间进行测量的一个小实验。目的在于更全面了解flash自己特色(尤为是限制),从而方便设计出高效的内存管理驱动。函数

本文参考论文闪存的存储管理及索引方法研究_赵培_华中科技大博士论文_2011年性能

e-mail:beautifulzzzz@qq.com测试

 

 

1、Flash的特色 

  flash有几大奇葩的特色:ui

  闪存具备多种不用于磁盘的特性,例如:(1)闪存具备不对称的读写操做时间,即闪存的写时间远大于读时间,擦除时间远大于写时间。(2)闪存在重写同一闪存存储位置的数据以前须要执行擦除操做,即具备Erase-Before-Write特性。很显然,采用传统的“In-place-update"方法(即每次更新闪存页前均擦除整个闪存块)更新闪存的策略是不可行的。所以通常状况下,闪存存储系统采用”out-place-updata"方式更新闪存中的数据,即:将新版本的数据写入其余空闲的页面内,而后再将原始数据所在页面记为失效页面(Dead page 或Dirty Page),包含最新版本的闪存页面成为Live页面。当闪存中的空页面不足时,才执行擦除操做回收空间。若待回收的闪存块包含有效数据,则须要在执行擦除操做前将有效数据复制到闪存其余空闲页面,这一过程成为Garbage Collection。(3)每一个闪存块具备有限的擦除次数(通常为10K或100K次),若某个块超过最大擦除次数,则此块为“坏块”(Worn-out Block或Bad Block)。坏块的可靠性差,将会频繁出现读写错误,不能用于存储数据。(4)为了延长闪存使用寿命,闪存存储系统须要经过Wear-leveling机制尽可能使全部闪存块具备相同或类似的擦除次数。spa

  这些特性使得传统的基于磁盘设计的数据管理拌饭直接应用到闪存系统时的性能不好,不能充分发挥闪存本省的优良特性(SSD和机械式硬盘)。设计

 

2、GD25Q128B(16M)介绍

http://www.xinyahong.com/upLoad/product/month_1411/20141118164301603.pdf3d

2.一、GD25Q128B存储划分

  该款芯片在nRF51822EK_TM开发板上用~code

 

2.二、GD25Q128B操做速度

 

2.三、GD25Q128B的页写操做及函数

  • 像驱动代码里面的:void SpiFlash_Write_Data(char *pBuffer, uint8_t Block_Num, uint8_t Page_Num, uint32_t WriteBytesNum)
须要三个地址:Block_Num,Page_Num,addr
在该函数里将addr设为0
    pcmd[0] = Block_Num;
    pcmd[1] = Page_Num;
    pcmd[2] = 0;
 
  • void SpiFlash_Write_Sector_Data(char *pBuffer, uint8_t Block_Num, uint8_t Sector_Num, uint32_t WriteBytesNum)
写哪一个块中哪一个sector中的数据
首先计算将会占用多少page(1page=256bytes)
   Write_Page_Num = WriteBytesNum / 256;
   if((WriteBytesNum % 256) != 0) Write_Page_Num += 1;
 
  • uint8_t SpiFlash_Write_MorePage(uint8_t *pBuffer, uint32_t WriteAddr, uint32_t WriteBytesNum)

按页写,写多页,传入是地址和要写数据的量,内部写写的是零头,而后按页整页整页的写blog

 

3、Flash存取图片的具体案例(比较简单的一种内存管理)

一张图128X160的40960bytes=160X256(页),而1block为64KB=2^16=2^8X256≈256页(而2^7又小于160,所以把1block的64K用来存储一个图片)。所以:索引

 1 SPIFlash_Erase_Block(0);
 2 SPIFlash_Erase_Block(1);
 3 SPIFlash_Erase_Block(2);
 4 nrf_delay_ms(400);
 5 SpiFlash_Write_MorePage(gImage_A, 0, 40960);
 6 SpiFlash_Write_MorePage(gImage_B, 1<<16, 40960);
 7 SpiFlash_Write_MorePage(gImage_C, 2*(1<<16), 40960);
 8 //DispPic(pic_eval);
 9 DispPicFromSD(0);
10 DispPicFromSD(1);
11 DispPicFromSD(2);
注意:这里有一点小坑就是SpiFlash_Write_MorePage是先把零头写好,而后整页整页写,读是在DispPicFromSD中调用SpiFlash_Read_Data(buffer, PicNum , Address_S , 256);
void SpiFlash_Read_Data(uint8_t *pBuffer, uint8_t Block_Num , uint8_t Page_Num , uint32_t ReadBytesNum)          
 

4、实测Flash读写及清除的速度(为作更复杂、高效的存储管理作准备)

  因为第三节中介绍的一张图片约为1block大小,此外整个存储所有用来存放相同规格的图片,加之这些图片只须要存一遍,以后仅仅是读取这些图片(不涉及屡次删除、随机索引等状况),所以,在第三节中的存储利用方法还算能够知足需求。

  可是对于一种带有陀螺仪采集数据、存储和同步的一种手环:每帧17byte的传感器采集数据,(1)首先要知足采集数据的时候高速存储,(2)其次要知足同步数据时完整同步,(3)同时也要知足Flash满了以后能用新的数据覆盖老的数据。

  针对这3点要求能够按照下面的方法进行实施:

  针对上面实施办法,须要具体测试下存取的效果:

 

4.一、Write_Before_EraseSector与Read_Before_EraseSector延时时差计算:  

  实验核心代码:48行以上测试sector erase后最短多久进行write操做没有问题;48行如下是测试sector erase后最短多久read操做没有问题:

测试结果:erase sector后write至少须要100ms的延时(建议选120ms),write后read和erase sector后read均不须要延时。

 

4.二、Write_Before_EraseBlock与Read_Before_EraseBlock延时时差计算:

同4.1理解.

  测试结果:erase block后至少须要350ms的延时,才能进行有效写!(其中后半段是注释掉第50行代码致使的)

 

PS:erase full至少40s,测试6次未出现错误,实验同4.1,4.2。

 

 

PS:若是您以为还不错,点个赞,让更多人受益~

@link:http://pan.baidu.com/s/1pK13HUV(私用)
@beautifulzzzz 2016-03-19 continue~  
e-mail:beautifulzzzz@qq.com

相关文章
相关标签/搜索