Skip to content

Instantly share code, notes, and snippets.

@effective-light
Last active October 5, 2018 19:17
Show Gist options
  • Select an option

  • Save effective-light/78c328dbb1c4f022a767c6c46c09e8d9 to your computer and use it in GitHub Desktop.

Select an option

Save effective-light/78c328dbb1c4f022a767c6c46c09e8d9 to your computer and use it in GitHub Desktop.
Simple monitor implementation
#include <stdio.h>
#include <unistd.h>
#include <stdlib.h>
#include <pthread.h>
#define N 50
#define M 1000
int marbles = M;
int scores[N];
// Declare and initialize locks and CVs
pthread_mutex_t mux = PTHREAD_MUTEX_INITIALIZER;
pthread_cond_t con_cv = PTHREAD_COND_INITIALIZER;
pthread_cond_t prod_cv = PTHREAD_COND_INITIALIZER;
void print_and_clear_scores() {
int i;
int sum = 0;
printf("Scores:\n");
for(i = 0; i < N; i++) {
printf("%d ", scores[i]);
sum += scores[i];
scores[i] = 0;
}
printf(" SUM= %d\n", sum);
}
void eat(int id){
pthread_mutex_lock(&mux);
while (marbles == 0) {
pthread_cond_wait(&con_cv, &mux);
}
marbles--;
scores[id]++;
pthread_cond_signal(&prod_cv);
pthread_mutex_unlock(&mux);
}
void restart_game() {
pthread_mutex_lock(&mux);
while (marbles > 0) {
pthread_cond_wait(&prod_cv, &mux);
}
print_and_clear_scores();
marbles = M;
// must broadcast to prevent starvation
pthread_cond_broadcast(&con_cv);
pthread_mutex_unlock(&mux);
}
void *hippo(void *id_ptr) {
long int id = (long int)id_ptr;
while (1) eat(id);
pthread_exit(NULL);
}
void *referee(void *ID) {
while (1) restart_game();
}
int main() {
pthread_t hippos[N];
pthread_t ref;
long i;
for(i = 0; i < N; i++) {
scores[i] = 0;
}
for(i = 0; i < N; i++) {
pthread_create(&hippos[i], NULL, hippo, (void *)i);
}
pthread_create(&ref, NULL, referee, NULL);
for(i = 0; i < N; i++) {
pthread_join(hippos[i], NULL);
}
pthread_join(ref, NULL);
pthread_exit(NULL);
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment