以前曾寫(xiě)過(guò)一個(gè) bugslayer.dll 的介紹. 在程序出錯(cuò)時(shí)將調(diào)用棧寫(xiě)到文件. 覺(jué)得不錯(cuò). 后來(lái)開(kāi)始用 windbg. 知道了 userdump. 知道了如何調(diào)試 dump... 才知道程序崩潰的時(shí)候?qū)?span lang=EN-US> dump 文件其實(shí)可以獲取比調(diào)用棧多得多的信息.
如果你的程序什么都不干. 那么在程序出錯(cuò)的時(shí)候. drwtsn32.exe 會(huì)寫(xiě)一個(gè) userdump. 但 drwtsn32 有些缺點(diǎn). 比如只能寫(xiě)一個(gè) dump 文件. 后面的崩潰寫(xiě) dump 文件時(shí)會(huì)覆蓋前面的. win2000 下的 drwtsn32 只能寫(xiě)舊式的 dump 文件(往往尺寸比較大). 有一篇文章論述的比較清楚:
http://www.debuginfo.com/articles/ntsdwatson.html
建議使用 ntsd 代替 drwtsn32. 但 ntsd 的缺點(diǎn)就是需要安裝最新的 windbg. 這是一個(gè)硬傷. 在看了 debuginfo.com 的另一篇文章:
http://www.debuginfo.com/articles/effminidumps.html
之后, 我選擇的是在程序出錯(cuò)的時(shí)候調(diào)用 api 自己寫(xiě) minidump. 克服了 drwtsn32, ntsd 的缺點(diǎn).
將封裝好的函數(shù)放到了一個(gè)頭文件中, 包含即可. 使用的方法很簡(jiǎn)單:
#include <windows.h>
#include "minidump.h"
LONG __stdcall MyUnhandledExceptionFilter(PEXCEPTION_POINTERS pExceptionInfo)
{
CreateMiniDump(pExceptionInfo, "c:\\user.dmp");
return EXCEPTION_EXECUTE_HANDLER;
}
void main()
{
SetUnhandledExceptionFilter(MyUnhandledExceptionFilter);
*(int*)0=0; // AV
}
這樣就好了. 注意安裝至少 xp 以上的 sdk.
這里用到了一個(gè) api SetUnhandledExceptionFilter(), 如果不明白可以搜一下 msdn.
運(yùn)行例子程序出錯(cuò)退出之后, 就得到了 c:\\user.dmp. 可以用 windbg 等調(diào)試器來(lái)分析了.
代碼從這里下載 http://nicoster.googlepages.com/minidump.rar