pthread_cond_wait永不阻塞-线程池 [英] pthread_cond_wait never unblocking - thread pools

查看:249
本文介绍了pthread_cond_wait永不阻塞-线程池的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在尝试实现一种线程池,借此将线程保留在FIFO中并处理一堆图像.不幸的是,由于某种原因,即使我的cond_wait被信号通知,它也并不总是唤醒.

I'm trying to implement a sort of thread pool whereby I keep threads in a FIFO and process a bunch of images. Unfortunately, for some reason my cond_wait doesn't always wake even though it's been signaled.

        // Initialize the thread pool
        for(i=0;i<numThreads;i++)
        {

            pthread_t *tmpthread = (pthread_t *) malloc(sizeof(pthread_t));

            struct Node* newNode;
            newNode=(struct Node *) malloc(sizeof(struct Node));
            newNode->Thread = tmpthread;
            newNode->Id = i;
            newNode->threadParams = 0;
            pthread_cond_init(&(newNode->cond),NULL);
            pthread_mutex_init(&(newNode->mutx),NULL);

            pthread_create( tmpthread, NULL, someprocess, (void*) newNode);
            push_back(newNode, &threadPool);

        }



    for() //stuff here
    {
    //...stuff
        pthread_mutex_lock(&queueMutex);        
            struct Node *tmpNode = pop_front(&threadPool);
        pthread_mutex_unlock(&queueMutex);  

        if(tmpNode != 0)
        {
            pthread_mutex_lock(&(tmpNode->mutx));
                pthread_cond_signal(&(tmpNode->cond)); // Not starting mutex sometimes? 
            pthread_mutex_unlock(&(tmpNode->mutx));     
        }
    //...stuff
    }

 destroy_threads=1;
 //loop through and signal all the threads again so they can exit. 
 //pthread_join here


}

    void *someprocess(void* threadarg)
    {
        do
        {
    //...stuff
            pthread_mutex_lock(&(threadNode->mutx));
                pthread_cond_wait(&(threadNode->cond), &(threadNode->mutx));
                // Doesn't always seem to resume here after signalled.
            pthread_mutex_unlock(&(threadNode->mutx));
        } while(!destroy_threads);

        pthread_exit(NULL);
    }

我错过了什么吗?它大约有一半的时间有效,所以我假设我在某个地方有比赛,但是我唯一能想到的就是我正在加紧互斥体吗?我读到一些有关在锁定之前不发信号的信息,但我不太了解发生了什么.

Am I missing something? It works about half of the time, so I would assume that I have a race somewhere, but the only thing I can think of is that I'm screwing up the mutexes? I read something about not signalling before locking or something, but I don't really understand what's going on.

有什么建议吗?

谢谢!

推荐答案

首先,您的示例显示将queueMutex锁定在对pop_front的调用周围,但没有对push_back进行舍入.通常,除非您可以保证在所有爆破声发生之前进行所有推送,否则您都需要锁定两者.

Firstly, your example shows you locking the queueMutex around the call to pop_front, but not round push_back. Typically you would need to lock round both, unless you can guarantee that all the pushes happen-before all the pops.

第二,您对pthread_cond_wait的调用似乎没有关联的谓词.条件变量的典型用法是:

Secondly, your call to pthread_cond_wait doesn't seem to have an associated predicate. Typical usage of condition variables is:

pthread_mutex_lock(&mtx);
while(!ready)
{
    pthread_cond_wait(&cond,&mtx);
}
do_stuff();
pthread_mutex_unlock(&mtx);

在此示例中,ready是由另一个线程设置的某个变量,而该线程持有对mtx的锁定.

In this example, ready is some variable that is set by another thread whilst that thread holds a lock on mtx.

如果在调用pthread_cond_signal时未在pthread_cond_wait中阻塞等待线程,则该信号将被忽略.关联的ready变量使您能够处理这种情况,还使您能够处理所谓的虚假唤醒,其中返回pthread_cond_wait的调用而无需从另一个线程.

If the waiting thread is not blocked in the pthread_cond_wait when pthread_cond_signal is called then the signal will be ignored. The associated ready variable allows you to handle this scenario, and also allows you to handle so-called spurious wake-ups where the call to pthread_cond_wait returns without a corresponding call to pthread_cond_signal from another thread.

这篇关于pthread_cond_wait永不阻塞-线程池的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆