philosophers_prep/rendu/producer_consumer.c

141 lines
3.3 KiB
C

/* ************************************************************************** */
/* */
/* ::: :::::::: */
/* producer_consumer.c :+: :+: :+: */
/* +:+ +:+ +:+ */
/* By: ruiferna <ruiferna@student.42porto.com> +#+ +:+ +#+ */
/* +#+#+#+#+#+ +#+ */
/* Created: 2025/10/07 22:17:29 by ruiferna #+# #+# */
/* Updated: 2025/10/08 18:38:50 by ruiferna ### ########.fr */
/* */
/* ************************************************************************** */
#include <pthread.h>
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <sys/time.h>
#define BUFFER_SIZE 100
#define NUM_PRODUCERS 2
#define NUM_CONSUMERS 2
#define ITEMS_TO_PRODUCE 100
typedef struct s_buffer
{
int items[BUFFER_SIZE];
int count;
int in;
int out;
int produced_count;
pthread_mutex_t mutex;
} t_buffer;
long get_time(void)
{
struct timeval tv;
gettimeofday(&tv, NULL);
return ((tv.tv_sec * 1000) + (tv.tv_usec / 1000));
}
void *producer(void *arg)
{
t_buffer *buffer;
int item;
buffer = (t_buffer *)arg;
while (1)
{
pthread_mutex_lock(&buffer->mutex);
if (buffer->count < BUFFER_SIZE)
{
if (buffer->produced_count >= ITEMS_TO_PRODUCE)
{
pthread_mutex_unlock(&buffer->mutex);
break ;
}
buffer->produced_count++;
item = buffer->produced_count;
buffer->items[buffer->in] = item;
buffer->in = (buffer->in + 1) % BUFFER_SIZE;
buffer->count++;
printf("%ldms - Producer produced item: %d\n", get_time(), item);
pthread_mutex_unlock(&buffer->mutex);
}
else
{
pthread_mutex_unlock(&buffer->mutex);
usleep(100);
}
}
return (NULL);
}
void *consumer(void *arg)
{
t_buffer *buffer;
int item;
buffer = (t_buffer *)arg;
while (1)
{
pthread_mutex_lock(&buffer->mutex);
if (buffer->count > 0)
{
item = buffer->items[buffer->out];
buffer->out = (buffer->out + 1) % BUFFER_SIZE;
buffer->count--;
printf("%ldms - Consumer consumed item: %d\n", get_time(), item);
pthread_mutex_unlock(&buffer->mutex);
}
else
{
if (buffer->produced_count >= ITEMS_TO_PRODUCE)
{
pthread_mutex_unlock(&buffer->mutex);
break ;
}
pthread_mutex_unlock(&buffer->mutex);
usleep(100);
}
}
return (NULL);
}
int main(void)
{
pthread_t producers[NUM_PRODUCERS];
pthread_t consumers[NUM_CONSUMERS];
t_buffer *buffer;
int i;
buffer = malloc(sizeof(t_buffer));
if (!buffer)
return (1);
buffer->count = 0;
buffer->in = 0;
buffer->out = 0;
buffer->produced_count = 0;
pthread_mutex_init(&buffer->mutex, NULL);
i = -1;
while (++i < NUM_PRODUCERS)
pthread_create(&producers[i], NULL, producer, buffer);
i = -1;
while (++i < NUM_CONSUMERS)
pthread_create(&consumers[i], NULL, consumer, buffer);
i = -1;
while (++i < NUM_PRODUCERS)
pthread_join(producers[i], NULL);
i = -1;
while (++i < NUM_CONSUMERS)
pthread_join(consumers[i], NULL);
pthread_mutex_destroy(&buffer->mutex);
free(buffer);
return (0);
}