Winbond W25QXX SPI Flash使用笔记

相较于EEPROM而言,SPI Flash的存储空间简直就是打开了一个新世界。以W25Q16为例,16Mb也就是2MB的空间,是AT24C08芯片的1KB空间的2048倍,价格也没有相差很多。同时使用SPI总线可以实现更高的读写速度,W25Qxx的SPI总线可以达到80MHz,这是IIC总线望尘莫及的,而且我比较喜欢用的STM32单片机的IIC总线总是让人那么揪心,所以我一直都是用的软件模拟IIC,而STM32的SPI则好用得多。但是SPI Flash也属于是闪存的一种,内部也是由Nand flash或者是Nor flash构成的,Flash存储结构的毛病就是在写入之前必须要执行擦除操作,就像STM32单片对自身的Flash空间进行编程的时候需要先擦除一页然后在写入数据,SPI Flash也一样,每次写入都要先擦除,不像EEPROM一样方便,想读哪个读哪个,想写哪个写哪个。并且W25Qxx系列的Flash的数据保存时间是20年,而AT24Cxx系列的EEPROM的数据保存时间为100年,当然我们不指望我们的产品能够用100年,至少这说明了EEPROM和FLASH各有优势,但是随着生活生产中数据量的增加,Flash的优势变得越来越突出。

由于之后的设计可能会使用SPI Flash代替EEPROM,所以特地用开发板上的W25Q16测试了一下Flash的性能。电路连接示意如下图:

Winbond W25QXX SPI Flash使用笔记

W25Qxx系列(W25Q80, W25Q16 and W25Q32)的Flash内部是按照Page、Sector、Block的结构来划分的,一个Page为256个Byte,一个Sector为16个Page也就是4KB,一个Block为16个Sector也就是64KB。

不像上学那会一样有时间自己写驱动代码了,现在直接拿例程代码进行修改了。总的来说W25Qxx系列的Flash的SPI控制逻辑就是:

1、拉低片选引脚

2、SPI写命令字

3、SPI读/写数据

4、拉高片选引脚

5、等待完成操作

数据擦除可以以Sector为单位也可以以Block为单位,进行Sector擦除的时候发送0x20命令字,然后跟随24位的存储地址,写入的24位地址应该是会将低12位忽略掉,不过数据手册上没有说明。进行Block(64KB)擦除的时候发送0xD8命令字,然后发送24位的地址,芯片内部同样会忽略低16位地址。擦除之后芯片内所有数据都是0xFF,这是Flash的特性,感兴趣的可以查阅资料,这里做个简单的说明。Flash存储单元中是无法写入位1的,只能写入位0,所以要写入数据的话要先将原来的数据都擦出成0xFF然后写入数据的时候遇到bit 1时不做处理,遇到bit 0时写入0即可。这就是为什么Flash进行写入之前需要进行擦除的原因。我在W25Q16上做了一个有趣的测试,在不擦除Sector的情况下写入,发现依然可以写入,读出写入的数据发现新写入的数据的0会将源数据中的对应位的1覆盖,但是新写入的1并不会覆盖原数据中对应位的0,印证了上面介绍的Flash原理。也就是说如果一个地址处的数据是0xFF,那么这个地址还可以写入任何数据,否则不可能完整写入任何数据。

数据写入的时候只能按照Page来写入,最多一次只能写256个字节,也就是一个页的空间,写入的时候可以不从页的开始地址写入,如果一次写入字节数溢出了一个页的空间,那么多出来的会从循环到页的开始地址处覆盖原来的数据,数据手册的10.2.14节说的很明白。页写的命令字为0x02,尾随24位的地址。

有时候我们还需要读取芯片的ID号,W25Qxx系列Flash有多个ID号,Manufacturer ID、Device ID、Unique ID、JEDEC ID,W25Q16读取到的Manufacturer ID为0xEF,Device ID为0x14,Unique ID没读出来,JEDEC ID没兴趣读......我感兴趣的Unique ID却没读出来,因为这个ID是可以当做程序加密使用的。算了,反正STM32也有唯一标识ID,写入到FLASH中也可以实现程序加密。

其实使用上面的4个命令就可以正常得使用SPI Flash工作了,其他的很多命令字都用不上。

 

 

 

 

 

 

 

上一篇:OSDI文章分享,论文(Determinizing Crash Behavior with a Verified Snapshot-Consistent Flash ...)的结构化文摘.


下一篇:谈谈跨界能力对技术公众号带来的改变