Skip to content

Instantly share code, notes, and snippets.

@ecylmz
Created March 29, 2012 16:10
Show Gist options
  • Save ecylmz/2239086 to your computer and use it in GitHub Desktop.
Save ecylmz/2239086 to your computer and use it in GitHub Desktop.
Dining philosophers problem
#include <stdio.h>
#include <stdlib.h>
#include <pthread.h>
#include <unistd.h> /* sleep için */
#include <stdint.h> /* uintptr_t için */
/*
* 5 filozof yuvarlak bir masaya oturur. Masada 5 tane tabak ve 5 tane de
* çatal vardır. 5 kişi aynı anda yiyemeceklerini farketmeleri zor olmadı ve
* çatalları sırayla kullanalım dediler (tabii temizledikten sonra).
*/
/*
* Hazırlıklar başlar.
*/
/* Filozof sayısı */
#define NUMP 5
/* Çatallar için kardış */
pthread_mutex_t fork_mutex[NUMP];
/* Yemek sırasında girecekler için kardış */
pthread_mutex_t eat_mutex;
/* Kullanılabilir boş alan için durum değişkeni tanımlanır ve ilklenir */
pthread_cond_t space_avail = PTHREAD_COND_INITIALIZER;
/* O anda yemek yiyenlerin sayısını belirten global değişken */
int num_diners = 0;
/* Kaçıncı filozofun yemek yediği bilgisi void argümanla alınır ve bu da philo
* değişkeninde saklanır.
*/
void
*diner(void *arg)
{
/*
* Argüman ile alınan void işaretçiden pozitif tamsayıya
* dönüştürmek için uygun tip tanımlanır.
*/
uintptr_t philo;
/* Tip dönüşümü */
philo = (uintptr_t) arg;
/*
* Filozofların kaç kez yemek yediklerini tutmak için değişken
* tanımlanır.
*/
int eating = 0;
/* Filozoflar bize kim olduklarını söylerler */
printf("I'm diner %d\n", philo);
/*
* Bir filozof 5 kere yemek yiyebilir. Kritik değişken
* buradaki eating değişkeni, eğer ki yemek yiyen kişi
* yemeğe başlamadan önce çatalları "kardış" ile kilitlemezse
* diğer filozoflar bu çatallara ulaşmak ister ve ortalık karışır.
*/
while (eating < 5) {
printf("%d is thinking\n", philo);
sleep( philo / 2 );
printf("%d is hungry\n", philo );
/* Filozof sıraya girer ve bu sıra benim diye diğerlerine söyler. */
pthread_mutex_lock(&eat_mutex);
/* Filozof yemeğe başlamadan önce boş yer var mı kontrolü yapar */
if (num_diners == (NUMP - 1))
/* Yer yoksa filozoflardan birisinin yemeğinin bitmesini
* bekler
*/
pthread_cond_wait(&space_avail, &eat_mutex);
/* Boş yer bulan filozof sofraya oturur */
num_diners++;
/* Sıradan sofraya geçtiği için sıradaki yeri boşaltmış oldu */
pthread_mutex_unlock(&eat_mutex);
/* Sağındaki ve solundaki çatalları alır. */
pthread_mutex_lock(&fork_mutex[philo]);
pthread_mutex_lock(&fork_mutex[( philo + 1) % NUMP]);
/* Şimdi yemeği yiyebilir */
printf("%d is eating\n", philo);
/* Kaç kez yemek yediğini unutmamak için `eating` değişkenini
* arttıır.
*/
eating++;
/* Filozofun yemek yeme süresi */
sleep(1);
/* Yemek bittiyse bunu duyurur ve çatallarını geri bırakır. */
printf("%d is done eating\n", philo);
pthread_mutex_unlock(&fork_mutex[philo]);
pthread_mutex_unlock(&fork_mutex[(philo + 1)%NUMP]);
/* Filozof yine sıraya girer. Bu seferki amacı sırada bekleyen varsa
* kendisinin yemeğinin bittiğini diğer filozoflara duyurmak.
* Sıraya girerken kullanılan `eat_mutex` kardışını kilitler.
*/
pthread_mutex_lock(&eat_mutex);
/* Eğer yemek yiyenlerin sayısı 4 ise kendisi sıradan çıkacağı için
* Ben çıkıyorum yemekten sinyalini gönderir.
*/
if (num_diners == (NUMP - 1))
pthread_cond_signal(&space_avail);
num_diners--;
/* Şimdi sıradaki yerinden de çıkabilir */
pthread_mutex_unlock(&eat_mutex);
}
/*
* Yemek yeme işleri tamamlandı. pthread_join bu çağrıyı bekliyor.
*/
pthread_exit(NULL);
}
int
main()
{
uintptr_t i;
/*
* Evre dizisi.
*/
pthread_t diner_thread[NUMP];
/*
* Yemek sırası için karşılıklı dışlayıcı hazırla.
*/
pthread_mutex_init(&eat_mutex, NULL);
/*
* Çatallar için karşılıklı dışlayıcı hazırla.
*/
for (i=0; i < NUMP; i++)
pthread_mutex_init(&fork_mutex[i], NULL);
/*
* Evreleri oluştur ve ilgili işleve bağla.
*/
for (i=0; i < NUMP; i++){
pthread_create(&diner_thread[i], NULL, diner, (void *) i);
}
/*
* Filozofların yemeklerini yemelerini bekle.
*/
for (i=0; i < NUMP; i++)
pthread_join(diner_thread[i], NULL);
exit(EXIT_SUCCESS);
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment