📄 gprs.c
字号:
if(strncmp(GprsRcvQueue[i].RcvBuf,"AT",2) == 0)
{
OS_ENTER_CRITICAL();
// GprsRcvQueue[i].RcvBuf[0] = '\0';
GprsRcvQueue[i].Status = 0;
OS_EXIT_CRITICAL();
}
else if(strncmp(GprsRcvQueue[i].RcvBuf,"OK",2) == 0)
{
OS_ENTER_CRITICAL();
// GprsRcvQueue[i].RcvBuf[0] = '\0';
GprsRcvQueue[i].Status = 0;
OS_EXIT_CRITICAL();
}
else if(strncmp(GprsRcvQueue[i].RcvBuf, SpecStr, strlen(SpecStr)) == 0)
{
OS_ENTER_CRITICAL();
// GprsRcvQueue[i].RcvBuf[0] = '\0';
GprsRcvQueue[i].Status = 0;
OS_EXIT_CRITICAL();
}
}
else
{
OS_EXIT_CRITICAL();
}
}
}
/*********************************************************************************************************
** 函数名称: GPRSFlushQueueAll( void )
** 功能描述: 清空接收缓冲区中特定类型的字符串,AT指令的回显等
** 输 入: 指向特定类型的字符串的指针
** 输 出: 无
** 全局变量: GprsRcvQueue,数据接收缓存
** 调用模块: 无
**
** 作 者: 谢陆伟
** 日 期: 2007年7月16日
**-------------------------------------------------------------------------------------------------------
** 修改人:
** 日 期:
**------------------------------------------------------------------------------------------------------
********************************************************************************************************/
void GPRSFlushQueueAll( void )
{
uint32 i;
for(i=0; i<RCV_MAX; i++)
{
OS_ENTER_CRITICAL();
if(GprsRcvQueue[i].Status == 2)
{
GprsRcvQueue[i].RcvBuf[0] = '\0';
GprsRcvQueue[i].Status = 0;
OS_EXIT_CRITICAL();
}
else
{
OS_EXIT_CRITICAL();
}
}
}
/*********************************************************************************************************
** 函数名称: GPRSSendStr
** 功能描述: 给GPRS GPRS发送一条指令
** 输 入: SendString: 待发送的字符串
pResp: 期望返回的字符串的开头部分或者全部的字符串
pos: 期望字符串的位置
WaitTime:等待应答的最长时间,为0时相当于为4个时钟节拍,得到预期的数据立即返回
** 输 出: 指令是否成功执行
** 全局变量: 无
** 调用模块: 无
**
** 作 者: XieLuWei
** 日 期: 2007年6月13日
**-------------------------------------------------------------------------------------------------------
** 修改人:
** 日 期:
**------------------------------------------------------------------------------------------------------
********************************************************************************************************/
uint8 GPRSSendStr(const char *SendString, const char *pResp, char *pos, uint16 WaitTime)
{
GPRSWrite(SendString);
if(GPRSCheckQueueExt(pResp, pos, WaitTime)) //等待回复值
{
return 1;
}
return 0;
}
/*********************************************************************************************************
** 函数名称: GPRSInit
** 功能描述: 初始化GPRS,包括连接GPRS模块,注册网络,查询信号强度等操作
** 输 入: 无
**
** 输 出: 无
**
** 全局变量:
** 调用模块:
**
** 作 者:
** 日 期:
**-------------------------------------------------------------------------------------------------------
** 修改人:
** 日 期:
**-------------------------------------------------------------------------------------------------------
********************************************************************************************************/
void GPRSInit(void)
{
uint8 i;
uint8 err;
char pos;
char *tmptr;
DuartRcv = OSSemCreate(0); //中断函数和任务之间通信的信号量
GPRSSem = OSSemCreate(1); //对GPRS进行访问
GPRSSetState(NO_GPRS);
OSTimeDly(OS_TICKS_PER_SEC*16); //等待GPRS模块完成内部初始化
OSSemPend(GPRSSem, 0, &err); //得到对GPRS模块进行操作的信号量
for(i=0;i<20;i++) //一共进行20次尝试
{
GPRSFlushQueueSpec("OK");
if( GPRSSendStr("AT\r", "OK", &pos, OS_TICKS_PER_SEC*2) )
{
break;
}
OSTimeDly(OS_TICKS_PER_SEC*2);
}
if(i >= 20) //没有找到GPRS模块
{
OSSemPost(GPRSSem); //释放对GPRS模块进行操作的信号量
return ;
}
GPRSFlushQueueSpec("OK"); //清理用过的缓存
OSTimeDly(OS_TICKS_PER_SEC);
for(i=0;i<30;i++)
{
GPRSFlushQueueSpec("+CSMINS");
if( GPRSSendStr("AT+CSMINS?\r", "+CSMINS", &pos, OS_TICKS_PER_SEC*3) )
{
tmptr = GPRSQueuePosPtr(pos);
if(*(tmptr+11)=='1') //检测到SIM卡
{
GPRSSetState(CSIM_INS);
break;
}
}
OSTimeDly(OS_TICKS_PER_SEC*2);
}
if(i >= 25)
{
GPRSSetState(NO_REG); //卡无法登陆网络
OSSemPost(GPRSSem); //释放对GPRS模块进行操作的信号量
GPRSFlushQueueSpec("+CSMINS");
return;
}
GPRSFlushQueueSpec("+CSMINS");
if(GPRSGetState() == CSIM_INS)
{
if( GPRSSendStr("AT+CPIN?\r", "+CPIN:", &pos, OS_TICKS_PER_SEC*20) )
{
tmptr = GPRSQueuePosPtr(pos);
if(strcmp(tmptr,"+CPIN: READY") == 0) //不需要输入PIN码
{
GPRSSetState(CPIN_READY);
}
else
{
GPRSSetState(NO_CPIN);
}
}
GPRSFlushQueueSpec("+CPIN"); //清理用过的缓存
OSTimeDly(OS_TICKS_PER_SEC*2);
}
if(GPRSGetState() == CPIN_READY)
{
for(i=0;i<30;i++)
{
GPRSFlushQueueSpec("+CREG");
if( GPRSSendStr("AT+CREG?\r", "+CREG:", &pos, OS_TICKS_PER_SEC*3) )
{
tmptr = GPRSQueuePosPtr(pos);
if(*(tmptr+9)=='5' || *(tmptr+9)=='1') //漫游或者本地状态
{
GPRSSetState(GPRS_IDLE);
break;
}
}
OSTimeDly(OS_TICKS_PER_SEC*2);
}
if(i >= 20)
{
GPRSSetState(NO_REG); //卡无法登陆网络
}
GPRSFlushQueueSpec("+CREG");
OSTimeDly(OS_TICKS_PER_SEC*2);
GPRSFlushQueueSpec("OK");
if( !GPRSSendStr("AT+CMGF=1\r", "OK", &pos, OS_TICKS_PER_SEC*2) ) //设置为文本模式
{
OSSemPost(GPRSSem);
GPRSFlushQueueSpec("+CMGF");
return;
}
OSTimeDly(OS_TICKS_PER_SEC*2);
GPRSFlushQueueSpec("OK");
if( !GPRSSendStr("AT+CSCS=\"GSM\"\r", "OK", &pos, OS_TICKS_PER_SEC*2) ) //设置字符集
{
OSSemPost(GPRSSem);
GPRSFlushQueueSpec("+CSCS");
return;
}
OSTimeDly(OS_TICKS_PER_SEC*2);
GPRSFlushQueueSpec("OK");
if( !GPRSSendStr("AT+CSMP=17,168,0,0\r", "OK", &pos, OS_TICKS_PER_SEC*2) ) //设置文本模式参数
{
OSSemPost(GPRSSem);
GPRSFlushQueueSpec("+CSCS");
return;
}
}
OSSemPost(GPRSSem); //释放信号量
return ;
}
/*********************************************************************************************************
** 函数名称: GPRSViewCSQ(void)
** 功能描述: 判断当前信号强度是否正常
** 输 入: 无
**
** 输 出: 信号强度正常 1 ; 信号强度比较弱或者信号质量比较差 0
**
** 全局变量:
** 调用模块:
**
** 作 者:
** 日 期:
**-------------------------------------------------------------------------------------------------------
** 修改人:
** 日 期:
**-------------------------------------------------------------------------------------------------------
********************************************************************************************************/
uint8 GPRSViewCSQ(void)
{
char *buf;
char pos;
char CsqValue;
uint8 err;
GPRSFlushQueueSpec("+CSQ");
OSSemPend(GPRSSem, 0, &err); //得到对GPRS模块进行操作的信号量
if( GPRSSendStr("AT+CSQ\r", "+CSQ", &pos, OS_TICKS_PER_SEC*2) )
{
buf = GPRSQueuePosPtr(pos);
CsqValue = (char)atoi(buf+6);
if(CsqValue == 99 || CsqValue < 10) //没有信号或者信号强度较弱
{
OSSemPost(GPRSSem);
GPRSFlushQueueSpec("+CSQ");
return 0;
}
else
{
/* if( atoi(strchr(buf,',')+1) > 0)
{
OSSemPost(GPRSSem);
GPRSFlushQueueSpec("+CSQ");
return 0; //信号的质量比较差
}*/
}
}
OSSemPost(GPRSSem);
GPRSFlushQueueSpec("+CSQ");
return 1;
}
/*********************************************************************************************************
** 函数名称: GPRSQueryQ
** 功能描述: GPRS处理模块主动提供的信息
** 输 入: char *result 附加在消息的数据信息
**
** 输 出: 无
**
** 全局变量: GPRSState
** 调用模块: GPRS1Init,OSTimeDly,GPRSCommand,
**
** 作 者: XieLuWei
** 日 期: 2005年7月2日
**-------------------------------------------------------------------------------------------------------
** 修改人:
** 日 期:
**-------------------------------------------------------------------------------------------------------
********************************************************************************************************/
uint8 GPRSQueryQ(char *const reStr)
{
char pos;
if( GPRSCheckQueue("RING", &pos) ) //查看来电的消息
{
GPRSSetQueuePosSta(pos);
return RECEIVED_CALL;
}
else if( GPRSCheckQueue("NO CARRIER", &pos) ) //对方结束通话的消息
{
GPRSSetQueuePosSta(pos);
return RECEIVED_NOCARRIER;
}
else if( GPRSCheckQueue("+CMTI", &pos) ) //收到短消息的通知
{
strcpy(reStr,GPRSQueuePosPtr(pos));
GPRSSetQueuePosSta(pos);
return RECEIVED_SMS;
}
else if( GPRSCheckQueue("Call Ready", &pos) ) //收到短消息的通知
{
GPRSSetQueuePosSta(pos);
return RECEIVED_CALLREADY;
}
else
{
GPRSFlushQueueAll();
return RECEIVED_NO; //没有收到模块主动提供的信息
}
}
/*********************************************************************************************************
** 函数名称: GPRSDialUp
** 功能描述: 通过GPRS拨号
** 输 入: 电话号码
**
** 输 出: 拨号的结果
**
** 全局变量: GPRSState
** 调用模块: GPRSWrite,OSTimeDly
**
** 作 者: XieLuWei
** 日 期: 2005年2月25日
**-------------------------------------------------------------------------------------------------------
** 修改人: gumanzhou
** 日 期: 2008.07.08
**-------------------------------------------------------------------------------------------------------
********************************************************************************************************/
char AT_Buf[32];
uint8 GPRSDialUp(char *number)
{
uint32 i;
uint8 status = 0;
char *CLCCPtr; //指向CLCC回复的指针
char pos;
uint8 err;
if( !GPRSViewCSQ() ) //信号强度不满足需求的时候不拨号
return 0;//信号强度比较差
OSTimeDly(OS_TICKS_PER_SEC/2);
OSSemPend(GPRSSem, 0, &err); //得到对模块进行操作的信号量
_sprintf(AT_Buf,"ATD%s;\r",number);
GPRSFlushQueueSpec("OK");
GPRSWrite(AT_Buf);
OSTimeDly(OS_TICKS_PER_SEC*2);
GPRSSetState(GPRS_SENDATD);
for(i=0;i<20;i++) //最多等待20秒钟,判断是否成功拨号
{
OSTimeDly(OS_TICKS_PER_SEC/2); //每秒钟查询一次回复的状态,共20秒钟
if(GPRSCheckQueue("OK", &pos))
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -