
このような状況では、デバッガーが接続された仮想マシンを使用すると役立ちます(GDBやIDAなど)。 これは、プログラムが仮想マシンでも「ブレーク」しようとしない場合です。
幸運であり、プログラムが仮想マシンでの実行を気にしない場合、GDBを使用すると、バイナリにDWARF形式のデバッグ情報が含まれている場合、GDBを使用して内部を調べたり、ソーステキストと比較したりできます。


WinDbgとGDBを使用してWindowsカーネルを調べます
プログラムがVisual Studioでビルドされている場合、GDBはデバッグ情報を表示できません。 リスト内のWindows API関数の名前も忘れてしまう可能性があります。 ここではWinDbgが便利ですが、OSデバッグモードが適切でない場合、どのように仮想マシンに接続できますか?
GDBで使用されるものと同様の仮想マシンにリモートデバッグインターフェイスがあれば素晴らしいと思います。QEMU仮想マシン用のこのようなモジュールを考えて作成しました。 すべてがWindows用の ソースとバイナリの形式でレイアウトされているため、誰もがそれを適用することができます。
WinDbgを使用したリモートデバッグについては、 Haberに既に資料があります。 Windowsデバッグモードを有効にし、それを使用してWinDbgをリモート接続する方法を示します。 デバッガーは、Windowsの名前付きパイプに関連付けられた仮想COMポートを介して接続します。

QEMUに組み込まれた通常のパウダーとデバッグサーバー
私たちの場合、ゲストシステムの関与のないQEMUはこの名前付きパイプに接続して、Windows内で何が起こっているかについての情報をデバッガに提供します。 オペレーティングシステム自体は、デバッグされていることを認識していないため、デバッグは何らかの方法で非表示になります。
このモードでQEMUを起動するには、-windbgスイッチが必要です。
qemu-system-i386.exe -windbg pipe:windbg -hda disk.qcow2
その後、QEMUはデバッガーが接続するのを待ちます。 次のコマンドで実行する必要があります。
windbg.exe -b -k com:pipe,baud=115200,port=\\.\pipe\windbg,resets=0
エミュレーションが開始したら、Windowsデバッグモジュールなしで動作モードを選択します。

しばらくすると、OSはデバッガーが動作するために必要なすべてを初期化し、エミュレーターを停止し、コマンドの入力を求めます。

WinDbgは、シンボリック情報が見つからなかったことをすぐに書き込みます。
Symbol search path is: *** Invalid ***
いくつかの.symfixおよび.reloadコマンドを使用して、システムライブラリに関するシンボリック情報
Symbol search path is: *** Invalid ***
ダウンロード
Symbol search path is: *** Invalid ***
ます。
同じことは、メニューの[ファイル]-> [シンボルファイルパス...]からも実行できます。ここで、一時ディレクトリとMicrosoftサーバーのパスを指定できますsrv * d:\ tmp * http://msdl.microsoft.com/download/symbols

これで、WinDbgは、Windowsの内部構造と関数の名前、およびライブラリ関数の名前を認識します。 これらはリストに表示され、ブレークポイントをバインドすることができます。
その後、gコマンドを使用してOSのロードを続行し、そこで必要なアプリケーションを実行して
たとえば、!Dllsコマンドは、現在のプロセスでロードされたモジュールのリストを表示します。

「現在のプロセス」の概念は、リモートデバッグで表示されます。 結局のところ、OSはタスクに関連付けられている仮想アドレススペースを常に切り替えます。 !Dml_procコマンドは、実行中のプロセスのリストを表示します。

CrashMeアプリケーションがシステムで実行されていることがわかります(サイトwww.windbg.infoから取得しました )。 システムで実行中のデバッガーが見つかりませんでした。

このプログラムをデバッグするには、.processコマンドを使用してコンテキストに切り替えます。 そのパラメーターは、EPROCESS構造体のアドレスであり、!Dml_procコマンド出力の最初の列に示されています。 コマンドですべてがうまくいったことを確認できます!Peb:

デバッグを快適にするために、記号情報をアップロードし、このプログラムのソースコードが保存されている場所を示します。 その後、bpコマンドを使用してブレークポイントを作成できます。
.sympath+ E:\QemuImages\CrashMe\debug .reload /user .srcpath+ E:\QemuImages\CrashMe\CrashMe bp CCrashMeDlg::OnBnClicked_CallingConvention g
ここで、アプリケーションフォームの[Test Testing Conventions]ボタンをクリックすると、デバッガーに分類されます。

次に、ソーステキストでファイルを開くことができます。

呼び出し履歴を確認します。

または、ローカル変数を調べます。

WinDbgのもう1つの便利な機能は、イベントフィルターです。 さまざまな例外的な状況、モジュールのロードまたはアプリケーションの起動のイベントを中断できます。 通常、このようなイベントに関するメッセージはゲストシステムのデバッグサーバーによって送信され、それらのWinDbgフィルターでは、[デバッグ]→[イベントフィルター]ウィンドウで構成されます。

イベントや例外的な状況の傍受はまだ実装していません。
int 3または0による除算がエミュレータレベルで非常に簡単に理解できる場合、プロセスの作成を識別するためにさらに多くの作業を行う必要があります。
他のすべてのWinDbg関数は32ビットシステムで正常に機能するはずですが、64ビットを実際に扱ったことはありません。これらのすべての機能がデフォルトですべてのQEMUユーザーが利用できるようにパッチを準備しています。
参照資料