00001 00002 // 00003 // Copyright (c) 2000-2003 Intel Corporation 00004 // All rights reserved. 00005 // 00006 // Redistribution and use in source and binary forms, with or without 00007 // modification, are permitted provided that the following conditions are met: 00008 // 00009 // * Redistributions of source code must retain the above copyright notice, 00010 // this list of conditions and the following disclaimer. 00011 // * Redistributions in binary form must reproduce the above copyright notice, 00012 // this list of conditions and the following disclaimer in the documentation 00013 // and/or other materials provided with the distribution. 00014 // * Neither name of Intel Corporation nor the names of its contributors 00015 // may be used to endorse or promote products derived from this software 00016 // without specific prior written permission. 00017 // 00018 // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 00019 // "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 00020 // LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 00021 // A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL INTEL OR 00022 // CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, 00023 // EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, 00024 // PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR 00025 // PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY 00026 // OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING 00027 // NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS 00028 // SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 00029 // 00031 /*TU* 00032 00033 TombUPnP - a library for developing UPnP applications. 00034 00035 Copyright (C) 2006-2010 Sergey 'Jin' Bostandzhyan <jin@mediatomb.cc> 00036 00037 This library is free software; you can redistribute it and/or 00038 modify it under the terms of the GNU Lesser General Public 00039 License version 2.1 as published by the Free Software Foundation. 00040 00041 This library is distributed in the hope that it will be useful, 00042 but WITHOUT ANY WARRANTY; without even the implied warranty of 00043 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 00044 Lesser General Public License for more details. 00045 00046 You should have received a copy of the GNU Lesser General Public 00047 License along with this library; if not, write to the Free Software 00048 Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA. 00049 00050 $Id: ThreadPool.h 2081 2010-03-23 20:18:00Z lww $ 00051 */ 00052 #ifndef THREADPOOL_H 00053 #define THREADPOOL_H 00054 00055 #ifdef __cplusplus 00056 extern "C" { 00057 #endif 00058 00059 //Size of job free list 00060 #define JOBFREELISTSIZE 100 00061 00062 #define INFINITE_THREADS -1 00063 00064 #define EMAXTHREADS (-8 & 1<<29) 00065 00066 //Invalid Policy 00067 #define INVALID_POLICY (-9 & 1<<29) 00068 00069 //Invalid JOB Id 00070 #define INVALID_JOB_ID (-2 & 1<<29) 00071 00072 typedef enum duration {SHORT_TERM,PERSISTENT} Duration; 00073 00074 typedef enum priority {LOW_PRIORITY, 00075 MED_PRIORITY, 00076 HIGH_PRIORITY} ThreadPriority; 00077 00078 #define DEFAULT_PRIORITY MED_PRIORITY //default priority used by TPJobInit 00079 #define DEFAULT_MIN_THREADS 1 //default minimum used by TPAttrInit 00080 #define DEFAULT_MAX_THREADS 10 //default max used by TPAttrInit 00081 #define DEFAULT_JOBS_PER_THREAD 10 //default jobs per thread used by TPAttrInit 00082 #define DEFAULT_STARVATION_TIME 500 //default starvation time used by TPAttrInit 00083 #define DEFAULT_IDLE_TIME 10 * 1000 //default idle time used by TPAttrInit 00084 #define DEFAULT_FREE_ROUTINE NULL //default free routine used TPJobInit 00085 #define DEFAULT_MAX_JOBS_TOTAL 100 //default max jobs used TPAttrInit 00086 00087 #define STATS 1 //always include stats because code change is minimal 00088 00089 00090 //Statistics 00091 #ifdef WIN32 // todo: check why STATSONLY fails during compilation 00092 #undef STATS 00093 #endif 00094 00095 #ifdef STATS 00096 #define STATSONLY(x) x 00097 #else 00098 #define STATSONLY(x) 00099 #endif 00100 00101 #ifdef _DEBUG 00102 #define DEBUG 1 00103 #endif 00104 00105 //DEBUGGING 00106 #ifndef WIN32 00107 #ifdef DEBUG 00108 #define DBGONLY(x) x 00109 #else 00110 #define DBGONLY(x) 00111 #endif 00112 #endif 00113 00114 #include "LinkedList.h" 00115 #include <sys/time.h> 00116 #include "FreeList.h" 00117 00118 #include "ithread.h" 00119 #include <errno.h> 00120 #define EXPORT 00121 typedef int PolicyType; 00122 #define DEFAULT_POLICY SCHED_OTHER 00123 #define DEFAULT_SCHED_PARAM 0 //default priority 00124 00125 /**************************************************************************** 00126 * Name: free_routine 00127 * 00128 * Description: 00129 * Function for freeing a thread argument 00130 *****************************************************************************/ 00131 typedef void (*free_routine)(void *arg); 00132 typedef void (*free_thread_func)(void); 00133 00134 /**************************************************************************** 00135 * Name: ThreadPoolAttr 00136 * 00137 * Description: 00138 * Attributes for thread pool. Used to set and change parameters of 00139 * thread pool 00140 *****************************************************************************/ 00141 typedef struct THREADPOOLATTR 00142 { 00143 int minThreads; // minThreads, ThreadPool will always maintain at least 00144 // this many threads 00145 00146 int maxThreads; // maxThreads, ThreadPool will never have more than this 00147 // number of threads 00148 00149 int maxIdleTime; // maxIdleTime (in milliseconds) 00150 // this is the maximum time a thread will remain idle 00151 // before dying 00152 00153 int jobsPerThread; // jobs per thread to maintain 00154 00155 int maxJobsTotal; // maximum number of jobs that can be queued totally. 00156 00157 int starvationTime; // the time a low priority or med priority 00158 // job waits before getting bumped 00159 // up a priority (in milliseconds) 00160 00161 PolicyType schedPolicy; // scheduling policy to use 00162 00163 } ThreadPoolAttr; 00164 00165 /**************************************************************************** 00166 * Name: ThreadPool 00167 * 00168 * Description: 00169 * Internal ThreadPool Job 00170 *****************************************************************************/ 00171 typedef struct THREADPOOLJOB 00172 { 00173 start_routine func; //function 00174 void *arg; //arg 00175 free_routine free_func; //free function 00176 struct timeval requestTime; //time of request 00177 int priority; //priority of request 00178 int jobId; //id 00179 } ThreadPoolJob; 00180 00181 /**************************************************************************** 00182 * Name: ThreadPoolStats 00183 * 00184 * Description: 00185 * Structure to hold statistics 00186 *****************************************************************************/ 00187 00188 STATSONLY( 00189 00190 typedef struct TPOOLSTATS 00191 { 00192 double totalTimeHQ; //total time spent by all jobs in high priority Q 00193 int totalJobsHQ; //total jobs in HQ run so far 00194 double avgWaitHQ; //average wait in HQ 00195 double totalTimeMQ; //total time spent by all jobs in med priority Q 00196 int totalJobsMQ; //total jobs in MQ run so far 00197 double avgWaitMQ; //average wait in MQ 00198 double totalTimeLQ; //total time spent by all jobs in low priority Q 00199 int totalJobsLQ; //total jobs in LQ run so far 00200 double avgWaitLQ; //average wait in LQ 00201 double totalWorkTime; //total time spent working for all threads 00202 double totalIdleTime; //total time spent idle for all threads 00203 int workerThreads; //number of current workerThreads 00204 int idleThreads; //number of current idle threads 00205 int persistentThreads; //number of persistent threads 00206 int totalThreads; //total number of current threads 00207 int maxThreads; //max threads so far 00208 int currentJobsHQ; // current jobs in Q 00209 int currentJobsLQ; //current jobs in Q 00210 int currentJobsMQ; //current jobs in Q 00211 }ThreadPoolStats; 00212 00213 ) 00214 00215 00216 /**************************************************************************** 00217 * Name: ThreadPool 00218 * 00219 * Description: 00220 * A thread pool similar to the thread pool in the UPnP SDK. 00221 * Allows jobs to be scheduled for running by threads in a 00222 * thread pool. The thread pool is initialized with a 00223 * minimum and maximum thread number as well as a 00224 * max idle time 00225 * and a jobs per thread ratio. If a worker thread waits the whole 00226 * max idle time without receiving a job and the thread pool 00227 * currently has more threads running than the minimum 00228 * then the worker thread will exit. If when 00229 * scheduling a job the current job to thread ratio 00230 * becomes greater than the set ratio and the thread pool currently has 00231 * less than the maximum threads then a new thread will 00232 * be created. 00233 * 00234 *****************************************************************************/ 00235 00236 typedef struct THREADPOOL 00237 { 00238 ithread_mutex_t mutex; //mutex to protect job qs 00239 ithread_cond_t condition; //condition variable to signal Q 00240 ithread_cond_t start_and_shutdown; //condition variable for start 00241 //and stop 00242 int lastJobId; //ids for jobs 00243 int shutdown; //whether or not we are shutting down 00244 int totalThreads; //total number of threads 00245 int busyThreads; // number of threads that are currently executing jobs 00246 int persistentThreads; //number of persistent threads 00247 FreeList jobFreeList; //free list of jobs 00248 LinkedList lowJobQ; //low priority job Q 00249 LinkedList medJobQ; //med priority job Q 00250 LinkedList highJobQ; //high priority job Q 00251 ThreadPoolJob *persistentJob; //persistent job 00252 00253 ThreadPoolAttr attr; //thread pool attributes 00254 00255 free_thread_func free_func; // user defined thread cleanup function 00256 00257 //statistics 00258 STATSONLY(ThreadPoolStats stats;) 00259 00260 } ThreadPool; 00261 00262 00263 00264 /**************************************************************************** 00265 * Function: ThreadPoolInit 00266 * 00267 * Description: 00268 * Initializes and starts ThreadPool. Must be called first. 00269 * And only once for ThreadPool. 00270 * Parameters: 00271 * tp - must be valid, non null, pointer to ThreadPool. 00272 * attr - can be null 00273 * 00274 * if not null then attr contains the following fields: 00275 * 00276 * minWorkerThreads - minimum number of worker threads 00277 * thread pool will never have less than this 00278 * number of threads. 00279 * maxWorkerThreads - maximum number of worker threads 00280 * thread pool will never have more than this 00281 * number of threads. 00282 * maxIdleTime - maximum time that a worker thread will spend 00283 * idle. If a worker is idle longer than this 00284 * time and there are more than the min 00285 * number of workers running, than the 00286 * worker thread exits. 00287 * jobsPerThread - ratio of jobs to thread to try and maintain 00288 * if a job is scheduled and the number of jobs per 00289 * thread is greater than this number,and 00290 * if less than the maximum number of 00291 * workers are running then a new thread is 00292 * started to help out with efficiency. 00293 * schedPolicy - scheduling policy to try and set (OS dependent) 00294 * Returns: 00295 * 0 on success, nonzero on failure. 00296 * EAGAIN if not enough system resources to create minimum threads. 00297 * INVALID_POLICY if schedPolicy can't be set 00298 * EMAXTHREADS if minimum threads is greater than maximum threads 00299 *****************************************************************************/ 00300 int ThreadPoolInit(ThreadPool *tp, 00301 ThreadPoolAttr *attr); 00302 00303 /**************************************************************************** 00304 * Function: ThreadPoolAddPersistent 00305 * 00306 * Description: 00307 * Adds a persistent job to the thread pool. 00308 * Job will be run as soon as possible. 00309 * Call will block until job is scheduled. 00310 * Parameters: 00311 * tp - valid thread pool pointer 00312 * ThreadPoolJob - valid thread pool job with the following fields: 00313 * 00314 * func - ThreadFunction to run 00315 * arg - argument to function. 00316 * priority - priority of job. 00317 * 00318 * Returns: 00319 * 0 on success, nonzero on failure 00320 * EOUTOFMEM not enough memory to add job. 00321 * EMAXTHREADS not enough threads to add persistent job. 00322 *****************************************************************************/ 00323 int ThreadPoolAddPersistent (ThreadPool*tp, 00324 ThreadPoolJob *job, 00325 int *jobId); 00326 00327 /**************************************************************************** 00328 * Function: ThreadPoolGetAttr 00329 * 00330 * Description: 00331 * Gets the current set of attributes 00332 * associated with the thread pool. 00333 * Parameters: 00334 * tp - valid thread pool pointer 00335 * out - non null pointer to store attributes 00336 * Returns: 00337 * 0 on success, nonzero on failure 00338 * Always returns 0. 00339 *****************************************************************************/ 00340 int ThreadPoolGetAttr(ThreadPool *tp, 00341 ThreadPoolAttr *out); 00342 /**************************************************************************** 00343 * Function: ThreadPoolSetAttr 00344 * 00345 * Description: 00346 * Sets the attributes for the thread pool. 00347 * Only affects future calculations. 00348 * Parameters: 00349 * tp - valid thread pool pointer 00350 * attr - pointer to attributes, null sets attributes to default. 00351 * Returns: 00352 * 0 on success, nonzero on failure 00353 * Returns INVALID_POLICY if policy can not be set. 00354 *****************************************************************************/ 00355 int ThreadPoolSetAttr(ThreadPool *tp, 00356 ThreadPoolAttr *attr); 00357 00358 /**************************************************************************** 00359 * Function: ThreadPoolAdd 00360 * 00361 * Description: 00362 * Adds a job to the thread pool. 00363 * Job will be run as soon as possible. 00364 * Parameters: 00365 * tp - valid thread pool pointer 00366 * func - ThreadFunction to run 00367 * arg - argument to function. 00368 * priority - priority of job. 00369 * poolid - id of job 00370 * free_function - function to use when freeing argument 00371 * Returns: 00372 * 0 on success, nonzero on failure 00373 * EOUTOFMEM if not enough memory to add job. 00374 *****************************************************************************/ 00375 int ThreadPoolAdd (ThreadPool*tp, 00376 ThreadPoolJob *job, 00377 int *jobId); 00378 00379 /**************************************************************************** 00380 * Function: ThreadPoolRemove 00381 * 00382 * Description: 00383 * Removes a job from the thread pool. 00384 * Can only remove jobs which are not 00385 * currently running. 00386 * Parameters: 00387 * tp - valid thread pool pointer 00388 * jobid - id of job 00389 * out - space for removed job. 00390 * Returns: 00391 * 0 on success, nonzero on failure. 00392 * INVALID_JOB_ID if job not found. 00393 *****************************************************************************/ 00394 int ThreadPoolRemove(ThreadPool *tp, 00395 int jobId, ThreadPoolJob *out); 00396 00397 00398 00399 /**************************************************************************** 00400 * Function: ThreadPoolShutdown 00401 * 00402 * Description: 00403 * Shuts the thread pool down. 00404 * Waits for all threads to finish. 00405 * May block indefinitely if jobs do not 00406 * exit. 00407 * Parameters: 00408 * tp - must be valid tp 00409 * Returns: 00410 * 0 on success, nonzero on failure 00411 * Always returns 0. 00412 *****************************************************************************/ 00413 int ThreadPoolShutdown(ThreadPool *tp); 00414 00415 00416 /**************************************************************************** 00417 * Function: TPJobInit 00418 * 00419 * Description: 00420 * Initializes thread pool job. 00421 * Sets the priority to default defined in ThreadPool.h. 00422 * Sets the free_routine to default defined in ThreadPool.h 00423 * Parameters: 00424 * ThreadPoolJob *job - must be valid thread pool attributes. 00425 * start_routine func - function to run, must be valid 00426 * void * arg - argument to pass to function. 00427 * Returns: 00428 * Always returns 0. 00429 *****************************************************************************/ 00430 int TPJobInit(ThreadPoolJob *job, start_routine func, void *arg); 00431 00432 /**************************************************************************** 00433 * Function: TPJobSetPriority 00434 * 00435 * Description: 00436 * Sets the max threads for the thread pool attributes. 00437 * Parameters: 00438 * attr - must be valid thread pool attributes. 00439 * maxThreads - value to set 00440 * Returns: 00441 * Always returns 0. 00442 *****************************************************************************/ 00443 int TPJobSetPriority(ThreadPoolJob *job, ThreadPriority priority); 00444 00445 /**************************************************************************** 00446 * Function: TPJobSetFreeFunction 00447 * 00448 * Description: 00449 * Sets the max threads for the thread pool attributes. 00450 * Parameters: 00451 * attr - must be valid thread pool attributes. 00452 * maxThreads - value to set 00453 * Returns: 00454 * Always returns 0. 00455 *****************************************************************************/ 00456 int TPJobSetFreeFunction(ThreadPoolJob *job, free_routine func); 00457 00458 /**************************************************************************** 00459 * Function: TPAttrInit 00460 * 00461 * Description: 00462 * Initializes thread pool attributes. 00463 * Sets values to defaults defined in ThreadPool.h. 00464 * Parameters: 00465 * attr - must be valid thread pool attributes. 00466 * Returns: 00467 * Always returns 0. 00468 *****************************************************************************/ 00469 int TPAttrInit(ThreadPoolAttr *attr); 00470 00471 /**************************************************************************** 00472 * Function: TPAttrSetMaxThreads 00473 * 00474 * Description: 00475 * Sets the max threads for the thread pool attributes. 00476 * Parameters: 00477 * attr - must be valid thread pool attributes. 00478 * maxThreads - value to set 00479 * Returns: 00480 * Always returns 0. 00481 *****************************************************************************/ 00482 int TPAttrSetMaxThreads(ThreadPoolAttr *attr, int maxThreads); 00483 00484 /**************************************************************************** 00485 * Function: TPAttrSetMinThreads 00486 * 00487 * Description: 00488 * Sets the min threads for the thread pool attributes. 00489 * Parameters: 00490 * attr - must be valid thread pool attributes. 00491 * minThreads - value to set 00492 * Returns: 00493 * Always returns 0. 00494 *****************************************************************************/ 00495 int TPAttrSetMinThreads(ThreadPoolAttr *attr, int minThreads); 00496 00497 /**************************************************************************** 00498 * Function: TPAttrSetIdleTime 00499 * 00500 * Description: 00501 * Sets the idle time for the thread pool attributes. 00502 * Parameters: 00503 * attr - must be valid thread pool attributes. 00504 * Returns: 00505 * Always returns 0. 00506 *****************************************************************************/ 00507 int TPAttrSetIdleTime(ThreadPoolAttr *attr, int idleTime); 00508 00509 /**************************************************************************** 00510 * Function: TPAttrSetJobsPerThread 00511 * 00512 * Description: 00513 * Sets the jobs per thread ratio 00514 * Parameters: 00515 * attr - must be valid thread pool attributes. 00516 * jobsPerThread - number of jobs per thread to maintain 00517 * Returns: 00518 * Always returns 0. 00519 *****************************************************************************/ 00520 int TPAttrSetJobsPerThread(ThreadPoolAttr *attr, int jobsPerThread); 00521 00522 /**************************************************************************** 00523 * Function: TPAttrSetStarvationTime 00524 * 00525 * Description: 00526 * Sets the starvation time for the thread pool attributes. 00527 * Parameters: 00528 * attr - must be valid thread pool attributes. 00529 * int starvationTime - milliseconds 00530 * Returns: 00531 * Always returns 0. 00532 *****************************************************************************/ 00533 int TPAttrSetStarvationTime(ThreadPoolAttr *attr, int starvationTime); 00534 00535 /**************************************************************************** 00536 * Function: TPAttrSetSchedPolicy 00537 * 00538 * Description: 00539 * Sets the scheduling policy for the thread pool attributes. 00540 * Parameters: 00541 * attr - must be valid thread pool attributes. 00542 * PolicyType schedPolicy - must be a valid policy type. 00543 * Returns: 00544 * Always returns 0. 00545 *****************************************************************************/ 00546 int TPAttrSetSchedPolicy(ThreadPoolAttr *attr, PolicyType schedPolicy); 00547 00548 00549 /**************************************************************************** 00550 * Function: TPAttrSetMaxJobsTotal 00551 * 00552 * Description: 00553 * Sets the maximum number jobs that can be qeued totally. 00554 * Parameters: 00555 * attr - must be valid thread pool attributes. 00556 * maxJobsTotal - maximum number of jobs 00557 * Returns: 00558 * Always returns 0. 00559 *****************************************************************************/ 00560 int TPAttrSetMaxJobsTotal(ThreadPoolAttr *attr, int maxJobsTotal); 00561 00562 /**************************************************************************** 00563 * Function: ThreadPoolGetStats 00564 * 00565 * Description: 00566 * Returns various statistics about the 00567 * thread pool. 00568 * Only valid if STATS has been defined. 00569 * Parameters: 00570 * ThreadPool *tp - valid initialized threadpool 00571 * ThreadPoolStats *stats - valid stats, out parameter 00572 * Returns: 00573 * Always returns 0. 00574 *****************************************************************************/ 00575 STATSONLY( EXPORT int ThreadPoolGetStats(ThreadPool *tp, ThreadPoolStats *stats);); 00576 00577 STATSONLY(EXPORT void ThreadPoolPrintStats(ThreadPoolStats *stats);); 00578 00579 #ifdef __cplusplus 00580 } 00581 #endif 00582 00583 #endif //ThreadPool
1.6.1