8.2 プロファイルとトレース (profiling and tracing)

Python インタプリタは、プロファイル: 分析 (profile) や実行の トレース: 追跡 (trace) といった機能を組み込むために低水準の サポートを提供しています。このサポートは、プロファイルや デバッグ、適用範囲分析 (coverage analysis) ツールなどに使われます。

Python 2.2 になってから、この機能の実装は実質的に作り直され、 C から呼び出すためのインタフェースが追加されました。 この C インタフェースは、プロファイルやトレース作業時に、 Python レベルの呼び出し可能オブジェクトが呼び出されることによる オーバヘッドを避け、直接 C 関数呼び出しが行えるようにしています。 プロファイルやトレース機能の本質的な特性は変わっていません; インタフェースではとレース関数をスレッドごとにインストールでき、 トレース関数に報告される基本イベント (basic event) は以前の バージョンにおいて Python レベルのトレース関数で報告されていた ものと同じです。

int (*Py_tracefunc)(PyObject *obj, PyFrameObject *frame, int what, PyObject *arg)
PyEval_SetProfile() および PyEval_SetTrace() を使って登録できるトレース関数の形式です。最初のパラメタは オブジェクトで、登録関数に obj として渡されます。 frame はイベントが属している実行フレームオブジェクトで、 what は定数 PyTrace_CALL, PyTrace_EXCEPTION, PyTrace_LINE, PyTrace_RETURN, PyTrace_C_CALL, PyTrace_C_EXCEPTION, あるいはPyTrace_C_RETURN のいずれかで、argwhat の値によって以下のように 異なります:

what の値 arg の意味
PyTrace_CALL 常に NULLです。
PyTrace_EXCEPTION sys.exc_info() の返す例外情報です。
PyTrace_LINE 常に NULLです。
PyTrace_RETURN 呼び出し側に返される予定の値です。
PyTrace_C_CALL 呼び出している関数の名前です。
PyTrace_C_EXCEPTION 常に NULLです。
PyTrace_C_RETURN 常に NULLです。

int PyTrace_CALL
関数やメソッドが新たに呼び出されたり、ジェネレータが新たなエントリの 処理に入ったことを報告する際の、Py_tracefuncwhat の 値です。イテレータやジェネレータ関数の生成は、対応するフレーム内の Python バイトコードに制御の委譲 (control transfer) が起こらない ため報告されないので注意してください。

int PyTrace_EXCEPTION
例外が送出された際のPy_tracefuncwhat の値です。 現在実行されているフレームで例外がセットされ、何らかのバイトコードが 処理された後に、what にこの値がセットされた状態でコールバック 関数が呼び出されます。

この結果、例外の伝播によって Python が呼び出しスタックを逆戻りする 際に、各フレームから処理が戻るごとにコールバック関数が呼び出されます。 トレース関数だけがこれらのイベントを受け取ります; プロファイラは この種のイベントを必要としません。

int PyTrace_LINE
行番号イベントを報告するときに (プロファイル関数ではなく) トレース関数のwhat パラメタとして渡す値です。

int PyTrace_RETURN
関数呼び出しが例外の伝播なしに返るときに Py_tracefunc 関数のwhat パラメタとして渡す値です。

int PyTrace_C_CALL
C関数を呼び出す直前に Py_tracefunc 関数のwhat パラメタとして渡す値です。

int PyTrace_C_EXCEPTION
C関数が例外を送出したときに Py_tracefunc 関数のwhat パラメタとして渡す値です。

int PyTrace_C_RETURN
C関数から戻るときに Py_tracefunc 関数のwhat パラメタとして渡す値です。

void PyEval_SetProfile(Py_tracefunc func, PyObject *obj)
プロファイル関数を func に設定します。obj パラメタは 関数の第一パラメタとして渡され、何らかの Python オブジェクトかまたは NULLになります。プロファイル関数がスレッド状態を維持する必要が あるなら、各々のスレッドに異なる obj を使うことで、状態を 記憶しておく便利でスレッドセーフな場所を提供できます。プロファイル 関数は、モニタされているイベントのうち、行番号イベントを除く全ての イベントに対して呼び出されます。

void PyEval_SetTrace(Py_tracefunc func, PyObject *obj)
トレース関数を func にセットします。 PyEval_SetProfile() に似ていますが、トレース関数は 行番号イベントを受け取る点が違います。

ご意見やご指摘をお寄せになりたい方は、 このドキュメントについて... をご覧ください。