Crate poolio

source ·
Expand description

poolio is a thread-pool-implementation using only channels for concurrency.

Design

A poolio-thread-pool is essentially made up by a ‘supervisor’-thread and a specified number of ‘worker’-threads. A worker’s only purpose is executing jobs (in the guise of closures) while the supervisor is responsible for anything else like - most importantly - assigning jobs to workers it gets from outside the pool via the public API. To this end the thread-pool is set up in such a way that the supervisor can communicate with each worker seperately but concurrently. This, in particular, ensures that each worker is equally busy. A single supervisor-worker-communication is roughly as follows:

  1. worker tells its current status to the supervisor
  2. supervisor decides what to tell the worker to do on the basis of the current order-message from outside the pool and the worker-status
  3. supervisor tells the work what to do
  4. worker tries to do what it was told by the supervisor
  5. worker tells its current status to the supervisor

The following graphic illustrates the aformentioned communication-model of a supervisor-thread S and a worker-thread W:

   W
   _
   .
   .
   send-status
   .   O
   .     O
   .       O                 send-message
   .         O                   O
   .           O               O
   recv         recv         O
  * .  O       O  . .      O
 .   .   O   O   .   .   O
.     e    O    m     recv . . | S
 .   .   O   O   .   *
  . .  O       O  . .
   send-status  send-message

X | . . * : arrow starting at | and ending at * representing the control-flow of thread X
O O O O O : channel
e : execute job
m : manage workers

Usage

To use a poolio-ThreadPool you simply have to set one up using the ThreadPool::new-method and task the pool to run jobs using the ThreadPool::execute-method.

Examples

Setting up a pool to make some server multi-threaded:

fn handle(req: usize) {
    println!("Handled!")
}

let server_requests = [1, 2, 3, 4, 5, 6, 7, 8, 9];

let pool = poolio::ThreadPool::new(3, poolio::PanicSwitch::Kill).unwrap();

for req in server_requests {
    pool.execute(move || {
        handle(req);
    });
}

Structs

Abstracts the thread-pools.

Enums

Configures what the ThreadPool is supposed to do in case of a ‘panicking job’, that is, a job which panics while running in a thread.