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

📄 eeprom.c

📁 RTL8019以太网开发板资料
💻 C
字号:

#include <reg52.h>
#include <intrins.h>        /* use _nop_() function */
#include "EEPROM.h"
//sfr16 DPTR = 0x82;

/*        新增特殊功能寄存器定义        */
sfr	 ISP_DATA	=   0xe2;
sfr  ISP_ADDRH	=   0xe3;  
sfr	 ISP_ADDRL	=   0xe4;
sfr	 ISP_CMD	=   0xe5; 
sfr	 ISP_TRIG	=   0xe6;   
sfr	 ISP_CONTR    =   0xe7; 


/* 定义命令 */
#define READ_AP_and_Data_Memory_Command				0x01        /*  字节读数据存储区   */
#define PROGRAM_AP_and_Data_Memory_Command          0x02        /*  字节编程数据存储区 */
#define SECTOR_ERASE_AP_and_Data_Memory_Command     0x03        /*  扇区擦除数据存储区 */

typedef     unsigned char	INT8U;		/* 8 bit 无符号整型  */
typedef     unsigned int    INT16U;     /* 16 bit 无符号整型 */
#define		DELAY_CONST  60000

/* 定义常量 */
#define ERROR   0
#define OK      1

/* 定义Flash 操作等待时间 */
#define        MCU_CLOCK_20MHz
//#define         MCU_CLOCK_20MHz
//#define        MCU_CLOCK_10MHz
//#define        MCU_CLOCK_5MHz
#ifdef MCU_CLOCK_40MHz
#define WAIT_TIME        0x00
#endif
#ifdef MCU_CLOCK_20MHz
#define WAIT_TIME        0x01
#endif
#ifdef MCU_CLOCK_10MHz
#define WAIT_TIME        0x02
#endif
#ifdef MCU_CLOCK_5MHz
#define WAIT_TIME        0x03
#endif


#define SECTOR_SIZE                256
/*********************************************************************
函数名:       void  ISP_IAP_enable(void)
功能:         打开 ISP,IAP 功能
输入:         
输出:         
返回:         
日期:         2004/08/08
*********************************************************************/
void ISP_IAP_enable(void)
{
	EA	=	0;								// 关中断 /
	ISP_CONTR	=	ISP_CONTR & 0x18;       // 0001,1000 
	ISP_CONTR	=	ISP_CONTR | WAIT_TIME;
	ISP_CONTR	=	ISP_CONTR | 0x80;       // 1000,0000 
}
/*********************************************************************
函数名:       void  ISP_IAP_disable(void)
功能:         关闭 ISP,IAP 功能 
输入:         
输出:         
返回:         
日期:         2004/08/08
*********************************************************************/

void ISP_IAP_disable(void)
{
	ISP_CONTR	=	ISP_CONTR & 0x7f;	// 0111,1111 
	ISP_TRIG	=	0x00;
	EA			=   1;                	// 开中断 
}
/*********************************************************************
函数名:       void  FlashInit(void)
功能:         字节读
输入:         存放地址:byte_addr
输出:         
返回:         存储数据:ISP_DATA
日期:         2004/08/08
*********************************************************************/
/* 字节读 */
UWORK8 byte_read(INT16U byte_addr)
{
	ISP_ADDRH	=	(INT8U)(byte_addr >> 8);
	ISP_ADDRL	=	(INT8U)(byte_addr & 0x00ff);

	ISP_CMD		=	ISP_CMD	&	0xf8;        /* 1111,1000 */
	ISP_CMD		=	ISP_CMD	|	READ_AP_and_Data_Memory_Command;        /* 0000,0001 */

	ISP_IAP_enable();

	ISP_TRIG	=	0x46;
	ISP_TRIG	=	0xb9;
	_nop_();

	ISP_IAP_disable();
	return (ISP_DATA);
}
/*********************************************************************
函数名:       void  FlashWriteData(void)
功能:        写数据进 数据Flash存储器, 只在同一个扇区内写,不保留原有数据	
 			begin_addr,被写数据Flash开始地址;counter,连续写多少个字节; array[],数据来源	
输入:         begin_addr:写入的启起地址, counter:数据长度.array所有数据  
输出:         None
返回:         none
日期:         2004/08/08
*********************************************************************/
UWORK8 FlashWriteData(WORK16 begin_addr,  UWORK8 *array, WORK16 counter)
{
	WORK16	i	=	0;
	WORK16	in_sector_begin_addr	=	0;
	WORK16	sector_addr	=	0;

	if(counter > SECTOR_SIZE)		 //判是否是有效范围,此函数不允许跨扇区操作
		return	ERROR;
	in_sector_begin_addr =        begin_addr & 0x01ff;         // 0000,0001,1111,1111 
	if( (in_sector_begin_addr + counter) > SECTOR_SIZE )
		return ERROR;


	sector_addr	=	(begin_addr & 0xfe00);	// 1111,1110,0000,0000; 取扇区地址 擦除 要修改/写入 的扇区
	ISP_ADDRH	=	(INT8U)(sector_addr >> 8);
	ISP_ADDRL	=	0x00;
	ISP_CMD		=	ISP_CMD	&	0xf8;		// 1111,1000 
	ISP_CMD		=	ISP_CMD	|	SECTOR_ERASE_AP_and_Data_Memory_Command;	// 0000,0011 

	ISP_IAP_enable();
	ISP_TRIG	=	0x46;        // 触发ISP_IAP命令 
	ISP_TRIG	=	0xb9;        // 触发ISP_IAP命令 
	_nop_();

	for(i = 0; i< counter; i++)
	{
		ISP_ADDRH	=	(INT8U)(begin_addr >> 8);		 //写一个字节
		ISP_ADDRL	=	(INT8U)(begin_addr & 0x00ff);
		ISP_DATA	=	*array;
		ISP_CMD		=	ISP_CMD	&	0xf8;	// 1111,1000 
		ISP_CMD		=	ISP_CMD	|	PROGRAM_AP_and_Data_Memory_Command;		// 0000,0010 

		ISP_TRIG	=	0x46;	// 触发ISP_IAP命令 
		ISP_TRIG	=	0xb9;	// 触发ISP_IAP命令 
		_nop_();

		ISP_DATA	=	0x00;			//读回来

		ISP_CMD		=	ISP_CMD	&	0xf8;	// 1111,1000 
		ISP_CMD     =	ISP_CMD	|	READ_AP_and_Data_Memory_Command;	// 0000,0001 

		ISP_TRIG	=	0x46;	// 触发ISP_IAP命令 
		ISP_TRIG	=	0xb9;	// 触发ISP_IAP命令 
		_nop_();

		if(ISP_DATA != *array)	   //比较对错
		{
			ISP_IAP_disable();
			return ERROR;
		}
		begin_addr++;
		array++;
	}
	ISP_IAP_disable();
	return	OK;
}

/*********************************************************************
函数名:       FlashReadData
功能:         从FLASH中读数据
输入:         1. FLASH的地址 
              2. 数据起始地址
              3. 写的字节数
输出:         None
返回:         OK, ERROR
日期:         2005/11/19
*********************************************************************/
UWORK8 FlashReadData(UWORK16 usAtaddr,UWORK8 *pucMemAddr,UWORK16 usReadLen)
{
    UWORK16 usSectorBeginAddr,usLoop;
    
    if(usReadLen > SECTOR_SIZE)
    {
        return ERROR;                                              /* 超出一个扇区的大小 */
    }

    usSectorBeginAddr = usAtaddr & 0x01ff;
    if((usSectorBeginAddr + usReadLen) > SECTOR_SIZE)
    {
        return ERROR;                                              /* 超出一个扇区的大小 */
    }

    for(usLoop = 0; usLoop < usReadLen; usLoop++)
    {
       *pucMemAddr = byte_read(usAtaddr);
        usAtaddr++;
        pucMemAddr++;
    }
    return OK;
}

⌨️ 快捷键说明

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