学完STM32和FreeRTOS,想做一个项目巩固提高一下水平。接下来的一个月我都会实时更新项目进度,项目代码纯手打,编译调试过程也会演示。
一.简要介绍MQTT协议
1.物联网介绍
Ⅰ.物联网(IOT, internet of things),顾名思义,万物联网,让所有设备联网以达到消费者用户能够实时了解以及控制这些设备的目的。物联网实际上就是网络通信的过程。
Ⅱ.MQTT协议。关于MQTT协议,本网站有专业的简介和源码分析,网址:你不得不看的图文并茂的MQTT协议通信过程!!!_你不得不看mqtt-CSDN博客长话短说,MQTT协议是基于TCP协议的<客户端-服务端>的轻量级应用层物联网通信协议。在通信过程中,有三种身份,分别是:订阅者,服务器和发布者。用MQTT作者的比喻就是:订阅者要订阅主题,这个消息会发给CCTV,如果该主题的发布者要发布主题了,就会将该主题消息发送给CCTV,CCTV就会将该消息转发给订阅了该主题的订阅者,实现MQTT通信。流程如下:
可见MQTT通信过程主要步骤有:连接,订阅,发布,断开连接
二.移植FreeRTOS
1.为什么需要FreeRTOS
STM32F103开发板是没有操作系统的,但是在MQTT客户端,显而易见的,至少会有两个任务:订阅主题和发布主题。而这两个任务必须得并发执行,因为STM32F103开发板既是订阅者也是发布者。这时操作系统就必须介入,合理安排任务执行,这里的任务就类比Linux的进程和线程。而FreeRTOS作为一个轻量级的实时操作系统正好满足我们的需求。
2.移植FreeRTOS
FreeRTOS源码可以直接去官网下载。需要移植的文件有:FreeRTOS-Kernel-main-include,这是头文件目录;FreeRTOS-Kernel-main-portable,移植里面的内存管理和RVDS;FreeRTOS-Kernel-main所有.c文件,这些是FreeRTOS核心文件;最后别忘了!还有专门为STM32F103准备的头文件FreeRTOSConfig.h。将这些文件添加到keil目录并添加路径即可。
三.移植MQTT客户端代码
这部分代码移植比较麻烦,一定会有许多报错,但是我们没有必要怕这些错误。我们可以这么想:编译器也是程序员写出来的,因此对于编译器的各种报错我们的程序员前辈一定都预料到了,所以才会给我们提示错误,既然这些错误会被提示,就一定有解决办法,只是我们暂时不知道而已!
一般来说,移植代码的步骤分为:合并代码,解决编译报错,解决链接错误,调试。
MQTT的源代码可以去github上搜索,应该是jiejie或者kawaii这两位大佬贡献的。我们先在keil工程目录里添加MQTT的代码,然后在keil里面编译,然后-----就是一堆错误啦o.o
因为是第一次做项目,作者解决这些这些错误总共花了5 / 6个小时@.@,真的是在最后想要放弃的时候突然就调好了!!所以说不要被报错吓到了,“懦弱之举,我决不姑息!”以下是作者总结的处理各种报错的方法:
Ⅰ找不到头文件,这是最常见的错误,编译器一般首先都会报这个错误。解决办法是:
if (在工程文件中真实存在该文件) {
将其路径添加进来
} else {
if (确实需要) {
另外找一份该文件 | 自己手撸一份o.o
} else {
注释掉 #include
}
}
Ⅱ 变量,宏,函数未定义,解决完第一种报错后,大概率就是这一种了,解决办法:
if (在工程文件里面真是定义过) {
#include "定义该变量(宏)的头文件"
if (已经include头文件) {
检查其是否声明
}
} else {
if (真的需要) {
自己手动添加定义
} else {
注释掉
}
}
Ⅲ 宏定义不能强制转换,记住就行,因为预处理的时候编译器不知道你要强转的类型的定义
Ⅴ 不支持匿名结构体:两种办法:1.增加-gnu选项;2.添加 #pragma anon_unions
Ⅵ link error,undefined symbol xxx.首先检查是否将需要用到的文件添加到了keil目录,如果添加了,检查定义该函数(变量)的文件,是否因为条件编译中的宏没有定义导致无法识别(作者在被这个错误耗了3个小时@.@)
ConfigUSE_MUTEXS这个宏没有定义,导致一直连接错误 undefined symbol prvInitialiseMutex,一气之下我直接将其改成 #if 1 ,强制生效!结果编译通过了o.o
OK,今天先写到这里,作者做完这些已经很累了,明天开始梳理代码结构并开始coding