What each thread is doing * * In principle this is an endless loop. The only time this loop gets interuppted is once * thpool_destroy() is invoked or the program exits. * * @param thread thread that will run this function * @return nothing */
| 389 | * @return nothing |
| 390 | */ |
| 391 | static void *thread_do(struct thread *thread_p) { |
| 392 | |
| 393 | /* Set thread name for profiling and debuging */ |
| 394 | char thread_name[128] = {0}; |
| 395 | sprintf(thread_name, "thread-pool-%s-%d", thread_p->thpool_p->name, thread_p->id); |
| 396 | |
| 397 | #if defined(__linux__) |
| 398 | /* Use prctl instead to prevent using _GNU_SOURCE flag and implicit declaration */ |
| 399 | prctl(PR_SET_NAME, thread_name); |
| 400 | #elif defined(__APPLE__) && defined(__MACH__) |
| 401 | pthread_setname_np(thread_name); |
| 402 | #else |
| 403 | err("thread_do(): pthread_setname_np is not supported on this system"); |
| 404 | #endif |
| 405 | |
| 406 | /* Assure all threads have been created before starting serving */ |
| 407 | thpool_* thpool_p = thread_p->thpool_p; |
| 408 | |
| 409 | /* Register signal handler */ |
| 410 | struct sigaction act; |
| 411 | sigemptyset(&act.sa_mask); |
| 412 | act.sa_flags = 0; |
| 413 | act.sa_handler = thread_hold; |
| 414 | if(sigaction(SIGUSR2, &act, NULL) == -1) { |
| 415 | err("thread_do(): cannot handle SIGUSR1"); |
| 416 | } |
| 417 | |
| 418 | /* Mark thread as alive (initialized) */ |
| 419 | ++thpool_p->num_threads_alive; |
| 420 | |
| 421 | while(threads_keepalive) { |
| 422 | |
| 423 | bsem_wait(thpool_p->jobqueue.has_jobs); |
| 424 | |
| 425 | if(threads_keepalive) { |
| 426 | ++thpool_p->num_threads_working; |
| 427 | |
| 428 | /* Read job from queue and execute it */ |
| 429 | void (*func_buff)(void *); |
| 430 | void *arg_buff; |
| 431 | job *job_p = jobqueue_pull(&thpool_p->jobqueue); |
| 432 | if(job_p) { |
| 433 | func_buff = job_p->function; |
| 434 | arg_buff = job_p->arg; |
| 435 | func_buff(arg_buff); |
| 436 | rm_free(job_p); |
| 437 | } |
| 438 | |
| 439 | --thpool_p->num_threads_working; |
| 440 | pthread_mutex_lock(&thpool_p->thcount_lock); |
| 441 | if (!thpool_p->num_threads_working) { |
| 442 | pthread_cond_signal(&thpool_p->threads_all_idle); |
| 443 | } |
| 444 | pthread_mutex_unlock(&thpool_p->thcount_lock); |
| 445 | } |
| 446 | } |
| 447 | |
| 448 | --thpool_p->num_threads_alive; |
nothing calls this directly
no test coverage detected