Skip to content

Commit

Permalink
implement thread ops error handling
Browse files Browse the repository at this point in the history
  • Loading branch information
alx-sch committed Oct 12, 2024
1 parent d3b07ff commit 3f64304
Show file tree
Hide file tree
Showing 9 changed files with 65 additions and 48 deletions.
24 changes: 12 additions & 12 deletions philo/include/types.h
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@
/* By: aschenk <aschenk@student.42berlin.de> +#+ +:+ +#+ */
/* +#+#+#+#+#+ +#+ */
/* Created: 2024/09/19 17:19:12 by aschenk #+# #+# */
/* Updated: 2024/10/11 22:26:12 by aschenk ### ########.fr */
/* Updated: 2024/10/11 23:38:34 by aschenk ### ########.fr */
/* */
/* ************************************************************************** */

Expand Down Expand Up @@ -107,16 +107,16 @@ Structure representing the overall simulation state:
haven't start eating.
- t_eat: Time in milliseconds a philosopher takes to eat.
- t_sleep: Time in milliseconds a philosopher sleeps after eating.
- t_think: Philosophers are altruistic in this simulation, meaning they delay
taking forks and eating for as long as possible without starving.
This behavior helps keep every philosopher alive as long as
possible, especially when there's an odd number of philosophers:
t_think = t_die - t_eat - t_sleep.
- t_think: Philosophers are altruistic in this simulation, meaning they
delay taking forks and eating for as long as possible without
starving. This behavior helps keep every philosopher alive as
long as possible, especially when there's an odd number of
philosophers: t_think = t_die - t_eat - t_sleep.
- max_meals: Max. number of meals a philosopher can eat before they stop
dining; `-1` means unlimited meals.
- full_philos: The number of philosophers who have eaten their maximum number
of meals (if specified) and have stopped eating.
- philo_dead: Flag indicating if a philosopher has died.
- stop_sim: Flag indicating if to stop the simulation.
- t_start_sim: Timestamp in milliseconds for when the simulation started.
- forks: Array of forks available for the philosophers.
- philos: Array of philosophers participating in the simulation.
Expand All @@ -127,8 +127,8 @@ Structure representing the overall simulation state:
- mtx_full_philos: Mutex for checking / increasing 'full_philos'.
- mtx_full_philos_init: Flag checking if 'full_philos' mutex has been
initialized.
- mtx_philo_dead: Mutex for synchronizing access to the `philo_dead` flag.
- mtx_philo_dead_init: Flag checking if 'philo dead' mutex has been initialized.
- mtx_stop_sim: Mutex for synchronizing access to the `stop_sim` flag.
- mtx_stop_sim_init: Flag checking if 'stop_sim' mutex has been initialized.
*/
typedef struct s_sim
{
Expand All @@ -139,7 +139,7 @@ typedef struct s_sim
int t_think;
int max_meals;
int full_philos;
int philo_dead;
int stop_sim;
t_ull t_start_sim;
t_fork *forks;
t_philo *philos;
Expand All @@ -148,8 +148,8 @@ typedef struct s_sim
int mtx_print_init;
t_mtx mtx_full_philos;
int mtx_full_philos_init;
t_mtx mtx_philo_dead;
int mtx_philo_dead_init;
t_mtx mtx_stop_sim;
int mtx_stop_sim_init;
} t_sim;

#endif
10 changes: 5 additions & 5 deletions philo/src/2_init_sim.c
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@
/* By: aschenk <aschenk@student.42berlin.de> +#+ +:+ +#+ */
/* +#+#+#+#+#+ +#+ */
/* Created: 2024/09/05 13:53:20 by aschenk #+# #+# */
/* Updated: 2024/10/11 22:17:42 by aschenk ### ########.fr */
/* Updated: 2024/10/11 23:39:03 by aschenk ### ########.fr */
/* */
/* ************************************************************************** */

Expand Down Expand Up @@ -59,11 +59,11 @@ Sets initial values for the simulation state and initializes mutexes.
static int init_sim_state(t_sim *sim, int argc, char **argv)
{
sim->full_philos = 0;
sim->philo_dead = 0;
sim->stop_sim = 0;
sim->forks = NULL;
sim->philos = NULL;
sim->mtx_print_init = 0;
sim->mtx_philo_dead_init = 0;
sim->mtx_stop_sim_init = 0;
if (init_args(sim, argc, argv))
return (1);
sim->t_think = sim->t_die - sim->t_eat - sim->t_sleep;
Expand All @@ -73,9 +73,9 @@ static int init_sim_state(t_sim *sim, int argc, char **argv)
return (1);
sim->mtx_full_philos_init = 1;
sim->mtx_print_init = 1;
if (mtx_action(&sim->mtx_philo_dead, INIT))
if (mtx_action(&sim->mtx_stop_sim, INIT))
return (1);
sim->mtx_philo_dead_init = 1;
sim->mtx_stop_sim_init = 1;
return (0);
}

Expand Down
6 changes: 3 additions & 3 deletions philo/src/3_eat.c
Original file line number Diff line number Diff line change
@@ -1,12 +1,12 @@
/* ************************************************************************** */
/* */
/* ::: :::::::: */
/* 4_eat.c :+: :+: :+: */
/* 3_eat.c :+: :+: :+: */
/* +:+ +:+ +:+ */
/* By: aschenk <aschenk@student.42berlin.de> +#+ +:+ +#+ */
/* +#+#+#+#+#+ +#+ */
/* Created: 2024/10/11 16:23:15 by aschenk #+# #+# */
/* Updated: 2024/10/11 19:54:59 by aschenk ### ########.fr */
/* Updated: 2024/10/11 23:30:19 by aschenk ### ########.fr */
/* */
/* ************************************************************************** */

Expand Down Expand Up @@ -85,7 +85,7 @@ int pick_forks_and_log(t_philo *philo)
return (pick_forks(philo));
else
{
usleep(900);
(void)usleep(900);
return (pick_forks(philo));
}
}
Expand Down
18 changes: 9 additions & 9 deletions philo/src/3_eat_sleep_think.c
Original file line number Diff line number Diff line change
@@ -1,12 +1,12 @@
/* ************************************************************************** */
/* */
/* ::: :::::::: */
/* 5_eat_sleep_think.c :+: :+: :+: */
/* 3_eat_sleep_think.c :+: :+: :+: */
/* +:+ +:+ +:+ */
/* By: aschenk <aschenk@student.42berlin.de> +#+ +:+ +#+ */
/* +#+#+#+#+#+ +#+ */
/* Created: 2024/10/05 18:47:34 by aschenk #+# #+# */
/* Updated: 2024/10/11 21:33:23 by aschenk ### ########.fr */
/* Updated: 2024/10/11 23:41:10 by aschenk ### ########.fr */
/* */
/* ************************************************************************** */

Expand All @@ -24,23 +24,23 @@ reaches the maximum number of meals.
void *eat_sleep_think(void *arg);

/**
Checks whether a philo thread should stop by accessing the `philo_dead` flag.
Checks whether a philo thread should stop by accessing the `stop_sim` flag.
@param sim Pointer to the simulation struct containing the `philo_dead` flag.
@param sim Pointer to the simulation struct containing the `stop_sim` flag.
@return The value of the `stop_sim` flag:
`0` if no philo died (simulation can continue);
`1` if a philosopher has died (simulation should stop);
`2` if there is an error in mutex (un)locking.
*/
static int check_death(t_philo *philo)
static int stop_sim(t_philo *philo)
{
int dead;

if (mtx_action(&philo->sim->mtx_philo_dead, LOCK))
if (mtx_action(&philo->sim->mtx_stop_sim, LOCK))
return (2);
dead = philo->sim->philo_dead;
if (mtx_action(&philo->sim->mtx_philo_dead, UNLOCK))
dead = philo->sim->stop_sim;
if (mtx_action(&philo->sim->mtx_stop_sim, UNLOCK))
return (2);
return (dead);
}
Expand Down Expand Up @@ -141,7 +141,7 @@ void *eat_sleep_think(void *arg)
max_meals = philo->sim->max_meals;
if (handle_no_meals(philo, max_meals) == 1)
return (NULL);
while (check_death(philo) == 0)
while (stop_sim(philo) == 0)
{
(void)pick_forks_and_log(philo);
(void)eat_and_log(philo, t_eat);
Expand Down
10 changes: 5 additions & 5 deletions philo/src/4_monitor.c
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@
/* By: aschenk <aschenk@student.42berlin.de> +#+ +:+ +#+ */
/* +#+#+#+#+#+ +#+ */
/* Created: 2024/10/11 17:28:17 by aschenk #+# #+# */
/* Updated: 2024/10/11 22:16:56 by aschenk ### ########.fr */
/* Updated: 2024/10/11 23:39:36 by aschenk ### ########.fr */
/* */
/* ************************************************************************** */

Expand Down Expand Up @@ -53,10 +53,10 @@ static int handle_death(t_sim *sim, t_philo *philo)
if (mtx_action(&philo->mtx_last_meal, UNLOCK)
|| record_time_of_death(philo)
|| print_action(philo->timestamp_death, philo, DIE, 0)
|| mtx_action(&sim->mtx_philo_dead, LOCK))
|| mtx_action(&sim->mtx_stop_sim, LOCK))
return (2);
sim->philo_dead = 1;
if (mtx_action(&sim->mtx_philo_dead, UNLOCK))
sim->stop_sim = 1;
if (mtx_action(&sim->mtx_stop_sim, UNLOCK))
return (2);
return (1);
}
Expand Down Expand Up @@ -128,7 +128,7 @@ void *monitor(void *arg)
return (NULL);
i++;
}
usleep(100);
(void)usleep(100);
}
return (NULL);
}
25 changes: 21 additions & 4 deletions philo/src/5_run_sim.c
Original file line number Diff line number Diff line change
@@ -1,12 +1,12 @@
/* ************************************************************************** */
/* */
/* ::: :::::::: */
/* 7_run_sim.c :+: :+: :+: */
/* 5_run_sim.c :+: :+: :+: */
/* +:+ +:+ +:+ */
/* By: aschenk <aschenk@student.42berlin.de> +#+ +:+ +#+ */
/* +#+#+#+#+#+ +#+ */
/* Created: 2024/10/11 22:06:38 by aschenk #+# #+# */
/* Updated: 2024/10/11 22:11:25 by aschenk ### ########.fr */
/* Updated: 2024/10/11 23:57:52 by aschenk ### ########.fr */
/* */
/* ************************************************************************** */

Expand Down Expand Up @@ -44,7 +44,7 @@ static int start_monitoring(t_sim *sim)
print_err_msg(ERR_TR_CREATE);
return (1);
}
usleep(100);
(void)usleep(100);
return (0);
}

Expand Down Expand Up @@ -75,6 +75,9 @@ static int end_monitoring(t_sim *sim)
Starts the dining simulation by creating threads for each philosopher. Each
thread will run the `dining` function that simulates the philosopher's behavior.
If any thread creation fails, the simulation stops, all previously created
threads are joined (cleaned up), and the simulation is terminated.
@param sim Pointer to the sim structure, which holds the philosopher data.
@return `0` on success;
Expand All @@ -83,13 +86,22 @@ thread will run the `dining` function that simulates the philosopher's behavior.
static int start_dining(t_sim *sim)
{
int i;
int nr_philo;

i = 0;
while (i < sim->nr_philo)
nr_philo = sim->nr_philo;
while (i < nr_philo)
{
if (pthread_create(&sim->philos[i].thread_id, NULL, &eat_sleep_think,
&sim->philos[i]))
{
mtx_action(&sim->mtx_stop_sim, LOCK);
sim->stop_sim = 1;
mtx_action(&sim->mtx_stop_sim, UNLOCK);
while (i-- >= 0)
pthread_join(sim->philos[i].thread_id, NULL);
end_monitoring(sim);
(void)usleep(100);
print_err_msg(ERR_TR_CREATE);
return (1);
}
Expand All @@ -116,6 +128,11 @@ static int end_dining(t_sim *sim)
{
if (pthread_join(sim->philos[i].thread_id, NULL))
{
mtx_action(&sim->mtx_stop_sim, LOCK);
sim->stop_sim = 1;
mtx_action(&sim->mtx_stop_sim, UNLOCK);
end_monitoring(sim);
(void)usleep(100);
print_err_msg(ERR_TR_JOIN);
return (1);
}
Expand Down
10 changes: 5 additions & 5 deletions philo/src/utils/1_print_action.c
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@
/* By: aschenk <aschenk@student.42berlin.de> +#+ +:+ +#+ */
/* +#+#+#+#+#+ +#+ */
/* Created: 2024/10/05 13:49:37 by aschenk #+# #+# */
/* Updated: 2024/10/11 14:42:29 by aschenk ### ########.fr */
/* Updated: 2024/10/11 23:40:16 by aschenk ### ########.fr */
/* */
/* ************************************************************************** */

Expand Down Expand Up @@ -123,13 +123,13 @@ compilation) before being printed to enhance readability (default: no rounding).
int print_action(t_ull timestamp, t_philo *philo, t_action action,
int update_timestamp)
{
mtx_action(&philo->sim->mtx_philo_dead, LOCK);
if (philo->sim->philo_dead)
mtx_action(&philo->sim->mtx_stop_sim, LOCK);
if (philo->sim->stop_sim)
{
mtx_action(&philo->sim->mtx_philo_dead, UNLOCK);
mtx_action(&philo->sim->mtx_stop_sim, UNLOCK);
return (0);
}
mtx_action(&philo->sim->mtx_philo_dead, UNLOCK);
mtx_action(&philo->sim->mtx_stop_sim, UNLOCK);
if (mtx_action(&philo->sim->mtx_print, LOCK))
return (1);
if (update_timestamp)
Expand Down
4 changes: 2 additions & 2 deletions philo/src/utils/3_time.c
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@
/* By: aschenk <aschenk@student.42berlin.de> +#+ +:+ +#+ */
/* +#+#+#+#+#+ +#+ */
/* Created: 2024/09/20 20:44:46 by aschenk #+# #+# */
/* Updated: 2024/10/10 15:51:05 by aschenk ### ########.fr */
/* Updated: 2024/10/11 23:31:09 by aschenk ### ########.fr */
/* */
/* ************************************************************************** */

Expand Down Expand Up @@ -128,7 +128,7 @@ int precise_wait(int duration_to_wait)
return (1);
if (current_time >= time_stop_waiting)
break ;
usleep((duration_to_wait * 1000) / SLEEP_INTERVALS);
(void)usleep((duration_to_wait * 1000) / SLEEP_INTERVALS);
}
return (0);
}
6 changes: 3 additions & 3 deletions philo/src/utils/4_free.c
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@
/* By: aschenk <aschenk@student.42berlin.de> +#+ +:+ +#+ */
/* +#+#+#+#+#+ +#+ */
/* Created: 2024/09/18 18:08:52 by aschenk #+# #+# */
/* Updated: 2024/10/11 19:47:33 by aschenk ### ########.fr */
/* Updated: 2024/10/11 23:41:25 by aschenk ### ########.fr */
/* */
/* ************************************************************************** */

Expand Down Expand Up @@ -95,8 +95,8 @@ void cleanup_sim(t_sim **sim_ptr)
clean_philos(sim);
if (sim->mtx_print_init)
mtx_action(&sim->mtx_print, DESTROY);
if (sim->mtx_philo_dead_init)
mtx_action(&sim->mtx_philo_dead, DESTROY);
if (sim->mtx_stop_sim_init)
mtx_action(&sim->mtx_stop_sim, DESTROY);
free(sim);
*sim_ptr = NULL;
}

0 comments on commit 3f64304

Please sign in to comment.