locked
WER exception handling in a .NET 2.0 WinForms application RRS feed

  • Question

  •  

    Hi,

     

    I'm working on adapting an existing .NET 2.0 WinForms application to throw its unhandled exceptions to the O/S for handling (where available/enabled) by Windows Error Reporting. What I want to do when an exception occurs is: write a local error log file, attempt to close some database connections, and then handball the exception to the O/S for handling by Windows Error Reporting.

     

    Here's the guts of the code I've come up with so far, but a lot of my comments here are based on trial and error. What I'd like to know is, are these comments correct? Will this code trigger WER (if available/enabled in the O/S) for all exceptions, regardless of what thread they come from?

     

    Is there a better way of doing what I'm trying to do? Are there any good references out there for calling WER from a WinForms application?

     

    /// <summary>

    /// The main entry point for the application.

    /// </summary>

    [STAThread]

    static void Main(string[] argv)

    {

    // Configure the application so that exceptions rethrown by our code will be

    // thrown to the operating system (rather than the .NET Framework's unhandled

    // exception handler), triggering Windows Error Reporting functionality on

    // supported platforms (Windows XP and later) if enabled in the O/S

    // See http://forums.microsoft.com/MSDN/ShowPost.aspx?PostID=528848&SiteID=1

     

    Application.SetUnhandledExceptionMode(UnhandledExceptionMode.ThrowException);

     

    // The following two event subscriptions subscribe to notification events for exceptions

    // originating in various threads

    // See http://msdn.microsoft.com/msdnmag/issues/04/06/NET/

    // and http://msdn.microsoft.com/msdnmag/issues/04/06/NET/default.aspx?loc=&fig=true#fig3

     

    // The event handlers for these events attempt to write an error log file and clean up

    // before the exception is thrown to the operating system for Windows Error Reporting.

    // (Note that these event handlers are just subscribing to a notification - they don't

    // actually "catch" the exception, which instead just bubbles up to the O/S afterwards.)

     

    // For Windows Error Reporting to kick in as intended, it appears that:

    // - These event handlers must not forcibly terminate using a call such as Environment.Exit(),

    // which would kill the process before the exception bubbles up to the O/S

    // - They must not rethrow the exception (which would lose the original stack trace context

    // required for Windows Error Reporting to categorise exceptions on the server side

    // and for QSR to debug the error report), and must not throw new exceptions

    // - There must be no try/catch block in Main() or SubMain() to catch the exception before

    // it reaches the O/S

     

    // 1) Be notified of exceptions that occur in threads not created and owned by Windows Forms

    // See http://msdn2.microsoft.com/en-us/library/system.appdomain.unhandledexception(vs.80).aspx

     

    AppDomain.CurrentDomain.UnhandledException += new System.UnhandledExceptionEventHandler(OnUnhandledException);

     

    // 2) Be notified of exceptions that occur in Windows Forms threads

    // See http://msdn2.microsoft.com/en-us/library/system.windows.forms.application.threadexception(vs.80).aspx

     

    Application.ThreadException += new System.Threading.ThreadExceptionEventHandler(OnGuiUnhandedException);

     

    // :

     

    // Application.Run(), etc.

    }

     

    cheers,

     

    Marcus Ogden

    QSR International

    www.qsrinternational.com

     

     

    • Moved by Max Wang_1983 Tuesday, April 26, 2011 1:28 AM forum consolidation (From:Windows Error Reporting for ISVs)
    Sunday, October 21, 2007 4:02 PM

Answers

  •  

    All you need for a winforms app is to do

     

    Application.SetUnhandledExceptionMode(UnhandledExceptionMode.ThrowException). 

    Thursday, October 25, 2007 11:25 PM

All replies

  • Marcus,

    my understanding of crash reporting for managed apps is as follows: When an exception occurs, the CLR and/or the OS walk the stack to look for an exception handler in the application code which wants to deal with the exception. If there is no such exception handler, the exception is classified as "unhandled". The CLR will then fire the UnhandledException event and call all handlers registered to this event. The event handlers can then write to logfiles, clean up resources et cetera. When the handler returns, the CLR and the OS will terminate the application - after displaying the WER dialog which allows the user to send crash data to Microsoft's Watson servers.

    This is the simple version of the story. In practice, both Windows Forms and WPF add their own special exception handling strategies which go beyond what UnhandledException event handlers provide. Myself, I only tried this for WPF (using
    DispatcherUnhandledException). More on this in the discussion at http://forums.microsoft.com/msdn/showpost.aspx?postid=1164067&siteid=1. Another potentially useful links is Unexpected Errors in Managed Applications.

    Hope this helps,

    Claus

    http://www.clausbrod.de/Blog

    Sunday, October 21, 2007 5:33 PM
  •  

    All you need for a winforms app is to do

     

    Application.SetUnhandledExceptionMode(UnhandledExceptionMode.ThrowException). 

    Thursday, October 25, 2007 11:25 PM
  • Hi there

    I am hoping that you can assist me with the issue described below:

    The problem with calling the line above (Application.SetUnhandledExceptionMode....) is that you need to do it before creating any window handles. The answer is creating a Main Sub as shown below:

     Public Sub Main()
            Application.SetUnhandledExceptionMode(UnhandledExceptionMode.ThrowException)
            Application.EnableVisualStyles()
            Application.SetCompatibleTextRenderingDefault(False)
            Application.Run(New frmMain)
        End Sub
    

    The problem with doing this is that you need to disable the application framework as you need to specify a startup object (Sub Main) and not a form (frmMain). This in turn leads to other problems. We have now picked up an issue where MDI forms that are opened from dialog forms just do not open when the application framework is disabled.

    So my question is, is there another way of setting the UnhandledExceptionMode of the application to ThrowException where the Application Framework is still enabled. I have found references on the internet to a line which can be added to the app.config file (<legacyUnhandledExceptionPolicy enabled="1" />), but this does not seem to have any effect.

    Any help in this regard will be greatly appreciated.

    Regards

    Johan

    Wednesday, November 4, 2009 10:35 AM
  • Hi there

    I am hoping that you can assist me with the issue described below:

    The problem with calling the line above (Application.SetUnhandledExceptionMode....) is that you need to do it before creating any window handles. The answer is creating a Main Sub as shown below:

     Public Sub Main()    Application.SetUnhandledExceptionMode(UnhandledExceptionMode.ThrowException)    Application.EnableVisualStyles()    Application.SetCompatibleTextRenderingDefault(False)    Application.Run(New frmMain)  End Sub

    The problem with doing this is that you need to disable the application framework as you need to specify a startup object (Sub Main) and not a form (frmMain). This in turn leads to other problems. We have now picked up an issue where MDI forms that are opened from dialog forms just do not open when the 3gp application framework is disabled.

    So my question is, is there another way of setting the UnhandledExceptionMode of the application to ThrowException where the Application Framework is still enabled. I have found references on the internet to a line which can be added to the app.config file (<legacyUnhandledExceptionPolicy enabled="1" />), but this does not seem to have any effect.

    Any help in this regard will be greatly appreciated.

    Regards

    Johan


    I've got the same question. Have you got the answer? Maybe you can share with me? Thanks in advance.
    Friday, July 23, 2010 2:22 AM