1.什么是交叉编译?
宿主机(Host)是编辑和编译程序的平台,一般是基于X86的PC,本文指虚拟机中运行的Ubuntu。
目标机(Target)是目标运行环境,通常是非X86平台的设备,本文指SiRider S1开发板。
交叉编译是指在一台计算机上进行编译,生成在另一种不同体系结构或操作系统上运行的可执行程序或库文件。通常用于开发跨平台的软件,或者在资源有限的嵌入式系统上进行开发,在本文中指的是在虚拟机Ubuntu中编译SiRider S1开发板运行的程序。
2.编译器安装
在SDK编译过程中,已经将交叉编译器下载了(se1000-sdk/toolchain/gcc-arm-10.3-2021.07-x86_64-aarch64-none-linux-gnu.tar.xz),需要配置下虚拟机ubuntu中的环境。以下操作为将编译器解压到/opt/siengine/目录。
tar -xvf gcc-arm-10.3-2021.07-x86_64-aarch64-none-linux-gnu.tar.xz
mkdir /opt/siengine/
cp gcc-arm-10.3-2021.07-x86_64-aarch64-none-linux-gnu /opt/siengine/ -rf
配置编译器环境变量,在/etc/profile文件末尾添加配置:
vi /etc/profile
export PATH="/opt/siengine/gcc-arm-10.3-2021.07-x86_64-aarch64-none-linux-gnu/bin:$PATH"
3.QT交叉编译
①.QT源码解压
以qt-everywhere-opensource-src-5.15.15.tar.xz为例:
tar -xvf qt-everywhere-opensource-src-5.15.15.tar.xz
②.编译器配置
进入qt-everywhere-src-5.15.15/qtbase/mkspecs目录,复制linux-aarch64-gnu-g++配置为aarch64-none-linux-gnu-g++
cp linux-aarch64-gnu-g++ aarch64-none-linux-gnu-g++ -r
进入aarch64-none-linux-gnu-g++目录,修改qmake.conf配置中编译器相关配置为aarch64-none-linux-gnu-
②.编译配置与编译
回到QT目录,输入QT编译配置:
./configure -prefix "$PWD"/SE1000_QT_INTASLL \
-opensource \
-confirm-license \
-release -strip \
-no-eglfs -linuxfb \
-qt-zlib \
-no-gif \
-qt-libpng \
-qt-libjpeg \
-qt-freetype \
-no-rpath \
-no-pch \
-no-avx \
-no-openssl \
-no-cups \
-no-dbus \
-no-pkg-config \
-no-glib \
-no-iconv \
-xplatform aarch64-none-linux-gnu-g++ \
-no-opengl \
-nomake examples \
-nomake tools \
-no-sqlite \
-optimize-size \
-skip qtgamepad \
-skip qtandroidextras \
-skip qtmacextras \
-skip qtx11extras \
-skip qtsensors \
-skip qtserialbus \
-skip qtserialport \
-skip qtwebengine \
-skip qtwebchannel \
-skip qtwebsockets \
-skip qtlocation \
-skip qtquickcontrols \
-skip qtpurchasing \
-skip qtconnectivity \
-skip qtscxml \
-skip qtxmlpatterns \
-skip qtnetworkauth \
-skip qtspeech \
-skip qtscript \
-skip qtremoteobjects \
-skip qtcharts \
-skip qtdatavis3d \
-skip qtwebview \
-skip qt3d \
-skip qtquick3d \
-skip qtdoc \
-skip qttranslations \
-skip qtwayland \
-skip qtwayland \
-skip qtwebglplugin \
-skip qtwinextras \
-skip qttools
等待编译配置完成,之后执行make -j8进行编译,此时会根据电脑配置的不同,需要等待不定时长以完成编译。
出现以下信息则说明已完成编译。
③.安装
完成编译之后,执行make install即可在当前目录中SE1000_QT_INTASLL生成编译后的文件。
为了方便管理,本文习惯会将相关文件拷贝到/opt/Qt5.15.15/aarch64-none-linux目录。
mkdir -p /opt/Qt5.15.15/
cp -r SE1000_QT_INTASLL /opt/Qt5.15.15/aarch64-none-linux
同时在原有编译器目录建立软链接。
ln -s /opt/Qt5.15.15/aarch64-none-linux/bin/qmake /opt/siengine/gcc-arm-10.3-2021.07-x86_64-aarch64-none-linux-gnu/bin/aarch64-none-linux-gnu-qmake
④.交叉编译QT demo
以moveblocks为例,先进入源码目录,执行aarch64-none-linux-gnu-qmake即可生成makefile文件,再执行make即可生成可执行程序moveblocks。
cd qt-everywhere-src-5.15.15/qtbase/examples/widgets/animation/moveblocks
aarch64-none-linux-gnu-qmake
make
4.QT程序运行测试
*以下操作均为在板端执行。
在嵌入式开发中,常常通过NFS进行主机与板端进行数据共享,本文亦如此。
先在板端安装NFS挂载支持功能。
sudo apt install nfs-common
本文以虚拟机ubuntu开发环境中/home/ebaina/Workspace/NFS/SE1000/为NFS挂载目录,并已将SE1000_QT_INTASLL和moveblocks程序拷贝到该目录,虚拟机ubuntu NFS服务器需自行搭建,本文并未提及。
将交叉编译生成的QT库文件拷贝到板端。
cd SE1000_QT_INTASLL
cp lib plugins /opt/ -rf
配置QT环境变量。
export QT_QPA_PLATFORM_PLUGIN_PATH=/opt/plugins
export LD_LIBRARY_PATH=/opt/lib/
export QT_QPA_PLATFORM=linuxfb:tty=/dev/fb0
export QT_QPA_PLATFORM=linuxfb:fb=/dev/fb0:size=1920x1080:offset=0x0:nographicsmodeswitch
export QT_QPA_FONTDIR=/opt/lib/fonts
运行测试程序moveblocks,发现程序无法运行,因为libc.so.6版本不匹配,交叉编译器中的版本为gcc 10.3,而板子则为gcc 9.4.
①.尝试将交叉编译器中的库直接拷贝到板端,结果发现直接导致板子死机。
②.尝试更新libc,发现软件源上的并没有匹配的版本,测试了国内外的源均如此。
至此,以上为一次SiRider S1开发板平台的交叉编译尝试,最终由于libc.so.6版本不匹配导致程序无法运行而结束,后续有解决办法都再进行尝试并记录。