リーナス・トーバルズ氏、Linuxカーネルの開発を「C89」から「C11」に移行方針へ 76
ストーリー by nagazou
移行 部門より
移行 部門より
Linuxカーネルは「C」言語で記述されているのは知られているが、現在使われているのは主に1989年の規格である「C89」であるという。ZDNetによれば、Linus Torvalds氏が、Linuxカーネルの公式な開発言語を2011年規格の「C11」に移行しようとしているそうだ(ZDNet Japan)。
移行判断のきっかけとなったのは、あるカーネルの脆弱性問題にあったという。Torvalds氏がこれを解決するパッチを適用しようとしたとき、該当パッチの問題が判明した。この問題を修正するには「C99」の機能が必要だった。これをきっかけにC89に別れを告げ、この種の問題が起こり得ないCの新規格に移行する方針に決めた模様。
移行判断のきっかけとなったのは、あるカーネルの脆弱性問題にあったという。Torvalds氏がこれを解決するパッチを適用しようとしたとき、該当パッチの問題が判明した。この問題を修正するには「C99」の機能が必要だった。これをきっかけにC89に別れを告げ、この種の問題が起こり得ないCの新規格に移行する方針に決めた模様。
C89からC11への変更点 (スコア:5, 参考になる)
C89からC11だと間に C99があります.
C99で標準化された機能でカーネルコードに影響がありそうなものは
- 可変引数マクロ. __VA_ARGS__ 使うやつ
- designated の初期化. struct A { int hoge; int fuga}; A a = { .hoge = 1, .fuga= 2}; って書けるやつ
- 可変長配列
- サイズゼロ配列
- for (int x=0; x<10; ++x) って感じでローカル変数が宣言できるやつ
などがあります.
最後の for文内でローカル変数が宣言できる機能が,今回のC89からC11に移行するきっかけになった新機能です.
LKMLの議論だと,全部のメールを読んだわけではありませんが流し読みした感じでは
C89からC99に移行しようと言う話になって,どうせならC11にしたら?って流れになってました.
ただし上記のC99機能は以前からgccなどたいていのコンパイラでは実装済みになっていて(確か GCC 5.0あたりで実装された)
例えば,サイズゼロ配列や designated 初期子は既存のlinuxカーネルでも多様利用されています.
ですから厳密にはC89だけではlinuxカーネルはコンパイルできません.
次にC11で標準化された機能でカーネルコードで役に立ちそうなのは
- _Generic キーワード.c++ でいうtemplate関数みたいなtype genericなマクロが書ける
- stdalign.h .アラインメントを指定する修飾子が使える
です.
特に _Genericキーワードはかなり強力で,よりセキュアで実行速度が速いコードが簡単に実装できるようになります.今後の展開が楽しみです.
Re: (スコア:0)
まともに追いかけていない門外漢だけど、linuxってgcc固有機能もあちこちで使っている印象だったので
今でも(建前上は)C89縛りだったんかい!という感じ
Re:C89からC11への変更点 (スコア:1)
C99の新機能はライブラリの機能ばっかりでカーネルのコード書くときは関係ないよねというのがC89にとどまってた理由
Re: (スコア:0)
で、今回ついに-std=gnu89では使えないコア言語の機能(for文内でローカル変数を宣言できる機能)が問題になったと
Re: (スコア:0)
なんか以前移行を試みたときはgcc 4.x系のバグを踏んで断念したらしい
Re: (スコア:0)
組み込みに使えないコードとか吐き出してこないのかだけ心配
Re: (スコア:0)
どういうののこと言ってんの?
Re: (スコア:0)
ベンダが対応するだろ多分。i386見たくメインストリームからバッサリ切られるかもしれないけど。
Re: (スコア:0)
C99からのジャンルの統合ありますのでご注意を
え?コミケじゃない?
Re: (スコア:0)
GCC拡張のサイズゼロ配列は使ってるとこあるだろうけど、C99のは使ってるとこある?
同機能別文法のものが使われてるって言いたいのかもしれんが。
Re: (スコア:0)
C99からC11の変更点。
・VLAがオプションになった。
不思議。サポートしないコンパイラがあるようには思えないけど。
しかしなぜC18ではないのか。新しすぎか。
Re: (スコア:0)
gccとc99でinlineの仕様が微妙に変わってなかったっけ?
確かextern inlineとinlineの意味が入れ替わった。
参考: ガチ浦島太郎さん向け (スコア:2, 参考になる)
C++の勉強にかまけて、Cの進化には全然キャッチアップしてなかった俺みたいな奴へ
> Cといえば、「ファイルスコープでない変数宣言がブロックの先頭になければならない」。
> Cといえば、「//」は非標準。
このへんはもう、C99で緩和(標準化)されてるから、もうこれだけでぐっとラクになってるよ!
C11は、さらにその先。
Re: (スコア:0)
自分もこれですね
//コメントは常用してますが
先頭以外での宣言はデバッグ用の一時的な書き捨てコードで利用してます(本番コードでは使ってません)
Re: (スコア:0)
今後は/* */コメントは非推奨で//コメントで書く必要あり?
Re: (スコア:0)
え?C11だと /* */ コメントは非推奨になったの?
Re: (スコア:0)
コーディングスタイルの問題として、今後は積極的に新式にしましょう、それで気軽にどんどんコメント入れましょう、って現場はありそう
複数行なら、従来通り、/* */ のほうがはやいし
Re: (スコア:0)
Linux kernel の話では無いが、 Windows で Shift_JIS (CP932) で書いていると
// の1行コメントの最後にうっかりダメ文字を書いて次の行までコメントになることがある。
時代は (スコア:1)
小型機関車やね
https://ja.wikipedia.org/wiki/%E5%9B%BD%E9%89%84C11%E5%BD%A2%E8%92%B8%... [wikipedia.org]
機能必要か? (スコア:0)
ブロックを加え波括弧で囲めば済む話じゃん
インデントがウザいとか?
Re:機能必要か? (スコア:1)
Re:機能必要か? (スコア:1)
>ブロックを加え波括弧で囲めば済む話じゃん
そうすると、波括弧を閉じるのにもう一つマクロが必要で
構文を変えたくなかったのでC99でってことですかね
(And by "couldn't", I mean "without making for special syntax": we do
exactly that in "for_each_thread ()" and friends, but they have an
"end_for_each_thread()" thing at the end).
一応、list_for_each_entry()関係は以下が分かりやすいかな?
https://qiita.com/n01e0/items/95922a475bac458f0b47 [qiita.com]
Re: (スコア:0)
必要かといえば、代替の書き方はあるので、必要ない。
今後も類似の不具合を持ち込まないためには、全てのfor文で同じことやるべきってことだから、その手間が将来常に発生しつづけるコストと、今c99に移行するコスト考えて、移行しちゃったほうがええんちゃうかという話では?
c99にするのは差分がまだ少ないからということなんだろうけど、テストとかの移行コストかけるのなら、c99と言わずc11/c17とかにしといたほうが先々は良いと思うけど。
Re: (スコア:0)
でもやっぱりウザいよね
バグ避けにfor文は毎度ブロックで囲みましょうなんてコーディングスタイル
Re: (スコア:0)
そういうこと(for(){})じゃなくて{for()}なんて書き方を毎回やるのか?って話なんだけど
Re: (スコア:0)
Goっていう言語だと、if, for, switchで暗黙ブロック [zenn.dev]だそうで
まだC89だったのか (スコア:0)
といいつつ自分も把握してるのはC89の範囲…
Re: (スコア:0)
次回はC100だったと思います!
Y2K (スコア:0)
C89 → C99 → C11 って、信じられないネーミング。
Re:Y2K (スコア:1)
まぁ通称とか俗称であって、正規の名称じゃないから。
Re: (スコア:0)
Windows1.0→2.0→3.0→3.1→95→98→2000→ME→XP→Vista→7→8→8.1→10(最終バージョン)→11
あとは番号と世代が入り乱れてるRyzenとか、一回リセットしたり過去の世代に差し込んだりするGeforceとか、採番って難しいね
Re: (スコア:0)
Windows1.0→2.0→3.0→3.1→95→98→2000→ME→XP→Vista→7→8→8.1→10(最終バージョン)→11
NT「わしもまぜろ」
CE、Mobile、Phone、RT、Start「ぼくたちも」
# IoTもToT状態だしなぁ
Re: (スコア:0)
10.2→…→13.2→Leap 42.1→…Leap 42.3→Leap 15.0→Leap 15.1→Leap 15.2→
という謎バージョニングのopenSUSE…
エンタープライズ版のSLESと同期させるときにSLESのバージョン番号(12.1)そのままだとに13.2からバージョンが戻ったように見えるのでLeapで+30する→やっぱりやめるということのせいですが…
Re: (スコア:0)
2000は98の改良じゃないんだし、その後継がMEというのもおかしい。
Windowsは一子相伝ではない。
Re: (スコア:0)
NT2000だったら良かったんだ!
Re: (スコア:0)
CA1 よりはマシ…かな?
Re: (スコア:0)
インテルのプロセスルール
Intel 7 → Intel 4 → Intel 3 → Intel 20A
https://ascii.jp/elem/000/003/236/3236851/img.html [ascii.jp]
Re: (スコア:0)
20Aは20オングストロームのことじゃないの?
Re: (スコア:0)
マイクロメートル(0.35・0.25・0.18)からナノメートル(90~)も巻き戻りに見えるかも。
Re: (スコア:0)
アメリカの軍用機みたいなもんだよ。日本を焼け野原にしたB-29より強いB-2とか。
オーバーフローしたらリセットする。長ったらしい表記になるよりはマシ。
Re:Y2K (スコア:1)
米軍の場合、B-XXがオーバーフロー下からB-1にしたわけでも無いけどな。命名規則変更に伴いリセットされた。
一方日本は、オーバーフローでリセットした。ゼロ戦(零式)の前は九六式だし、隼(一式)の前は九七式。
Re: (スコア:0)
年号に対してオーバーフローという言い方もなんだかなあと思う
Re:Y2K (スコア:1)
自分のコメントのタイトルを見直したことある?
それと、年号 [wikipedia.org]じゃなくて皇紀な。
ゼロ戦は、皇紀2600年に制式採用。昭和100年と勘違いした?
Re:Y2K (スコア:1)
陸軍の飛行機の名前はそれこそWindosXPとかVistaみたいな宣伝名
「隼」とか「疾風」とかはそうだけど、「一式戦闘機」とか「四式戦闘機」とかは制式名称だよ。
本来の名前はキ-XXで一貫してる。
キ番号は、統一された命名規則で一貫しているのはその通り。
ただ、キ番号はあくまでも試作名称。制式名称決定後も広く使われたけど、キ番号を「本来の名前」と説明するのは違う気がするよ。
Re:Y2K (スコア:1)
そりゃWindowsだってXPが正式な商品名だよ?
解ってないなあ。
私が言っているのは、「隼」とか「疾風」とかは愛称であって、「宣伝名 [srad.jp]」みたいなものだ、と言っている。
「WindosXPとかVistaみたいな宣伝名 [srad.jp]」と書いたのは、私でなく、#4211672のAC。
君は、試作名称・制式名称・愛称の区別が付いてないようだね。
Wikipediaの記事 [wikipedia.org]を百回写経して出直し給え。
これで分からないからお前はRyo.Fだって言われんだよ。
残念。解ってないのはキミの方だったね。
加えて、私はIDで発言してるわけで、Ryo.Fと呼ばれても構わないんだよ。
匿名の臆病者でないと怖くてRyo.Fに反論することもできないキミと違うんだよ。
自分が臆病者からと言って、相手もそうだと妄想するのは間違っているよ。
# 次はどんなマヌケなコメントを書いてくれるんだろ。ワクワク(笑)。
Re: (スコア:0)
100の補数になってるところが面白い
Re: (スコア:0)
C++もC++97→C++03だったな。
むしろFortran 2003やCOBOL 2002のほうがY2K対応してるってなんの冗談だよ
Re: (スコア:0)
マジレスすると、運用で回避する自信があるからでしょ。もし、2089年に新しい規格ができたら、2088年に完成したことにしておいてC88にするってこと。
浮動小数点 (スコア:0)
OSには無関係だろうが、浮動小数点演算関係も新しい規格のほうが良くなっててありがたい
Re: (スコア:0)
整数の範囲に限定しても、負数の除算の動作が規格で統一された。おかげでdiv関数の存在意義がいまいち謎になってしまったが