📄 2main.c
字号:
#include <reg52.h>
#include <math.h>
#define uchar unsigned char
#define uint unsigned int
/*ad*/
uint ad_result(uchar port);
float ad_v(uint x);
float ad_a(uint x);
/*24c*/
void I2C_Init(void);
void AT24C64_W(void *mcu_address,uint AT24C64_address,uint count);
void AT24C64_R(void *mcu_address,uint AT24C64_address,uint count);
/*ds12887*/
void get_clock(void);
void set_clock(void);
/*232*/
void send_word(uchar *p,uchar leng);
void uart_int(void);
/*serial */
void uart_int(void);
uchar checkOder(void);
/*12887*/
extern uchar time[7];
uchar xdata rbuf[10],wbuf[10]; //24c 操作
float xdata Q;//电量总数
float xdata Q1,Q2=0;//当天电量
float xdata U;
float xdata I;
float W;//功率
uchar hour,AM,PM,month;
uchar xdata send[40];
sbit WDOG=P3^4; //看门狗
sbit GPRS_OK=P2^4;//判断GPRS连接是否成
sbit LED_ON=P2^3; //点亮路灯
sbit NO_POWER=P2^5;//断电报警
uchar receive[40];
uchar start=0;//接收开始标志
uchar re_num=0;
uchar receiveFinish=0;//接收结束,在main调用
////////////////////////////////////////////////////////////////
void uart_int(void)
{
TMOD=0x20;
PCON=0x00;
TH1=0xfd;
TL1=0xfd;
//TR0=1;
TR1=1;
//IE=0;
//ET0=0;
SCON=0x50;
ES=1;
EA=1;
}
void send_word(uchar *p,uchar leng) //串行口发送处理子程序
{
uchar i;
EA=0;
ES=0;
for(i=0;i<leng;i++)
{
SBUF=*p;
p++;
while (TI==0);
TI=0;
}
ES=1;
EA=1;
}
uchar checkOder(void)
{
uchar flag;
if((receive[1]==67)&&(receive[2]==74)&&(receive[3]==86)&&(receive[4]==65)&&(receive[5]==81))
flag=1;
if((receive[1]==83)&&(receive[2]==69)&&(receive[3]==84)&&(receive[4]==84))
flag=2;
if((receive[1]==83)&&(receive[2]==69)&&(receive[3]==84)&&(receive[4]==84)&&(receive[5]==79)&&(receive[6]==67))
flag=3;
if((receive[1]==79)&&(receive[2]==80)&&(receive[3]==33))
flag=4;
if((receive[1]==79)&&(receive[2]==70)&&(receive[3]==33))
flag=5;
return flag;
}
void comm(void) interrupt 4 using 3 //串行口中断程序
{
if(RI==1)
{
ES=0;
//while (RI==0); RI=0;
if(start==1)
{
re_num++;
receive[re_num]=SBUF;
if(SBUF==33)//receive "!"
{receiveFinish=1;start=0;}
}
else
{
receive[0]=SBUF;
if(SBUF==63)//receive "?"
{start=1;re_num=0;}
}
ES=1;
RI=0;
}
}
////////////////////////////////////////////////////////////////
void Delay(uint n)
{
uint ii;
for(ii=0;ii<n;ii++)//WDOG!=WDOG;
;
}
//计算部分
void computer_s(float da,uchar lent) //分
{
unsigned long int T,a,h;
uchar i;
if(lent==4)
h=(long int)(da*10);
if(lent==9)
h=(long int)(da*100);
for(i=lent;i>0;i--)
{
a=pow(10,i-1);
wbuf[lent-i]=(char)(h/a);
T=h%a;
h=T;
}
}
float computer_o(uchar *p,uchar lent) //合
{
unsigned long int T;
float f=0;
uchar i;
for(i=lent;i>0;i--)
{
T=(*p)*pow(10,i-1);
f=f+T;
p++;
}
if(lent==4)
f=f/10;
if(lent==9)
f=f/100;
return(f);
}
main()
{
uchar i,temp;
uint count1,count2=0;
uchar oneFlag=0;//1个月存一次,
GPRS_OK=1;
NO_POWER=0;
LED_ON=1;
I2C_Init();
uart_int();
AT24C64_R(&rbuf,22,9);
Q=computer_o(rbuf,9);
Q1=Q;
/*wbuf[0]=1;wbuf[1]=7; wbuf[2]=0;wbuf[3]=6;
AT24C64_W(&wbuf,222,4); */
get_clock();
hour=time[3];
if((time[1]==1)||(time[1]==2)||(time[1]==3))
AT24C64_R(&rbuf,210,4);
else if((time[1]==4)||(time[1]==5)||(time[1]==6))
AT24C64_R(&rbuf,214,4);
else if((time[1]==7)||(time[1]==8)||(time[1]==9))
AT24C64_R(&rbuf,218,4);
else if((time[1]==10)||(time[1]==11)||(time[1]==12))
AT24C64_R(&rbuf,222,4);
AM=rbuf[0]*10+rbuf[1]; //17 开灯时间
PM=rbuf[2]*10+rbuf[3]; //06 关灯时间
while(1)
{
// WDOG!=WDOG;
if(count1==54000)
{
if(GPRS_OK==1) //给GPRS发送复位命令
{
send[0]=63;send[1]=89;send[2]=78;send[3]=43;send[4]=82;send[5]=83;
send[6]=84;send[7]=13;send[8]=33;
send_word(send,7);
}
count1=0;
}
if(hour==AM) //开灯
{
wbuf[0]=1; wbuf[1]=1;wbuf[2]=1;wbuf[3]=0;
AT24C64_W(&wbuf,200,4);
LED_ON=0;
// WDOG!=WDOG;
if((time[4]%5)==0) //5分钟采样一次
{
temp=ad_result(0);
I=ad_a(temp);
temp=ad_result(3);
U=ad_v(temp);
if(I<50) //低电流报警
{
send[0]=63;send[1]=66;send[2]=74;send[3]=48;send[4]=49;send[5]=33;
send_word(send,6);
}
if(I>450)//高电流报警
{
send[0]=63;send[1]=66;send[2]=74;send[3]=48;send[4]=50;send[5]=33;
send_word(send,6);
}
if(U<170) //低电压报警
{
send[0]=63;send[1]=66;send[2]=74;send[3]=48;send[4]=51;send[5]=33;
send_word(send,6);
}
if(U>260)//高电压报警
{
send[0]=63;send[1]=66;send[2]=74;send[3]=48;send[4]=52;send[5]=33;
send_word(send,6);
}
if(NO_POWER==0) //掉电报警
{
send[0]=63;send[1]=66;send[2]=74;send[3]=48;send[4]=53;send[5]=63;
send_word(send,6);
}
W=U*I/1000; //及时功
}
if(time[2]==1)//保存每个月的电量
{
if(oneFlag==0)
{
oneFlag=1;
count2=time[1];
computer_s(Q,9);
AT24C64_W(&wbuf,32+count2*10,9);
}
}
else
{
oneFlag=0;
}
if(time[3]!=hour)//1小时保存一次数据
{
hour=time[3];
Q=Q+U*I/2;
computer_s(Q,9);
AT24C64_W(&wbuf,22,9);
computer_s(I,4);
AT24C64_W(&wbuf,12,4);
computer_s(U,4);
AT24C64_W(&wbuf,0,4);
}
}
if(hour==PM) //关灯
{
wbuf[0]=1; wbuf[1]=1;wbuf[2]=1;wbuf[3]=1;
AT24C64_W(&wbuf,200,4);
LED_ON=1;
Q2=Q-Q1;
computer_s(Q2,9);
AT24C64_W(&wbuf,32,9);
}
if(receiveFinish==1) //串口收数结束
{
switch(checkOder())
{
case 1:
//FeedDog();
send[0]=63;send[1]=68;send[2]=65;send[3]=84;send[4]=65;
AT24C64_R(&rbuf,0,4);
for(i=0;i<4;i++)
send[5+i]=rbuf[i]+0x30;
AT24C64_R(&rbuf,12,4);
for(i=0;i<4;i++)
send[9+i]=rbuf[i]+0x30;
AT24C64_R(&rbuf,24,9);
for(i=0;i<9;i++)
send[13+i]=rbuf[i]+0x30;
computer_s(W,9);
for(i=0;i<9;i++)
send[22+i]=wbuf[i]+0x30;
AT24C64_R(&rbuf,200,4);
for(i=0;i<4;i++)
send[31+i]=rbuf[i]+0x30;
send[35]=33;
send_word(send,36);
break;
case 2:
for(i=0;i<6;i++)
time[i]=(receive[i*2]-0x30)*10+receive[i*2+1]-0x30;
set_clock();
get_clock();
send[0]=63;
send[1]=84;
for(i=0;i<6;i++)
{
send[(i+1)*2]=time[i]/10+0x30;
send[(i+1)*2+1]=time[i]%10+0x30;
}
send[14]=33;
send_word(send,15);
break;
case 3:
for(i=0;i<4;i++)
wbuf[i]=receive[i+7]-48;
AT24C64_W(&wbuf,210,4);
for(i=0;i<4;i++)
wbuf[i]=receive[i+11]-48;
AT24C64_W(&wbuf,214,4);
for(i=0;i<4;i++)
wbuf[i]=receive[i+15]-48;
AT24C64_W(&wbuf,218,4);
for(i=0;i<4;i++)
wbuf[i]=receive[i+19]-48;
AT24C64_W(&wbuf,222,4);
send[0]=63;send[1]=79;send[2]=75;send[3]=33;
send_word(send,4);
break;
case 4:
LED_ON=0;
send[0]=63;send[1]=79;send[2]=75;send[3]=33;
send_word(send,4);
break;
case 5:
LED_ON=1;
send[0]=63;send[1]=79;send[2]=75;send[3]=33;
send_word(send,4);
break;
default:
break;
}
}
Delay(300);//保证12887可以读数据
get_clock();
count1++;
}
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -