/* SPDX-License-Identifier: GPL-3.0-only */ /* Native ESP-IDF Wi-Fi lifecycle and connection policy manager. */ #pragma once #include #include #include "esp_err.h" #include "esp_wifi_types.h" #include "wifi_config.h" #ifdef __cplusplus extern "C" { #endif typedef enum { WIFI_MANAGER_STATE_STOPPED = 0, WIFI_MANAGER_STATE_STARTING, WIFI_MANAGER_STATE_CONNECTING, WIFI_MANAGER_STATE_WAITING_IP, WIFI_MANAGER_STATE_ONLINE, WIFI_MANAGER_STATE_BACKOFF, WIFI_MANAGER_STATE_AP_ONLY, WIFI_MANAGER_STATE_ERROR, } wifi_manager_state_t; typedef struct { uint64_t starts; uint64_t stops; uint64_t applies; uint64_t connect_attempts; uint64_t associations; uint64_t got_ip; uint64_t disconnects; uint64_t profile_cycles; uint64_t retries; uint64_t ap_starts; uint64_t ap_stops; uint64_t client_joins; uint64_t client_leaves; uint64_t queue_drops; } wifi_manager_counters_t; typedef struct { bool initialized; bool started; wifi_manager_state_t state; /* -1 means that no station profile is currently being attempted or used. */ int8_t active_profile; uint8_t sta_ssid_len; char sta_ssid[WIFI_CONFIG_SSID_MAX_LEN + 1U]; uint32_t ip; uint32_t netmask; uint32_t gateway; uint8_t sta_channel; int8_t sta_rssi; wifi_auth_mode_t sta_auth; wifi_config_ap_policy_t ap_policy; bool ap_running; uint8_t ap_ssid_len; char ap_ssid[WIFI_CONFIG_SSID_MAX_LEN + 1U]; uint8_t ap_client_count; uint8_t ap_channel; uint16_t last_disconnect_reason; esp_err_t last_error; uint32_t retry_seconds; uint32_t config_generation; wifi_manager_counters_t counters; } wifi_manager_snapshot_t; /* A stale expected working-config generation maps cleanly to HTTP 409. */ #define WIFI_MANAGER_ERR_CONFIG_CONFLICT ESP_ERR_INVALID_VERSION /* * Initializes ESP-NETIF, the default event loop, both default Wi-Fi netifs, * Wi-Fi itself, and the permanent policy task. The manager never aborts the * application on failure; callers may keep UART/USB services operational. */ esp_err_t wifi_manager_init(const wifi_app_config_t *config); /* * Returns a copy of the RAM working configuration, including credentials. * The caller owns the returned copy and must securely wipe it after use. */ esp_err_t wifi_manager_get_working_config(wifi_app_config_t *config); /* * Atomically copies the credential-bearing working configuration and the exact * nonzero generation that identified it. Both outputs are cleared on failure; * the caller must securely wipe config after every successful call. */ esp_err_t wifi_manager_get_working_config_versioned(wifi_app_config_t *config, uint32_t *generation); /* * Atomically replace the complete validated working configuration only when * expected_generation still identifies the current configuration. A stale * expectation returns WIFI_MANAGER_ERR_CONFIG_CONFLICT without queueing a * restart or changing state. resulting_generation is optional and is set to * zero on failure. Generation exhaustion returns ESP_ERR_INVALID_STATE. */ esp_err_t wifi_manager_compare_exchange_working_config( const wifi_app_config_t *config, uint32_t expected_generation, uint32_t *resulting_generation); /* * Persist exactly the working configuration identified by expected_generation. * All config writers are excluded through the NVS operation. A stale * expectation returns WIFI_MANAGER_ERR_CONFIG_CONFLICT. Generation exhaustion * returns ESP_ERR_INVALID_STATE. The saved generation is not incremented because * the RAM working configuration is unchanged. */ esp_err_t wifi_manager_save_working_config_if_generation( uint32_t expected_generation); /* Lifecycle requests are asynchronous and serialized by the manager task. */ esp_err_t wifi_manager_start(void); esp_err_t wifi_manager_stop(void); esp_err_t wifi_manager_reconnect(void); /* Advance to the next enabled station profile in priority order, wrapping safely. */ esp_err_t wifi_manager_next_profile(void); /* Reannounce the configured hostname when the manager currently has a STA IP. */ esp_err_t wifi_manager_mdns_reannounce(void); /* Snapshot data never contains station or AP passwords. */ esp_err_t wifi_manager_get_snapshot(wifi_manager_snapshot_t *snapshot); esp_err_t wifi_manager_clear_counters(void); const char *wifi_manager_state_to_string(wifi_manager_state_t state); #ifdef __cplusplus } #endif