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

ARM環境のRaspbianイメージをx86上のDockerで動かす

More than 1 year has passed since last update.

※2019/6/24 buster対応により、imgファイルのbootパーティションのサイズが変わったため変更

はじめに

Raspberry Piを深く触っていると、実機上の作業では時間がかかりすぎて耐えられないことはないでしょうか。例えば…

  • Qt等、巨大なライブラリの最新版がどうしても必要となり、実機上でコンパイルしたら終わりそうにない or エラーのモグラ叩き(しかもスペックが貧弱なので、エラーが数時間おきで発生し収束しない)に陥ることが多々あります
    • パワフルなマシン上で、実機と同じ仮想環境を構築してコンパイルしたい
    • クロスコンパイルだと設定が複雑なので、時間は少しかかってもいいから単純にやりたい(Raspbianをやめて、最新のライブラリがあるArch Linuxを使うという手もあります)
  • 実機と同じアーキテクチャ上の仮想環境で、実機より効率よく開発したい

ということで、お手持ちのPCをビルド環境や開発環境にするため、ARMアーキテクチャで動くRaspbianイメージをDockerで動かす手順をまとめました。

qemuのシステムエミュレーションを使うので、ホストPCのスペックと比べたら動作は全体的に遅くなります。
それでも馬力のあるマシンなら実機よりはるかにマシで、また、実機と同じ手順・バイナリが使えるので環境間の差異をあまり気にしなくて済む、というのが大きなメリットです。

本頁は、以下のサイトの手順を簡易にしたものになります
http://blog.guiraudet.com/raspberrypi/2016/03/03/raspbian-image-for-docker.html

また、Dockerの基本的な操作は割愛します。コンテナの起動/ログイン/終了といった手順は別途お調べください。

ざっくりとした手順

  • Dockerをインストール
  • Linux環境を用意 (上記のDocker上でも別マシン上でも良い)
  • Linux環境でRaspbianイメージを取得し、イメージファイルを展開
  • 展開先にqemu-arm-staticを入れる
  • tarで固め、Dockerのホスト環境へ移動
  • Dockerイメージを作成
  • Dockerを起動

なお、筆者が確認した環境ですが、Host環境はmacOS Mojave、Linux環境はDocker上のDebian(多分64bit)、Raspbianは32bit版です。

詳細な手順

Dockerのインストール

割愛します

Linux環境を用意

ここも詳細は割愛しますが、上述のDockerにDebianを入れた前提で記載を進めます。
別環境で行う場合、特権が必要なコマンドは頭にsudoをつけてください。

Dockerで行うときはイメージファイルがマウントできるよう、--privilegedオプションをつけてください。

$ docker pull debian
$ docker run -it --privileged debian
(Debian環境にログイン)
#

Linux環境でRaspbianイメージを取得し、イメージファイルを展開

lite、desktop、fullなdesuktop、なんでもいいです。
コマンド中の日本語は正しいファイル名に置き換えてください(「ダウンロードしたファイル」、「imgファイル」)

(Raspbian Lite)
# wget https://downloads.raspberrypi.org/raspbian_lite_latest
(Raspbian with desktop)
# wget https://downloads.raspberrypi.org/raspbian_latest
(Raspbian with desktop and recommended software)
# wget https://downloads.raspberrypi.org/raspbian_full_latest

(zipを展開)
$ unzip ダウンロードしたファイル

(imgを展開 ※offsetの箇所の解説は追記予定)
# mkdir image

(stretchまで)
# sudo mount -o loop,offset=$((512*98304)) imgファイル image
(buster※)
# sudo mount -o loop,offset=$((512*532480)) imgファイル image

※リリースによって変動がある模様。開始セクタを調べるには
# fdisk imgファイル
で、pコマンド(printの略)を実行
# Command (m for help): p

Device                          Boot  Start     End Sectors  Size Id Type
2019-09-26-raspbian-buster.img1        8192  532479  524288  256M  c W95 FAT32 (LBA)
2019-09-26-raspbian-buster.img2      532480 7479295 6946816  3.3G 83 Linux

第2パーティションの開始セクタの数字を使います。この例だと532480。

展開先にqemu-arm-staticを入れる

# apt-get -y install qemu-user-static
# mv image/etc/ld.so.preload image/etc/ld.so.preload.bak
# cp /usr/bin/qemu-arm-static image/usr/bin

Dockerイメージを作成

いつ基準のものかをファイル名のYYYY-MM-DDにつけておくとあとでわかりやすいと思います。不要な場合は除去してください。

# cd image
# tar cf ../docker-image-YYYY-MM-DD-raspbian-stretch.tar .

何らかの手段でホスト環境に上記tarファイルをコピー

(Linux環境を抜けます)
# exit

(ホスト環境にて)
$ docker import docker-image-YYYY-MM-DD-raspbian-stretch.tar raspbian-x86_64:YYYYMMDD

Dockerを起動

ホスト環境にて実施します。docker run時は必要に応じてオプションをいじってください。下記の例ではポート5901番で起動したVNCに接続可、マウント可にしてあります。

$ docker run -p 5901:5901 --privileged -it raspbian-x86_64:YYYYMMDD /bin/bash

無事起動したら、raspi-configでタイムゾーン等を変更後、いつもの通りapt-get updateapt-get upgradeにて、環境が出来上がります。
ユーザpiで作業したい場合は、以下のようにします。

# su pi
$ cd
(以下、/home/pi下で作業)

また、CPUやメモリをどのくらい割くかはDockerのオプションで指定してください。
CPU8コアメモリ4GBとか、贅沢な環境が手に入ります。

普段の運用

詳細は割愛しますが、以下の繰り返しになります。stopしないと裏でずっと回ってくれます。VNCを併用するのもいいと思います。

$ docker start (コンテナID)
$ docker attach (コンテナID)
(ログイン)
#
(作業)
# exit
(ログアウト)
$ docker stop (コンテナID)
hishi
趣味でサイクルコンピュータを作っている人です。
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