|
- #include "all.h"
- uchar xdata W25X16_Write_Buffer[256];//写入的数据
- uchar xdata W25X16_Read_Buffer[256];//读出的数据
- ////发送数据
- //uchar SPI_Flash_Send_Byte(uchar dat)
- //{
- // while(!(SPI_DIO&0x02));//等待发送缓冲区为空//SPI_SR=TXE位
- // Flash_DO=dat;//将发送的数据送到数据寄存器
- // while(!(SPI_DIO&0x01));//等待接收缓冲区非空//SPI_SR=RXNE位
- // return SPI_DR;
- //}
- //向W25X16发送一个字节
- void SPI_Flash_Send_Reg(uchar dat)
- {
- uchar idata i;
- _nop_();
- _nop_();
- Flash_SCLK=1;
- _nop_();
- _nop_();
- for(i=0;i<8;i++)
- {
- Flash_SCLK=0;
- _nop_();
- _nop_();
- Flash_DIO=(bit)(dat&0x80);//先传送高位
- _nop_();
- _nop_();
- Flash_SCLK=1;//上升沿输入数据
- _nop_();
- _nop_();
- dat<<=1;
- }
- }
- //向W25X16读一个字节
- uchar SPI_Flash_Read_Data()
- {
- uchar idata i;
- uchar idata dat;
- _nop_();
- _nop_();
- Flash_SCLK=1;
- // _NOP_();
- // _NOP_();
- for(i=0,dat=0;i<8;i++)
- {
- Flash_SCLK=0;
- _nop_();
- _nop_();
- dat<<=1;//高位
- if(Flash_DO)//如果高位为1
- dat|=0x01;
- Flash_SCLK=1;//一个上升沿读一次
- _nop_();
- _nop_();
- }
- return dat;
- }
- //1、写使能
- void SPI_Flash_Write_Enable()
- {
- Flash_CS=0;//拉低选中芯片
- SPI_Flash_Send_Reg(0x06);//
- Flash_CS=1;//拉高不选中芯片
- }
- ////2.写禁止指令
- //void SPI_Flash_Write_Forbid()
- //{
- // Flash_CS=0;//拉低选中芯片
- // SPI_Flash_Send_Reg(0x04);//
- // Flash_CS=1;//拉高不选中芯片
- //}
- //3.读状态寄存器//测试擦除是否完成
- void SPI_Flash_Read_Status()
- {
- uchar Flash_statue=0;//状态寄存器值变量
- Flash_CS=0;//拉低选中芯片
- SPI_Flash_Send_Reg(0x05);//
- do
- {
- //Flash_statue=SPI_Send_byte(0xff);//
- Flash_statue=SPI_Flash_Read_Data();//
- }
- while(Flash_statue&0x01);//等待芯片非忙绿状态
- Flash_CS=1; //拉高不选中芯片
-
-
- }
- ////4.写状态寄存器指令
- //void SPI_Flash_Write_Status()
- //{
- // Flash_CS=0;//拉低选中芯片
- // SPI_Flash_Write_Enable();//使能
- // SPI_Flash_Send_Reg(0x01);//
- // SPI_Flash_Send_Reg(0x00);//写入状态的数据
- // //通过写入的状态的值可以把芯片的部分或全部设置成只读
- // //
- // Flash_CS=1;//拉高不选中芯片
- //}
- //5.读数据指令
- void SPI_Flash_Read_Byte(uchar *pBuffer,ulong ReadAddr,uint NumRead)
- {
- Flash_CS=0;//拉低选中芯片
- SPI_Flash_Send_Reg(0x03);//
- //24位地址
- SPI_Flash_Send_Reg((ReadAddr&0xff0000)>>16);//先发送高8位
- SPI_Flash_Send_Reg((ReadAddr&0xff00)>>8);//再发送中间8位
- SPI_Flash_Send_Reg(ReadAddr&0xff);//低8位
-
- while(NumRead--)
- {
- *pBuffer=SPI_Flash_Read_Data();//读一个字节的数据
- pBuffer++;//指向下一个要读取的地址
- }
-
- Flash_CS=1;//拉高不选中芯片
- }
- ////6.快速读数据指令
- //void SPI_Flash_Fast_Read_Data(uchar *pBuffer,ulong *ReadAddr,uint NumRead)
- //{
- // Flash_CS=0;//拉低选中芯片
- // SPI_Flash_Send_Reg(0x0B);//
- //
- // SPI_Flash_Send_Reg((ReadAddr&0xff0000)>>16);先发送高8位
- // SPI_Flash_Send_Reg((ReadAddr&0xff00)>>8);再发送中间8位
- // SPI_Flash_Send_Reg(ReadAddr&0xff);低8位
- //
- // SPI_Flash_Send_Reg(0xff);//等待8个时钟
- //
- // while(NumRead--)
- // {
- // *pBuffer=SPI_Flash_Read_Data();//读一个字节的数据
- // pBuffer++;//指向下一个要读取的地址
- // }
- //
- // Flash_CS=1;//拉高不选中芯片
- //}
- ////7.快速读双输出数据指令
- ////双读数据的读取函数
- //uchar SPI_Flash_Fast_Read_Data()
- //{
- // uchar idata i;
- // uchar idata dat=0;
- //
- // //双读
- // for(i=0;i<4;i++)
- // {
- // //读取DO 的数据
- // Flash_SCLK=1;
- // _NOP_();
- // _NOP_();
- // dat<<=1;//高位
- // if(Flash_DO)//如果高位为1
- // dat|=0x01;
- // Flash_SCLK=0;//下降沿
- // _NOP_();
- // _NOP_();
- // //读取DIO的数据
- // dat<<=1;//高位
- // if(Flash_DIO)//如果高位为1
- // dat|=0x01;
- // Flash_SCLK=1;//上升沿
- // _NOP_();
- // _NOP_();
- // }
- //}
- //void SPI_Flash_Fast_Two_Read_Data(uchar *pBuffer,ulong *ReadAddr,uint NumRead)
- //{
- // Flash_CS=0;//拉低选中芯片
- // SPI_Flash_Send_Reg(0x3B);//
- //
- // SPI_Flash_Send_Reg((ReadAddr&0xff0000)>>16);先发送高8位
- // SPI_Flash_Send_Reg((ReadAddr&0xff00)>>8);再发送中间8位
- // SPI_Flash_Send_Reg(ReadAddr&0xff);低8位
- //
- // SPI_Flash_Send_Reg(0xff);//等待8个时钟
- // while(NumRead--)
- // {
- // *pBuffer=SPI_Flash_Fast_Read_Data();//读一个字节的数据
- // pBuffer++;//指向下一个要读取的地址
- // }
- //
- // Flash_CS=1;//拉高不选中芯片
- //}
- //8.页编程指令
- void SPI_Flash_Write_Page(uchar *pBuffer,ulong WriteAddr,uint NumWrite)
- {
- SPI_Flash_Write_Enable();//先使能对芯片的操作
- Flash_CS=0;//拉低选中芯片
- SPI_Flash_Send_Reg(0x02);//
-
- SPI_Flash_Send_Reg((WriteAddr&0xff0000)>>16);//先发送高8位
- SPI_Flash_Send_Reg((WriteAddr&0xff00)>>8);//再发送中间8位
- SPI_Flash_Send_Reg(WriteAddr&0xff);//低8位
-
- while(NumWrite--)
- {
- SPI_Flash_Send_Reg(*pBuffer);//发送欲写入flash的数据
- pBuffer++;//指向下一个要写入的地址
- }
- Flash_CS=1;//拉高不选中芯片
- SPI_Flash_Read_Status();//等待写操作结束
- }
- ////页地址不对齐
- //void SPI_Flash_Write_Addr(uchar *pBuffer,ulong WriteAddr,uint NumWrite)
- //{
- // uchar Numofpage=0,Numofsingle=0,addr=0,count=0,time=0;//剩下的
- // addr=WriteAddr%256;//判断要写入的地址是否页对齐
- // count=256-addr;//剩下的地址
- // Numofpage=NumWrite/256;//一共写多少整页
- // Numofsingle=NumWrite%256;//还剩多少字节
- //
- // if(addr==0)//判断写入的地址是否页对齐
- // {
- // if(Numofpage===0)//如果只需写一页
- // {
- // SPI_Flash_Write_Page(pBuffer,WriteAddr,NumWrite);
- // }
- // else//不止写一页
- // {
- // while(Numofpage--)
- // {
- // SPI_Flash_Write_Page(pBuffer,WriteAddr,256);
- // WriteAddr+=256;//换下一页
- // pBuffer+=256;
- // }
- // SPI_Flash_Write_Page(pBuffer,WriteAddr,Numofsingle);//把剩下的字节写完
- // }
- // else //要写入的地址不是页对齐的地址
- // {
- // if(Numofpage==0)//只需要写一页
- // {
- // if(count<Numofsingle)//判断要剩下的地址如果不够写字节
- // {
- // temp=Numofsingle-count;//还剩下的字节
- // SPI_Flash_Write_Page(pBuffer,WriteAddr,count);//写满一页
- // WriteAddr+=count;//换下一页
- // pBuffer+=count;
- // SPI_Flash_Write_Page(pBuffer,WriteAddr,temp);//往新的一页里写剩下的数据
- // }
- // else//剩下的地址够写字节
- // {
- // SPI_Flash_Write_Page(pBuffer,WriteAddr,NumWrite);
- // }
- // }
- // else//不止写一页
- // {
- // NumWrite-=count;//先把空的地址填满之后还剩的字节
- // Numofpage=NumWrite/256;//总共还要写多少页
- // Numofsingle=NumWrite%256;//还剩下的字节数
- // SPI_Flash_Write_Page(pBuffer,WriteAddr,count);//把空的地址填满
- // WriteAddr+=count;//换下一页
- // pBuffer+=count;
- // while(Numofpage--)//整页
- // {
- // SPI_Flash_Write_Page(pBuffer,WriteAddr,256);
- // WriteAddr+=256;//换下一页
- // pBuffer+=256;
- // }
- // if(Numofsingle!=0)
- // {
- // SPI_Flash_Write_Page(pBuffer,WriteAddr,Numofsingle);//把剩下的写完
- // }
- // }
- // }
- // }
- //}
- ////9.块擦除指令(64KB)256页
- //void SPI_Flash_Block_Erase(ulong BlockAddr)
- //{
- // SPI_Flash_Write_Enable();//写使能
- // Flash_CS=0;//拉低选中芯片
- // SPI_Flash_Send_Reg(0xD8);//
- //
- // SPI_Flash_Send_Reg((BlockAddr&0xff0000)>>16);先发送高8位
- // SPI_Flash_Send_Reg((BlockAddr&0xff00)>>8);再发送中间8位
- // SPI_Flash_Send_Reg(BlockAddr&0xff);低8位
- //
- // Flash_CS=1;//拉高不选中芯片
- // SPI_Flash_Read_Status();//等待块清除操作完成
- //}
- //10.扇区擦除(4KB)16页
- void SPI_Flash_Section_Erase(ulong SectionAddr)
- {
- SPI_Flash_Write_Enable();//写使能
- Flash_CS=0;//拉低选中芯片
- SPI_Flash_Send_Reg(0x20);//
-
- SPI_Flash_Send_Reg((SectionAddr&0xff0000)>>16);//先发送高8位
- SPI_Flash_Send_Reg((SectionAddr&0xff00)>>8);//再发送中间8位
- SPI_Flash_Send_Reg(SectionAddr&0xff);//低8位
-
- Flash_CS=1;//拉高不选中芯片
- SPI_Flash_Read_Status();//等待扇区操作完成
- }
- ////11.芯片擦除指令
- //void SPI_Flash_Chip_Erase()
- //{
- // SPI_Flash_Write_Enable();//写使能
- // Flash_CS=0;//拉低选中芯片
- // SPI_Flash_Send_Reg(0xc7);//
- // Flash_CS=1;//拉高不选中芯片
- // SPI_Flash_Read_Status();//等待块清除操作完成
- //}
- ////12.芯片掉电命令
- //void SPI_Flash_Power-Fail()
- //{
- // Flash_CS=0;//拉低选中芯片
- // SPI_Flash_Send_Reg(0xB9);//
- // Flash_CS=1;//拉高不选中芯片
- // SPI_Flash_Read_Status();//等待块清除操作完成
- //}
- //13.芯片掉电释放/器件ID命令
- //14.芯片制造商/器件ID命令
- ////15.JEDEC ID序列指令
- //ulong SPI_Flash_Read_ID()
- //{
- // ulong temp=0,temp1=0,temp2=0,temp3=0;//Flash暂存变量
- // Flash_CS=0;//拉低选中芯片
- // SPI_Flash_Send_Reg(0x9F);//
- // SPI_Flash_Send_Reg(0xff);
- // temp1=SPI_Flash_Read_Data();//从flash读取第一个字节数据
- // SPI_Flash_Send_Reg(0xff);
- // temp2=SPI_Flash_Read_Data();//从flash读取第一个字节数据
- // SPI_Flash_Send_Reg(0xff);
- // temp3=SPI_Flash_Read_Data();//从flash读取第一个字节数据
- // Flash_CS=1;//拉高不选中芯片
- // temp=(((temp1<<16)|temp2<<8)|temp3);//拼合数据组成ID序列
- // return temp;//返回序列号
- //}
复制代码
本人大二新生,暑假期间写了一点点基本程序,开发版是STC8A8K的,我在初学期间发现在这个板子的资料比较少,学习起来不太方便。以下程序本人都亲自测试过,有个别没有搞明白的,本人也都做了标记,希望能给初学者一点帮助,另外欢迎大佬纠正错误,完善程序。
|
-
TIM图片20190825201502.png
(40.74 KB, 下载次数: 64)
-
TIM图片20190825201526.png
(56.96 KB, 下载次数: 61)
-
-
STC8A8K原理图.pdf
258.34 KB, 下载次数: 63, 下载积分: 黑币 -5
原理图
-
-
STC8手册-20180507.pdf
8.21 MB, 下载次数: 43, 下载积分: 黑币 -5
数据手册
-
-
stc8a8k单个程序.zip
1.01 MB, 下载次数: 175, 下载积分: 黑币 -5
单个程序
-
-
stc8a8k.zip
98.75 KB, 下载次数: 125, 下载积分: 黑币 -5
一个工程多个文件
|