目的
- 了解如何在x86架构电脑下进行arm程序的交叉编译
- 了解如何对qt源码程序的交叉编译
- 了解如何进行qt程序的交叉编译
- 在网上借鉴了很多大佬的分享,所以自己也总结一下自己经验,希望帮助更多的人
- 希望大佬积极纠错,大家共同成长
准备步骤
交叉编译要注意版本问题,主要是向目标机器(最终要运行程序的机器)看齐,多花一些时间把目标机器开发环境的版本搞清楚,找到对应版本的交叉编译链,后面的大方向大多是正确的。 这次目标机器搭载了银河麒麟(V10 注意不是V10 SP1),版本信息如下
Linux version 4.4.131-20210817.kylin.desktop-generic (YHKYLIN-OS@d0ee15aef8b2)
(gcc version 5.4.0 20160609 (Ubuntu/Linaro 5.4.0-6kord1~16.04.12) ) #kylin-KylinOS SMP Tue Aug 17 08:41:44 UTC 2021
进行交叉编译的环境我用虚拟机搭建,使用ubuntu系统,版本信息如下。
Linux version 5.13.0-40-generic (buildd@ubuntu) (gcc (Ubuntu 9.4.0-1ubuntu1~20.04.1) 9.4.0,
GNU ld (GNU Binutils for Ubuntu) 2.34) #45~20.04.1-Ubuntu SMP Mon Apr 4 09:38:31 UTC 2022
现在要看一下开发环境的版本问题,其实主要是匹配对gcc的版本,目标机的gcc版本是gcc version 5.4.0 20160609 (Ubuntu/Linaro 5.4.0-6kord1~16.04.12),ubuntu20.04自带的gcc肯定是不能用,因为那是x86架构版本的。需要找一个匹配目标机gcc版本的交叉编译链安装到虚拟机上,但是版本需要匹配到什么程度才行,是要两个gcc版本必须一致吗?还是存在几个小版本差别的gcc就可以算作匹配。这里还需要查看一个参数,就是libc.so.6的版本(这个文件的历史和作用可以自行百度),这是gcc安装目录下的一个库文件的软连接,找到这个文件执行ls -l,查看结果。目标机版本是libc-2.23.so,那目标机的gcc只能支持2.23这个版本吗?这里可以执行strings /lib/aarch64-linux-gnu/libc.so.6 |grep GLIBC_,查看结果,可以支持的版本有2.17、2.18、2.22、2.23,也就是说我们要找的交叉编译链gcc中的那个库的版本符合其中的一个就行,这样提高了兼容性。
xxx@xxx:/lib/aarch64-linux-gnu$ strings libc.so.6 | grep ^GLIBC_
GLIBC_2.17
GLIBC_2.18
GLIBC_2.22
GLIBC_2.23
GLIBC_PRIVATE
接下来就是找一个交叉编译链,在上文可以看到目标机gcc的版本是gcc version 5.4.0 20160609,就以这个版本开始前后找。我这次是在下面这个网站找的
https://releases.linaro.org/components/toolchain/binaries/
folder 4.9-2016.02 -
folder 4.9-2017.01 -
folder 5.1-2015.08 -
folder 5.2-2015.11 -
folder 5.2-2015.11-1 -
folder 5.2-2015.11-2 -
folder 5.3-2016.02 -
folder 5.3-2016.05 -
folder 5.4-2017.01 - //这两个版本看样子符合我们的要求起码是5.4版本的
folder 5.4-2017.05 -
再点击进入几层目录,直接到达这个地址,选择解压后能直接用的成品(还要注意32位、64位,大端序还是小端序,选择基于自己开发环境的系统和机器)
https://releases.linaro.org/components/toolchain/binaries/5.4-2017.05/aarch64-linux-gnu/
Name Last modified Size License
gcc-linaro-5.4.1-2017.05-x86_64_aarch64-linux-gnu.tar.xz 27-Feb-2018 00:14 86.5M open //这个是解压后就能用的
直接下载,放到虚拟机中,解压,首先查看一下上面说到的版本,结果如下,目标机器的版本正好兼容虚拟机的版本,这应该是可以用的
xxx@xxx:/usr/local/gcc-linaro-5.4.1-2017.05-x86_64_aarch64-linux-gnu/aarch64-linux-gnu/libc/lib$ strings libc.so.6 | grep ^GLIBC_
GLIBC_2.17
GLIBC_2.18
GLIBC_PRIVATE
交叉编译Qt源码
在编译源码前一定要阅读一下源码目录下的README文件,基本就能搭配编译环境了
现在已经找到合适交叉编译链,接下来就可以使用交叉编译链编译Qt源码生产arm版的库文件,大家可以参考下面大佬的博客,我基本是按照他的步骤来的。
当然,即使是按部就班的来,还是会出现不可预知的问题,前进的道路还是坎坷的,我刚开始是想编译5.15.2版本的,结果报错内存字节没有对齐。接着又尝试4.8.7版本,又错了。最后尝试5.13.2版本,经过多次尝试编译成功。
编译Qt源码主要是要写好configure参数,大家可以参考一下我的
#!/bin/bash
./configure -prefix /usr/local/qt5.13.2ForArm \
-opensource \
-confirm-license \
-skip qtlocation \ # 这个模块当时编译报错,我用不到为了赶时间直接跳过了
-nomake examples \
-nomake tests \
-xplatform aarch64-linux-gnu-g++ \
-debug \
-no-opengl \
大家也可以参考这篇文章,看看Qt模块
https://www.devbean.net/2012/08/qt-study-road-2-modules/
在make install中还遇到了,没有找到python的错误,可以参考这篇文章
在执行make的时候,会报错找不到交叉编译器,但我确实添加了编译器的环境变量,在这个问题上纠结了许久,可以参考这篇文章
按照上述方法可以交叉编译qt源码,并且编译成功,当然模块肯定不是全的,很多模块对应的环境还没有,但是基础使用还是够的。
qtcreator编译arm版qt程序
直接使用交叉编译链命令行编译程序对我来说有点复杂,还要写Makefile什么的。所以我决定用qtcreator编译程序。这里要注意,在安装qtcreator时,只需要勾选qtcreator模块本身就行了,其他qt提供的编译器不需要。至于qtcreator的版本,我用的也是5.13.2版本。
操作步骤可以参考下面的博客,可以找qt自带的例子程序编一下,看看能不能通过(我是从windows上找的源码,ubuntu上我没有下载例子程序源码)
下面是我配置的界面