private void EventConsumer() { while (!Disposed) { CounterQueueEvent evt = null; lock (_lock) { if (_events.Count > 0) { evt = _events.Dequeue(); } } if (evt == null) { _queuedEvent.WaitOne(); // No more events to go through, wait for more. } else { // Spin-wait rather than sleeping if there are any waiters, by passing null instead of the wake signal. evt.TryConsume(ref _accumulatedCounter, true, _waiterCount == 0 ? _wakeSignal : null); } if (_waiterCount > 0) { _eventConsumed.Set(); } } }
public void FlushTo(CounterQueueEvent evt) { lock (_lock) { if (evt.Disposed) { return; } // Tell the queue to process all events up to this one. while (_events.Count > 0) { CounterQueueEvent flush = _events.Peek(); if (flush.DrawIndex > evt.DrawIndex) { return; } _events.Dequeue(); flush.TryConsume(ref _accumulatedCounter, true); if (flush == evt) { return; } } } }
public void Flush(bool blocking) { if (!blocking) { // Just wake the consumer thread - it will update the queries. _wakeSignal.Set(); return; } lock (_lock) { // Tell the queue to process all events. while (_events.Count > 0) { CounterQueueEvent flush = _events.Peek(); if (!flush.TryConsume(ref _accumulatedCounter, true)) { return; // If not blocking, then return when we encounter an event that is not ready yet. } _events.Dequeue(); } } }
private void EventConsumer() { while (!Disposed) { CounterQueueEvent evt = null; lock (_lock) { if (_events.Count > 0) { evt = _events.Dequeue(); } } if (evt == null) { _queuedEvent.WaitOne(); // No more events to go through, wait for more. } else { evt.TryConsume(ref _accumulatedCounter, true, _wakeSignal); } } }