libfoedus-core
FOEDUS Core Library
foedus::thread::ThreadPool Class Referencefinal

The pool of pre-allocated threads in the engine to execute transactions. More...

Detailed Description

The pool of pre-allocated threads in the engine to execute transactions.

This is the main API class of thread package. Its gut is impersonate() which allows client programs to create a new session (ImpersonateSession) that runs user-defined procedures (System and User Procedures). The sessions are executed on pre-allocated threads in the engine. We throttle sessions, meaning impersonate() blocks when there is no available thread. To avoid waiting too long, impersonate() receives timeout parameter.

Definition at line 127 of file thread_pool.hpp.

#include <thread_pool.hpp>

Inheritance diagram for foedus::thread::ThreadPool:
Collaboration diagram for foedus::thread::ThreadPool:

Public Member Functions

 ThreadPool ()=delete
 
 ThreadPool (Engine *engine)
 
 ~ThreadPool ()
 
ErrorStack initialize () override
 Acquires resources in this object, usually called right after constructor. More...
 
bool is_initialized () const override
 Returns whether the object has been already initialized or not. More...
 
ErrorStack uninitialize () override
 An idempotent method to release all resources of this object, if any. More...
 
bool impersonate (const proc::ProcName &proc_name, const void *task_input, uint64_t task_input_size, ImpersonateSession *session)
 Impersonate as one of pre-allocated threads in this engine, executing the procedure on the impersonated thread (NOT the current thread). More...
 
ErrorStack impersonate_synchronous (const proc::ProcName &proc_name, const void *task_input=nullptr, uint64_t task_input_size=0)
 A shorthand for impersonating a session and synchronously waiting for its end. More...
 
bool impersonate_on_numa_node (ThreadGroupId node, const proc::ProcName &proc_name, const void *task_input, uint64_t task_input_size, ImpersonateSession *session)
 Overload to specify a NUMA node to run on. More...
 
ErrorStack impersonate_on_numa_node_synchronous (ThreadGroupId node, const proc::ProcName &proc_name, const void *task_input=nullptr, uint64_t task_input_size=0)
 A shorthand for impersonating a session and synchronously waiting for its end. More...
 
bool impersonate_on_numa_core (ThreadId core, const proc::ProcName &proc_name, const void *task_input, uint64_t task_input_size, ImpersonateSession *session)
 Overload to specify a core to run on. More...
 
ErrorStack impersonate_on_numa_core_synchronous (ThreadId core, const proc::ProcName &proc_name, const void *task_input=nullptr, uint64_t task_input_size=0)
 A shorthand for impersonating a session and synchronously waiting for its end. More...
 
ThreadPoolPimplget_pimpl () const
 Returns the pimpl of this object. More...
 
ThreadGroupRefget_group_ref (ThreadGroupId numa_node)
 
ThreadRefget_thread_ref (ThreadId id)
 
- Public Member Functions inherited from foedus::Initializable
virtual ~Initializable ()
 

Friends

std::ostream & operator<< (std::ostream &o, const ThreadPool &v)
 

Constructor & Destructor Documentation

foedus::thread::ThreadPool::ThreadPool ( )
delete
foedus::thread::ThreadPool::ThreadPool ( Engine engine)
explicit

Definition at line 28 of file thread_pool.cpp.

28  : pimpl_(nullptr) {
29  pimpl_ = new ThreadPoolPimpl(engine);
30 }
foedus::thread::ThreadPool::~ThreadPool ( )

Definition at line 31 of file thread_pool.cpp.

31  {
32  delete pimpl_;
33  pimpl_ = nullptr;
34 }

Member Function Documentation

ThreadGroupRef * foedus::thread::ThreadPool::get_group_ref ( ThreadGroupId  numa_node)

Definition at line 66 of file thread_pool.cpp.

References foedus::thread::ThreadPoolPimpl::get_group().

Referenced by foedus::xct::XctManagerPimpl::handle_epoch_chime_wait_grace_period().

66  {
67  return pimpl_->get_group(numa_node);
68 }
ThreadGroupRef * get_group(ThreadGroupId numa_node)

Here is the call graph for this function:

Here is the caller graph for this function:

ThreadPoolPimpl* foedus::thread::ThreadPool::get_pimpl ( ) const
inline

Returns the pimpl of this object.

Use it only when you know what you are doing.

Definition at line 237 of file thread_pool.hpp.

Referenced by foedus::thread::ThreadPimpl::get_thread_ref(), and foedus::log::Logger::initialize_once().

237 { return pimpl_; }

Here is the caller graph for this function:

ThreadRef * foedus::thread::ThreadPool::get_thread_ref ( ThreadId  id)

Definition at line 70 of file thread_pool.cpp.

References foedus::thread::ThreadPoolPimpl::get_thread().

70  {
71  return pimpl_->get_thread(id);
72 }
ThreadRef * get_thread(ThreadId id)

Here is the call graph for this function:

bool foedus::thread::ThreadPool::impersonate ( const proc::ProcName proc_name,
const void *  task_input,
uint64_t  task_input_size,
ImpersonateSession session 
)

Impersonate as one of pre-allocated threads in this engine, executing the procedure on the impersonated thread (NOT the current thread).

Parameters
[in]proc_namethe name of the procedure to run on this thread.
[in]task_inputinput data of arbitrary format for the procedure.
[in]task_input_sizebyte size of the input data to copy into the thread's memory.
[out]sessionthe session to run on this thread. On success, the session receives a ticket so that the caller can wait for the completion.

This is similar to launch a new thread that calls the functor. The difference is that this doesn't actually create a thread (which is very expensive) but instead just impersonates as one of the pre-allocated threads in the engine.

Returns
whether successfully impersonated.

Definition at line 40 of file thread_pool.cpp.

References foedus::thread::ThreadPoolPimpl::impersonate().

Referenced by impersonate_synchronous().

44  {
45  return pimpl_->impersonate(proc_name, task_input, task_input_size, session);
46 }
bool impersonate(const proc::ProcName &proc_name, const void *task_input, uint64_t task_input_size, ImpersonateSession *session)

Here is the call graph for this function:

Here is the caller graph for this function:

bool foedus::thread::ThreadPool::impersonate_on_numa_core ( ThreadId  core,
const proc::ProcName proc_name,
const void *  task_input,
uint64_t  task_input_size,
ImpersonateSession session 
)

Overload to specify a core to run on.

See also
impersonate()

Definition at line 57 of file thread_pool.cpp.

References foedus::thread::ThreadPoolPimpl::impersonate_on_numa_core().

Referenced by impersonate_on_numa_core_synchronous().

62  {
63  return pimpl_->impersonate_on_numa_core(core, proc_name, task_input, task_input_size, session);
64 }
bool impersonate_on_numa_core(ThreadId core, const proc::ProcName &proc_name, const void *task_input, uint64_t task_input_size, ImpersonateSession *session)

Here is the call graph for this function:

Here is the caller graph for this function:

ErrorStack foedus::thread::ThreadPool::impersonate_on_numa_core_synchronous ( ThreadId  core,
const proc::ProcName proc_name,
const void *  task_input = nullptr,
uint64_t  task_input_size = 0 
)
inline

A shorthand for impersonating a session and synchronously waiting for its end.

See also
impersonate_synchronous()

Definition at line 224 of file thread_pool.hpp.

References ERROR_STACK, foedus::thread::ImpersonateSession::get_result(), impersonate_on_numa_core(), and foedus::kErrorCodeThrNoThreadAvailable.

228  {
229  ImpersonateSession session;
230  if (!impersonate_on_numa_core(core, proc_name, task_input, task_input_size, &session)) {
232  }
233  return session.get_result();
234  }
#define ERROR_STACK(e)
Instantiates ErrorStack with the given foedus::error_code, creating an error stack with the current f...
bool impersonate_on_numa_core(ThreadId core, const proc::ProcName &proc_name, const void *task_input, uint64_t task_input_size, ImpersonateSession *session)
Overload to specify a core to run on.
Definition: thread_pool.cpp:57
0x0E01 : "THREAD : No worker thread is available for impersonation." .
Definition: error_code.hpp:242

Here is the call graph for this function:

bool foedus::thread::ThreadPool::impersonate_on_numa_node ( ThreadGroupId  node,
const proc::ProcName proc_name,
const void *  task_input,
uint64_t  task_input_size,
ImpersonateSession session 
)

Overload to specify a NUMA node to run on.

See also
impersonate()

Definition at line 48 of file thread_pool.cpp.

References foedus::thread::ThreadPoolPimpl::impersonate_on_numa_node().

Referenced by impersonate_on_numa_node_synchronous().

53  {
54  return pimpl_->impersonate_on_numa_node(node, proc_name, task_input, task_input_size, session);
55 }
bool impersonate_on_numa_node(ThreadGroupId node, const proc::ProcName &proc_name, const void *task_input, uint64_t task_input_size, ImpersonateSession *session)

Here is the call graph for this function:

Here is the caller graph for this function:

ErrorStack foedus::thread::ThreadPool::impersonate_on_numa_node_synchronous ( ThreadGroupId  node,
const proc::ProcName proc_name,
const void *  task_input = nullptr,
uint64_t  task_input_size = 0 
)
inline

A shorthand for impersonating a session and synchronously waiting for its end.

See also
impersonate_synchronous()

Definition at line 197 of file thread_pool.hpp.

References ERROR_STACK, foedus::thread::ImpersonateSession::get_result(), impersonate_on_numa_node(), and foedus::kErrorCodeThrNoThreadAvailable.

201  {
202  ImpersonateSession session;
203  if (!impersonate_on_numa_node(node, proc_name, task_input, task_input_size, &session)) {
205  }
206  return session.get_result();
207  }
#define ERROR_STACK(e)
Instantiates ErrorStack with the given foedus::error_code, creating an error stack with the current f...
0x0E01 : "THREAD : No worker thread is available for impersonation." .
Definition: error_code.hpp:242
bool impersonate_on_numa_node(ThreadGroupId node, const proc::ProcName &proc_name, const void *task_input, uint64_t task_input_size, ImpersonateSession *session)
Overload to specify a NUMA node to run on.
Definition: thread_pool.cpp:48

Here is the call graph for this function:

ErrorStack foedus::thread::ThreadPool::impersonate_synchronous ( const proc::ProcName proc_name,
const void *  task_input = nullptr,
uint64_t  task_input_size = 0 
)
inline

A shorthand for impersonating a session and synchronously waiting for its end.

Useful for a single and synchronous task invocation. This is equivalent to the following impersonate() invocation.

ImpersonateSession session;
if (!pool.impersonate(proc_name, task_input, task_input_size, &session)) {
}
return session.get_result();

{.cpp}

Returns
Error code of the impersonation or (if impersonation succeeds) of the task. This returns kRetOk iff impersonation and the task succeed.

Definition at line 171 of file thread_pool.hpp.

References ERROR_STACK, foedus::thread::ImpersonateSession::get_result(), impersonate(), and foedus::kErrorCodeThrNoThreadAvailable.

174  {
175  ImpersonateSession session;
176  if (!impersonate(proc_name, task_input, task_input_size, &session)) {
178  }
179  return session.get_result();
180  }
#define ERROR_STACK(e)
Instantiates ErrorStack with the given foedus::error_code, creating an error stack with the current f...
0x0E01 : "THREAD : No worker thread is available for impersonation." .
Definition: error_code.hpp:242
bool impersonate(const proc::ProcName &proc_name, const void *task_input, uint64_t task_input_size, ImpersonateSession *session)
Impersonate as one of pre-allocated threads in this engine, executing the procedure on the impersonat...
Definition: thread_pool.cpp:40

Here is the call graph for this function:

ErrorStack foedus::thread::ThreadPool::initialize ( )
overridevirtual

Acquires resources in this object, usually called right after constructor.

Precondition
is_initialized() == FALSE

If and only if the return value was not an error, is_initialized() will return TRUE. This method is usually not idempotent, but some implementation can choose to be. In that case, the implementation class should clarify that it's idempotent. This method is responsible for releasing all acquired resources when initialization fails. This method itself is NOT thread-safe. Do not call this in a racy situation.

Implements foedus::Initializable.

Definition at line 36 of file thread_pool.cpp.

References foedus::DefaultInitializable::initialize().

36 { return pimpl_->initialize(); }
ErrorStack initialize() override final
Typical implementation of Initializable::initialize() that provides initialize-once semantics...

Here is the call graph for this function:

bool foedus::thread::ThreadPool::is_initialized ( ) const
overridevirtual

Returns whether the object has been already initialized or not.

Implements foedus::Initializable.

Definition at line 37 of file thread_pool.cpp.

References foedus::DefaultInitializable::is_initialized().

Referenced by foedus::storage::StorageManagerPimpl::initialize_once(), foedus::log::LogManagerPimpl::initialize_once(), foedus::storage::StorageManagerPimpl::uninitialize_once(), and foedus::log::LogManagerPimpl::uninitialize_once().

37 { return pimpl_->is_initialized(); }
bool is_initialized() const override final
Returns whether the object has been already initialized or not.

Here is the call graph for this function:

Here is the caller graph for this function:

ErrorStack foedus::thread::ThreadPool::uninitialize ( )
overridevirtual

An idempotent method to release all resources of this object, if any.

After this method, is_initialized() will return FALSE. Whether this method encounters an error or not, the implementation should make the best effort to release as many resources as possible. In other words, Do not leak all resources because of one issue. This method itself is NOT thread-safe. Do not call this in a racy situation.

Attention
This method is NOT automatically called from the destructor. This is due to the fundamental limitation in C++. Explicitly call this method as soon as you are done, checking the returned value. You can also use UninitializeGuard to ameliorate the issue, but it's not perfect.
Returns
The error this method encounters, if any. In case there are multiple errors while uninitialization, the implementation should use ErrorStackBatch to produce a batched ErrorStack object.

Implements foedus::Initializable.

Definition at line 38 of file thread_pool.cpp.

References foedus::DefaultInitializable::uninitialize().

38 { return pimpl_->uninitialize(); }
ErrorStack uninitialize() override final
Typical implementation of Initializable::uninitialize() that provides uninitialize-once semantics...

Here is the call graph for this function:

Friends And Related Function Documentation

std::ostream& operator<< ( std::ostream &  o,
const ThreadPool v 
)
friend

Definition at line 75 of file thread_pool.cpp.

75  {
76  o << *v.pimpl_;
77  return o;
78 }

The documentation for this class was generated from the following files: