概述
单片机使用C语言实现MQTT协议
在单片机使用MQTT协议非常普遍,特别是在物联网相关领域,在阿里云,华为云等公有云都提供MQTT协议连接物联网平台。
本篇介绍如何用C语言实现MQTT的连接
MQTT连接主要有五步骤:
1. 连接云平台
2. 登录用户名密码等
3. 订阅主题
4. 发送心跳包
5. 发布主题
1. 连接云平台跟其他网站一样,只要有服务器地址和端口号就行,在这里我使用了以太网口去连接
代码如下:
u16 AnalyTarIp(u8 *TarIp,u16 port,u8 i)
{
static u8 dnsSel = 0;
u16 stateStamp;
uip_ipaddr_t ipaddr;
u8 ip[4];
g_mconn[i].flag = 0;
stateStamp = GetSecCnt();
//Á¬½Ó·þÎñÆ÷
g_mconn[i].port = port;
//端口
//IP还是域名
if(IsIPaVailable(TarIp))
//IP
{
if(str2ip(ip, TarIp))
//str To num
{
uip_ipaddr(&ipaddr, ip[0], ip[1], ip[2], ip[3]);
uip_ipaddr_copy(g_mconn[i].ip, ipaddr);
//记录IP
S282_Log("uip connecting...");
g_mconn[i].tcp = uip_connect(&g_mconn[i].ip, htons(g_mconn[i].port));
g_mconn[i].state = TcpClient_Connectting;
stateStamp = GetSecCnt();
}
}
else //域名
{
u8 HaveDns = 0;
if(DhcpOk == 0)
{
if(dnsSel == 0)
{
if(SysInfo.DnsIp1[1] != 0 && SysInfo.DnsIp1[0] != 0xff)
{
uip_ipaddr(ipaddr, SysInfo.DnsIp1[0],SysInfo.DnsIp1[1],SysInfo.DnsIp1[2],SysInfo.DnsIp1[3]);
HaveDns = 1;
}
if(SysInfo.DnsIp2[1] !=0 || SysInfo.DnsIp1[2] !=0 )
{
dnsSel = 1;
}
}
if((HaveDns == 0) && dnsSel)
{ //DNS2
dnsSel = 0;
if(SysInfo.DnsIp2[1] != 0 && SysInfo.DnsIp2[0] != 0xff)
{
uip_ipaddr(ipaddr, SysInfo.DnsIp2[0],SysInfo.DnsIp2[1],SysInfo.DnsIp2[2],SysInfo.DnsIp2[3]);
HaveDns = 1;
}
}
}
if(HaveDns || DhcpOk)
{//进行域名解析
g_mconn[i].state = TcpClient_DnsRequest;
g_mconn[i].flag &= ~e_Dns_found;
S282_Log("Analy Target Server ip");
if(resolv_getserver() == NULL)
{
resolv_conf(ipaddr);
//配置DNS服务器
}
g_mconn[i].dnsno = resolv_query((char*)&TarIp[0]);//请求域名解析
g_mconn[i].dnsno |= 0x80;
stateStamp = GetSecCnt();
}
}
return stateStamp;
}
域名解析成功后直接连接
g_mconn[i].tcp = uip_connect(&g_mconn[i].ip, htons(g_mconn[i].port));
g_mconn[i].state = TcpClient_Connectting;
- 登录用户 需要用户名 密码和设备ID
代码如下:
/*
MQTT 连接
入参 mode: 0 GPRS网络 1 以太网网络
*/
void MqttConnect(u8 mode)
{
u8 i;
u16 len;
MQTTPacket_connectData mqttConnDat = MQTTPacket_connectData_initializer;
GetMqttConnectData(m_mqttBuf,M_CLIENT);
if(SysInfo.MqttDeviceID[MQT_TXT_DATLEN] == 0)
{
//设备ID为空使用IMEI码
for(i = 0; i < 15; i++)
{
m_mqttBuf[i] = g_IMEI[i];
}
m_mqttBuf[i] = '