0

次のようにして未処理の例外フィルターを設定しました: SetUnhandledExceptionFilter(UnhandledException)

UnhandledException 関数では、MiniDumpWriteDump を使用してミニダンプを書き出します。

MiniDumpWriteDump(GetCurrentProcess(), GetCurrentProcessId(), hFile, MiniDumpNormal, excpInfo? &eInfo : NULL, NULL, NULL);

WinDbg のスタック トレースを見ると、あまりわかりません。

0:023>キロバイト
ChildEBP RetAddr Args から子へ              
警告: スタック アンワインド情報は利用できません。次のフレームは間違っている可能性があります。
15e7e7dc 08f00150 08f00a78 08f00000 08f00150 ntdll!ZwGetContextThread+0x12
15e7e7fc 777d301e 6f00016e 00000044 627e056a 0x8f00150
15e7e890 777d2ffa 777d2bf2 00000000 00650000 ntdll!RtlInterlockedFlushSList+0x889
15e7e894 777d2bf2 00000000 00650000 077e1b88 ntdll!RtlInterlockedFlushSList+0x865
15e7e8b4 772b14d1 08f00000 00000000 077e0c48 ntdll!RtlInterlockedFlushSList+0x45d
15e7e8d0 777ce023 077e1b88 08f00138 00000001 kernel32!HeapFree+0x14
15e7e8e8 777d48c6 777bfafa 777d419a ffffffff ntdll!RtlFreeHeap+0x7e
15e7e914 777e9ed7 ffffffff 15e7e938 15e7e944 ntdll!RtlImageNtHeader+0xe2
15e7e93c 777e9e49 00010000 00000000 08c70000 ntdll!RtlDestroyHeap+0x139
15e7e958 75d5458e 08f00000 00000000 08ccfe46 ntdll!RtlDestroyHeap+0xab
15e7e9c4 777ce023 104d9250 104d91f0 104d9250 カーネルベース!HeapDestroy+0xe
00000000 00000000 00000000 00000000 00000000 ntdll!RtlFreeHeap+0x7e

MiniDumpWriteDump のドキュメントには、strack トレースが良くない可能性があると記載されていますが、それについて何をすべきかよくわかりません: http://msdn.microsoft.com/en-us/library/ms680360%28v=vs.85 %29.aspx

どんな助けでも大歓迎です!

4

2 に答える 2

2

現在実行中のスレッドから信頼できるコールスタックを取得することはできません。ダンプファイルからコールスタックを取得するために、WinDbgはダンプファイルからスレッドコンテキストレコードを抽出します(CONTEXT構造体。これは基本的にスレッドのすべてのレジスタのスナップショットです)。レジスタ(具体的にはRIPとRSP)とシンボルに基づいて、スタックをウォークし、コールスタックを抽出できます。実行中のスレッドの場合、すべての命令が変更されるため、一貫したCONTEXT構造を取得する方法はありません。

あなたがMSDNで見たリンクは、現在実行中のスレッドに対して一貫したCONTEXTを取得する簡単な方法に言及しています。コードは次のようになります。

   __try
   {
      RaiseException(0, 0, 0, 0);
   }
   __except (
      MyStackTraceFilter(GetExceptionInformation()->ContextRecord)))
   {
      // do nothing in the handler
   }

ここでの作業はMyStackTraceFilterで行われます。この関数を提供する必要があります。入力パラメータは、信頼できるCONTEXTレコードになります。つまり、exceptinが発生したときの特定の時間における現在のスレッドのスナップショットです。MyStackTraceFilter内でスタックをウォークするコードを実際に記述して、実行中のスレッドの優れた呼び出しスタックを取得できます。コールスタックのみに関心がある場合、これは回避策になる可能性があります。

ほとんどの場合、矛盾するCONTEXT構造から「より良い」コールスタックを取得することが可能です。RSP / espが多かれ少なかれ正しいと信頼できる場合、あなたがすることは

  • スタックをダンプします(x86の場合は「ddsesp」、x64の場合は「dqsrsp」)
  • 例外の前に最後のスタックフレームがどこにあったかを推測してみてください
  • コマンド'kBasePtr StackPtr InstructionPtr'を使用して、コールスタックをダンプします
于 2011-03-31T00:10:06.010 に答える
1

未処理の例外フィルターから MinidumpWriteDump を呼び出している場合は、MINIDUMP_EXCEPTION_INFORMATION パラメーターで渡す有効な EXCEPTION_POINTERS が必要です。これを行った場合、ミニダンプには、クラッシュしているスレッドの状態を表す特別な CONTEXT を含む例外ストリームが含まれます。このようなダンプを WinDBG にロードすると、次のメッセージが表示されます: このダンプ ファイルには対象の例外が保存されています。保存された例外情報は、.ecxr 経由でアクセスできます。

その時点から始まるスタック トレースを表示できるように、.ecxr コマンドを入力してそのコンテキストを読み込む必要があります。

于 2012-09-25T11:42:23.970 に答える