work1
Dependencies: mbed MAX44009 mbed-os Si7021
app/AppMain.cpp@2:25f27478fdf9, 2020-05-28 (annotated)
- Committer:
- danaeb
- Date:
- Thu May 28 07:31:51 2020 +0000
- Revision:
- 2:25f27478fdf9
- Parent:
- 1:3656b45f17a8
work
Who changed what in which revision?
User | Revision | Line number | New contents of line |
---|---|---|---|
danaeb | 0:d3e390d62607 | 1 | #include "mbed.h" |
danaeb | 0:d3e390d62607 | 2 | #include "mbed_mktime.h" |
danaeb | 0:d3e390d62607 | 3 | #include "rtc_api_hal.h" |
danaeb | 0:d3e390d62607 | 4 | #include "tools.h" |
danaeb | 0:d3e390d62607 | 5 | #include "AppMain.h" |
danaeb | 0:d3e390d62607 | 6 | #include "AppLora.h" |
danaeb | 0:d3e390d62607 | 7 | #include "Button.h" |
danaeb | 0:d3e390d62607 | 8 | #include "LedBlinker.h" |
danaeb | 0:d3e390d62607 | 9 | //#include "SensorTag.h" |
danaeb | 0:d3e390d62607 | 10 | #include "Sensor.h" |
danaeb | 0:d3e390d62607 | 11 | #include "SensorManager.h" |
danaeb | 0:d3e390d62607 | 12 | #include "CommandSample.h" |
danaeb | 0:d3e390d62607 | 13 | #include "CommandSampleSelector.h" |
danaeb | 0:d3e390d62607 | 14 | #include "CommandSampleBoard.h" |
danaeb | 0:d3e390d62607 | 15 | #include "AppCommand.h" |
danaeb | 0:d3e390d62607 | 16 | //#include "Latch.h" |
danaeb | 0:d3e390d62607 | 17 | #include "MemoryDeviceEeprom.h" |
danaeb | 0:d3e390d62607 | 18 | #include "Calendar.h" |
danaeb | 0:d3e390d62607 | 19 | #include "mbed-trace/mbed_trace.h" |
danaeb | 0:d3e390d62607 | 20 | #include "board/SensorBoard.h" |
danaeb | 0:d3e390d62607 | 21 | #include "board/PowerManager.h" |
danaeb | 0:d3e390d62607 | 22 | #include "rtc.h" |
danaeb | 0:d3e390d62607 | 23 | #include "Si7021.h" |
danaeb | 0:d3e390d62607 | 24 | #include "ProfileManager.h" |
danaeb | 0:d3e390d62607 | 25 | #define MS_PER_SEC 1000 |
danaeb | 0:d3e390d62607 | 26 | #define MINUTES_PER_DAY 1440 |
danaeb | 0:d3e390d62607 | 27 | |
danaeb | 0:d3e390d62607 | 28 | #define JOIN_TRIES 3 |
danaeb | 0:d3e390d62607 | 29 | |
danaeb | 0:d3e390d62607 | 30 | #define LED_RUN_PERIOD 1000 |
danaeb | 0:d3e390d62607 | 31 | #define LED_RUN_COUNT 2 |
danaeb | 0:d3e390d62607 | 32 | |
danaeb | 0:d3e390d62607 | 33 | // no need to define join failed because |
danaeb | 0:d3e390d62607 | 34 | // after all join tries failed the device go in stop mode |
danaeb | 0:d3e390d62607 | 35 | // U |
danaeb | 0:d3e390d62607 | 36 | // and advertise it |
danaeb | 0:d3e390d62607 | 37 | //#define LED_JOIN_FAILED_PERIOD 1000 |
danaeb | 0:d3e390d62607 | 38 | //#define LED_JOIN_FAILED_COUNT 3 |
danaeb | 0:d3e390d62607 | 39 | // |
danaeb | 0:d3e390d62607 | 40 | #define SENSOR_GROUP_MAIN 0x1 |
danaeb | 0:d3e390d62607 | 41 | #define SENSOR_GROUP_ALTERNATE 0x2 |
danaeb | 0:d3e390d62607 | 42 | |
danaeb | 0:d3e390d62607 | 43 | #define LED_JOIN_JOINING_PERIOD 100 |
danaeb | 0:d3e390d62607 | 44 | #define JOIN_RETRY_DELAY_MS 3000 |
danaeb | 0:d3e390d62607 | 45 | |
danaeb | 0:d3e390d62607 | 46 | #define LED_STOP_PERIOD 1000 |
danaeb | 0:d3e390d62607 | 47 | #define LED_STOP_COUNT 5 |
danaeb | 0:d3e390d62607 | 48 | #define COMMAND_TIMESTAMP_PORT 0x80 |
danaeb | 0:d3e390d62607 | 49 | |
danaeb | 0:d3e390d62607 | 50 | #define RUN_MODE_STANDARD 0x01 |
danaeb | 0:d3e390d62607 | 51 | #define RUN_MODE_TEST 0x02 |
danaeb | 0:d3e390d62607 | 52 | #define RUN_MODE_PRODUCTION_TEST 0x03 |
danaeb | 0:d3e390d62607 | 53 | |
danaeb | 0:d3e390d62607 | 54 | #ifdef MBED_CONF_APP_RUN_MODE |
danaeb | 0:d3e390d62607 | 55 | #endif |
danaeb | 0:d3e390d62607 | 56 | // TEST |
danaeb | 0:d3e390d62607 | 57 | #if MBED_CONF_APP_RUN_MODE == RUN_MODE_STANDARD |
danaeb | 0:d3e390d62607 | 58 | #define SAMPLING_PERIOD 5 |
danaeb | 0:d3e390d62607 | 59 | #define NUMBER_OF_SAMPLE_BEFORE_SEND 1 |
danaeb | 0:d3e390d62607 | 60 | #define NUMBER_OF_TRANSMIT_BEFORE_ALERNATE 1 |
danaeb | 0:d3e390d62607 | 61 | #elif MBED_CONF_APP_RUN_MODE == RUN_MODE_PRODUCTION_TEST |
danaeb | 0:d3e390d62607 | 62 | #define SKIP_JOIN |
danaeb | 0:d3e390d62607 | 63 | #define SAMPLING_PERIOD 1 |
danaeb | 0:d3e390d62607 | 64 | #define NUMBER_OF_SAMPLE_BEFORE_SEND 255 |
danaeb | 0:d3e390d62607 | 65 | #define NUMBER_OF_TRANSMIT_BEFORE_ALERNATE 1 |
danaeb | 0:d3e390d62607 | 66 | #elif MBED_CONF_APP_RUN_MODE == RUN_MODE_TEST |
danaeb | 0:d3e390d62607 | 67 | #define SAMPLING_PERIOD 2 |
danaeb | 0:d3e390d62607 | 68 | #define NUMBER_OF_SAMPLE_BEFORE_SEND 1 |
danaeb | 0:d3e390d62607 | 69 | #define NUMBER_OF_TRANSMIT_BEFORE_ALERNATE 1 |
danaeb | 0:d3e390d62607 | 70 | #endif |
danaeb | 0:d3e390d62607 | 71 | #define MAX_SEND_DELAY (SAMPLING_PERIOD*60-15) |
danaeb | 0:d3e390d62607 | 72 | |
danaeb | 0:d3e390d62607 | 73 | #define SOFTWARE_WATCHDOG_TIMEOUT 12 |
danaeb | 0:d3e390d62607 | 74 | |
danaeb | 0:d3e390d62607 | 75 | |
danaeb | 0:d3e390d62607 | 76 | #define CALENDAR_CONFIGURATION_SIZE 1 // to save the start time offset |
danaeb | 0:d3e390d62607 | 77 | #define CALENDAR_DAY_COUNT 32 |
danaeb | 0:d3e390d62607 | 78 | #define CALENDAR_TIME_SLOT_SIZE 5 // in minutes |
danaeb | 0:d3e390d62607 | 79 | #define CALENDAR_TIME_SLOT_PER_DAY ((MINUTES_PER_DAY) / (CALENDAR_TIME_SLOT_SIZE)) |
danaeb | 0:d3e390d62607 | 80 | |
danaeb | 0:d3e390d62607 | 81 | #define CALENDAR_BIT_COUNT ((CALENDAR_TIME_SLOT_PER_DAY)*(CALENDAR_DAY_COUNT) + \ |
danaeb | 0:d3e390d62607 | 82 | CALENDAR_CONFIGURATION_SIZE*8) |
danaeb | 0:d3e390d62607 | 83 | |
danaeb | 0:d3e390d62607 | 84 | // +7 for ceiling |
danaeb | 0:d3e390d62607 | 85 | #define CALENDAR_BYTES_COUNT ((CALENDAR_BIT_COUNT+7)/8) |
danaeb | 0:d3e390d62607 | 86 | |
danaeb | 0:d3e390d62607 | 87 | |
danaeb | 0:d3e390d62607 | 88 | #define LATCH_TRIGGER_VOLTAGE 12000 // 12 volt |
danaeb | 0:d3e390d62607 | 89 | #define TRACE_GROUP "sm" |
danaeb | 0:d3e390d62607 | 90 | |
danaeb | 0:d3e390d62607 | 91 | |
danaeb | 0:d3e390d62607 | 92 | using namespace events; |
danaeb | 0:d3e390d62607 | 93 | using namespace liboo; |
danaeb | 0:d3e390d62607 | 94 | |
danaeb | 0:d3e390d62607 | 95 | // TODO Too much code in this modules, it will need some refactoring |
danaeb | 0:d3e390d62607 | 96 | |
danaeb | 0:d3e390d62607 | 97 | |
danaeb | 0:d3e390d62607 | 98 | Sensor *AppMain::_sensor_array[CONFIG_SENSOR_COUNT] = {0}; |
danaeb | 0:d3e390d62607 | 99 | SensorManager *AppMain::_sensor_manager = NULL; |
danaeb | 0:d3e390d62607 | 100 | EventQueue *AppMain::_queue = NULL; |
danaeb | 0:d3e390d62607 | 101 | LedBlinker *AppMain::_led_blinker = NULL; |
danaeb | 0:d3e390d62607 | 102 | Button *AppMain::_button = NULL; |
danaeb | 0:d3e390d62607 | 103 | //Calendar *AppMain::_calendar = NULL; |
danaeb | 0:d3e390d62607 | 104 | //MemoryDeviceEeprom *AppMain::_memory_device_calendar = NULL; |
danaeb | 0:d3e390d62607 | 105 | //Latch *AppMain::_latch = NULL; |
danaeb | 0:d3e390d62607 | 106 | |
danaeb | 0:d3e390d62607 | 107 | I2C i2c(I2C_SDA, I2C_SCL); |
danaeb | 0:d3e390d62607 | 108 | SensorData AppMain::_sensor_data; |
danaeb | 0:d3e390d62607 | 109 | |
danaeb | 0:d3e390d62607 | 110 | AppMain::GLOBAL_STATE AppMain::_global_state; |
danaeb | 0:d3e390d62607 | 111 | AppMain::RUN_STATE AppMain::_run_state; |
danaeb | 0:d3e390d62607 | 112 | |
danaeb | 0:d3e390d62607 | 113 | u32 AppMain::_daily_send_s; |
danaeb | 0:d3e390d62607 | 114 | u8 AppMain::_remaining_join_tries; |
danaeb | 0:d3e390d62607 | 115 | u8 AppMain::_remaining_sample_before_send; |
danaeb | 0:d3e390d62607 | 116 | u8 AppMain::_transmit_count_before_alternate; |
danaeb | 0:d3e390d62607 | 117 | u8 AppMain::_send_delay; |
danaeb | 0:d3e390d62607 | 118 | u8 AppMain::_history_size; |
danaeb | 0:d3e390d62607 | 119 | //bool AppMain::_forced_timestamp; |
danaeb | 0:d3e390d62607 | 120 | //bool AppMain::_next_frame_timestamped; |
danaeb | 0:d3e390d62607 | 121 | |
danaeb | 0:d3e390d62607 | 122 | // buffer for uplink commands |
danaeb | 0:d3e390d62607 | 123 | u8 AppMain::_command_payload[COMMAND_PAYLOAD_SIZE]; |
danaeb | 0:d3e390d62607 | 124 | char AppMain::_time_buffer[24]; |
danaeb | 0:d3e390d62607 | 125 | |
danaeb | 0:d3e390d62607 | 126 | u8 AppMain::_software_watchdog_time; |
danaeb | 0:d3e390d62607 | 127 | bool AppMain::_software_watchdog_is_enable; |
danaeb | 0:d3e390d62607 | 128 | |
danaeb | 0:d3e390d62607 | 129 | void AppMain::_software_watchdog_enable(){ |
danaeb | 0:d3e390d62607 | 130 | _software_watchdog_reset(); |
danaeb | 0:d3e390d62607 | 131 | _software_watchdog_is_enable = true; |
danaeb | 0:d3e390d62607 | 132 | } |
danaeb | 0:d3e390d62607 | 133 | |
danaeb | 0:d3e390d62607 | 134 | void AppMain::_software_watchdog_disable(){ |
danaeb | 0:d3e390d62607 | 135 | _software_watchdog_is_enable = false; |
danaeb | 0:d3e390d62607 | 136 | |
danaeb | 0:d3e390d62607 | 137 | } |
danaeb | 0:d3e390d62607 | 138 | |
danaeb | 0:d3e390d62607 | 139 | void AppMain::_software_watchdog_reset(){ |
danaeb | 0:d3e390d62607 | 140 | _software_watchdog_time = 0; |
danaeb | 0:d3e390d62607 | 141 | } |
danaeb | 0:d3e390d62607 | 142 | |
danaeb | 0:d3e390d62607 | 143 | void AppMain::_software_watchdog_increment(){ |
danaeb | 0:d3e390d62607 | 144 | if(!_software_watchdog_is_enable){ |
danaeb | 0:d3e390d62607 | 145 | return; |
danaeb | 0:d3e390d62607 | 146 | } |
danaeb | 0:d3e390d62607 | 147 | ++_software_watchdog_time; |
danaeb | 0:d3e390d62607 | 148 | if(_software_watchdog_time >= SOFTWARE_WATCHDOG_TIMEOUT){ |
danaeb | 0:d3e390d62607 | 149 | tr_error("watchdog triggered, the system will restart"); |
danaeb | 0:d3e390d62607 | 150 | NVIC_SystemReset(); |
danaeb | 0:d3e390d62607 | 151 | //mbed_reset(); |
danaeb | 0:d3e390d62607 | 152 | } |
danaeb | 0:d3e390d62607 | 153 | } |
danaeb | 0:d3e390d62607 | 154 | |
danaeb | 0:d3e390d62607 | 155 | CommandSample *AppMain::_command_sample_array[COMMAND_COUNT] = { |
danaeb | 0:d3e390d62607 | 156 | new CommandSampleCapacitive1(), |
danaeb | 0:d3e390d62607 | 157 | new CommandSampleCapacitive2(), |
danaeb | 0:d3e390d62607 | 158 | new CommandSampleCapacitive3(), |
danaeb | 0:d3e390d62607 | 159 | new CommandSampleCapacitive4(), |
danaeb | 0:d3e390d62607 | 160 | new CommandSampleCapacitive5(), |
danaeb | 0:d3e390d62607 | 161 | //new CommandSampleTest(), |
danaeb | 0:d3e390d62607 | 162 | /* |
danaeb | 0:d3e390d62607 | 163 | new CommandSampleGenericTag1(), |
danaeb | 0:d3e390d62607 | 164 | new CommandSample1Tag1(), |
danaeb | 0:d3e390d62607 | 165 | new CommandSample2Tag1(), |
danaeb | 0:d3e390d62607 | 166 | new CommandSample3Tag1(), |
danaeb | 0:d3e390d62607 | 167 | new CommandSample4Tag1(), |
danaeb | 0:d3e390d62607 | 168 | new CommandSample5Tag1(), |
danaeb | 0:d3e390d62607 | 169 | new CommandSample6Tag1(), |
danaeb | 0:d3e390d62607 | 170 | new CommandSample7Tag1(), |
danaeb | 0:d3e390d62607 | 171 | new CommandSampleGenericAlternativeTag1(), |
danaeb | 0:d3e390d62607 | 172 | new CommandSample1AlternativeTag1(), |
danaeb | 0:d3e390d62607 | 173 | new CommandSample2AlternativeTag1(), |
danaeb | 0:d3e390d62607 | 174 | new CommandSample3AlternativeTag1(), |
danaeb | 0:d3e390d62607 | 175 | new CommandSample4AlternativeTag1(), |
danaeb | 0:d3e390d62607 | 176 | new CommandSample5AlternativeTag1(), |
danaeb | 0:d3e390d62607 | 177 | new CommandSample6AlternativeTag1(), |
danaeb | 0:d3e390d62607 | 178 | new CommandSample7AlternativeTag1(), |
danaeb | 0:d3e390d62607 | 179 | */ |
danaeb | 0:d3e390d62607 | 180 | |
danaeb | 0:d3e390d62607 | 181 | }; |
danaeb | 0:d3e390d62607 | 182 | |
danaeb | 0:d3e390d62607 | 183 | CommandSampleSelector AppMain::_command_selector(_command_sample_array, COMMAND_COUNT, |
danaeb | 0:d3e390d62607 | 184 | &_sensor_data); |
danaeb | 0:d3e390d62607 | 185 | |
danaeb | 0:d3e390d62607 | 186 | void AppMain::set_history_size(u8 history_size){ |
danaeb | 0:d3e390d62607 | 187 | if(history_size < 9){ |
danaeb | 0:d3e390d62607 | 188 | _history_size = history_size; |
danaeb | 0:d3e390d62607 | 189 | tr_info("setting history size to %d", _history_size); |
danaeb | 0:d3e390d62607 | 190 | } |
danaeb | 0:d3e390d62607 | 191 | } |
danaeb | 0:d3e390d62607 | 192 | |
danaeb | 0:d3e390d62607 | 193 | void AppMain::_minute_elapsed_callback_handler(void){ |
danaeb | 0:d3e390d62607 | 194 | tr_debug("one minute elapsed "); |
danaeb | 0:d3e390d62607 | 195 | |
danaeb | 0:d3e390d62607 | 196 | Rtc::get_instance()->get_formatted_time(_time_buffer); |
danaeb | 0:d3e390d62607 | 197 | //_write_time(_time_buffer); |
danaeb | 0:d3e390d62607 | 198 | tr_info("time: %s", _time_buffer); |
danaeb | 0:d3e390d62607 | 199 | _software_watchdog_increment(); |
danaeb | 0:d3e390d62607 | 200 | _queue->call(callback(_global_event_handler), EVENT_MINUTE_ELAPSED); |
danaeb | 0:d3e390d62607 | 201 | } |
danaeb | 0:d3e390d62607 | 202 | |
danaeb | 0:d3e390d62607 | 203 | void AppMain::_daily_send_callback_handler(void){ |
danaeb | 0:d3e390d62607 | 204 | tr_info("daily callback"); |
danaeb | 0:d3e390d62607 | 205 | Rtc::get_instance()->get_formatted_time(_time_buffer); |
danaeb | 0:d3e390d62607 | 206 | //_write_time(_time_buffer); |
danaeb | 0:d3e390d62607 | 207 | tr_debug("time: %s", _time_buffer); |
danaeb | 0:d3e390d62607 | 208 | _queue->call(callback(_global_event_handler), EVENT_DAILY_SEND); |
danaeb | 0:d3e390d62607 | 209 | } |
danaeb | 0:d3e390d62607 | 210 | |
danaeb | 0:d3e390d62607 | 211 | void AppMain::_button_callback_handler(Button::ACTION action){ |
danaeb | 0:d3e390d62607 | 212 | tr_debug("button handler: "); |
danaeb | 0:d3e390d62607 | 213 | switch(action){ |
danaeb | 0:d3e390d62607 | 214 | case Button::ACTION_SHORT: |
danaeb | 0:d3e390d62607 | 215 | tr_debug("\tshort"); |
danaeb | 0:d3e390d62607 | 216 | _queue->call(callback(&AppMain::_global_event_handler), |
danaeb | 0:d3e390d62607 | 217 | AppMain::EVENT_SHORT_PUSH); |
danaeb | 0:d3e390d62607 | 218 | break; |
danaeb | 0:d3e390d62607 | 219 | case Button::ACTION_LONG: |
danaeb | 0:d3e390d62607 | 220 | tr_debug("\tshort"); |
danaeb | 0:d3e390d62607 | 221 | _queue->call(callback(&AppMain::_global_event_handler), |
danaeb | 0:d3e390d62607 | 222 | AppMain::EVENT_LONG_PUSH); |
danaeb | 0:d3e390d62607 | 223 | break; |
danaeb | 0:d3e390d62607 | 224 | } |
danaeb | 0:d3e390d62607 | 225 | } |
danaeb | 0:d3e390d62607 | 226 | |
danaeb | 0:d3e390d62607 | 227 | |
danaeb | 0:d3e390d62607 | 228 | void AppMain::_lora_callback_handler(AppLora::EVENT lora_event){ |
danaeb | 0:d3e390d62607 | 229 | switch(lora_event){ |
danaeb | 0:d3e390d62607 | 230 | case AppLora::EVENT_CONNECTED: |
danaeb | 0:d3e390d62607 | 231 | _global_event_handler(AppMain::EVENT_JOIN_SUCCESS); |
danaeb | 0:d3e390d62607 | 232 | break; |
danaeb | 0:d3e390d62607 | 233 | case AppLora::EVENT_DISCONNECTED: |
danaeb | 0:d3e390d62607 | 234 | _global_event_handler(AppMain::EVENT_DISCONNECTED); |
danaeb | 0:d3e390d62607 | 235 | break; |
danaeb | 0:d3e390d62607 | 236 | case AppLora::EVENT_CONNECTION_ERROR: |
danaeb | 0:d3e390d62607 | 237 | _global_event_handler(AppMain::EVENT_CONNECTION_ERROR); |
danaeb | 0:d3e390d62607 | 238 | break; |
danaeb | 0:d3e390d62607 | 239 | case AppLora::EVENT_JOIN_FAILURE: |
danaeb | 0:d3e390d62607 | 240 | _global_event_handler(AppMain::EVENT_JOIN_FAILED); |
danaeb | 0:d3e390d62607 | 241 | break; |
danaeb | 0:d3e390d62607 | 242 | case AppLora::EVENT_TX_DONE: |
danaeb | 0:d3e390d62607 | 243 | _global_event_handler(AppMain::EVENT_TX_DONE); |
danaeb | 0:d3e390d62607 | 244 | tr_info("tx done"); |
danaeb | 0:d3e390d62607 | 245 | break; |
danaeb | 0:d3e390d62607 | 246 | case AppLora::EVENT_TX_ERROR: |
danaeb | 0:d3e390d62607 | 247 | _global_event_handler(AppMain::EVENT_TX_ERROR); |
danaeb | 0:d3e390d62607 | 248 | tr_err("tx error"); |
danaeb | 0:d3e390d62607 | 249 | break; |
danaeb | 0:d3e390d62607 | 250 | case AppLora::EVENT_RX_ERROR: |
danaeb | 0:d3e390d62607 | 251 | _global_event_handler(AppMain::EVENT_RX_ERROR); |
danaeb | 0:d3e390d62607 | 252 | tr_err("rx error"); |
danaeb | 0:d3e390d62607 | 253 | break; |
danaeb | 0:d3e390d62607 | 254 | default: |
danaeb | 0:d3e390d62607 | 255 | // nothing to do for now |
danaeb | 0:d3e390d62607 | 256 | break; |
danaeb | 0:d3e390d62607 | 257 | } |
danaeb | 0:d3e390d62607 | 258 | } |
danaeb | 0:d3e390d62607 | 259 | void AppMain::_global_event_handler_from_interrupt(AppMain::EVENT event){ |
danaeb | 0:d3e390d62607 | 260 | _queue->call(callback(&AppMain::_global_event_handler), event); |
danaeb | 0:d3e390d62607 | 261 | } |
danaeb | 0:d3e390d62607 | 262 | |
danaeb | 0:d3e390d62607 | 263 | void AppMain::_enter_global_state_stop(void){ |
danaeb | 0:d3e390d62607 | 264 | tr_info("enter stop mode"); |
danaeb | 0:d3e390d62607 | 265 | _software_watchdog_disable(); |
danaeb | 0:d3e390d62607 | 266 | _global_state = AppMain::GLOBAL_STATE_STOP; |
danaeb | 0:d3e390d62607 | 267 | _remaining_join_tries = JOIN_TRIES; |
danaeb | 0:d3e390d62607 | 268 | |
danaeb | 0:d3e390d62607 | 269 | // sensor manager allocated in create_sensors |
danaeb | 0:d3e390d62607 | 270 | Rtc *rtc = Rtc::get_instance(); |
danaeb | 0:d3e390d62607 | 271 | // disable minutes callback |
danaeb | 0:d3e390d62607 | 272 | rtc->disable_alarm(Rtc::ALARM_A); |
danaeb | 0:d3e390d62607 | 273 | // disable daily callback |
danaeb | 0:d3e390d62607 | 274 | rtc->disable_alarm(Rtc::ALARM_B); |
danaeb | 0:d3e390d62607 | 275 | //_calendar->disable(); |
danaeb | 0:d3e390d62607 | 276 | PowerManager *pm= PowerManager::get_instance(); |
danaeb | 0:d3e390d62607 | 277 | pm->sleep_mode(); |
danaeb | 0:d3e390d62607 | 278 | |
danaeb | 0:d3e390d62607 | 279 | _led_blinker->blink(LED_STOP_PERIOD, LED_STOP_COUNT); |
danaeb | 0:d3e390d62607 | 280 | |
danaeb | 0:d3e390d62607 | 281 | |
danaeb | 0:d3e390d62607 | 282 | // unlock latch |
danaeb | 0:d3e390d62607 | 283 | } |
danaeb | 0:d3e390d62607 | 284 | |
danaeb | 0:d3e390d62607 | 285 | void AppMain::_enter_global_state_disconnecting(void){ |
danaeb | 0:d3e390d62607 | 286 | tr_info("enter disconnecting mode"); |
danaeb | 0:d3e390d62607 | 287 | _global_state = AppMain::GLOBAL_STATE_DISCONNECTING; |
danaeb | 0:d3e390d62607 | 288 | _queue->call(AppLora::disconnect); |
danaeb | 0:d3e390d62607 | 289 | } |
danaeb | 0:d3e390d62607 | 290 | |
danaeb | 0:d3e390d62607 | 291 | void AppMain::_enter_global_state_join(void){ |
danaeb | 0:d3e390d62607 | 292 | tr_info("enter join mode"); |
danaeb | 0:d3e390d62607 | 293 | _global_state = AppMain::GLOBAL_STATE_JOIN; |
danaeb | 0:d3e390d62607 | 294 | _queue->call(AppLora::connect); |
danaeb | 0:d3e390d62607 | 295 | |
danaeb | 0:d3e390d62607 | 296 | // this call can potentially make the rx window drifting |
danaeb | 0:d3e390d62607 | 297 | // because the led is blinked through I2C, this takes time |
danaeb | 0:d3e390d62607 | 298 | //_led_blinker->blink_from_interrupt(LED_JOIN_JOINING_PERIOD, |
danaeb | 0:d3e390d62607 | 299 | //LedBlinker::COUNT_INFINITE); |
danaeb | 0:d3e390d62607 | 300 | } |
danaeb | 0:d3e390d62607 | 301 | #if 0 |
danaeb | 0:d3e390d62607 | 302 | void AppMain::_write_time(char* buffer){ |
danaeb | 0:d3e390d62607 | 303 | time_t time; |
danaeb | 0:d3e390d62607 | 304 | tm time_info; |
danaeb | 0:d3e390d62607 | 305 | Rtc &rtc = Rtc::get_instance(); |
danaeb | 0:d3e390d62607 | 306 | time = rtc.get_time(); |
danaeb | 0:d3e390d62607 | 307 | // epoch timestamp the 1 January 2018 0h00 |
danaeb | 0:d3e390d62607 | 308 | time += 1514764800; |
danaeb | 0:d3e390d62607 | 309 | _rtc_localtime(time, &time_info, RTC_4_YEAR_LEAP_YEAR_SUPPORT); |
danaeb | 0:d3e390d62607 | 310 | sprintf(buffer, "%d-%d-%d %d:%d:%d", time_info.tm_mday, |
danaeb | 0:d3e390d62607 | 311 | time_info.tm_mon+1, time_info.tm_year+1900, time_info.tm_hour, |
danaeb | 0:d3e390d62607 | 312 | time_info.tm_min, time_info.tm_sec); |
danaeb | 0:d3e390d62607 | 313 | } |
danaeb | 0:d3e390d62607 | 314 | #endif |
danaeb | 0:d3e390d62607 | 315 | |
danaeb | 0:d3e390d62607 | 316 | void AppMain::_enter_global_state_run(void){ |
danaeb | 0:d3e390d62607 | 317 | tr_info("enter run mode"); |
danaeb | 0:d3e390d62607 | 318 | _software_watchdog_enable(); |
danaeb | 0:d3e390d62607 | 319 | _global_state = AppMain::GLOBAL_STATE_RUN; |
danaeb | 0:d3e390d62607 | 320 | _transmit_count_before_alternate = 1; // first packet use alternate |
danaeb | 0:d3e390d62607 | 321 | |
danaeb | 0:d3e390d62607 | 322 | // random number are recomputed at each restart |
danaeb | 0:d3e390d62607 | 323 | AppMain::_compute_random_number(); |
danaeb | 0:d3e390d62607 | 324 | |
danaeb | 0:d3e390d62607 | 325 | Rtc *rtc = Rtc::get_instance(); |
danaeb | 0:d3e390d62607 | 326 | time_t time = _daily_send_s; |
danaeb | 0:d3e390d62607 | 327 | tm time_info; |
danaeb | 0:d3e390d62607 | 328 | _rtc_localtime(time, &time_info, RTC_4_YEAR_LEAP_YEAR_SUPPORT); |
danaeb | 0:d3e390d62607 | 329 | |
danaeb | 0:d3e390d62607 | 330 | // schedule sampling, sending and calendar check |
danaeb | 0:d3e390d62607 | 331 | rtc->set_alarm(Rtc::ALARM_A, Rtc::ALARM_FIELD_UNUSED, |
danaeb | 0:d3e390d62607 | 332 | Rtc::ALARM_FIELD_UNUSED, 0x00); |
danaeb | 0:d3e390d62607 | 333 | |
danaeb | 0:d3e390d62607 | 334 | |
danaeb | 0:d3e390d62607 | 335 | tr_info("setting daily send to %d:%d:%d", time_info.tm_hour, |
danaeb | 0:d3e390d62607 | 336 | time_info.tm_min, time_info.tm_sec); |
danaeb | 0:d3e390d62607 | 337 | //rtc.set_alarm(Rtc::ALARM_B, Rtc::ALARM_FIELD_UNUSED, |
danaeb | 0:d3e390d62607 | 338 | //Rtc::ALARM_FIELD_UNUSED, time_info.tm_sec); |
danaeb | 0:d3e390d62607 | 339 | rtc->set_alarm(Rtc::ALARM_B, time_info.tm_hour, |
danaeb | 0:d3e390d62607 | 340 | time_info.tm_min, time_info.tm_sec); |
danaeb | 0:d3e390d62607 | 341 | |
danaeb | 0:d3e390d62607 | 342 | _led_blinker->blink(LED_RUN_PERIOD, LED_RUN_COUNT); |
danaeb | 0:d3e390d62607 | 343 | |
danaeb | 0:d3e390d62607 | 344 | // when start run mode check calendar |
danaeb | 0:d3e390d62607 | 345 | // to check the latch is in correct state |
danaeb | 0:d3e390d62607 | 346 | #if 0 |
danaeb | 0:d3e390d62607 | 347 | tr_debug("enable calendar"); |
danaeb | 0:d3e390d62607 | 348 | //_calendar->enable(); |
danaeb | 0:d3e390d62607 | 349 | tr_debug("checking calendar"); |
danaeb | 0:d3e390d62607 | 350 | //_calendar->check(rtc->get_time()); |
danaeb | 0:d3e390d62607 | 351 | tr_debug("check calendar done"); |
danaeb | 0:d3e390d62607 | 352 | //wait(5); |
danaeb | 0:d3e390d62607 | 353 | #endif |
danaeb | 0:d3e390d62607 | 354 | //_forced_timestamp = true; |
danaeb | 0:d3e390d62607 | 355 | |
danaeb | 0:d3e390d62607 | 356 | // erase all old samples |
danaeb | 0:d3e390d62607 | 357 | _sensor_data.reset(); |
danaeb | 0:d3e390d62607 | 358 | // send timestamped packet until answer |
danaeb | 0:d3e390d62607 | 359 | //_forced_timestamp = true; |
danaeb | 0:d3e390d62607 | 360 | |
danaeb | 0:d3e390d62607 | 361 | // send a first message at boot |
danaeb | 0:d3e390d62607 | 362 | // It enable to get the next packet size |
danaeb | 0:d3e390d62607 | 363 | #if 0 |
danaeb | 0:d3e390d62607 | 364 | if(_send_empty_timestamped() < 0){ |
danaeb | 0:d3e390d62607 | 365 | _run_state = AppMain::RUN_STATE_WAIT_SEND_COMPLETE; |
danaeb | 0:d3e390d62607 | 366 | } |
danaeb | 0:d3e390d62607 | 367 | else{ |
danaeb | 0:d3e390d62607 | 368 | _run_state = AppMain::RUN_STATE_READY; |
danaeb | 0:d3e390d62607 | 369 | } |
danaeb | 0:d3e390d62607 | 370 | #endif |
danaeb | 0:d3e390d62607 | 371 | |
danaeb | 0:d3e390d62607 | 372 | } |
danaeb | 0:d3e390d62607 | 373 | |
danaeb | 0:d3e390d62607 | 374 | void AppMain::_global_event_handler(AppMain::EVENT event){ |
danaeb | 0:d3e390d62607 | 375 | tr_debug("global_event_handler"); |
danaeb | 0:d3e390d62607 | 376 | tr_debug("\tglobal_state: %d", _global_state); |
danaeb | 0:d3e390d62607 | 377 | tr_debug("\tevent : %d", event); |
danaeb | 0:d3e390d62607 | 378 | switch(_global_state){ |
danaeb | 0:d3e390d62607 | 379 | case GLOBAL_STATE_STOP: |
danaeb | 0:d3e390d62607 | 380 | if(event == AppMain::EVENT_SHORT_PUSH){ |
danaeb | 0:d3e390d62607 | 381 | _enter_global_state_join(); |
danaeb | 0:d3e390d62607 | 382 | } |
danaeb | 0:d3e390d62607 | 383 | break; |
danaeb | 0:d3e390d62607 | 384 | case GLOBAL_STATE_JOIN: |
danaeb | 0:d3e390d62607 | 385 | if(event == AppMain::EVENT_JOIN_SUCCESS){ |
danaeb | 0:d3e390d62607 | 386 | _led_blinker->stop(); |
danaeb | 0:d3e390d62607 | 387 | _enter_global_state_run(); |
danaeb | 0:d3e390d62607 | 388 | } |
danaeb | 0:d3e390d62607 | 389 | if(event == AppMain::EVENT_CONNECTION_ERROR || |
danaeb | 0:d3e390d62607 | 390 | event == AppMain::EVENT_TX_ERROR || |
danaeb | 0:d3e390d62607 | 391 | event == AppMain::EVENT_JOIN_FAILED){ |
danaeb | 0:d3e390d62607 | 392 | --_remaining_join_tries; |
danaeb | 0:d3e390d62607 | 393 | if(_remaining_join_tries == 0){ |
danaeb | 0:d3e390d62607 | 394 | tr_err("join failed after %d tries", JOIN_TRIES); |
danaeb | 0:d3e390d62607 | 395 | _enter_global_state_stop(); |
danaeb | 0:d3e390d62607 | 396 | } |
danaeb | 0:d3e390d62607 | 397 | else{ |
danaeb | 0:d3e390d62607 | 398 | //retry join |
danaeb | 0:d3e390d62607 | 399 | tr_warn("join failed, retry join in %dms", JOIN_RETRY_DELAY_MS); |
danaeb | 0:d3e390d62607 | 400 | _led_blinker->stop(); |
danaeb | 0:d3e390d62607 | 401 | //wait_ms(JOIN_RETRY_DELAY_MS); |
danaeb | 0:d3e390d62607 | 402 | //ThisThread::sleep_for(JOIN_RETRY_DELAY_MS); |
danaeb | 0:d3e390d62607 | 403 | wait_us(JOIN_RETRY_DELAY_MS*1000); |
danaeb | 0:d3e390d62607 | 404 | _enter_global_state_join(); |
danaeb | 0:d3e390d62607 | 405 | } |
danaeb | 0:d3e390d62607 | 406 | } |
danaeb | 0:d3e390d62607 | 407 | |
danaeb | 0:d3e390d62607 | 408 | break; |
danaeb | 0:d3e390d62607 | 409 | case GLOBAL_STATE_RUN: |
danaeb | 0:d3e390d62607 | 410 | if(event == AppMain::EVENT_SHORT_PUSH){ |
danaeb | 0:d3e390d62607 | 411 | _send_empty(); |
danaeb | 0:d3e390d62607 | 412 | //_write_time(_time_buffer); |
danaeb | 0:d3e390d62607 | 413 | Rtc::get_instance()->get_formatted_time(_time_buffer); |
danaeb | 0:d3e390d62607 | 414 | tr_info("time: %s", _time_buffer); |
danaeb | 0:d3e390d62607 | 415 | //Rtc &rtc = Rtc::get_instance(); |
danaeb | 0:d3e390d62607 | 416 | //rtc.set_time(9537861); |
danaeb | 0:d3e390d62607 | 417 | |
danaeb | 0:d3e390d62607 | 418 | } |
danaeb | 0:d3e390d62607 | 419 | else if(event == AppMain::EVENT_LONG_PUSH){ |
danaeb | 0:d3e390d62607 | 420 | _enter_global_state_disconnecting(); |
danaeb | 0:d3e390d62607 | 421 | } |
danaeb | 0:d3e390d62607 | 422 | else{ |
danaeb | 0:d3e390d62607 | 423 | _run_event_handler(event); |
danaeb | 0:d3e390d62607 | 424 | } |
danaeb | 0:d3e390d62607 | 425 | break; |
danaeb | 0:d3e390d62607 | 426 | case GLOBAL_STATE_DISCONNECTING: |
danaeb | 0:d3e390d62607 | 427 | if(event == AppMain::EVENT_DISCONNECTED){ |
danaeb | 0:d3e390d62607 | 428 | _enter_global_state_stop(); |
danaeb | 0:d3e390d62607 | 429 | } |
danaeb | 0:d3e390d62607 | 430 | } |
danaeb | 0:d3e390d62607 | 431 | } |
danaeb | 0:d3e390d62607 | 432 | |
danaeb | 0:d3e390d62607 | 433 | |
danaeb | 0:d3e390d62607 | 434 | void AppMain::_run_event_handler(AppMain::EVENT event){ |
danaeb | 0:d3e390d62607 | 435 | switch(_run_state){ |
danaeb | 0:d3e390d62607 | 436 | case RUN_STATE_READY: |
danaeb | 0:d3e390d62607 | 437 | if(event == AppMain::EVENT_MINUTE_ELAPSED){ |
danaeb | 0:d3e390d62607 | 438 | Rtc *rtc = Rtc::get_instance(); |
danaeb | 0:d3e390d62607 | 439 | time_t time = rtc->get_time(); |
danaeb | 0:d3e390d62607 | 440 | tm time_info; |
danaeb | 0:d3e390d62607 | 441 | _rtc_localtime(time, &time_info, RTC_4_YEAR_LEAP_YEAR_SUPPORT); |
danaeb | 0:d3e390d62607 | 442 | |
danaeb | 0:d3e390d62607 | 443 | if((time_info.tm_min % SAMPLING_PERIOD) == 0) // if minute is pair |
danaeb | 0:d3e390d62607 | 444 | { |
danaeb | 0:d3e390d62607 | 445 | bool is_hourly_send = false; |
danaeb | 0:d3e390d62607 | 446 | // forbid latch operation to avoid wrong measure or degraded RF |
danaeb | 0:d3e390d62607 | 447 | // this cannot protect against a latch which is already charging |
danaeb | 0:d3e390d62607 | 448 | // it will forbid only trigger latch |
danaeb | 0:d3e390d62607 | 449 | // TODO lock latch |
danaeb | 0:d3e390d62607 | 450 | _sensor_manager->sample_all(); |
danaeb | 0:d3e390d62607 | 451 | --_remaining_sample_before_send; |
danaeb | 0:d3e390d62607 | 452 | |
danaeb | 0:d3e390d62607 | 453 | tr_debug("remaining sampling before transmit: %d", |
danaeb | 0:d3e390d62607 | 454 | _remaining_sample_before_send); |
danaeb | 0:d3e390d62607 | 455 | if(_remaining_sample_before_send == 0){ |
danaeb | 0:d3e390d62607 | 456 | /* |
danaeb | 0:d3e390d62607 | 457 | static u8 sample_id = 0; |
danaeb | 0:d3e390d62607 | 458 | ++sample_id; |
danaeb | 0:d3e390d62607 | 459 | */ |
danaeb | 0:d3e390d62607 | 460 | _remaining_sample_before_send = NUMBER_OF_SAMPLE_BEFORE_SEND; |
danaeb | 0:d3e390d62607 | 461 | --_transmit_count_before_alternate; |
danaeb | 0:d3e390d62607 | 462 | if(_transmit_count_before_alternate == 0){ |
danaeb | 0:d3e390d62607 | 463 | _transmit_count_before_alternate = NUMBER_OF_TRANSMIT_BEFORE_ALERNATE; |
danaeb | 0:d3e390d62607 | 464 | is_hourly_send = 1; |
danaeb | 0:d3e390d62607 | 465 | } |
danaeb | 0:d3e390d62607 | 466 | |
danaeb | 0:d3e390d62607 | 467 | _sensor_manager->record_samples(); |
danaeb | 0:d3e390d62607 | 468 | if(!_sensor_manager->are_all_sensor_disabled()){ |
danaeb | 0:d3e390d62607 | 469 | tr_info(" Scheduling transmit in %d secondes", _send_delay); |
danaeb | 0:d3e390d62607 | 470 | //_write_time(_time_buffer); |
danaeb | 0:d3e390d62607 | 471 | Rtc::get_instance()->get_formatted_time(_time_buffer); |
danaeb | 0:d3e390d62607 | 472 | tr_debug("time: %s", _time_buffer); |
danaeb | 0:d3e390d62607 | 473 | _queue->call_in(_send_delay*1000, |
danaeb | 0:d3e390d62607 | 474 | callback(_scheduled_send), is_hourly_send); |
danaeb | 0:d3e390d62607 | 475 | } |
danaeb | 0:d3e390d62607 | 476 | } |
danaeb | 0:d3e390d62607 | 477 | else{ |
danaeb | 0:d3e390d62607 | 478 | // [TODO]unlock latch |
danaeb | 0:d3e390d62607 | 479 | } |
danaeb | 0:d3e390d62607 | 480 | //check calendar every minnutes |
danaeb | 0:d3e390d62607 | 481 | #if 0 |
danaeb | 0:d3e390d62607 | 482 | Rtc *rtc = Rtc::get_instance(); |
danaeb | 0:d3e390d62607 | 483 | u32 time = rtc->get_time(); |
danaeb | 0:d3e390d62607 | 484 | _calendar->check(time); |
danaeb | 0:d3e390d62607 | 485 | #endif |
danaeb | 0:d3e390d62607 | 486 | } |
danaeb | 0:d3e390d62607 | 487 | |
danaeb | 0:d3e390d62607 | 488 | #if MBED_CONF_APP_RUN_MODE == RUN_MODE_PRODUCTION_TEST |
danaeb | 0:d3e390d62607 | 489 | tr_info("turn on pump"); |
danaeb | 0:d3e390d62607 | 490 | // toggle latch 10s |
danaeb | 0:d3e390d62607 | 491 | PowerManager *pm= PowerManager::get_instance(); |
danaeb | 0:d3e390d62607 | 492 | pm->lock_and_turn_on_motor(); |
danaeb | 0:d3e390d62607 | 493 | wait_us(10*1000*1000); |
danaeb | 0:d3e390d62607 | 494 | pm->unlock_and_turn_off_motor(); |
danaeb | 0:d3e390d62607 | 495 | tr_info("turn off pump"); |
danaeb | 0:d3e390d62607 | 496 | #endif |
danaeb | 0:d3e390d62607 | 497 | } |
danaeb | 0:d3e390d62607 | 498 | if(event == AppMain::EVENT_DAILY_SEND){ |
danaeb | 0:d3e390d62607 | 499 | // at least one packet is timestamped every days |
danaeb | 0:d3e390d62607 | 500 | //_next_frame_timestamped = true; |
danaeb | 0:d3e390d62607 | 501 | if(_sensor_manager->are_all_sensor_disabled()){ |
danaeb | 0:d3e390d62607 | 502 | if(_send_empty() < 0){ |
danaeb | 0:d3e390d62607 | 503 | _run_state = RUN_STATE_WAIT_SEND_COMPLETE; |
danaeb | 0:d3e390d62607 | 504 | } |
danaeb | 0:d3e390d62607 | 505 | } |
danaeb | 0:d3e390d62607 | 506 | } |
danaeb | 0:d3e390d62607 | 507 | break; |
danaeb | 0:d3e390d62607 | 508 | case RUN_STATE_WAIT_SEND_COMPLETE: |
danaeb | 0:d3e390d62607 | 509 | // other event like daily send or event minutes elapsed |
danaeb | 0:d3e390d62607 | 510 | // doesnt need to be process together because |
danaeb | 0:d3e390d62607 | 511 | // theses event are generated in two different mode. |
danaeb | 0:d3e390d62607 | 512 | // One is when sensor are enable the other is when all sensor are disabled |
danaeb | 0:d3e390d62607 | 513 | if( event == AppMain::EVENT_TX_DONE || |
danaeb | 0:d3e390d62607 | 514 | event == AppMain::EVENT_RX_ERROR || |
danaeb | 0:d3e390d62607 | 515 | event == AppMain::EVENT_TX_ERROR){ |
danaeb | 0:d3e390d62607 | 516 | // TODO unlock latch |
danaeb | 0:d3e390d62607 | 517 | _run_state = AppMain::RUN_STATE_READY; |
danaeb | 0:d3e390d62607 | 518 | } |
danaeb | 0:d3e390d62607 | 519 | break; |
danaeb | 0:d3e390d62607 | 520 | } |
danaeb | 0:d3e390d62607 | 521 | } |
danaeb | 0:d3e390d62607 | 522 | |
danaeb | 0:d3e390d62607 | 523 | void AppMain::_compute_random_number(void){ |
danaeb | 0:d3e390d62607 | 524 | u32 rand; |
danaeb | 0:d3e390d62607 | 525 | //value between 0 and 4 which is the number of samples sinces the last |
danaeb | 0:d3e390d62607 | 526 | //send |
danaeb | 0:d3e390d62607 | 527 | rand = AppLora::get_random(); |
danaeb | 0:d3e390d62607 | 528 | _remaining_sample_before_send = (rand % NUMBER_OF_SAMPLE_BEFORE_SEND) + 1; |
danaeb | 0:d3e390d62607 | 529 | //_remaining_sample_before_send = 1; |
danaeb | 0:d3e390d62607 | 530 | tr_info("random: Transmit in %d sample", _remaining_sample_before_send); |
danaeb | 0:d3e390d62607 | 531 | |
danaeb | 0:d3e390d62607 | 532 | // delay between the 5th sample and the send action |
danaeb | 0:d3e390d62607 | 533 | // value between 0 and 90 seconds. The actual range could be 0-120 seconds |
danaeb | 0:d3e390d62607 | 534 | // but in order to send the data before the next sample 30 secondes are removed. |
danaeb | 0:d3e390d62607 | 535 | rand = AppLora::get_random(); |
danaeb | 0:d3e390d62607 | 536 | _send_delay = rand % MAX_SEND_DELAY; |
danaeb | 0:d3e390d62607 | 537 | tr_info("random: Send delay %ds", _send_delay); |
danaeb | 0:d3e390d62607 | 538 | |
danaeb | 0:d3e390d62607 | 539 | // hours in seconds for the dayli sent |
danaeb | 0:d3e390d62607 | 540 | // this sending is done only when all sensors are deactivated |
danaeb | 0:d3e390d62607 | 541 | rand = AppLora::get_random(); |
danaeb | 0:d3e390d62607 | 542 | _daily_send_s = rand % 86400; // 86400 number of seconds in one day |
danaeb | 0:d3e390d62607 | 543 | tr_info("random: Daily send %lus", _daily_send_s); |
danaeb | 0:d3e390d62607 | 544 | |
danaeb | 0:d3e390d62607 | 545 | } |
danaeb | 0:d3e390d62607 | 546 | |
danaeb | 0:d3e390d62607 | 547 | // this function is called only once at start |
danaeb | 0:d3e390d62607 | 548 | void AppMain::initialize(EventQueue *queue){ |
danaeb | 0:d3e390d62607 | 549 | tr_info("Main initialization"); |
danaeb | 0:d3e390d62607 | 550 | _queue = queue; |
danaeb | 0:d3e390d62607 | 551 | |
danaeb | 0:d3e390d62607 | 552 | ProfileManager* profile_manager = ProfileManager::get_instance(); |
danaeb | 0:d3e390d62607 | 553 | |
danaeb | 0:d3e390d62607 | 554 | //CommandSample::set_endianness(CommandSample::EndiannessBig); |
danaeb | 0:d3e390d62607 | 555 | |
danaeb | 0:d3e390d62607 | 556 | AppLora::set_lora_callback(_lora_callback_handler); |
danaeb | 0:d3e390d62607 | 557 | //wait(0.05); |
danaeb | 0:d3e390d62607 | 558 | wait_us(50000); |
danaeb | 0:d3e390d62607 | 559 | |
danaeb | 0:d3e390d62607 | 560 | // sensor manager allocated in create_sensors |
danaeb | 0:d3e390d62607 | 561 | Rtc *rtc = Rtc::get_instance(); |
danaeb | 0:d3e390d62607 | 562 | rtc->set_alarm_callback(Rtc::ALARM_B, _daily_send_callback_handler); |
danaeb | 0:d3e390d62607 | 563 | rtc->set_alarm_callback(Rtc::ALARM_A, _minute_elapsed_callback_handler); |
danaeb | 0:d3e390d62607 | 564 | |
danaeb | 0:d3e390d62607 | 565 | // set default time |
danaeb | 0:d3e390d62607 | 566 | // set default time to delivery day: 2018/09/12 00:00 |
danaeb | 0:d3e390d62607 | 567 | rtc->set_rtc_time(22032000); |
danaeb | 0:d3e390d62607 | 568 | |
danaeb | 0:d3e390d62607 | 569 | //pcal_i2c.frequency(100000); |
danaeb | 0:d3e390d62607 | 570 | //_gpio_exp = new PCAL6416(pcal_i2c, 0x42); |
danaeb | 0:d3e390d62607 | 571 | _led_blinker = new LedBlinker(AppMain::_queue, LED1); |
danaeb | 0:d3e390d62607 | 572 | _button = new Button(_led_blinker, USER_BUTTON); |
danaeb | 0:d3e390d62607 | 573 | |
danaeb | 0:d3e390d62607 | 574 | _history_size = 1; |
danaeb | 0:d3e390d62607 | 575 | _create_sensors(); |
danaeb | 0:d3e390d62607 | 576 | _button->set_action_callback(_button_callback_handler); |
danaeb | 0:d3e390d62607 | 577 | // sensor manager allocated in create_sensors |
danaeb | 0:d3e390d62607 | 578 | //_memory_device_calendar = new MemoryDeviceEeprom(0, CALENDAR_BYTES_COUNT); |
danaeb | 0:d3e390d62607 | 579 | //_latch = new Latch(LATCH_TRIGGER_VOLTAGE, _gpio_exp); |
danaeb | 0:d3e390d62607 | 580 | #if 0 |
danaeb | 0:d3e390d62607 | 581 | _calendar = new Calendar(_memory_device_calendar, |
danaeb | 0:d3e390d62607 | 582 | CALENDAR_DAY_COUNT, |
danaeb | 0:d3e390d62607 | 583 | CALENDAR_TIME_SLOT_PER_DAY, |
danaeb | 0:d3e390d62607 | 584 | _trigger_latch); |
danaeb | 0:d3e390d62607 | 585 | #endif |
danaeb | 0:d3e390d62607 | 586 | AppCommand::configure(_sensor_manager, NULL /* _calendar */); |
danaeb | 0:d3e390d62607 | 587 | |
danaeb | 0:d3e390d62607 | 588 | // short wait to charge all capacitor before triggering latch |
danaeb | 0:d3e390d62607 | 589 | //wait_ms(20); |
danaeb | 0:d3e390d62607 | 590 | wait_us(20000); |
danaeb | 0:d3e390d62607 | 591 | //_enter_global_state_stop(); |
danaeb | 0:d3e390d62607 | 592 | #ifdef SKIP_JOIN |
danaeb | 0:d3e390d62607 | 593 | _enter_global_state_run(); |
danaeb | 0:d3e390d62607 | 594 | #else |
danaeb | 0:d3e390d62607 | 595 | _enter_global_state_join(); |
danaeb | 0:d3e390d62607 | 596 | #endif |
danaeb | 0:d3e390d62607 | 597 | |
danaeb | 0:d3e390d62607 | 598 | } |
danaeb | 0:d3e390d62607 | 599 | |
danaeb | 0:d3e390d62607 | 600 | void AppMain::_trigger_latch(bool sens){ |
danaeb | 0:d3e390d62607 | 601 | if(sens){ |
danaeb | 0:d3e390d62607 | 602 | tr_debug("trigger latch forward"); |
danaeb | 0:d3e390d62607 | 603 | //_latch->trigger(Latch::TRIGGER_SENS_FORWARD); |
danaeb | 0:d3e390d62607 | 604 | } |
danaeb | 0:d3e390d62607 | 605 | else{ |
danaeb | 0:d3e390d62607 | 606 | tr_debug("trigger latch reverse"); |
danaeb | 0:d3e390d62607 | 607 | //_latch->trigger(Latch::TRIGGER_SENS_REVERSE); |
danaeb | 0:d3e390d62607 | 608 | } |
danaeb | 0:d3e390d62607 | 609 | } |
danaeb | 0:d3e390d62607 | 610 | |
danaeb | 0:d3e390d62607 | 611 | void AppMain::_create_sensors(void){ |
danaeb | 0:d3e390d62607 | 612 | |
danaeb | 0:d3e390d62607 | 613 | PowerManager *pm= PowerManager::get_instance(); |
danaeb | 0:d3e390d62607 | 614 | pm->run_mode(); |
danaeb | 0:d3e390d62607 | 615 | |
danaeb | 0:d3e390d62607 | 616 | //TPS62740 *tps = TPS62740::get_instance(); |
danaeb | 0:d3e390d62607 | 617 | //tps->set_voltage(TPS62740::V3_0); |
danaeb | 0:d3e390d62607 | 618 | |
danaeb | 0:d3e390d62607 | 619 | tr_info("initialize sensors"); |
danaeb | 0:d3e390d62607 | 620 | tr_debug("initialize battery"); |
danaeb | 0:d3e390d62607 | 621 | _sensor_array[0] = new SensorBoardBattery(SENSOR_ID_BOARD_BAT, SENSOR_GROUP_MAIN); |
danaeb | 0:d3e390d62607 | 622 | |
danaeb | 0:d3e390d62607 | 623 | tr_debug("initialize SI7021"); |
danaeb | 0:d3e390d62607 | 624 | Si7021 *si = new Si7021(I2C_SDA, I2C_SCL); |
danaeb | 0:d3e390d62607 | 625 | bool ping_success = si->check(); |
danaeb | 0:d3e390d62607 | 626 | if(ping_success){ |
danaeb | 0:d3e390d62607 | 627 | tr_debug("SI7021 detected"); |
danaeb | 0:d3e390d62607 | 628 | } |
danaeb | 0:d3e390d62607 | 629 | else{ |
danaeb | 0:d3e390d62607 | 630 | tr_warn("couldn't communicate with SI7021"); |
danaeb | 0:d3e390d62607 | 631 | } |
danaeb | 0:d3e390d62607 | 632 | |
danaeb | 0:d3e390d62607 | 633 | _sensor_array[1] = new SensorBoardTempRH(SENSOR_ID_BOARD_TEMPERATURE, |
danaeb | 0:d3e390d62607 | 634 | SENSOR_GROUP_MAIN, si); |
danaeb | 0:d3e390d62607 | 635 | _sensor_array[2] = new SensorBoardTempRH(SENSOR_ID_BOARD_HUMIDITY, |
danaeb | 0:d3e390d62607 | 636 | SENSOR_GROUP_MAIN, si); |
danaeb | 0:d3e390d62607 | 637 | |
danaeb | 0:d3e390d62607 | 638 | tr_debug("initialize MAX44009"); |
danaeb | 0:d3e390d62607 | 639 | MAX44009 *max44009 = new MAX44009(&i2c, 0x94); |
danaeb | 0:d3e390d62607 | 640 | _sensor_array[3] = new SensorBoardIllumination(SENSOR_ID_BOARD_ILLUMINATION, |
danaeb | 0:d3e390d62607 | 641 | SENSOR_GROUP_MAIN, max44009); |
danaeb | 0:d3e390d62607 | 642 | tr_debug("initialize sensor board 1"); |
danaeb | 0:d3e390d62607 | 643 | _sensor_array[4] = new SensorBoardCapacitive(SENSOR_ID_BOARD_CAPACITIVE_0, SENSOR_GROUP_MAIN); |
danaeb | 0:d3e390d62607 | 644 | tr_debug("initialize sensor board 2"); |
danaeb | 0:d3e390d62607 | 645 | _sensor_array[5] = new SensorBoardCapacitive(SENSOR_ID_BOARD_CAPACITIVE_1, SENSOR_GROUP_MAIN); |
danaeb | 0:d3e390d62607 | 646 | tr_debug("initialize sensor board 3"); |
danaeb | 0:d3e390d62607 | 647 | _sensor_array[6] = new SensorBoardCapacitive(SENSOR_ID_BOARD_CAPACITIVE_2, SENSOR_GROUP_MAIN); |
danaeb | 0:d3e390d62607 | 648 | tr_debug("initialize sensor board 4"); |
danaeb | 0:d3e390d62607 | 649 | _sensor_array[7] = new SensorBoardCapacitive(SENSOR_ID_BOARD_CAPACITIVE_3, SENSOR_GROUP_MAIN); |
danaeb | 0:d3e390d62607 | 650 | |
danaeb | 0:d3e390d62607 | 651 | //_sensor_array[11] = new SensorImpulse(SENSOR_ID_IMPULSE); |
danaeb | 0:d3e390d62607 | 652 | |
danaeb | 0:d3e390d62607 | 653 | //_sensor_array[11] = new SensorImpulse(SENSOR_ID_IMPULSE); |
danaeb | 0:d3e390d62607 | 654 | //_sensor_data = new SensorData(); |
danaeb | 0:d3e390d62607 | 655 | //_sensor_manager = new SensorManager(_sensor_data, _sensor_array, 11); |
danaeb | 0:d3e390d62607 | 656 | tr_debug("initialize sensor manager"); |
danaeb | 0:d3e390d62607 | 657 | _sensor_manager = SensorManager::get_instance(); |
danaeb | 0:d3e390d62607 | 658 | _sensor_manager->initialize(&_sensor_data, _sensor_array, CONFIG_SENSOR_COUNT); |
danaeb | 0:d3e390d62607 | 659 | tr_info("initialization done"); |
danaeb | 0:d3e390d62607 | 660 | } |
danaeb | 0:d3e390d62607 | 661 | |
danaeb | 0:d3e390d62607 | 662 | void AppMain::incoming_lora_message_callback(void){ |
danaeb | 0:d3e390d62607 | 663 | u8 app_port; |
danaeb | 0:d3e390d62607 | 664 | u8 data[256]; |
danaeb | 0:d3e390d62607 | 665 | s16 received_size; |
danaeb | 0:d3e390d62607 | 666 | u16 data_size = 256; |
danaeb | 0:d3e390d62607 | 667 | |
danaeb | 0:d3e390d62607 | 668 | //_forced_timestamp = false; |
danaeb | 0:d3e390d62607 | 669 | received_size = AppLora::get_rx_message(data, data_size, app_port); |
danaeb | 0:d3e390d62607 | 670 | if(received_size >= 0){ |
danaeb | 0:d3e390d62607 | 671 | AppCommand::process_command(app_port, data, received_size); |
danaeb | 0:d3e390d62607 | 672 | } |
danaeb | 0:d3e390d62607 | 673 | // else it an error |
danaeb | 0:d3e390d62607 | 674 | } |
danaeb | 0:d3e390d62607 | 675 | |
danaeb | 0:d3e390d62607 | 676 | void AppMain::_scheduled_send(bool is_hourly_send){ |
danaeb | 0:d3e390d62607 | 677 | tr_info("proceed scheduled send"); |
danaeb | 0:d3e390d62607 | 678 | Rtc::get_instance()->get_formatted_time(_time_buffer); |
danaeb | 0:d3e390d62607 | 679 | |
danaeb | 0:d3e390d62607 | 680 | //_write_time(_time_buffer); |
danaeb | 0:d3e390d62607 | 681 | tr_debug("time: %s", _time_buffer); |
danaeb | 0:d3e390d62607 | 682 | if(_send_samples(is_hourly_send) >= 0){ |
danaeb | 0:d3e390d62607 | 683 | _run_state = RUN_STATE_WAIT_SEND_COMPLETE; |
danaeb | 0:d3e390d62607 | 684 | } |
danaeb | 0:d3e390d62607 | 685 | } |
danaeb | 0:d3e390d62607 | 686 | |
danaeb | 0:d3e390d62607 | 687 | s8 AppMain::_send_samples(bool is_hourly_send){ |
danaeb | 0:d3e390d62607 | 688 | CommandSample *selected_command; |
danaeb | 0:d3e390d62607 | 689 | //command_field_t field; |
danaeb | 0:d3e390d62607 | 690 | u32 timestamp; |
danaeb | 0:d3e390d62607 | 691 | s16 retcode; |
danaeb | 0:d3e390d62607 | 692 | u8 max_lora_payload; |
danaeb | 0:d3e390d62607 | 693 | u8 command_payload_size = 0; |
danaeb | 0:d3e390d62607 | 694 | u8 command_port = 0; |
danaeb | 0:d3e390d62607 | 695 | //u8 history_size = _history_size; |
danaeb | 0:d3e390d62607 | 696 | u8 history_size; |
danaeb | 0:d3e390d62607 | 697 | u8 command_group = SENSOR_GROUP_MAIN; |
danaeb | 0:d3e390d62607 | 698 | //bool _add_timestamp = false; |
danaeb | 0:d3e390d62607 | 699 | |
danaeb | 0:d3e390d62607 | 700 | // select if the frame must be timestamped |
danaeb | 0:d3e390d62607 | 701 | // not generic |
danaeb | 0:d3e390d62607 | 702 | //if(_next_frame_timestamped || _forced_timestamp){ |
danaeb | 0:d3e390d62607 | 703 | //_add_timestamp = true; |
danaeb | 0:d3e390d62607 | 704 | //} |
danaeb | 0:d3e390d62607 | 705 | |
danaeb | 0:d3e390d62607 | 706 | // not generic |
danaeb | 0:d3e390d62607 | 707 | if(is_hourly_send){ |
danaeb | 0:d3e390d62607 | 708 | // do nothing for now |
danaeb | 0:d3e390d62607 | 709 | //history_size = _history_size; |
danaeb | 0:d3e390d62607 | 710 | history_size = 1; |
danaeb | 0:d3e390d62607 | 711 | command_group = SENSOR_GROUP_MAIN; |
danaeb | 0:d3e390d62607 | 712 | } |
danaeb | 0:d3e390d62607 | 713 | else { |
danaeb | 0:d3e390d62607 | 714 | history_size = _history_size; |
danaeb | 0:d3e390d62607 | 715 | } |
danaeb | 0:d3e390d62607 | 716 | // get mask, it tells what are the sensor used which have set values |
danaeb | 0:d3e390d62607 | 717 | // in memory for a given history size |
danaeb | 0:d3e390d62607 | 718 | |
danaeb | 0:d3e390d62607 | 719 | //_command_selector.compute_requiered_field(&_sensor_data, history_size, &field); |
danaeb | 0:d3e390d62607 | 720 | |
danaeb | 0:d3e390d62607 | 721 | #if 0 |
danaeb | 0:d3e390d62607 | 722 | if(!is_hourly_send){ |
danaeb | 0:d3e390d62607 | 723 | //these value are only set one time by hours |
danaeb | 0:d3e390d62607 | 724 | field.battery = 0; |
danaeb | 0:d3e390d62607 | 725 | field.board_temperature = 0; |
danaeb | 0:d3e390d62607 | 726 | field.board_humidity = 0; |
danaeb | 0:d3e390d62607 | 727 | } |
danaeb | 0:d3e390d62607 | 728 | #endif |
danaeb | 0:d3e390d62607 | 729 | /* |
danaeb | 0:d3e390d62607 | 730 | else{ |
danaeb | 0:d3e390d62607 | 731 | // it is the hourly send |
danaeb | 0:d3e390d62607 | 732 | // do not use history |
danaeb | 0:d3e390d62607 | 733 | history_size = 1; |
danaeb | 0:d3e390d62607 | 734 | } |
danaeb | 0:d3e390d62607 | 735 | */ |
danaeb | 0:d3e390d62607 | 736 | |
danaeb | 0:d3e390d62607 | 737 | //tr_debug("requested fields: 0x%02u", field.bits); |
danaeb | 0:d3e390d62607 | 738 | // the the mask is used to select the smallest command |
danaeb | 0:d3e390d62607 | 739 | //selected_command = _command_selector.get_command_sample(&_sensor_data, &field, history_size); |
danaeb | 0:d3e390d62607 | 740 | selected_command = _command_selector.get_command_sample(history_size, command_group); |
danaeb | 0:d3e390d62607 | 741 | |
danaeb | 0:d3e390d62607 | 742 | |
danaeb | 0:d3e390d62607 | 743 | bool is_pump_on = AppCommand::get_pump_state(); |
danaeb | 0:d3e390d62607 | 744 | //tr_debug("requested fields: 0x%02u", field.bits); |
danaeb | 0:d3e390d62607 | 745 | if(selected_command == NULL){ |
danaeb | 0:d3e390d62607 | 746 | tr_err("no matching command"); |
danaeb | 0:d3e390d62607 | 747 | return -1; |
danaeb | 0:d3e390d62607 | 748 | } |
danaeb | 0:d3e390d62607 | 749 | else{ |
danaeb | 0:d3e390d62607 | 750 | tr_info("command %d selected", selected_command->get_command_id(false, |
danaeb | 0:d3e390d62607 | 751 | is_pump_on/*_calendar->is_enable()*/ )); |
danaeb | 0:d3e390d62607 | 752 | } |
danaeb | 0:d3e390d62607 | 753 | // get maxlora payload |
danaeb | 0:d3e390d62607 | 754 | max_lora_payload = AppLora::get_next_transmission_max_size(); |
danaeb | 0:d3e390d62607 | 755 | tr_info("LoRa max packet %d", max_lora_payload); |
danaeb | 0:d3e390d62607 | 756 | |
danaeb | 0:d3e390d62607 | 757 | // Decrement the size of history while the command is bigger than |
danaeb | 0:d3e390d62607 | 758 | // the max lora payload size (for the current bandwith and sf) |
danaeb | 0:d3e390d62607 | 759 | |
danaeb | 0:d3e390d62607 | 760 | // not completly optmised, changing the history size can also |
danaeb | 0:d3e390d62607 | 761 | // change the command used. Here we keep using the same command |
danaeb | 0:d3e390d62607 | 762 | tr_info("expected history size %d", history_size); |
danaeb | 0:d3e390d62607 | 763 | while(selected_command->get_command_size(history_size, false) > |
danaeb | 0:d3e390d62607 | 764 | max_lora_payload){ |
danaeb | 0:d3e390d62607 | 765 | --history_size; |
danaeb | 0:d3e390d62607 | 766 | |
danaeb | 0:d3e390d62607 | 767 | // not sure it can happen but just in case |
danaeb | 0:d3e390d62607 | 768 | // Doesnt try to send packet for history size of 0, this doesnt make sense |
danaeb | 0:d3e390d62607 | 769 | tr_warn("history size too, using : %d instead", history_size); |
danaeb | 0:d3e390d62607 | 770 | if(history_size == 0){ |
danaeb | 0:d3e390d62607 | 771 | tr_err("history size: 0\r\n"); |
danaeb | 0:d3e390d62607 | 772 | return -1; |
danaeb | 0:d3e390d62607 | 773 | } |
danaeb | 0:d3e390d62607 | 774 | } |
danaeb | 0:d3e390d62607 | 775 | tr_info("selected history size %d", history_size); |
danaeb | 0:d3e390d62607 | 776 | // |
danaeb | 0:d3e390d62607 | 777 | // command id is different if timestamp is used |
danaeb | 0:d3e390d62607 | 778 | command_port = selected_command->get_command_id(false, |
danaeb | 0:d3e390d62607 | 779 | is_pump_on /* _calendar->is_enable() */); |
danaeb | 0:d3e390d62607 | 780 | |
danaeb | 0:d3e390d62607 | 781 | tr_debug("using command port: %d", command_port); |
danaeb | 0:d3e390d62607 | 782 | // get the timestamp at the last moment |
danaeb | 0:d3e390d62607 | 783 | Rtc *rtc = Rtc::get_instance(); |
danaeb | 0:d3e390d62607 | 784 | timestamp = rtc->get_time(); |
danaeb | 0:d3e390d62607 | 785 | |
danaeb | 0:d3e390d62607 | 786 | command_payload_size = selected_command->generate_command( |
danaeb | 0:d3e390d62607 | 787 | &_sensor_data, history_size, |
danaeb | 0:d3e390d62607 | 788 | false, timestamp, |
danaeb | 0:d3e390d62607 | 789 | _command_payload, COMMAND_PAYLOAD_SIZE); |
danaeb | 0:d3e390d62607 | 790 | |
danaeb | 0:d3e390d62607 | 791 | tr_info("payload size : %d", command_payload_size); |
danaeb | 0:d3e390d62607 | 792 | if(_global_state == GLOBAL_STATE_RUN){ |
danaeb | 0:d3e390d62607 | 793 | tr_info("sending samples"); |
danaeb | 0:d3e390d62607 | 794 | // acknowledged -> false |
danaeb | 0:d3e390d62607 | 795 | retcode = AppLora::send_message(_command_payload, |
danaeb | 0:d3e390d62607 | 796 | command_payload_size, command_port, false); |
danaeb | 0:d3e390d62607 | 797 | if(retcode < 0){ |
danaeb | 0:d3e390d62607 | 798 | tr_err("send error %d\r\n", retcode); |
danaeb | 0:d3e390d62607 | 799 | return -1; |
danaeb | 0:d3e390d62607 | 800 | } |
danaeb | 0:d3e390d62607 | 801 | else{ |
danaeb | 0:d3e390d62607 | 802 | _software_watchdog_reset(); |
danaeb | 0:d3e390d62607 | 803 | //_next_frame_timestamped = false; |
danaeb | 0:d3e390d62607 | 804 | } |
danaeb | 0:d3e390d62607 | 805 | } |
danaeb | 0:d3e390d62607 | 806 | return 0; |
danaeb | 0:d3e390d62607 | 807 | } |
danaeb | 0:d3e390d62607 | 808 | |
danaeb | 0:d3e390d62607 | 809 | s8 AppMain::_send_empty(void){ |
danaeb | 0:d3e390d62607 | 810 | u16 command_size; |
danaeb | 0:d3e390d62607 | 811 | u32 time; |
danaeb | 0:d3e390d62607 | 812 | |
danaeb | 0:d3e390d62607 | 813 | Rtc *rtc = Rtc::get_instance(); |
danaeb | 0:d3e390d62607 | 814 | time = rtc->get_time(); |
danaeb | 0:d3e390d62607 | 815 | command_size = CommandSample::generate_raw_command(true, time, NULL, 0, |
danaeb | 0:d3e390d62607 | 816 | _command_payload, COMMAND_PAYLOAD_SIZE); |
danaeb | 0:d3e390d62607 | 817 | if(_global_state == GLOBAL_STATE_RUN){ |
danaeb | 0:d3e390d62607 | 818 | s16 retcode; |
danaeb | 0:d3e390d62607 | 819 | tr_info("sending empty frame"); |
danaeb | 0:d3e390d62607 | 820 | // acknowledged -> false |
danaeb | 0:d3e390d62607 | 821 | retcode = AppLora::send_message(_command_payload, command_size, |
danaeb | 0:d3e390d62607 | 822 | COMMAND_TIMESTAMP_PORT, false); |
danaeb | 0:d3e390d62607 | 823 | if(retcode < 0){ |
danaeb | 0:d3e390d62607 | 824 | tr_err("send error %d\r\n", retcode); |
danaeb | 0:d3e390d62607 | 825 | return -1; |
danaeb | 0:d3e390d62607 | 826 | } |
danaeb | 0:d3e390d62607 | 827 | } |
danaeb | 0:d3e390d62607 | 828 | return 0; |
danaeb | 0:d3e390d62607 | 829 | } |
danaeb | 0:d3e390d62607 | 830 | |
danaeb | 0:d3e390d62607 | 831 |