Index: /trunk/sources/HeuristicLab.BackgroundProcessing/3.2/ObservableBackgroundWorker.cs
===================================================================
--- /trunk/sources/HeuristicLab.BackgroundProcessing/3.2/ObservableBackgroundWorker.cs	(revision 2409)
+++ /trunk/sources/HeuristicLab.BackgroundProcessing/3.2/ObservableBackgroundWorker.cs	(revision 2410)
@@ -37,9 +37,11 @@
     public event PropertyChangedEventHandler PropertyChanged;
 
-    public ObservableBackgroundWorker(string name) {
+    public ObservableBackgroundWorker(string name, WorkerMonitor monitor) {
       Name = name;
-      WorkerMonitor.Default.RegisterWorker(this);
+      monitor.RegisterWorker(this);
       IsRunning = false;
     }
+
+    public ObservableBackgroundWorker(string name) : this(name, WorkerMonitor.Default) { }
 
     protected override void OnProgressChanged(ProgressChangedEventArgs e) {
Index: /trunk/sources/HeuristicLab.BackgroundProcessing/3.2/ObservableEnumerable.cs
===================================================================
--- /trunk/sources/HeuristicLab.BackgroundProcessing/3.2/ObservableEnumerable.cs	(revision 2409)
+++ /trunk/sources/HeuristicLab.BackgroundProcessing/3.2/ObservableEnumerable.cs	(revision 2410)
@@ -10,4 +10,4 @@
   /// </summary>
   /// <typeparam name="T"></typeparam>
-  public interface ObservableEnumerable<T> : IEnumerable<T>, INotifyCollectionChanged where T : class { }
+  public interface IObservableEnumerable<T> : IEnumerable<T>, INotifyCollectionChanged { }
 }
Index: /trunk/sources/HeuristicLab.BackgroundProcessing/3.2/WorkerMonitor.cs
===================================================================
--- /trunk/sources/HeuristicLab.BackgroundProcessing/3.2/WorkerMonitor.cs	(revision 2409)
+++ /trunk/sources/HeuristicLab.BackgroundProcessing/3.2/WorkerMonitor.cs	(revision 2410)
@@ -13,8 +13,15 @@
   /// Provides a list of all currently running or pending ObservableBackgroundWorkers.
   /// </summary>
-  public class WorkerMonitor : ObservableEnumerable<ObservableBackgroundWorker> {
+  public class WorkerMonitor : IObservableEnumerable<ObservableBackgroundWorker> {
+
     public static WorkerMonitor Default = new WorkerMonitor();
 
-    public event ThreadExceptionEventHandler ThreadException;
+    /// <summary>
+    /// Report all unhandled exceptions during background worker execution.
+    /// These exceptions are the same as reported by the RunWorkerCompleted but wrapped
+    /// in an additional exception containing the worker name as message and the original
+    /// exception as inner exception.
+    /// </summary>
+    public event ThreadExceptionEventHandler BackgroundWorkerException;
     public event NotifyCollectionChangedEventHandler CollectionChanged;
 
@@ -72,6 +79,6 @@
 
     protected void OnThreadException(Exception x) {
-      if (ThreadException != null)
-        ThreadException(this, new ThreadExceptionEventArgs(x));
+      if (BackgroundWorkerException != null)
+        BackgroundWorkerException(this, new ThreadExceptionEventArgs(x));
     }
 
@@ -95,21 +102,29 @@
     }
 
-    public void CancelAll() {
-      List<ObservableBackgroundWorker> cancelableWorkers = GetCancelableWorkers();
-      lock (cancelableWorkers) {
-        foreach (var worker in cancelableWorkers.ToList()) {
-          worker.WorkerStopped += (sender, args) => {
-            lock (cancelableWorkers) {
-              cancelableWorkers.Remove((ObservableBackgroundWorker)sender);
-              Monitor.Pulse(cancelableWorkers);
-            }
-          };
-          worker.CancelAsync();
-          if (!worker.IsRunning)
-            cancelableWorkers.Remove(worker);
+    public void CancelAllAsync() {
+      CancelAllAsync(null, null);
+    }
+
+    public void CancelAllAsync(WaitCallback callback, object state) {
+      ThreadPool.QueueUserWorkItem(_ => {
+        List<ObservableBackgroundWorker> cancelableWorkers = GetCancelableWorkers();
+        lock (cancelableWorkers) {
+          foreach (var worker in cancelableWorkers.ToList()) {
+            worker.WorkerStopped += (sender, args) => {
+              lock (cancelableWorkers) {
+                cancelableWorkers.Remove((ObservableBackgroundWorker)sender);
+                Monitor.Pulse(cancelableWorkers);
+              }
+            };
+            worker.CancelAsync();
+            if (!worker.IsRunning)
+              cancelableWorkers.Remove(worker);
+          }
+          while (cancelableWorkers.Count > 0)
+            Monitor.Wait(cancelableWorkers);
         }
-        while (cancelableWorkers.Count > 0)
-          Monitor.Wait(cancelableWorkers);
-      }
+        if (callback != null)
+          callback(state);
+      });
     }
 
