[英]C# unhandled exception handler, attempting to write to log file
我的應用程序是Windows Forms .NET 4 C#TCP / IP服務器。 它每天都會崩潰一次,發生一般的Windows Server崩潰消息(按關閉以關閉此應用程序)。 我插入以下代碼來捕獲可能導致此問題的任何異常,並將一個簡單的null Object插入到一個定期調用以生成測試異常的例程中。
兩件事情:
.NET消息對我來說沒用。 我需要崩潰的日志文件堆棧跟蹤。 有誰知道我怎么做到這一點? 謝謝。
static class Program
{
[STAThread]
static void Main(string[] rgszArgs)
{
//My exception handler
AppDomain.CurrentDomain.UnhandledException +=
new UnhandledExceptionEventHandler(CatchUnhandledException);
Application.EnableVisualStyles();
Application.SetCompatibleTextRenderingDefault(false);
Application.Run(new FormMain(rgszArgs));
}
static void CatchUnhandledException
(object sender, UnhandledExceptionEventArgs e)
{
StreamWriter sw;
DateTime dtLogFileCreated = DateTime.Now;
Exception ex;
try
{
sw = new StreamWriter("crash-" + dtLogFileCreated.Day + dtLogFileCreated.Month
+ dtLogFileCreated.Year + "-" + dtLogFileCreated.Second
+ dtLogFileCreated.Minute + dtLogFileCreated.Hour + ".txt");
ex = (Exception)e.ExceptionObject;
sw.WriteLine("### Server Crash ###");
sw.WriteLine(ex.Message + ex.StackTrace);
sw.Close();
}
finally
{
Application.Exit();
}
}
}
您需要Application.ThreadException事件。
AppDomain未發送的異常事件捕獲拋出的未處理異常 - 例如Main
方法拋出的任何異常,但Application.Run
內部處理異常 - 這意味着Application.Run
不會因事件處理程序中的異常而拋出異常,所以永遠不會運行CatchUnhandledException
。
這意味着如果ThreadException
處理程序能夠從異常中恢復,則應用程序將繼續正常運行(如果Application.Run
拋出異常,則無法恢復)。
由於我不明白的原因,這種行為在調試時是不同的。
。 調試時,此行為已更改,以便拋出異常,允許您在Visual Studio中立即調試異常 - 這就是您的未處理異常處理程序在調試時正在運行的原因。
請注意,上面的CatchUnhandledException
處理程序將捕獲應用程序域中后台線程拋出的異常。
我不得不猜測這是AppDomain.UnhandledException事件的事件處理程序。 你絕對不能做的一件事就是調用Application.Exit(),程序不再處於正確狀態以便很好地關閉,你必須調用Environment.Exit()。 Application.Exit()調用可能是“繼續或退出”消息的來源,聽起來像Winforms應用程序顯示的ThreadExceptionDialog在UI線程中遭受了一次爐膛攻擊。
下一個問題是您傳遞給StreamWriter構造函數的參數。 您沒有為文件指定完整路徑名(例如c:\\ mumble \\ foo.txt),它可能會嘗試將文件寫入您沒有寫訪問權限的目錄。 很可能在Vista或Win7上。 或者文件實際上已經寫好但你找不到它,因為你不知道在哪里看。
使用Environment.GetFolderPath()選擇一個您知道可以寫入的目錄。
這是來自MSDN的AppDomain.UnhandledException事件 :
從.NET Framework版本4開始,不會針對損壞進程狀態的異常(例如堆棧溢出或訪問沖突)引發此事件,除非事件處理程序是安全關鍵的並且具有HandleProcessCorruptedStateExceptionsAttribute屬性。
這可能嗎?
如果你的程序狀態混亂,try / finally塊中的任何代碼都會破壞你的程序,你也可以嘗試調用Environment.FailFast("reason for failure here"
)。 這將自動寫入事件日志。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.