nok*_*oko 5 c++ mutex pthreads race-condition
我正在尝试设置几个线程以处于等待状态,直到它们收到pthread_cond_broadcast().
完成工作后,我希望线程回到等待状态。
我还希望调用 的进程pthread_cond_broadcast()在继续之前等待所有线程返回到它们的等待状态。在这种情况下,调用广播的是 main() 函数。我正在尝试使用 main(0pthread_cond_wait()在调用广播后执行 a 来执行此操作。
void* Work::job(void* id)
{
int idx = (long)id;
while(1)
{
pthread_mutex_lock(&job_lock);
while(!jobs_complete)
{
// wait for main to broadcast
pthread_cond_wait(&can_work, &job_lock);
pthread_mutex_unlock(&job_lock);
// work here
pthread_mutex_lock(&job_lock);
++jobs_completed;
if(jobs_completed == NUM_THREADS)
{
jobs_complete = true;
pthread_cond_signal(&jobs_done);
pthread_mutex_unlock(&job_lock);
}
pthread_mutex_unlock(&job_lock);
}
pthread_mutex_unlock(&job_lock);
}
return NULL;
}
Run Code Online (Sandbox Code Playgroud)
NUM_THREADS是 4,job_lock是一个pthread_mutex_t,can_work和jobs_done是pthread_cond_t,jobs_completed是一个,bool而jobs_complete是一个int。
// work
jobs_completed = false;
jobs_complete = 0;
pthread_mutex_lock(&job_lock);
pthread_cond_broadcast(&can_work);
pthread_cond_wait(&jobs_complete);
pthread_mutex_unlock(&job_lock);
// work that depends on jobs_complete
Run Code Online (Sandbox Code Playgroud)
现在,我正在通过调用pthread_cond_broadcast()然后立即调用来执行此操作pthread_cond_wait(),但这似乎陷入僵局。
任何人都可以解释我应该如何做或我哪里出错了?我很感激任何帮助。
谢谢!
pthread_mutex_unlock在函数末尾可能有 3 次连续调用,这将导致未定义的行为。你实际上不需要两个内部的。如果jobs_complete是true,线程将退出循环并释放锁,否则它将循环并需要它来等待条件can_work。
还有,还有
pthread_cond_wait(&jobs_complete);
Run Code Online (Sandbox Code Playgroud)
你可能的意思是:
pthread_cond_wait(&jobs_complete,&job_lock);
Run Code Online (Sandbox Code Playgroud)
此外,该函数需要 apthread_cond_t *和 a pthread_mutex_t *,而不是 an int,所以即使这样,该代码也明显被破坏了。
请注意,条件变量上的信号或广播只会对已经等待该变量的线程产生影响。该信号不会保留以供将来等待。因此,当线程在jobs_completewhile 块上循环并再次等待时,必须再次向它们发出信号以恢复工作。
job_complete另一件事:您提到了asint 和job_completedas的类型bool,但您的代码似乎并不同意:
if(jobs_completed == NUM_THREADS)
{
jobs_complete = true;
Run Code Online (Sandbox Code Playgroud)
我的建议是:学习信号量和屏障抽象模型,如果可以的话,使用现有的实现(boost或stdC++11 中的实现),或者使用pthreadAPI 重新实现它们。这些将帮助您比操作 cond 变量更轻松地处理这种情况。在这个网站上查找现有的解决方案。例如,这个问题处理一个非常相似的问题,我提供的解决方案可以轻松修改以使用 pthread API 来满足您的要求。
| 归档时间: |
|
| 查看次数: |
6806 次 |
| 最近记录: |