HOME  >  2014/02

Hit a Hint for Windows 0.5.19.6 公開

要素が入れ子状態になった場合、ごちゃっと見えるので入れ子にならないように変更してみました。
ダウンロードはこちらから

スクリーンショット
修正前
hw_ireko01.jpg
修正後
hw_ireko02.jpg

Version.0.5.19.6

  • ヒント表示が入れ子状態になった場合、中のヒントのみ表示するよう変更。
スポンサーサイト



2014/02/24 | カテゴリ:ソフトウェア開発 | トラックバック(0) | コメント(0)

Windows 7 に Ruby 2.0 x64 を その5 ~EventMachine の問題と対策~

2014/5/13 追記 公式に修正が取り込まれました。gem も公開されていました。
なのでこの記事はもはや *無意味* です。

Windows 7, Ruby2.0 で guard-livereload を使おうと思い、インストールしようとしたら
EventMachine が必要といわれ、入れようとしたらビルドエラー発生。

ということで、EventMachine を修正してみました。
GitHub 上にソースをおいたので、以下のコマンドでインストールできます。
# プルリクエストしたので、そのうち取り込まれる……といいな。
2014/5/13 追記 マージされました。
gem specific_install -l 'git://github.com/u338steven/eventmachine.git'
specific_install をインストールしていない方は、以下のコマンドで用意してください。
gem install specific_install
# ビルドエラーを修正しただけだと、guard-livereload が変な挙動をしたので、
# 他にも、ちょこっと直しています。

修正した内容

以下 4 つのエラーに対処。
  1. undefined method `each' for "i386-mingw32":String
  2. error: conflicting declaration 'typedef _pid_t pid_t'
  3. rubyeventmachine.so (LoadError)
  4. guard-livereload の妙な動き(EventMachine が原因)
以下、修正内容をざっくりと記載します。
修正したソースの詳細を見たい方は、 GitHub 上のソース差分 をどうぞ。

1. undefined method `each' for "i386-mingw32":String

ある変数に配列が入ったり、配列以外が入ったりしていたのが原因でした。
なので、事前に配列かどうかチェックします。
    if ext.cross_platform.is_a?(Array) then
      ext.cross_platform.each do |platform|
        (略)
    end

2. error: conflicting declaration 'typedef _pid_t pid_t'

これは、ccoenen さんのパッチをそのまま流用してます。
pid_t が重複して定義されちゃってるので、#ifndef を使って定義済かチェックしてます。
c:\ruby\devkit\mingw\bin\../lib/gcc/x86_64-w64-mingw32/4.7.2/../../../../x86_64-w64-mingw32/include/sys/types.h:68:16: error: conflicting declaration 'typedef _pid_t pid_t'
In file included from ../../../../ext/binder.cpp:20:0:
../../../../ext/project.h:97:13: error: 'pid_t' has a previous declaration as 'typedef int pid_t'
In file included from ../../../../ext/project.h:151:0,
                 from ../../../../ext/binder.cpp:20:
#ifndef _PID_T_
#define	_PID_T_
typedef int pid_t;
#endif
ここまでで、ビルドエラーの修正は終了です。

3. rubyeventmachine.so (LoadError)

次は、実行時のエラー。
やっとビルドできたと思ったらrequire 'eventmachine'するだけでエラーが発生します。
Unable to load the EventMachine C extension; To use the pure-ruby reactor, require 'em/pure_ruby'
C:/ruby/lib/ruby/site_ruby/2.0.0/rubygems/core_ext/kernel_require.rb:55:in `require': 126: 指定されたモジュールが見つかりません。   - C:/ruby/lib/ruby/gems/2.0.0/extensions/x64-mingw32/2.0.0/eventmachine-1.0.3/rubyeventmachine.so (LoadError)
        from C:/ruby/lib/ruby/site_ruby/2.0.0/rubygems/core_ext/kernel_require.rb:55:in `require'
        from C:/ruby/lib/ruby/gems/2.0.0/gems/eventmachine-1.0.3/lib/eventmachine.rb:8:in `'
        from C:/ruby/lib/ruby/site_ruby/2.0.0/rubygems/core_ext/kernel_require.rb:135:in `require'
        from C:/ruby/lib/ruby/site_ruby/2.0.0/rubygems/core_ext/kernel_require.rb:135:in `rescue in require'
        from C:/ruby/lib/ruby/site_ruby/2.0.0/rubygems/core_ext/kernel_require.rb:144:in `require'
        from require.rb:1:in `
'
rubyeventmachine.so は存在してるのですが、依存関係にある libgcc_s_sjlj-1.dll と libstdc++.dll が
実行時に見つからなくてエラーになっています。

というわけで libgcc_s_sjlj-1.dll と libstdc++.dll を読まないようにするため、
ビルド時のオプションに、-static-libgcc, -static-libstdc++を追加します。
    CONFIG['LDSHAREDXX'] = "$(CXX) -shared -static-libgcc -static-libstdc++"
ここまでで、EventMachine が一応使えるようになります。

4. guard-livereload の妙な動き(EventMachine が原因)

やっと EventMachine が動いて guard-livereload を使えると思ったら、 guard-livereload 起動後、最初の数回だけまともに動いて、以降リロードされないという謎現象が発生。

ソースみまくったところ、EventMachine のソケットの後処理に問題がありました。
Windows のソケットは close じゃなく、closesocketで閉じます。
#define close closesocket
これには、なかなか気づかなくて、ものすごくハマりました。
最初の数回だけは動いていたので、GC が悪さしてるのか?とか迷走したり。
# 実際GC.disableすると、何故か普通に動いちゃったし。
# なんで普通に動いちゃったのか、いまだにわからない……。

ここまできて、やっとまともに guard-livereload が動きました……。
2014/02/22 | カテゴリ:Ruby | トラックバック(1) | コメント(0)

Hit a Hint for Windows 0.5.18.5 公開

タスク切り替えモード時に、実行ファイルのアイコンを表示するようにしてみました。
オプションで表示/非表示を切り替えできます。
ダウンロードはこちらから
スクリーンショット hw_desktop.jpg

Version.0.5.18.5

  • タスク切り替えモード時に、実行ファイルのアイコンを表示するオプションを追加。
    (デフォルトは表示)
2014/02/10 | カテゴリ:ソフトウェア開発 | トラックバック(0) | コメント(0)

実行中の Ruby コマンドのパスを取得する方法

とてもレアなケースだと思われますが、
個人的に必要になったのでメモとして残しておきます。
puts RbConfig.ruby    #=>"C:/ruby/bin/ruby.exe"
Ruby スクリプト内から、別プロセスで既存の Ruby スクリプトを実行したかったので、
こんなことしてます。(IO.popen との組み合わせで)
他のやり方もあるのかなぁ。

# どうせパスが通ってるんだろうから、
# 単純に "ruby" で呼び出してもいいんじゃないかというツッコミもあると思います。
# ですが、僕の環境だと、Ruby2.0 系、Ruby1.9 系、JRuby が共存してるので、
# 例えば、JRuby でも動くよね?っていう確認をしたくて、JRuby で実行したのに、
# 別プロセスとして呼び出されたのが Ruby2.0 系……とか、
# そんな悲劇が起こってしまうのです……。
2014/02/04 | カテゴリ:Ruby | トラックバック(0) | コメント(0)
外部リンク

カンパのお願い
公開しているソフトウェアはフリーウェアなので無料でご利用いただけます。 気に入ってくださった方は、Amazon でお買い物をする際に下記のリンクを経由して頂ければ励みになります。

検索BOX・タグ一覧