[英]Implementing an thread-safe queue with pThreads: Deadlock?
我正在嘗試實現基於固定數組的線程安全隊列。 該隊列包含一個void指針數組。
pthread_t a;
pthread_t b;
Queue *q;
Queue* queue_new(int size)
{
// malloc stuff
}
void queue_put(Queue* q, void* item)
{
pthread_mutex_lock(&(q->lock));
// details on array queue managment
pthread_mutex_unlock(&(q->lock));
}
void* queue_get(Queue* q)
{
pthread_mutex_lock(&(q->lock));
// more details ...
return q->queue[old_front];
pthread_mutex_unlock(&(q->lock));
}
void *func_a (void *ptr)
{
void *ptr1 = malloc(sizeof(int));
*((int*)ptr1) = 5;
queue_put(q, ptr1);
void *ptr2 = malloc(sizeof(int));
*((int*)ptr2) = 4;
queue_put(q, ptr2);
return NULL;
}
void *func_b (void *ptr)
{
void *ptr3 = malloc(sizeof(int));
*((int*)ptr3) = 7;
queue_put(q, ptr3);
queue_get(q); // critical part !
return NULL;
}
int main ()
{
q = queue_new(3);
pthread_create(&a, NULL, func_a, NULL);
pthread_create(&b, NULL, func_b, NULL);
pthread_join(a, NULL);
pthread_join(b, NULL);
queue_print(q);
return 0;
}
我認為這是一個非常簡單的方法。 不幸的是,程序凍結了。 但是,當我刪除queue_get(q);
在func_b
它工作得很好。 我認為這必定是某種僵局。 有任何想法嗎? Queue的非線程安全版本已經過測試,工作正常。 為清晰起見,隱藏了代碼。 有任何想法嗎?
我相信問題在於queue_get
。 您在互斥鎖解鎖之前返回。 嘗試將返回值存儲到一個temprary變量中,解鎖互斥鎖,然后返回該值。
void* queue_get(Queue* q)
{
void* temp;
pthread_mutex_lock(&(q->lock));
// more details ...
temp = q->queue[old_front];
pthread_mutex_unlock(&(q->lock));
return temp;
}
在解鎖queue_get中的互斥鎖之前,您將返回:
return q->queue[old_front];
pthread_mutex_unlock(&(q->lock));
這應該是:
void *retValue = q->queue[old_front];
pthread_mutex_unlock(&(q->lock));
return retValue;
您將要在queue_get
移動return
上方的解鎖行,截至目前它從未到達。 所以鎖從未被釋放。
pthread_mutex_unlock(&(q->lock));
return q->queue[old_front];
或者,你可能想要的,避免在鎖外觸摸它:
void * ret = q->queue[old_front];
pthread_mutex_unlock(&(q->lock));
return ret;
(從更具風格的觀點來看:你的價值分配方式會更加“清潔”:
int * ptr1 = malloc(sizeof(*ptr1));
*ptr1 = 5;
queue_put(q, ptr1);
注意缺少演員陣容)
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.