#include <stdio.h>
#include <stdlib.h>
#include <signal.h>
#include <unistd.h>
#include <time.h>
#include <sys/ipc.h>
#include <sys/shm.h>
#include <sys/sem.h>
#include <sys/types.h>
#define MAX_BUFFER_SIZE 5
#define SHM_MODE 0600
#define SEM_MODE 0600
#define N 5
#define THINKING 0
#define HUNGRY 1
#define EATING 2
int state[N];
int sem_id;
int mutex;
int s[N];
//P Operation
void Wait(int sem_id,int sem_num)
{
struct sembuf sop;
sop.sem_num = sem_num;
sop.sem_op = -1;
sop.sem_flg = 0;
if (semop(sem_id, &sop, 1) == -1) {
perror("Wait failed");
exit(1);
}
}
//V Operation
void Signal(int sem_id,int sem_num)
{
struct sembuf sop;
sop.sem_num = sem_num;
sop.sem_op = 1;
sop.sem_flg = 0;
if (semop(sem_id, &sop, 1) == -1) {
perror("Signal failed");
exit(1);
}
}
void test(int i) {
if (state[i] == HUNGRY && state[LEFT] != EATING && state[RIGHT] != EATING) {
state[i] = EATING;
Signal(sem_id, s[i]);
}
}
void take_forks(int i) {
Wait(sem_id, mutex);
state[i] = HUNGRY;
test(i);
Signal(sem_id, mutex);
Wait(sem_id, s[i]);
}
void put_forks(int i) {
Wait(sem_id, mutex);
state[i] = THINKING;
test(LEFT);
test(RIGHT);
Signal(sem_id, mutex);
}
void think(int i)
{
printf("The philosopher of %d is thinking.\n", i);
}
void eat(int i)
{
printf("The philosopher of %d is eating.\n", i);
sleep(1);
}
void Philosophers(int i)
{
while (1)
{
think(i);
take_forks(i); // Take forks
eat(i);
put_forks(i); // Put forks
printf("The philosopher of %d has finished eating.\n", i);
}
exit(0);
}
int main()
{
sem_id = semget(IPC_PRIVATE, N+1, IPC_CREAT | SEM_MODE); // Initialize semaphores
for(int i = 0; i < N; i++) {
semctl(sem_id, i, SETVAL, 1);
s[i] = i;
}
mutex = N;
for (int i = 0; i < N; i++) {
if(fork() == 0) {
Philosophers(i); // Fork child processes
}
}
printf("Parent Process is over!\n");
fflush(stdout);
exit(0);
return 0;
}