首先我們要知道什么是EEPROM
這里要看自己的單片機EEPROM地址大小和起始地址
主要要用到的寄存器并不多,一個是IAP_CMD(C5H),還有的就是IAP_CONTR(C7H)
然后以下就是通過代碼寫命令到寄存器最后進行數據操作即可
單片機源程序如下:
- #include "STC15F2kxx.h"
- #include "stceeprom.h"
- #include <intrins.h>
- #include <string.h>
- #include "delay.h"
- //關閉IAP功能
- void IapIdle()
- {
- IAP_CONTR = 0;
- IAP_CMD = 0;
- IAP_TRIG = 0;
- IAP_ADDRH = 0x80;
- IAP_ADDRL = 0;
- }
- //擦除指定地址的扇區
- void IapEraseSector(WORD addr)
- {
- IAP_CONTR = ENABLE_IAP;//使能IAP
- IAP_CMD = CMD_ERASE; //擦除命令
- IAP_ADDRL = addr; //指定地址
- IAP_ADDRH = addr >> 8;
- IAP_TRIG = 0x5a; //命令觸發器先寫5ah,再寫a5h命令才能生效
- _nop_(); //等待
- IAP_TRIG = 0xa5;
- _nop_();
- IapIdle();//關閉IAP功能
- }
- //往指定地址中寫入一個字節字符數據
- void IapWritecChar(WORD addr, BYTE dat)
- {
- IAP_CONTR = ENABLE_IAP; //使能IAP
- IAP_CMD = CMD_PROGRAM; //寫命令
- IAP_ADDRL = addr; //指定地址
- IAP_ADDRH = addr >> 8;
- IAP_DATA = dat;
- IAP_TRIG = 0x5a; //命令觸發器先寫5ah,再寫a5h命令才能生效
- _nop_();
- IAP_TRIG = 0xa5;
- _nop_();
- IapIdle();
- }
- //往指定地址寫入兩個字節數據
- void IapWriteInt(WORD addr,unsigned int dat)
- {
- unsigned char i;
- typedef union //設置共用體,用char分攤2字節
- {
- unsigned int dat1;
- char mchar[2];
- }NEW_DATA;
- NEW_DATA data1;
- data1.dat1 = dat;
- IAP_CONTR = ENABLE_IAP; //使能IAP
- IAP_CMD = CMD_PROGRAM; //寫命令
- for(i = 0; i < 2; i++)
- {
- IAP_ADDRL = addr; //指定地址
- IAP_ADDRH = addr >> 8;
- IAP_DATA = data1.mchar[i];
- IAP_TRIG = 0x5a; //命令觸發器先寫5ah,再寫a5h命令才能生效
- _nop_();
- IAP_TRIG = 0xa5;
- _nop_();
- addr++;
- }
- IapIdle(); //關閉IAP功能
- }
- //往指定地址寫入四個字節數據
- void IapWriteI32(WORD addr, unsigned long dat)
- {
- unsigned char i;
- typedef union//設置共用體,用char分攤4字節
- {
- unsigned long dat1;
- char mchar[4];
- }NEW_DATA;
- NEW_DATA data1;
- data1.dat1 = dat;
-
- IAP_CONTR = ENABLE_IAP; //使能IAP
- IAP_CMD = CMD_PROGRAM; //寫命令
- for(i = 0; i < 4; i++)
- {
- IAP_ADDRL = addr; //指定地址
- IAP_ADDRH = addr >> 8;
- IAP_DATA = data1.mchar[i];
- IAP_TRIG = 0x5a; //命令觸發器先寫5ah,再寫a5h命令才能生效
- _nop_();
- IAP_TRIG = 0xa5;
- _nop_();
- addr++;
- }
- IapIdle(); //關閉IAP功能
- }
- /*******************************************************************************
- * 函數名 : Powerlost_data
- * 描述 : 斷電中斷數據寫入函數
- * 輸入 : addr 地址 dat 寫入數據
- * 輸出 : 無
- * 返回值 : 無
- * 說明 : 為了應對中斷函數與主函數循環使用IapWriteI32函數沖突
- *******************************************************************************/
- void Powerlost_data(WORD addr ,unsigned long dat)
- {
- unsigned char i;
- typedef union//設置共用體,用char分攤4字節
- {
- unsigned long dat1;
- char mchar[4];
- }NEW_DATA;
- NEW_DATA data1;
- data1.dat1 = dat;
-
- IAP_CONTR = ENABLE_IAP; //使能IAP
- IAP_CMD = CMD_PROGRAM; //寫命令
- for(i = 0; i < 4; i++)
- {
- IAP_ADDRL = addr; //指定地址
- IAP_ADDRH = addr >> 8;
- IAP_DATA = data1.mchar[i];
- IAP_TRIG = 0x5a; //命令觸發器先寫5ah,再寫a5h命令才能生效
- _nop_();
- IAP_TRIG = 0xa5;
- _nop_();
- addr++;
- }
- IapIdle(); //關閉IAP功能
- }
- //往指定起始地址寫入不固定長度的字符串數據
- void IapWriteString(WORD addr,BYTE *mString,BYTE n)
- {
- unsigned char i;
- IAP_CONTR = ENABLE_IAP; //使能IAP
- IAP_CMD = CMD_PROGRAM; //寫命令
- for(i=0; i<n ;i++)
- {
- IAP_ADDRL = addr; //指定地址
- IAP_ADDRH = addr >> 8;
- IAP_DATA = mString[i];
- IAP_TRIG = 0x5a; //命令觸發器先寫5ah,再寫a5h命令才能生效
- _nop_();
- IAP_TRIG = 0xa5;
- _nop_();
- addr++;
- }
- IapIdle(); //關閉IAP功能
- }
- //向指定地址讀取一個字節的字符數據
- char IapReadChar(WORD addr)
- {
- BYTE dat;
- IAP_CONTR = ENABLE_IAP; //使能IAP
- IAP_CMD = CMD_READ; //讀命令
- IAP_ADDRL = addr; //指定地址
- IAP_ADDRH = addr >> 8;
- IAP_TRIG = 0x5a; //命令觸發器先寫5ah,再寫a5h命令才能生效
- _nop_();
- IAP_TRIG = 0xa5;
- _nop_();
- dat = IAP_DATA;
- IapIdle(); //關閉IAP功能
- return dat;
- }
- //向指定地址讀取兩個字節的數字數據
- unsigned int IapReadInt(WORD addr)
- {
- unsigned int dat;
- unsigned char i;
- typedef union //設置共用體,用char分攤2字節
- {
- unsigned int dat1;
- char mchar[2];
- }NEW_DATA;
- NEW_DATA data1;
- IAP_CONTR = ENABLE_IAP; //使能IAP
- IAP_CMD = CMD_READ; //讀命令
- for(i = 0; i < 2; i++)
- {
- IAP_ADDRL = (addr + i); //指定地址
- IAP_ADDRH = ((addr + i) >> 8);
- IAP_TRIG = 0x5a; //命令觸發器先寫5ah,再寫a5h命令才能生效
- _nop_();
- IAP_TRIG = 0xa5;
- _nop_();
- data1.mchar[i]= IAP_DATA;
- }
- IapIdle(); //關閉IAP功能
- dat = data1.dat1;
- return dat;
- }
- //向指定地址讀取四個字節的數字數據
- unsigned long IapReadI32(WORD addr)
- {
- unsigned long dat;
- unsigned char i;
- typedef union//設置共用體,用char分攤4字節
- {
- unsigned long dat1;
- char mchar[4];
- }NEW_DATA;
- NEW_DATA data1;
- IAP_CONTR = ENABLE_IAP; //使能IAP
- IAP_CMD = CMD_READ; //讀命令
-
- for(i = 0; i < 4; i++)
- {
- IAP_ADDRL = (addr + i); //指定地址
- IAP_ADDRH = ((addr + i) >> 8);
- IAP_TRIG = 0x5a; //命令觸發器先寫5ah,再寫a5h命令才能生效
- _nop_();
- IAP_TRIG = 0xa5;
- _nop_();
- data1.mchar[i] = IAP_DATA;
- }
- IapIdle();//關閉IAP功能
- dat = data1.dat1;
- return dat;
- }
- //向指定地址讀取不定長度的字符串數據
- void IapReadString(WORD addr,BYTE *mString, BYTE n)
- {
- unsigned char i;
- memset(mString,0,strlen(mString));
- IAP_CONTR = ENABLE_IAP; //使能IAP
- IAP_CMD = CMD_READ; //讀命令
- for(i = 0; i < n; i++)
- {
- IAP_ADDRL = (addr + i); //指定地址
- IAP_ADDRH = ((addr + i) >> 8);
- IAP_TRIG = 0x5a; //命令觸發器先寫5ah,再寫a5h命令才能生效
- _nop_();
- IAP_TRIG = 0xa5;
- _nop_();
- mString[i] = IAP_DATA;
- }
- IapIdle();//關閉IAP功能
- }
復制代碼
|