前言
QQ:562983648
由于工作原因,已经许久没有接触飞控了。18年的时候曾经写过一个半成品开源飞控,是基于Keil MDK这款商业IDE开发的,只能在Windows下运行。由于笔者现在绝大部分时间都在使用Linux,偶尔想回顾一下以前的代码,竟不太方便,因此萌生了将原先的飞控项目移植到Linux下的想法。
目前国内单片机开发的教程绝大部分都是基于Keil的,Keil MDK作为一款商业IDE,的确存在它的优势:集成度高、上手快、编译器优化较好等。但是其劣势也很明显,首先这是款商业软件,需要付费,虽然绝大部分人所使用的是盗版,在国内个人使用不是什么大问题,但是如果是公司使用的话,极可能会收到起诉函(笔者工作后已经碰见过数起案例了)。其次最重要的是无法跨平台,只能在Windows下使用,这也是笔者想要替换它的最大原因。最后,Keil MDK的编辑器功能在2019年看来,已经算是古董级别了。。。
VSCode & CMake
Linux平台下,并没有一款成熟好用的单片机IDE。笔者这里推荐的是较为热门的开源代码编辑器:VSCode,前面有几篇博文也均介绍了如何使用VSCode开发APM之类的开源飞控,感兴趣的可以去看一下,这里就不详细介绍了。
编译器使用gcc,这是一款支持多种编程语言的开源编译器。虽然对代码的优化程度有所不及Keil内置的armcc商业编译器,但也足够我们使用了,主流开源嵌入式项目基本全部使用gcc。
IDE的便利之处在于自动搞定了编译及链接规则,解放了双手。现在我们要在不依赖IDE的情况下,手动编写编译规则,大名鼎鼎的Makefile便是这样的工具。但很多时候手动编写Makefile较为繁琐,工作量很大。所以通常我们会使用更加高级的自动构建工具,比如CMake,同样类似的工具还有SCons、Waf(APM项目使用的工具)等等。这里笔者选择使用CMake,原因很多无需赘述(其实只是因为对CMake更熟点),非常多的开源C/C++项目都是基于CMake构建的。
CMake是一个跨平台的自动构建工具,使用简单的描述语句,就能自动生成Makefile或其它project文件(和Makefile同级别的还有ninja之类的)。由于VSCode、CMake及gcc编译工具链都可以跨平台,因此这套开发编译系统同样能在Windows下运行,MDK可以再见了。
安装gcc-arm-none-eabi交叉编译工具链
gcc编译工具链可从下面链接下载,版本的话没有特殊要求,最新的便可以。
https://developer.arm.com/tools-and-software/open-source-software/developer-tools/gnu-toolchain/gnu-rm/downloads
Linux下具体的安装方式可以参考前面一篇博文:使用VSCode打造APM飞控的编译+烧录+调试一体的终极开发环境。
安装完后在终端中输入
arm-none-eabi-gcc --version
如果正确输出版本信息表示已经安装成功。
编写CMakeLists.txt
首先到Github上把天穹飞控clone下来,然后在项目根目录下新建一个CMakeLists.txt。
由于网上资料丰富,这里就不仔细介绍CMake语法了,可自行百度或者谷歌,下面只会简单说明所使用到的CMake语句。
1.指定CMake版本和工程名字
cmake_minimum_required(VERSION 3.10)
project(BlueSkyPilot)
这里指定了项目所需求的CMake最低版本,并定义了工程名。
2.设置编译工具链
由于飞控使用C语言编写,因此这里指定C编译器为arm-none-eabi-gcc,注意前面必须要正确安装了编译工具链,CMake才能识别。
set(CMAKE_C_COMPILER arm-none-eabi-gcc)
下面还定义了几个需要用到的工具,其中arm-none-eabi-objcopy用于输出bin文件,arm-none-eabi-size用于查看文件占用flash和ram的大小。
set(CMAKE_OBJCOPY arm-none-eabi-objcopy)
set(CMAKE_SIZE arm-none-eabi-size)
3.添加宏定义
如果你使用过MDK开发STM32,可能会记得需要添加几个宏定义,这个主要是STM32固件库的需求,这里就照搬过来了。
add_definitions(
-DSTM32F40_41xxx
-DUSE_STDPERIPH_DRIVER
-DARM_MATH_CM4
)
其中STM32F40_41xxx指定了所使用的单片机型号(仅跟STM32固件库有关系)。
4.设置编译选项
set(MCU_FLAGS "-mcpu=cortex-m4 -mfloat-abi=hard -mfpu=fpv4-sp-d16")
set(CMAKE_C_FLAGS "${MCU_FLAGS} -w -Wno-unknown-pragmas")
set(CMAKE_C_FLAGS_DEBUG "-O0 -g2 -ggdb")
set(CMAKE_C_FLAGS_RELEASE "-O3")
CMAKE_C_FLAGS表示编译C语言文件时需要附带的编译选项