クラッシュ (segfault) の報告と解析
Julia を壊したのですね、おめでとうございます! この章では Julia 内部で不具合が起こったときによく現れる症状を見たときに行える一般的な手続きを紹介します。ここで紹介されるデバッグ方法から得られる情報があれば、メンテナはスクリプトの実行速度が予想より遅い理由の調査や segfault の解析をずっと簡単に行えます。
このページを読むよう言われたのなら、現在の症状に最も近いものを次から見つけ、そこにある指示に従ってデバッグ情報を生成してください。症状は次の通りです:
バージョン/環境の情報
エラーの種類に関わらず、私たちは実行している Julia のバージョンを知る必要があります。Julia が最初にスタートアップ処理を終えたときにバージョンとリリース日時を示すヘッダーが表示されます。これに加えて versioninfo()
の出力も報告に加えるようにしてください。この関数は標準ライブラリの InteractiveUtils
モジュールでエクスポートされます:
julia> using InteractiveUtils
julia> versioninfo()
Julia Version 1.5.4
Commit 69fcb5745b (2021-03-11 19:13 UTC)
Platform Info:
OS: Linux (x86_64-linux-gnu)
CPU: Intel(R) Core(TM) i7-7700 CPU @ 3.60GHz
WORD_SIZE: 64
LIBM: libopenlibm
LLVM: libLLVM-9.0.1 (ORCJIT, skylake)
Environment:
...
ブートストラップ (sysimg.jl
) 中の segfault
Julia をビルドする make
の最後の方で起こる segfault は、Julia が base
フォルダに含まれる全てのコードを実行に先立って解析しているときに発生した問題から起きている場合がよくあります。この処理が予期しない形で終了する原因は様々なものが考えられますが、Julia の C コードに起因することも少なくありません。そのような場合にはデバッグビルドを作成して gdb
でデバッグする必要があります。具体的には次の手順で行います:
まず Julia のデバッグビルドを作成します:
$ cd <julia_root>
$ make debug
この処理はおそらく通常の make
と同じエラーで失敗しますが、そのとき正確なバックトレースを gdb
へ提供するために必要なデバッグ用実行形式が作成されます。続いて gdb
の中からブートストラップ処理を手動で実行します:
$ cd base/
$ gdb -x ../contrib/debug_bootstrap.gdb
起動した gdb
によって Julia のデバッグビルドを使ったブートストラップ処理が開始され、segfault が起こった時点のバックトレースが出力されます。完全なバックトレースを得るには <enter>
を何回か押す必要があります。そのバックトレースとバージョン情報、その他の役に立つと思う情報を含んだ gist を作成し、その gist のリンクを入れて Github に issue を立ててください。
スクリプト実行中の segfault
手続きはブートストラップ (sysimg.jl
) 中の segfault とほぼ同じです。Julia のデバッグビルドを作成し、デバッグされた Julia プロセスの中でスクリプトを実行してください:
$ cd <julia_root>
$ make debug
$ gdb --args usr/bin/julia-debug <path_to_your_script>
こうすると gdb
は実行を開始せずに命令を待つので、r
を入力して実行を開始してください。segfault したら bt
でバックトレースを生成できます:
(gdb) r
Starting program: /home/sabae/src/julia/usr/bin/julia-debug ./test.jl
...
(gdb) bt
このバックトレースとバージョン情報、その他の役に立つと思う情報を含んだ gist を作成し、その gist のリンクを入れて Github に issue を立ててください。
Julia スタートアップ中の segfault
Julia のスタートアップ処理にエラーが起こることも時にはあります (特に Julia をソースからビルドせずにバイナリディストリビューションを使ったとき)。例えば次のようなエラーです:
$ julia
exec: error -5
こういったエラーは通常ブートアップフェーズのごく早い段階で何かが正しくロードされなかったことを示します。このような場合に何が悪さをしているかを調べるには、外部ツールを使って julia
プロセスのディスクアクセスを確認するとよいでしょう:
-
Linux では
strace
が利用できます:$ strace julia
-
OSX では
dtruss
が利用できます:$ dtruss -f julia
strace
/dtruss
の出力とバージョン情報、その他の関連する情報を含んだ gist を作成し、その gist のリンクを入れて Github に issue を立ててください。
用語
このガイドで使った略語を示します:
<julia_root>
は Julia ソースツリーのルートディレクトリを表します。これはbase
,deps
,src
,test
といったフォルダを持つディレクトリです。