#include <stdio.h>
#include <stdlib.h>
#include <pthread.h>
#include <semaphore.h>
#include <unistd.h>
//global variables
int c1, c2; //counters for imp1, imp2
pthread_mutex_t m1, m2;
sem_t corridor;
//implementation thread attendant
void * attendant( void * arg) {
sleep( 2 ) ; //rest 2 seconds
if ( c1== 0 && c2== 0 ) {
printf ( "I'm starting to clean up\n " ) ; sem_wait( & corridor) ;
sleep( 2 ) ;
sem_post( & corridor) ;
printf ( "I finished cleaning n" ) ; } else {
printf ( "I can't clean, the corridor is busy\n " ) ; }
return NULL;
}
//thread employee type 1
void * emp1( void * arg) {
printf ( "I'm the number %d\n " , c1
) ; pthread_mutex_lock( & m1) ; //beginning critical section
c1++; //it increases to signal the presence of a thread of the same type that wants to enter the corridor
if ( c1 == 1 ) { //the thread is the only one in the corridor. Can pass
printf ( "I am the first of my group n" ) ; sem_wait( & corridor) ; //takes possession of the corridor
}
pthread_mutex_unlock( & m1) ; //allows other threads of the same type to pass in the corridor since it was the first in his group. End of critical section
// invents "passage" function
pthread_mutex_lock( & m1) ; //beginning of the critical section. Once crossed the corridor, the variable c1 is modified. A mutex is used to avoid inconsistency
c1--;
if ( c1 == 0 ) {
printf ( "I am the last of my group n" ) ; sem_post( & corridor) ;
} //if c1 == 0, it is the last thread imp1 and releases the corridor
pthread_mutex_unlock( & m1) ; //end critical section
return NULL;
}
//thread employee type 2
void * emp2( void * arg) {
printf ( "I'm the number %d\n " , c1
) ; pthread_mutex_lock( & m2) ; //beginning critical section
c2++; //it increases to signal the presence of a thread of the same type that wants to enter the corridor
if ( c2 == 1 ) { // the thread is the only one in the corridor. Can pass
printf ( "I am the first of my group n" ) ; sem_wait( & corridor) ; //takes possession of the corridor
}
pthread_mutex_unlock( & m2) ; //allows other threads of the same type to pass in the corridor since it was the first in his group. End of critical sectionritica
// invents "passage" function
pthread_mutex_lock( & m2) ; //beginning of the critical section. Once crossed the corridor, the variable c1 is modified. A mutex is used to avoid inconsistency
c2--;
if ( c2 == 0 ) {
printf ( "I am the last of my group n" ) ; sem_post( & corridor) ;
} //if c1 == 0, it is the last thread imp1 and releases the corridor
pthread_mutex_unlock( & m2) ; //end critical section
return NULL;
}
int main( int argc, char const * argv[ ] ) {
//pthread_t emp1, emp2, attendant;
pthread_t idt;
int r; //var random to create thread emp1 or emp2
int i; //index
//variable initialization
c1 = c2 = 0 ;
pthread_mutex_init( & m1, NULL) ;
pthread_mutex_init( & m2, NULL) ;
sem_init( & corridor, 0 , 1 ) ;
pthread_create( & idt, NULL, attendant, NULL) ;
while ( i< 40 ) {
if ( r== 0 ) {
printf ( "Employee creation 1\n " ) ; pthread_create( & idt, NULL, emp1, NULL) ;
} else {
printf ( "Employee creation 1\n " ) ; pthread_create( & idt, NULL, emp2, NULL) ;
}
i++;
}
return 0 ;
}
I2luY2x1ZGUgPHN0ZGlvLmg+CiNpbmNsdWRlIDxzdGRsaWIuaD4KI2luY2x1ZGUgPHB0aHJlYWQuaD4KI2luY2x1ZGUgPHNlbWFwaG9yZS5oPgojaW5jbHVkZSA8dW5pc3RkLmg+CgoKLy9nbG9iYWwgdmFyaWFibGVzIAppbnQgYzEsYzI7IC8vY291bnRlcnMgZm9yIGltcDEsIGltcDIKcHRocmVhZF9tdXRleF90IG0xLCBtMjsKc2VtX3QgY29ycmlkb3I7IAoKLy9pbXBsZW1lbnRhdGlvbiB0aHJlYWQgYXR0ZW5kYW50CnZvaWQqIGF0dGVuZGFudCh2b2lkKiBhcmcpewogICAgc2xlZXAoMik7IC8vcmVzdCAyIHNlY29uZHMKICAgIGlmIChjMT09MCAmJiBjMj09MCl7CiAgICAgICAgcHJpbnRmKCJJJ20gc3RhcnRpbmcgdG8gY2xlYW4gdXBcbiIpOwogICAgICAgIHNlbV93YWl0KCZjb3JyaWRvcik7CiAgICAgICAgc2xlZXAoMik7CiAgICAgICAgc2VtX3Bvc3QoJmNvcnJpZG9yKTsKICAgICAgICBwcmludGYgKCJJIGZpbmlzaGVkIGNsZWFuaW5nIG4iKTsKICAgICAgICB9ZWxzZXsKICAgICAgICAgICBwcmludGYgKCJJIGNhbid0IGNsZWFuLCB0aGUgY29ycmlkb3IgaXMgYnVzeVxuIik7CiAgICAgICAgfQogICAgcmV0dXJuIE5VTEw7Cn0KCgovL3RocmVhZCBlbXBsb3llZSB0eXBlIDEKdm9pZCogZW1wMSh2b2lkICphcmcpewogICAgcHJpbnRmKCJJJ20gdGhlIG51bWJlciAlZFxuIiwgYzEpOwogICAgcHRocmVhZF9tdXRleF9sb2NrKCZtMSk7IC8vYmVnaW5uaW5nIGNyaXRpY2FsIHNlY3Rpb24KICAgIGMxKys7ICAgICAgICAgICAgICAgICAgICAvL2l0IGluY3JlYXNlcyB0byBzaWduYWwgdGhlIHByZXNlbmNlIG9mIGEgdGhyZWFkIG9mIHRoZSBzYW1lIHR5cGUgdGhhdCB3YW50cyB0byBlbnRlciB0aGUgY29ycmlkb3IKICAgIGlmIChjMSA9PSAxKXsgICAgICAgICAgICAvL3RoZSB0aHJlYWQgaXMgdGhlIG9ubHkgb25lIGluIHRoZSBjb3JyaWRvci4gQ2FuIHBhc3MKICAgICAgICBwcmludGYgKCJJIGFtIHRoZSBmaXJzdCBvZiBteSBncm91cCBuIik7CiAgICAgICAgc2VtX3dhaXQoJmNvcnJpZG9yKTsgIC8vdGFrZXMgcG9zc2Vzc2lvbiBvZiB0aGUgY29ycmlkb3IKICAgIH0KICAgIHB0aHJlYWRfbXV0ZXhfdW5sb2NrKCZtMSk7IC8vYWxsb3dzIG90aGVyIHRocmVhZHMgb2YgdGhlIHNhbWUgdHlwZSB0byBwYXNzIGluIHRoZSBjb3JyaWRvciBzaW5jZSBpdCB3YXMgdGhlIGZpcnN0IGluIGhpcyBncm91cC4gRW5kIG9mIGNyaXRpY2FsIHNlY3Rpb24KCiAgICAvLyBpbnZlbnRzICJwYXNzYWdlIiBmdW5jdGlvbgoKICAgIHB0aHJlYWRfbXV0ZXhfbG9jaygmbTEpOyAgLy9iZWdpbm5pbmcgb2YgdGhlIGNyaXRpY2FsIHNlY3Rpb24uIE9uY2UgY3Jvc3NlZCB0aGUgY29ycmlkb3IsIHRoZSB2YXJpYWJsZSBjMSBpcyBtb2RpZmllZC4gQSBtdXRleCBpcyB1c2VkIHRvIGF2b2lkIGluY29uc2lzdGVuY3kKICAgIGMxLS07CiAgICBpZihjMSA9PSAwKXsKICAgICAgICBwcmludGYgKCJJIGFtIHRoZSBsYXN0IG9mIG15IGdyb3VwIG4iKTsKICAgICAgICBzZW1fcG9zdCgmY29ycmlkb3IpOwogICAgfSAvL2lmIGMxID09IDAsIGl0IGlzIHRoZSBsYXN0IHRocmVhZCBpbXAxIGFuZCByZWxlYXNlcyB0aGUgY29ycmlkb3IKICAgIHB0aHJlYWRfbXV0ZXhfdW5sb2NrKCZtMSk7IC8vZW5kIGNyaXRpY2FsIHNlY3Rpb24KICAgIHJldHVybiBOVUxMOwp9CgoKLy90aHJlYWQgZW1wbG95ZWUgdHlwZSAyIAp2b2lkKiBlbXAyKHZvaWQgKmFyZyl7CiAgICBwcmludGYoIkknbSB0aGUgbnVtYmVyICVkXG4iLCBjMSk7CiAgICBwdGhyZWFkX211dGV4X2xvY2soJm0yKTsgLy9iZWdpbm5pbmcgY3JpdGljYWwgc2VjdGlvbgogICAgYzIrKzsgICAgICAgICAgICAgICAgICAgIC8vaXQgaW5jcmVhc2VzIHRvIHNpZ25hbCB0aGUgcHJlc2VuY2Ugb2YgYSB0aHJlYWQgb2YgdGhlIHNhbWUgdHlwZSB0aGF0IHdhbnRzIHRvIGVudGVyIHRoZSBjb3JyaWRvcgogICAgaWYgKGMyID09IDEpeyAgICAgICAgICAgIC8vIHRoZSB0aHJlYWQgaXMgdGhlIG9ubHkgb25lIGluIHRoZSBjb3JyaWRvci4gQ2FuIHBhc3MKICAgICAgICBwcmludGYgKCJJIGFtIHRoZSBmaXJzdCBvZiBteSBncm91cCBuIik7CiAgICAgICAgc2VtX3dhaXQoJmNvcnJpZG9yKTsgIC8vdGFrZXMgcG9zc2Vzc2lvbiBvZiB0aGUgY29ycmlkb3IKICAgIH0KICAgIHB0aHJlYWRfbXV0ZXhfdW5sb2NrKCZtMik7IC8vYWxsb3dzIG90aGVyIHRocmVhZHMgb2YgdGhlIHNhbWUgdHlwZSB0byBwYXNzIGluIHRoZSBjb3JyaWRvciBzaW5jZSBpdCB3YXMgdGhlIGZpcnN0IGluIGhpcyBncm91cC4gRW5kIG9mIGNyaXRpY2FsIHNlY3Rpb25yaXRpY2EKCiAgICAvLyBpbnZlbnRzICJwYXNzYWdlIiBmdW5jdGlvbgoKICAgIHB0aHJlYWRfbXV0ZXhfbG9jaygmbTIpOyAgLy9iZWdpbm5pbmcgb2YgdGhlIGNyaXRpY2FsIHNlY3Rpb24uIE9uY2UgY3Jvc3NlZCB0aGUgY29ycmlkb3IsIHRoZSB2YXJpYWJsZSBjMSBpcyBtb2RpZmllZC4gQSBtdXRleCBpcyB1c2VkIHRvIGF2b2lkIGluY29uc2lzdGVuY3kKICAgIGMyLS07CiAgICBpZihjMiA9PSAwKXsKICAgICAgICBwcmludGYgKCJJIGFtIHRoZSBsYXN0IG9mIG15IGdyb3VwIG4iKTsKICAgICAgICBzZW1fcG9zdCgmY29ycmlkb3IpOwogICAgfS8vaWYgYzEgPT0gMCwgaXQgaXMgdGhlIGxhc3QgdGhyZWFkIGltcDEgYW5kIHJlbGVhc2VzIHRoZSBjb3JyaWRvcgogICAgcHRocmVhZF9tdXRleF91bmxvY2soJm0yKTsgLy9lbmQgY3JpdGljYWwgc2VjdGlvbgogICAgcmV0dXJuIE5VTEw7Cn0KCgppbnQgbWFpbihpbnQgYXJnYywgY2hhciBjb25zdCAqYXJndltdKSB7CiAgICAvL3B0aHJlYWRfdCBlbXAxLCBlbXAyLCBhdHRlbmRhbnQ7CiAgICBwdGhyZWFkX3QgaWR0OwogICAgaW50IHI7IC8vdmFyIHJhbmRvbSB0byBjcmVhdGUgdGhyZWFkIGVtcDEgb3IgZW1wMgogICAgaW50IGk7IC8vaW5kZXggCgogICAgLy92YXJpYWJsZSBpbml0aWFsaXphdGlvbgogICAgYzEgPSBjMiA9IDA7CiAgICBwdGhyZWFkX211dGV4X2luaXQoJm0xLCBOVUxMKTsgCiAgICBwdGhyZWFkX211dGV4X2luaXQoJm0yLCBOVUxMKTsKICAgIHNlbV9pbml0KCZjb3JyaWRvciwwLDEpOyAKCiAgICBwdGhyZWFkX2NyZWF0ZSgmaWR0LE5VTEwsYXR0ZW5kYW50LE5VTEwpOyAKICAgIHdoaWxlKGk8NDApewogICAgICAgIHIgPSByYW5kKCklMjsKICAgICAgICBpZihyPT0wKXsKICAgICAgICAgICAgcHJpbnRmKCJFbXBsb3llZSBjcmVhdGlvbiAxXG4iKTsKICAgICAgICAgICAgcHRocmVhZF9jcmVhdGUoJmlkdCxOVUxMLGVtcDEsTlVMTCk7CiAgICAgICAgfWVsc2V7CiAgICAgICAgICAgIHByaW50ZigiRW1wbG95ZWUgY3JlYXRpb24gMVxuIik7CiAgICAgICAgICAgIHB0aHJlYWRfY3JlYXRlKCZpZHQsTlVMTCxlbXAyLE5VTEwpOwogICAgICAgIH0KICAgICAgICBpKys7CiAgICB9CiAgICByZXR1cm4gMDsKfQ==