- 投稿日:2020-11-12T17:46:17+09:00
Debian上でRaspberry Pi Zero向けクロスコンパイル ~自作の共有ライブラリを作ってみる
概要
これらの記事の続きです。
簡単な共有ライブラリと共有ライブラリを呼び出すプログラムを(Windows10 の VirtualBox の)Debian 上でビルドして、Raspberry Pi で動かしてみます。
環境
ホスト: Debian 10.6.0 < Virtual Box 6.1 < WIndows10
ターゲット: Raspberry Pi 3 Model A+前回の Raspberry Pi Zero から Raspberry Pi 3 に変わってます。
なぜかというと Raspberry Pi Zero の ARM v6系 CPU向けのクロスコンパイルがうまく動かなかったからです。Raspberry Pi 3 の ARM v8系 CPU向けの方はあっさり通りました。
コンパイラのバグのような気がするけど、何が悪いかご存じの方がいらっしゃいましたら教えてください。
今回のプログラム
全然中身はないですが、お試し用のプログラムはこんな感じにしました。
test_so_lib.h#ifndef TEST_SO_LIB_H #define TEST_SO_LIB_H void print_hoge (int num); #endiftest_so_lib.c#include <stdio.h> #include "test_so_lib.h" void print_hoge (int num) { int i; for (i = 0; i < num; i++) { printf("hogehoge\n"); } }main.c#include "test_so_lib.h" int main (void) { print_hoge(5); return 0; }これを普通にビルドして動かすとこんな感じ。
$ gcc -shared test_so_lib.c -o libtestso.so $ gcc test_so_main.c -o test_so_main -I./ -L./ -Wl,-rpath=./ -ltestso $ ./test_so_main hogehoge hogehoge hogehoge hogehoge hogehogeクロスコンパイルしてみる
Raspberry Pi Zero 向け
ダメだった Raspberry Pi Zero 向けの方の話を手短に、、
ビルド環境は 前回の記事 の通りです。その環境でこんな感じ、、Debian$ arm-linux-gnueabi-gcc -march=armv6 -shared test_so_lib.c -o libtestso_armv6.so $ arm-linux-gnueabi-gcc -march=armv6 test_so_main.c -o test_so_main_armv6 -I./ -L./ -Wl,-rpath=./ -ltestso_armv6ビルドでできた test_so_main_armv6, libtestso_armv6.so を Raspberry Pi Zero にコピーして、実行してみると、、
RaspberryPiZero$ ./test_so_main_armv6 ./test_so_main_armv6: error while loading shared libraries: libtestso_armv6.so: cannot open shared object file: No such file or directoryなんかエラーが出ました。共有ライブラリ libtestso_armv6.so が見つからないっぽい。原因がよく分かりません。
Raspberry Pi 3 向け
ビルド環境
Raspberry Pi 3 の ARM v8系のビルドには armhf向けのクロスコンパイラを使います。
前回の記事 でarmelって書いてあるところをarmhfに修正してこんな感じ。armhfクロスコンパイラのインストール
$ sudo apt install crossbuild-essential-armhfアーキテクチャの追加
$ sudo dpkg --add-architecture armhf $ sudo nano /etc/apt/sources.list/etc/apt/sources.listdeb [arch=armel,armhf] http://ftp.jp.debian.org/debian buster main今回は armel は使いませんが両方使いたいなら書き方はこんな感じでいいはず。
$ sudo apt update $ sudo apt install libusb-dev:armhf $ sudo apt install libjpeg-dev:armhfちなみに、今回は自作の共有ライブラリ以外は使わないので、
crossbuild-essential-armhfのインストールだけすれば大丈夫です。
(ここまで書いたのは自分用のメモ)ビルド
-marchで指定するアーキテクチャをarmv8-aにしています。
(armv8というのは指定できないらしい)Debian$ arm-linux-gnueabihf-gcc -march=armv8-a -shared test_so_lib.c -o libtestso_armv8a.so $ arm-linux-gnueabihf-gcc -march=armv8-a test_so_main.c -o test_so_main_armv8a -I./ -L./ -Wl,-rpath=./ -ltestso_armv8aビルドでできた test_so_main_armv8a, libtestso_armv8a.so を Raspberry Pi 3 にコピーして、実行。
RaspberryPi3$ ./test_so_main_armv8a hogehoge hogehoge hogehoge hogehoge hogehogeあっさり動いた。
まとめ
arm-linux-gnueabi-gccでarmv6向けにビルドして Raspberry Pi Zero で動かなくてしばらく悩んでたのだけど、arm-linux-gnueabihf-gccでarmv8-a向けに同じ手順でビルドしてあっさり動いてるところをみるとarm-linux-gnueabi-gcc自体がちょっと怪しいのかなと思ったりしている。もしかすると何かビルド時にオプションが必要とか環境が足りてないとかあるのかもしれないけど、よく分からなかったので、もし分かる方がいらっしゃったら教えてください。