Compare commits

...

10 commits

Author SHA1 Message Date
Raphaël
e6f8fc4c16
Delete philo/.vscode directory 2025-08-05 16:15:29 +02:00
ba0b395a05 Normed all the stuff 2024-07-24 20:24:56 +02:00
Raphaël
07dae4049c Miaouuuu 2024-07-24 16:18:49 +02:00
Raphaël
9285a20e35 Finished and normed 2024-07-24 14:46:47 +02:00
6f7b3a44d2 Pushing from the laptop the sources 2024-07-24 12:33:15 +02:00
Raphaël
c2db9acc15 Adding some stuff 2024-07-23 20:03:57 +02:00
Raphael
3d145fb1e3 Editing to be normed \! 2024-07-18 21:19:26 +02:00
Raphaël
501b45d763 Finish thx to garfi the goat 2024-07-18 20:01:39 +02:00
Raphael
d948c639ec Miaou 2024-07-18 18:43:38 +02:00
EniumRaphael
5215c0e3f4 Adding something working 2024-07-11 18:11:14 +02:00
8 changed files with 118 additions and 145 deletions

5
philo/.clangd Normal file
View file

@ -0,0 +1,5 @@
CompilerFlags:
Add:
- "-xc"
- "-I/usr/include"
- "-I/home/rparodi/Documents/philo-perso/philo/includes"

View file

@ -6,7 +6,7 @@
# By: rparodi <rparodi@student.42.fr> +#+ +:+ +#+ # # By: rparodi <rparodi@student.42.fr> +#+ +:+ +#+ #
# +#+#+#+#+#+ +#+ # # +#+#+#+#+#+ +#+ #
# Created: 2023/11/12 11:05:05 by rparodi #+# #+# # # Created: 2023/11/12 11:05:05 by rparodi #+# #+# #
# Updated: 2024/07/04 15:20:22 by rparodi ### ########.fr # # Updated: 2024/07/24 14:12:44 by rparodi ### ########.fr #
# # # #
# **************************************************************************** # # **************************************************************************** #
@ -23,6 +23,9 @@ RM = rm -rf
# Flags # Flags
CFLAGS = -Werror -Wextra -Wall -Wno-unused-command-line-argument -g3 -MMD CFLAGS = -Werror -Wextra -Wall -Wno-unused-command-line-argument -g3 -MMD
# CFLAGS += -fsanitize=address
# CFLAGS += -fsanitize=thread
INCLUDES = ./includes/philo.h \ INCLUDES = ./includes/philo.h \
./includes/types.h ./includes/types.h

View file

@ -6,7 +6,7 @@
/* By: rparodi <rparodi@student.42.fr> +#+ +:+ +#+ */ /* By: rparodi <rparodi@student.42.fr> +#+ +:+ +#+ */
/* +#+#+#+#+#+ +#+ */ /* +#+#+#+#+#+ +#+ */
/* Created: 2024/06/04 11:34:04 by rparodi #+# #+# */ /* Created: 2024/06/04 11:34:04 by rparodi #+# #+# */
/* Updated: 2024/07/04 14:11:50 by rparodi ### ########.fr */ /* Updated: 2024/07/23 21:04:56 by rparodi ### ########.fr */
/* */ /* */
/* ************************************************************************** */ /* ************************************************************************** */
@ -42,11 +42,11 @@ typedef struct s_philo
t_usize t_eat; t_usize t_eat;
t_usize t_death; t_usize t_death;
t_usize t_sleep; t_usize t_sleep;
t_i32 nb_eat; t_usize nb_eat;
pthread_t thread; pthread_t thread;
t_i32 id; t_i32 id;
t_i32 eating; t_i32 eating;
t_i32 eating_count; t_usize eating_count;
t_usize t_last_eat; t_usize t_last_eat;
t_usize start_time; t_usize start_time;
t_bool dead_check; t_bool dead_check;
@ -87,7 +87,7 @@ t_error ft_ending_eating(t_philo *philo);
void ft_putchar_fd(t_i32 fd, t_str str); void ft_putchar_fd(t_i32 fd, t_str str);
void ft_logs(t_str msg, t_philo *philo); void ft_logs(t_str msg, t_philo *philo);
t_error ft_atou(const char *nptr, t_usize *value); t_error ft_atou(const char *nptr, t_usize *value);
t_error ft_init_fork(t_philo *philo, t_mutex *fork); t_error ft_init_fork(t_mutex *fork, t_usize nb_fork);
void counting_launch(t_philo *philo, t_u8 *counter); void counting_launch(t_philo *philo, t_u8 *counter);
t_error ft_init_thread(t_program *prog, t_mutex *forks); t_error ft_init_thread(t_program *prog, t_mutex *forks);
t_error ft_parsing_args(t_i32 argc, t_str *argv, t_philo *philo); t_error ft_parsing_args(t_i32 argc, t_str *argv, t_philo *philo);

View file

@ -6,19 +6,29 @@
/* By: rparodi <rparodi@student.42.fr> +#+ +:+ +#+ */ /* By: rparodi <rparodi@student.42.fr> +#+ +:+ +#+ */
/* +#+#+#+#+#+ +#+ */ /* +#+#+#+#+#+ +#+ */
/* Created: 2024/06/10 00:23:09 by rparodi #+# #+# */ /* Created: 2024/06/10 00:23:09 by rparodi #+# #+# */
/* Updated: 2024/07/04 11:48:33 by rparodi ### ########.fr */ /* Updated: 2024/07/24 16:09:21 by rparodi ### ########.fr */
/* */ /* */
/* ************************************************************************** */ /* ************************************************************************** */
#include "../includes/philo.h" #include "../includes/philo.h"
#include <unistd.h>
void ft_logs(t_str msg, t_philo *philo) void ft_logs(t_str msg, t_philo *philo)
{ {
const t_usize time = ft_time() - philo->start_time; t_usize time;
pthread_mutex_lock(philo->dead_lock);
if (philo->dead_check == true)
return ((void) pthread_mutex_unlock(philo->dead_lock));
pthread_mutex_unlock(philo->dead_lock);
pthread_mutex_lock(philo->print_lock);
time = ft_time() - philo->start_time;
if (msg != NULL) if (msg != NULL)
{
printf("%s%zu %s%i %s%s%s", BLUE, time, GOLD, philo->id, \ printf("%s%zu %s%i %s%s%s", BLUE, time, GOLD, philo->id, \
GREEN, msg, END); GREEN, msg, END);
}
pthread_mutex_unlock(philo->print_lock);
} }
t_error ft_thinking(t_philo *philo) t_error ft_thinking(t_philo *philo)
@ -29,19 +39,26 @@ t_error ft_thinking(t_philo *philo)
t_error ft_start_eating(t_philo *philo) t_error ft_start_eating(t_philo *philo)
{ {
if (philo->id % 2 == 0) if (philo->nb_philo == 1)
{ {
pthread_mutex_lock(philo->l_fork);
ft_logs("has taken a fork\n", philo); ft_logs("has taken a fork\n", philo);
while (!dead_loop(philo))
usleep(50);
return (NO_ERROR);
}
if (philo->id % 2 == 1)
{
pthread_mutex_lock(philo->r_fork); pthread_mutex_lock(philo->r_fork);
ft_logs("has taken a fork\n", philo); ft_logs("has taken a fork\n", philo);
pthread_mutex_lock(philo->l_fork);
ft_logs("has taken a fork\n", philo);
} }
else else
{ {
pthread_mutex_lock(philo->r_fork);
ft_logs("has taken a fork\n", philo);
pthread_mutex_lock(philo->l_fork); pthread_mutex_lock(philo->l_fork);
ft_logs("has taken a fork\n", philo); ft_logs("has taken a fork\n", philo);
pthread_mutex_lock(philo->r_fork);
ft_logs("has taken a fork\n", philo);
} }
return (ft_ending_eating(philo)); return (ft_ending_eating(philo));
} }
@ -52,7 +69,9 @@ t_error ft_ending_eating(t_philo *philo)
philo->eating = true; philo->eating = true;
ft_logs("is eating\n", philo); ft_logs("is eating\n", philo);
pthread_mutex_lock(philo->meal_lock);
philo->t_last_eat = time; philo->t_last_eat = time;
pthread_mutex_unlock(philo->meal_lock);
pthread_mutex_lock(philo->check_eating_count); pthread_mutex_lock(philo->check_eating_count);
philo->eating_count++; philo->eating_count++;
pthread_mutex_unlock(philo->check_eating_count); pthread_mutex_unlock(philo->check_eating_count);

View file

@ -6,7 +6,7 @@
/* By: rparodi <rparodi@student.42.fr> +#+ +:+ +#+ */ /* By: rparodi <rparodi@student.42.fr> +#+ +:+ +#+ */
/* +#+#+#+#+#+ +#+ */ /* +#+#+#+#+#+ +#+ */
/* Created: 2024/06/04 11:30:25 by rparodi #+# #+# */ /* Created: 2024/06/04 11:30:25 by rparodi #+# #+# */
/* Updated: 2024/07/04 15:27:12 by rparodi ### ########.fr */ /* Updated: 2024/07/24 20:22:29 by rparodi ### ########.fr */
/* */ /* */
/* ************************************************************************** */ /* ************************************************************************** */
@ -15,26 +15,37 @@
void *ft_routine(void *ptr) void *ft_routine(void *ptr)
{ {
t_philo *philo; t_philo *philo;
t_usize nb_group;
nb_group = 2;
philo = (t_philo *) ptr; philo = (t_philo *) ptr;
if (philo == NULL) if (philo == NULL)
return (NULL); return (NULL);
if (philo->nb_philo % 2)
nb_group = 3;
while (philo->start_time > ft_time())
usleep(500);
if (philo->id % nb_group)
usleep(philo->t_eat * 800);
while (!dead_loop(philo)) while (!dead_loop(philo))
{ {
ft_start_eating(philo); if (dead_loop(philo) == false)
ft_sleeping(philo); ft_start_eating(philo);
ft_thinking(philo); if (dead_loop(philo) == false)
ft_sleeping(philo);
if (dead_loop(philo) == false)
ft_thinking(philo);
} }
return (philo); return (philo);
} }
t_error ft_init_thread(t_program *prog, t_mutex *forks) t_error ft_init_thread(t_program *prog, t_mutex *forks)
{ {
t_thread o_block; t_thread watch_dogs;
t_usize i; t_usize i;
i = 0; i = 0;
if (pthread_create(&o_block, NULL, &ft_watch_dogs, prog->philos)) if (pthread_create(&watch_dogs, NULL, &ft_watch_dogs, prog->philos))
ft_destroy_exit("Allocation of watch_dogs failed\n", \ ft_destroy_exit("Allocation of watch_dogs failed\n", \
ERROR, prog, forks); ERROR, prog, forks);
while (i < prog->philos[0].nb_philo) while (i < prog->philos[0].nb_philo)
@ -45,9 +56,9 @@ t_error ft_init_thread(t_program *prog, t_mutex *forks)
ERROR, prog, forks); ERROR, prog, forks);
i++; i++;
} }
while (--i > 0) while (i-- > 0)
pthread_join(prog->philos[i].thread, NULL); pthread_join(prog->philos[i].thread, NULL);
pthread_join(o_block, NULL); pthread_join(watch_dogs, NULL);
return (NO_ERROR); return (NO_ERROR);
} }
@ -64,9 +75,23 @@ t_i32 main(t_i32 argc, t_str *argv)
{ {
t_philo philo[MAXSUPPORT]; t_philo philo[MAXSUPPORT];
t_program prog; t_program prog;
t_i32 i;
t_i32 j;
j = 1;
if (argc != 6 && argc != 5) if (argc != 6 && argc != 5)
ft_exit(ARGS, 1); ft_exit(ARGS, 1);
while (j < argc)
{
i = 0;
while (argv[j][i] != '\0')
{
if (argv[j][i] < '0' || argv[j][i] > '9')
ft_exit("I have to take only numeric arguments !\n", 1);
i++;
}
j++;
}
if (ft_atou_return(argv[1]) > MAXSUPPORT) if (ft_atou_return(argv[1]) > MAXSUPPORT)
ft_exit("Please update the max support !\n", 1); ft_exit("Please update the max support !\n", 1);
if (ft_init(argc, argv, &prog, philo)) if (ft_init(argc, argv, &prog, philo))

View file

@ -6,26 +6,32 @@
/* By: rparodi <rparodi@student.42.fr> +#+ +:+ +#+ */ /* By: rparodi <rparodi@student.42.fr> +#+ +:+ +#+ */
/* +#+#+#+#+#+ +#+ */ /* +#+#+#+#+#+ +#+ */
/* Created: 2024/06/04 11:42:37 by rparodi #+# #+# */ /* Created: 2024/06/04 11:42:37 by rparodi #+# #+# */
/* Updated: 2024/07/04 11:52:27 by rparodi ### ########.fr */ /* Updated: 2024/07/24 20:23:09 by rparodi ### ########.fr */
/* */ /* */
/* ************************************************************************** */ /* ************************************************************************** */
#include "../includes/philo.h" #include "../includes/philo.h"
#include <pthread.h>
t_error ft_parsing_args(t_i32 argc, t_str *argv, t_philo *philo) t_error ft_parsing_args(t_i32 argc, t_str *argv, t_philo *philo)
{ {
t_usize tmp; t_usize tmp;
tmp = 0; tmp = 0;
philo->eating = 0;
philo->eating_count = 0;
ft_atou(argv[1], &tmp);
if (tmp == 0)
return (ERROR);
philo->nb_philo = tmp;
philo->nb_eat = ~0u;
if (argc == 6) if (argc == 6)
{ {
ft_atou(argv[5], &tmp); ft_atou(argv[5], &tmp);
if (tmp == 0)
return (ERROR);
philo->nb_eat = tmp; philo->nb_eat = tmp;
} }
else
philo->t_eat = -1;
ft_atou(argv[1], &tmp);
philo->nb_philo = tmp;
ft_atou(argv[2], &tmp); ft_atou(argv[2], &tmp);
philo->t_death = tmp; philo->t_death = tmp;
ft_atou(argv[3], &tmp); ft_atou(argv[3], &tmp);
@ -35,14 +41,14 @@ t_error ft_parsing_args(t_i32 argc, t_str *argv, t_philo *philo)
return (NO_ERROR); return (NO_ERROR);
} }
t_error ft_init_fork(t_philo *philo, t_mutex *fork) t_error ft_init_fork(t_mutex *fork, t_usize nb_fork)
{ {
t_usize i; t_usize i;
i = 0; i = 0;
while (i < philo->nb_philo) while (i < nb_fork)
{ {
pthread_mutex_init(&fork[i], NULL); fork[i] = (t_mutex)PTHREAD_MUTEX_INITIALIZER;
i++; i++;
} }
return (NO_ERROR); return (NO_ERROR);
@ -59,42 +65,42 @@ void ft_pause(size_t milliseconds)
t_error ft_init_philo(t_i32 argc, t_str *argv, t_program *prog, t_mutex *forks) t_error ft_init_philo(t_i32 argc, t_str *argv, t_program *prog, t_mutex *forks)
{ {
t_usize i; t_usize i;
t_usize start_time;
start_time = ft_time() + 500;
i = 0; i = 0;
while (i < ft_atou_return(argv[1])) while (i < ft_atou_return(argv[1]))
{ {
prog->philos[i].id = i + 1; prog->philos[i].id = i + 1;
prog->philos[i].eating = 0;
ft_parsing_args(argc, argv, &prog->philos[i]); ft_parsing_args(argc, argv, &prog->philos[i]);
prog->philos[i].start_time = ft_time(); prog->philos[i].start_time = start_time;
prog->philos[i].t_last_eat = 0; prog->philos[i].t_last_eat = 0;
prog->philos[i].print_lock = &prog->print_lock; prog->philos[i].print_lock = &prog->print_lock;
prog->philos[i].dead_lock = &prog->dead_lock; prog->philos[i].dead_lock = &prog->dead_lock;
prog->philos[i].meal_lock = &prog->meal_lock; prog->philos[i].meal_lock = &prog->meal_lock;
prog->philos[i].dead_check = false; prog->philos[i].dead_check = false;
prog->philos[i].check_eating_count = &prog->check_eating_count; prog->philos[i].check_eating_count = &prog->check_eating_count;
prog->philos[i].l_fork = &forks[i];
if (i == 0) if (i == 0)
prog->philos[i].r_fork = &forks[prog->philos[i].nb_philo - 1]; prog->philos[i].r_fork = &forks[prog->philos[i].nb_philo - 1];
else else
prog->philos[i].r_fork = &forks[i - 1]; prog->philos[i].r_fork = &forks[i - 1];
prog->philos[i].l_fork = &forks[i];
i++; i++;
} }
if (ft_parsing_args(argc, argv, prog->philos)) return (ft_parsing_args(argc, argv, prog->philos));
return (ERROR);
return (NO_ERROR);
} }
t_error ft_init(t_i32 argc, t_str *argv, t_program *prog, t_philo *philo) t_error ft_init(t_i32 argc, t_str *argv, t_program *prog, t_philo *philo)
{ {
static t_mutex forks[MAXSUPPORT] = {0}; static t_mutex forks[MAXSUPPORT] = {0};
pthread_mutex_init(&prog->print_lock, NULL); prog->print_lock = (t_mutex)PTHREAD_MUTEX_INITIALIZER;
pthread_mutex_init(&prog->dead_lock, NULL); prog->dead_lock = (t_mutex)PTHREAD_MUTEX_INITIALIZER;
pthread_mutex_init(&prog->meal_lock, NULL); prog->meal_lock = (t_mutex)PTHREAD_MUTEX_INITIALIZER;
pthread_mutex_init(&prog->check_eating_count, NULL); prog->check_eating_count = (t_mutex)PTHREAD_MUTEX_INITIALIZER;
prog->philos = philo; prog->philos = philo;
prog->dead_flag = false; prog->dead_flag = false;
ft_init_fork(forks, ft_atou_return(argv[1]));
if (ft_init_philo(argc, argv, prog, forks)) if (ft_init_philo(argc, argv, prog, forks))
return (ERROR); return (ERROR);
if (philo->nb_philo != 0 && philo->nb_philo > MAXSUPPORT) if (philo->nb_philo != 0 && philo->nb_philo > MAXSUPPORT)

View file

@ -1,21 +1,22 @@
/* ************************************************************************** */ /* ************************************************************************** */
/* */ /* */
/* ::: :::::::: */ /* ::: :::::::: */
/* routine.c :+: :+: :+: */ /* routine.c :+: :+: :+: */
/* +:+ +:+ +:+ */ /* +:+ +:+ +:+ */
/* By: rparodi <rparodi@student.42.fr> +#+ +:+ +#+ */ /* By: rparodi <rparodi@student.42.fr> +#+ +:+ +#+ */
/* +#+#+#+#+#+ +#+ */ /* +#+#+#+#+#+ +#+ */
/* Created: 2024/06/11 11:42:31 by rparodi #+# #+# */ /* Created: 2024/06/11 11:42:31 by rparodi #+# #+# */
/* Updated: 2024/07/04 13:29:39 by rparodi ### ########.fr */ /* Updated: 2024/07/24 14:07:27 by rparodi ### ########.fr */
/* */ /* */
/* ************************************************************************** */ /* ************************************************************************** */
#include "../includes/philo.h" #include "../includes/philo.h"
#include <stdio.h>
t_bool dead_loop(t_philo *philo) t_bool dead_loop(t_philo *philo)
{ {
pthread_mutex_lock(philo->dead_lock); pthread_mutex_lock(philo->dead_lock);
if (philo[0].dead_check == true) if (philo->dead_check == true)
return (pthread_mutex_unlock(philo->dead_lock), true); return (pthread_mutex_unlock(philo->dead_lock), true);
pthread_mutex_unlock(philo->dead_lock); pthread_mutex_unlock(philo->dead_lock);
return (false); return (false);
@ -29,15 +30,18 @@ t_bool check_dead(t_philo *philo)
i = 0; i = 0;
while (i < philo[0].nb_philo) while (i < philo[0].nb_philo)
{ {
pthread_mutex_lock(philo->meal_lock);
timecheck = ft_time() - philo[i].start_time - philo[i].t_last_eat; timecheck = ft_time() - philo[i].start_time - philo[i].t_last_eat;
if (philo[i].t_last_eat != 0 && timecheck >= philo[i].t_death) if (timecheck >= philo[i].t_death)
{ {
pthread_mutex_unlock(philo[i].dead_lock); pthread_mutex_unlock(philo->meal_lock);
ft_logs("died\n", &philo[i]); ft_logs("died\n", &philo[i]);
philo[i].dead_check = true;
pthread_mutex_lock(philo[i].dead_lock); pthread_mutex_lock(philo[i].dead_lock);
philo[i].dead_check = true;
pthread_mutex_unlock(philo[i].dead_lock);
return (true); return (true);
} }
pthread_mutex_unlock(philo->meal_lock);
i++; i++;
} }
return (false); return (false);
@ -60,37 +64,26 @@ void counting_launch(t_philo *philo, t_u8 *counter)
t_bool check_eat(t_philo *philo) t_bool check_eat(t_philo *philo)
{ {
t_usize i;
t_u8 check; t_u8 check;
i = 0;
check = 0; check = 0;
if (philo[0].nb_eat == -1)
return (false);
counting_launch(philo, &check); counting_launch(philo, &check);
if (check == philo[0].nb_philo) if (check == philo[0].nb_philo)
{
pthread_mutex_lock(philo[0].dead_lock);
while (i < philo[0].nb_philo)
{
pthread_mutex_unlock(philo[i].dead_lock);
philo[i].dead_check = true;
pthread_mutex_lock(philo[i].dead_lock);
i++;
}
pthread_mutex_unlock(philo[0].dead_lock);
return (true); return (true);
}
return (false); return (false);
} }
void *ft_watch_dogs(void *ptr) void *ft_watch_dogs(void *ptr)
{ {
t_philo *philo; t_philo *philo;
t_usize i;
philo = (t_philo *) ptr; philo = (t_philo *) ptr;
if (philo == NULL) if (philo == NULL)
return (NULL); return (NULL);
while (philo[0].start_time > ft_time())
usleep(500);
i = philo[0].nb_philo;
while (true) while (true)
{ {
if (check_eat(philo) == true) if (check_eat(philo) == true)
@ -98,5 +91,11 @@ void *ft_watch_dogs(void *ptr)
if (check_dead(philo) == true) if (check_dead(philo) == true)
break ; break ;
} }
while (i-- != 0)
{
pthread_mutex_lock(philo[i].dead_lock);
philo[i].dead_check = true;
pthread_mutex_unlock(philo[i].dead_lock);
}
return (philo); return (philo);
} }

View file

@ -1,84 +0,0 @@
/* ************************************************************************** */
/* */
/* ::: :::::::: */
/* test.c :+: :+: :+: */
/* +:+ +:+ +:+ */
/* By: rparodi <rparodi@student.42.fr> +#+ +:+ +#+ */
/* +#+#+#+#+#+ +#+ */
/* Created: 2024/06/09 15:08:23 by rparodi #+# #+# */
/* Updated: 2024/06/17 12:24:16 by rparodi ### ########.fr */
/* */
/* ************************************************************************** */
#include <stdio.h>
#include <stdlib.h>
#include <pthread.h>
#include <sys/_types/_null.h>
#include <sys/time.h>
#include <time.h>
#include <unistd.h>
// printf derriere un mutex pour le printf
// zero printf apres une mort
// mort shared avec un mutex
// compte le nombre de ois manger par philo, et chec via un thread si tous a manger X fois
pthread_t philosopher[15];
pthread_mutex_t chopstick[15];
int ft_sleep(size_t milliseconds)
{
struct timeval start;
struct timeval tempo;
gettimeofday(&tempo, NULL);
gettimeofday(&start, NULL);
while ((tempo - start) < milliseconds)
{
usleep(500);
gettimeofday(&tempo, NULL);
}
return (0);
}
void *func(void *arg) {
int n = *((int *)arg);
printf("Philosopher %d is thinking\n", n);
pthread_mutex_lock(&chopstick[n]);
pthread_mutex_lock(&chopstick[(n + 1) % 15]);
printf("Philosopher %d is eating\n", n);
ft_sleep(3000000); // sleep for 3 seconds to simulate eating
pthread_mutex_unlock(&chopstick[n]);
pthread_mutex_unlock(&chopstick[(n + 1) % 15]);
printf("Philosopher %d finished eating\n", n);
free(arg); // Free the allocated memory
return NULL;
}
int main() {
int i;
for (i = 0; i < 15; i++)
pthread_mutex_init(&chopstick[i], NULL);
for (i = 0; i < 15; i++) {
int *arg = malloc(sizeof(*arg));
if (arg == NULL) {
fprintf(stderr, "Couldn't allocate memory for thread arg.\n");
exit(EXIT_FAILURE);
}
*arg = i;
pthread_create(&philosopher[i], NULL, func, arg);
}
for (i = 0; i < 15; i++)
pthread_join(philosopher[i], NULL);
for (i = 0; i < 15; i++)
pthread_mutex_destroy(&chopstick[i]);
return 0;
}