How to Catch Exceptions from a Threadpool.Queueuserworkitem

C# ThreadPool QueueUserWorkItem Exception Handling

The best practice is that your background threads should not throw exceptions. Let them handle their exceptions on their own.

Ideally you should wrap the code in your method that executes on a thread in a try-catch block and handle the exception in the catch block. Do not re-throw it from the catch block.

Read this for more details. http://www.albahari.com/threading/#_Exception_Handling

If you want to update the UI from background thread you can do that by using Control.InvokeRequired property and Control.Invoke method. See the MSDN links for details and examples.

How to catch exceptions from a ThreadPool.QueueUserWorkItem?

If you have access to action's source code, insert a try/catch block in that method; otherwise, create a new tryAction method which wraps the call to action in a try/catch block.

How to try..catch ThreadPool.QueueUserWorkItem code

Exceptions propagate up the call stack on the thread on which they are thrown. Because the commands run on a thread pool thread, it will be on a different thread to your try ... catch hence it doesn't get caught.

EDIT: Assuming you do actually invoke the command within the try ... catch

Exceptions on threadpool threads

NO, the exception will never propagate to another thread. It will eventually crash the thread, and be caught by the runtime. At this point the runtime raises the AppDomain.UnhandledException event where the exception can be observed.

You can read more about this here.

Do I need to use try catch or check the return value of ThreadPool.QueueUserWorkItem

You need to read the docs carefully. While MSDN states:

true if the method is successfully queued; NotSupportedException is
thrown if the work item could not be queued.

...just bellow also states:

NotSupportedException: The common language runtime (CLR) is hosted,
and the host does not support this action.

I mean, NotSupportedException will be thrown if the hosting environment doesn't support thread pooling.

Thus, if you're queueing threads where you can do so, you don't need a try/catch block. At least, you can check that the thread could be queued using the regular boolean return value.

Exception Thrown in thread pool

If the application is .Net 2+, an unhandled exception on a non-main thread will flatten the process.

You can configure this behavior using the app.config LegacyUnhandledExceptionPolicy setting, but I wouldn't recommend this as it potentially masks serious bugs.

Update

If you wish to ignore the occasional timeout exception, consider placing your WebService call in a try\catch block and ignore the timeout exception:

try
{
//Call WebService
}
catch(System.Net.WebException ex)
{
//Ignore
}

Catch UnhandledExceptions raised on Threads, Tasks, Timers, ThreadPool threads, and BackgroundWorkers

After searching around more and testing, here is how I will handle exceptions raised on other threads. For unhandled exceptions, ensure that I make the following call at the top of Application.OnStartup():

AppDomain.CurrentDomain.UnhandledException += 
this.CurrentDomain_UnhandledException;

For creating threads, I'll prefer to use System.Threading.Thread, System.Threading.ThreadPool.QueueUserWorkItem, or System.Threading.Timer. I find BackgroundWorkers useful, so I extended the class in a way that will make it easier to handle unhandled exceptions:

public class MyBackgroundWorker : BackgroundWorker
{
protected override void OnRunWorkerCompleted(RunWorkerCompletedEventArgs e)
{
if (e.Error != null)
throw e.Error;
else
base.OnRunWorkerCompleted(e);
}
}

I can use IEnumerable.AsParallel or System.Threading.Tasks.Parallel.For for parallel loops because the AppDomain.CurrentDomain.UnhandledException will catch their exceptions as well.

I will avoid Tasks. I will also avoid Action<T>s, and Func<T>s if I call BeginInvoke on them. I'll avoid these because AppDomain.CurrentDomain.UnhandledException does not catch their exceptions.

ThreadPool QueueUserWorkItem Throws NullReferenceException

I think the analysis in the question is flawed (e.g. the exception is coming from <LoadArmoryData>b__0(System.Object), which represent a lambda expression in LoadArmoryData whose signature expects an object parameter; but you are looking at the IL for LoadArmoryData, which is a method whose signature expects a string parameter).

This is just a straightforward NullReferenceException, probably coming from nameRegex.Match(simcString).Groups[2].Value; when the Regex doesn't match.

Exceptions on .Net ThreadPool Threads

I do this a lot in my current project. The approach I took was to make my own scheduler that takes the delegate, adds it to my own queue, and runs them to handle the synchronization at the end, etc.

The "trick" I've used in this case is to not call the delegate directly on the thread pool, but rather call a method in my scheduler that wraps the delegate and handles the exception more gracefully. This way, the actual, internal method call is always handled in an appropriate (for me) manner.

When an exception happens, my scheduler is notified and stops scheduling future tasks (which is a nice bonus), but also takes care of telling the caller that there was a single exception.



Related Topics



Leave a reply



Submit