⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 mem25vf.c

📁 串行flash芯片应用程序 25vf020
💻 C
字号:

/**********************************************************************************************
* 当前版本:2.1.2
* 作    者:陈兆红
* 完成日期:2005年10月15日
**********************************************************************************************/

#include "mem25vf.h"
//===========================================================================
//SPI初始化,设置输入输出、SPI时钟等
//===========================================================================
void SPI_Init(void)
{
    
    /* Set MOSI and SCK output, all others input */
    PORTB=0xff;
    DDRB=0xBF;
    /* Enable SPI, Master, set clock rate fck/16 */
    SPCR = 0x52;
    SPSR = 0x00;
    CE11;  
    CE21;
    return;
}
//===========================================================================
//SPI 发送程序
//===========================================================================
void SPI_Send(uchar cData)
{
    uint i;
    i=0x0fff;
    /* Start transmission */
    SPDR = cData;
    /* Wait for transmission complete */
    while( (!(SPSR & 0x80)) && (i--))  ;
    SPSR = 0x00;
    return;
}
//===========================================================================
//SPI接收程序,通过发送任意虚字节产生SPI时钟
//===========================================================================
uchar SPI_Receive(void)
{
    uchar i;
    
    SPI_Send(0xFF);                //send a dummy byte to generate spi's clock
    DelayUs(2);
         
    i = SPDR;                       // play data from shift register
    
    return i;       
}
//===========================================================================
//读取flash状态
//===========================================================================
uchar Read_Status(uchar chipcs)
{
    uchar temp;
    if ( chipcs == 1 )
    {
        CE10;
        CE21;
    }
    else 
    {
        CE20;
        CE11;
    }
    //read command
    SPI_Send(MEM_READ_STATUS);
        
    //get data
    temp=SPI_Receive();
    
    CE11;
    CE21;
    
    return temp;
}
//===========================================================================
//写状态
//===========================================================================
void Write_Status(uchar status,uchar chipcs)
{
    if ( chipcs == 1 )
    {
        CE10;
        CE21;
    }
    else 
    {
        CE20;
        CE11;
    }
    
    SPI_Send(MEM_ENABLE_STATUS_WRITE);
    
    CE11;
    CE21;
    
    if ( chipcs == 1 )
    {
        CE10;
        CE21;
    }
    else 
    {
        CE20;
        CE11;
    }
    SPI_Send(MEM_WRITE_STATUS);
    SPI_Send(status);     
    CE11;  
    CE21;
    
    return ;
}
//===========================================================================
//写允许
//===========================================================================
void Write_Enable(uchar chipcs)
{
    //WP11;
    if ( chipcs == 1 )
    {
        CE10;
        CE21;
    }
    else 
    {
        CE20;
        CE11;
    }
    SPI_Send( MEM_WRITE_ENABLE );
    
    CE11;
    CE21;
}
//===========================================================================
//写禁止
//===========================================================================
void Write_Disable(uchar chipcs)
{
    
    if ( chipcs == 1 )
    {
        CE10;
        CE21;
    }
    else 
    {
        CE20;
        CE11;
    }
    SPI_Send( MEM_WRITE_DISABLE );
    
    CE11;
    CE21;
}

//读一个字节
uchar Mem_Read(ulong address,uchar chipcs)
{
    uchar temp;
    
    if ( chipcs == 1 )
    {
        CE10;
        CE21;
    }
    else 
    {
        CE20;
        CE11;
    }
    //read command
    SPI_Send(MEM_READ);
    //address to read
    temp=(uchar)((address&0xff0000)>>16);
    SPI_Send(temp);
    temp=(uchar)((address&0xff00)>>8);
    SPI_Send(temp);
    temp=(uchar)(address&0xff);
    SPI_Send(temp);
    //get data
    temp=SPI_Receive();
    
    CE11;
    CE21;
    DelayUs(1);
    return temp;
}
//===========================================================================

//===========================================================================
void  Mem_Read1(ulong address,uchar chipcs,uchar n,uchar *tp)
{ 
    uchar i,temp;

    if( chipcs == 1 )
      { CE10;  CE21;}
    else 
      {  CE20; CE11; }
    
    //read command
    SPI_Send(MEM_READ);
    //address to read
    temp=(uchar)((address&0xff0000)>>16);
    SPI_Send(temp);
    temp=(uchar)((address&0xff00)>>8);
    SPI_Send(temp);
    temp=(uchar)(address&0xff);
    SPI_Send(temp);
    
    //get data
    for(i=0;i<n;i++) tp[i]=SPI_Receive();   
    CE11;
    CE21;
    DelayUs(1);
    return ;
}
//===========================================================================

//===========================================================================
void read_flash(ulong addr,uchar chip_cs,uchar n,uchar *p)
{
       Mem_Read1(addr,chip_cs,n,p); 
}

//===========================================================================

//===========================================================================
uchar wait_idle(uchar chipcs)
{
    uchar i,temp;      
    for ( i=0; i<0xff; i++ ){
        temp=Read_Status(chipcs);
        if( !(temp & 0x01) )  return 1;
        DelayMs(1);
    }
    return 0;
}    
//===========================================================================
//扇区擦除
//===========================================================================
uchar Sector_Erase1(ulong address,uchar chipcs)
{
    uchar temp;    
    //uchar i;
    if(wait_idle(chipcs)==0) 
      return 0;
    
    Write_Status(0x00,chipcs);    
    Write_Enable(chipcs);
    if ( chipcs == 1 )
    {
        CE10;
        CE21;
    }
    else 
    {
        CE20;
        CE11;
    }
    //read command
    SPI_Send(MEM_SECTOR_ERASE);
    //address to read
    temp=(uchar)((address&0xff0000)>>16);
    SPI_Send(temp);
    temp=(uchar)((address&0xff00)>>8);
    SPI_Send(temp);
    temp=(uchar)(address&0xff);
    SPI_Send(temp);    
    CE11;
    CE21;
    if(wait_idle(chipcs)==0) 
      return 0;
    
    Write_Disable(chipcs);
    DelayMs(12);  //DelayMs(12);
    
    return  1;
}
//===========================================================================
//
//===========================================================================
void Sector_Erase(ulong address,uchar chipcs)
{
      uchar i=0;
      while(1)
      {
          if(Sector_Erase1(address,chipcs)==1) 
            return;
          else 
            i++;
          if(i>10) 
            return ;
          DelayMs(10);
      }
}  
//===========================================================================

//===========================================================================
//整片擦除
uchar Chip_Erase1(uchar chipcs){

    if(wait_idle(chipcs)==0) return 0;
    Write_Status(0x00,chipcs);
    Write_Enable(chipcs);
    
    if ( chipcs == 1 )
    {
        CE10;
        CE21;
    }
    else 
    {
        CE20;
        CE11;
    }
    //read command
    SPI_Send(MEM_CHIP_ERASE);
    CE11;
    CE21;

    if(wait_idle(chipcs)==0) return 0;
    Write_Disable(chipcs);
    DelayMs(83);  
    return 1;
}

//===========================================================================
//===========================================================================
void  Chip_Erase(uchar chipcs)
{
     uchar i=0;
     while(1)
     {
        if(Chip_Erase1(chipcs)==1) return ;
          else i++;
        if(i>10) return ;
          DelayMs(20);
     }
}     
//===========================================================================
//连续字节写入
//===========================================================================
uchar AAI_Write1(uchar num,ulong address,uchar *sData,uchar chipcs)
{
    uchar temp;
    uchar i;

    if(wait_idle(chipcs)==0) return 0;
    Write_Status(0x00,chipcs);

    if(wait_idle(chipcs)==0) return 0;
    Write_Enable(chipcs);

    if(wait_idle(chipcs)==0) return 0;
    if ( chipcs == 1 )
    {
        CE10;
        CE21;
    }
    else 
    {
        CE20;
        CE11;
    }
    
    //read command
    SPI_Send(MEM_AAI_WRITE);
    //address to read
    temp=(uchar)((address&0xff0000)>>16);
    SPI_Send(temp);
    temp=(uchar)((address&0xff00)>>8);
    SPI_Send(temp);
    temp=(uchar)(address&0xff);
    SPI_Send(temp);
    
    for ( i=0; i<num; i++ )
    {        
        SPI_Send(sData[i]);
        CE21;
        DelayUs(20);                  //byte program time,max 20uS
        CE20;
        if( i<(num-1) ) 
          SPI_Send(MEM_AAI_WRITE);    //AAI mode
    }
    
    Write_Disable(chipcs);
    
    CE11;
    CE21;
    DelayMs(2);  
    
    return 1;
}
//===========================================================================
// 连续往 Flash 中写入数据,
//===========================================================================
void  AAI_Write(uchar num,ulong address,uchar *sData,uchar chipcs)
{
      uchar i=0;
      
      while(1)
      {
        if(AAI_Write1(num,address,sData,chipcs)==1) 
          return ;
        else 
          i++;
        if(i>10) 
          return ;
        DelayMs(5);
      }
}

//===========================================================================
//===========================================================================

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -