1

我想为当前的 AppDomain 设置 UnhandledExceptionMode.ThrowException 而不仅仅是应用程序线程。来自另一个线程的异常也应该由我的 CurrentDomain_UnhandledException 事件处理程序处理。这可能吗?这是我的代码:

static class Program
{
    /// <summary>
    /// The main entry point for the application.
    /// </summary>
    [STAThread]
    static void Main()
    {
        Application.SetUnhandledExceptionMode(UnhandledExceptionMode.ThrowException);
        AppDomain.CurrentDomain.UnhandledException += new UnhandledExceptionEventHandler(CurrentDomain_UnhandledException);
        Application.EnableVisualStyles();
        Application.SetCompatibleTextRenderingDefault(false);
        Application.Run(new Form1());
    }

    static void CurrentDomain_UnhandledException(object sender, UnhandledExceptionEventArgs e)
    {
        File.AppendAllText("Log.txt", ((Exception)e.ExceptionObject).Message + Environment.NewLine);
    }
}
4

1 回答 1

2

也许您正在寻找由 提供的行为Application.ThreadExceptionhttp://msdn.microsoft.com/en-us/library/system.windows.forms.application.threadexception%28v=vs.80%29.aspx

根据您的评论,实现所需行为的一种方法是启用 .Net 1 中旧的未处理异常策略。

在 App.config 中:

<runtime>
    <legacyUnhandledExceptionPolicy enabled="1" />
</runtime>

然后像这样修改你的主要方法:

class Program
{
    [STAThread]
    static void Main(string[] args)
    {
        try
        {
            AppDomain.CurrentDomain.UnhandledException += CurrentDomain_UnhandledException;

            ThreadPool.QueueUserWorkItem((object state) =>
            {
                throw new Exception("Exception thrown on Background Thread");
            });

            throw new Exception("Exception at the end of Main");
        }
        catch (Exception exception)
        {
            // Exceptions thrown on the Main Thread will pass through here
            HandleUnhandledException(exception);
        }
    }

    static void CurrentDomain_UnhandledException(object sender, UnhandledExceptionEventArgs e)
    {
        // Exceptions thrown on Background Threads will pass through here
        HandleUnhandledException((Exception)e.ExceptionObject);
    }

    static void HandleUnhandledException(Exception exception)
    {
        // TODO: Write your Unhandled Exception routine here
        Console.WriteLine(exception.Message);
    }
}

启用遗留异常策略会导致主线程忽略后台线程上的异常。它们只会被未处理的异常事件侦听器看到。确实需要处理主线程上的异常以防止出现 .NET Unhandled Exception 对话框,但通过使用共享方法,您可以重新使用异常处理代码。


您附加到的事件处理程序AppDomain.UnhandledException 捕获源自AppDomain. 如果您从图片中删除 Windows-Forms,下面是一些说明它的代码:

class Program
{
    [STAThread]
    static void Main(string[] args)
    {
        AppDomain.CurrentDomain.UnhandledException += CurrentDomain_UnhandledException;

        ThreadPool.QueueUserWorkItem((object state) =>
        {
            throw new Exception("Exception thrown on Background Thread");
        });

        throw new Exception("Exception at the end of Main");
    }

    static void CurrentDomain_UnhandledException(object sender, UnhandledExceptionEventArgs e)
    {
        Console.WriteLine(((Exception)e.ExceptionObject).Message);
    }
}

如果您运行此程序,您将看到两个异常消息都在应用程序崩溃之前立即写入控制台,因为Main. (注意这确实说明事件处理程序适用于两种异常,但它有一个竞争条件 - 在现实生活中,未处理的异常将AppDomain在下一个可能引发之前杀死)

于 2014-10-17T11:28:52.857 回答