thread/m_threadpool.c
/*! Fetch the next task to perform from the pool.  Used by the threads in the
 *  threadpool
 *  \param pool            Initialized threadpool handle
 *  \param queue_copy[out] Copy of queue task to perform
 *  \return M_TRUE on success, M_FALSE on queue shutdown or thread idle timeout expired */
Fetch the next task to perform from the pool.  Used by the threads in the
threadpool
\param pool            Initialized threadpool handle
\param queue_copy[out] Copy of queue task to perform
\return M_TRUE on success, M_FALSE on queue shutdown or thread idle timeout expired
Fetch the next task to perform from the pool . Used by the threads in the threadpool \ param pool Initialized threadpool handle \ param queue_copy [ out ] Copy of queue task to perform \ return M_TRUE on success M_FALSE on queue shutdown or thread idle timeout expired
static M_bool M_threadpool_queue_fetch(M_threadpool_t *pool, M_threadpool_queue_t *queue_copy)
{
	M_bool acquired   = M_FALSE;
	M_bool is_timeout = M_FALSE;
	M_mem_set(queue_copy, 0, sizeof(*queue_copy));
	M_thread_mutex_lock(pool->queue_lock);
	while (pool->up) {
		M_threadpool_queue_t *q = M_llist_take_node(M_llist_first(pool->queue));
		if (q != NULL) {
			queue_copy->parent   = q->parent;
			queue_copy->task     = q->task;
			queue_copy->task_arg = q->task_arg;
			queue_copy->finished = q->finished;
			M_free(q);
			if (pool->queue_waiters) {
				M_thread_cond_signal(pool->queue_icond);
			}
			acquired = M_TRUE;
			break;
		}
		if (is_timeout && pool->num_threads > pool->min_threads) {
			break;
		}
		is_timeout = M_FALSE;
		pool->num_idle_threads++;
		if (pool->queue_waiters) {
			M_thread_cond_signal(pool->queue_icond);
		}
		if (pool->num_threads > pool->min_threads && pool->idle_time_ms != M_UINT64_MAX) {
			if (pool->idle_time_ms == 0 || !M_thread_cond_timedwait(pool->queue_ocond, pool->queue_lock, pool->idle_time_ms)) {
					is_timeout = M_TRUE;
			}
		} else {
			M_thread_cond_wait(pool->queue_ocond, pool->queue_lock);
		}
		pool->num_idle_threads--;
	}
	M_thread_mutex_unlock(pool->queue_lock);
	return acquired;
}
static M_bool M_threadpool_queue_fetch ( M_threadpool_t * pool , M_threadpool_queue_t * queue_copy ) { M_bool acquired = M_FALSE ; M_bool is_timeout = M_FALSE ; M_mem_set ( queue_copy , 0 , sizeof ( * queue_copy ) ) ; M_thread_mutex_lock ( pool -> queue_lock ) ; while ( pool -> up ) { M_threadpool_queue_t * q = M_llist_take_node ( M_llist_first ( pool -> queue ) ) ; if ( q != NULL ) { queue_copy -> parent = q -> parent ; queue_copy -> task = q -> task ; queue_copy -> task_arg = q -> task_arg ; queue_copy -> finished = q -> finished ; M_free ( q ) ; if ( pool -> queue_waiters ) { M_thread_cond_signal ( pool -> queue_icond ) ; } acquired = M_TRUE ; break ; } if ( is_timeout && pool -> num_threads > pool -> min_threads ) { break ; } is_timeout = M_FALSE ; pool -> num_idle_threads ++ ; if ( pool -> queue_waiters ) { M_thread_cond_signal ( pool -> queue_icond ) ; } if ( pool -> num_threads > pool -> min_threads && pool -> idle_time_ms != M_UINT64_MAX ) { if ( pool -> idle_time_ms == 0 || ! M_thread_cond_timedwait ( pool -> queue_ocond , pool -> queue_lock , pool -> idle_time_ms ) ) { is_timeout = M_TRUE ; } } else { M_thread_cond_wait ( pool -> queue_ocond , pool -> queue_lock ) ; } pool -> num_idle_threads -- ; } M_thread_mutex_unlock ( pool -> queue_lock ) ; return acquired ; }
Fetch the next task to perform from the pool.
Fetch the next task to perform from the pool .
/* Signal someone waiting for a queue slot to put a task in */ /* NOTE: even on a timeout condition, we'll look for a task first before
		 *       exiting just to make sure we don't have an accidental stall */ /* Wait for a signal to see if there is something to be processed
		 * there is no need here to ensure order or anything, the tasks
		 * fetching from the queue is first to get a lock */ /* Odd, we have a waiter registered, but no queued entries.  This could 
		 * happen if all threads were busy, but the caller was waiting on 
		 * M_threadpool_wait_available_thread() instead of an actual queue slot.
		 */