📄 m25p80.c
字号:
#define CS1 IO0SET|=(1<<7) ///
#define CS0 IO0CLR|=(1<<7)
#define Wrn1 IO1SET|=(1<<24) ///
#define Wrn0 IO1CLR|=(1<<24)
#define QOut (IO0PIN&(1<<5))!=0//下降沿
#define CLK1 IO0SET|=(1<<4)
#define CLK0 IO0CLR|=(1<<4) //时钟
#define DIn1 IO0SET|=(1<<6)
#define DIn0 IO0CLR|=(1<<6) //上升沿
// Define M25P80 instructions 地址字节 伪数据 数据字节
#define WREN 0x06 //Write Enable 0 0 0
#define WRDI 0x04 //Write Disable 0 0 0
#define RDID 0x9F //读取标识 0 0 1~3
#define RDSR 0x05 //读取状态寄存器 read status register 0 0 1~。。。
#define WRSR 0x01 //写状态寄存器 write status register 0 0 1
#define READ 0x03 //读字节数据 read data bytes 3 0 1~
#define FAST 0x0B //高速读取字节数据 read data bytes at higher speed
#define PPRO 0x02 //页编程
#define ERSE 0xD8 //扇区擦除
#define ERBK 0xC7 //芯片擦除
#define PWDN 0xB9 //深度节电
#define RLSE 0xAB //退出深度节电
// Define the addresses
#define RAMBUF1_ADDRESS 0x0000
#define RAMBUF2_ADDRESS 0x0100
#define BUF_SIZE 64
uint32 Writeaddr=0;//一共4096页,每写够256页,
//擦除一次芯片的扇区,其中前255页写纪录,最后一页写特殊数据用。
uint32 Readaddr=0;
uchar rndData[BUF_SIZE]={0x00};
uchar TempRam[BUF_SIZE]={0x00};
// EEPROM access function prototypes
void InitFlash(void);
void WriteByte(uchar Wdata);
uchar ReadByte(void);
void M25PWait(void);
uchar M25PReadStatus(void);
void M25PWriteWait(void);
void M25PWriteEnable(void);
void M25PWriteDisable(void);
uchar M25PReadByte(uchar AD2, uchar AD1, uchar AD0);// one byte only
void M25PReadBytes(uchar AD2, uchar AD1, uchar AD0, uchar *buffer,uchar length);
void M25PWriteByte(uchar AD2, uchar AD1, uchar AD0, uchar databyte); // one byte only
void M25PWriteBytes(uchar AD2, uchar AD1, uchar AD0, uchar *buffer, uchar length);
void M25PWriteStatus(uchar databyte);
void M25PEraseSector(uint32 address);
void M25PEraseChip(void);
void M25PWait(void);
void M25PBulkErase(void);
void M25PFill(void);//Fill the chip with rand data
/***************************初始化flash*************************************************/
// FLASH access functions
void InitFlash(void)
{
//PINSEL0=0X00000000;
IO0DIR|=(1<<7)|(1<<4)|(1<<6);
IO1DIR|= (1<<24);
IO0DIR &=~(1<<5);
CS1;Wrn1;CLK0;
M25PWriteStatus(0x00);
}
// Function counts 8 clock cycles and waits for write to finish
void M25PWait(void) {
del(9);WDR();
}
/************************基本读写单元*****************************************/
void WriteByte(uchar Wdata)//写字节,先写数据的高位,上升沿
{
uchar i;
for(i=0;i<8;i++)
{
if(Wdata&0x80) DIn1;else DIn0;
CLK0;CLK1;
Wdata<<=1;
}
}
uchar ReadByte(void) //读字节,先读字节的高位,下降沿
{
uchar i,Rdata=0;
for(i=0;i<8;i++)
{
CLK1;CLK0;
Rdata<<=1;
if(QOut) Rdata|=0x01;
}
return Rdata;
}
/***************************读功能寄存器状态***********************************/
// Function reads the EEPROM status register
// SPDR will contain the status byte
uchar M25PReadStatus(void) {
uchar ReadState;
CS0; // Set CS_N low
WriteByte(RDSR); // write instruction
ReadState=ReadByte(); // clock in answer
CS1; // Set CS_N high
M25PWait();
return ReadState;
}
// Function waits for write to finish
void M25PWriteWait(void) {
// Wait until finished with write
while (M25PReadStatus()&0x01)WDR();
}
/*************************写功能寄存器状态*******************************************/
// Function writes the FlashROM status register
void M25PWriteStatus(uchar databyte)
{
M25PWriteEnable(); // Must enable write latch first
CS0; // Set CS_N low
WriteByte(WRSR);
WriteByte(databyte);
CS1; // Set CS_N high
M25PWait();
M25PWriteWait();
M25PWriteDisable();
}
/**************************读取数据******************************************/
// Function reads a byte at the specified address location
// SPDR will contain the read byte
uchar M25PReadByte(uchar AD2, uchar AD1, uchar AD0)
{
uchar ReadState;
CS0; // Set CS_N low
WriteByte(READ); // write instruction
WriteByte(AD2); // write address
WriteByte(AD1); // write address
WriteByte(AD0); // write address
ReadState=ReadByte();//读取单个字节
CS1; // Set CS_N high
M25PWait();
return ReadState;
}
// Function reads _length_ bytes from the specified address
// location and puts them in _buffer_
//可以读取得字节数位 0--255
void M25PReadBytes(uchar AD2, uchar AD1, uchar AD0, uchar *buffer, uchar length)
{
uchar i;
CS0; // Set CS_N low
WriteByte(READ); // write instruction
WriteByte(AD2); // write address
WriteByte(AD1); // write address
WriteByte(AD0); // write address
for (i=0; i<length; i++) *(buffer+i) =ReadByte();
CS1; // Set CS_N high
M25PWait();
}
/*************************写使能*******************************************/
// Function sets the write enable latch
void M25PWriteEnable(void) {
CS0; // Set CS_N low
WriteByte(WREN);// write instruction
CS1; // Set CS_N high
M25PWait();
}
// Function resets the write enable latch
void M25PWriteDisable(void)
{
CS0; // Set CS_N low
WriteByte(WRDI); // write instruction
CS1; // Set CS_N high
M25PWait();
}
/*************************写数据*******************************************/
// Function writes specified byte to the specified address location
void M25PWriteByte(uchar AD2, uchar AD1, uchar AD0, uchar databyte)
{
M25PWriteEnable(); // Must enable write latch first
CS0; // Set CS_N low
WriteByte(PPRO); // write instruction 页编程
WriteByte(AD2); // write address
WriteByte(AD1); // write address
WriteByte(AD0); // write address
WriteByte(databyte); // write data
CS1; // Set CS_N high
M25PWait();
M25PWriteWait();
M25PWriteDisable();
}
// Function writes _length_ bytes to the specified address location
void M25PWriteBytes(uchar AD2, uchar AD1, uchar AD0, uchar *buffer,uchar length) {
uint bytes_to_write=0;
M25PWriteEnable(); // Must enable write latch first
CS0; // Set CS_N low
WriteByte(PPRO); // write instruction 页编程
WriteByte(AD2); // write address
WriteByte(AD1); // write address
WriteByte(AD0); // write address
for(bytes_to_write=0;bytes_to_write<length;bytes_to_write++)
WriteByte(*(buffer+bytes_to_write));
// Post-processing
CS1; // Set CS_N high
M25PWait();
M25PWriteWait();
M25PWriteDisable();
}
//*************************擦除扇区,芯片*******************************************/
//The Sector Erase (SE) instruction sets to 1 (FFh) all bits inside the chosen sector.
void M25PEraseSector(uint32 address)//扇区擦除
{
uchar WAD0,WAD1,WAD2;
WAD0 = address&0xff;//0..7
WAD1 = (address >> 8)&0xff;//8..15
WAD2 = (address >> 16)&0xff;//16..23
M25PWriteEnable(); // Must enable write latch first
CS0;
WriteByte(ERSE);
WriteByte(WAD2); // write address
WriteByte(WAD1); // write address
WriteByte( WAD0 ); // write address
CS1;
M25PWait();
M25PWriteWait();
M25PWriteDisable();
}
void M25PEraseChip(void)
{
M25PWriteEnable(); // Must enable write latch first
CS0;
WriteByte(ERBK);
CS1;
M25PWait();
M25PWriteWait();
M25PWriteDisable();
}
void M25PBulkErase(void)//芯片擦除
{
M25PWriteEnable(); // Must enable write latch first
CS0;
WriteByte(ERBK);
CS1;
M25PWait();
M25PWriteWait();
M25PWriteDisable();
}
void M25PWritePage(uint32 address,uchar *buffer,uint length)
{
uchar WAD0,WAD1,WAD2;
WAD0 = address&0xff;//0..7
WAD1 = (address >> 8)&0xff;//8..15
WAD2 = (address >> 16)&0xff;//16..23
M25PWriteBytes(WAD2,WAD1,WAD0, buffer,length );
}
//************************写状态,检测数据到flash**************************/
void M25PWriteDate(void)
{
if((Writeaddr&0xffff)==0x0000)
{
M25PEraseSector(Writeaddr+1);del(10000);
M25PWritePage(Writeaddr, rndData, BUF_SIZE );
Writeaddr+=BUF_SIZE;//加一页 ,flash忽略高4位
}
else
{
M25PWritePage(Writeaddr, rndData, BUF_SIZE );
Writeaddr+=BUF_SIZE;//加一页
}
}
/************************读flash检测数据**************************/
void M25PReadDate(void)
{
uchar WAD0,WAD1,WAD2;
WAD0 = Readaddr&0xff;//0..7
WAD1 = (Readaddr >> 8)&0xff;//8..15
WAD2 = (Readaddr >> 16)&0xff;//16..23
M25PReadBytes(WAD2,WAD1,WAD0,TempRam,BUF_SIZE );
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -