19#include <boost/shared_ptr.hpp>
33HttpThreadPool::HttpThreadPool(
IOServicePtr io_service,
size_t pool_size,
35 : pool_size_(pool_size), io_service_(io_service),
36 run_state_(
State::STOPPED), mutex_(), thread_cv_(),
37 main_cv_(), paused_(0), running_(0), exited_(0) {
73HttpThreadPool::getState() {
74 std::lock_guard<std::mutex> lck(mutex_);
79HttpThreadPool::validateStateChange(
State state)
const {
92HttpThreadPool::stateToText(
State state) {
95 return (std::string(
"stopped"));
97 return (std::string(
"running"));
99 return (std::string(
"paused"));
101 return (std::string(
"unknown-state"));
110HttpThreadPool::checkPermissions(
State state) {
111 auto id = std::this_thread::get_id();
112 if (checkThreadId(
id)) {
114 << HttpThreadPool::stateToText(state) <<
" performed by worker thread");
119HttpThreadPool::checkThreadId(std::thread::id
id) {
120 for (
auto thread : threads_) {
121 if (
id == thread->get_id()) {
129HttpThreadPool::setState(
State state) {
130 checkPermissions(state);
132 std::unique_lock<std::mutex> main_lck(mutex_);
135 if (!validateStateChange(state)) {
141 thread_cv_.notify_all();
146 io_service_->restart();
149 while (threads_.size() < pool_size_) {
150 boost::shared_ptr<std::thread> thread(
new std::thread(
151 std::bind(&HttpThreadPool::threadWork,
this)));
154 threads_.push_back(thread);
158 main_cv_.wait(main_lck,
160 return (running_ == threads_.size());
169 if (!io_service_->stopped()) {
175 main_cv_.wait(main_lck,
177 return (paused_ == threads_.size());
185 if (!io_service_->stopped()) {
191 main_cv_.wait(main_lck,
193 return (exited_ == threads_.size());
196 for (
auto const& thread : threads_) {
206HttpThreadPool::threadWork() {
209 switch (getState()) {
212 std::unique_lock<std::mutex> lck(mutex_);
216 if (running_ == pool_size_) {
217 main_cv_.notify_all();
225 std::unique_lock<std::mutex> lck(mutex_);
233 std::unique_lock<std::mutex> lck(mutex_);
237 if (paused_ == threads_.size()) {
238 main_cv_.notify_all();
257 std::unique_lock<std::mutex> lck(mutex_);
261 if (exited_ == threads_.size()) {
262 main_cv_.notify_all();
268 return (io_service_);
278 return (threads_.size());
A generic exception that is thrown if a parameter given to a method is considered invalid in that con...
Exception thrown when a worker thread is trying to stop or pause the respective thread pool (which wo...
The IOService class is a wrapper for the ASIO io_service class.
void pause()
Transitions the pool from RUNNING to PAUSED.
asiolink::IOServicePtr getIOService() const
Fetches the IOService that drives the pool.
uint16_t getPoolSize() const
Fetches the maximum size of the thread pool.
void stop()
Transitions the pool from RUNNING or PAUSED to STOPPED.
void checkPausePermissions()
Check current thread permissions to transition to the new PAUSED state.
~HttpThreadPool()
Destructor.
void run()
Transitions the pool from STOPPED or PAUSED to RUNNING.
uint16_t getThreadCount() const
Fetches the number of threads in the pool.
State
Describes the possible operational state of the thread pool.
@ RUNNING
Pool is not operational.
@ PAUSED
Pool is populated with running threads.
Defines a State within the State Model.
#define isc_throw(type, stream)
A shortcut macro to insert known values into exception arguments.
boost::shared_ptr< IOService > IOServicePtr
Defines a smart pointer to an IOService instance.
Defines the logger used by the top-level component of kea-lfc.