[英]Why is the AppDomain.CurrentDomain.UnhandledException not catching unhandled exceptions from non-UI threads?
I've read some other threads and articles suggesting that there is a way to catch unhandled exceptions that originate on non-UI threads. 我还阅读了其他一些线程和文章,这些文章和文章建议有一种方法可以捕获源自非UI线程的未处理异常。 For some reason, this is not working for me. 由于某种原因,这对我不起作用。 Unhandled UI exceptions are being caught. 捕获了未处理的UI异常。 CurrentDomainUnhandledException never executes even when I test by throwing an exception from within a non-UI thread. 即使我通过从非UI线程内抛出异常进行测试,CurrentDomainUnhandledException也永远不会执行。
What's weirder is that the exception on the non-UI thread doesn't shut down the application as I thought it would. 奇怪的是,非UI线程上的异常不会像我想的那样关闭应用程序。
public partial class MainWindow : Window
{
public MainWindow()
{
InitializeComponent();
Application.Current.DispatcherUnhandledException += CurrentDispatcherUnhandledException;
AppDomain.CurrentDomain.UnhandledException +=
CurrentDomainUnhandledException;
}
void CurrentDispatcherUnhandledException(object sender, System.Windows.Threading.DispatcherUnhandledExceptionEventArgs e)
{
e.Handled = true;
MessageBox.Show(e.Exception.Message, "Caught an unhandled exception!");
}
void CurrentDomainUnhandledException(object sender, UnhandledExceptionEventArgs e)
{
Exception ex = e.ExceptionObject as Exception;
MessageBox.Show(ex.Message, "Uncaught Thread Exception",
MessageBoxButton.OK, MessageBoxImage.Error);
}
}
I'm throwing from an event handler that handles devices being plugged in which is definitely not a UI thread. 我从一个事件处理程序中抛出该事件处理程序,该事件处理程序绝对不是UI线程,它处理插入的设备。 The debugger breaks and shows me a message that the exception is unhandled. 调试器中断,并向我显示一条消息,指出未处理异常。 However when I continue the application keeps running and appears to keep working. 但是,当我继续时,该应用程序将继续运行,并且似乎可以正常工作。 I'm baffled by that. 我对此感到困惑。
_devicePlugWatcher = new ManagementEventWatcher(pluggedQueryStr);
_devicePlugWatcher.EventArrived += (DevicePluggedEventReceived);
The AppDomain.CurrentDomain.UnhandledException
event handler should be invoked if an exception is thrown on a non-thread pool thread (or non- Task
). 如果在非线程池线程(或非Task
)上引发了异常,则应调用AppDomain.CurrentDomain.UnhandledException
事件处理程序。 Try this for example: 尝试以下示例:
public partial class MainWindow : Window
{
public MainWindow()
{
InitializeComponent();
AppDomain.CurrentDomain.UnhandledException += CurrentDomainUnhandledException;
Thread thread = new Thread(() =>
{
Thread.Sleep(5000);
throw new Exception("test");
});
thread.Start();
}
void CurrentDomainUnhandledException(object sender, UnhandledExceptionEventArgs e)
{
Exception ex = e.ExceptionObject as Exception;
MessageBox.Show(ex.Message, "Uncaught Thread Exception",
MessageBoxButton.OK, MessageBoxImage.Error);
}
}
And compare it to this where the exception occurs inside a non-observed Task
: 并将其与未观察到的Task
发生异常的情况进行比较:
public partial class MainWindow : Window
{
public MainWindow()
{
InitializeComponent();
TaskScheduler.UnobservedTaskException += TaskScheduler_UnobservedTaskException;
Task.Run(() =>
{
throw new Exception("test");
});
Loaded += (s, e) =>
{
//gc so the unobserved exception "bubbles" up
GC.Collect(3, GCCollectionMode.Forced, true);
};
}
private void TaskScheduler_UnobservedTaskException(object sender, UnobservedTaskExceptionEventArgs e)
{
Exception ex = e.Exception;
MessageBox.Show(ex.Message, "Uncaught Thread Exception",
MessageBoxButton.OK, MessageBoxImage.Error);
}
}
So you should also handle TaskScheduler.UnobservedTaskException
. 因此,您还应该处理TaskScheduler.UnobservedTaskException
。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.