From e2beb598a9664c7dc2f9f10de31a5d9537d76261 Mon Sep 17 00:00:00 2001 From: klmp200 Date: Fri, 22 Jun 2018 02:50:04 +0200 Subject: [PATCH] =?UTF-8?q?Voil=C3=A0=20comment=20g=C3=A9rer=20ses=20threa?= =?UTF-8?q?ds=20comme=20un=20boss?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- Elevator/Elevator.c | 27 ++++++++++++++++----------- Elevator/Elevator.h | 2 ++ Passenger/Passenger.c | 7 +++++++ Passenger/Passenger.h | 1 + Resident/Resident.c | 14 +++++++++----- Resident/Resident.h | 2 ++ SharedData/SharedData.c | 38 ++++++++++++++++++++++++++++++-------- SharedData/SharedData.h | 4 +++- Visitor/Visitor.c | 12 ++++++++---- Visitor/Visitor.h | 2 ++ 10 files changed, 80 insertions(+), 29 deletions(-) diff --git a/Elevator/Elevator.c b/Elevator/Elevator.c index 6962dae..e5ac460 100644 --- a/Elevator/Elevator.c +++ b/Elevator/Elevator.c @@ -12,6 +12,7 @@ SYNCHRONIZED_GETTER(Elevator, ELEVATOR_STATE, state) SYNCHRONIZED_SETTER(Elevator, ELEVATOR_STATE, state) SYNCHRONIZED_GETTER(Elevator, int, floor) SYNCHRONIZED_SETTER(Elevator, int, floor) +SETTER(Elevator, int, thread_number); void _free__Elevator(THIS(Elevator)){ DELETE(this->passengers); @@ -167,6 +168,7 @@ void *runnable_Elevator(void * void_this){ printf("Ascenseur %s : Je suis en route vers l'étage %d\n", this->name, this->target_floor); } } + data->unregister_thread(data, this->thread_number); return NULL; } @@ -176,22 +178,25 @@ Elevator *_init_Elevator(char * name){ new_elevator->name = strdup(name); new_elevator->passengers = NEW(List); new_elevator->target_floor = 0; + new_elevator->thread_number = -1; + pthread_mutex_init(&new_elevator->mutex_passengers, NULL); pthread_mutex_init(&new_elevator->mutex_state, NULL); pthread_mutex_init(&new_elevator->mutex_floor, NULL); LINK_ALL(Elevator, new_elevator, - runnable, - get_number_of_passengers, - get_next_passenger_stop, - can_get_inside, - remove_passenger, - add_passenger, - get_state, - set_state, - get_floor, - set_floor, - repair + runnable, + get_number_of_passengers, + get_next_passenger_stop, + can_get_inside, + remove_passenger, + add_passenger, + get_state, + set_state, + get_floor, + set_floor, + repair, + set_thread_number ); new_elevator->set_floor(new_elevator, 0); diff --git a/Elevator/Elevator.h b/Elevator/Elevator.h index 38d993f..c9e7571 100644 --- a/Elevator/Elevator.h +++ b/Elevator/Elevator.h @@ -21,11 +21,13 @@ typedef struct o_Elevator { PRIVATE char * name; PRIVATE int floor; PRIVATE int target_floor; + PRIVATE int thread_number; PRIVATE pthread_mutex_t mutex_passengers; PRIVATE pthread_mutex_t mutex_state; PRIVATE pthread_mutex_t mutex_floor; PUBLIC void * (*runnable)(void * void_this); + PUBLIC void (*set_thread_number)(_THIS(Elevator), int data); SYNCHRONIZE PRIVATE void (*set_state)(_THIS(Elevator), ELEVATOR_STATE var); SYNCHRONIZE PRIVATE void (*set_floor)(_THIS(Elevator), int var); diff --git a/Passenger/Passenger.c b/Passenger/Passenger.c index 3a6f7b5..106200d 100644 --- a/Passenger/Passenger.c +++ b/Passenger/Passenger.c @@ -42,6 +42,13 @@ void *runnable_Passenger(void * void_this){ return NULL; } +void set_thread_number_Passenger(THIS(Passenger), int thread_number){ + if (this->type == RESIDENT) + this->resident->set_thread_number(this->resident, thread_number); + if (this->type == VISITOR) + this->visitor->set_thread_number(this->visitor, thread_number); +} + void _free__Passenger(THIS(Passenger)){ free(this); } diff --git a/Passenger/Passenger.h b/Passenger/Passenger.h index 6c2c59c..d41218d 100644 --- a/Passenger/Passenger.h +++ b/Passenger/Passenger.h @@ -23,6 +23,7 @@ typedef struct o_Passenger { PUBLIC int (*get_destination)(_THIS(Passenger)); PUBLIC void * (*runnable)(void* void_this); PUBLIC int (*compare)(void * passenger1, void * passenger2);//yeah I know, but i needed int (*) (void*, void*) + PUBLIC void (*set_thread_number)(_THIS(Passenger), int thread_number); DESTRUCTOR(Passenger); } Passenger; diff --git a/Resident/Resident.c b/Resident/Resident.c index 512b789..d2972d0 100644 --- a/Resident/Resident.c +++ b/Resident/Resident.c @@ -11,6 +11,7 @@ GETTER(Resident, char *, name); GETTER(Resident, int, destination); GETTER(Resident, int, id); GETTER(Resident, int, apartment_floor); +SETTER(Resident, int, thread_number); void * runnable_Resident(void * void_this){ Resident * this = (Resident*) void_this; @@ -30,6 +31,7 @@ void * runnable_Resident(void * void_this){ else data->main_building->go_to_floor(data->main_building, this->position, this->destination, passenger); data->decrement_active_passengers(data); + data->unregister_thread(data, this->thread_number); return NULL; } @@ -50,13 +52,15 @@ Resident *_init_Resident(int id, char* name, int apartment_floor, int destinatio new_resident->position = new_resident->apartment_floor; new_resident->destination = destination; new_resident->passenger = NULL; + new_resident->thread_number = -1; LINK_ALL(Resident, new_resident, - get_name, - get_destination, - get_id, - runnable, - get_apartment_floor + get_name, + get_destination, + get_id, + runnable, + get_apartment_floor, + set_thread_number ) return new_resident; diff --git a/Resident/Resident.h b/Resident/Resident.h index 3641713..e0d7472 100644 --- a/Resident/Resident.h +++ b/Resident/Resident.h @@ -9,6 +9,7 @@ typedef struct o_Resident { PRIVATE int id; + PRIVATE int thread_number; PRIVATE int apartment_floor; PRIVATE int destination; PRIVATE int position; @@ -20,6 +21,7 @@ typedef struct o_Resident { PUBLIC int (*get_id)(_THIS(Resident)); PUBLIC int (*get_apartment_floor)(_THIS(Resident)); PUBLIC int (*get_destination)(_THIS(Resident)); + PUBLIC void (*set_thread_number)(_THIS(Resident), int data); DESTRUCTOR(Resident); } Resident; diff --git a/SharedData/SharedData.c b/SharedData/SharedData.c index 9ab0a8e..7313701 100644 --- a/SharedData/SharedData.c +++ b/SharedData/SharedData.c @@ -22,7 +22,7 @@ int call_elevator_SharedData(THIS(SharedData), int starting_floor, int destinati return 0; } void start_thread_SharedData(THIS(SharedData), void * (*thread)(void *), void * data, int thread_number){ - pthread_create(&this->threads[thread_number], 0, thread, data); + pthread_create(this->threads[thread_number], 0, thread, data); } void start_all_threads_SharedData(THIS(SharedData)){ @@ -39,18 +39,25 @@ void start_all_threads_SharedData(THIS(SharedData)){ residents = this->main_building->residents; visitors = this->main_building->visitors; this->threads_nb = residents->get_size(residents) + visitors->get_size(visitors) + ELEVATOR_NB; - this->threads = malloc_or_die(sizeof(pthread_t) * this->threads_nb); + this->threads = malloc_or_die(sizeof(pthread_t*) * this->threads_nb); + + for (i=0; i < this->threads_nb; i++) + this->threads[i] = malloc_or_die(sizeof(pthread_t)); pthread_mutex_lock(&this->mutex_active_passengers); + pthread_mutex_lock(&this->mutex_threads); /* starts threading elevators */ - for (i=0; istart_thread(this, this->main_building->elevators[i]->runnable, this->main_building->elevators[i], i); + this->main_building->elevators[i]->set_thread_number(this->main_building->elevators[i], i); + } /* starts threading visitors */ current = visitors->get_head(visitors); while (current != NULL){ this->start_thread(this, ((Visitor*)current->get_data(current))->runnable, current->get_data(current), i); + ((Visitor*)current->get_data(current))->set_thread_number((Visitor*)current->get_data(current), i); current = current->get_next(current); this->active_passengers++; i++; @@ -60,10 +67,12 @@ void start_all_threads_SharedData(THIS(SharedData)){ current = residents->get_head(residents); while (current != NULL){ this->start_thread(this, ((Resident*)current->get_data(current))->runnable, current->get_data(current), i); + ((Resident*)current->get_data(current))->set_thread_number((Resident*)current->get_data(current), i); current = current->get_next(current); this->active_passengers++; i++; } + pthread_mutex_unlock(&this->mutex_threads); pthread_mutex_unlock(&this->mutex_active_passengers); } } @@ -71,8 +80,10 @@ void start_all_threads_SharedData(THIS(SharedData)){ void wait_all_threads_SharedData(THIS(SharedData)){ int i; - for (i=0; ithreads_nb; i++) - pthread_join(this->threads[i], NULL); + for (i=0; ithreads_nb; i++) { + if (this->threads[i] != NULL) + pthread_join(*this->threads[i], NULL); + } } int use_call_box_SharedData(THIS(SharedData), char * resident_name){ @@ -83,8 +94,11 @@ void _free__SharedData(THIS(SharedData)){ int i; if (this->threads != NULL){ for (i=0; ithreads_nb; i++) { - printf("Quitting thread %d\n", (int) this->threads[i]); - pthread_kill(this->threads[i], SIGUSR1); + if (this->threads[i] != NULL) { + printf("Quitting thread %d\n", (int) this->threads[i]); + pthread_kill(*this->threads[i], SIGUSR1); + } + free(this->threads[i]); } free(this->threads); } @@ -111,6 +125,12 @@ void decrement_active_passengers_SharedData(THIS(SharedData)){ pthread_mutex_unlock(&this->mutex_active_passengers); } +void unregister_thread_SharedData(THIS(SharedData), int thread_number){ + pthread_mutex_lock(&this->mutex_threads); + this->threads[thread_number] = NULL; + pthread_mutex_unlock(&this->mutex_threads); +} + SharedData *_get_instance_SharedData(){ static SharedData * new_shared_data = NULL; if (new_shared_data == NULL){ @@ -122,6 +142,7 @@ SharedData *_get_instance_SharedData(){ new_shared_data->active_passengers = 0; pthread_mutex_init(&new_shared_data->mutex_active_passengers, NULL); + pthread_mutex_init(&new_shared_data->mutex_threads, NULL); LINK_ALL(SharedData, new_shared_data, start_thread, @@ -132,7 +153,8 @@ SharedData *_get_instance_SharedData(){ use_call_box, call_elevator, decrement_active_passengers, - is_active_passengers_left + is_active_passengers_left, + unregister_thread ); } return new_shared_data; diff --git a/SharedData/SharedData.h b/SharedData/SharedData.h index 18de379..ffdbd34 100644 --- a/SharedData/SharedData.h +++ b/SharedData/SharedData.h @@ -12,9 +12,10 @@ typedef struct o_SharedData { PRIVATE int threads_nb; PRIVATE int active_passengers; - PRIVATE pthread_t *threads; + PRIVATE pthread_t ** threads; PRIVATE Building * main_building; PRIVATE pthread_mutex_t mutex_active_passengers; + PRIVATE pthread_mutex_t mutex_threads; PRIVATE void (*start_thread)(_THIS(SharedData), void * (*thread)(void *), void * data, int thread_number); @@ -26,6 +27,7 @@ typedef struct o_SharedData { PUBLIC int (*use_call_box)(_THIS(SharedData), char * resident_name); SYNCHRONIZE PUBLIC void (*decrement_active_passengers)(_THIS(SharedData)); SYNCHRONIZE PUBLIC int (*is_active_passengers_left)(_THIS(SharedData)); + SYNCHRONIZE PUBLIC void (*unregister_thread)(_THIS(SharedData), int thread_number); DESTRUCTOR(SharedData); } SharedData; diff --git a/Visitor/Visitor.c b/Visitor/Visitor.c index ac6c8a5..f8d7475 100644 --- a/Visitor/Visitor.c +++ b/Visitor/Visitor.c @@ -9,6 +9,7 @@ GETTER(Visitor, char*, name); GETTER(Visitor, int, destination); GETTER(Visitor, int, id); +SETTER(Visitor, int, thread_number); void * runnable_Visitor(void * void_this){ Visitor *this = (Visitor*) void_this; @@ -24,6 +25,7 @@ void * runnable_Visitor(void * void_this){ printf("Visiteur %s : J'apelle à l'interphone\nVisiteur %s : J'apprends que %s habite à l'étage %d\n", this->name, this->name, this->contact_name, (this->destination = data->use_call_box(data, this->contact_name))); data->main_building->go_to_floor(data->main_building, this->position, this->destination, passenger); data->decrement_active_passengers(data); + data->unregister_thread(data, this->thread_number); return NULL; } @@ -44,6 +46,7 @@ Visitor *_init_Visitor(int id, char* name, char * contact_name){ new_visitor->position = 0; new_visitor->destination = -1; new_visitor->passenger = NULL; + new_visitor->thread_number = -1; if (contact_name != NULL) new_visitor->contact_name = strdup(contact_name); @@ -51,10 +54,11 @@ Visitor *_init_Visitor(int id, char* name, char * contact_name){ new_visitor->contact_name = NULL; LINK_ALL(Visitor, new_visitor, - get_name, - get_destination, - get_id, - runnable + get_name, + get_destination, + get_id, + runnable, + set_thread_number ); return new_visitor; diff --git a/Visitor/Visitor.h b/Visitor/Visitor.h index 734c144..618ac25 100644 --- a/Visitor/Visitor.h +++ b/Visitor/Visitor.h @@ -9,6 +9,7 @@ typedef struct o_Visitor { PRIVATE int id; + PRIVATE int thread_number; PRIVATE char * name; PRIVATE char * contact_name; PRIVATE int position; @@ -19,6 +20,7 @@ typedef struct o_Visitor { PUBLIC char * (*get_name)(_THIS(Visitor)); PUBLIC int (*get_id)(_THIS(Visitor)); PUBLIC int (*get_destination)(_THIS(Visitor)); + PUBLIC void (*set_thread_number)(_THIS(Visitor), int data); DESTRUCTOR(Visitor); } Visitor;