マルチスレッド Python アプリケーションがロックされた後、デッドロックをデバッグしようとしています。デバッガをアタッチしてプロセスの状態を検査する方法はありますか?
編集:Linuxでこれを試みていますが、クロスプラットフォームのソリューションがあれば素晴らしいでしょう. 結局、それはPythonです:)
Winpdbを使用します。ネットワークを介したリモート デバッグ、複数のスレッド、名前空間の変更、埋め込みデバッグ、暗号化された通信をサポートする、プラットフォームに依存しないグラフィカルな GPL Python デバッガーであり、pdb より最大 20 倍高速です。
特徴:
(出典: winpdb.org )
デバッガーをマルチスレッド Python プロセスに接続できますが、C レベルで行う必要があります。何が起こっているのかを理解するには、Python インタープリターをシンボルでコンパイルする必要があります。持っていない場合は、python.org からソースをダウンロードして自分でビルドする必要があります。
./configure --prefix=/usr/local/pydbg
make OPT=-g
sudo make install
sudo ln -s /usr/local/pydbg/bin/python /usr/local/bin/dbgpy
ワークロードがそのバージョンのインタープリターで実行されていることを確認してください。その後、GDB を使用していつでも接続できます。Python 関係者は、Misc ディレクトリにサンプルの ".gdbinit" を含めました。これには、いくつかの便利なマクロが含まれています。ただし、マルチスレッド デバッグ (!) では機能しません。このような行を置き換える必要があります
while $pc < Py_Main || $pc > Py_GetArgcArgv
次のように:
while ($pc < Py_Main || $pc > Py_GetArgcArgv) && ($pc < t_bootstrap || $pc > thread_PyThread_start_new_thread)
そうしないと、次のようなコマンドpystack
はメイン スレッド以外のスレッドでは終了しません。このようなものがあれば、次のようなことができます
gdb> attach <PID>
gdb> info threads
gdb> thread <N>
gdb> bt
gdb> pystack
gdb> detach
そして何が起こっているか見てください。すこし。
「pyo」マクロを使用して、オブジェクトが何であるかを解析できます。 Chrisのブログにいくつかの例があります。
幸運を。
(私にとって重要な情報、特にスレッドの修正については、 Dan のブログに感謝します!)
あなたがpydbを意味するなら、それを行う方法はありません。その方向でいくつかの努力がありました: svn commit を参照してください。しかし、それは放棄されました。おそらくwinpdbはそれをサポートしています。
PyDev (Windows XP 上の Eclipse) でマルチスレッド プログラムをデバッグした私の経験では、thread.start_new_thread を使用して作成されたスレッドはフックできませんでしたが、threading.Thread を使用して作成されたスレッドはフックできました。情報がお役に立てば幸いです。
どのプラットフォームでこれを試みていますか?ほとんどのデバッガーでは、プロセスIDを使用して実行中のプロセスにアタッチできます。ロギングを介して、またはタスクマネージャなどを使用してプロセスIDを出力できます。それが達成されると、個々のスレッドとその呼び出しスタックを検査できるようになります。
編集:クロスプラットフォームであるGNU Debugger(GDB)の経験はありませんが、このリンクを見つけたので、正しい道を歩むことができます。デバッグシンボルを追加する方法(スタックトレースを読み取るのに便利)と、実行中のPythonプロセスに接続するようにgdbに指示する方法について説明します。
PyCharm IDEでは、バージョン 4.0 以降、実行中の Python プロセスにアタッチできます。
ここでは、その方法について説明します。
pdbinjectを使用すると、既に実行中の python プロセスに pdb を注入できます。
pdbinject 実行可能ファイルは python2 でのみ機能しますが、python3 にも正常に挿入できます。