From ae6c5197e7a3ba9dcaaf60a479f6a2dbfe99c498 Mon Sep 17 00:00:00 2001 From: Serhii Salamakha Date: Wed, 22 Jan 2025 18:51:09 +0200 Subject: [PATCH] [Telink] adopt WiFi driver --- .../wifi/ConnectivityManagerImplWiFi.cpp | 16 +- src/platform/telink/wifi/TelinkWiFiDriver.cpp | 25 ++- src/platform/telink/wifi/TelinkWiFiDriver.h | 2 +- src/platform/telink/wifi/WiFiManager.cpp | 166 +++++++++++++++--- src/platform/telink/wifi/WiFiManager.h | 33 +++- 5 files changed, 193 insertions(+), 49 deletions(-) diff --git a/src/platform/telink/wifi/ConnectivityManagerImplWiFi.cpp b/src/platform/telink/wifi/ConnectivityManagerImplWiFi.cpp index 5bef79bb22fdc5..9b605c31560142 100644 --- a/src/platform/telink/wifi/ConnectivityManagerImplWiFi.cpp +++ b/src/platform/telink/wifi/ConnectivityManagerImplWiFi.cpp @@ -42,7 +42,7 @@ ConnectivityManager::WiFiStationMode ConnectivityManagerImplWiFi::_GetWiFiStatio { if (mStationMode != ConnectivityManager::WiFiStationMode::kWiFiStationMode_ApplicationControlled) { - mStationMode = (WiFiManager::StationStatus::DISABLED == WiFiManager().Instance().GetStationStatus()) + mStationMode = (WiFiManager::StationStatus::DISABLED == WiFiManager::Instance().GetStationStatus()) ? ConnectivityManager::WiFiStationMode::kWiFiStationMode_Disabled : ConnectivityManager::WiFiStationMode::kWiFiStationMode_Enabled; } @@ -60,7 +60,7 @@ CHIP_ERROR ConnectivityManagerImplWiFi::_SetWiFiStationMode(ConnectivityManager: bool ConnectivityManagerImplWiFi::_IsWiFiStationEnabled(void) { - return (WiFiManager::StationStatus::DISABLED <= WiFiManager().Instance().GetStationStatus()); + return (WiFiManager::StationStatus::DISABLED <= WiFiManager::Instance().GetStationStatus()); } bool ConnectivityManagerImplWiFi::_IsWiFiStationApplicationControlled(void) @@ -70,7 +70,7 @@ bool ConnectivityManagerImplWiFi::_IsWiFiStationApplicationControlled(void) bool ConnectivityManagerImplWiFi::_IsWiFiStationConnected(void) { - return (WiFiManager::StationStatus::CONNECTED == WiFiManager().Instance().GetStationStatus()); + return (WiFiManager::StationStatus::CONNECTED == WiFiManager::Instance().GetStationStatus()); } System::Clock::Timeout ConnectivityManagerImplWiFi::_GetWiFiStationReconnectInterval(void) @@ -88,14 +88,14 @@ bool ConnectivityManagerImplWiFi::_IsWiFiStationProvisioned(void) { // from Matter perspective `provisioned` means that the supplicant has been provided // with SSID and password (doesn't matter if valid or not) - return (WiFiManager::StationStatus::CONNECTING <= WiFiManager().Instance().GetStationStatus()); + return (WiFiManager::StationStatus::CONNECTING <= WiFiManager::Instance().GetStationStatus()); } void ConnectivityManagerImplWiFi::_ClearWiFiStationProvision(void) { if (_IsWiFiStationProvisioned()) { - if (CHIP_NO_ERROR != WiFiManager().Instance().ClearStationProvisioningData()) + if (CHIP_NO_ERROR != WiFiManager::Instance().ClearStationProvisioningData()) { ChipLogError(DeviceLayer, "Cannot clear WiFi station provisioning data"); } @@ -104,9 +104,9 @@ void ConnectivityManagerImplWiFi::_ClearWiFiStationProvision(void) bool ConnectivityManagerImplWiFi::_CanStartWiFiScan() { - return (WiFiManager::StationStatus::DISABLED != WiFiManager().Instance().GetStationStatus() && - WiFiManager::StationStatus::SCANNING != WiFiManager().Instance().GetStationStatus() && - WiFiManager::StationStatus::CONNECTING != WiFiManager().Instance().GetStationStatus()); + return (WiFiManager::StationStatus::DISABLED != WiFiManager::Instance().GetStationStatus() && + WiFiManager::StationStatus::SCANNING != WiFiManager::Instance().GetStationStatus() && + WiFiManager::StationStatus::CONNECTING != WiFiManager::Instance().GetStationStatus()); } void ConnectivityManagerImplWiFi::_OnWiFiStationProvisionChange() diff --git a/src/platform/telink/wifi/TelinkWiFiDriver.cpp b/src/platform/telink/wifi/TelinkWiFiDriver.cpp index f6c19a2c1f3030..e42344c5f5a909 100644 --- a/src/platform/telink/wifi/TelinkWiFiDriver.cpp +++ b/src/platform/telink/wifi/TelinkWiFiDriver.cpp @@ -17,10 +17,13 @@ #include "TelinkWiFiDriver.h" +#include + #include #include #include +#include #include using namespace ::chip; @@ -103,8 +106,8 @@ CHIP_ERROR TelinkWiFiDriver::Init(NetworkStatusChangeCallback * networkStatusCha if (mStagingNetwork.IsConfigured()) { - WiFiManager::ConnectionHandling handling{ [] { Instance().OnNetworkStatusChanged(Status::kSuccess); }, - [] { Instance().OnNetworkStatusChanged(Status::kUnknownError); }, + WiFiManager::ConnectionHandling handling{ [](const wifi_conn_status & connStatus) { + Instance().OnNetworkConnStatusChanged(connStatus); }, System::Clock::Seconds32{ kWiFiConnectNetworkTimeoutSeconds } }; ReturnErrorOnFailure( WiFiManager::Instance().Connect(mStagingNetwork.GetSsidSpan(), mStagingNetwork.GetPassSpan(), handling)); @@ -113,8 +116,11 @@ CHIP_ERROR TelinkWiFiDriver::Init(NetworkStatusChangeCallback * networkStatusCha return CHIP_NO_ERROR; } -void TelinkWiFiDriver::OnNetworkStatusChanged(Status status) +void TelinkWiFiDriver::OnNetworkConnStatusChanged(const wifi_conn_status & connStatus) { + // TODO: check if we can report more accurate errors + Status status = connStatus ? Status::kUnknownError : Status::kSuccess; + if (status == Status::kSuccess) { ConnectivityMgr().SetWiFiStationMode(ConnectivityManager::kWiFiStationMode_Enabled); @@ -136,8 +142,9 @@ void TelinkWiFiDriver::OnNetworkStatusChanged(Status status) ssid = WiFiManager::Instance().GetWantedNetwork().ssid; ssidLen = WiFiManager::Instance().GetWantedNetwork().ssidLen; } - mpNetworkStatusChangeCallback->OnNetworkingStatusChange(status, MakeOptional(ByteSpan(wifiInfo.mSsid, wifiInfo.mSsidLen)), - NullOptional); + mpNetworkStatusChangeCallback->OnNetworkingStatusChange(status, MakeOptional(ByteSpan(ssid, ssidLen)), + connStatus ? MakeOptional(static_cast(connStatus)) + : NullOptional); } if (mpConnectCallback) @@ -179,8 +186,8 @@ CHIP_ERROR TelinkWiFiDriver::RevertConfiguration() if (mStagingNetwork.IsConfigured()) { - WiFiManager::ConnectionHandling handling{ [] { Instance().OnNetworkStatusChanged(Status::kSuccess); }, - [] { Instance().OnNetworkStatusChanged(Status::kUnknownError); }, + WiFiManager::ConnectionHandling handling{ [](const wifi_conn_status & connStatus) { + Instance().OnNetworkConnStatusChanged(connStatus); }, System::Clock::Seconds32{ kWiFiConnectNetworkTimeoutSeconds } }; ReturnErrorOnFailure( WiFiManager::Instance().Connect(mStagingNetwork.GetSsidSpan(), mStagingNetwork.GetPassSpan(), handling)); @@ -233,8 +240,8 @@ Status TelinkWiFiDriver::ReorderNetwork(ByteSpan networkId, uint8_t index, Mutab void TelinkWiFiDriver::ConnectNetwork(ByteSpan networkId, ConnectCallback * callback) { Status status = Status::kSuccess; - WiFiManager::ConnectionHandling handling{ [] { Instance().OnNetworkStatusChanged(Status::kSuccess); }, - [] { Instance().OnNetworkStatusChanged(Status::kUnknownError); }, + WiFiManager::ConnectionHandling handling{ [](const wifi_conn_status & connStatus) { + Instance().OnNetworkConnStatusChanged(connStatus); }, System::Clock::Seconds32{ kWiFiConnectNetworkTimeoutSeconds } }; VerifyOrExit(mpConnectCallback == nullptr, status = Status::kUnknownError); diff --git a/src/platform/telink/wifi/TelinkWiFiDriver.h b/src/platform/telink/wifi/TelinkWiFiDriver.h index 9c5b1e61d1f0e1..e3a66e3a279d07 100644 --- a/src/platform/telink/wifi/TelinkWiFiDriver.h +++ b/src/platform/telink/wifi/TelinkWiFiDriver.h @@ -94,7 +94,7 @@ class TelinkWiFiDriver final : public WiFiDriver return sInstance; } - void OnNetworkStatusChanged(Status status); + void OnNetworkConnStatusChanged(const wifi_conn_status & connStatus); void OnScanWiFiNetworkResult(const WiFiScanResponse & result); void OnScanWiFiNetworkDone(const WiFiManager::ScanDoneStatus & status); diff --git a/src/platform/telink/wifi/WiFiManager.cpp b/src/platform/telink/wifi/WiFiManager.cpp index dfbfcfec354227..d149ef11bd466d 100644 --- a/src/platform/telink/wifi/WiFiManager.cpp +++ b/src/platform/telink/wifi/WiFiManager.cpp @@ -25,19 +25,30 @@ #include #include #include +#include #include #include #include #include #include -#include namespace chip { namespace DeviceLayer { namespace { +app::Clusters::NetworkCommissioning::WiFiBandEnum ConvertBandEnum(uint8_t band) +{ + switch (band) + { + case WIFI_FREQ_BAND_2_4_GHZ: + return app::Clusters::NetworkCommissioning::WiFiBandEnum::k2g4; + default: + return app::Clusters::NetworkCommissioning::WiFiBandEnum::kUnknownEnumValue; + } +} + NetworkCommissioning::WiFiScanResponse ToScanResponse(const wifi_scan_result * result) { NetworkCommissioning::WiFiScanResponse response = {}; @@ -53,6 +64,7 @@ NetworkCommissioning::WiFiScanResponse ToScanResponse(const wifi_scan_result * r response.channel = result->channel; response.rssi = result->rssi; response.ssidLen = result->ssid_length; + response.wiFiBand = ConvertBandEnum(result->band); memcpy(response.ssid, result->ssid, result->ssid_length); // TODO: MAC/BSSID is not filled by the Wi-Fi driver memcpy(response.bssid, result->mac, result->mac_length); @@ -131,6 +143,7 @@ const Map WiFiManager::sEventHandlerM { NET_EVENT_WIFI_SCAN_DONE, WiFiManager::ScanDoneHandler }, { NET_EVENT_WIFI_CONNECT_RESULT, WiFiManager::ConnectHandler }, { NET_EVENT_WIFI_DISCONNECT_RESULT, WiFiManager::DisconnectHandler }, + { NET_EVENT_WIFI_DISCONNECT_COMPLETE, WiFiManager::DisconnectHandler }, }); void WiFiManager::WifiMgmtEventHandler(net_mgmt_event_callback * cb, uint32_t mgmtEvent, net_if * iface) @@ -157,8 +170,6 @@ CHIP_ERROR WiFiManager::Init() mNetIf = InetUtils::GetWiFiInterface(); VerifyOrReturnError(mNetIf != nullptr, INET_ERROR_UNKNOWN_INTERFACE); - net_if_down(mNetIf); // block netif auto start - net_mgmt_init_event_callback(&mWiFiMgmtClbk, WifiMgmtEventHandler, kWifiManagementEvents); net_mgmt_init_event_callback(&mIPv6MgmtClbk, IPv6MgmtEventHandler, kIPv6ManagementEvents); @@ -179,7 +190,24 @@ CHIP_ERROR WiFiManager::Scan(const ByteSpan & ssid, ScanResultCallback resultCal mWiFiState = WIFI_STATE_SCANNING; mSsidFound = false; - if (0 != net_mgmt(NET_REQUEST_WIFI_SCAN, mNetIf, NULL, 0)) + wifi_scan_params * scanParams{ nullptr }; + size_t scanParamsSize{ 0 }; + + if (!ssid.empty()) + { + /* We must assume that the ssid is handled as a NULL-terminated string. + Note that the mScanSsidBuffer is initialized with zeros. */ + VerifyOrReturnError(ssid.size() < sizeof(mScanSsidBuffer), CHIP_ERROR_INVALID_ARGUMENT); + memcpy(mScanSsidBuffer, ssid.data(), ssid.size()); + mScanSsidBuffer[ssid.size()] = 0; // indicate the end of ssid string + mScanParams.ssids[0] = mScanSsidBuffer; +#if (CONFIG_WIFI_MGMT_SCAN_SSID_FILT_MAX > 1) + mScanParams.ssids[1] = nullptr; // indicate the end of ssids list +#endif + scanParams = &mScanParams; + scanParamsSize = sizeof(*scanParams); + } + if (0 != net_mgmt(NET_REQUEST_WIFI_SCAN, mNetIf, scanParams, scanParamsSize)) { ChipLogError(DeviceLayer, "Scan request failed"); return CHIP_ERROR_INTERNAL; @@ -201,9 +229,7 @@ CHIP_ERROR WiFiManager::Connect(const ByteSpan & ssid, const ByteSpan & credenti { ChipLogDetail(DeviceLayer, "Connecting to WiFi network: %*s", ssid.size(), ssid.data()); - mHandling.mOnConnectionSuccess = handling.mOnConnectionSuccess; - mHandling.mOnConnectionFailed = handling.mOnConnectionFailed; - mHandling.mConnectionTimeout = handling.mConnectionTimeout; + mHandling = handling; mWiFiState = WIFI_STATE_ASSOCIATING; @@ -277,8 +303,8 @@ CHIP_ERROR WiFiManager::GetNetworkStatistics(NetworkStatistics & stats) const stats.mPacketMulticastRxCount = data.multicast.rx; stats.mPacketMulticastTxCount = data.multicast.tx; - stats.mPacketUnicastRxCount = data.pkts.rx - data.multicast.rx - data.broadcast.rx; - stats.mPacketUnicastTxCount = data.pkts.tx - data.multicast.tx - data.broadcast.tx; + stats.mPacketUnicastRxCount = data.unicast.rx; + stats.mPacketUnicastTxCount = data.unicast.tx; stats.mBeaconsSuccessCount = data.sta_mgmt.beacons_rx; stats.mBeaconsLostCount = data.sta_mgmt.beacons_miss; @@ -380,9 +406,9 @@ void WiFiManager::ScanDoneHandler(Platform::UniquePtr data, size_t leng sizeof(wifi_connect_req_params))) { ChipLogError(DeviceLayer, "Connection request failed"); - if (Instance().mHandling.mOnConnectionFailed) + if (Instance().mHandling.mOnConnectionDone) { - Instance().mHandling.mOnConnectionFailed(); + Instance().mHandling.mOnConnectionDone(WIFI_STATUS_CONN_FAIL); } Instance().mWiFiState = WIFI_STATE_DISCONNECTED; return; @@ -400,36 +426,81 @@ void WiFiManager::ScanDoneHandler(Platform::UniquePtr data, size_t leng } } +void WiFiManager::SendRouterSolicitation(System::Layer * layer, void * param) +{ + net_if_start_rs(Instance().mNetIf); + Instance().mRouterSolicitationCounter++; + if (Instance().mRouterSolicitationCounter < kRouterSolicitationMaxCount) + { + DeviceLayer::SystemLayer().StartTimer(System::Clock::Milliseconds32(kRouterSolicitationIntervalMs), SendRouterSolicitation, + nullptr); + } + else + { + Instance().mRouterSolicitationCounter = 0; + } +} + void WiFiManager::ConnectHandler(Platform::UniquePtr data, size_t length) { + using app::Clusters::WiFiNetworkDiagnostics::AssociationFailureCauseEnum; + // Validate that input data size matches the expected one. VerifyOrReturn(length == sizeof(wifi_status)); CHIP_ERROR err = SystemLayer().ScheduleLambda([capturedData = data.get()] { Platform::UniquePtr safePtr(capturedData); - uint8_t * rawData = safePtr.get(); - const wifi_status * status = reinterpret_cast(rawData); - WiFiRequestStatus requestStatus = static_cast(status->status); + uint8_t * rawData = safePtr.get(); + const wifi_status * status = reinterpret_cast(rawData); + wifi_conn_status connStatus = status->conn_status; - if (requestStatus == WiFiRequestStatus::FAILURE || requestStatus == WiFiRequestStatus::TERMINATED) + if (connStatus) { ChipLogProgress(DeviceLayer, "Connection to WiFi network failed or was terminated by another request"); Instance().mWiFiState = WIFI_STATE_DISCONNECTED; - if (Instance().mHandling.mOnConnectionFailed) + if (Instance().mHandling.mOnConnectionDone) { - Instance().mHandling.mOnConnectionFailed(); + Instance().mHandling.mOnConnectionDone(connStatus); + } + + WiFiDiagnosticsDelegate * delegate = GetDiagnosticDataProvider().GetWiFiDiagnosticsDelegate(); + if (delegate) + { + uint16_t reason = Instance().GetLastDisconnectReason(); + uint8_t associationFailureCause; + + switch (connStatus) + { + case WIFI_STATUS_CONN_WRONG_PASSWORD: + associationFailureCause = to_underlying(AssociationFailureCauseEnum::kAuthenticationFailed); + break; + case WIFI_STATUS_CONN_FAIL: + case WIFI_STATUS_CONN_TIMEOUT: + associationFailureCause = to_underlying(AssociationFailureCauseEnum::kAssociationFailed); + break; + case WIFI_STATUS_CONN_AP_NOT_FOUND: + associationFailureCause = to_underlying(AssociationFailureCauseEnum::kSsidNotFound); + break; + default: + associationFailureCause = to_underlying(AssociationFailureCauseEnum::kUnknown); + break; + } + + delegate->OnAssociationFailureDetected(associationFailureCause, reason); } } else // The connection has been established successfully. { - // Now we can send/receive data via WiFi - net_if_up(InetUtils::GetWiFiInterface()); + // Workaround needed until sending Router Solicitation after connect will be done by the driver. + DeviceLayer::SystemLayer().StartTimer( + System::Clock::Milliseconds32(chip::Crypto::GetRandU16() % kMaxInitialRouterSolicitationDelayMs), + SendRouterSolicitation, nullptr); ChipLogProgress(DeviceLayer, "Connected to WiFi network"); Instance().mWiFiState = WIFI_STATE_COMPLETED; - if (Instance().mHandling.mOnConnectionSuccess) + if (Instance().mHandling.mOnConnectionDone) { - Instance().mHandling.mOnConnectionSuccess(); + Instance().mHandling.mOnConnectionDone(connStatus); } Instance().PostConnectivityStatusChange(kConnectivity_Established); @@ -442,6 +513,13 @@ void WiFiManager::ConnectHandler(Platform::UniquePtr data, size_t lengt { ChipLogError(DeviceLayer, "Cannot post event [error: %s]", ErrorStr(error)); } + + WiFiDiagnosticsDelegate * delegate = GetDiagnosticDataProvider().GetWiFiDiagnosticsDelegate(); + if (delegate) + { + delegate->OnConnectionStatusChanged( + to_underlying(app::Clusters::WiFiNetworkDiagnostics::ConnectionStatusEnum::kConnected)); + } } // cleanup the provisioning data as it is configured per each connect request Instance().ClearStationProvisioningData(); @@ -459,10 +537,44 @@ void WiFiManager::DisconnectHandler(Platform::UniquePtr data, size_t le // Validate that input data size matches the expected one. VerifyOrReturn(length == sizeof(wifi_status)); - CHIP_ERROR err = SystemLayer().ScheduleLambda([] { + CHIP_ERROR err = SystemLayer().ScheduleLambda([capturedData = data.get()] { + Platform::UniquePtr safePtr(capturedData); + uint8_t * rawData = safePtr.get(); + const wifi_status * status = reinterpret_cast(rawData); + uint16_t reason; + + switch (status->disconn_reason) + { + case WIFI_REASON_DISCONN_UNSPECIFIED: + reason = static_cast(WlanReason::UNSPECIFIED); + break; + case WIFI_REASON_DISCONN_USER_REQUEST: + reason = static_cast(WlanReason::DEAUTH_LEAVING); + break; + case WIFI_REASON_DISCONN_AP_LEAVING: + reason = static_cast(WlanReason::DEAUTH_LEAVING); + break; + case WIFI_REASON_DISCONN_INACTIVITY: + reason = static_cast(WlanReason::DISASSOC_DUE_TO_INACTIVITY); + break; + default: + reason = static_cast(WlanReason::UNSPECIFIED); + break; + } + + Instance().SetLastDisconnectReason(reason); + ChipLogProgress(DeviceLayer, "WiFi station disconnected"); Instance().mWiFiState = WIFI_STATE_DISCONNECTED; Instance().PostConnectivityStatusChange(kConnectivity_Lost); + + WiFiDiagnosticsDelegate * delegate = GetDiagnosticDataProvider().GetWiFiDiagnosticsDelegate(); + if (delegate) + { + delegate->OnConnectionStatusChanged( + to_underlying(app::Clusters::WiFiNetworkDiagnostics::ConnectionStatusEnum::kNotConnected)); + delegate->OnDisconnectionDetected(reason); + } }); if (CHIP_NO_ERROR == err) @@ -587,5 +699,15 @@ CHIP_ERROR WiFiManager::SetLowPowerMode(bool onoff) return CHIP_NO_ERROR; } +void WiFiManager::SetLastDisconnectReason(uint16_t reason) +{ + mLastDisconnectedReason = reason; +} + +uint16_t WiFiManager::GetLastDisconnectReason() +{ + return mLastDisconnectedReason; +} + } // namespace DeviceLayer } // namespace chip diff --git a/src/platform/telink/wifi/WiFiManager.h b/src/platform/telink/wifi/WiFiManager.h index 49c9496f5d13be..6674b5c6165f9f 100644 --- a/src/platform/telink/wifi/WiFiManager.h +++ b/src/platform/telink/wifi/WiFiManager.h @@ -83,17 +83,16 @@ class Map class WiFiManager { public: - enum WiFiRequestStatus : int - { - SUCCESS = 0, - FAILURE = 1, - TERMINATED = 2 - }; + /* No copy, nor move. */ + WiFiManager(const WiFiManager &) = delete; + WiFiManager & operator=(const WiFiManager &) = delete; + WiFiManager(WiFiManager &&) = delete; + WiFiManager & operator=(WiFiManager &&) = delete; using ScanDoneStatus = decltype(wifi_status::status); using ScanResultCallback = void (*)(const NetworkCommissioning::WiFiScanResponse &); using ScanDoneCallback = void (*)(const ScanDoneStatus &); - using ConnectionCallback = void (*)(); + using ConnectionCallback = void (*)(const wifi_conn_status &); enum class StationStatus : uint8_t { @@ -108,6 +107,15 @@ class WiFiManager UNKNOWN }; + enum class WlanReason : uint8_t + { + UNSPECIFIED = 1, + PREV_AUTH_NOT_VALID, + DEAUTH_LEAVING, + DISASSOC_DUE_TO_INACTIVITY, + DISASSOC_AP_BUSY + }; + static WiFiManager & Instance() { static WiFiManager sInstance; @@ -116,8 +124,7 @@ class WiFiManager struct ConnectionHandling { - ConnectionCallback mOnConnectionSuccess{}; - ConnectionCallback mOnConnectionFailed{}; + ConnectionCallback mOnConnectionDone{}; System::Clock::Seconds32 mConnectionTimeout{}; }; @@ -182,10 +189,15 @@ class WiFiManager CHIP_ERROR GetNetworkStatistics(NetworkStatistics & stats) const; void AbortConnectionRecovery(); CHIP_ERROR SetLowPowerMode(bool onoff); + void SetLastDisconnectReason(uint16_t reason); + uint16_t GetLastDisconnectReason(); private: using NetEventHandler = void (*)(Platform::UniquePtr, size_t); + WiFiManager() = default; + ~WiFiManager() = default; + struct ConnectionParams { wifi_connect_req_params mParams; @@ -224,6 +236,8 @@ class WiFiManager net_if * mNetIf{ nullptr }; ConnectionParams mWiFiParams{}; ConnectionHandling mHandling{}; + wifi_scan_params mScanParams{}; + char mScanSsidBuffer[DeviceLayer::Internal::kMaxWiFiSSIDLength + 1] = { 0 }; wifi_iface_state mWiFiState; wifi_iface_state mCachedWiFiState; net_mgmt_event_callback mWiFiMgmtClbk{}; @@ -237,6 +251,7 @@ class WiFiManager uint32_t mConnectionRecoveryCounter{ 0 }; uint32_t mConnectionRecoveryTimeMs{ kConnectionRecoveryMinIntervalMs }; bool mApplicationDisconnectRequested{ false }; + uint16_t mLastDisconnectedReason = static_cast(WlanReason::UNSPECIFIED); static const Map sStatusMap; static const Map sEventHandlerMap;