与Pthread和互斥锁有界的缓冲区共享锁定忙碌的等待

时间:2019-10-20 20:07:19

标签: c multithreading synchronization buffer mutex

我正在尝试使用互斥锁创建生产者使用者队列,从而在线程之间创建繁忙的等待。我的主文件使用X数量的整数参数,将它们压入大小为50的BOUNDED BUFFER上。我使用while循环来执行此操作,因为您不知道事前的数量。我不确定何时何地创建生产者线程。 注意:Main从某种意义上说是一个“生产者”,它填充了缓冲区,但是我的实际生产者函数将在以后的代码中传递给我的消费者函数,因此请忽略名称。 Main将通过推送“生产”数字,而Producer将弹出这些数字供以后使用。我的问题是,何时在何时为生产者在我的代码中创建Pthread_create,我是否正确使用Mutex锁以使两个线程之间保持同步?

#include <pthread.h>
#include <stdlib.h>
#include <math.h>
#include <stdio.h>
#define BUFFER_SIZE (50)

typedef struct {
        int buffer[BUFFER_SIZE];
        int count;
        int top;
        int next;
        pthread_mutex_t count_lock;
} prodcons;

void pc_init(prodcons *pc);
int pc_pop(prodcons *pc);
void pc_push(prodcons *pc, int val);

void factor2pc(prodcons *pc, int number);
void *producer(void *data);
void *consumer(void *data);

int main(int argc, char *argv[])
{
        int index = 1;
        int num;
        prodcons pc_nums;



        //pthread_t tid[argc - 1];
        pthread_t tid;
        pthread_attr_t attr;

        if (argc <  2) {
                fprintf(stderr, "usage: No arguments\n");
                return -1;
        }
        if (atoi(argv[1]) <= 0)
        {
                fprintf(stderr, "%d not > 0 or you must provide a positive integer.\n", atoi(argv[1]));
                return -1;
        }


        pthread_attr_init(&attr);


        pc_init(&pc_nums);


        //DO I PUT THIS HERE or WHILE LOOP?
        pthread_create(&tid, &attr, *producer, &pc_nums);

        while (index < argc)
        {
                num = atoi(argv[index]);
                pc_push(&pc_nums, num);
                index++;
        }

}

void *producer(void *data)
{
        prodcons *dataStruct = data;







        while (dataStruct->count < BUFFER_SIZE)
        {
                number = pc_pop(data);
                //This print is just here to make sure I am correctly "poping" from buffer
                printf("%d\n", number);
        }
}

void pc_init(prodcons *pc)
{
        pc->count = 0;
        pc->top = 0;
        pc->next = 0;
        if (pthread_mutex_init(&pc->count_lock, NULL) != 0)
        {
        printf("\n mutex init has failed\n");
        }
}


int pc_pop(prodcons *pc)
{
        int val;
        pthread_mutex_lock(&pc->count_lock);

        if (pc->count > pc->top)
        {
                val = pc->buffer[pc->count];
                printf("%d\n", val);
                pc->buffer[pc->count] = 0;
                pc->count--;
        }

        pthread_mutex_unlock(&pc->count_lock);
        return val;
}

void pc_push(prodcons *pc, int val)
{
        pthread_mutex_lock(&pc->count_lock);

        if (pc->count < BUFFER_SIZE)
        {
                pc->buffer[pc->count] = val;
                pc->count++;
        }

        pthread_mutex_unlock(&pc->count_lock);
}

1 个答案:

答案 0 :(得分:0)

  

我的问题是我应该在何时何地在生产者代码中创建Pthread_create,我是否正确使用Mutex锁来使两个线程之间保持同步?

只要正确初始化和同步了所有代码,您就可以将pthread_create()调用放在所需的任何位置,包括在给定程序中的放置位置。但是至少有两件事是错误的:

    如果缓冲区中没有要弹出的数字,则
  • pc_pop()的行为不确定(通过return的未初始化值)。
  • 由于dataStruct->countproducer()进行访问而没有锁定,因此声明应为_Atomic(int) count;