相対パスをフルパスに
先日、親ディレクトリにMakefileを探しにいってmakeするmake.shを書いて、それを使っていると思わぬ問題に遭遇した。使い始めて5分で。
next-errorでエラーに飛べない
/foo/Makefileを作っておいて、シンタクスエラーを含む/foo/bar/baz.mlをカレントバッファに読み込んだ状態でcompileする。すると/foo/までディレクトリをさかのぼってmakeするもんだから、コンパイラのエラーメッセージではbaz.mlはbar/baz.mlとなる。しかし、baz.mlを編集しているemacsバッファのカレントディレクトリは/foo/barなもんでbar/baz.mlを/foo/bar/bar/baz.mlとしてしまい「そんなファイルはみつからないよーと」なってしまい、全然便利じゃなかったのだ。
elispでなんとかしたいところだが、ちょっと調べてめんどくさくなったので「コンパイラの出力のうちコンパイルエラーっぽいやつを検出してファイル名をフルパスにするスクリプト」を書いた。
#!/usr/bin/env ruby def expand_path(p) fp = File.expand_path(p) if RUBY_PLATFORM == "i386-cygwin" `cygpath -w #{fp}`.chomp() else fp end end if ARGV.size == 0 exit 0 end IO.popen("#{ARGV.join(" ")} 2>&1") {|io| while (l = io.gets()) if l =~ /File \"([^\"]+)\", line (\d+), characters (\d+)\-(\d+)\:/ f = expand_path($1) l = $2 c1 = $3 c2 = $4 print "File \"#{f}\", line #{l}, characters #{c1}-#{c2}:\n" else print l end end } exit $?.exitstatus
こんなん。CYGWINの処理が気持ち悪いけど、どうせMeadowかLinuxのemacsからしか使わないからこれでいいや。
$ full_path.rb ocamlc foo.ml
みたいに使います。
あー便利だ。これでデバッグが当社比3倍くらいの速さで進むに違いない(棒読み)。