Qiita Teams that are logged in
You are not logged in to any team

Log in to Qiita Team
Community
OrganizationAdvent CalendarQiitadon (β)
Service
Qiita JobsQiita ZineQiita Blog
39
Help us understand the problem. What is going on with this article?
@tetsu_koba

x86_64のUbuntuでC/C++のソースコードをARM/ARM64用にクロスコンパイルしてQEMUで実行する方法のまとめ

More than 3 years have passed since last update.

はじめに

x86_64のLinux上でQEMUを使ってarm用の実行ファイルを動かす方法は以前に書いたことがあるのですが、最近は「マルチプラットフォームのライブラリをビルドしたときにCIを回す」というユースケースが出てきたので再度まとめてみました。

題材とするソースコードはこれ。

hello.c
#include <stdio.h>

int main()
{
    printf("Hello, world!\n");
}

Ubuntu 16.04 を使用しています。

ネイティブのコンパイルと実行

$ gcc -o hello_native hello.c
$ file hello_native 
hello_native: ELF 64-bit LSB executable, x86-64, version 1 (SYSV), dynamically linked, interpreter /lib64/ld-linux-x86-64.so.2, for GNU/Linux 2.6.32, BuildID[sha1]=ffce96d91ecac8524b1d8af9f37c9e719364df7e, not stripped
$ ./hello_native 
Hello, world!

クロスコンパイラのインストール

sudo apt install g++-arm-linux-gnueabihf

gccしか必要なくても、あえてg++をインストールするのがコツです。そうするとクロスのlibcなど必要な物が全て芋づる式にインストールされます。

クロスコンパイル

$ arm-linux-gnueabihf-gcc -o hello_arm hello.c 
$ file ./hello_arm 
./hello_arm: ELF 32-bit LSB executable, ARM, EABI5 version 1 (SYSV), dynamically linked, interpreter /lib/ld-linux-armhf.so.3, for GNU/Linux 3.2.0, BuildID[sha1]=9719544312d6cdfb69a31ca70a4655c12e5596d8, not stripped
$ ./hello_arm
-bash: ./hello_arm: cannot execute binary file: Exec format error

そのままではx86_64のUbuntuの上ではARM用の実行ファイルは実行することができません。

QEMUのインストール

sudo apt install qemu-user-binfmt

これでスタティックリンクされたARMの実行ファイルならそのまま実行できるようになります。

$ arm-linux-gnueabihf-gcc -o hello_arm_static -static hello.c 
$ file ./hello_arm_static 
./hello_arm_static: ELF 32-bit LSB executable, ARM, EABI5 version 1 (GNU/Linux), statically linked, for GNU/Linux 3.2.0, BuildID[sha1]=72d599d8f0e385a6daa8ebe6216f8fbe8755bda2, not stripped
$ ./hello_arm_static 
Hello, world!

ダイナミックリンクされたARMの実行ファイルは以下のようにクロスのルートディレクトリをQEMUに明示的に指定すれば実行できるようになります。

$ qemu-arm -L /usr/arm-linux-gnueabihf/ ./hello_arm
Hello, world!

ダイナミックリンクされたARMの実行ファイルもそのまま実行できるようにする

sudo ln -s /usr/arm-linux-gnueabihf/lib /lib/arm-linux-gnueabihf
sudo ln -s /lib/arm-linux-gnueabihf/ld-2.23.so /lib/ld-linux-armhf.so.3
$ ./hello_arm
Hello, world!

arm64の場合

arm64のツールチェインの名前が違うだけで同様にできます。

sudo apt install g++-aarch64-linux-gnu qemu-user-binfmt
sudo ln -s /usr/aarch64-linux-gnu/lib/ /lib/aarch64-linux-gnu
sudo ln -s /lib/aarch64-linux-gnu/ld-2.23.so /lib/ld-linux-aarch64.so.1
$ aarch64-linux-gnu-gcc -o hello_arm64 hello.c
$ file ./hello_arm64 
./hello_arm64: ELF 64-bit LSB executable, ARM aarch64, version 1 (SYSV), dynamically linked, interpreter /lib/ld-linux-aarch64.so.1, for GNU/Linux 3.7.0, BuildID[sha1]=776d40691c4192c0521c641f17b3754b37b73109, not stripped
$ ./hello_arm64 
Hello, world!

参考

QEMUのもうひとつの使い方: ユーザーモードエミュレーションとbinfmtとchrootの組み合わせ
Ubuntu 12.04LTS Beta2でMultiarchを試す
Ubuntu 12.04LTS 正式版でMultiarchを試す

39
Help us understand the problem. What is going on with this article?
Why not register and get more from Qiita?
  1. We will deliver articles that match you
    By following users and tags, you can catch up information on technical fields that you are interested in as a whole
  2. you can read useful information later efficiently
    By "stocking" the articles you like, you can search right away
tetsu_koba
組み込みの人。

Comments

No comments
Sign up for free and join this conversation.
Sign Up
If you already have a Qiita account Login
39
Help us understand the problem. What is going on with this article?