最近は忙しさのせいか趣味よりのプログラミング的なことはあんまりできてないけど、仕事/趣味のプログラミング環境をできるだけノマド化するためにemacsの設定なんかを頑張ってみている。
その中で掲題の件、emacs のauto-complete-clangの導入を試みたけれどなかなか手間がかかったのでメモ
なかなかgeekっぽくていい感じ。
基本的には こちら とか こちら とか先人が公開してくれてる通りにやれば出来るんだけれど、 以下の点で躓いた。
- yasnippetは0.6系じゃないと動かない
- clang -cc1のインクルードパスが…ない!
auto-completeと協調して動かすためにはgoogle codeに残っている方の最新(0.6系)を使う必要があった。
2の方が結構厄介だった。
llvm/clangに関してmacを使っていればアップル謹製のclangがあるので特に問題はなくauto-complete-clangが動いた。
しかし、業務用のlinuxサーバ環境で独自にビルドしたclangだと-cc1オプションをつけた場合デフォルトのインクルードパスをちゃんと見てくれないという症状が出た。(-cc1をつけないとOK。不思議。。。)
この問題も同じ症状の先人が既にいてしかしまだ未解決の模様。
http://b0r0nji.blogspot.jp/2012/05/clangcc1.html
clang -cc1でインクルードパスを見てくれないとプリコンパイルヘッダの生成もできないしそもそも動かない…
どうしても諦めきれなかったので色々試行錯誤してみた。
まず環境変数でインクルードパスを与えられないかと思ってトライ。clangがインクルードパスとしてみている環境変数はINCLUDEではなくCPATHらしい、こちらに必要なパスを埋め込んでみた。結果としてはclang のみだとCPATH見てくれるけど、やはりcc1をつけると見てくれない。。
ここで心はもう折れかけたけどなんか-Iのオプションは有効みたい。
オプションで与えられるならなんか設定のところで
(setq ac-clang-flags '("-w" "-ferror-limit" "1"))とかでclangのオプション与えてたような…
というわけで ここ の最後の方の記述も参考にして以下の記述をemacsの設定ファイルに書いてみたところ、なんとか動くようになった。
(setq ac-clang-flags (append (mapcar (lambda (item)(concat "-I" item)) (split-string " /path/to/include/c++/4.7.1 /path/to/include/c++/4.7.1/x86_64-unknown-linux-gnu /path/to/include/c++/4.7.1/backward /usr/local/include /path/to/lib/clang/3.2/include /usr/include " )) ac-clang-flags ))
上のインクルードパスは"clang -v -x c++ /dev/null -fsyntax-only"とかやって出てくる奴をコピペしたもの。それをsplitしてリストにして"-I"つけてオプションのリストの変数であるac-clang-flagsにくっつけてやる感じ(lisperではないので適当)。
ちなみにこの記述の前にac-clang-flagsが定義されている必要があるかも... ない場合は (append と ac-clang-flags)をのぞけば大丈夫のはず(未確認)。
ちなみにヘッダのプリコンパイルも同様に-I/path/to/include/c++/4.7.1 ...とかを片っ端からつけてやれば出来た。
これでめくるめくauto-complete-clangの世界を堪能できます。
参考
http://d.hatena.ne.jp/kenbell1988/20120428/1335609313
http://www.nomtats.com/2010/11/auto-completeelemacs.html
http://b0r0nji.blogspot.jp/2012/05/clangcc1.html