/// <summary> /// Launches the worker threads and waits for them to complete. /// </summary> /// <param name="data">The threading data.</param> /// <param name="count">The number of threads to create.</param> /// <returns>Returns a value indicating whether analysis of all /// files has been completed. If this returns false, another round /// of analysis must be performed.</returns> private bool RunWorkerThreads(StyleCopThread.Data data, int count) { Param.AssertNotNull(data, "data"); Param.AssertGreaterThanZero(count, "count"); // Indicates whether total sanalysis of all files has been completed. bool complete = true; // Create the worker and thread class arrays. BackgroundWorker[] workers = new BackgroundWorker[count]; StyleCopThread[] threadClasses = new StyleCopThread[count]; // Allocate and start all the threads. for (int i = 0; i < count; ++i) { // Allocate the worker classes for this thread. workers[i] = new BackgroundWorker(); threadClasses[i] = new StyleCopThread(data); // Register for events on the background worker class. workers[i].DoWork += new DoWorkEventHandler(threadClasses[i].DoWork); // Register for the completion event on the thread data class. We do not use the standard BackgroundWorker // completion event because for some reason it does not get fired when running inside of Visual Studio using // the MSBuild task, and so everything ends up blocked. This may have to do with the way Visual Studio uses // threads when running a build. Therefore, we do not rely on the BackgroundWorker's completion event, and // instead use our own event. threadClasses[i].ThreadCompleted += new EventHandler<StyleCopThreadCompletedEventArgs>(this.StyleCopThreadCompleted); // Indicate that we are launching another thread. data.IncrementThreadCount(); } // The lock is required so that we can wait on the Monitor. lock (this) { // Start each of the worker threads. for (int i = 0; i < count; ++i) { workers[i].RunWorkerAsync(); } // Wait for the threads to complete. Monitor.Wait(this); } // Dispose the workers and determine whether all analysis is complete. for (int i = 0; i < count; ++i) { workers[i].Dispose(); if (!threadClasses[i].Complete) { complete = false; } } return complete; }
private bool RunWorkerThreads(StyleCopThread.Data data, int count) { bool flag = true; BackgroundWorker[] workerArray = new BackgroundWorker[count]; StyleCopThread[] threadArray = new StyleCopThread[count]; for (int i = 0; i < count; i++) { workerArray[i] = new BackgroundWorker(); threadArray[i] = new StyleCopThread(data); workerArray[i].DoWork += new DoWorkEventHandler(threadArray[i].DoWork); threadArray[i].ThreadCompleted += new EventHandler<StyleCopThreadCompletedEventArgs>(this.StyleCopThreadCompleted); data.IncrementThreadCount(); } lock (this) { for (int k = 0; k < count; k++) { workerArray[k].RunWorkerAsync(); } Monitor.Wait(this); } for (int j = 0; j < count; j++) { workerArray[j].Dispose(); if (!threadArray[j].Complete) { flag = false; } } return flag; }