MinGWでBoost 1.48.0を使う
ビルドが必要なboost::threadやboost::regexを使いたい時にはまったので私的メモ、
試したOSはWindows7。
手順
解凍したboostのパスにて、以下のコマンドでビルド用のbjam.exeを作る
bootstrap.bat gcc
生成されたbjam.exeを使い、ライブラリをビルドする
bjam.exe -sTOOLS=mingw --toolset=gcc --stagedir="boostのパス\stage\mingw" --without-python --without-mpi --build-type=complete variant=debug,release link=static threading=multi runtime-link=static release debug stage -j4
※ビルドするのは静的リンクのみ、理由は後述
※-jnでビルド時の並列処理数を記述、この辺はビルドを行うマシンのスペックと相談
次にboost::threadをincludeした時にwarningが出ないように、以下のパッチを施す、
参考にしたのはここ。
ファイルのパスは boostへのパス\boost\thread\win32\thread_heap_alloc.hpp
行数は59行目辺り
// inline BOOST_THREAD_DECL void* allocate_raw_heap_memory(unsigned size) inline void* allocate_raw_heap_memory(unsigned size) { void* const heap_memory=detail::win32::HeapAlloc(detail::win32::GetProcessHeap(),0,size); if(!heap_memory) { boost::throw_exception(std::bad_alloc()); } return heap_memory; } // inline BOOST_THREAD_DECL void free_raw_heap_memory(void* heap_memory) inline void free_raw_heap_memory(void* heap_memory) { BOOST_VERIFY(detail::win32::HeapFree(detail::win32::GetProcessHeap(),0,heap_memory)!=0); }
ここまでで準備完了。
次にboost::threadを使ったサンプルをBoostライブラリを静的リンクでビルドして実行してみる。
ソースは、以前書いたSleep Sortのソースを使おう。
sleepsort.cpp
#include <iostream> #include <algorithm> #include <vector> #include <functional> #include <boost/thread/thread.hpp> #include <boost/thread/mutex.hpp> #include <boost/bind/bind.hpp> #define BOOST_SLEEP(n) boost::thread::sleep(boost::get_system_time() + boost::posix_time::milliseconds((n))) std::vector<int> SleepSort(std::vector<int> v) { boost::mutex m; std::vector<int> ret; std::function<void(int)> f = [&](int n) { BOOST_SLEEP(n * 100); { boost::mutex::scoped_lock lock(m); ret.push_back(n); } }; boost::thread_group group; std::for_each(v.begin(), v.end(), [&](int n) { group.create_thread(boost::bind(f, n)); }); group.join_all(); return ret; } int main() { int a[] = {3, 1, 8, 7, 2, 4, 9, 6, 0, 5}; int n = sizeof(a) / sizeof(a[0]); std::vector<int> v(a, a + n); v = SleepSort(std::move(v)); std::for_each(v.begin(), v.end(), [](int n) { std::cout << n << " "; }); return 0; }
ビルドする時は以下のコマンド
g++ sleepsort.cpp -o sleepsort.exe -std=c++0x -DBOOST_THREAD_USE_LIB -Iboostのincludeパス -Lboostのlibパス -lboost_thread-mgwXX-mt-s-X_XX
※MinGWではVisual Studioの時とは違い、-lオプションで明示的にライブラリを指定する必要がある(参考)
※静的リンクなので、 libファイル(MinGWでは.a)はmt-s-X_XXのようになっているのに注意
※静的リンクの時には、 -DBOOST_THREAD_USE_LIB オプションを付加する
これでsleepsort.exeを実行すれば実行結果が確認できる。
はまった事
Boostライブラリをビルドする際、動的リンク用も生成するように
bjam -sTOOLS=mingw --toolset=gcc --stagedir="boostのパス\stage\mingw" --without-python --without-mpi --build-type=complete variant=debug,release link=static,shared threading=multi runtime-link=static,shared release debug stage -j4
とすると、Boostライブラリの静的リンク用を使ってサンプルをビルドする際に
MinGWのld.exeがboost_thread-mgwXX-mt-s-X_XXが見つからないというエラーを出した。
なのでBoostライブラリを静的リンクで使う際には、Boostライブラリは静的リンク用だけビルドした方がいいかもしれない。