iPhone用に boostのユニバーサルスタティックライブラリを作成

色々と調べたけど、現状の最新環境でうまく行かなかったので、最終的に作成した手順をまとめておくことにしました。

前提として、以下の環境でユニバーサルスタティックライブラリを作成

  • OS: MacOSX 10.8 Mountain Lion
  • コンパイラ: XCode 4.4.1の clang
    • さらに、libc++ を使用する
  • boost: ver 1.50.0
    • ビルド対象ライブラリ: regex, thread(特に指定していないため、ひと通りのライブラリが作成されますが、この手順では arm版のsignalだけbuildエラーになるため、そこは諦めました。。。)

それでは、buildの手順です。

何はともあれ、boost_1_50_0.tar.bz2 をdownloadしてきて解凍します。

$ tar zxf boost_1_50_0.tar.bz2
$ cd boost_1_50_0

次に、boostのbuildのキモになる、bootstrapとbjamを実行します。
今回は、ユニバーサルスタティックライブラリを作成するのが目的ですが、一回のbuildで作成する方法が分からなかったため、arm版とi386版を別々にbuildしてあとからユニバーサルバイナリを作成するという手順になっています。*1

$ ./bootstrap.sh --with-toolset=clang
$ ./b2 toolset=clang cxxflags="-std=c++11 -stdlib=libc++" linkflags="-stdlib=libc++" cflags="-std=c99 -arch armv7 -fvisibility=default -miphoneos-version-min=5.0" architecture=arm target-os=iphone link=static threading=multi define=_LITTLE_ENDIAN include=/Applications/Xcode.app/Contents/Developer/Platforms/iPhoneOS.platform/Developer/SDKs/iPhoneOS5.1.sdk/usr/include/
$ mv stage/lib stage/lib_arm
$ ./b2 toolset=clang cxxflags="-std=c++11 -stdlib=libc++" linkflags="-stdlib=libc++ -arch i386" cflags="-std=c99 -fvisibility=default -arch i386" architecture=x86 address-model=32 target-os=iphone link=static threading=multi include=/Applications/Xcode.app/Contents/Developer/Platforms/MacOSX.platform/Developer/SDKs/MacOSX10.7.sdk/usr/include
$ mv stage/lib stage/lib_i386
$ mkdir stage/lib
$ lipo -create -output stage/lib/libboost_thread.a -arch armv7 stage/lib_arm/libboost_thread.a -arch i386 stage/lib_i386/libboost_thread.a 
$ lipo -create -output stage/lib/libboost_regex.a -arch armv7 stage/lib_arm/libboost_regex.a -arch i386 stage/lib_i386/libboost_regex.a 

以上で、完了です。stage/lib 以下にユニバーサルスタティックライブラリが作られます。
手順としては、基本に忠実に bootstrap.sh→b2*2×2 でライブラリを生成→lipo でユニバーサルライブラリ生成 となっています。最後のlipoコマンドで、ライブラリ名を変えていけばそれぞれのライブラリのユニバーサルバイナリが作成できます。

*1:もっと、うまいやり方があれば教えて下さい。

*2:いつの間にか bjamが新しくなってたんですね。