I perform parallel operations on the list of computers that I get from ActiveDirectory. I used this method to check the status of a PC, for example, if the computer was online, or if a specific directory exists. However, due to the nature of these sometimes slow operations, I wanted to enable a timeout so that my application could continue.
public static T MethodTimeout<T>(Func<T> f, int timeout, out bool completed) { T result = default(T); var thread = new Thread(() => result = F()); thread.Start(); Completed = thread.Join(Timeout); if (!Completed) thread.Abort(); return result; }
This works for the most part, but the use of processing seems to have increased slightly, and in some cases I have run into memory exceptions. Therefore, I have since changed the way we use tasks in the hope that ThreadPool will fix the above problems:
public static T MethodTimeout<T>(Func<T> f, int timeout, out bool completed) { T result = default(T); var timedTask = Task.Factory.StartNew(() => result = F()); Completed = timedTask.Wait(Timeout); return result; }
However, I have a feeling that I am just populating ThreadPool with processes that are hanging up, waiting for the completion of these potentially long tasks. Since I pass the task function as a parameter, I see no way to use the cancel token, however my experience is very limited to these classes, and I could skip some excellent methods.
This is how I used the method above:
bool isReachable; // Check if the directory exists (1 second) MethodTimeout(() => Directory.Exists(startDirectory), 1000, out isReachable);
Quick note. I perform the above verification only after I have already confirmed that the computer is connected through a WMI call (also using MethodTimeout). I am well aware of my early testing that checking a directory before this becomes incredibly inefficient.
I, too, of course, am open to disrupt my approach with something better. My loyalty is in the number of operations per second, and not just in what I could come up with.