100 lines
2.0 KiB
C++
100 lines
2.0 KiB
C++
#pragma once
|
|
|
|
#include "RuntimeEvent.h"
|
|
|
|
#include <chrono>
|
|
#include <cstddef>
|
|
#include <deque>
|
|
#include <mutex>
|
|
#include <vector>
|
|
|
|
struct RuntimeEventQueueMetrics
|
|
{
|
|
std::size_t depth = 0;
|
|
std::size_t capacity = 0;
|
|
std::size_t droppedCount = 0;
|
|
double oldestEventAgeMilliseconds = 0.0;
|
|
};
|
|
|
|
class RuntimeEventQueue
|
|
{
|
|
public:
|
|
explicit RuntimeEventQueue(std::size_t capacity = 1024) :
|
|
mCapacity(capacity)
|
|
{
|
|
}
|
|
|
|
bool Push(RuntimeEvent event)
|
|
{
|
|
std::lock_guard<std::mutex> lock(mMutex);
|
|
if (mEvents.size() >= mCapacity)
|
|
{
|
|
++mDroppedCount;
|
|
return false;
|
|
}
|
|
|
|
mEvents.push_back(std::move(event));
|
|
return true;
|
|
}
|
|
|
|
bool TryPop(RuntimeEvent& event)
|
|
{
|
|
std::lock_guard<std::mutex> lock(mMutex);
|
|
if (mEvents.empty())
|
|
return false;
|
|
|
|
event = std::move(mEvents.front());
|
|
mEvents.pop_front();
|
|
return true;
|
|
}
|
|
|
|
std::vector<RuntimeEvent> Drain(std::size_t maxEvents = 0)
|
|
{
|
|
std::vector<RuntimeEvent> events;
|
|
|
|
std::lock_guard<std::mutex> lock(mMutex);
|
|
const std::size_t count = maxEvents == 0 || maxEvents > mEvents.size() ? mEvents.size() : maxEvents;
|
|
events.reserve(count);
|
|
for (std::size_t index = 0; index < count; ++index)
|
|
{
|
|
events.push_back(std::move(mEvents.front()));
|
|
mEvents.pop_front();
|
|
}
|
|
|
|
return events;
|
|
}
|
|
|
|
RuntimeEventQueueMetrics GetMetrics(std::chrono::steady_clock::time_point now = std::chrono::steady_clock::now()) const
|
|
{
|
|
std::lock_guard<std::mutex> lock(mMutex);
|
|
|
|
RuntimeEventQueueMetrics metrics;
|
|
metrics.depth = mEvents.size();
|
|
metrics.capacity = mCapacity;
|
|
metrics.droppedCount = mDroppedCount;
|
|
if (!mEvents.empty())
|
|
{
|
|
const auto age = now - mEvents.front().createdAt;
|
|
metrics.oldestEventAgeMilliseconds = std::chrono::duration<double, std::milli>(age).count();
|
|
}
|
|
return metrics;
|
|
}
|
|
|
|
std::size_t Depth() const
|
|
{
|
|
std::lock_guard<std::mutex> lock(mMutex);
|
|
return mEvents.size();
|
|
}
|
|
|
|
std::size_t Capacity() const
|
|
{
|
|
return mCapacity;
|
|
}
|
|
|
|
private:
|
|
mutable std::mutex mMutex;
|
|
std::deque<RuntimeEvent> mEvents;
|
|
std::size_t mCapacity = 0;
|
|
std::size_t mDroppedCount = 0;
|
|
};
|