private void Evaluate(Chromosome chromosome) { SocketPoolItem socketPoolItem = null; try { //Get a connected socket from the socket collection. As this is a blocking collection //wrapping a concurrent queue, then '_sockets.Take()' will remove the next item (Socket) //from the queue. If nothing is on the queue the task will wait (block). This is by //design as the task(s) that call this method (one worker per endpoint) are defined //as long running tasks. //use the connected socket and then pop it back on the queue. //this ensures that only unused sockets are selected. socketPoolItem = _socketPool.Dequeue(); Log.Debug(string.Format("SocketPoolItem: {0} retrieved from the pool.", socketPoolItem.EndPoint)); //if not connected, attempt to reconnect if (!socketPoolItem.Socket.Connected) { Log.Debug(string.Format("SocketPoolItem: {0} not connected, attempting to re-connect.", socketPoolItem.EndPoint)); socketPoolItem = new SocketPoolItem( SocketClient.Connect(socketPoolItem.EndPoint), socketPoolItem.EndPoint); } else { Log.Debug(string.Format("SocketPoolItem: {0} connected.", socketPoolItem.EndPoint)); } //pass the socket to the fitness function using the tag property chromosome.Tag = socketPoolItem; chromosome.Evaluate(RemoteFitnessDelegateFunction); } catch (Exception ex) { if (socketPoolItem != null && socketPoolItem.Socket != null && socketPoolItem.EndPoint != null) { Log.Error(string.Format("{0} [Socket:{1}]", ex.Message, socketPoolItem.EndPoint)); } else { Log.Error(ex); } var task = _pcQueue.Enqueue(() => Evaluate(chromosome)); Log.Debug(string.Format("Chromosome [{0}] evaluation re-queued as Task {1} queued.", chromosome.Id, task.Id)); throw; } finally { //finished with the endpoint so pop it back in the list to be used by this or another worker _socketPool.Enqueue(socketPoolItem); } }