26 Apr 2015

MSYS2上のMinGW-w64 GCCでcolored diagnosticsを使う

MSYS2上のMinGW-w64 GCCでcolored diagnostics (-fdiagnostics-color)を使いたかったのでメモ

ネイティブWindows環境ではGCCのcolored diagnosticsが無効化されている.
これはWindowsのネイティブシェル環境(つまりコマンドプロンプト)がANSI color codeに対応していないからだと思われる.
ただし,*nix環境のみでしか動かないようなコードにはなっていない.要はANSI color codeに対応している環境であれば,GCCのビルド時にこの機能を有効化すれば普通に使えるのだ.
基本的にMSYS2のbash上でしか使わないので#ifdef guardを削除して使えるようにしてしまおうと考えたが割りと面倒なことがあった.

何が面倒かというとMSYSやCygwinを使う人なら周知の"mintty上でのisatty問題"のせいでstderrが端末かどうかの判定が出来ず-fdiagnostics-color=autoが動かないということ."mintty上でのisatty問題"が何かわからない人は"mintty isatty"とかでググればいいと思う.
もちろん-fdiagnostics-color=alwaysだと動くがログ用にstderrをファイルにリダイレクトしている時とかに非常に困る.ANSI color codeがそのまま出力される.
常にcatなどでログを表示するという手もあるがそれは何か違う気がする(catはANSI color codeを認識し色付きで表示してくれる).
どうしたものかと考えていたところでちょうどgit for windowsの方で"mintty上でのisatty問題"に対するwork aroundがされたので[1, 2]そのままそっくりパクってGCCに入れて使わせてもらうことにした.
ちなみに今回の件とは関係ないがgit for windowsはMSYSベースからMSYS2ベースへと移行し,git v2.xをリリースする予定である.これに関しては色々思うところはあるし,インターネット上の日本語ベースの情報には間違った内容が非常に多いのだがここでは述べない…

これがGCCへのpatch
これで-fdiagnostics-color=autoが使える.

実行結果がこちら
※GCCを--with-diagnostics-color=auto-if-envでビルドし, GCC_COLORSを設定しているためデフォルトで-fdiagnostics-color=autoとなっている

MSYS2のbash & mintty上で使用した例
ちなみにminttyではないwinネイティブなANSI color codeが扱える端末エミュレータであるConEmuなどでも問題なく動く.
MSYS2のbash & winネイティブなConEmu上で使用した例
更に言うとコマンドプロンプト上でもansicon等を使いANSI color codeが使えるとOK.
MSYS2のbash & (windows cmd + ansicon)で使用した例
ちなみに上記のpatchはGCCのgit gcc-5-branchのgit SHAがf6a5ddfであるソースに対して適用したものです.
あとMSYS2ターゲットなgccだとこんなことせずとも,もともとcolored diagnosticsが有効になっているしMSVCRTのisattyではなくmsys-2.0.dllのisattyを使うのでmintty上でも問題なく-fdiagnostics-color=autoを使える.
今回の件はあくまでもMinGW-w64なwinネイティブなGCCをmintty上で動かす時の話である.


[1] https://github.com/git-for-windows/git/pull/28
[2] https://github.com/git-for-windows/git/pull/102

No comments:

Post a Comment