#include #include #include #include #include #define N 5 /* 哲学家数目 */ #define LEFT (i-1+N)%N /* i的左邻号码 */ #define RIGHT (i+1)%N /* i的右邻号码 */ #define THINKING 0 /* 哲学家正在思考 */ #define HUNGRY 1 /* 哲学家想取得叉子 */ #define EATING 2 /* 哲学家正在吃面 */ #define TIMES 4 /* 吃4次饭 */ #define SLEEP_TIME 10 //-----------------philosopher problem using monitor ------------ /*PSEUDO CODE :philosopher problem using semaphore system DINING_PHILOSOPHERS VAR me: semaphore, initially 1; # for mutual exclusion s[5]: semaphore s[5], initially 0; # for synchronization pflag[5]: {THINK, HUNGRY, EAT}, initially THINK; # philosopher flag # As before, each philosopher is an endless cycle of thinking and eating. procedure philosopher(i) { while TRUE do { THINKING; take_chopsticks(i); EATING; drop_chopsticks(i); } } # The take_chopsticks procedure involves checking the status of neighboring # philosophers and then declaring one's own intention to eat. This is a two-phase # protocol; first declaring the status HUNGRY, then going on to EAT. procedure take_chopsticks(i) { DOWN(me); # critical section pflag[i] := HUNGRY; test[i]; UP(me); # end critical section DOWN(s[i]) # Eat if enabled } void test(i) # Let phil[i] eat, if waiting { if ( pflag[i] == HUNGRY && pflag[i-1] != EAT && pflag[i+1] != EAT) then { pflag[i] := EAT; UP(s[i]) } } # Once a philosopher finishes eating, all that remains is to relinquish the # resources---its two chopsticks---and thereby release waiting neighbors. void drop_chopsticks(int i) { DOWN(me); # critical section test(i-1); # Let phil. on left eat if possible test(i+1); # Let phil. on rght eat if possible UP(me); # up critical section } */ //---------- philosophers problem using semaphore ---------------------- int state_sema[N]; /* 记录每个人状态的数组 */ /* 信号量是一个特殊的整型变量 */ semaphore_t mutex; /* 临界区互斥 */ semaphore_t s[N]; /* 每个哲学家一个信号量 */ struct proc_struct *philosopher_proc_sema[N]; void phi_test_sema(i) /* i:哲学家号码从0到N-1 */ { if(state_sema[i]==HUNGRY&&state_sema[LEFT]!=EATING &&state_sema[RIGHT]!=EATING) { state_sema[i]=EATING; up(&s[i]); } } void phi_take_forks_sema(int i) /* i:哲学家号码从0到N-1 */ { down(&mutex); /* 进入临界区 */ state_sema[i]=HUNGRY; /* 记录下哲学家i饥饿的事实 */ phi_test_sema(i); /* 试图得到两只叉子 */ up(&mutex); /* 离开临界区 */ down(&s[i]); /* 如果得不到叉子就阻塞 */ } void phi_put_forks_sema(int i) /* i:哲学家号码从0到N-1 */ { down(&mutex); /* 进入临界区 */ state_sema[i]=THINKING; /* 哲学家进餐结束 */ phi_test_sema(LEFT); /* 看一下左邻居现在是否能进餐 */ phi_test_sema(RIGHT); /* 看一下右邻居现在是否能进餐 */ up(&mutex); /* 离开临界区 */ } int philosopher_using_semaphore(void * arg) /* i:哲学家号码,从0到N-1 */ { int i, iter=0; i=(int)arg; cprintf("I am No.%d philosopher_sema\n",i); while(iter++cv[i]) ; } } void phi_take_forks_condvar(int i) { down(&(mtp->mutex)); //--------into routine in monitor-------------- // LAB7 EXERCISE1: YOUR CODE // I am hungry // try to get fork //--------leave routine in monitor-------------- if(mtp->next_count>0) up(&(mtp->next)); else up(&(mtp->mutex)); } void phi_put_forks_condvar(int i) { down(&(mtp->mutex)); //--------into routine in monitor-------------- // LAB7 EXERCISE1: YOUR CODE // I ate over // test left and right neighbors //--------leave routine in monitor-------------- if(mtp->next_count>0) up(&(mtp->next)); else up(&(mtp->mutex)); } //---------- philosophers using monitor (condition variable) ---------------------- int philosopher_using_condvar(void * arg) { /* arg is the No. of philosopher 0~N-1*/ int i, iter=0; i=(int)arg; cprintf("I am No.%d philosopher_condvar\n",i); while(iter++