📄 flash.c
字号:
/****************************************************************
** *
** FILE : flash.C *
** COPYRIGHT : (c) 2004 .Xiamen Yaxon NetWork CO.LTD *
** *
** 2004.12.24 *
****************************************************************/
#include "includes.h"
#include "bsp.h"
#include "ErrTask.h"
#include "uart_drv.h"
#include "flash.h"
#include "flashimg.h"
static INT16U tempdata;
/**************************************************************************
检测flash的DQ6位,确认擦除的完成
**************************************************************************/
static void readtogglebit(void)
{
INT16U read1, read2;
for(;;) {
read1 = *(volatile INT16U *)SST_BASE_ADDR & 0x4040;
read2 = *(volatile INT16U *)SST_BASE_ADDR & 0x4040;
if (read1 == read2) break;
}
}
void ProgramFlash_AtAbsAddr(INT16U *addr, INT8U *buffer, INT32U length)
{
INT32U len;
INT16U *gBuffer;
len = (length + 1)/2; //计算半字长度.
if(1 == ((INT32U)buffer %2) ) ErrExit(ERR_FLASH_WRITEADDR);
gBuffer = (INT16U *)buffer;
while (len-- > 0)
{
*((volatile INT16U *)SST_BASE_ADDR + SST_ADDR_UNLOCK1) = SST_DATA_UNLOCK1; //解锁.
*((volatile INT16U *)SST_BASE_ADDR + SST_ADDR_UNLOCK2) = SST_DATA_UNLOCK2;
*((volatile INT16U *)SST_BASE_ADDR + SST_ADDR_UNLOCK1) = SST_SETUP_WRITE;
*addr++ = *gBuffer++; //写入数据.
readtogglebit(); //检测写入是否成功.
}
}
void HWordProgram_Flash(INT16U nSector, INT32U offset, INT16U prghword)
{
tempdata = prghword;
//if (nSector >= 204 || nSector < 76) ErrExit(ERR_FLASH_WRITEADDR);
if (offset >= SST_SECTOR_BYTE_SIZE) ErrExit(ERR_FLASH_WRITEADDR);
if (offset%2) ErrExit(ERR_FLASH_WRITEADDR);
ProgramFlash_AtAbsAddr((INT16U *)FlashAbsAddr(nSector, offset), (INT8U *)&tempdata, 2);
}
void FlashWrite(INT16U nSector, INT32U offset, INT8U *buffer, INT32U length)
{
if (offset >= SST_SECTOR_BYTE_SIZE) ErrExit(ERR_FLASH_WRITEADDR);
if (offset%2) ErrExit(ERR_FLASH_WRITEADDR);
ProgramFlash_AtAbsAddr((INT16U *)FlashAbsAddr(nSector, offset), buffer, length);
}
void SectorErase_Flash(INT16U nSector)
{
//if (nSector >= 204 || nSector < 76) ErrExit(ERR_FLASH_WRITEADDR);
*((volatile INT16U *)SST_BASE_ADDR + SST_ADDR_UNLOCK1) = SST_DATA_UNLOCK1; //连续解锁.
*((volatile INT16U *)SST_BASE_ADDR + SST_ADDR_UNLOCK2) = SST_DATA_UNLOCK2;
*((volatile INT16U *)SST_BASE_ADDR + SST_ADDR_UNLOCK1) = SST_SETUP_ERASE;
*((volatile INT16U *)SST_BASE_ADDR + SST_ADDR_UNLOCK1) = SST_DATA_UNLOCK1;
*((volatile INT16U *)SST_BASE_ADDR + SST_ADDR_UNLOCK2) = SST_DATA_UNLOCK2;
*((volatile INT16U *)FlashAbsAddr(nSector, 0)) = SST_SECTOR_ERASE; //写入擦除命令.
readtogglebit();
}
void ChipErase_Flash(void)
{
*((volatile INT16U *)SST_BASE_ADDR + SST_ADDR_UNLOCK1) = SST_DATA_UNLOCK1; //连续解锁.
*((volatile INT16U *)SST_BASE_ADDR + SST_ADDR_UNLOCK2) = SST_DATA_UNLOCK2;
*((volatile INT16U *)SST_BASE_ADDR + SST_ADDR_UNLOCK1) = SST_SETUP_ERASE;
*((volatile INT16U *)SST_BASE_ADDR + SST_ADDR_UNLOCK1) = SST_DATA_UNLOCK1;
*((volatile INT16U *)SST_BASE_ADDR + SST_ADDR_UNLOCK2) = SST_DATA_UNLOCK2;
*((volatile INT16U *)SST_BASE_ADDR + SST_ADDR_UNLOCK1) = SST_CHIP_ERASE; //写入擦除命令.
readtogglebit();
}
INT8U ReadByteFrom_Flash(INT16U nSector, INT32U offset)
{
INT8U value;
value = *(INT8U *)FlashAbsAddr(nSector, offset);
return value;
}
void ReadRecFromFlash(INT8U type,INT32U nPackage,INT8U len, INT8U *dptr)
{
INT32U stbyte;
INT32U address;
INT32U offset;
stbyte = nPackage * len;
address = SST_DATA_BASE + type * 4;
offset = *(INT32U*)address;
address = SST_DATA_BASE + offset;
address += stbyte;
for(; len>0; len--)
{
*dptr++ = *( INT8U *)address++;
}
}
void ReadDotFromFlash(INT16U nSector,INT32U nPackage,INT8U len, INT8U *dptr)
{
INT8U *fptr;
INT32U stbyte;
if (nSector >= 512) return;
if ( len == 0)
{
stbyte = nPackage*len + SIZE_FLASHID; /*计算一个包数据在一个扇区中的位置*/
fptr = ( INT8U *)FlashAbsAddr(nSector, stbyte);
*dptr = *(INT8U*)fptr;
*(dptr+1) = *(INT8U*)(fptr+1);
}
else
{
stbyte = nPackage*len + SIZE_FLASHID+2; /*计算一个包数据在一个扇区中的位置*/
fptr = ( INT8U *)FlashAbsAddr(nSector, stbyte);
memcpy(dptr, fptr, len);
}
}
void ReadTableCellFromFlash(INT8U type,INT32U nPackage,INT8U len, INT8U *dptr)
{
INT32U stbyte;
INT32U address;
INT32U offset;
address = SST_CFGTABL_BASE + type * 4;
offset = *(INT32U*)address;
address = SST_CFGTABL_BASE + offset;
if(len == 0)
{
*dptr = *( INT8U *)address;
*(dptr+1) = *(INT8U *)(address+1);
}
else
{
stbyte = nPackage * len + 2;
address += stbyte;
for(; len>0; len--)
{
*dptr++ = *( INT8U *)address++;
}
}
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -