STM32F1与GSM-SIM900A模块短信测试

平台:野火霸道开发板(STM32F103ZET6)

模块:SIM900A(大卡的SIM卡)

测试内容: STM32对GSM模块控制(串口2),控制其发送短信给10086(我用的移动卡),然后通过32转发接收,再把其内容发到串口1上

连接:

GSM模块上的STX <-> STM32 PA3;  SRX <-> STM32 PA2; GND(GSM) <-> GND(开发板上随便一个地)

注意,GSM模块上有STX和MRX,这个M指的是MAX3232,是工业串口用的, S才是我们常用的TTL电平(有可能是MOS电平)

程序:

需要发送短信号码修改为10086

USART_Config(); 

配置串口1,主要是用来GSM与STM32通信的内容,通过串口1进行转发打印到串口助手上

 GSM_USART_Config();

配置串口2,主要是通过STM32通过串口2对GSM模块进行AT控制发送指令

 SysTick_Init();

系统滴答定时器,主要是用来做延时的,如后面的delay_ms

    //检测模块响应是否正常
    while(gsm_cmd("AT\r","OK",1000) != GSM_TRUE)
    {
      printf("\r\n模块响应测试不正常!!\r\n");
      printf("\r\n若模块响应测试一直不正常,请检查模块的连接或是否已开启电源开关\r\n");
    }

gsm_cmd("AT\r","OK",1000)

通过这个封装好的函数, stm32通过串口2,对GSM发送 'AT\r' 指令,

发送之后,再通过里面的

gsm_cmd_check(reply); 

进行对接收数据的判断,判断接收到GSM返回来的指令是不是"OK",是OK就返回正常(GSM_TRUE)

如果返回不是OK, 串口1就会输出

      printf("\r\n模块响应测试不正常!!\r\n");
      printf("\r\n若模块响应测试一直不正常,请检查模块的连接或是否已开启电源开关\r\n");
 

如果串口没有打印上面的信息,那么就是正常,证明连接上了GSM了

如果错误,检测下你是不是接错线,或者漏了接GND-GND的线,又或者没有插入SIM卡

    printf("\r\n通过了模块响应测试\r\n");
    
		printf("\r\n正在等待GSM模块初始化...\r\n");
		while(IsInsertCard() != GSM_TRUE)
		{
			
			if(++testCard >20)
			{
				printf("\r\n检测不到电话卡,请断电并重新接入电话卡\r\n");
			}
			GSM_DELAY(1000); 		
		}	

IsInsertCard() 

同样的,有用的只有这一条

gsm_cmd("AT+CNUM\r","OK",200);

通过串口2发送"AT+CNUM\r", 然后等待200ms,然后判断接收的内容是不是"OK",是就返回正常(GSM_TRUE)

这时候GSM模块就已经初始化好了,下面可以发送消息了

    /* 延时5秒再发送命令到模块 */
    GSM_DELAY(5000);    
    
    //发送英文短信
	if(gsm_sms((char *)num,"cxye") == GSM_TRUE)
		printf("\r\n英文短信已发送至:%s,为方便测试,请在程序中修改接收短信的手机号码",num);
	else
	{
		printf("\r\n短信发送失败,请确认目标号码有效");
	}
    GSM_DELAY(2000);    

通过下面函数,发送"cxye" 查询余额

gsm_sms((char *)num,"cxye")

其中num是上面的 10086号码, "cxye"就是发送的内容

            //生成电话号码命令 
            sprintf(cmdbuff,"AT+CMGS=\"%s\"\r",num);

将发送的电话号码10086,通过sprintf,复制到cmdbuff里面, 并且附加上短信头指令

然后把cxye内容复制到converbuff里面去

先发送电话号码 \\ sprintf(cmdbuff,"AT+CMGS=\"%s\"\r",num);

gsm_cmd(cmdbuff,">",200)

然后坐等回复一个>

再把信息通过

GSM_USART_printf("%s",converbuff);//发送短信内容

发送出去 (类似上图的This is a test 只是这里换成了cxye)

主循环

  while(1)
	{
		GSM_DELAY(1000);
		newmessadd=IsReceiveMS();	
		if(newmessadd)
		{			
			IsRead=readmessage(newmessadd,namenum,str);				
			 
//			printf("newmessadd=%d,IsRead:%d\n",newmessadd,IsRead);
			if(IsRead)
			{				
				printf("新短信\n\r");

				hexuni2gbk(namenum,namegbk);	
				hexuni2gbk(str,gbkstr);						
				printf("新短信:\n发件人:%s\n内容:%s\n\r",namegbk,gbkstr);
			}
		}
		
	}

newmessadd=IsReceiveMS();

查询是否接收到新短信

gsm_cmd_check("+CMTI:")

这个就是判断 有没有接收到 +CMTI:   字符串

找到回复信息的 内容首地址,通过strstr来匹配"+CMTI: \"SM\"
        redata_off = strstr(redata,"+CMTI: \"SM\",");

主函数中的

IsRead=readmessage(newmessadd,namenum,str);    

newmessadd为接收到回复信息的内容首地址

namenum为发送人(10086给你发送回信,这里发送人就是10086)

str 为10086给你发送的内容信息

sprintf(cmd,"AT+CMGR=%d\r",messadd);    

先准备好字符内容cmd(通过sprintf,将AT+CMGR=内容地址,赋值给cmd的)

然后把要读取的信息头cmd发送出去, 然后坐等匹配到+CMGR:

匹配到之后 看看是不是首次读(UNREAD)

把发送人的手机号码提取出来(10086)

把日期,时间,和回复的内容都保存到str上面去

主函数中

hexuni2gbk功能为unicode与gbk互转功能

hexuni2gbk(namenum,namegbk); // 转换接受人姓名

hexuni2gbk(str,gbkstr);    // 接收内容

最后把转好的内容通过printf打印到串口1上

printf("新短信:\n发件人:%s\n内容:%s\n\r",namegbk,gbkstr);

编译, 下载 看看

结果没有收到回信

开始调试程序

串口助手显示了下面

查一下CMGS:36, 只是说明已经发送成功了而已(现在发的是第36条),还是没接收到回信

现在问题是系统没有给我 自动上报接收到短信通知

不用32调试,直接用串口来发送AT命令看看

把串口1的短接帽拔下,拿来给GSM作USB转串口用

sTX->RXD ; sRx-> TXD, GND->GND

不需要程序,直接打开开关发命令就好

先发AT\r\n ,看看正常不

注意敲个回车

显示正常

检测是否插卡了, 显示也是正常

发短信试试

但还是没有收到新信息的命令

--------------------------------------------------------------------

2020年10月9日 昨天已经发现问题所在了,今天才有空写一写

1.AT+CNMI=?新消息指示 需要设置

设置为 AT+CNMI=2,1,0,0,0 

就好,转自

https://blog.csdn.net/qq_35629563/article/details/82752886

2.问题调试出现再:短信只能存50条,多余50条就接受不了新消息了,只能删除

因此,我们要先查看信息

短信查看全部的,获取的数据要转码

AT+CMGL="ALL"

一般用上面语句,列出所有信息

删除具体某一条信息可以用

AT+CMGD=50

具体作用为删除第50条短信

也可以用AT+CMGDA="DEL READ"

作用为删除所有已读短信

3.当你再输入AT+CMGL="ALL" 列出所有信息时,如果还有空间容纳新短信(小于50条才能接受新内容,指示SIM900A是这样的),这时才能接受新的信息

比如你收到了一条信息, 它是下面的语句格式的(AT+CNMI=2,1,0,0,0设置情况下)

+CMTI: "SM",22

+CMTI就是标头, SM是指信息, 22是指的信息存储的位置

如果你要读22位置的短信,使用下面语句

AT+CMGR=32,0

作用为读取第32条消息,0指正常读

读完之后,22这位置的短信状态会由 REC UNREAD 变成 REC READ

猜你喜欢

转载自blog.csdn.net/jwdeng1995/article/details/108745559