#include "config.h"
#include "WebHeapAgent.h"
#include <wtf/RunLoop.h>
namespace WebCore {
using namespace Inspector;
struct GarbageCollectionData {
Inspector::Protocol::Heap::GarbageCollection::Type type;
Seconds startTime;
Seconds endTime;
};
class SendGarbageCollectionEventsTask {
public:
SendGarbageCollectionEventsTask(WebHeapAgent&);
void addGarbageCollection(GarbageCollectionData&&);
void reset();
private:
void timerFired();
WebHeapAgent& m_agent;
Vector<GarbageCollectionData> m_collections;
RunLoop::Timer<SendGarbageCollectionEventsTask> m_timer;
Lock m_mutex;
};
SendGarbageCollectionEventsTask::SendGarbageCollectionEventsTask(WebHeapAgent& agent)
: m_agent(agent)
, m_timer(RunLoop::main(), this, &SendGarbageCollectionEventsTask::timerFired)
{
}
void SendGarbageCollectionEventsTask::addGarbageCollection(GarbageCollectionData&& collection)
{
{
std::lock_guard<Lock> lock(m_mutex);
m_collections.append(WTFMove(collection));
}
if (!m_timer.isActive())
m_timer.startOneShot(0_s);
}
void SendGarbageCollectionEventsTask::reset()
{
{
std::lock_guard<Lock> lock(m_mutex);
m_collections.clear();
}
m_timer.stop();
}
void SendGarbageCollectionEventsTask::timerFired()
{
Vector<GarbageCollectionData> collectionsToSend;
{
std::lock_guard<Lock> lock(m_mutex);
m_collections.swap(collectionsToSend);
}
m_agent.dispatchGarbageCollectionEventsAfterDelay(WTFMove(collectionsToSend));
}
WebHeapAgent::WebHeapAgent(Inspector::AgentContext& context)
: InspectorHeapAgent(context)
, m_sendGarbageCollectionEventsTask(std::make_unique<SendGarbageCollectionEventsTask>(*this))
{
}
WebHeapAgent::~WebHeapAgent()
{
m_sendGarbageCollectionEventsTask->reset();
}
void WebHeapAgent::disable(ErrorString& errorString)
{
m_sendGarbageCollectionEventsTask->reset();
InspectorHeapAgent::disable(errorString);
}
void WebHeapAgent::dispatchGarbageCollectedEvent(Inspector::Protocol::Heap::GarbageCollection::Type type, Seconds startTime, Seconds endTime)
{
GarbageCollectionData data = {type, startTime, endTime};
m_sendGarbageCollectionEventsTask->addGarbageCollection(WTFMove(data));
}
void WebHeapAgent::dispatchGarbageCollectionEventsAfterDelay(Vector<GarbageCollectionData>&& collections)
{
for (auto& collection : collections)
InspectorHeapAgent::dispatchGarbageCollectedEvent(collection.type, collection.startTime, collection.endTime);
}
}