mirror of
				https://github.com/esphome/esphome.git
				synced 2025-11-04 09:01:49 +00:00 
			
		
		
		
	handle bad connection and reboot_timeout
This commit is contained in:
		@@ -14,6 +14,7 @@ from esphome.const import (
 | 
				
			|||||||
    CONF_ON_CONNECT,
 | 
					    CONF_ON_CONNECT,
 | 
				
			||||||
    CONF_ON_DISCONNECT,
 | 
					    CONF_ON_DISCONNECT,
 | 
				
			||||||
    CONF_PASSWORD,
 | 
					    CONF_PASSWORD,
 | 
				
			||||||
 | 
					    CONF_REBOOT_TIMEOUT,
 | 
				
			||||||
    CONF_RX_PIN,
 | 
					    CONF_RX_PIN,
 | 
				
			||||||
    CONF_TRIGGER_ID,
 | 
					    CONF_TRIGGER_ID,
 | 
				
			||||||
    CONF_TX_PIN,
 | 
					    CONF_TX_PIN,
 | 
				
			||||||
@@ -88,6 +89,9 @@ CONFIG_SCHEMA = cv.All(
 | 
				
			|||||||
            cv.Optional(CONF_ENABLE_ON_BOOT, default=True): cv.boolean,
 | 
					            cv.Optional(CONF_ENABLE_ON_BOOT, default=True): cv.boolean,
 | 
				
			||||||
            cv.Optional(CONF_ENABLE_CMUX, default=False): cv.boolean,
 | 
					            cv.Optional(CONF_ENABLE_CMUX, default=False): cv.boolean,
 | 
				
			||||||
            cv.Optional(CONF_DEBUG, default=False): cv.boolean,
 | 
					            cv.Optional(CONF_DEBUG, default=False): cv.boolean,
 | 
				
			||||||
 | 
					            cv.Optional(
 | 
				
			||||||
 | 
					                CONF_REBOOT_TIMEOUT, default="10min"
 | 
				
			||||||
 | 
					            ): cv.positive_time_period_milliseconds,
 | 
				
			||||||
            cv.Optional(CONF_ON_NOT_RESPONDING): automation.validate_automation(
 | 
					            cv.Optional(CONF_ON_NOT_RESPONDING): automation.validate_automation(
 | 
				
			||||||
                {
 | 
					                {
 | 
				
			||||||
                    cv.GenerateID(CONF_TRIGGER_ID): cv.declare_id(
 | 
					                    cv.GenerateID(CONF_TRIGGER_ID): cv.declare_id(
 | 
				
			||||||
@@ -168,6 +172,9 @@ async def to_code(config):
 | 
				
			|||||||
    cg.add_define("USE_MODEM")
 | 
					    cg.add_define("USE_MODEM")
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    var = cg.new_Pvariable(config[CONF_ID])
 | 
					    var = cg.new_Pvariable(config[CONF_ID])
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    cg.add(var.set_reboot_timeout(config[CONF_REBOOT_TIMEOUT]))
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    if use_address := config.get(CONF_USE_ADDRESS, None):
 | 
					    if use_address := config.get(CONF_USE_ADDRESS, None):
 | 
				
			||||||
        cg.add(var.set_use_address(use_address))
 | 
					        cg.add(var.set_use_address(use_address))
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -54,6 +54,21 @@ void ModemComponent::enable_debug() {
 | 
				
			|||||||
  // esp_log_level_set("CMUX Received", ESP_LOG_VERBOSE);
 | 
					  // esp_log_level_set("CMUX Received", ESP_LOG_VERBOSE);
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					bool ModemComponent::is_modem_connected(bool verbose) {
 | 
				
			||||||
 | 
					  float rssi, ber;
 | 
				
			||||||
 | 
					  int network_mode = 0;
 | 
				
			||||||
 | 
					  bool network_attached = this->is_network_attached_();
 | 
				
			||||||
 | 
					  this->get_signal_quality(rssi, ber);
 | 
				
			||||||
 | 
					  this->dce->get_network_system_mode(network_mode);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  bool connected = (network_mode != 0) && (!std::isnan(rssi)) && network_attached;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  ESP_LOGD(TAG, "Modem internal network status: %s (attached: %s, type: %s, rssi: %.0fdB %s, ber: %.0f%%)",
 | 
				
			||||||
 | 
					           connected ? "Good" : "BAD", network_attached ? "Yes" : "NO",
 | 
				
			||||||
 | 
					           network_system_mode_to_string(network_mode).c_str(), rssi, get_signal_bars(rssi).c_str(), ber);
 | 
				
			||||||
 | 
					  return connected;
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
AtCommandResult ModemComponent::send_at(const std::string &cmd, uint32_t timeout) {
 | 
					AtCommandResult ModemComponent::send_at(const std::string &cmd, uint32_t timeout) {
 | 
				
			||||||
  AtCommandResult at_command_result;
 | 
					  AtCommandResult at_command_result;
 | 
				
			||||||
  at_command_result.success = false;
 | 
					  at_command_result.success = false;
 | 
				
			||||||
@@ -141,13 +156,13 @@ void ModemComponent::enable() {
 | 
				
			|||||||
  if (this->component_state_ == ModemComponentState::DISABLED) {
 | 
					  if (this->component_state_ == ModemComponentState::DISABLED) {
 | 
				
			||||||
    this->component_state_ = ModemComponentState::DISCONNECTED;
 | 
					    this->component_state_ = ModemComponentState::DISCONNECTED;
 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
  this->internal_state_.start = true;
 | 
					 | 
				
			||||||
  this->internal_state_.enabled = true;
 | 
					  this->internal_state_.enabled = true;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
void ModemComponent::disable() {
 | 
					void ModemComponent::disable() {
 | 
				
			||||||
  ESP_LOGD(TAG, "Disabling modem");
 | 
					  ESP_LOGD(TAG, "Disabling modem");
 | 
				
			||||||
  this->internal_state_.enabled = false;
 | 
					  this->internal_state_.enabled = false;
 | 
				
			||||||
 | 
					  this->internal_state_.starting = false;
 | 
				
			||||||
  if (this->component_state_ != ModemComponentState::CONNECTED) {
 | 
					  if (this->component_state_ != ModemComponentState::CONNECTED) {
 | 
				
			||||||
    this->component_state_ = ModemComponentState::DISCONNECTED;
 | 
					    this->component_state_ = ModemComponentState::DISCONNECTED;
 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
@@ -156,14 +171,32 @@ void ModemComponent::disable() {
 | 
				
			|||||||
void ModemComponent::reconnect() {
 | 
					void ModemComponent::reconnect() {
 | 
				
			||||||
  if (!this->internal_state_.reconnect) {
 | 
					  if (!this->internal_state_.reconnect) {
 | 
				
			||||||
    this->internal_state_.reconnect = true;
 | 
					    this->internal_state_.reconnect = true;
 | 
				
			||||||
    this->component_state_ = ModemComponentState::NOT_RESPONDING;
 | 
					    this->internal_state_.connected = false;
 | 
				
			||||||
 | 
					    this->component_state_ = ModemComponentState::DISCONNECTED;
 | 
				
			||||||
    // if reconnect fail, let some time before retry
 | 
					    // if reconnect fail, let some time before retry
 | 
				
			||||||
    set_timeout(120000, [this]() { this->internal_state_.reconnect = false; });
 | 
					    set_timeout("retry_reconnect", this->reconnect_grace_period_,
 | 
				
			||||||
 | 
					                [this]() { this->internal_state_.reconnect = false; });
 | 
				
			||||||
  } else {
 | 
					  } else {
 | 
				
			||||||
    ESP_LOGD(TAG, "Reconnecting already in progress.");
 | 
					    ESP_LOGD(TAG, "Reconnecting already in progress.");
 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					bool ModemComponent::get_signal_quality(float &rssi, float &ber) {
 | 
				
			||||||
 | 
					  rssi = NAN;
 | 
				
			||||||
 | 
					  ber = NAN;
 | 
				
			||||||
 | 
					  int modem_rssi = 99;
 | 
				
			||||||
 | 
					  int modem_ber = 99;
 | 
				
			||||||
 | 
					  if (this->modem_ready() &&
 | 
				
			||||||
 | 
					      (global_modem_component->dce->get_signal_quality(modem_rssi, modem_ber) == command_result::OK)) {
 | 
				
			||||||
 | 
					    if (modem_rssi != 99)
 | 
				
			||||||
 | 
					      rssi = -113 + (modem_rssi * 2);
 | 
				
			||||||
 | 
					    if (modem_ber != 99)
 | 
				
			||||||
 | 
					      ber = 0.1f * (modem_ber * modem_ber);
 | 
				
			||||||
 | 
					    return true;
 | 
				
			||||||
 | 
					  }
 | 
				
			||||||
 | 
					  return false;
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
network::IPAddresses ModemComponent::get_ip_addresses() {
 | 
					network::IPAddresses ModemComponent::get_ip_addresses() {
 | 
				
			||||||
  network::IPAddresses addresses;
 | 
					  network::IPAddresses addresses;
 | 
				
			||||||
  esp_netif_ip_info_t ip;
 | 
					  esp_netif_ip_info_t ip;
 | 
				
			||||||
@@ -243,7 +276,6 @@ void ModemComponent::loop() {
 | 
				
			|||||||
  static uint32_t next_loop_millis = millis();
 | 
					  static uint32_t next_loop_millis = millis();
 | 
				
			||||||
  static uint32_t last_health_check = millis();
 | 
					  static uint32_t last_health_check = millis();
 | 
				
			||||||
  static bool connecting = false;
 | 
					  static bool connecting = false;
 | 
				
			||||||
  static uint8_t network_attach_retry = 10;
 | 
					 | 
				
			||||||
 | 
					
 | 
				
			||||||
  if ((millis() < next_loop_millis)) {
 | 
					  if ((millis() < next_loop_millis)) {
 | 
				
			||||||
    // some commands need some delay
 | 
					    // some commands need some delay
 | 
				
			||||||
@@ -265,13 +297,13 @@ void ModemComponent::loop() {
 | 
				
			|||||||
        ESP_LOGD(TAG, "Will check that the modem is on in %.1fs...", float(this->power_tonuart_) / 1000);
 | 
					        ESP_LOGD(TAG, "Will check that the modem is on in %.1fs...", float(this->power_tonuart_) / 1000);
 | 
				
			||||||
        break;
 | 
					        break;
 | 
				
			||||||
      case ModemPowerState::TONUART:
 | 
					      case ModemPowerState::TONUART:
 | 
				
			||||||
        this->internal_state_.power_transition = false;
 | 
					 | 
				
			||||||
        ESP_LOGD(TAG, "TONUART check sync");
 | 
					        ESP_LOGD(TAG, "TONUART check sync");
 | 
				
			||||||
        if (!this->modem_sync_()) {
 | 
					        if (!this->modem_sync_()) {
 | 
				
			||||||
          ESP_LOGE(TAG, "Unable to power on the modem");
 | 
					          ESP_LOGE(TAG, "Unable to power on the modem");
 | 
				
			||||||
        } else {
 | 
					        } else {
 | 
				
			||||||
          ESP_LOGI(TAG, "Modem powered ON");
 | 
					          ESP_LOGI(TAG, "Modem powered ON");
 | 
				
			||||||
        }
 | 
					        }
 | 
				
			||||||
 | 
					        this->internal_state_.power_transition = false;
 | 
				
			||||||
        break;
 | 
					        break;
 | 
				
			||||||
      case ModemPowerState::TOFF:
 | 
					      case ModemPowerState::TOFF:
 | 
				
			||||||
        delay(10);
 | 
					        delay(10);
 | 
				
			||||||
@@ -301,23 +333,14 @@ void ModemComponent::loop() {
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
  switch (this->component_state_) {
 | 
					  switch (this->component_state_) {
 | 
				
			||||||
    case ModemComponentState::NOT_RESPONDING:
 | 
					    case ModemComponentState::NOT_RESPONDING:
 | 
				
			||||||
      if (this->internal_state_.start) {
 | 
					      if (this->internal_state_.starting) {
 | 
				
			||||||
        if (this->modem_ready(true) && !this->internal_state_.connected) {
 | 
					        ESP_LOGW(TAG, "Modem not responding, resetting...");
 | 
				
			||||||
          ESP_LOGI(TAG, "Modem recovered");
 | 
					        this->internal_state_.connected = false;
 | 
				
			||||||
          this->status_clear_warning();
 | 
					        // this->modem_lazy_init_();
 | 
				
			||||||
          this->component_state_ = ModemComponentState::DISCONNECTED;
 | 
					        if (!this->modem_sync_()) {
 | 
				
			||||||
 | 
					          ESP_LOGE(TAG, "Unable to recover modem");
 | 
				
			||||||
        } else {
 | 
					        } else {
 | 
				
			||||||
          ESP_LOGI(TAG, "Resetting modem");
 | 
					          this->component_state_ = ModemComponentState::DISCONNECTED;
 | 
				
			||||||
          this->internal_state_.connected = false;
 | 
					 | 
				
			||||||
          this->modem_lazy_init_();
 | 
					 | 
				
			||||||
          if (!this->modem_sync_()) {
 | 
					 | 
				
			||||||
            ESP_LOGE(TAG, "Unable to recover modem");
 | 
					 | 
				
			||||||
          } else {
 | 
					 | 
				
			||||||
            this->component_state_ = ModemComponentState::DISCONNECTED;
 | 
					 | 
				
			||||||
          }
 | 
					 | 
				
			||||||
          // if (!this->internal_state_.powered_on) {
 | 
					 | 
				
			||||||
          //   this->poweron_();
 | 
					 | 
				
			||||||
          // }
 | 
					 | 
				
			||||||
        }
 | 
					        }
 | 
				
			||||||
      }
 | 
					      }
 | 
				
			||||||
      break;
 | 
					      break;
 | 
				
			||||||
@@ -330,31 +353,30 @@ void ModemComponent::loop() {
 | 
				
			|||||||
          break;
 | 
					          break;
 | 
				
			||||||
        } else if (!this->internal_state_.modem_synced) {
 | 
					        } else if (!this->internal_state_.modem_synced) {
 | 
				
			||||||
          if (!this->modem_sync_()) {
 | 
					          if (!this->modem_sync_()) {
 | 
				
			||||||
            ESP_LOGE(TAG, "Modem not responding");
 | 
					 | 
				
			||||||
            this->component_state_ = ModemComponentState::NOT_RESPONDING;
 | 
					            this->component_state_ = ModemComponentState::NOT_RESPONDING;
 | 
				
			||||||
          }
 | 
					          }
 | 
				
			||||||
        }
 | 
					        }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
        if (this->internal_state_.start) {
 | 
					        if (this->internal_state_.starting) {
 | 
				
			||||||
 | 
					          float time_left_s = float(this->timeout_ - (millis() - this->internal_state_.startms)) / 1000;
 | 
				
			||||||
          // want to connect
 | 
					          // want to connect
 | 
				
			||||||
 | 
					          if ((millis() - this->internal_state_.startms) > this->timeout_) {
 | 
				
			||||||
 | 
					            this->abort_("Timeout while trying to connect");
 | 
				
			||||||
 | 
					          }
 | 
				
			||||||
          if (!connecting) {
 | 
					          if (!connecting) {
 | 
				
			||||||
            // wait for the modem be attached to a network, start ppp, and set connecting=true
 | 
					            // wait for the modem be attached to a network, start ppp, and set connecting=true
 | 
				
			||||||
            if (is_network_attached_()) {
 | 
					            if (this->is_modem_connected()) {
 | 
				
			||||||
              network_attach_retry = 10;
 | 
					 | 
				
			||||||
              if (this->start_ppp_()) {
 | 
					              if (this->start_ppp_()) {
 | 
				
			||||||
                connecting = true;
 | 
					                connecting = true;
 | 
				
			||||||
                next_loop_millis = millis() + 2000;  // delay for next loop
 | 
					              } else {
 | 
				
			||||||
 | 
					                ESP_LOGE(TAG, "modem is unable to enter PPP (time left before abort: %.0fs)", time_left_s);
 | 
				
			||||||
 | 
					                this->stop_ppp_();
 | 
				
			||||||
 | 
					                this->is_modem_connected();
 | 
				
			||||||
              }
 | 
					              }
 | 
				
			||||||
            } else {
 | 
					            } else {
 | 
				
			||||||
              ESP_LOGD(TAG, "Waiting for the modem to be attached to a network (left retries: %" PRIu8 ")",
 | 
					              ESP_LOGW(TAG, "Waiting for the modem to be attached to a network (time left before abort: %.0fs)",
 | 
				
			||||||
                       network_attach_retry);
 | 
					                       time_left_s);
 | 
				
			||||||
              network_attach_retry--;
 | 
					              next_loop_millis = millis() + 5000;  // delay to retry
 | 
				
			||||||
              if (network_attach_retry == 0) {
 | 
					 | 
				
			||||||
                ESP_LOGE(TAG, "modem is unable to attach to a network");
 | 
					 | 
				
			||||||
                network_attach_retry = 10;
 | 
					 | 
				
			||||||
                this->component_state_ = ModemComponentState::NOT_RESPONDING;
 | 
					 | 
				
			||||||
              }
 | 
					 | 
				
			||||||
              next_loop_millis = millis() + 1000;  // delay to retry
 | 
					 | 
				
			||||||
            }
 | 
					            }
 | 
				
			||||||
          } else {
 | 
					          } else {
 | 
				
			||||||
            // connecting
 | 
					            // connecting
 | 
				
			||||||
@@ -378,7 +400,8 @@ void ModemComponent::loop() {
 | 
				
			|||||||
            }
 | 
					            }
 | 
				
			||||||
          }
 | 
					          }
 | 
				
			||||||
        } else {
 | 
					        } else {
 | 
				
			||||||
          this->internal_state_.start = true;
 | 
					          this->internal_state_.starting = true;
 | 
				
			||||||
 | 
					          this->internal_state_.startms = millis();
 | 
				
			||||||
        }
 | 
					        }
 | 
				
			||||||
      } else {
 | 
					      } else {
 | 
				
			||||||
        this->component_state_ = ModemComponentState::DISABLED;
 | 
					        this->component_state_ = ModemComponentState::DISABLED;
 | 
				
			||||||
@@ -386,21 +409,19 @@ void ModemComponent::loop() {
 | 
				
			|||||||
      break;
 | 
					      break;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    case ModemComponentState::CONNECTED:
 | 
					    case ModemComponentState::CONNECTED:
 | 
				
			||||||
 | 
					      this->internal_state_.starting = false;
 | 
				
			||||||
      if (this->internal_state_.enabled) {
 | 
					      if (this->internal_state_.enabled) {
 | 
				
			||||||
        if (!this->internal_state_.connected) {
 | 
					        if (!this->internal_state_.connected) {
 | 
				
			||||||
          this->status_set_warning("Connection via Modem lost!");
 | 
					          this->status_set_warning("Connection via Modem lost!");
 | 
				
			||||||
          this->component_state_ = ModemComponentState::DISCONNECTED;
 | 
					          this->component_state_ = ModemComponentState::DISCONNECTED;
 | 
				
			||||||
          break;
 | 
					          break;
 | 
				
			||||||
        }
 | 
					        }
 | 
				
			||||||
        // clear flags if previously set by this->reconnect()
 | 
					 | 
				
			||||||
        this->internal_state_.reconnect = false;
 | 
					 | 
				
			||||||
 | 
					
 | 
				
			||||||
        if (this->cmux_ && (millis() - last_health_check) > 30000) {
 | 
					        if (this->cmux_ && (millis() - last_health_check) > 30000) {
 | 
				
			||||||
          ESP_LOGD(TAG, "modem health check");
 | 
					 | 
				
			||||||
          last_health_check = millis();
 | 
					          last_health_check = millis();
 | 
				
			||||||
          if (!this->get_imei()) {
 | 
					          if (!this->is_modem_connected()) {
 | 
				
			||||||
            ESP_LOGW(TAG, "modem health check failed");
 | 
					            ESP_LOGW(TAG, "Reconnecting...");
 | 
				
			||||||
            this->component_state_ = ModemComponentState::NOT_RESPONDING;
 | 
					            this->reconnect();
 | 
				
			||||||
          }
 | 
					          }
 | 
				
			||||||
        }
 | 
					        }
 | 
				
			||||||
      } else {
 | 
					      } else {
 | 
				
			||||||
@@ -626,7 +647,9 @@ bool ModemComponent::is_network_attached_() {
 | 
				
			|||||||
bool ModemComponent::start_ppp_() {
 | 
					bool ModemComponent::start_ppp_() {
 | 
				
			||||||
  this->internal_state_.connect_begin = millis();
 | 
					  this->internal_state_.connect_begin = millis();
 | 
				
			||||||
  this->status_set_warning("Starting connection");
 | 
					  this->status_set_warning("Starting connection");
 | 
				
			||||||
  watchdog::WatchdogManager wdt(10000);
 | 
					  watchdog::WatchdogManager wdt(15000);  // mini 10000
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  uint32_t now = millis();
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  // will be set to true on event IP_EVENT_PPP_GOT_IP
 | 
					  // will be set to true on event IP_EVENT_PPP_GOT_IP
 | 
				
			||||||
  this->internal_state_.got_ipv4_address = false;
 | 
					  this->internal_state_.got_ipv4_address = false;
 | 
				
			||||||
@@ -643,7 +666,9 @@ bool ModemComponent::start_ppp_() {
 | 
				
			|||||||
  }
 | 
					  }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  if (!status) {
 | 
					  if (!status) {
 | 
				
			||||||
    ESP_LOGE(TAG, "Unable to change modem mode to PPP");
 | 
					    ESP_LOGE(TAG, "Unable to change modem mode to PPP after %" PRIu32 "ms", millis() - now);
 | 
				
			||||||
 | 
					  } else {
 | 
				
			||||||
 | 
					    ESP_LOGD(TAG, "Entered PPP after %" PRIu32 "ms", millis() - now);
 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  return status;
 | 
					  return status;
 | 
				
			||||||
@@ -658,7 +683,7 @@ bool ModemComponent::stop_ppp_() {
 | 
				
			|||||||
    status = this->dce->set_mode(modem_mode::COMMAND_MODE);
 | 
					    status = this->dce->set_mode(modem_mode::COMMAND_MODE);
 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
  if (!status) {
 | 
					  if (!status) {
 | 
				
			||||||
    ESP_LOGE(TAG, "Error exiting PPP");
 | 
					    ESP_LOGW(TAG, "Error exiting PPP");
 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
  return status;
 | 
					  return status;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
@@ -709,6 +734,12 @@ void ModemComponent::poweroff_() {
 | 
				
			|||||||
  }
 | 
					  }
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					void ModemComponent::abort_(const std::string &message) {
 | 
				
			||||||
 | 
					  ESP_LOGE(TAG, "Aborting: %s", message.c_str());
 | 
				
			||||||
 | 
					  this->send_at("AT+CFUN=1,1");
 | 
				
			||||||
 | 
					  App.reboot();
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
void ModemComponent::dump_connect_params_() {
 | 
					void ModemComponent::dump_connect_params_() {
 | 
				
			||||||
  if (!this->internal_state_.connected) {
 | 
					  if (!this->internal_state_.connected) {
 | 
				
			||||||
    ESP_LOGCONFIG(TAG, "Modem connection: Not connected");
 | 
					    ESP_LOGCONFIG(TAG, "Modem connection: Not connected");
 | 
				
			||||||
@@ -716,11 +747,11 @@ void ModemComponent::dump_connect_params_() {
 | 
				
			|||||||
  }
 | 
					  }
 | 
				
			||||||
  esp_netif_ip_info_t ip;
 | 
					  esp_netif_ip_info_t ip;
 | 
				
			||||||
  esp_netif_get_ip_info(this->ppp_netif_, &ip);
 | 
					  esp_netif_get_ip_info(this->ppp_netif_, &ip);
 | 
				
			||||||
  ESP_LOGCONFIG(TAG, "Modem connection:");
 | 
					  ESP_LOGI(TAG, "Modem connection:");
 | 
				
			||||||
  ESP_LOGCONFIG(TAG, "  IP Address  : %s", network::IPAddress(&ip.ip).str().c_str());
 | 
					  ESP_LOGI(TAG, "  IP Address  : %s", network::IPAddress(&ip.ip).str().c_str());
 | 
				
			||||||
  ESP_LOGCONFIG(TAG, "  Hostname    : '%s'", App.get_name().c_str());
 | 
					  ESP_LOGI(TAG, "  Hostname    : '%s'", App.get_name().c_str());
 | 
				
			||||||
  ESP_LOGCONFIG(TAG, "  Subnet      : %s", network::IPAddress(&ip.netmask).str().c_str());
 | 
					  ESP_LOGI(TAG, "  Subnet      : %s", network::IPAddress(&ip.netmask).str().c_str());
 | 
				
			||||||
  ESP_LOGCONFIG(TAG, "  Gateway     : %s", network::IPAddress(&ip.gw).str().c_str());
 | 
					  ESP_LOGI(TAG, "  Gateway     : %s", network::IPAddress(&ip.gw).str().c_str());
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  const ip_addr_t *dns_main_ip = dns_getserver(ESP_NETIF_DNS_MAIN);
 | 
					  const ip_addr_t *dns_main_ip = dns_getserver(ESP_NETIF_DNS_MAIN);
 | 
				
			||||||
  const ip_addr_t *dns_backup_ip = dns_getserver(ESP_NETIF_DNS_BACKUP);
 | 
					  const ip_addr_t *dns_backup_ip = dns_getserver(ESP_NETIF_DNS_BACKUP);
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -52,6 +52,7 @@ struct AtCommandResult {
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
class ModemComponent : public Component {
 | 
					class ModemComponent : public Component {
 | 
				
			||||||
 public:
 | 
					 public:
 | 
				
			||||||
 | 
					  void set_reboot_timeout(uint16_t timeout) { this->timeout_ = timeout; }
 | 
				
			||||||
  void set_use_address(const std::string &use_address) { this->use_address_ = use_address; }
 | 
					  void set_use_address(const std::string &use_address) { this->use_address_ = use_address; }
 | 
				
			||||||
  void set_rx_pin(InternalGPIOPin *rx_pin) { this->rx_pin_ = rx_pin; }
 | 
					  void set_rx_pin(InternalGPIOPin *rx_pin) { this->rx_pin_ = rx_pin; }
 | 
				
			||||||
  void set_tx_pin(InternalGPIOPin *tx_pin) { this->tx_pin_ = tx_pin; }
 | 
					  void set_tx_pin(InternalGPIOPin *tx_pin) { this->tx_pin_ = tx_pin; }
 | 
				
			||||||
@@ -67,8 +68,10 @@ class ModemComponent : public Component {
 | 
				
			|||||||
  void enable_cmux() { this->cmux_ = true; }
 | 
					  void enable_cmux() { this->cmux_ = true; }
 | 
				
			||||||
  void enable_debug();
 | 
					  void enable_debug();
 | 
				
			||||||
  void add_init_at_command(const std::string &cmd) { this->init_at_commands_.push_back(cmd); }
 | 
					  void add_init_at_command(const std::string &cmd) { this->init_at_commands_.push_back(cmd); }
 | 
				
			||||||
  bool is_connected() { return this->component_state_ == ModemComponentState::CONNECTED; }
 | 
					  bool is_connected() { return this->internal_state_.connected; }
 | 
				
			||||||
  bool is_disabled() { return this->component_state_ == ModemComponentState::DISABLED; }
 | 
					  bool is_disabled() { return this->component_state_ == ModemComponentState::DISABLED; }
 | 
				
			||||||
 | 
					  bool is_modem_connected(bool verbose);  // this if for modem only, not PPP
 | 
				
			||||||
 | 
					  bool is_modem_connected() { return this->is_modem_connected(true); }
 | 
				
			||||||
  AtCommandResult send_at(const std::string &cmd, uint32_t timeout);
 | 
					  AtCommandResult send_at(const std::string &cmd, uint32_t timeout);
 | 
				
			||||||
  AtCommandResult send_at(const std::string &cmd);
 | 
					  AtCommandResult send_at(const std::string &cmd);
 | 
				
			||||||
  AtCommandResult get_imei();
 | 
					  AtCommandResult get_imei();
 | 
				
			||||||
@@ -78,6 +81,7 @@ class ModemComponent : public Component {
 | 
				
			|||||||
  void enable();
 | 
					  void enable();
 | 
				
			||||||
  void disable();
 | 
					  void disable();
 | 
				
			||||||
  void reconnect();
 | 
					  void reconnect();
 | 
				
			||||||
 | 
					  bool get_signal_quality(float &rssi, float &ber);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  network::IPAddresses get_ip_addresses();
 | 
					  network::IPAddresses get_ip_addresses();
 | 
				
			||||||
  std::string get_use_address() const;
 | 
					  std::string get_use_address() const;
 | 
				
			||||||
@@ -90,12 +94,7 @@ class ModemComponent : public Component {
 | 
				
			|||||||
  void loop() override;
 | 
					  void loop() override;
 | 
				
			||||||
  void dump_config() override { this->dump_connect_params_(); }
 | 
					  void dump_config() override { this->dump_connect_params_(); }
 | 
				
			||||||
  float get_setup_priority() const override { return setup_priority::WIFI + 1; }  // just before WIFI
 | 
					  float get_setup_priority() const override { return setup_priority::WIFI + 1; }  // just before WIFI
 | 
				
			||||||
  bool can_proceed() override {
 | 
					  bool can_proceed() override { return network::is_disabled() || this->is_connected(); };
 | 
				
			||||||
    if (!this->internal_state_.enabled) {
 | 
					 | 
				
			||||||
      return true;
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
    return this->is_connected();
 | 
					 | 
				
			||||||
  };
 | 
					 | 
				
			||||||
  void add_on_state_callback(std::function<void(ModemComponentState, ModemComponentState)> &&callback) {
 | 
					  void add_on_state_callback(std::function<void(ModemComponentState, ModemComponentState)> &&callback) {
 | 
				
			||||||
    this->on_state_callback_.add(std::move(callback));
 | 
					    this->on_state_callback_.add(std::move(callback));
 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
@@ -113,10 +112,12 @@ class ModemComponent : public Component {
 | 
				
			|||||||
  bool stop_ppp_();
 | 
					  bool stop_ppp_();
 | 
				
			||||||
  void poweron_();
 | 
					  void poweron_();
 | 
				
			||||||
  void poweroff_();
 | 
					  void poweroff_();
 | 
				
			||||||
 | 
					  void abort_(const std::string &message);
 | 
				
			||||||
  static void ip_event_handler(void *arg, esp_event_base_t event_base, int32_t event_id, void *event_data);
 | 
					  static void ip_event_handler(void *arg, esp_event_base_t event_base, int32_t event_id, void *event_data);
 | 
				
			||||||
  void dump_connect_params_();
 | 
					  void dump_connect_params_();
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  // Attributes from yaml config
 | 
					  // Attributes from yaml config
 | 
				
			||||||
 | 
					  uint16_t timeout_;
 | 
				
			||||||
  InternalGPIOPin *tx_pin_;
 | 
					  InternalGPIOPin *tx_pin_;
 | 
				
			||||||
  InternalGPIOPin *rx_pin_;
 | 
					  InternalGPIOPin *rx_pin_;
 | 
				
			||||||
  std::string model_;
 | 
					  std::string model_;
 | 
				
			||||||
@@ -142,7 +143,7 @@ class ModemComponent : public Component {
 | 
				
			|||||||
  size_t uart_event_task_stack_size_ = 4096;  // 2000-6000
 | 
					  size_t uart_event_task_stack_size_ = 4096;  // 2000-6000
 | 
				
			||||||
  uint8_t uart_event_task_priority_ = 5;      // 3-22
 | 
					  uint8_t uart_event_task_priority_ = 5;      // 3-22
 | 
				
			||||||
  uint32_t command_delay_ = 1000;             // timeout for AT commands
 | 
					  uint32_t command_delay_ = 1000;             // timeout for AT commands
 | 
				
			||||||
  uint32_t update_interval_ = 60 * 1000;
 | 
					  uint32_t reconnect_grace_period_ = 30000;   // let some time to mqtt or api to reconnect before retry
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  // Changes will trigger user callback
 | 
					  // Changes will trigger user callback
 | 
				
			||||||
  ModemComponentState component_state_{ModemComponentState::DISABLED};
 | 
					  ModemComponentState component_state_{ModemComponentState::DISABLED};
 | 
				
			||||||
@@ -153,7 +154,9 @@ class ModemComponent : public Component {
 | 
				
			|||||||
  esp_netif_t *ppp_netif_{nullptr};
 | 
					  esp_netif_t *ppp_netif_{nullptr};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  struct InternalState {
 | 
					  struct InternalState {
 | 
				
			||||||
    bool start{false};
 | 
					    bool starting{false};
 | 
				
			||||||
 | 
					    // trying to connect timestamp (for timeout)
 | 
				
			||||||
 | 
					    uint32_t startms;
 | 
				
			||||||
    bool enabled{false};
 | 
					    bool enabled{false};
 | 
				
			||||||
    bool connected{false};
 | 
					    bool connected{false};
 | 
				
			||||||
    bool got_ipv4_address{false};
 | 
					    bool got_ipv4_address{false};
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -47,23 +47,14 @@ void ModemSensor::update() {
 | 
				
			|||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
void ModemSensor::update_signal_sensors_() {
 | 
					void ModemSensor::update_signal_sensors_() {
 | 
				
			||||||
  float rssi = NAN;
 | 
					 | 
				
			||||||
  float ber = NAN;
 | 
					 | 
				
			||||||
  if (this->rssi_sensor_ || this->ber_sensor_) {
 | 
					  if (this->rssi_sensor_ || this->ber_sensor_) {
 | 
				
			||||||
    int modem_rssi = 99;
 | 
					    float rssi;
 | 
				
			||||||
    int modem_ber = 99;
 | 
					    float ber;
 | 
				
			||||||
    if (global_modem_component->modem_ready() &&
 | 
					    global_modem_component->get_signal_quality(rssi, ber);
 | 
				
			||||||
        (global_modem_component->dce->get_signal_quality(modem_rssi, modem_ber) == command_result::OK)) {
 | 
					    if (this->rssi_sensor_)
 | 
				
			||||||
      if (modem_rssi != 99)
 | 
					      this->rssi_sensor_->publish_state(rssi);
 | 
				
			||||||
        rssi = -113 + (modem_rssi * 2);
 | 
					    if (this->ber_sensor_)
 | 
				
			||||||
      if (modem_ber != 99)
 | 
					      this->ber_sensor_->publish_state(ber);
 | 
				
			||||||
        ber = 0.1f * (modem_ber * modem_ber);
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
      if (this->rssi_sensor_)
 | 
					 | 
				
			||||||
        this->rssi_sensor_->publish_state(rssi);
 | 
					 | 
				
			||||||
      if (this->ber_sensor_)
 | 
					 | 
				
			||||||
        this->ber_sensor_->publish_state(ber);
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 
 | 
				
			|||||||
		Reference in New Issue
	
	Block a user