[STM32F0] stc15单片机驱动W25Q16整页读取问题 求解

[复制链接]
 楼主| huohu52 发表于 2017-9-4 15:31 | 显示全部楼层 |阅读模式
用stc15的单片机驱动W25Q16,用地址读写数据都没问题,想问下,因为芯片擦除是最少一个扇区擦除,我要整页写数据前先要擦除的时候,该扇区被的其他数据会被擦除,这个怎么处理?在线等
 楼主| huohu52 发表于 2017-9-4 15:36 | 显示全部楼层
补充一点,因为是用的stc15的单片机,受片内RAM(2K)限制,不能定义数组data[4096]这样的数组,不能采用将整个扇区的数据读出->修改数组的值->擦写扇区->把数据写进去 这样操作
feelhyq 发表于 2017-9-4 15:49 | 显示全部楼层
擦除之前 把不需要擦除的数据线拷贝到 flash的其他地址,擦除之后再考回来
 楼主| huohu52 发表于 2017-9-4 15:51 | 显示全部楼层
feelhyq 发表于 2017-9-4 15:49
擦除之前 把不需要擦除的数据线拷贝到 flash的其他地址,擦除之后再考回来

谢谢你的回复,主要是stc15的单片机数据存储空间很有限,一个扇区4096个字节,单片机没那么大的数据存储量
feelhyq 发表于 2017-9-4 15:52 | 显示全部楼层
huohu52 发表于 2017-9-4 15:51
谢谢你的回复,主要是stc15的单片机数据存储空间很有限,一个扇区4096个字节,单片机没那么大的数据存储 ...

不需要那么大的空间,你可以先读256个字节出来,然后写到某个page里面去,依次类推,不就全部备份了吗?
擦除玩后,同样的考回来

评论

正解!原理正确,调试好即可。  发表于 2017-9-5 20:48
 楼主| huohu52 发表于 2017-9-4 15:56 | 显示全部楼层
feelhyq 发表于 2017-9-4 15:52
不需要那么大的空间,你可以先读256个字节出来,然后写到某个page里面去,依次类推,不就全部备份了吗?
...

整个是相当于把其中一个扇区当中转站,我也是这么想的,但是我测试的时候遇到了问题,不知道是哪里的问题,程序如下,你帮我看下:
void W25q16_PageWrite(uint page,uchar *DataBuffer,uint DataSize)
{
uint_32 DataAddr,Sector_Addr,Page_Addr,Zhong_Addr;
uint j;
uchar i;
j=page/16;
Sector_Addr=j*4096; //page/16Ϊ¸ÃÒ³ËùÔÚµÄÉÈÇø ³ËÒÔ4096ΪÉÈÇøµÄÊ×µØÖ·       
DataAddr=page*256;//Ò³µÄÆðʼÊ×µØÖ·

SectorErase(0); //ÉÈÇø0×öÖÐתվ ²Á³öÉÈÇø0µÄÊý¾Ý
for(i=0;i<16;i++) //ÉÈÇø°áÒÆÊý¾Ý Ä¿±êÉÈÇøÊý¾Ý->ÉÈÇø0
        {
        Zhong_Addr=256*i;
        Page_Addr=Sector_Addr+Zhong_Addr;
        W25Q16_Read(Page_Addr,Page_BUFFER,256);  //¶ÁȡĿ±êÉÈÇøÒ³Êý¾Ý
        W25Q16_Write(Zhong_Addr,Page_BUFFER,256);//Êý¾Ýдµ½ÖÐתÉÈÇøÒ³
        }
       
SectorErase(Sector_Addr);  //²Á³ýÄ¿±êÉÈÇøÊý¾Ý
for(i=0;i<16;i++)
        {
        Zhong_Addr=256*i;
        Page_Addr=Sector_Addr+Zhong_Addr;
        W25Q16_Read(Zhong_Addr,Page_BUFFER,256);//¶ÁÈ¡ÖÐתÉÈÇøÒ³Êý¾Ý
        //if(Page_Addr==DataAddr)
        if(i==(page%16))
          W25Q16_Write(Page_Addr,DataBuffer,DataSize);//Òª´æ´¢µÄÄ¿±êÒ³
        else
                W25Q16_Write(Page_Addr,Page_BUFFER,256);//Êý¾Ý×ªÒÆµ½Ä¿±êÉÈÇøÒ³
        }

}
 楼主| huohu52 发表于 2017-9-4 16:00 | 显示全部楼层
huohu52 发表于 2017-9-4 15:56
整个是相当于把其中一个扇区当中转站,我也是这么想的,但是我测试的时候遇到了问题,不知道是哪里的问题 ...

这个函数测试的时候,感觉像是扇区擦除函数有问题,要是在主函数里,先把待写入的page所在的扇区擦除,再执行这个函数,数据存储有有效,要是不先擦除,就写不进去,但是函数里也加了扇区擦除,不知道是哪里的问题
feelhyq 发表于 2017-9-4 16:14 | 显示全部楼层
huohu52 发表于 2017-9-4 16:00
这个函数测试的时候,感觉像是扇区擦除函数有问题,要是在主函数里,先把待写入的page所在的扇区擦除,再 ...

肯定是先擦除再写入
feelhyq 发表于 2017-9-4 16:16 | 显示全部楼层
huohu52 发表于 2017-9-4 16:00
这个函数测试的时候,感觉像是扇区擦除函数有问题,要是在主函数里,先把待写入的page所在的扇区擦除,再 ...

SectorErase(0); //ÉÈÇø0×öÖÐתվ ²Á³öÉÈÇø0µÄÊý¾Ý 这个擦除的地址怎么固定是0,好奇怪
 楼主| huohu52 发表于 2017-9-4 16:22 | 显示全部楼层
feelhyq 发表于 2017-9-4 16:16
SectorErase(0); //ÉÈÇø0×öÖÐתվ ²Á³öÉÈÇø0µÄÊý¾Ý 这个擦除的地址怎么固定是 ...

把第0扇区当成固定的中转站
 楼主| huohu52 发表于 2017-9-4 16:23 | 显示全部楼层
feelhyq 发表于 2017-9-4 16:16
SectorErase(0); //ÉÈÇø0×öÖÐתվ ²Á³öÉÈÇø0µÄÊý¾Ý 这个擦除的地址怎么固定是 ...

我想问一下,擦除的时候,扇区的地址是0-511吗?还是按照字节的地址,第一个扇区的地址是1还是4096?
feelhyq 发表于 2017-9-4 16:37 | 显示全部楼层
huohu52 发表于 2017-9-4 15:56
整个是相当于把其中一个扇区当中转站,我也是这么想的,但是我测试的时候遇到了问题,不知道是哪里的问题 ...

feelhyq 发表于 2017-9-4 16:39 | 显示全部楼层
SectorErase(Sector_Addr);  //²Á³ýÄ¿±êÉÈÇøÊý¾Ý  看看这个地址 是不是你要擦除sector的地址
 楼主| huohu52 发表于 2017-9-4 17:10 | 显示全部楼层
feelhyq 发表于 2017-9-4 16:39
SectorErase(Sector_Addr);  //²Á³ýÄ¿±êÉÈÇøÊý¾Ý  看看这个地址 是不是你要擦除sector的地 ...

sector的地址是0-511还是0 4096......这样???
feelhyq 发表于 2017-9-4 17:11 | 显示全部楼层
0  4096这样
feelhyq 发表于 2017-9-4 17:11 | 显示全部楼层
huohu52 发表于 2017-9-4 17:10
sector的地址是0-511还是0 4096......这样???

这个知识点去看flash手册就知道了,自己动手丰衣足食啊
 楼主| huohu52 发表于 2017-9-4 17:13 | 显示全部楼层
feelhyq 发表于 2017-9-4 17:11
这个知识点去看flash手册就知道了,自己动手丰衣足食啊

那我的就没错呀,不知道咋回事
mmuuss586 发表于 2017-9-4 19:48 | 显示全部楼层
huohu52 发表于 2017-9-4 17:13
那我的就没错呀,不知道咋回事

看了下没错,跟踪下程序,看是不是哪里被优化了,或者没改对
戈卫东 发表于 2017-9-4 20:27 | 显示全部楼层
换有8K RAM的单片机
 楼主| huohu52 发表于 2017-9-5 16:29 | 显示全部楼层
戈卫东 发表于 2017-9-4 20:27
换有8K RAM的单片机

单片机型号已经定了的
您需要登录后才可以回帖 登录 | 注册

本版积分规则

1

主题

14

帖子

0

粉丝
快速回复 在线客服 返回列表 返回顶部