#include"reg51.h"
#include"intrins.h"
#define uchar unsigned char
#define uint unsigned int
/*Declare SFR associated with the ISP */
sfr IAP_DATA = 0xE2; //Flash data register 闪存数据寄存器
sfr IAP_ADDRH = 0xE3; //Flash address HIGH 闪存地址高
sfr IAP_ADDRL = 0xE4; //Flash address LOW 闪存地址低
sfr IAP_CMD = 0xE5; //Flash command register 闪存命令寄存器
sfr IAP_TRIG = 0xE6; //Flash command trigger 闪存命令触发
sfr IAP_CONTR = 0xE7; //Flash control register 闪存控制寄存器
/*Define ISP/IAP/EEPROM command*/
#define CMD_IDLE 0x00 //Stand-By
#define CMD_READ 0x00 //unsigned char-Read
#define CMD_PROGRAM 0x02 //unsigned char-Program
#define CMD_ERASE 0x03 //Sector-Erase
/*Define ISP/IAP/EEPROM operation const for IAP_CONTR*/
//#define ENABLE_IAP 0x80 //if SYSCLK<30MHz
//#define ENABLE_IAP 0x81 //if SYSCLK<24MHz
//#define ENABLE_IAP 0x82 //if SYSCLK<200MHz
#define ENABLE_IAP 0x83 //if SYSCLK<12MHz
//#define ENABLE_IAP 0x80 //if SYSCLK<6MHz
#define IAP_ADDRESS 0x0000
/**AD特殊寄存器***/
sfr ADC_DATA =0xc6;
sfr ADC_LOW2 =0xbe;
sfr ADC_CONTR =0xc5;
sfr P1M0 =0x91;
sfr P1M1 =0x92;
/***按键定义*****/
sbit KEY_P3_4 =P3^4; //左边拨动开关(拨向左:P3^4==0,表示需要标定电压;否则不需要标定)
sbit KEY_P0_0 =P0^0; //右边红色按钮(按下时:P0^0==0,表示开始标定电压;否则不标定)
sbit led=P1^1;
void ISP_IAP_Disable();
/***程序用到的定义****/
uint i,j,AD_finished=0,pj=0;mj=0,x=5,su[8]={1,2,3,4,5,6,7,8},y;
unsigned char *str=su;
uchar num,result,di,flag;
/**********延时函数*****************/
void delayms(uint xms)
{
for(i=xms;i>0;i--)
for(j=110;j>0;j--);
}
/*********串口/定时器初始化***************/
void init()
{
TMOD=0x21;//设定T1定时器工作方式2 0010 0001
TH1=0xfd;//T1定时器高8位赋值
TL1=0xfd;//T1定时器低8位赋值
TH0=0x4c;//T0定时器高8位赋值
TL0=0x00;//T0定时器低8位赋值
SCON=0x40;//设定串口工作方式1
EA=1;//开中断
TR0=1;//开启定时器T0
TR1=1;//开启定时器T1
ET0=1;//开定时器0中断
ES=1;//允许串口中断
REN=1;//允许串口接收
}
//==================================================
//函数:void UART1_Send_Char(uchar send_data)
//描述:单片机向串口发送一个字符
//参数:uchar send_data //待发送数据
//返回:无
void UART1_Send_Char(uchar send_data)//1.32===int 1.0//==132
{
ES=0;
SBUF=send_data;//接收数据
while(!TI);
TI=0;
ES=1;
}
// 函数:void UART1_Send_String(uchar *str, uchar len)
//描述:单片机向串口发送一个字符串
//参数:uchar *str //待发送数据
// uchar len //字符串长度
//返回:无
//---------------------------------//
void UART1_Send_String(uchar *str, uchar len)
{
uchar z;
for(z=0;z<len;z++)
{
UART1_Send_Char(*(str+z));
}
}
/*********AD函数**************/
void AD_init()
{
P1M0=0x80;P1M1=0x00;
ADC_DATA=0;
ADC_CONTR=0xe0;//1110 0000开启启动电源和选择转换速度
delayms(60);
}
/*****AD转换函数*********/
uint getAD()
{
uchar AD_finished=0;
ADC_CONTR|=0x07; //1110 0000 | 1111 1111 或上AD口的值
ADC_CONTR|=0x08;//0000 1000启动AD电源
while(AD_finished==0)//等待A/D转换结束
(AD_finished=(ADC_CONTR&0x10));//0000 1000 & 0001 0000 =0000 0000查询ADC_FLAG位是否置1
ADC_CONTR=0Xf7;//1111 0111//关闭启动位
return ADC_DATA; //值返回给高8位
}
/*********定时中断***********/
void T0_time() interrupt 1
{
TH0=0x4c;
TL0=0x00;
num++;
if(num>=20)
{
num=0;
pj=1;
}
}
/****关闭ISP,IAP功能*******/
void ISP_IAP_Disable()
{
IAP_CONTR=0x00;//Close IAP function关闭控制寄存器
IAP_CMD =0x00;//clear command to standby清除命令备用
IAP_TRIG =0x00;//Clear trigger register
IAP_ADDRH=0x00;//Data ptr point to non-EEPROM area
IAP_ADDRL=0x00;//Clear IAP address to prevent misuse
}
/**向EEPROM16位地址写入8位数据**/
void IapProgramINT8U(unsigned int add,unsigned char dat)
{
IAP_CONTR=ENABLE_IAP;//Open IAP function,and set wait time 打开IAP功能,设置Flash操作等待时间
IAP_CMD=0x02;//对用户的应用程序Flash区及数据Flash区编程
// my_unTemp16.un_temp16 = add;
IAP_ADDRH=add>>8/*my_unTemp16.un_temp8[0]*/; //设置目标单元地址的高8位地址
IAP_ADDRL=add/*my_unTemp16.un_temp8[1]*/; //设置目标单元地址的低8位地址
IAP_DATA=dat; //写入数据准备
IAP_TRIG=0x46;//Send trigger command1 (0x46)
IAP_TRIG=0xb9;//Send trigger command1 (0xb9)
_nop_(); //延时一个机器周期
ISP_IAP_Disable(); //关闭IAP,ISP功能
}
/********读出值***********/
unsigned char IapReadINT8U(unsigned int add)
{
unsigned char dat;
IAP_DATA=0x00;
IAP_CONTR=ENABLE_IAP; // 打开IAP功能,设置Flash操作等待时间
IAP_CMD =0x01; // 对用户的应用程序Flash区及数据Flash区字节读
// my_unTemp16.un_temp16 = add;
IAP_ADDRH=add>>8/*my_unTemp16.un_temp8[0]*/; //设置目标单元地址的高8位地址
IAP_ADDRL=add/*my_unTemp16.un_temp8[1]*/; //设置目标单元地址的低8位地址
IAP_TRIG =0x46; //触发ISP_IAP命令字节1(0x46)
IAP_TRIG =0xb9; //触发ISP_IAP命令字节2(0xb9)
_nop_(); //延时一个机器周期
dat=IAP_DATA; //读出数据准备
ISP_IAP_Disable(); //关闭IAP,ISP功能
return dat; //返回给函数
}
/**扇区擦除**/
void IapEraseSector(unsigned int add)
{
IAP_CONTR = ENABLE_IAP;//打开IAP功能,设置Flash操作等待时间
IAP_CMD = 0x03;//对用户的应用程序Flash区及数据Flash区擦出
//my_unTemp16.un_temp16 = addr;
IAP_ADDRH=add>>8/*my_unTemp16.un_temp8[0]*/; //设置目标单元地址的高8位地址
IAP_ADDRL=add/*my_unTemp16.un_temp8[1]*/; //设置目标单元地址的低8位地址
IAP_TRIG=0x46;//Send trigger command1 (0x46)
IAP_TRIG=0xb9;//Send trigger command1 (0xb9)
_nop_(); //延时一个机械周期
ISP_IAP_Disable();//关闭IAP/ISP
}
/**主函数***/
void main()
{
init();
while(1)
{
UART1_Send_String(str,8);
}
} |