apr_thread_pool.h revision 302408
1/* 2 * Licensed to the Apache Software Foundation (ASF) under one or more 3 * contributor license agreements. See the NOTICE file distributed 4 * with this work for additional information regarding copyright 5 * ownership. The ASF licenses this file to you under the Apache 6 * License, Version 2.0 (the "License"); you may not use this file 7 * except in compliance with the License. You may obtain a copy of 8 * the License at 9 * 10 * http://www.apache.org/licenses/LICENSE-2.0 11 * 12 * Unless required by applicable law or agreed to in writing, software 13 * distributed under the License is distributed on an "AS IS" BASIS, 14 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or 15 * implied. See the License for the specific language governing 16 * permissions and limitations under the License. 17 */ 18 19#ifndef APU_THREAD_POOL_H 20#define APU_THREAD_POOL_H 21 22#include "apu.h" 23#include "apr_thread_proc.h" 24 25/** 26 * @file apr_thread_pool.h 27 * @brief APR Thread Pool Library 28 29 * @remarks This library implements a thread pool using apr_thread_t. A thread 30 * pool is a set of threads that can be created in advance or on demand until a 31 * maximum number. When a task is scheduled, the thread pool will find an idle 32 * thread to handle the task. In case all existing threads are busy and the 33 * number of tasks in the queue is higher than the adjustable threshold, the 34 * pool will try to create a new thread to serve the task if the maximum number 35 * has not been reached. Otherwise, the task will be put into a queue based on 36 * priority, which can be valued from 0 to 255, with higher values being served 37 * first. If there are tasks with the same priority, the new task might be put at 38 * the top or at the bottom - it depends on which function is used to put the task. 39 * 40 * @remarks There may be the case where the thread pool can use up to the maximum 41 * number of threads at peak load, but having those threads idle afterwards. A 42 * maximum number of idle threads can be set so that the extra idling threads will 43 * be terminated to save system resources. 44 */ 45#if APR_HAS_THREADS 46 47#ifdef __cplusplus 48extern "C" { 49#endif /* __cplusplus */ 50 51/** 52 * @defgroup APR_Util_TP Thread Pool routines 53 * @ingroup APR_Util 54 * @{ 55 */ 56 57/** Opaque Thread Pool structure. */ 58typedef struct apr_thread_pool apr_thread_pool_t; 59 60#define APR_THREAD_TASK_PRIORITY_LOWEST 0 61#define APR_THREAD_TASK_PRIORITY_LOW 63 62#define APR_THREAD_TASK_PRIORITY_NORMAL 127 63#define APR_THREAD_TASK_PRIORITY_HIGH 191 64#define APR_THREAD_TASK_PRIORITY_HIGHEST 255 65 66/** 67 * Create a thread pool 68 * @param me The pointer in which to return the newly created apr_thread_pool 69 * object, or NULL if thread pool creation fails. 70 * @param init_threads The number of threads to be created initially, this number 71 * will also be used as the initial value for the maximum number of idle threads. 72 * @param max_threads The maximum number of threads that can be created 73 * @param pool The pool to use 74 * @return APR_SUCCESS if the thread pool was created successfully. Otherwise, 75 * the error code. 76 */ 77APU_DECLARE(apr_status_t) apr_thread_pool_create(apr_thread_pool_t **me, 78 apr_size_t init_threads, 79 apr_size_t max_threads, 80 apr_pool_t *pool); 81 82/** 83 * Destroy the thread pool and stop all the threads 84 * @return APR_SUCCESS if all threads are stopped. 85 */ 86APU_DECLARE(apr_status_t) apr_thread_pool_destroy(apr_thread_pool_t *me); 87 88/** 89 * Schedule a task to the bottom of the tasks of same priority. 90 * @param me The thread pool 91 * @param func The task function 92 * @param param The parameter for the task function 93 * @param priority The priority of the task. 94 * @param owner Owner of this task. 95 * @return APR_SUCCESS if the task had been scheduled successfully 96 */ 97APU_DECLARE(apr_status_t) apr_thread_pool_push(apr_thread_pool_t *me, 98 apr_thread_start_t func, 99 void *param, 100 apr_byte_t priority, 101 void *owner); 102/** 103 * Schedule a task to be run after a delay 104 * @param me The thread pool 105 * @param func The task function 106 * @param param The parameter for the task function 107 * @param time Time in microseconds 108 * @param owner Owner of this task. 109 * @return APR_SUCCESS if the task had been scheduled successfully 110 */ 111APU_DECLARE(apr_status_t) apr_thread_pool_schedule(apr_thread_pool_t *me, 112 apr_thread_start_t func, 113 void *param, 114 apr_interval_time_t time, 115 void *owner); 116 117/** 118 * Schedule a task to the top of the tasks of same priority. 119 * @param me The thread pool 120 * @param func The task function 121 * @param param The parameter for the task function 122 * @param priority The priority of the task. 123 * @param owner Owner of this task. 124 * @return APR_SUCCESS if the task had been scheduled successfully 125 */ 126APU_DECLARE(apr_status_t) apr_thread_pool_top(apr_thread_pool_t *me, 127 apr_thread_start_t func, 128 void *param, 129 apr_byte_t priority, 130 void *owner); 131 132/** 133 * Cancel tasks submitted by the owner. If there is any task from the owner that 134 * is currently running, the function will spin until the task finished. 135 * @param me The thread pool 136 * @param owner Owner of the task 137 * @return APR_SUCCESS if the task has been cancelled successfully 138 * @note The task function should not be calling cancel, otherwise the function 139 * may get stuck forever. The function assert if it detect such a case. 140 */ 141APU_DECLARE(apr_status_t) apr_thread_pool_tasks_cancel(apr_thread_pool_t *me, 142 void *owner); 143 144/** 145 * Get the current number of tasks waiting in the queue 146 * @param me The thread pool 147 * @return Number of tasks in the queue 148 */ 149APU_DECLARE(apr_size_t) apr_thread_pool_tasks_count(apr_thread_pool_t *me); 150 151/** 152 * Get the current number of scheduled tasks waiting in the queue 153 * @param me The thread pool 154 * @return Number of scheduled tasks in the queue 155 */ 156APU_DECLARE(apr_size_t) apr_thread_pool_scheduled_tasks_count(apr_thread_pool_t *me); 157 158/** 159 * Get the current number of threads 160 * @param me The thread pool 161 * @return Total number of threads 162 */ 163APU_DECLARE(apr_size_t) apr_thread_pool_threads_count(apr_thread_pool_t *me); 164 165/** 166 * Get the current number of busy threads 167 * @param me The thread pool 168 * @return Number of busy threads 169 */ 170APU_DECLARE(apr_size_t) apr_thread_pool_busy_count(apr_thread_pool_t *me); 171 172/** 173 * Get the current number of idle threads 174 * @param me The thread pool 175 * @return Number of idle threads 176 */ 177APU_DECLARE(apr_size_t) apr_thread_pool_idle_count(apr_thread_pool_t *me); 178 179/** 180 * Access function for the maximum number of idle threads. Number of current 181 * idle threads will be reduced to the new limit. 182 * @param me The thread pool 183 * @param cnt The number 184 * @return The number of threads that were stopped. 185 */ 186APU_DECLARE(apr_size_t) apr_thread_pool_idle_max_set(apr_thread_pool_t *me, 187 apr_size_t cnt); 188 189/** 190 * Get number of tasks that have run 191 * @param me The thread pool 192 * @return Number of tasks that have run 193 */ 194APU_DECLARE(apr_size_t) 195 apr_thread_pool_tasks_run_count(apr_thread_pool_t * me); 196 197/** 198 * Get high water mark of the number of tasks waiting to run 199 * @param me The thread pool 200 * @return High water mark of tasks waiting to run 201 */ 202APU_DECLARE(apr_size_t) 203 apr_thread_pool_tasks_high_count(apr_thread_pool_t * me); 204 205/** 206 * Get high water mark of the number of threads 207 * @param me The thread pool 208 * @return High water mark of threads in thread pool 209 */ 210APU_DECLARE(apr_size_t) 211 apr_thread_pool_threads_high_count(apr_thread_pool_t * me); 212 213/** 214 * Get the number of idle threads that were destroyed after timing out 215 * @param me The thread pool 216 * @return Number of idle threads that timed out 217 */ 218APU_DECLARE(apr_size_t) 219 apr_thread_pool_threads_idle_timeout_count(apr_thread_pool_t * me); 220 221/** 222 * Access function for the maximum number of idle threads 223 * @param me The thread pool 224 * @return The current maximum number 225 */ 226APU_DECLARE(apr_size_t) apr_thread_pool_idle_max_get(apr_thread_pool_t *me); 227 228/** 229 * Access function for the maximum number of threads. 230 * @param me The thread pool 231 * @param cnt Number of threads 232 * @return The original maximum number of threads 233 */ 234APU_DECLARE(apr_size_t) apr_thread_pool_thread_max_set(apr_thread_pool_t *me, 235 apr_size_t cnt); 236 237/** 238 * Access function for the maximum wait time (in microseconds) of an 239 * idling thread that exceeds the maximum number of idling threads. 240 * A non-zero value allows for the reaping of idling threads to shrink 241 * over time. Which helps reduce thrashing. 242 * @param me The thread pool 243 * @param timeout The number of microseconds an idle thread should wait 244 * till it reaps itself 245 * @return The original maximum wait time 246 */ 247APU_DECLARE(apr_interval_time_t) 248 apr_thread_pool_idle_wait_set(apr_thread_pool_t * me, 249 apr_interval_time_t timeout); 250 251/** 252 * Access function for the maximum wait time (in microseconds) of an 253 * idling thread that exceeds the maximum number of idling threads 254 * @param me The thread pool 255 * @return The current maximum wait time 256 */ 257APU_DECLARE(apr_interval_time_t) 258 apr_thread_pool_idle_wait_get(apr_thread_pool_t * me); 259 260/** 261 * Access function for the maximum number of threads 262 * @param me The thread pool 263 * @return The current maximum number 264 */ 265APU_DECLARE(apr_size_t) apr_thread_pool_thread_max_get(apr_thread_pool_t *me); 266 267/** 268 * Access function for the threshold of tasks in queue to trigger a new thread. 269 * @param me The thread pool 270 * @param cnt The new threshold 271 * @return The original threshold 272 */ 273APU_DECLARE(apr_size_t) apr_thread_pool_threshold_set(apr_thread_pool_t *me, 274 apr_size_t val); 275 276/** 277 * Access function for the threshold of tasks in queue to trigger a new thread. 278 * @param me The thread pool 279 * @return The current threshold 280 */ 281APU_DECLARE(apr_size_t) apr_thread_pool_threshold_get(apr_thread_pool_t * me); 282 283/** 284 * Get owner of the task currently been executed by the thread. 285 * @param thd The thread is executing a task 286 * @param owner Pointer to receive owner of the task. 287 * @return APR_SUCCESS if the owner is retrieved successfully 288 */ 289APU_DECLARE(apr_status_t) apr_thread_pool_task_owner_get(apr_thread_t *thd, 290 void **owner); 291 292/** @} */ 293 294#ifdef __cplusplus 295} 296#endif 297 298#endif /* APR_HAS_THREADS */ 299#endif /* !APR_THREAD_POOL_H */ 300