static int threadpool_work_func()

in linux/src/threadpool_linux.c [176:225]


static int threadpool_work_func(void* param)
{
    if (param == NULL)
    {
        /* Codes_SRS_THREADPOOL_LINUX_07_073: [ If param is NULL, threadpool_work_func shall fail and return. ]*/
        LogCritical("Invalid args: param: %p", param);
    }
    else
    {
        struct timespec ts;
        THREADPOOL* threadpool = param;

        do
        {
            /* Codes_SRS_THREADPOOL_LINUX_07_074: [ threadpool_work_func shall get the real time by calling clock_gettime to set the waiting time for semaphore. ]*/
            if (clock_gettime(CLOCK_REALTIME, &ts) == -1)
            {
                /* Codes_SRS_THREADPOOL_LINUX_07_088: [ If clock_gettime fails, threadpool_work_func shall run the loop again. ]*/
                LogError("Failure getting time from clock_gettime");
            }
            else
            {
                ts.tv_nsec += TP_SEMAPHORE_TIMEOUT_MS;

                /* Codes_SRS_THREADPOOL_LINUX_07_075: [ threadpool_work_func shall wait on the semaphore with a time limit. ]*/
                if (sem_timedwait(&threadpool->semaphore, &ts) != 0)
                {
                    /* Codes_SRS_THREADPOOL_LINUX_07_087: [ If sem_timedwait fails, threadpool_work_func shall timeout and run the loop again. ]*/
                }
                else
                {
                    THANDLE(THREADPOOL_WORK_ITEM) threadpool_work_item;

                    /* Codes_SRS_THREADPOOL_LINUX_01_016: [ threadpool_work_func shall pop an item from the task queue by calling TQUEUE_POP(THANDLE(THREADPOOL_WORK_ITEM)). ]*/
                    /* Codes_SRS_THREADPOOL_LINUX_01_017: [ If the pop returns TQUEUE_POP_OK: ]*/
                    while (TQUEUE_POP(THANDLE(THREADPOOL_WORK_ITEM))(threadpool->task_queue, &threadpool_work_item, NULL, NULL, NULL) == TQUEUE_POP_OK)
                    {
                        /* Codes_SRS_THREADPOOL_LINUX_07_084: [ threadpool_work_func shall execute the work_function with work_function_ctx. ]*/
                        threadpool_work_item->work_function(threadpool_work_item->work_function_ctx);

                        /* Codes_SRS_THREADPOOL_LINUX_01_018: [ threadpool_work_func shall release the reference to the work item. ]*/
                        THANDLE_ASSIGN(THREADPOOL_WORK_ITEM)(&threadpool_work_item, NULL);
                    }
                }
            }
        /* Codes_SRS_THREADPOOL_LINUX_07_085: [ threadpool_work_func shall loop until the flag to stop the threads is not set to 1. ]*/
        } while (interlocked_add(&threadpool->stop_thread, 0) != 1);
    }
    return 0;
}