[ < ] | [ > ] | [ << ] | [ Up ] | [ >> ] | [Top] | [Contents] | [Index] | [ ? ] |
バグレポートの出し方についての追加や、最新の手順については ‘<URL:http://www.gnu.org/software/gcc/bugs.html>’. を見て欲しい。
役に立つバグ報告の第一原則は次のとおり。 全ての事実を報告すること。 ある事実について、それに言及すべきか、しないでおくべきか確信が 持てないときは、言及すべきである。
人は良く事実を省略しがちである。問題を引き起こしたのが何かということを 知っているつもりになり、そのために詳細は関係ないと思ってしまうからである。 このため、報告する人のサンプルプログラムで変数名がどうなっているかは 関係ないだろうと思ってしまう。多分関係ないことが多いだろうが、 確認できないこともある。問題のバグは、その変数名が格納されている メモリ位置からデータを取り出すときに、そのメモリ参照の指す先が 正しくないためかもしれない。変数名が違っていたら、バグがあっても、 その位置の内容がコンパイラに正しい動作を行なわせるかもしれない。 そういうこともあるので、確実を期すために、詳細で完全な例を 送って欲しいのである。これは読者ができる最も簡単なことで、 最も役に立つことでもある。
バグレポートの目的は、そのバグがまだ知られていないものなら、誰かが 修正出来るようにすることにあることを忘れないで欲しい。 バグが既に知られているものであるなら、何が起きたかはあまり重要ではない。 つまり、バグレポートを書くときは必ず、そのバグは既知のものではないと 想定したうえで書いて欲しいのである。
概略的な事実しか書かずに、「これ当たりかな|?」等と書いてくる人が 時々いるが、これではバグを直す助けにはならないので、基本的には 役に立たないと言える。我々は、調査可能になる程度に充分な詳細を 教えてくれるよう返事することになる。最初から詳細に書いてくれると 物事が早く進むのである。
バグレポートはそれ自体に全てが含まれるようにして欲しい。 我々がさらなる情報提供をお願いしたときには、 最初書いてなかった情報に加えて、最初に報告済みの情報も全部含めて くれるのが最善である。
報告するバグは一個のメッセージにつき一個にして欲しい。 そうしてもらうと、どのバグが修正済みかを追跡するのと、読者の バグレポートを適切な保守担当者に転送するのが容易になる。
バグを調査できるようにするためには、以下の項目を全て報告して欲しい。
これがないと、GCC の最新版にバグを見つける手掛りがあるかどうか 判らないのである
文一個だけでは例として充分ではない。それをコンパイルためには、 コンパイラへの入力として完全なファイルに入っていなければならない。 問題のバグが、そのファイルにどういう風に入っているかの詳細に 依存しているかもしれないからである。
実際にコンパイルが通る例がないと、読者のバグレポートについて 出来ることは読者が幸運であることを祈るしかないのである。 どうやったらそのバグを引き起こせるか推測しても役に立たない。 例えば、レジスタ割当と再ロードにバグがあったとすると、それが 現れる関数の非常に詳細な点に依存していることが非常に多い
問題の起きる入力フィアルが、GNU のプログラムに含まれるものであっても、 やはり完全なテストケースを送ってもらわなければならない。 GCC の保守担当者に、問題となるプログラムを取り寄せるような 余計な仕事はさせて欲しくないのである。保守担当者達は、今でも 仕事を抱え過ぎているのである。また、問題は、読者のシステム上の ヘッダファイルに依存しているかもしれない。GCC の保守担当者が 利用可能なヘッダファイルを使って問題の調査を行なうのは、信頼性が ないと言える。CPP の出力を送れば、このソースファイルの確実性の 問題もなくなるし、見込みのない調査を幾分かでも減らしてくれる。
我々の方で引数が何かを推測することになったら、おそらく 正しくは推測できず、バグに出会うことがないかもしれない。
configure
に指定した引数。
変更点については正確である必要がある。文章による説明では 充分ではない。コンテキストつき差分(context diff)を送って欲しい。
読者が新たにファイルを追加したなら(例えば、我々がサポートしていない 機種に対するマシン記述のように)、それもコンパイラのソースの変更である。
当然ながら、バグが GCC が致命的シグナルを受け取ったというものであるなら、 誰も見逃すはずがない。だが、もしバグが出力が正しくないというものなら、 その間違いが非常にはっきりしていない限り、保守担当者が気が付かない 可能性がある。命令が一個間違っているかもしれないと言って、 50行の C プログラムから生成されたアセンブラコードを全部調べるような暇は 我々にはないのである。そういう調査は是非とも 読者 に やってもらわなければならない。
また、読者の出会った問題が致命的なシグナルを受けたというものであっても、 やはりその事をはっきりと知らせてもらう必要がある。 何か変なことが起きているとしよう。例えば、読者のところのコンパイラのコピー が古かったり、システムの C ライブラリのバグに遭遇したとする。 (これは実際にあったことである。) 読者のコンパイラのコピーは落ちるが、 我々のところにあるものでは落ちないということがある。 読者が、落ちることが予想されると言ってくれれば、こちらにあるコンパイラが 落ちなければ、我々はそのバグは起きなかったということを知ることになる。 読者が落ちることを予想されると言ってくれなければ、どこでバグが発生するか 我々には判らないだろう。我々は、観察結果から何も結論を引き出すことが できないのである。
問題が、GCC を何か他のコンパイラでコンパイルしたときの診断メッセージ にあるなら、それが警告なのかエラーなのかを教えて欲しい。
観察された症状が、読者のプログラムを実行したときの正しくない出力 であるということも多い。こんなことは言いたくないが、これだけでは そのプログラムが小さくて単純なものでない限り、充分な情報ではない。 我々には、大きなプログラムを研究して、正しくコンパイルされた場合に どのように動作するかを明らかにする時間は無いし、ましてどの行で 間違ったコンパイルが行われたかを知ることはできない。それは読者が 行わなければならないのである。問題のあるソース行と、 そしてその行が実行されたときにどんな正しくない結果が起きるのかを 我々に知らせて欲しい。プログラムを理解している非とは、プログラム自体の バグを見つけるのと同じぐらい簡単に上記のことは見つけられるはずである。
開発中のソースの行番号と読者のところにあるソースの行番号とは 一致しない。読者のところの行番号が判っても、保守担当者にとっては 役に立たないのである。
例えば、バックトレースだけ送ってくる人が多いが、それだけで 役に立つことはないと言える。単なる引数情報付きのバックトレースでは、 GCC について得られるところはほとんどない。GCC は非常に データ駆動になっているからである。同じ関数が異なる RTL insn について 何度も何度も呼び出され、その insn の詳細によって別々の作業を 行なうのである。
バックトレースで表示される引数はほとんどが役に立たない。 それが RTL のリスト構造へのポインタだからである。 ポインタの数値としての値をデバッガがバックトレースで表示するが、 それはどんな値でも意味はもたない。問題になるのは全て、そのポインタが 指し示すオブジェクトの内容だからである(さらに、その内容のほとんどは 他の同様なポインタになっている)。
さらに、コンパイラのほとんどのパスは、RTL insn 列を操作するループを 一つ以上持つ。そういうループについての最も生きた情報は、通常は、 insn がそこに到達したときの、ローカル変数にあるのであって、引数に あるのではない。
バックトレースに加えて提供すべきものは、スタックフレームを段階的に
遡ってみた各スタックフレームのローカル変数の値である。
ローカル変数や引数が RTX である場合、まずその値を表示し、
次に GDV の pr
コマンドを使ってその RTX が指す RTL 式を
表示する。(GDB が使えないマシンでは、使えるデバッガを使って、
その RTX を引数として関数 debug_rtx
を呼べば良い。)
一般に、ある変数がポインタならば、それが指すデータなしでは
ポインタ自身の値は役に立たない。
以下は必要ないものである。
人はバグに出会うと、入力ファイルをどう変更するとバグがなくなり、 何を変更すると影響がないかを調査するのに時間を費やすというのを 良くやる。
これは時間がかかることが多く、実はあまり役に立たない。 というのは、我々がバグを見つける方法というのは、一個のサンプルを デバッガの元でブレークポイントを設定して実行させるという方法を 取るからで、幾つかの例から純粋に演繹的に探すわけではないからである。 読者も同じようにすれば何か他のことに時間を回せるだろう。
もちろん、元々のもの 代わりにに、もっと簡単な例を見つけて 報告できれば、それは役に立つ。出力中のエラーを見つけやすくなるし、 デバッガの元で実行するのも時間がかからなくなる等。 GCC のバグのほとんどは、たった一個の関数にあることが多いので、 サンプルを単純化するのにもっとも直截的な方法は、バグが発生する関数 以外の関数定義を全部削除することである。ファイル中で問題の関数の前に ある関数群については、その関数が依存しているなら外部宣言に置き換えれば 良い。(例外がある。インライン展開関数は、ファイルのその関数以降で 定義されている関数のコンパイルに影響する。)
だが、単純化は必須ではない。単純化をやりたくなければ、何はともあれ、 バグを報告するようにし、読者が使ったテストケース全体を送って欲しい。
バグに対するパッチは、それが良いものなら役に立つ。 ただし、パッチが我々が必要な全てであるという前提のもとで、 テストケースのような必要な情報を落とさないようにして欲しい。 我々は読者のパッチで問題を理解し、それを別な方法で修正することを 決定するかもしれないし、あるいは全く理解できない可能性もある。
GCC ぐらい複雑なプログラムだと、プログラムをある一定のコード中の 経路を通らせるような例を作るのが非常に難しいことが良くある。 読者が例を送ってくれないと、我々自身では例を作り出せないだろうし、 バグが修正されたことを検証することもできないだろう。
そして、どんなバグを読者が修正しようとしているのか、あるいは、 読者のパッチが何故改良になるのかを理解できないときは、我々は そのパッチをインストールしないだろう。テストケースがあれば理解の 助けとなる。
我々が読者のパッチを理解し、インストールするのを容易にするための 指針として、See section GCC に対するパッチの送り方 を参照のこと。
そういう推測はだいたい間違っている。まずはデバッガを使って 事実を見つけないことには、私でもその点について正しい推測をすることは できない。
読者と同じシステムがない限り、読者のマシンのコアダンプを調べる方法は ない。もし同じシステムがあったとしても、我々自身がそのコアダンプを 再現できなければならない。
This document was generated
using texi2html 1.78.