[C#] Multithreading in C# 3 [7] – Exception Handling

The same technique can be applied to handle exceptions in a thread. You can just use a try/catch block.

But what if an unhandled exception is thrown from a thread? How can you handle it in the main thread? And what will happen?

1. Try/Catch

Let’s catch an exception from a second thread in the main thread.

public static void Test1()
{
  try
  {
    Thread worker = new Thread(() =>
      { throw new ApplicationException("Thread Error"); });

    worker.Start();
    worker.Join();
  }
  catch (ApplicationException ex)
  {
    Console.WriteLine("Exception: " + ex.Message);
  }
  finally
  {
    Console.WriteLine("Exiting...");
  }
}

Looks pretty good. Let’s run the code.

Alas, the exception is not catched and the application is crashed.

2. UnhandledException Event

So what can we do to catch unhandled exceptions from threads?

The solution is to use the “UnhandledException” event of “AppDomain”. The UnhandledException callback will fire for all unhandled exceptions on threads within the application domain, including the main thread.

public sealed class AppDomain
{
  public event UnhandledExceptionEventHandler UnhandledException;
}
public delegate void UnhandledExceptionEventHandler(Object sender, UnhandledExceptionEventArgs e);

UnhandledExceptionEventArgs” has the following additional properties:

public class UnhandledExceptionEventArgs : EventArgs
{ 
  public Object ExceptionObject { get; }
  public bool IsTerminating { get; } // indicates whether the CLR is terminating.
}

3. Getting the Current AppDomain

To use the “UnhandledException” Event, you need to get the current AppDomain instance.

public sealed class AppDomain
{
  public static AppDomain CurrentDomain { get; }
}

4. Catching Unhandled Exceptions

It’s time to catch the unhandled exceptions.

static void OnHandler(object sender, UnhandledExceptionEventArgs ags)
{
  Exception ex = (Exception)ags.ExceptionObject;
  Console.WriteLine("Thread Error: {0}", ex.Message);
  Console.WriteLine("Is CLR terminating? {0}", ags.IsTerminating);
}

public static void Test1()
{
  AppDomain.CurrentDomain.UnhandledException += OnHandler;

  Thread worker = new Thread(() =>
    { throw new ApplicationException("Thread Error"); });

  worker.Start();
  worker.Join();
  Console.WriteLine("Exiting ... ");
}

Let’s run the code.

An exception from a new thread is handled by the “UnhandledException” handler. But wait a minute! The application still crashes.

Look at the value of the “IsTerminating” property. It is “true”, which means CLR terminates the current application domain.

The purpose of the “UnhandledException” handler is to give you the final chance to clean up the resources before the application is closed.

 

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out /  Change )

Google photo

You are commenting using your Google account. Log Out /  Change )

Twitter picture

You are commenting using your Twitter account. Log Out /  Change )

Facebook photo

You are commenting using your Facebook account. Log Out /  Change )

Connecting to %s