各種条件
Long Term Support の Qt5.12.0 が出ているので、それを Raspberry Pi (以降RPi) 用にビルドする手順を残します。
(ARMv6 も含めた全シリーズ向けのビルドになり、ARMv7 以降の最適化は適用していません)
作業環境は、Ubuntu16.04(x86-64) で行っていますが、debian 系であれば差異はないと思います。
また、本記事で対象とした Raspbian は 2018-11-13-raspbian-stretch です。
まず、必要なファイル群の置き場とその環境変数を下記として作業を進めます。
項目 | 環境変数 | 設定値 |
---|---|---|
作業場 | WORK_PATH | /home/user/work |
RPi ルートファイルシステム | RPI_ROOTFS | /home/user/work/raspbian |
クロスコンパイラの保管場所 | CROSS_TOOLS | /home/user/work/tools |
作業用パス | QT_SOURCE | /home/user/work/qt5.12.0/src |
インストール先(Raspbian内の) | QT_TARGET_INSTALL_PATH | /opt/qt/Qt5.12.0 |
それぞれ、設定方法は下記の通り。設定は好みによります(実際のところ私も下記PATHは使っていません)。
$ export WORK_PATH=/home/user/work
$ export RPI_ROOTFS=${WORK_PATH}/raspbian
$ export CROSS_TOOLS=${WORK_PATH}/tools
$ export QT_SOURCE=${WORK_PATH}/qt5.12.0/src
$ export QT_TARGET_INSTALL_PATH=/opt/qt/Qt5.12.0
必要なファイル群の準備
RPi 用クロスコンパイラの準備
汎用的なARM向けのコンパイラも使えるとは思いますが、RPi向けとしてコンパイラも提供されているのでそちらを使う。
$ cd ${WORK_PATH}
$ git clone https://github.com/raspberrypi/tools.git
$ ls tools/
arm-bcm2708 build-qt.sh mkimage sysidk usbboot
armstubs configs pkg test_code
実際に利用するのは下記のファイル群(x86/x64は環境にあわせて)。
tools/arm-bcm2708/gcc-linaro-arm-linux-gnueabihf-raspbian/bin/arm-linux-gnueabihf-*
tools/arm-bcm2708/gcc-linaro-arm-linux-gnueabihf-raspbian-x64/bin/arm-linux-gnueabihf-*
対象のRPiイメージファイルを取得
下記で、現時点で最新のイメージファイルを取得。
$ cd ${WORK_PATH}
$ wget https://downloads.raspberrypi.org/raspbian_lite_latest
$ ls
tools wheezy-raspbian-latest.zip
イメージファイル内へアクセスするためにマウント
何はともあれ、まずは解凍。
$ cd ${WORK_PATH}
$ mkdir ${RPI_ROOTFS}
$ unzip wheezy-raspbian-latest.zip
$ ls
tools wheezy-raspbian-latest.zip 2018-11-13-raspbian-stretch.img
Raspbian は FAT32 の boot パーティションと ext4 の rootfs パーティションに分かれている。
$ fdisk -l 2018-11-13-raspbian-stretch.img
Disk 2018-11-13-raspbian-stretch.img: 3.2 GiB, 3405774848 bytes, 6651904 sectors
Units: sectors of 1 * 512 = 512 bytes
Sector size (logical/physical): 512 bytes / 512 bytes
I/O size (minimum/optimal): 512 bytes / 512 bytes
Disklabel type: dos
Disk identifier: 0x025ce4e3
デバイス 起動 Start 最後から セクタ Size Id タイプ
2018-11-13-raspbian-stretch.img1 8192 98045 89854 43.9M c W95 FA
2018-11-13-raspbian-stretch.img2 98304 6651903 6553600 3.1G 83 Linux
それぞれのパーティションの開始位置を算出してマウント。
$ sudo mount -o loop,offset=$((512*98304)) 2018-11-13-raspbian-stretch.img ${RPI_ROOTFS}
$ sudo mount -o loop,offset=$((512*8192)) 2018-11-13-raspbian-stretch.img ${RPI_ROOTFS}/boot
$ ls ${RPI_ROOTFS}
bin dev home lost+found mnt proc run srv tmp var
boot etc lib media opt root sbin sys usr
Qemu の準備
Raspbian は当然 ARM 向けのバイナリで、作業環境が x86 系の場合、ファイルにアクセスできても直接実行できない。
そこで、ホスト側に CPU エミュレータである Qemu をインストールして x86 上でも実行できるように準備する。
$ sudo apt-get -y install qemu-user-static
$ sudo cp /usr/bin/qemu-arm-static ${RPI_ROOTFS}/usr/bin
Raspbian 内からネットワークにアクセスするための準備
上記 Qemu の準備で、${RPI_ROOTFS} へ chroot すれば作業できるようにはなっている。
ただ、そのままでは Raspbian 内からネットワーク等へのアクセスはできないため、ホストの環境を共有させる。
$ sudo mount --bind /dev ${RPI_ROOTFS}/dev
$ sudo mount --bind /sys ${RPI_ROOTFS}/sys
$ sudo mount --bind /proc ${RPI_ROOTFS}/proc
Raspbian 内の環境準備
ここまでで、Raspbian 内で作業するための準備が整ったので、引き続き、Raspbian 内の環境を構築していく。
$ sudo chroot ${RPI_ROOTFS}
# apt-get -y update
# apt-get -y upgrade
# apt-get -y install libglu1-mesa-dev gperf bison flex
Qt の Configure 時、OpenGL 系のライブラリが一部アクセスできなかったため、シンボリックリンクを張って補う。
Raspbian 内での作業はこれで終わりなので、exit で chroot から抜けておく。
# cd /opt/vc/lib
# ln -s libbrcmEGL.so libEGL.so
# ln -s libbrcmGLESv2.so libGLESv2.so
# ln -s libbrcmOpenVG.so libOpenVG.so
# ln -s libbrcmWFC.so libWFC.so
# exit
共有したホストの環境(とboot)のマウントを解除しておく。
$ sudo umount ${RPI_ROOTFS}/*
さらに、Raspbian を外部(今作業しているPC)からアクセスして使うために、一部の絶対パスで張られているシンボリックリンクを相対パスに置き換えておく。
$ cd ${RPI_ROOTFS}/usr/lib/arm-linux-gnueabihf
$ find . -maxdepth 1 -type l | while read i; do qualifies=$(file $i | sed -e "s/.*link to \(.*\)/\1/g" | grep ^/lib); if [ -n "$qualifies" ]; then echo $qualifies; newPath=$(file $i | sed -e "s/.*link to \(.*\)/\1/g" | sed -e "s,\`,,g" | sed -e "s,',,g" | sed -e "s,^/lib,../../../lib,g"); sudo rm $i; sudo ln -s $newPath $i; fi done
以上で、ターゲットとなる Raspbian の準備は完了。
Qt の最新のソースコードを取得
$ git clone git://code.qt.io/qt/qt5.git ${QT_SOURCE}
$ cd ${QT_SOURCE}
$ git branch
* 5.12
なお、ビルドに使用したリビジョンは下記。
$ git log -n 1
commit f95cd8d3f148ce6c5892a73b343f4889ca04762c
Author: Qt Submodule Update Bot <qt_submodule_update_bot@qt-project.org>
Date: Wed Dec 26 22:30:43 2018 +0100
Update submodules on '5.12' in qt5
Change-Id: I4b4259963187eeeb8a4914c5581f3b4c69d70aa5
Reviewed-by: Qt Submodule Update Bot <qt_submodule_update_bot@qt-project.org>
リポジトリの初期設定
clone 後の環境には、初期設定を行うためのスクリプトが用意されている。
これを使って、適宜必要な追加ファイルを取得しておく。
$ cd ${QT_SOURCE}
$ ./init-repository
configure の実行
clone した Qt5.12.0 のソースコードを、必要に応じて設定を変えて configure 実行。下記はexampleをコンパイルせず、ARMv6も含めたコンパイル指定。
-prefix によるインストール先の指定は Raspbian から見た絶対パスで、ホスト基準だと ${RPI_ROOTFS}/${QT_TARGET_INSTALL_PATH} 以下に配置される。
(未指定だと ${RPI_ROOTFS}/usr/local/Qt-5.12.0 以下)
./configure -opensource -confirm-license -device linux-rasp-pi-g++ -device-option \
CROSS_COMPILE=${CROSS_TOOLS}/arm-bcm2708/gcc-linaro-arm-linux-gnueabihf-raspbian-x64/bin/arm-linux-gnueabihf- \
-sysroot /opt/raspbian -make libs -no-compile-examples -prefix ${QT_TARGET_INSTALL_PATH}
ビルドの実施
ビルドの実施。make の後の -j は、物理コア数(Hyper Thread による増分はカウントしない) +1 がベター。
その後、ビルドが正常に完了したことを確認できれば、上記 -prefix で指定したパスへインストール実施。
$ cd ${QT_SOURCE}
$ make -j3
$ make install
謝辞
下記が大変参考になりました。違いは、
・Qemu の 完全仮想化を用いたエミュレーションではなく、chroot での作業方法に置き換え
・tar.xz で固められているソースからではビルドが通らず、git から取得して実施
[Qt5.11.2のRaspberry Pi 3 クロスコンパイル環境(まだ実験中)] https://qiita.com/muratamuu/items/66199590b54da5b2c59b