/// <summary> /// Executes the provided evaluator. If a result is obtained before RunTimeout milliseconds, /// the method ends returning True. /// If it does not finish after RunTimeout milliseconds, the method ends retuning False, although /// the evaluation continues in the background. In that case, when evaluation ends, the provided /// delayedDoneCallback delegate is called. /// </summary> public bool Run(EvaluatorDelegate evaluator, EvaluatorDelegate delayedDoneCallback) { if (!UseTimeout) { SafeRun(evaluator); return(true); } Task task = new Task(); task.Evaluator = evaluator; task.FinishedCallback = delayedDoneCallback; lock (runningLock) { if (disposed) { return(false); } if (busyThreads == runningThreads && runningThreads < maxThreads) { runningThreads++; var tr = new Thread(Runner); tr.Name = "Debugger evaluator " + threadNameId++; tr.IsBackground = true; tr.Start(); } pendingTasks.Enqueue(task); if (busyThreads == runningThreads) { task.TimedOut = true; return(false); } newTaskEvent.Set(); } WaitHandle.WaitAny(new WaitHandle [] { task.RunningEvent, disposedEvent }); if (WaitHandle.WaitAny(new WaitHandle [] { task.RunFinishedEvent, disposedEvent }, TimeSpan.FromMilliseconds(RunTimeout), false) != 0) { lock (task) { if (task.Processed) { return(true); } else { task.TimedOut = true; return(false); } } } return(true); }
/// <summary> /// Executes the provided evaluator. If a result is obtained before RunTimeout milliseconds, /// the method ends returning True. /// If it does not finish after RunTimeout milliseconds, the method ends retuning False, although /// the evaluation continues in the background. In that case, when evaluation ends, the provided /// delayedDoneCallback delegate is called. /// </summary> public bool Run (EvaluatorDelegate evaluator, EvaluatorDelegate delayedDoneCallback) { if (!useTimeout) { SafeRun (evaluator); return true; } Task task = new Task (); task.Evaluator = evaluator; task.FinishedCallback = delayedDoneCallback; lock (runningLock) { if (disposed) return false; if (mainThreadBusy || runningThreads == 0) { if (runningThreads < maxThreads) { runningThreads++; Thread tr = new Thread (Runner); tr.Name = "Debugger evaluator"; tr.IsBackground = true; tr.Start (); } else { // The main thread is busy evaluating and we can't tell // how much time it will take, so we can't wait for it. task.TimedOut = true; pendingTasks.Enqueue (task); return false; } } mainThreadBusy = true; currentTask = task; } OnStartEval (); newTaskEvent.Set (); task.RunningEvent.WaitOne (); lock (task) { if (!task.RunFinishedEvent.WaitOne (RunTimeout, false)) { task.TimedOut = true; return false; } else { lock (runningLock) { mainThreadBusy = false; Monitor.PulseAll (runningLock); } } } return true; }
void SafeRun (EvaluatorDelegate del) { try { del (); } catch { } }
/// <summary> /// Executes the provided evaluator. If a result is obtained before RunTimeout milliseconds, /// the method ends returning True. /// If it does not finish after RunTimeout milliseconds, the method ends retuning False, although /// the evaluation continues in the background. In that case, when evaluation ends, the provided /// delayedDoneCallback delegate is called. /// </summary> public bool Run(EvaluatorDelegate evaluator, EvaluatorDelegate delayedDoneCallback) { if (!useTimeout) { SafeRun(evaluator); return(true); } Task task = new Task(); task.Evaluator = evaluator; task.FinishedCallback = delayedDoneCallback; lock (runningLock) { if (disposed) { return(false); } if (mainThreadBusy || runningThreads == 0) { if (runningThreads < maxThreads) { runningThreads++; Thread tr = new Thread(Runner); tr.Name = "Debugger evaluator"; tr.IsBackground = true; tr.Start(); } else { // The main thread is busy evaluating and we can't tell // how much time it will take, so we can't wait for it. task.TimedOut = true; pendingTasks.Enqueue(task); return(false); } } mainThreadBusy = true; currentTask = task; } OnStartEval(); newTaskEvent.Set(); task.RunningEvent.WaitOne(); lock (task) { if (!task.RunFinishedEvent.WaitOne(RunTimeout, false)) { task.TimedOut = true; return(false); } else { lock (runningLock) { mainThreadBusy = false; Monitor.PulseAll(runningLock); } } } return(true); }
/// <summary> /// Executes the provided evaluator. If a result is obtained before RunTimeout milliseconds, /// the method ends returning True. /// If it does not finish after RunTimeout milliseconds, the method ends retuning False, although /// the evaluation continues in the background. In that case, when evaluation ends, the provided /// delayedDoneCallback delegate is called. /// </summary> public bool Run(EvaluatorDelegate evaluator, EvaluatorDelegate delayedDoneCallback) { if (!useTimeout) { SafeRun (evaluator); return true; } Task task = new Task (); task.Evaluator = evaluator; task.FinishedCallback = delayedDoneCallback; lock (runningLock) { if (disposed) return false; if (busyThreads == runningThreads && runningThreads < maxThreads) { runningThreads++; var tr = new Thread (Runner); tr.Name = "Debugger evaluator " + threadNameId++; tr.IsBackground = true; tr.Start (); } pendingTasks.Enqueue (task); if (busyThreads == runningThreads) { task.TimedOut = true; return false; } newTaskEvent.Set (); } WaitHandle.WaitAny (new WaitHandle [] { task.RunningEvent, disposedEvent }); if (WaitHandle.WaitAny (new WaitHandle [] { task.RunFinishedEvent, disposedEvent }, TimeSpan.FromMilliseconds (RunTimeout), false) != 0) { lock (task) { if (task.Processed) { return true; } else { task.TimedOut = true; return false; } } } return true; }