MinGWでクロスコンパイラをビルドする(その1)2014年02月22日 22:31

 えーと、たぶんこのブログを読んでいる人には何の役にも立たない情報になると思いますが、世の中の同業者(同趣味?)向けの情報を記載しておきます。

 いろいろと理由があって、ARMのクロスコンパイラが欲しくなりました。
一番簡単なのはどこかの誰かがビルドしたバイナリを持ってくること、またはLinux上でビルドすることになります。
 でも、誰かがビルドしたものを持ってくるのは性に合わないので、自力でビルドすることにします。
 次にビルド環境をLinuxにするのかWindowsにするのかという選択肢がありますが、かかれこれ4年ほどLinuxから離れてWindowsアプリ開発者になってしまった身ですので、
Windows上でクロスコンパイラを作成してみます。
 4年前ならLinux上でのクロスコンパイラのビルドなんてルーチンワークのようにこなしていたのですが、もうすっかり忘れてしまって覚えていません。よって今回はInterface2008年11月号を参考にしながら作業しました。

1. MinGWをインストール
 MinGWの公式HPからセットアップツールをダウンロードして実行します。
 とにかく何も考えずにデフォルト設定でインストールしました。
 インストールが終わり、「Continue」ボタンを押下してMinGW Installation Managerを起動します。
 何を入れて良いかわからない(調べるのが面倒とも言う)ので、とりあえず「Basic Setup」を選択し、それっぽいものにチェックをしてインストールをしました。
今回チェックしたのは以下の4つです。
・mingw-developer-toolkit
・mingw32-base
・mingw32-gcc-g++
・msys-base(developer-toolkitを選択すると自動的に選択される)
これらをチェック後、「Installation」メニューから「Apply Changes」を選択して「Schedule of Pending Actions」ダイアログを開き、ダイアログの「Apply」ボタンを押下するとインストールが開始します。

2. MinGW/MSysのセットアップ
 MinGWはGNUのツールチェインで、それらを使うための環境(シェルで良いのかな?)がMSysになります。ここではMSysを使うための設定を行います。
 まず、C:\MinGW\msys\1.0\msys.batをダブルクリックしてMSysを起動します。
 次に、C:\MinGWをMSys内で/mingwにマウントするための設定をします。
 とはいっても、設定サンプルが用意されているのでコピーするだけです。
$ cp /etc/fstab.sample /etc/fstab
 MSysを一回閉じてもう一度起動するとgccが使えるようになっています。
 ついでにコンパイラ環境をインストールするディレクトリarm-toolsをExplorerで作成します。
 名前はなんでもいいですが、今回はC:\MinGW\arm-toolsとしておきます。
 (Explorerを使わずにMSysから作っても良いですが)

3. binutilsとgccソースコードをダウンロード
 まずはbinutilsとgccのソースコードをダウンロードします。
 以下からGCC4.8.2とbinutils2.24をダウンロードしました。
 ExplorerでC:\MinGW\msys\1.0\home\ユーザ名\に各ファイルをコピーしてここはおしまい。

4. binutilsをビルド
 binutilsのソースコードを解凍し、解凍したディレクトリに移動してビルドとインストールを行います。
$ tar zxvf binutils-2.24.tar.gz
$ cd binutils-2.24
$ ./configure --target=arm-elf-eabi --prefix=/mingw/arm-tools
$ make
$ make install

5. GCCをビルド
 gccのソースコードを解凍し、解凍したディレクトリに移動してビルドとインストールを行います。
$ tar jxvf gcc-4.8.2.tar.bz2
$ mkdir arm-elf-obj
$ cd arm-elf-obj
$ ../gcc-4.8.2/configure --target=arm-elf-eabi --prefix=/mingw/arm-tools/ --enable-language=c --disable-libssp
と、ここでエラーが出ました。
configure: error: Building GCC requires GMP 4.2+, MPFR 2.4.0+ and MPC 0.8.0+.
Try the --with-gmp, --with-mpfr and/or --with-mpc options to specify
their locations.
 GMPとMPFRとMPCを入れろということです。
 そんなわけで、GCCのビルドはやめてこれらのインストールを行います。

6. いろいろインストール
 上記の通り、GMPとMPFRとMPCのインストールが必要になりました。
 これらは以下からダウンロードできます。
 説明は面倒なのでコマンドだけ記載しますが、ビルド手順は以下の通りにしてください。(mpfrはgmpが必要、mpcはgmpとmpfrが必要なため)
$ tar jxvf gmp-5.1.3.tar.bz2
$ cd gmp-5.1.3
$ ./configure --prefix=/mingw/gmp-5.1.3
$ make
$ make check
$ make install

$ tar jxvf mpfr-3.1.2.tar.bz2
$ cd mpfr-3.1.2
$ ./configure --prefix=/mingw/mpfr-3.1.2 --with-gmp=/mingw/gmp-5.1.3
$ make
$ make check
$ make install

$ tar zxvf mpc-1.0.2.tar.gz
$ cd mpc-1.0.2
$ ./configure --prefix=/mingw/mpc-1.0.2 --with-mpfr=/mingw/mpfr-3.1.2 --with-gmp=/mingw/gmp-5.1.3 --disable-shared
$ make
$ make check
$ make install

7. GCCをビルド(再チャレンジ)
 物がそろったのでGCCのビルドに再チャレンジします。
$ cd ~/arm-elf-obj
$ rm -rf *
 make distcleanでも良いように思えますが何かエラーが出たような気がするので全削除をしました。(エラー内容を忘れました)
 ../configure --target=arm-elf-eabi --with-gmp=/mingw/gmp-5.1.3 --with-mpfr=/mingw/mpfr-3.1.2 --with-mpc=/mingw/mpc-1.0.2 --prefix=/mingw/arm-tools --enable-languages=c --disable-libssp
$ make
 ビルドが始まり、暇な時間が過ぎていきます。
 ...
 お、終わった?と思ってみると謎のエラーで止まっています。
C:\MinGW\msys\1.0\bin\make.exe: *** couldn't commit memory for cygwin heap, Win32 error 0
make[3]: *** [multi-do] Error 1
make[3]: Leaving directory `/home/ユーザID/arm-elf-obj/arm-elf-eabi/libgcc'
make[2]: *** [all-multi] Error 2
make[2]: Leaving directory `/home/ユーザID/arm-elf-obj/arm-elf-eabi/libgcc'
make[1]: *** [all-target-libgcc] Error 2
make[1]: Leaving directory `/home/ユーザID/arm-elf-obj'
make: *** [all] Error 2

 Google先生に聞いてみるとGHCで同様の現象が報告されています。
This error occurs when using the new build system with MSYS on Windows. It is a temporary error; just type make again to continue the build. Hopefully this is a bug in MSYS that will be fixed at some point.
「このエラーはWindowsのMSYSで新しいビルドシステムを使うと発生します。一時的なエラーなので、再度makeしてビルドを続けてください。このバグがそのうち修正されることを望みます。」
 よく分かりませんが、またmakeします。
$ make
 また暇な時間が過ぎていきます。
 ...
 でもまた同じエラーで止まります。
C:\MinGW\msys\1.0\bin\make.exe: *** couldn't commit memory for cygwin heap, Win32 error 0
 Google先生に聞いてみると、GCCのビルド以外でもこの問題は発生する模様。
 ソースコードの修正で解決しているものもあるようです。
 ということは、GCC4.8.2を使い続ける以上無理なのかなと思い、古いバージョンのGCCをいくつかダウンロードします。
 ダウンロードしている間は退屈なので、とりあえず意味もなくmakeしておきます。
 ...
 でも、やっぱり同じエラー。もー...。
C:\MinGW\msys\1.0\bin\make.exe: *** couldn't commit memory for cygwin heap, Win32 error 0
make[1]: *** [all-target-libgcc] Error 1
make[1]: Leaving directory `/home/ユーザID/arm-elf-obj'
make: *** [all] Error 2

 ここであることに気づきます。このブログを書くために記録しておいたメモを見ると、エラーが微妙に違います。
 期待に胸を膨らませてmakeを繰り返し続けたところ無事にビルドができたようですのでインストールします。
$ make install

7. 動作確認
 動作確認といっても、実行環境がないのでソースをコンパイルし、それをobjdumpでダンプしてみます。
 まずはソースコードを作成します。
 こんなのとか。
 a.c
 main()
 {
  int a;
  a = a + 1;
 }
 次にコンパイルをします。
$ /mingw/arm-tools/bin/arm-elf-eabi-gcc-4.8.2.exe -c a.c -o a.o

 作成されたa.oをobjdumpで見てみます。
 MSysで見ると文字化けするのでテキストファイルに落とします。
$ /mingw/arm-tools/bin/arm-elf-eabi-objdump -Dx a.o > dump.txt
 
 メモ帳で開いた内容は以下の通り。(抜粋)
 無事にARMになっていそうな雰囲気です。
a.o:     ファイル形式 elf32-littlearm
a.o
アーキテクチャ: arm, フラグ 0x00000010:
HAS_SYMS
開始アドレス 0x00000000
private flags = 5000000: [Version5 EABI]

セクション:
索引名          サイズ      VMA       LMA       File off  Algn
  0 .text         00000018  00000000  00000000  00000034  2**2
                  CONTENTS, ALLOC, LOAD, READONLY, CODE
  1 .data         00000000  00000000  00000000  0000004c  2**0
                  CONTENTS, ALLOC, LOAD, DATA
  2 .bss          00000000  00000000  00000000  0000004c  2**0
                  ALLOC
  3 .comment      00000012  00000000  00000000  0000004c  2**0
                  CONTENTS, READONLY
  4 .ARM.attributes 00000033  00000000  00000000  0000005e  2**0
                  CONTENTS, READONLY
SYMBOL TABLE:
00000000 l    df *ABS* 00000000 a.c
00000000 l    d  .text 00000000 .text
00000000 l    d  .data 00000000 .data
00000000 l    d  .bss 00000000 .bss
00000000 l    d  .comment 00000000 .comment
00000000 l    d  .ARM.attributes 00000000 .ARM.attributes
00000000 g     F .text 00000018 main

 おしまい。

2014/03/31:追記
一つ忘れていましたので追記しておきます。
GCCのビルド時に以下のようなエラーが発生することがあります。
checking for shl_load... configure: error: Link tests are not allowed after GCC_NO_EXECUTABLES.
make[1]: *** [configure-target-libstdc++-v3] Error 1

この場合、gccのソースコードフォルダにあるlibtool.m4を以下のように修正してください。
・修正前
  _LT_LINKER_HARDCODE_LIBPATH($1)
  LT_SYS_DLOPEN_SELF
  _LT_CMD_STRIPLIB

・修正後
  _LT_LINKER_HARDCODE_LIBPATH($1)
 # LT_SYS_DLOPEN_SELF
  _LT_CMD_STRIPLIB

コメント

コメントをどうぞ

※メールアドレスとURLの入力は必須ではありません。 入力されたメールアドレスは記事に反映されず、ブログの管理者のみが参照できます。

※なお、送られたコメントはブログの管理者が確認するまで公開されません。

名前:
メールアドレス:
URL:
コメント:

トラックバック

このエントリのトラックバックURL: http://dorapanda.asablo.jp/blog/2014/02/22/7228977/tb

※なお、送られたトラックバックはブログの管理者が確認するまで公開されません。

総閲覧数:
現在の閲覧者数:
カウント開始日:From 2013/04/06 00:15