From 1f97a239dcd77bd29e7d71bb47ac99e45e289814 Mon Sep 17 00:00:00 2001 From: Vinnie Falco Date: Tue, 22 Oct 2013 17:09:58 -0700 Subject: [PATCH] Measure CPU usage in Workers --- beast/chrono/CPUMeter.h | 3 +- beast/threads/ServiceQueue.h | 4 +- modules/beast_core/thread/Workers.cpp | 65 ++++++++++++++++----------- modules/beast_core/thread/Workers.h | 4 ++ 4 files changed, 47 insertions(+), 29 deletions(-) diff --git a/beast/chrono/CPUMeter.h b/beast/chrono/CPUMeter.h index b78da25d7..5d21630a6 100644 --- a/beast/chrono/CPUMeter.h +++ b/beast/chrono/CPUMeter.h @@ -143,9 +143,10 @@ public: typedef ScopedTimeInterval ScopedActiveTime; /** Returns the fraction of time that the CPU is being used. */ - double getUtilizaton () const + double getUtilization () const { SharedState::ConstAccess state (m_state); + double const seconds (state->usage.seconds()); if (seconds > 0) return (state->usage.active.inSeconds() / seconds); diff --git a/beast/threads/ServiceQueue.h b/beast/threads/ServiceQueue.h index 2de4e44e0..715b6c52f 100644 --- a/beast/threads/ServiceQueue.h +++ b/beast/threads/ServiceQueue.h @@ -466,8 +466,8 @@ public: } /** Returns the percentage of time the queue is using the CPU. */ - double getUtilizaton () const - { return m_cpuMeter.getUtilizaton(); } + double getUtilization () const + { return m_cpuMeter.getUtilization(); } /** Returns the allocator associated with the container. */ allocator_type get_allocator() const diff --git a/modules/beast_core/thread/Workers.cpp b/modules/beast_core/thread/Workers.cpp index e856b06d3..576f58866 100644 --- a/modules/beast_core/thread/Workers.cpp +++ b/modules/beast_core/thread/Workers.cpp @@ -111,6 +111,11 @@ int Workers::numberOfCurrentlyRunningTasks () const noexcept return m_runningTaskCount.get (); } +double Workers::getUtilization () const +{ + return m_usage.getUtilization(); +} + void Workers::deleteWorkers (LockFreeStack & stack) { for (;;) @@ -157,36 +162,44 @@ void Workers::Worker::run () { // Acquire a task or "internal task." // - m_workers.m_semaphore.wait (); - - // See if there's a pause request. This - // counts as an "internal task." - // - int pauseCount = m_workers.m_pauseCount.get (); - - if (pauseCount > 0) { - // Try to decrement - pauseCount = --m_workers.m_pauseCount; + CPUMeter::ScopedIdleTime elapsed (m_workers.m_usage); - if (pauseCount >= 0) - { - // We got paused - break; - } - else - { - // Undo our decrement - ++m_workers.m_pauseCount; - } + m_workers.m_semaphore.wait (); } - // We couldn't pause so we must have gotten - // unblocked in order to process a task. - // - ++m_workers.m_runningTaskCount; - m_workers.m_callback.processTask (); - --m_workers.m_runningTaskCount; + { + CPUMeter::ScopedActiveTime elapsed (m_workers.m_usage); + + // See if there's a pause request. This + // counts as an "internal task." + // + int pauseCount = m_workers.m_pauseCount.get (); + + if (pauseCount > 0) + { + // Try to decrement + pauseCount = --m_workers.m_pauseCount; + + if (pauseCount >= 0) + { + // We got paused + break; + } + else + { + // Undo our decrement + ++m_workers.m_pauseCount; + } + } + + // We couldn't pause so we must have gotten + // unblocked in order to process a task. + // + ++m_workers.m_runningTaskCount; + m_workers.m_callback.processTask (); + --m_workers.m_runningTaskCount; + } // Put the name back in case the callback changed it Thread::setCurrentThreadName (m_threadName); diff --git a/modules/beast_core/thread/Workers.h b/modules/beast_core/thread/Workers.h index 8c072f0a6..ba50b50de 100644 --- a/modules/beast_core/thread/Workers.h +++ b/modules/beast_core/thread/Workers.h @@ -93,6 +93,9 @@ public: */ int numberOfCurrentlyRunningTasks () const noexcept; + /** Returns the fraction of time that the CPU is being used. */ + double getUtilization () const; + //-------------------------------------------------------------------------- private: @@ -129,6 +132,7 @@ private: private: Callback& m_callback; + CPUMeter m_usage; // CPU utilization across threads String m_threadNames; // The name to give each thread WaitableEvent m_allPaused; // signaled when all threads paused Semaphore m_semaphore; // each pending task is 1 resource