読者です 読者をやめる 読者になる 読者になる

chikuchikugonzalezの雑記帳

趣味とか日記とかメモとか(∩゚д゚)

Ruby 2.0.0 (RubyInstaller) + DevKit (mingw32 4.7.2) でハマったこと

開発 C/C++ Ruby

自前のC拡張 (C++使ってる) をビルドして動くかなー( ^ω^)ワクワク とかやってたんですが見事にはまったので誰かタスケテ

なにがあったのか

とりあえず環境はこんなの

Ruby 2.0.0 (patchlevel 353) RubyInstallerで入れた
DevKit (mingw32 4.7.2) RubyInstallerのところにあるやつ

で、前に作ったcosplayで全部パスを通してる *1

この状態でC拡張部分をビルドしてたんですが、ちょっと問題が出まして。何が問題って、パス設定してないコマンドプロンプトでrequireしたらLoadError: 126: 指定されたモジュールが見つかりませんとかほざくわけですよ(#゚Д゚)

再現方法とか

とりあえずほかのはどうかなー、ってことでeventmachineで試しました。試し方は

C:\>gem install --platform=ruby eventmachine

です *2

…うん、こいつもLoadErrorだったよ('A`)

原因

幸いVisual Studio 2013を入れてあるのでdumpbinが使えました。で、dumpbin /DEPENDENTSで依存関係見たら

   KERNEL32.dll
   msvcrt.dll
   libgcc_s_sjlj-1.dll
   libstdc++-6.dll
   msvcrt-ruby200.dll

っていう感じで、sjljとstdc++がdynamic linkでした('A`)

eventmachineのビルド済み版はコイツラなかったからたぶんこれだろっていう予想 (直せてないので確定ではない)

なので

libgcc_s_sjlj-1.dllとlibstdc++-6.dllをstatic linkにしてDLLを読み込まないようにしたいんですが誰かタスケテください。

暫定対処について

DevKit 4.5 (Ruby 1.9用) でビルドしたら問題なかったのでそっち使おうと思います

でもさ

普通にRubyInstaller + DevKitの環境作ったら基本DevKitはPATHに入らないわけで、ビルド済みバイナリを置いてないC++で作られたgemを入れたら発生するよねー。誰もコレ踏んでないのかな。それともWindowsだからかチクショウ

*1:なお、cosplay稼働中にCtrl+Cでなにかを終わらすとバグることが判明しました

*2:デフォルトだとコンパイル済みmingw32版が入るので、手元でビルドしろよ(゚Д゚)である