Help us understand the problem. What is going on with this article?

rustをインストールしてhello world をARM用にクロスコンパイルするまでの手順

More than 1 year has passed since last update.

最近話題のrustを自分でも勉強しようと思って。

rustのインストール

このページに書いてあることをなぞる。

https://rust-lang-ja.github.io/the-rust-programming-language-ja/1.6/book/getting-started.html

curl https://sh.rustup.rs -sSf | sh

一度ログアウトして再度ログイン。

$ rustc --version
rustc 1.25.0 (84203cac6 2018-03-25)
mkdir hello_world
cd hello_world

hello_world.rs を作成。

hello_world.rs
fn main() {
    println!("Hello, world!");
}

コンパイルして実行。

$ rustc hello_world.rs
$ ./hello_world 
Hello, world!
$ file ./hello_world
./hello_world: ELF 64-bit LSB shared object, x86-64, version 1 (SYSV), dynamically linked, interpreter /lib64/ld-linux-x86-64.so.2, for GNU/Linux 2.6.32, BuildID[sha1]=9671f9cd6d9b1bb7b84022bde4d26af80fe992f4, not stripped
$ ls -lh ./hello_world
-rwxrwxr-x 1 koba koba 4.5M Apr 30 07:41 ./hello_world

ダイナミックリンクなのに、かなりサイズが大きいな。

クロスコンパイルの準備

rustのコンパイラはLLVMベースで構成されていて、いろいろなターゲットを切り換えることができます。追加可能なターゲットの一覧は以下の通り。

$ rustup target list
aarch64-apple-ios
aarch64-linux-android
aarch64-unknown-cloudabi
aarch64-unknown-fuchsia
aarch64-unknown-linux-gnu
aarch64-unknown-linux-musl
arm-linux-androideabi
arm-unknown-linux-gnueabi
arm-unknown-linux-gnueabihf
arm-unknown-linux-musleabi
arm-unknown-linux-musleabihf
armv5te-unknown-linux-gnueabi
armv7-apple-ios
armv7-linux-androideabi
armv7-unknown-cloudabi-eabihf
armv7-unknown-linux-gnueabihf
armv7-unknown-linux-musleabihf
armv7s-apple-ios
asmjs-unknown-emscripten
i386-apple-ios
i586-pc-windows-msvc
i586-unknown-linux-gnu
i586-unknown-linux-musl
i686-apple-darwin
i686-linux-android
i686-pc-windows-gnu
i686-pc-windows-msvc
i686-unknown-cloudabi
i686-unknown-freebsd
i686-unknown-linux-gnu
i686-unknown-linux-musl
mips-unknown-linux-gnu
mips-unknown-linux-musl
mips64-unknown-linux-gnuabi64
mips64el-unknown-linux-gnuabi64
mipsel-unknown-linux-gnu
mipsel-unknown-linux-musl
powerpc-unknown-linux-gnu
powerpc64-unknown-linux-gnu
powerpc64le-unknown-linux-gnu
s390x-unknown-linux-gnu
sparc64-unknown-linux-gnu
sparcv9-sun-solaris
wasm32-unknown-emscripten
wasm32-unknown-unknown
x86_64-apple-darwin
x86_64-apple-ios
x86_64-linux-android
x86_64-pc-windows-gnu
x86_64-pc-windows-msvc
x86_64-rumprun-netbsd
x86_64-sun-solaris
x86_64-unknown-cloudabi
x86_64-unknown-freebsd
x86_64-unknown-fuchsia
x86_64-unknown-linux-gnu (default)
x86_64-unknown-linux-gnux32
x86_64-unknown-linux-musl
x86_64-unknown-netbsd
x86_64-unknown-redox

armv7-unknown-linux-gnueabihf に必要なものを追加でインストール。

$ rustup target add armv7-unknown-linux-gnueabihf
info: downloading component 'rust-std' for 'armv7-unknown-linux-gnueabihf'
 39.6 MiB /  39.6 MiB (100 %)   8.3 MiB/s ETA:   0 s                
info: installing component 'rust-std' for 'armv7-unknown-linux-gnueabihf'

リンカーとしてクロスのgccを使用するので、以下の記事に従ってインストール。
x86_64のUbuntuでC/C++のソースコードをARM/ARM64用にクロスコンパイルしてQEMUで実行する方法のまとめ

クロスコンパイルと実行

以下のようにオプションを指定するとarm用にクロスコンパイルできます。

$ rustc -C linker=arm-linux-gnueabihf-gcc --target=armv7-unknown-linux-gnueabihf hello_world.rs 
$ file ./hello_world
./hello_world: ELF 32-bit LSB shared object, ARM, EABI5 version 1 (SYSV), dynamically linked, interpreter /lib/ld-linux-armhf.so.3, for GNU/Linux 3.2.0, BuildID[sha1]=359e7216dc873f9b567c030dde53f825ee07c290, not stripped
$ ls -lh ./hello_world
-rwxrwxr-x 1 koba koba 4.0M Apr 30 07:50 ./hello_world

QEMUをセットアップしてあるので、この実行ファイルはそのまま実行可能です。

$ ./hello_world 
Hello, world!

追記:stripしてみた

実行ファイルのサイズがとても大きいことが気になったのですが、コメントで教えてもらったことを参考に、stripコマンドでシンボル情報を除去してみました。

$ file ./hello_world
./hello_world: ELF 32-bit LSB shared object, ARM, EABI5 version 1 (SYSV), dynamically linked, interpreter /lib/ld-linux-armhf.so.3, for GNU/Linux 3.2.0, BuildID[sha1]=359e7216dc873f9b567c030dde53f825ee07c290, not stripped
$ cp ./hello_world hello_world_g
$ arm-linux-gnueabihf-strip ./hello_world
$ ls -lh hello_world*
-rwxrwxr-x 1 koba koba 330K Apr 30 11:09 hello_world
-rwxrwxr-x 1 koba koba 4.0M Apr 30 11:09 hello_world_g
-rw-rw-r-- 1 koba koba   46 Apr 30 07:40 hello_world.rs

1/10以下に小さくなりました。実機にはstrip済みの実行ファイルをインストールします。

追記:Cargo を使う方法

rustのcargoでarm64 linux向けにクロスビルドする

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