概述
一、环境介绍
MCU: STM32F103C8T6
GSM模块: 移远MC20 (MT2503D)(GSM+GPS共存)功能很强大
开发软件: Keil5
MQTT协议采用OneNet的旧版协议,登录OneNet控制台创建应用时要选择旧版本。
如果想使用新版本的标准MQTT协议连接OnetNet请参考这里: https://blog.csdn.net/xiaolong1126626497/article/details/107385118
完整源代码下载: https://download.csdn.net/download/xiaolong1126626497/18245206
二、MC20模块
MC20模块采用联发科技最新推出的多功能通信定位芯片研制而成。它是一款集成LCC封装、四频段GSM/GPRS和先进算法GNSS引擎于一体的全功能通信模块,具有超小体积、低功耗、双卡单待等优势。MC20不仅内嵌丰富的网络协议(如 TCP、UDP、PPP、FTP、HTTP以及SSL),还集成了多星座卫星系统(如北斗、GPS、QZSS),因此能提供无线移动通信以及精准的导航定位功能。
除具备GSM/GPRS无线通信功能外,MC20模块还支持先进的GNSS技术。它集成了EPOTM(用户无需自设服务器,直接从MTK服务器获取EPO数据)、秒定等技术,能够实现快速首次定位。由于支持北斗、GPS、QZSS等多星座卫星系统解调算法,其定位更加精准,抗多路径干扰能力更强,比传统GPS模块具有更多优势。另外,MC20模块中内置LNA和低功耗算法:前者使其接收灵敏度提升至-149dBm;后者使其在低功耗模式(GLP Mode)下的耗流仅为正常工作模式的40%。
MC20模块较传统GSM+GNSS方案体积减少40%,使其在各种应用中占具更大优势。其主要应用领域为:可穿戴设备(智能手表)、宠物追踪、财产追踪及行车记录仪等等。
主要优势
● 超小体积: 18.7mm × 16.0mm × 2.1mm
● 多卫星导航系统: GPS/BeiDou/QZSS
● GNSS 接收机通道: 99 路捕获通道/33 路跟踪通道
● 支持多种 AGPS 技术,如 EASYTM 、EPOTM 、秒定等
● 内置 LNA 大大提升 GNSS 接收机灵敏度(-167dBm@跟踪模式):可使用无源 GNSS 天线而无需任何外部低噪声放大器
● 支持增强型 GNSS 功能,如 SDK 命令、LOCUSTM 、AIC 和 GLP
● 多功能四频段 GSM模块: 850/900/1800/1900MHz
● 内嵌丰富网络协议: TCP/UDP/PPP/HTTP/FTP/SSL
● 支持语音、短信、QuecFOTATM 、双卡单待以及 OpenCPU 功能
● 支持蓝牙 V3.0 以及 SPP & HFP-AG 配置文件
三、代码功能
使用STM32F103C8T6 通过串口+AT指令控制MC20模块+MQTT协议,登录OneNet服务器上传GPS数据,LED控制(网页按钮控制开发板上的LED灯)。
四、核心代码
4.1 main.c
#include "stm32f10x.h"
#include "beep.h"
#include "delay.h"
#include "led.h"
#include "sys.h"
#include "usart.h"
#include <string.h>
#include <stdio.h>
#include "timer.h"
#include "mc20.h"
//网络协议层
#include "onenet.h"
//协议封装文件
#include "dStream.h"
//产品ID
char PROID[]="231174";
//鉴权信息
char AUTH_INFO[]="1234567890";
//设备ID
char DEVID[]="523369555";
//API KEY
char API_KEY[]="k6vtrrEd1H7UMddiF3DzripS47w=";
//缓冲区
char onenet_http_cmd[1024];
//服务器IP地址
#define TCP_SERVER_IP_ADDR "183.230.40.39"
//服务器端口号
#define TCP_SERVER_PORT 6002
//数据流结构
DATA_STREAM data_stream[1]=
{
{"gps","88.88",TYPE_JSON,1},
};
/*
STM32开发板接线说明:
STM32 MC20
3.3V ------> V_IO
GND <-----> GND
PA3 <------ GSM_TX
PA2 ------> GSM_RX
*/
int main()
{
u32 time_cnt=0;
u32 cnt=0;
double Longitude; //经度
double latitude; //纬度
LED_Init();
BEEP_Init();
USART_X_Init(USART1,72,115200);
TIM2_Init(72,20000); //辅助串口2接收,超时时间为20ms
USART_X_Init(USART2,36,9600); //连接着MC20(GPS+GPRS)
printf("串口准备就绪.....rn");
DelayMs(500);
printf("程序修改时间: %srn",__TIME__);
while(1)
{
u8 stat;
/*初始化MC20,并连接到指定服务器*/
MC20_InitConnect(TCP_SERVER_IP_ADDR,TCP_SERVER_PORT);
/*登录OneNET服务器,上线设备*/
stat=OneNet_DevLink();
if(stat)printf("ERROR:%d,接入OneNET失败:%drn",stat,cnt++);
else break; //登录成功
LED1=!LED1;
delay_ms(200);
break;//失败也退出继续运行下面代码
}
printf("6. OneNET服务器登录成功!rn");
delay_ms(100);
while(1)
{
/*6. 向OneNet服务器5秒发送一次数据*/
time_cnt++;
DelayMs(1);
if(time_cnt>=5000)
{
time_cnt=0;
/*获取一次GPS输出的经纬度信息*/
switch(MC20_GetGPS_Data(&Longitude,&latitude))
{
case 0: printf("经度:%f,纬度:%frn",Longitude,latitude); break;
case 1: printf("ERROR:GPS数据接收失败!rn"); break;
case 2: printf("ERROR:GPS定位数据解码失败!<请将GPS拿到空旷位置定位>rn"); break;
}
//组装数据格式
sprintf(onenet_http_cmd,"{"lon":%f,"lat":%f}",Longitude,latitude);
data_stream[0].dataPoint=onenet_http_cmd; //赋值GPS数据
//向云端发送数据流
OneNet_SendData(FORMAT_TYPE1,DEVID,API_KEY,data_stream,1);
}
/*实时接收MC20收到的数据,进行解析*/
if(USART2_RX_FLAG)
{
USART2_RX_BUFF[USART2_RX_CNT]='