2013-11-29

Clangで-std=c++1yがいまだに使いにくい事情

ClangがC++14の機能完全に到達したことはすでに述べた。これはつまり、最新版のClangで、-std=c++1yを指定すると、現在のC++のドラフト規格の、動く実装が手に入るということだ。

これは素晴らしいことだ。

しかし、いざ実際にUbuntu 13.10でClangのSVN HEADを自前ビルドして使ってみようとすると、以下のようなエラーが表示される。

/usr/include/c++/v1/cstdio:156:9: error: no member named 'gets' in the global namespace

ヘッダーファイルを一切includeしなくても、このエラーは表示されてしまう。

この事情は・・・結構複雑なのだ。

C++14では、Cの標準ライブラリは、C11のものに合わせられた。C11の標準ライブラリでは、とうとうあの忌まわしき太古の呪いである、getsを廃止した。廃止である。非推奨ではない。C11では、もはやgetsは存在しないのだ。

したがって、C11やC++14モードでコンパイルするには、このgetsを#ifdefで囲むなどして、取り除く対応をしなければならない。

しかし、現行の多くのGNU/Linuxの安定版ディストロが使っているglibcのバージョンは、まだこの変更に対応していない。

それもそのはずで、C11のgets廃止に対応したglibcを使うには、GCC 4.9が必要なのだ。GCC 4.9は、まだ開発途中で安定リリースされていない。そんなGCCをデフォルトで出荷するGNU/Linuxディストロなどあるはずがない。

GNU/Linuxにおいては、libcのような基本的なライブラリと、C++コンパイラーは密接に関係していて、単にコンパイラーだけを自前ビルドして使うわけにはいかないのだ。

したがって、もし自前ビルドするとなると、ClangとGCC一式を完全に自前ビルドした上で、ライブラリへのパスを自前ビルドのglibcに通すなどしなければならない。おっと、C++標準ライブラリも、libc++を使いたいし、ABIライブラリも悩ましい。これらのコンパイラーとライブラリを正しく配置して正しくパスを通すのは、とても面倒なのだ。

やればできるだろうが、こんな面倒なことはやりたくない。私はおとなしく、GCC 4.9が安定リリースされて、GNU/Linuxディストロで、ソフトウェアがプロの手によってパッケージ化されるのを待つことにする。

とはいっても、とりあえずC++14の新機能を試してみたいものだ。実は、そんなあなたにうってつけのSaaSSがある。

[Wandbox]三へ( へ՞ਊ ՞)へ ハッハッ

melponさん、ありがとよ。

なんと、Vim用のプラグインまである。

rhysd/wandbox-vim

Linda_ppさん、ありがとよ。

参考:

Bug 13566 – Glibc should define gets for C++11

Bug 51785 – gets not anymore declared

No comments: