#ifndef _THREAD_POOL_H_
#define _THREAD_POOL_H_
#include <pthread.h>
#ifdef __cplusplus
extern "C" {
#endif
struct t_pool;
struct t_results_queue;
typedef struct t_pool_job {
void *(*func)(void *arg);
void *arg;
struct t_pool_job *next;
struct t_pool *p;
struct t_results_queue *q;
int serial;
} t_pool_job;
typedef struct t_res {
struct t_res *next;
int serial; void *data; } t_pool_result;
struct t_pool;
typedef struct {
struct t_pool *p;
int idx;
pthread_t tid;
pthread_cond_t pending_c;
long long wait_time;
} t_pool_worker_t;
typedef struct t_pool {
int qsize; int njobs; int nwaiting; int shutdown;
t_pool_job *head, *tail;
int tsize; t_pool_worker_t *t;
pthread_mutex_t pool_m;
pthread_cond_t empty_c;
pthread_cond_t pending_c; pthread_cond_t full_c;
int *t_stack, t_stack_top;
long long total_time, wait_time;
} t_pool;
typedef struct t_results_queue {
t_pool_result *result_head;
t_pool_result *result_tail;
int next_serial;
int curr_serial;
int queue_len; int pending; pthread_mutex_t result_m;
pthread_cond_t result_avail_c;
} t_results_queue;
t_pool *t_pool_init(int qsize, int tsize);
int t_pool_dispatch(t_pool *p, t_results_queue *q,
void *(*func)(void *arg), void *arg);
int t_pool_dispatch2(t_pool *p, t_results_queue *q,
void *(*func)(void *arg), void *arg, int nonblock);
int t_pool_flush(t_pool *p);
void t_pool_destroy(t_pool *p, int kill);
t_pool_result *t_pool_next_result(t_results_queue *q);
t_pool_result *t_pool_next_result_wait(t_results_queue *q);
void t_pool_delete_result(t_pool_result *r, int free_data);
t_results_queue *t_results_queue_init(void);
void t_results_queue_destroy(t_results_queue *q);
int t_pool_results_queue_empty(t_results_queue *q);
int t_pool_results_queue_len(t_results_queue *q);
int t_pool_results_queue_sz(t_results_queue *q);
#ifdef __cplusplus
}
#endif
#endif