📄 duan1224.c
字号:
/////////保定的GPRS模块///////////////////
#include "c:\comp51\reg52.h"
#include "c:\comp51\INTRINS.H"
#include "c:\comp51\math.H"
#define uint unsigned int
#define uchar unsigned char
#define ulong unsigned long
bit Send_oe=0; //定义可以发送命令信息标志//
bit Start_rec=0; //定义开始接收数据标志//
bit REc_end=0;//接收完成短信标志//
bit Command=0; //表示是单片机发送返回的数据//
bit Sending=0; //表示串口正占用//
bit Rec_message=0;//表示接收到短信//
bit read_message=0;//表示接收到的短信已读取//
bit errio=0;//AT24C02读写出错标志//
//sbit flash_lamp=P3^6; //工作闪烁指示灯控制//
sbit I2C_SDA=P3^7;//AT24C02 SDA
sbit I2C_SCL=P3^5;//AT24C02 SCL
//sbit I2C_SDA=P1^3;//AT24C02 SDA
//sbit I2C_SCL=P1^2;//AT24C02 SCL
sbit WDOG=P3^4; //T1引脚输出喂狗信号//
uchar data flash_time=0; //指示灯闪烁控制计数器//
uchar data Comm_send_errio=0; //发送数据错误计数器//
uchar data Comm_rec_errio=0; //接收数据错误计数器//
uchar data Comm_errio=0; //通讯错误计数器//
uchar data Comm_send_times=0;
uchar data Stats_old=0xe0; //端口保存上一次数据//
uchar data Stats_real=0x37; //状态实时数据//
uchar data AT_COM_STEP=0;//设置模块步骤标志//
uchar code AT[3]={0X41,0X54,0X0D};
uchar code AT_CNMI[12]={0X41,0X54,0X2B,0X43,0X4E,0X4D,0X49,0X3D,0X32,0X2C,0X31,0X0D};//设置短信保存位置,收到后提示代码//
uchar code AT_CMGF[10]={0X41,0X54,0X2B,0X43,0X4D,0X47,0X46,0X3D,0X31,0X0D};//设置短信文本方式代码//
/*
uchar code AT_OK[6]={0X0D,0X0A,0X4F,0X4B,0X0D,0X0D};//返回OK代码//
uchar code AT_ERRIO[9]={0x0d,0x0a,0x45,0x52,0x52,0x4f,0x52,0x0d,0x0a};//返回ERRIO代码//
uchar code AT_CMGR[8]={0X41,0X54,0X2B,0X43,0X4D,0X47,0X52,0X3D};//读短信命令代码AT+CMGR=//
uchar code AT_CMGS[8]={0X41,0X54,0X2B,0X43,0X4D,0X47,0X53,0X3D};//发短信命令代码AT+CMGS=//
uchar code AT_CMTI[]={0X0D,0x0A,0x2B,0x43,0x4D,0x54,0x49,0x3A,0x20,0x22,0x53,0x4D,0x22,0x2C,0x39,0x0D,0x0A};
*/
uchar code TEL_num_back[11]={0x31,0x33,0x31,0x33,0x33,0x31,0x30,0x32,0x39,0x36,0x32};//备用电话号码,开机读取24C02错误时使用//
uchar idata Rec_buff1[82];//接收数据缓冲区//
uchar idata Send_buff1[21];//发送数据缓冲区//
uchar data Rec_cont=0; //接收数据长度//
uchar data Send_cont=0; //发送数据长度//
uchar data Send_longth=0;//定义发送缓冲区数据长度//
uchar data Rec_stats=0;//接收数据状态标志//
uchar data Send_stats=0;//发送数据状态标志//
uchar data TEL_num[11]; //保存要发送信息的电话号码//
uint data message_addr=0; //短信模块接收到的新短信地址//
/////////////////////////////////////////////////
void dl(void)
{ unsigned int i;
for(i=0;i<1;i++)
{
WDOG=~WDOG;
}
}
void delay(unsigned int t)
{
unsigned int i,j;
for(i=0;i<t;i++)
for(j=0;j<3000;j++)
{
WDOG=~WDOG;
}
}
///////////////////////////////////////////////
/******************************AT24C64子程序********************************************/
void I2C_Start()
{ EA=0;
I2C_SDA=1;
dl();
I2C_SCL=1;
dl();
I2C_SDA=0;
dl();
I2C_SCL=0;
}
/********************************************
内部函数,I2C结束
********************************************/
void I2C_Stop()
{
I2C_SDA=0;
dl();
I2C_SCL=1;
dl();
I2C_SDA=1;
dl();
I2C_SCL=0;
dl();
EA=1;
}
/********************************************
内部函数,输出ACK ,每个字节传输完成,输出ack=0,结束读书据,ack=1;
********************************************/
void I2C_WriteACK(uchar ack)
{
I2C_SDA=ack;
dl();
I2C_SCL=1;
dl();
I2C_SCL=0;
}
/********************************************
内部函数,等待ACK
********************************************/
void I2C_WaitACK()
{ uchar errtime=60;
I2C_SDA=1;
dl();
I2C_SCL=1;
dl();
errio=0;
while(I2C_SDA)
{
errtime--;
if(!errtime)
{
I2C_Stop();
errio=1;
return;
}
}
I2C_SCL=0;
}
void I2C_writebyte(uchar wdata)
{
uchar i;
I2C_SCL=0;
for(i=0;i<8;i++)
{
dl();
if(wdata&0x80)
{
I2C_SDA=1;
}
else
{
I2C_SDA=0;
}
wdata<<=1;
I2C_SCL=1;
dl();
I2C_SCL=0;
}
I2C_WaitACK(); //I2C器件或通讯出错,将会退出I2C通讯
}
/********************************************
内部函数.输入数据
出口:B
********************************************/
uchar I2C_Readbyte()
{
uchar i,bytedata;
I2C_SDA=1;
for(i=0;i<8;i++)
{
I2C_SCL=1;
bytedata<<=1;
dl();
bytedata|=I2C_SDA;
I2C_SCL=0;
}
return(bytedata);
}
/********************************************
输出数据->24C02
********************************************/
void I2C_writebyte1(uchar address,uchar mdata)
{
I2C_Stop();
I2C_Start();
I2C_writebyte(0xa0); /*写命令*/
I2C_writebyte(address); /*写地址*/
I2C_writebyte(mdata); /*写数据*/
I2C_Stop();
delay(2);
}
void I2C_writeData(uchar address,uchar count,uchar *mdata)
{
uchar i;
I2C_Stop();
I2C_Start();
I2C_writebyte(0xa0); /*写命令*/
I2C_writebyte(address); /*写地址*/
for(i=0;i<count;i++)
{
I2C_writebyte(*mdata); /*写数据*/
mdata++;
}
I2C_Stop();
delay(2);
}
/********************************************
********************************************/
uchar I2C_ReadData(uint address) /*单字节*/
{
uchar buff;
I2C_Stop();
I2C_Start();
I2C_writebyte(0xa0); /*写命令*/
I2C_writebyte(address); /*写地址*/
I2C_Start();
I2C_writebyte(0xa1); /*读命令*/
buff=I2C_Readbyte();
I2C_WriteACK(1);
I2C_Stop();
return(buff);
delay(2);
}
void I2C_ReadData1(uchar address,uchar count,uchar * buff) /*多字节*/
{
uchar i;
I2C_Stop();
I2C_Start();
I2C_writebyte(0xa0); /*写命令*/
I2C_writebyte(address); /*写地址*/
I2C_Start();
I2C_writebyte(0xa1); /*读命令*/
for(i=0;i<count;i++)
{
buff[i]=I2C_Readbyte();
if(i<count)
{
I2C_WriteACK(0);
}
}
I2C_WriteACK(1);
I2C_Stop();
delay(2);
}
/******************************AT24C02子程序结束********************************************/
////////////////////////////////////////////////
void time0(void) interrupt 1 //定时器T0中断//
{
TH0=0x3C; //晶阵12M,T0 50ms;//
TL0=0xAF;
if(Start_rec)
{
Comm_errio++;
if(Comm_errio>=100)
{
Comm_errio=0;
Start_rec=0;
Rec_cont=0;
Rec_stats=0;
Command=0;
Sending=0;
}
}
else
{
Comm_errio=0;
}
if(Sending) //正在发送数据标志,如果发送出去命令后6秒内没有受到反馈信息,再发送,到三次停止。
{
Comm_send_times++;
if(Comm_send_times==120)
{
Send_cont=0;
Send_longth=0;
Send_oe=1;
Command=0;
}
if(Comm_send_times==240)
{
Send_cont=0;
Send_longth=0;
Send_oe=1;
Command=0;
}
if(Comm_send_times>=360)
{
Comm_send_times=0;
Sending=0;
Send_stats=0;
Command=0;
Send_cont=0;
Send_longth=0;
for(;;) // 连续3次发送没有反馈,死循环使看门狗复位//
{
}
}
}
flash_time++;
if(flash_time>=10)
{
flash_time=0;
//flash_lamp=~flash_lamp;
}
}
/////////////////////////////////////////////////
void RS232(void) interrupt 4 //串行口中断//
{
uchar i=0;
if(RI)
{ //接收中断//
RI=0;
if(Command==0)
{
switch (Rec_stats)
{
case 0: //判断接收数据是否以0D 0A开头,如果是继续接收,不是再等待判断
{
Rec_buff1[Rec_cont]=SBUF;
Rec_cont++;
if(Rec_cont>=2)
{
if(Rec_buff1[0]==0x0d&&Rec_buff1[1]==0x0a)
{
Rec_stats=1;
Start_rec=1;
Comm_errio=0;
Comm_send_times=0;
}
else
{
Rec_cont=0;
Rec_stats=0;
}
}
break;
}
case 1:
{
Rec_buff1[Rec_cont]=SBUF;
Rec_cont++;
if(Rec_cont>=4)
{
if(Rec_buff1[2]==0x3e&&Rec_buff1[3]==0x20) //表示发送命令成功,可以继续发送信息
{
Rec_cont=0;
Rec_stats=0;
//置标志继续发送短信内容,填充发送信息内容及长度//
Send_oe=1;
Send_stats=2;
Comm_send_errio=0;
Start_rec=0;
Comm_errio=0;
Comm_send_times=0;
}
else
{
Rec_stats=2;
}
}
break;
}
case 2:
{
Rec_buff1[Rec_cont]=SBUF;
Rec_cont++;
if(Rec_cont>=6)
{
if(Rec_buff1[2]==0x4f&&Rec_buff1[3]==0x4b&&Rec_buff1[4]==0x0d&&Rec_buff1[5]==0x0a) //返回OK,表示发送命令成功//
{
Rec_cont=0;
Rec_stats=0;
Comm_send_errio=0;
Start_rec=0;
Comm_errio=0;
Sending=0;
Comm_send_times=0;
}
else
{
Rec_stats=3; //不是返回OK,继续接收判断//
}
}
break;
}
case 3:
{
Rec_buff1[Rec_cont]=SBUF;
Rec_cont++;
if(Rec_cont>=7)
{
if(Rec_buff1[2]==0x45&&Rec_buff1[3]==0x52&&Rec_buff1[4]==0x52&&Rec_buff1[5]==0x4f) //收到错误提示ERROR,重新处理//
{
Rec_stats=4;
}
if(Rec_buff1[3]==0x43&&Rec_buff1[4]==0x4d&&Rec_buff1[5]==0x54&&Rec_buff1[6]==0x49) //返回接收到短信提示CMTI, 进行短信接收操作//
{
Rec_stats=5;
}
if(Rec_buff1[3]==0x43&&Rec_buff1[4]==0x4d&&Rec_buff1[5]==0x47&&Rec_buff1[6]==0x52) //返回接收到短信内容CMGR,继续接收///
{
Rec_stats=6;
}
if(Rec_buff1[3]==0x43&&Rec_buff1[4]==0x4d&&Rec_buff1[5]==0x47&&Rec_buff1[6]==0x53) //返回接收到内容CMGS,说明发送短信成功//
{
Rec_stats=8;
}
}
break;
}
case 4:
{
Rec_buff1[Rec_cont]=SBUF; //继续接收ERROR//
Rec_cont++;
if(Rec_buff1[Rec_cont-1]==0x0a&&Rec_buff1[Rec_cont-2]==0x0d) //接收完错误提示,从新处理命令数据。//
{
Rec_cont=0;
Rec_stats=0;
Start_rec=0;
Comm_errio=0;
Comm_send_times=0;
Sending=0;
Comm_send_errio++;
if(Comm_send_errio>=3) //接收错误超过3次退出,否则置标志从新发送//
{
Comm_send_errio=0;
Send_stats=0;
Send_cont=0;
Send_longth=0;
}
else
{
Send_oe=1; //如果是发送命令不成功,重新发送//
}
}
break;
}
case 5: //继续接收收到短消息提示信息
{
Rec_buff1[Rec_cont]=SBUF;
Rec_cont++;
if(Rec_buff1[Rec_cont-1]==0x0a&&Rec_buff1[Rec_cont-2]==0x0d)
{
// Rec_cont=0;
Rec_stats=0;
Start_rec=0;
Comm_errio=0;
Comm_send_times=0;
i=0;
message_addr=0;
while(Rec_buff1[Rec_cont-(3+i)]!=0x2c)
{ //接收完短信提示,确认短信存放地址//
switch (i)
{
case 0:
{
message_addr=Rec_buff1[Rec_cont-(3+i)]&0x0f;
break;
}
case 1:
{
message_addr=(Rec_buff1[Rec_cont-(3+i)]&0x0f)*10+message_addr;
break;
}
case 2:
{
message_addr=(Rec_buff1[Rec_cont-(3+i)]&0x0f)*100+message_addr;
break;
}
case 3:
{
message_addr=(Rec_buff1[Rec_cont-(3+i)]&0x0f)*1000+message_addr;
break;
}
default:
{
}
}
i++;
}
Rec_cont=0;
i=0;
Send_oe=1;
Send_stats=3;
Sending=0;
}
break;
}
case 6:
{
Rec_buff1[Rec_cont]=SBUF;
Rec_cont++;
if((Rec_cont<=82)&&Rec_buff1[Rec_cont-1]==0x0a&&Rec_buff1[Rec_cont-2]==0x0d&&Rec_buff1[Rec_cont-3]==0x4b&&Rec_buff1[Rec_cont-4]==0x4f)
{
//判断信息接收成功后,判断内容,如不是所需内容,丢弃处理//
Rec_message=1;
Comm_send_times=0;
if(Rec_cont==82)
{
REc_end=1;
}
else
{
read_message=1;
}
Rec_cont=0;
Rec_stats=0;
Send_stats=0;
Send_cont=0;
Send_longth=0;
Comm_send_errio=0;
Start_rec=0;
Comm_errio=0;
Sending=0;
}
else
{
if(Rec_cont>=82) //不是所需短信,继续接收,等待返回处理//
{
Rec_stats=7;
}
}
break;
}
case 7:
{
//Rec_buff1[Rec_cont]=SBUF; //不是所需短信,接收后无实际意义,等待超时复位//
read_message=1;//不是所要短信,置已读标志,准备删除//
Rec_message=1;
Comm_send_times=0;
WDOG=~WDOG;
break;
}
case 8:
{
Rec_buff1[Rec_cont]=SBUF;
Rec_cont++;
if(Rec_buff1[Rec_cont-1]==0x0a&&Rec_buff1[Rec_cont-2]==0x0d&&Rec_buff1[Rec_cont-3]==0x04b&&Rec_buff1[Rec_cont-4]==0x4f) //收到发送短信成功提示//
{
//判断信息发送成功//
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -