Emanuel Kuflik
/
smat_controller
Road.cpp@2:f10d6fecb345, 2019-12-06 (annotated)
- Committer:
- micallef25
- Date:
- Fri Dec 06 15:47:37 2019 +0000
- Revision:
- 2:f10d6fecb345
- Child:
- 4:64c6fc70ddb7
basic communication with mqtt and car threads
Who changed what in which revision?
User | Revision | Line number | New contents of line |
---|---|---|---|
micallef25 | 2:f10d6fecb345 | 1 | #include "Road.h" |
micallef25 | 2:f10d6fecb345 | 2 | |
micallef25 | 2:f10d6fecb345 | 3 | #define ROADLENGTH 100 |
micallef25 | 2:f10d6fecb345 | 4 | |
micallef25 | 2:f10d6fecb345 | 5 | Road::Road(int id) |
micallef25 | 2:f10d6fecb345 | 6 | { |
micallef25 | 2:f10d6fecb345 | 7 | road_id = id; |
micallef25 | 2:f10d6fecb345 | 8 | active_cars = 0; |
micallef25 | 2:f10d6fecb345 | 9 | active_car_bits = 0x00; |
micallef25 | 2:f10d6fecb345 | 10 | road_clock = 0; |
micallef25 | 2:f10d6fecb345 | 11 | // clear out our pointer table |
micallef25 | 2:f10d6fecb345 | 12 | for (int i = 0; i < MAX_CARS_ON_ROAD; ++i) |
micallef25 | 2:f10d6fecb345 | 13 | { |
micallef25 | 2:f10d6fecb345 | 14 | car_table[i] = NULL; |
micallef25 | 2:f10d6fecb345 | 15 | } |
micallef25 | 2:f10d6fecb345 | 16 | } |
micallef25 | 2:f10d6fecb345 | 17 | |
micallef25 | 2:f10d6fecb345 | 18 | void Road::add_acc_car(AccCar* car) { |
micallef25 | 2:f10d6fecb345 | 19 | |
micallef25 | 2:f10d6fecb345 | 20 | // make sure all is well on the road |
micallef25 | 2:f10d6fecb345 | 21 | assert( active_cars < MAX_CARS_ON_ROAD ); |
micallef25 | 2:f10d6fecb345 | 22 | |
micallef25 | 2:f10d6fecb345 | 23 | car_table[active_cars] = car; |
micallef25 | 2:f10d6fecb345 | 24 | |
micallef25 | 2:f10d6fecb345 | 25 | // no need to lock as main thread is only callee |
micallef25 | 2:f10d6fecb345 | 26 | active_car_bits = active_car_bits | car->flag; |
micallef25 | 2:f10d6fecb345 | 27 | active_cars++; |
micallef25 | 2:f10d6fecb345 | 28 | } |
micallef25 | 2:f10d6fecb345 | 29 | |
micallef25 | 2:f10d6fecb345 | 30 | void Road::let_cars_update() { |
micallef25 | 2:f10d6fecb345 | 31 | go_flags.set(active_car_bits); |
micallef25 | 2:f10d6fecb345 | 32 | road_clock++; |
micallef25 | 2:f10d6fecb345 | 33 | } |
micallef25 | 2:f10d6fecb345 | 34 | |
micallef25 | 2:f10d6fecb345 | 35 | void Road::wait_for_car_update() { |
micallef25 | 2:f10d6fecb345 | 36 | done_flags.wait_all(active_car_bits); |
micallef25 | 2:f10d6fecb345 | 37 | } |
micallef25 | 2:f10d6fecb345 | 38 | |
micallef25 | 2:f10d6fecb345 | 39 | bool Road::can_car_enter(int speed) |
micallef25 | 2:f10d6fecb345 | 40 | { |
micallef25 | 2:f10d6fecb345 | 41 | // if no cars on the road enter |
micallef25 | 2:f10d6fecb345 | 42 | if(active_cars == 0) |
micallef25 | 2:f10d6fecb345 | 43 | return true; |
micallef25 | 2:f10d6fecb345 | 44 | |
micallef25 | 2:f10d6fecb345 | 45 | // else make sure you have not exceed the max amount of cars and make sure you can safely enter |
micallef25 | 2:f10d6fecb345 | 46 | // safely being that you maintain your safety gap with your speed |
micallef25 | 2:f10d6fecb345 | 47 | AccCar* caboose = car_table[active_cars-1]; |
micallef25 | 2:f10d6fecb345 | 48 | assert( caboose != NULL); |
micallef25 | 2:f10d6fecb345 | 49 | if(active_cars < MAX_CARS_ON_ROAD && speed <= caboose->position - 2 ) // 2 is safety gap |
micallef25 | 2:f10d6fecb345 | 50 | { |
micallef25 | 2:f10d6fecb345 | 51 | return true; |
micallef25 | 2:f10d6fecb345 | 52 | } |
micallef25 | 2:f10d6fecb345 | 53 | return false; |
micallef25 | 2:f10d6fecb345 | 54 | } |
micallef25 | 2:f10d6fecb345 | 55 | |
micallef25 | 2:f10d6fecb345 | 56 | // whats the id of next car |
micallef25 | 2:f10d6fecb345 | 57 | // used to set bit flags really |
micallef25 | 2:f10d6fecb345 | 58 | int Road::get_new_car_id() |
micallef25 | 2:f10d6fecb345 | 59 | { |
micallef25 | 2:f10d6fecb345 | 60 | return active_cars; |
micallef25 | 2:f10d6fecb345 | 61 | } |
micallef25 | 2:f10d6fecb345 | 62 | |
micallef25 | 2:f10d6fecb345 | 63 | // how many active cars are there |
micallef25 | 2:f10d6fecb345 | 64 | int Road::get_active_cars() |
micallef25 | 2:f10d6fecb345 | 65 | { |
micallef25 | 2:f10d6fecb345 | 66 | return active_cars; |
micallef25 | 2:f10d6fecb345 | 67 | } |
micallef25 | 2:f10d6fecb345 | 68 | |
micallef25 | 2:f10d6fecb345 | 69 | // get a car pointer based off some id |
micallef25 | 2:f10d6fecb345 | 70 | AccCar* Road::get_car(int id) |
micallef25 | 2:f10d6fecb345 | 71 | { |
micallef25 | 2:f10d6fecb345 | 72 | assert(id < MAX_CARS_ON_ROAD); |
micallef25 | 2:f10d6fecb345 | 73 | return car_table[id]; |
micallef25 | 2:f10d6fecb345 | 74 | } |
micallef25 | 2:f10d6fecb345 | 75 | |
micallef25 | 2:f10d6fecb345 | 76 | // 0 is the lead car |
micallef25 | 2:f10d6fecb345 | 77 | // 1 is the second car and so on |
micallef25 | 2:f10d6fecb345 | 78 | AccCar* Road::get_forward_car(int id) |
micallef25 | 2:f10d6fecb345 | 79 | { |
micallef25 | 2:f10d6fecb345 | 80 | // make sure we don't go out of bounds |
micallef25 | 2:f10d6fecb345 | 81 | assert( id >= 0 && id <= MAX_CARS_ON_ROAD ); |
micallef25 | 2:f10d6fecb345 | 82 | if( id > 0 ) |
micallef25 | 2:f10d6fecb345 | 83 | return car_table[id-1]; |
micallef25 | 2:f10d6fecb345 | 84 | else |
micallef25 | 2:f10d6fecb345 | 85 | return NULL; // return null means there is no forward car |
micallef25 | 2:f10d6fecb345 | 86 | } |
micallef25 | 2:f10d6fecb345 | 87 | |
micallef25 | 2:f10d6fecb345 | 88 | // manages any clean up |
micallef25 | 2:f10d6fecb345 | 89 | void Road::DESTROY_ALL_CARS() |
micallef25 | 2:f10d6fecb345 | 90 | { |
micallef25 | 2:f10d6fecb345 | 91 | for( int i = 0; i < active_cars; i++) |
micallef25 | 2:f10d6fecb345 | 92 | { |
micallef25 | 2:f10d6fecb345 | 93 | AccCar* car = car_table[i]; |
micallef25 | 2:f10d6fecb345 | 94 | car->stop(); |
micallef25 | 2:f10d6fecb345 | 95 | delete car; |
micallef25 | 2:f10d6fecb345 | 96 | } |
micallef25 | 2:f10d6fecb345 | 97 | } |
micallef25 | 2:f10d6fecb345 | 98 | |
micallef25 | 2:f10d6fecb345 | 99 | // dumb function to end simulation only returns true when we have |
micallef25 | 2:f10d6fecb345 | 100 | // 5 cars and the last car is passed 100 or road length |
micallef25 | 2:f10d6fecb345 | 101 | bool Road::simulating() |
micallef25 | 2:f10d6fecb345 | 102 | { |
micallef25 | 2:f10d6fecb345 | 103 | if(active_cars != MAX_CARS_ON_ROAD ) |
micallef25 | 2:f10d6fecb345 | 104 | return true; |
micallef25 | 2:f10d6fecb345 | 105 | |
micallef25 | 2:f10d6fecb345 | 106 | else |
micallef25 | 2:f10d6fecb345 | 107 | { |
micallef25 | 2:f10d6fecb345 | 108 | AccCar* car = car_table[active_cars-1]; |
micallef25 | 2:f10d6fecb345 | 109 | assert( car != NULL ); |
micallef25 | 2:f10d6fecb345 | 110 | if(car->position > ROADLENGTH) // TODO use macro |
micallef25 | 2:f10d6fecb345 | 111 | return false; |
micallef25 | 2:f10d6fecb345 | 112 | } |
micallef25 | 2:f10d6fecb345 | 113 | return true; |
micallef25 | 2:f10d6fecb345 | 114 | } |
micallef25 | 2:f10d6fecb345 | 115 | |
micallef25 | 2:f10d6fecb345 | 116 | // typical getter functions |
micallef25 | 2:f10d6fecb345 | 117 | int Road::get_road_id() |
micallef25 | 2:f10d6fecb345 | 118 | { |
micallef25 | 2:f10d6fecb345 | 119 | return road_id; |
micallef25 | 2:f10d6fecb345 | 120 | } |
micallef25 | 2:f10d6fecb345 | 121 | |
micallef25 | 2:f10d6fecb345 | 122 | int Road::get_road_clock() |
micallef25 | 2:f10d6fecb345 | 123 | { |
micallef25 | 2:f10d6fecb345 | 124 | return road_clock; |
micallef25 | 2:f10d6fecb345 | 125 | } |
micallef25 | 2:f10d6fecb345 | 126 | |
micallef25 | 2:f10d6fecb345 | 127 | AccCar* Road::get_last_car() |
micallef25 | 2:f10d6fecb345 | 128 | { |
micallef25 | 2:f10d6fecb345 | 129 | return car_table[active_cars-1]; |
micallef25 | 2:f10d6fecb345 | 130 | } |
micallef25 | 2:f10d6fecb345 | 131 |