バグチェックしてくれるCのクローン:Cyclone 49
ストーリー by Oliver
いっそのこと関数型 部門より
いっそのこと関数型 部門より
k3c 曰く、 "NewScientist.comの記事で取り上げられていたのですが、カーネル大学とAT&T研究所が共同で進めているCycloneというC言語クローン(そのまんまやんけ!)のプロジェクトがあるのですね。なんでも、C言語(に非常に近い、らしい)ソースをコンパイルするときにバッファオーバーフローなどの典型的なバグを作りこんでいないかチェックしてソースに修正をかけてくれるようです。今のところLinuxとCygwinに対応しているとのこと。目標はLinuxのような大きなOS全体をCycloneでbuiltできるようにすること、だそうです。大きく出ましたね…。
ワタシは不勉強にしてC言語には詳しくないのですが、ありがちなバグを作りこまずに済むのなら、このようなアプローチはかなり有効だと思われます。(チェック機能自体をどこまで信じるか、という哲学的問題は残りますが…。)他の言語でもこういうのがどんどん出てくるといいですね。"
っていうか、GCCですら (スコア:2)
gcc -c src.c -Wallとか使ってないで「コンパイルが通った」とぬか喜びしている人がかなり居そうではと思いました。こういうときはこっそり、aliasか、gccのダミーShellScriptに「-Wall」を入れてしまうのがいいかもしれませんね。
# それよかヘッダファイルを「ライブラリ」にせんといてくれと思うけど。
gcc -Wall が通っても (スコア:1)
Re:gcc -Wall が通っても (スコア:3, 参考になる)
lintはすごい。っていうか、「そこまで言うか!?」というとこまで出てくる。どうせ仕様がコロコロ変わるからそんなにstatic関数にする必要もないってだけなんだけどね。
SunのWorkShopなやつは、gccで通ったと思ったコードをかますと、落ちちゃうときがあってgccって結構アレなんだなと感じました。
具体例とすると、fpos_tをポインタだけ宣言しておいて、fgetposとか、fsetposとかすると、gccなら平気な顔されて、SunCCだと見事に撃沈するとか。単に使い方間違ってる(はじめからインスタンスがいる)だけなんですがね。とりあえず期待の星かも。<さいくろん
Re:gcc -Wall が通っても (オフトピ) (スコア:2, おもしろおかしい)
臭いくろん って読んじゃった.
masashi
Re:gcc -Wall が通っても (オフトピ) (スコア:0)
>臭いくろん って読んじゃった.
ξclone じゃないんだから ...
ソースを他人に渡すとき (スコア:1)
あと、手持ちの他のコンパイラでコンパイルしてみたりとか。
Re:ソースを他人に渡すとき (スコア:2)
-Wall
-Wchar-subscripts
-Wmissing-declarations
-Wmissing-prototypes
-Wnested-externs
-Wpointer-arith
-Wcast-align
-Wsign-compare
-Werror
-Wsign-promo
-Wno-sign-compare
が使われていたりします。
バグチェックはうれしいけど・・・・・ (スコア:2, 興味深い)
おかしくないようなコーディングを意図的に行なう場合も
ありましたよね・・・・・
# void *a,b[10] ; a = b[0]; a--;
このような場合はどうやって回避していくのでしょうか・・・・?
『今日の屈辱に耐え明日の為に生きるのが男だ』
宇宙戦艦 ヤマト 艦長 沖田十三氏談
2006/06/23 JPN 1 - 4 BRA
Re:バグチェックはうれしいけど・・・・・ (スコア:1)
でも、警告が出ますよね。代入を真偽値として使う場合にはカッコでかこったほうがいいよ、って。たしかに、
とすると、警告は出なくなります。が、無意味なカッコが増えるので、かえって見づらくなるような気がします。
PS. すみません、znc さんのコードの意味が分からないです。
Re:バグチェックはうれしいけど・・・・・ (スコア:0)
if (fp != NULL) {
...
と書けばいいのでは。
「変な記述」のほとんどは、何の代償も無く「変じゃない記述」に変えられると思うんだがなぁ。
Re:バグチェックはうれしいけど・・・・・ (スコア:1)
って、俺には凄くエレガントだと思えるんですが、
なんで世間では冷遇されてるんでしたっけ?(^^;;;
Re:バグチェックはうれしいけど・・・・・ (スコア:1)
Re:バグチェックはうれしいけど・・・・・ (スコア:0)
Re:バグチェックはうれしいけど・・・・・ (スコア:2)
こういう書き方を糾弾していたのは
「Writing Solid Code」だったっけ?
from もなか
たぶん Cyclone ではこう書くのでは? (スコア:1)
まず、 Cyclone では通常のポインタは a-- のようなポインタ演算が 禁止されています。 ポインタ演算を使用したい時には fat pointer と呼ばれる Cyclone 特有の特殊ポインタを使う必要 があります。
fat pointer を使うと NULL チェックや配列の境界チェックが 入ります。
言語仕様を見ただけで書いているので 間違っているかもしれませんが、 上の C プログラムは 下のようにプログラムすると思われます。
発生した例外は try-catch するようです。
コンタミは発見の母
昔は定理証明とか・・・ (スコア:2, 参考になる)
結局実用的でないという事でみな衰退していった様な感じですが、Javaのassert節にその残滓を感じる事もあります。
なんか最近のコンピュータサイエンスというのはなーんかこういう「純」なアプローチが減って、工学的(実用的)な事ばっかりしているような気がするのは私だけ?
-----------------
#そんなワタシはOS/2ユーザー:-)
Re:昔は定理証明とか・・・ (スコア:1)
|AGなんか好きだったなぁ。これの流れを汲ん
|だRieとか今どうなっているんだろう・・・)
RieはAGの流れを汲んでないですね。
まつもと ゆきひろ /;|)
gcc なら既に (スコア:2, 参考になる)
IBM が研究している gcc 用の buffer overflow 対策パッチ [ibm.com]なんてものがあったりします。
既に GCC 3.0 用の patch も出ていたりしますし、C 言語ならこれを使っておくと、少しだけなら buffer overflow 対策ができるかと。
専用の -fstack-protector オプションを指定しなければ通常の gcc のまま動くので、差し換えてもそうそう問題が出るものではないかと思われます。
# 自動的に buffer overflow のチェックを行うコードが挿入されるため on にするとその分速度低下が発生しますが。
Region-based C (スコア:2, 興味深い)
C@ というのは、 David Gay(Univ of California, Berkeley) という人が C に region というメモリ管理システムを 足したものです。 って、よく見ると cyclone のページは カルフォルニア大学じゃん。
Cyclone は、 誤解をおそれずに言えばガベージコレクションが 入った C です。
malloc することは出きるけど、free は禁止。 ガーベージになったら GC を起こして回収します。 ってやつです。
あと Dynamic region という メモリ管理システムが 入っています。
これも誤解を恐れずにいうと、 ヒープからオブジェクトを 直接取ると 色々面倒です。 そこで、 ヒープから まずリージョンを取ってきて、 その中からオブジェクトを 小出しに取ってきます。 オブジェクトを解放する時には リージョンごと全部 解放してしまおうというアイデアです。
リージョンの取り方、解放の仕方は プログラマが決めるので、 メモリ管理が 賢くなりますし、 GCを使って回収するより高速です。
でも、 反射的に「この言語でまともなマルチスレッドプログラムは 書けるの?」という疑問が浮かぶのですが、、、
コンタミは発見の母
Re:Region-based C (スコア:1)
コンタミは発見の母
Re:Region-based C (スコア:1)
もし C++ に拡張できるのなら,理想のシステム開発言語だなあ。 …と思ってドキュメント見たら,「7 Polymorphism」という節がある。おおっ,と期待して見たら中身は1行で 「Use `a instead of void *.」--がっかり。
Polymorphism (スコア:1)
Cyclone の Polymorphism は, O'Caml [ocaml.org] などの
ML(Meta Language) で使われている方の意味ですね.
ドキュメントにもありますが [cornell.edu], ML の Polymorphism は
感覚的には C++ のテンプレートに近いです.
引数の型を特定せずに関数を定義することができます.
C に ML の機能がのったら超便利だなぁっておもってたところ
なので, かなり興味深々になってます.
Re:Polymorphism (スコア:1)
マニュアルを読んでみると subtype [cornell.edu] という C++ のクラス
みたいなのを定義できるみたいですね.
Re:Polymorphism (スコア:1)
関数ポインタは非常に C++ っぽいですね。そこまでしても,C++ の class にはしないのか。この人たち、C++ が嫌いなのかもしれない(笑)。
後者は部分範囲型でしょうかね(Pascalとかの)。
Re:Polymorphism (スコア:0)
「興味津々」ね。
TLS を使ったスレッドローカルヒープオブジェクト (スコア:1)
御意
必要なメモリをスレッド開始時にがっと取れるようなアルゴリズムだといいけど、実行中にちょびちょびメモリを確保しなければいけないアルゴリズムでは malloc / new は駄目ですね。
断片化が進むとコヒーレンス性のキャッシュミスが多発するので、性能が甚だしく低下します。
このような場合、マルチスレッドで書くよりマルチプロセスでプログラムを書いて必要なところだけ共有メモリで共有した方が速くなることも多いです。
完全な与太話ですが、
C++ を使う時に自前でメモリ管理をする根性があれば、Thread Local Strage(TLS) と組み合わせた面白いメモリ管理テクニックがあります。
概略だけ示すと、、、
プログラムの先頭で
DWORD dwThreadLocalHeap = TlsAlloc();
とやっておいてから、各スレッドの頭でスレッド専用のメモリをぶん取って TLS に登録します。
char* thread_local_heap = new char[いっぱい];
TlsSetValue( dwThreadLocalHeap, thread_local_heap );
でもって、以下のようなクラスを用意します。
class CThreadLocalObj {
public:
void* operator new(size_t size);
void operator delete(void* p);
void* new_array(size_t size);
};
void* CThreadLocalObj::operator new(size_t size) {
char* thread_local_heap = TlsGetValue( dwThreadLocalHeap );
// thread_local_heap は最初に取ったスレッド専用なメモリなのでここを切り分ける。
};
ユーザーは CThreadLocalObj を派生して、
class CMyObj : public CThreadLocalObj {
// ...
};
CMyObj obj = new CMyObj(); // スレッドローカルな領域に確保される。
という寸法です。
コンタミは発見の母
昔あったよ (スコア:2)
大昔、某社の某コンパイラは、エラーのチェックどころか、エラーの修正までしてくれた。が、エラーがエラーを呼ぶ場合など、ソースコードをぐちゃぐちゃにしてくれた挙げ句、「もうコンパイルできませーん!」と言って音を上げて止まったりする、という「優れもの」でしたねー。
プログラムがうまく動かないのは、コンパイラが悪いせいだ!なんていうのを「最初に」のたまうヘボプログラマみたいなそのコンパイラの挙動は、やはりそういうモノを作った人と似てる。
今回もそういうモノでないことを祈る。
Cの「クローン」である必要性は? (スコア:1)
単にチェックの厳しいCコンパイラを作るのと、何が違うの? 別言語を新たに作る必要性はあるのか?
Re:Cの「クローン」である必要性は? (スコア:1)
-- LightSpeed-J
Re:Cの「クローン」である必要性は? (スコア:0)
が、Cyclone は多相型、型推論、タグ付 union、パターンマッチ(データ構造の)
なども使えるようになっているみたい。
MLの便利なところが入っている感じで面白いかも。
Re:Cの「クローン」である必要性は? (スコア:1)
これに lambda 式 (無名関数) が使えたら,まんま ML ですね.
しかし, なんで Cyclone の ML 的な機能の話で議論が
盛り上がらんのか...
O'Caml [ocaml.org] 使いの僕としては少し寂しいですね.
--
O'Caml 普及委員会(うそ)
Re:Cの「クローン」である必要性は? (スコア:0)
たとえば、C の標準関数って sprintf のような思想の関数が多いですよねぇ。世の中のプログラムは sprintf を asprintf にするだけでも安全で簡単になると思うんで
結局プログラマの意識に帰着する (スコア:0)
「安全」と一口に言っても、 asprintfといえども%sに巨大な文字列突っ込まれてメモリ不足で死ぬことはありそう。 下手するとライブラリ含めて他の部分でメモリ不足による異常動作を惹起し、 より分かりづらいバグを生むこともありましょう。Cycloneもたぶん同様。
wcharの例にしても、例えば欧文+CJK程度の知識しかないプログラマは、 きっとbidiやligature等々を考慮しないので、 結局wcharライブラリが充実しててもまともな国際化プログラムにならないでしょう。
# そもそも国際化に関しては
# どんな基本操作があれば必要十
Re:結局プログラマの意識に帰着する (スコア:0)
FreeBSD 4.4-RELEASEで man asprintf を見たら「メモリが確保できない場合、関数は -1 を返してポインタは NULL が代入されてるよ」って書いてありますね。それともそういう話じゃないのかな?
Re:結局プログラマの意識に帰着する (スコア:0)
Cだとプログラムさぼって返値チェックしなくても動いちゃうからって話かな? Javaみたいにcatchやthrowsを強制されればこれはある程度防げますね。
あるいはasprintf()がギリギリ成功する巨大文字列作らされて、 その後のよりクリティカルなところでメモリ確保できなくて死ぬとか。 OSがスラッシング起こしたらまずいとか。
他には、意図的な攻撃のありうるサーバ類のプログラムでは、 メモリ
Cyclone はあくまで環境 (スコア:1)
さあ、ごいっしょに…
へん~しん。とぉぉぉぉぉぉぉぉ
※オフトピックです。-10が記録されました。
結局、バグチェックって何をやるの? (スコア:1)
実行時の動的なバグチェックに関しても、 境界チェックやヌルチェックは Java 程度だと思われます。 後は GC を導入することで dangling pointer を なくしている ぐらいでしょうか?
結局、 「C で掛かれたプログラムを Java で書き直すは大変でしょう? Cyclone でどう?」 というアプローチなのでしょうね。
Dynamic region のような スマートなメモリ管理機構を言語が サポートするのはありがたいですが、、、
コンタミは発見の母
Re:結局、バグチェックって何をやるの? (スコア:2)
Re:結局、バグチェックって何をやるの? (スコア:1)
CINT は C / C++ 言語の比較的忠実は インタプリタ処理系なので、 Java や Cyclone が 提供するような メモリ管理・保護の機能は 提供していないように 読めるのですが、、、
Java は、 C/C++ 言語の持つポテンシャルをあまり落とさずに memory access violation や dangling pointer や memory leak のバグを除去できる 丈夫なメモリ保護機構を導入しました。 セキュリティを求めて C / C++ のプログラムを Java に移植するのだとしたら、 このメモリ保護機構ゆえだと思います。
ネイティブコードを書く場合にも、 このメモリ保護機構と調和する ことが求められています (Java の ネイティブメソッドを書くための インターフェイスである JNI は、 「『ネイティブコードだからなんでもできる』のではなく、 『ネイティブコードでも Java の(メモリ保護の)作法を守ってよ!』」 と言っているように見える)。
一方 Java の対抗馬の C# は、 unsafe 文を導入することで メモリ保護機構を 一部を緩くしています。
例えば、 unsafe 構文の中では ポインタを使った配列のイテレート が可能ですが、 ポインタを使った場合には 配列の境界チェックが行われません。
C# の言語仕様書 [microsoft.com]には、 とあります。 勘弁してよ。
コンタミは発見の母
Re:結局、バグチェックって何をやるの? (スコア:2)
# あ、バグっぽいのめっけ。 < CINT
# 一応 FAQ 読んでからレポートしよう...
カーネル大学 (スコア:0)
なんか、またひとつ世界観が変わりそうです。オフトピなので匿名。
Re:カーネル大学 (スコア:1)
タレコむボタンを押した直後にしまったと思ったんですが手遅れでした。わはは。許して。
あと、builtっていうのも文脈的にはおかしいような気がするんですがこれは皆さん見て見ぬフリしてください。よろしく。
# さらにどうでもいいんですが「オフトピなので匿名」という理屈がよく分かりません。なぜ隠す?
Re:カーネル大学 (スコア:1, 参考になる)
スコア0は表示しないと設定している人のため、です。
そういう人はスレッドを「私物化」してるみたいなオフトピを読みたくないからそうしているんだろう、ということで。もちろん、匿名で書き込む人は、これといって悪意もなく、ただ面白がって楽しんでるだけなんでしょうけどね。
あと、なんだか恥ずかしいから匿名にしてます。許して・・・
Re:カーネル大学 (スコア:1)
今まで,ワシもそうしてました.
明らかな茶々入れや,ギャグはA/Cで.と.
ところがっ,そういうポストにかぎって,“おもしろおかしい”がついて
すぐにアゲられてしまうのだ!<ダメじゃん.
だからもうやめます>A/Cポスト.
#A/Cポストで付いたカルマを加算したら,倍くらいには....<ウソ
Re:カーネル大学 (スコア:1)
初耳です。
Anonymous Coward(匿名の臆病者)というアカウントは
重要な情報を投稿するため [srad.jp]にあるものだと思っていました。;-)
Re:カーネル大学 (スコア:0)
カーネル大学Linux学部...とか
Re:カーネル大学 (スコア:0, オフトピック)
#オフトピックね。
Re:カーネル大学 (スコア:0)