110 likes | 396 Vues
Classical Synchronization Problems. CS 537 - Introduction to Operating Systems. Classical Problem 1. Producer-Consumer. #include <stdio.h> #include <semaphore.h> #define SIZE 50 #define NUM_THREADS 5 struct object* buffer; sem_t mutex, empty, full; void nap() {
E N D
Classical Synchronization Problems CS 537 - Introduction to Operating Systems
Classical Problem 1 Producer-Consumer
#include <stdio.h> #include <semaphore.h> #define SIZE 50 #define NUM_THREADS 5 struct object* buffer; sem_t mutex, empty, full; void nap() { int sleepTime = (int)(5 * random()); sleep(sleepTime); } void enter(struct object item) { empty.down(); mutex.down(); count++; buffer[in] = item; in = (in + 1) % SIZE; mutex.up(); full.up(); } struct object remove() { full.down(); mutex.down(); count--; struct object item = buffer[out]; out = (out + 1) % SIZE; mutex.up(); empty.up(); return item; }
void producer() { struct object newObj; for(;;) { nap(); newObj = getObject(); enter(newObj); } } void consumer() { struct object item; for(;;) { nap(); item = remove(); useItem(item); } } int main(int argc, char** argv) { pthread_t threads[NUM_THREADS]; int i; sem_init(&mutex, 0, 1); sem_init(&empty, 0, SIZE); sem_init(&full, 0, 0); for(i=0; i<NUM_THREADS; i++) { if(i % 2) pthread_create(&threads[i], NULL, (void*)producer, NULL); else pthread_create(&threads[i], NULL, (void*)consumer, NULL); } consumer(); return 0; }
Classical Problem 2 Readers-Writers
Readers-Writers • Several threads accessing a database • Some threads read the database (readers) • Some threads write the database (writers) • Multiple readers can be accessing database at a time if no writers accessing it • Only one thread can be accessing database if it is a writer • 2 major variations • no reader waits if no writer in database • writers can starve • all readers wait if a writer is waiting • writer has to wait until current reader (or writer) is finished with database • readers may starve • Many more variations to deal with starvation issues • Following example is for the first variant • starvation is disregarded
#include <stdio.h> #include <pthreads.h> #define NUM_THREADS 5 sem_t mutex, database; void reader() { while(true) { nap(); startRead(); nap(); endRead(); } } void writer() { while(true) { nap(); startWrite(); nap(); endWrite(); } } void nap() { int sleepTime = (int)(5 * random()); sleep(sleepTime); }
void startRead() { mutex.down(); readerCount++; if(readerCount == 1) { database.down(); } mutex.up(); } void endRead() { mutex.down(); readerCount--; if(readerCount == 0) { database.up(); } mutex.up(); } void startWrite() { database.down(); } void endWrite() { database.up(); } int main() { pthread_t threads[NUM_THREADS]; int i; sem_init(&mutex, 0, 1); sem_init(&database, 0, 1); for(i=0; i<NUM_THREADS; i++) { if(i % 2) pthread_create(&threads[i], NULL, (void*)reader, NULL); else pthread_create(&threads[i], NULL, (void*)writer, NULL); } writer(); return 0; }