diff --git a/include/aprsis.h b/include/aprsis.h index c6f2907..cae8e0f 100644 --- a/include/aprsis.h +++ b/include/aprsis.h @@ -76,4 +76,6 @@ void aprsis_send_loginstring(const char * callsign_with_ssid); char * aprsis_get_tx_buffer(void); uint8_t aprsis_get_aprsis_logged(void); +void aprsis_debug_set_simulate_timeout(void); + #endif /* APRSIS_H_ */ diff --git a/include/backups/sr9wxp.config b/include/backups/sr9wxp.config index 68d7f29..1f0b57d 100644 --- a/include/backups/sr9wxp.config +++ b/include/backups/sr9wxp.config @@ -139,7 +139,7 @@ // Comment this to disable beacon auto sending during startup (this can be risky if RF feedback occur) #define _BCN_ON_STARTUP -#define _WX_INTERVAL 4 // WX packet interval in minutes +#define _WX_INTERVAL 5 // WX packet interval in minutes #define _BCN_INTERVAL 124 // Own beacon interval in minutes #define _PTT_PUSHPULL // Uncomment this if you want PTT line to work as Push-pull instead of Open Drain @@ -284,7 +284,7 @@ //!< ----------------------- //#define ENG1 ENGINEERING1_EARLY_TX_ASSERT | ENGINEERING1_PWRCYCLE_GSM_ON_NOCOMM -#define ENG1 ENGINEERING1_INH_WX_PWR_HNDL +#define ENG1 ENGINEERING1_EARLY_TX_ASSERT | ENGINEERING1_INH_WX_PWR_HNDL //#define ENG2 ENGINEERING2_POWER_CYCLE_R // Do not touch this diff --git a/include/main.h b/include/main.h index 8c0f77d..bc962eb 100644 --- a/include/main.h +++ b/include/main.h @@ -15,7 +15,7 @@ #define SYSTICK_TICKS_PER_SECONDS 100 #define SYSTICK_TICKS_PERIOD 10 -#define INTERNAL_WATCHDOG +//#define INTERNAL_WATCHDOG #define EXTERNAL_WATCHDOG #define PWR_SWITCH_BOTH diff --git a/include/software_version.h b/include/software_version.h index 63f1128..d47eae9 100644 --- a/include/software_version.h +++ b/include/software_version.h @@ -8,8 +8,8 @@ #ifndef SOFTWARE_VERSION_H_ #define SOFTWARE_VERSION_H_ -#define SW_VER "EB00" -#define SW_DATE "13102023" +#define SW_VER "EB01" +#define SW_DATE "15102023" #define SW_KISS_PROTO "B" extern const char software_version_str[5]; diff --git a/include/stored_configuration_nvm/config_data.h b/include/stored_configuration_nvm/config_data.h index 6654e5a..597f1f1 100644 --- a/include/stored_configuration_nvm/config_data.h +++ b/include/stored_configuration_nvm/config_data.h @@ -178,13 +178,14 @@ typedef struct __attribute__((aligned (4))) config_data_basic_t { BUTTON_RESET_GSM_GPRS = 6, BUTTON_RECONNECT_APRSIS = 7, */ - #define BUTTON_FUNCTION_SEND_WX 1U - #define BUTTON_FUNCTION_SEND_WX_INET 2U - #define BUTTON_FUNCTION_SEND_BEACON 3U - #define BUTTON_FUNCTION_UART_KISS 4U - #define BUTTON_FUNCTION_UART_LOG 5U - #define BUTTON_FUNCION_RESET_GSM_GPRS 6U - #define BUTTON_FUNCTION_RECONNECT_APRSIS 7U + #define BUTTON_FUNCTION_SEND_WX 1U + #define BUTTON_FUNCTION_SEND_WX_INET 2U + #define BUTTON_FUNCTION_SEND_BEACON 3U + #define BUTTON_FUNCTION_UART_KISS 4U + #define BUTTON_FUNCTION_UART_LOG 5U + #define BUTTON_FUNCION_RESET_GSM_GPRS 6U + #define BUTTON_FUNCTION_RECONNECT_APRSIS 7U + #define BUTTON_FUNCTION_SIMULATE_APRSIS_TIMEOUT 8U uint8_t button_one_left; diff --git a/include/stored_configuration_nvm/configuration_handler.h b/include/stored_configuration_nvm/configuration_handler.h index 60fcefd..5dc0af5 100644 --- a/include/stored_configuration_nvm/configuration_handler.h +++ b/include/stored_configuration_nvm/configuration_handler.h @@ -35,6 +35,7 @@ typedef enum configuration_button_function_t { BUTTON_FORCE_UART_LOG = 5, BUTTON_RESET_GSM_GPRS = 6, BUTTON_RECONNECT_APRSIS = 7, + BUTTON_SIMULATE_APRSIS_TIMEOUT = 8 }configuration_button_function_t; uint32_t configuration_handler_check_crc(void); diff --git a/src/aprsis.c b/src/aprsis.c index 1545aae..6eef072 100644 --- a/src/aprsis.c +++ b/src/aprsis.c @@ -84,6 +84,8 @@ uint8_t aprsis_connected = 0; const char * aprsis_sucessfull_login = "# logresp\0"; +static uint8_t aprsis_successfull_conn_counter = 0; + /** * Counter of unsuccessful connects to APRS-IS, to trigger GSM modem reset. * Please note that it works differently that 'aprsis_reset_on_timeout' and @@ -94,12 +96,7 @@ const char * aprsis_sucessfull_login = "# logresp\0"; * some reason etc. Of course there is no guarantee that a reset in such * case will help, but there is nothing better to do. */ -uint8_t aprsis_unsucessfull_conn_counter = 0; - -/** - * A timestamp when server has send anything - */ -uint32_t aprsis_last_keepalive_ts = 0; +static uint8_t aprsis_unsucessfull_conn_counter = 0; /** * Set to one if the GSM modem shall be immediately reset when APRS-IS communication @@ -108,29 +105,44 @@ uint32_t aprsis_last_keepalive_ts = 0; * comes in when the connection has been established at least one time. It won't * help if there is some problem with establishing connection at all. */ -uint32_t aprsis_reset_on_timeout = 0; +static uint32_t aprsis_reset_on_timeout = 0; /** * Number of RF packets igated to APRS-IS system */ -uint16_t aprsis_igated_counter = 0; +static uint16_t aprsis_igated_counter = 0; /** * Counter of all packets originated from the station transmitted to APRS-IS server. * This doesn't include igated packets! */ -uint16_t aprsis_tx_counter = 0; +static uint16_t aprsis_tx_counter = 0; /** * Amount of keepalive packet received from the server. It is reset to zero * every connect event */ -uint16_t aprsis_keepalive_received_counter = 0; +static uint16_t aprsis_keepalive_received_counter = 0; /** * Amount of packets which are not keepalive */ -uint16_t aprsis_another_received_counter = 0; +static uint16_t aprsis_another_received_counter = 0; + +/** + * A timestamp when server has send anything + */ +static uint32_t aprsis_last_keepalive_ts = 0; + +/** + * A timestamp when any packet has been sent to + */ +static uint32_t aprsis_last_packet_transmit_ts = 0; + +/** + * Only for debugging purposes + */ +static uint8_t aprsis_debug_simulate_timeout = 0; #define APRSIS_LOGIN_STRING_RECEIVED_LN 64 @@ -255,6 +267,8 @@ aprsis_return_t aprsis_connect_and_login(const char * address, uint8_t address_l aprsis_connected = 1; + aprsis_successfull_conn_counter++; + // fast forward to the beginning of a response offset = text_fast_forward_to_first_printable((char*)receive_buff, srl_get_num_bytes_rxed(aprsis_serial_port)); @@ -345,8 +359,6 @@ sim800_return_t aprsis_disconnect(void) { aprsis_logged = 0; aprsis_connected = 0; - - gsm_sim800_poolers_request_engineering(); } return out; @@ -378,23 +390,43 @@ void aprsis_receive_callback(srl_context_t* srl_context) { */ void aprsis_check_alive(void) { - uint32_t timestamp = 0; + const uint32_t timestamp = master_time; - timestamp = master_time; + uint8_t dead = 0; + + if (aprsis_debug_simulate_timeout == 1) { + dead = 1; + } + + if (aprsis_successfull_conn_counter > 0) { + if (timestamp > (aprsis_last_keepalive_ts + APRSIS_TIMEOUT_MS)) { + dead = 1; + } + + if (timestamp > (aprsis_last_packet_transmit_ts + APRSIS_TIMEOUT_MS * 3 )) { + dead = 1; + } + } // check if connection is alive - if (aprsis_logged == 1 && (timestamp > (aprsis_last_keepalive_ts + APRSIS_TIMEOUT_MS))) { + if (dead == 1){ // reset the flag aprsis_logged = 0; aprsis_connected = 0; + aprsis_debug_simulate_timeout = 0; + + aprsis_last_keepalive_ts = master_time; + + aprsis_last_packet_transmit_ts = master_time; + if (rte_main_curret_powersave_mode != PWSAVE_AGGRESV) { // send a status message that APRS-IS connectios is gone status_send_aprsis_timeout(aprsis_unsucessfull_conn_counter); } - // check if it is intendend to reset GSM modem in case of timeout + // check if it is intended to reset GSM modem in case of timeout if (aprsis_reset_on_timeout == 0) { // close connection with force flag as it is uncertain if a remote server // finished connection explicitly, or the connection is stuck for @@ -488,6 +520,8 @@ void aprsis_send_wx_frame( humidity); aprsis_packet_tx_buffer[aprsis_packet_tx_message_size] = 0; + aprsis_last_packet_transmit_ts = main_get_master_time(); + gsm_sim800_tcpip_async_write((uint8_t *)aprsis_packet_tx_buffer, aprsis_packet_tx_message_size, aprsis_serial_port, aprsis_gsm_modem_state); } @@ -533,6 +567,8 @@ void aprsis_send_beacon( else { gsm_sim800_tcpip_write((uint8_t *)aprsis_packet_tx_buffer, aprsis_packet_tx_message_size, aprsis_serial_port, aprsis_gsm_modem_state); } + + aprsis_last_packet_transmit_ts = main_get_master_time(); } void aprsis_igate_to_aprsis(AX25Msg *msg, const char * callsign_with_ssid) { @@ -646,6 +682,8 @@ void aprsis_send_server_conn_status(const char * callsign_with_ssid) { aprsis_keepalive_received_counter, aprsis_another_received_counter); + aprsis_last_packet_transmit_ts = main_get_master_time(); + gsm_sim800_tcpip_async_write((uint8_t *)aprsis_packet_tx_buffer, aprsis_packet_tx_message_size, aprsis_serial_port, aprsis_gsm_modem_state); } @@ -672,3 +710,7 @@ char * aprsis_get_tx_buffer(void) { uint8_t aprsis_get_aprsis_logged(void) { return aprsis_logged; } + +void aprsis_debug_set_simulate_timeout(void) { + aprsis_debug_simulate_timeout = 1; +} diff --git a/src/button_parameteo.c b/src/button_parameteo.c index 1c97e63..f08e993 100644 --- a/src/button_parameteo.c +++ b/src/button_parameteo.c @@ -58,6 +58,9 @@ void button_check_all(configuration_button_function_t left, configuration_button case BUTTON_RESET_GSM_GPRS: gsm_sim800_reset(&main_gsm_state); break; + case BUTTON_FUNCTION_SIMULATE_APRSIS_TIMEOUT: + aprsis_debug_set_simulate_timeout(); + break; default: break; } @@ -77,6 +80,9 @@ void button_check_all(configuration_button_function_t left, configuration_button case BUTTON_RESET_GSM_GPRS: gsm_sim800_reset(&main_gsm_state); break; + case BUTTON_FUNCTION_SIMULATE_APRSIS_TIMEOUT: + aprsis_debug_set_simulate_timeout(); + break; default: break; } diff --git a/src/it_handlers.c b/src/it_handlers.c index f313c19..d729db8 100644 --- a/src/it_handlers.c +++ b/src/it_handlers.c @@ -158,8 +158,6 @@ void SysTick_Handler(void) { delay_decrement_counter(); - button_debounce(); - if (it_handlers_inhibit_radiomodem_dcd_led == 0) { led_control_led1_upper(main_ax25.dcd); } diff --git a/src/main.c b/src/main.c index b800452..cd5fd34 100644 --- a/src/main.c +++ b/src/main.c @@ -791,6 +791,7 @@ int main(int argc, char* argv[]){ // configuring an APRS path used to transmit own packets (telemetry, wx, beacons) main_own_path_ln = ConfigPath(main_own_path, main_config_data_basic); +#ifdef INTERNAL_WATCHDOG #if defined(STM32F10X_MD_VL) // enable write access to watchdog registers IWDG_WriteAccessCmd(IWDG_WriteAccess_Enable); @@ -838,6 +839,7 @@ int main(int argc, char* argv[]){ // do not disable watchdog when MCU halts on breakpoints DBGMCU->APB1FZR1 &= (0xFFFFFFFF ^ DBGMCU_APB1FZR1_DBG_IWDG_STOP); +#endif #endif // initialize i2c controller @@ -1437,6 +1439,8 @@ int main(int argc, char* argv[]){ digi_pool_viscous(); + button_debounce(); + #ifdef PARAMETEO if (main_config_data_mode->gsm == 1) { diff --git a/src/stored_configuration_nvm/configuration_handler.c b/src/stored_configuration_nvm/configuration_handler.c index e7babdc..d2602c9 100644 --- a/src/stored_configuration_nvm/configuration_handler.c +++ b/src/stored_configuration_nvm/configuration_handler.c @@ -914,13 +914,14 @@ configuration_button_function_t configuration_get_left_button(void) { configuration_button_function_t out = BUTTON_DISABLED; switch (main_config_data_basic->button_one_left) { - case 1: out = BUTTON_SEND_WX; break; - case 2: out = BUTTON_SEND_WX_INTERNET; break; - case 3: out = BUTTON_SEND_BEACON; break; - case 4: out = BUTTON_FORCE_UART_KISS; break; - case 5: out = BUTTON_FORCE_UART_LOG; break; - case 6: out = BUTTON_RESET_GSM_GPRS; break; - case 7: out = BUTTON_RECONNECT_APRSIS; break; + case BUTTON_FUNCTION_SEND_WX: out = BUTTON_SEND_WX; break; + case BUTTON_FUNCTION_SEND_WX_INET: out = BUTTON_SEND_WX_INTERNET; break; + case BUTTON_FUNCTION_SEND_BEACON: out = BUTTON_SEND_BEACON; break; + case BUTTON_FUNCTION_UART_KISS: out = BUTTON_FORCE_UART_KISS; break; + case BUTTON_FUNCTION_UART_LOG: out = BUTTON_FORCE_UART_LOG; break; + case BUTTON_FUNCION_RESET_GSM_GPRS: out = BUTTON_RESET_GSM_GPRS; break; + case BUTTON_FUNCTION_RECONNECT_APRSIS: out = BUTTON_RECONNECT_APRSIS; break; + case BUTTON_FUNCTION_SIMULATE_APRSIS_TIMEOUT: out = BUTTON_SIMULATE_APRSIS_TIMEOUT; break; } return out; @@ -931,13 +932,14 @@ configuration_button_function_t configuration_get_right_button(void) { configuration_button_function_t out = BUTTON_DISABLED; switch (main_config_data_basic->button_two_right) { - case 1: out = BUTTON_SEND_WX; break; - case 2: out = BUTTON_SEND_WX_INTERNET; break; - case 3: out = BUTTON_SEND_BEACON; break; - case 4: out = BUTTON_FORCE_UART_KISS; break; - case 5: out = BUTTON_FORCE_UART_LOG; break; - case 6: out = BUTTON_RESET_GSM_GPRS; break; - case 7: out = BUTTON_RECONNECT_APRSIS; break; + case BUTTON_FUNCTION_SEND_WX: out = BUTTON_SEND_WX; break; + case BUTTON_FUNCTION_SEND_WX_INET: out = BUTTON_SEND_WX_INTERNET; break; + case BUTTON_FUNCTION_SEND_BEACON: out = BUTTON_SEND_BEACON; break; + case BUTTON_FUNCTION_UART_KISS: out = BUTTON_FORCE_UART_KISS; break; + case BUTTON_FUNCTION_UART_LOG: out = BUTTON_FORCE_UART_LOG; break; + case BUTTON_FUNCION_RESET_GSM_GPRS: out = BUTTON_RESET_GSM_GPRS; break; + case BUTTON_FUNCTION_RECONNECT_APRSIS: out = BUTTON_RECONNECT_APRSIS; break; + case BUTTON_FUNCTION_SIMULATE_APRSIS_TIMEOUT: out = BUTTON_SIMULATE_APRSIS_TIMEOUT; break; } return out; diff --git a/system/include/gsm/sim800c_engineering.h b/system/include/gsm/sim800c_engineering.h index ccb9018..94266eb 100644 --- a/system/include/gsm/sim800c_engineering.h +++ b/system/include/gsm/sim800c_engineering.h @@ -19,6 +19,8 @@ extern uint8_t gsm_sim800_engineering_is_enabled; extern uint8_t gsm_sim800_engineering_successed; +extern uint8_t gsm_sim800_engineering_fail; + void gsm_sim800_engineering_enable(srl_context_t * srl_context, gsm_sim800_state_t * state); void gsm_sim800_engineering_disable(srl_context_t * srl_context, gsm_sim800_state_t * state); void gsm_sim800_engineering_request_data(srl_context_t * srl_context, gsm_sim800_state_t * state); diff --git a/system/src/gsm/sim800c.c b/system/src/gsm/sim800c.c index 448e825..2702cc4 100644 --- a/system/src/gsm/sim800c.c +++ b/system/src/gsm/sim800c.c @@ -300,17 +300,17 @@ void gsm_sim800_initialization_pool(srl_context_t * srl_context, gsm_sim800_stat // turn power off gsm_sim800_power_off(); - if (gsm_reset_counter > GSM_RESET_COUNTER_LIMIT) { +// if (gsm_reset_counter > GSM_RESET_COUNTER_LIMIT) { TODO *state = SIM800_INHIBITED_RESET_COUNTER; - } - else { - *state = SIM800_POWERED_OFF; - } +// } +// else { +// *state = SIM800_POWERED_OFF; +// } } else if (*state == SIM800_INHIBITED_RESET_COUNTER) { - if (gsm_reset_counter < GSM_RESET_COUNTER_LIMIT) { +// if (gsm_reset_counter < GSM_RESET_COUNTER_LIMIT) { TODO *state = SIM800_POWERED_OFF; - } +// } } else if (*state == SIM800_POWERED_OFF) { gsm_sim800_power_on(); @@ -921,7 +921,9 @@ void gsm_sim800_reset(gsm_sim800_state_t * state) { gsm_sim800_tcpip_reset(); - gsm_reset_counter += GSM_RESET_COUNTER_INCREMENT; + if (gsm_reset_counter < GSM_RESET_COUNTER_INCREMENT * 3) { + gsm_reset_counter += GSM_RESET_COUNTER_INCREMENT; + } } void gsm_sim800_create_status(char * buffer, int ln) { diff --git a/system/src/gsm/sim800c_engineering.c b/system/src/gsm/sim800c_engineering.c index e6bad26..ab75036 100644 --- a/system/src/gsm/sim800c_engineering.c +++ b/system/src/gsm/sim800c_engineering.c @@ -30,14 +30,23 @@ static const char * CENG0 = "+CENG: 0,\0"; #define LAC_OFFSET 42 #define LAC_LN 4 -uint8_t gsm_sim800_engineering_is_requested = 0; - +/** + * Set to one if correct response to engineering enable AT command + * has been received + */ uint8_t gsm_sim800_engineering_is_enabled = 0; -// set to one if correct response has been received for engineering data request. This is reset back to zero -// after disabling CENG or after 'gsm_sim800_engineering_request_data' is called +/** + * set to one if correct response has been received for engineering data request + * and new engineering data have been read. This is reset back to zero + * after disabling CENG or after 'gsm_sim800_engineering_request_data' is called + */ uint8_t gsm_sim800_engineering_successed = 0; +/** + * Set to one in case of any failure during engineering AT commands communication + */ +uint8_t gsm_sim800_engineering_fail = 0; static uint16_t gsm_sim800_rewind_to_ceng_0(uint8_t *srl_rx_buf_pointer, uint16_t buffer_ln, uint16_t gsm_response_start_idx) { @@ -172,7 +181,9 @@ void gsm_sim800_engineering_response_callback(srl_context_t * srl_context, gsm_s } else { - gsm_sim800_engineering_is_enabled = 0; + //gsm_sim800_engineering_is_enabled = 0; + + gsm_sim800_engineering_fail = 1; } } @@ -189,12 +200,13 @@ void gsm_sim800_engineering_response_callback(srl_context_t * srl_context, gsm_s } else { gsm_sim800_engineering_successed = 0; + + gsm_sim800_engineering_fail = 1; } } else if (gsm_at_command_sent_last == ENGINEERING_DISABLE) { gsm_sim800_engineering_is_enabled = 0; - } } diff --git a/system/src/gsm/sim800c_poolers.c b/system/src/gsm/sim800c_poolers.c index 5188581..82c66c2 100644 --- a/system/src/gsm/sim800c_poolers.c +++ b/system/src/gsm/sim800c_poolers.c @@ -23,7 +23,7 @@ void gsm_sim800_poolers_ten_seconds(srl_context_t * srl_context, gsm_sim800_stat // if no engineering is currently processed, gprs is ready and APRS-IS connection // is not alive now. - if ( gsm_sim800_engineering_is_enabled == 0 && + if ( sim800_poolers_request_engineering == 0 && gsm_sim800_gprs_ready == 1 && aprsis_connected == 0) { aprsis_connect_and_login_default(1); @@ -47,6 +47,15 @@ void gsm_sim800_poolers_one_second(srl_context_t * srl_context, gsm_sim800_state // if GPRS is ready an there is a request to obtain engineering information if (sim800_poolers_request_engineering == 1 && aprsis_connected == 0) { + // check if engineering has failed or not + if (gsm_sim800_engineering_fail == 1) { + sim800_poolers_request_engineering = 0; + + gsm_sim800_engineering_fail = 0; + + return; + } + // initial state when engineering is not enabled and not finished if (gsm_sim800_engineering_is_enabled == 0 && gsm_sim800_engineering_successed == 0) { gsm_sim800_engineering_enable(srl_context, state);