ADPlusまたはDebugDiagを使用してクラッシュダンプファイルを生成する方法は知っていますが、これらのツールをインストールせずに顧客のコンピューターでこれを行う方法があるかどうか疑問に思っています...具体的には、アプリケーションを構成できるようにしたいです(たとえば、レジストリ値を使用して、重大な障害が発生した場合にクラッシュダンプを生成します。具体的には、C#アプリケーションからこれを実行できる必要がありますが、必要に応じてP/Invoke'ingを気にしません。ありがとう!
「失敗した」プロセス(またはスレッド)自体からミニダンプを作成するのは簡単ではないか、正確でない可能性があります( MiniDumpWriteDump 関数の備考)。
また、クラッシュダンプを作成する必要があるかもしれないような怒りがプロセスにある場合、通常、状況全体が非常にうんざりしているため、クラッシュダンプを作成しようとしても別のクラッシュを引き起こす可能性があります(ハングするような状況-現在のプロセス内から「キャッチ」するのが難しくなります)。
クライアントのシステムに個別のアプリケーションをインストールできない場合にできる「最善の」ことは、外部プロセスを開始し(重大な状況でも失敗する可能性があります!)、現在のプロセスからクラッシュダンプを作成することです(- John RobbinsのSuperassert.NET )。外部リソースをアプリリソースに配置し、起動時にそこから抽出して(重要な状況での障害を最小限に抑えるため)、ディスク(あえて)に移動することもできます。
次のレジストリスクリプトを使用して、特定のディレクトリにクラッシュダンプを作成するようにWindowsエラー報告(WER)を構成できます。
Windowsレジストリエディターバージョン5.00 [HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows\Windows Error Reporting\LocalDumps] "DumpFolder" = "C:\\ Dumps" "DumpCount" = dword:00000064 "DumpType" = dword:00000002 "CustomDumpFlags" = dword:00000000
ダンプは、クラッシュしたプロセスの名前を反映した名前でC:\ Dumpsに入ります。 DumpType = 2は、完全なメモリダンプを提供します。 DumpType = 1はミニダンプを提供します。 64ビットマシンでは、これらをWow32ノードの下に置く必要はありません。 WERは、上記で指定された非WOWレジストリキーのみを使用します。
クラッシュの種類によっては、この方法が機能しない場合があります。なぜ、またはどのクラッシュタイプがキャッチされないのか、まだわかりません。誰でも?
あなたのアプリがホース接続されている場合、ミニダンプファイルの作成を試してみるといいでしょう、最悪の事態は何ですか、あなたのアプリはクラッシュしますか?とにかくそれをやっているので、あなたも試してみてください。
VoiDedが言及したMSDNフォーラム のコードはかなり安定しているようです。 VB.Netバージョンが必要だったので、必要な人のためにVBバージョンがあります:
Friend Class MiniDump
'Code converted from C# code found here: http://social.msdn.Microsoft.com/Forums/en-US/clr/thread/6c8d3529-a493-49b9-93d7-07a3a2d715dc
Private Enum MINIDUMP_TYPE
MiniDumpNormal = 0
MiniDumpWithDataSegs = 1
MiniDumpWithFullMemory = 2
MiniDumpWithHandleData = 4
MiniDumpFilterMemory = 8
MiniDumpScanMemory = 10
MiniDumpWithUnloadedModules = 20
MiniDumpWithIndirectlyReferencedMemory = 40
MiniDumpFilterModulePaths = 80
MiniDumpWithProcessThreadData = 100
MiniDumpWithPrivateReadWriteMemory = 200
MiniDumpWithoutOptionalData = 400
MiniDumpWithFullMemoryInfo = 800
MiniDumpWithThreadInfo = 1000
MiniDumpWithCodeSegs = 2000
End Enum
<Runtime.InteropServices.DllImport("dbghelp.dll")> _
Private Shared Function MiniDumpWriteDump( _
ByVal hProcess As IntPtr, _
ByVal ProcessId As Int32, _
ByVal hFile As IntPtr, _
ByVal DumpType As MINIDUMP_TYPE, _
ByVal ExceptionParam As IntPtr, _
ByVal UserStreamParam As IntPtr, _
ByVal CallackParam As IntPtr) As Boolean
End Function
Friend Shared Sub MiniDumpToFile(ByVal fileToDump As String)
Dim fsToDump As IO.FileStream = Nothing
If (IO.File.Exists(fileToDump)) Then
fsToDump = IO.File.Open(fileToDump, IO.FileMode.Append)
Else
fsToDump = IO.File.Create(fileToDump)
End If
Dim thisProcess As Process = Process.GetCurrentProcess()
MiniDumpWriteDump(thisProcess.Handle, _
thisProcess.Id, _
fsToDump.SafeFileHandle.DangerousGetHandle(), _
MINIDUMP_TYPE.MiniDumpNormal, _
IntPtr.Zero, _
IntPtr.Zero, _
IntPtr.Zero)
fsToDump.Close()
End Sub
End Class
呼び出しが確実に処理されるようにし、比較的安全である必要があります。
P/Invoke dbghelp.dll
のMiniDumpWriteDump
関数AppDomain.UnhandledException
イベント。
この場合、.NET例外データのログをダンプし、ミニダンプをファイルに書き込むことができます。
MSDNフォーラムのスレッド もあり、P/Invoke署名と適切な使用法について説明しています。
Environment.FailFast を呼び出すことができます。
FailFastメソッドは、メッセージ文字列をWindowsアプリケーションイベントログに書き込み、アプリケーションのダンプを作成してから、現在のプロセスを終了します。メッセージ文字列は、Microsoftへのエラー報告にも含まれています。
とりわけ。
Log4netのようなロギングフレームワークを使用していますか?通常、リリースのデバッグレベルのメッセージをオフにします。ただし、特定のケース(クラッシュなど)でのみファイルにログを記録する特別なアペンダーの作成について考えることができます。このアペンダーは、最初はファイルに書き込むことができるメモリのみのリングバッファに書き込みます。後で、たとえば280Z28で推奨されるような例外ハンドラーによってトリガーされます。
必要な情報の種類に応じて、AppDomain.UnhandledException
イベントのハンドラーを追加できますか? (それはあなたが探しているものとは正確に異なりますが、クライアントマシンで間違いなく利用可能です。)