From 219f9b75e151aef37359d9145a23021b56c41dca Mon Sep 17 00:00:00 2001 From: hai007 Date: Mon, 7 Nov 2022 17:42:08 -0800 Subject: [PATCH] Restore the WIFI connection when connecting to Hotspot fails. PiperOrigin-RevId: 486809154 --- .../implementation/windows/wifi_hotspot.h | 3 +- .../windows/wifi_hotspot_medium.cc | 82 ++++++++++++------- 2 files changed, 55 insertions(+), 30 deletions(-) diff --git a/internal/platform/implementation/windows/wifi_hotspot.h b/internal/platform/implementation/windows/wifi_hotspot.h index b2c75ea2..c7a6f054 100644 --- a/internal/platform/implementation/windows/wifi_hotspot.h +++ b/internal/platform/implementation/windows/wifi_hotspot.h @@ -57,8 +57,8 @@ using ::winrt::Windows::Devices::WiFiDirect::WiFiDirectConnectionListener; using ::winrt::Windows::Devices::WiFiDirect::WiFiDirectConnectionRequest; using ::winrt::Windows::Devices::WiFiDirect:: WiFiDirectConnectionRequestedEventArgs; -using ::winrt::Windows::Devices::WiFiDirect::WiFiDirectDevice; using ::winrt::Windows::Devices::WiFiDirect::WiFiDirectConnectionStatus; +using ::winrt::Windows::Devices::WiFiDirect::WiFiDirectDevice; using ::winrt::Windows::Devices::WiFi::WiFiAccessStatus; using ::winrt::Windows::Devices::WiFi::WiFiAdapter; @@ -274,6 +274,7 @@ class WifiHotspotMedium : public api::WifiHotspotMedium { bool IsBeaconing() { return (medium_status_ & kMediumStatusBeaconing) != 0; } // Discoverer is connected with the Hotspot bool IsConnected() { return (medium_status_ & kMediumStatusConnected) != 0; } + void RestoreWifiConnection(); WiFiDirectAdvertisementPublisher publisher_{nullptr}; WiFiDirectConnectionListener listener_{nullptr}; diff --git a/internal/platform/implementation/windows/wifi_hotspot_medium.cc b/internal/platform/implementation/windows/wifi_hotspot_medium.cc index d3fbb302..905d2f1a 100644 --- a/internal/platform/implementation/windows/wifi_hotspot_medium.cc +++ b/internal/platform/implementation/windows/wifi_hotspot_medium.cc @@ -205,7 +205,7 @@ bool WifiHotspotMedium::StopWifiHotspot() { publisher_.Stop(); listener_.ConnectionRequested(connection_requested_token_); publisher_.StatusChanged(publisher_status_changed_token_); - wifi_direct_device_ = nullptr; + wifi_direct_device_ = nullptr; listener_ = nullptr; publisher_ = nullptr; NEARBY_LOGS(INFO) << "succeeded to stop WiFi Hotspot"; @@ -250,7 +250,7 @@ fire_and_forget WifiHotspotMedium::OnStatusChanged( NEARBY_LOGS(ERROR) << "Windows WiFi Hotspot cleanup."; listener_.ConnectionRequested(connection_requested_token_); publisher_.StatusChanged(publisher_status_changed_token_); - wifi_direct_device_ = nullptr; + wifi_direct_device_ = nullptr; listener_ = nullptr; publisher_ = nullptr; } @@ -275,12 +275,13 @@ fire_and_forget WifiHotspotMedium::OnConnectionRequested( // solve the problem. Guess when this object is created, // [Microsoft-Windows-WLAN-AutoConfig] will recognise it as a valid device // and won't kick it away. - wifi_direct_device_ = WiFiDirectDevice::FromIdAsync( - connection_request.DeviceInformation().Id()).get(); + wifi_direct_device_ = WiFiDirectDevice::FromIdAsync( + connection_request.DeviceInformation().Id()) + .get(); NEARBY_LOGS(INFO) << "Registered the device in WLAN-AutoConfig"; } catch (...) { NEARBY_LOGS(ERROR) << "Failed to registered the device in WLAN-AutoConfig"; - wifi_direct_device_ = nullptr; + wifi_direct_device_ = nullptr; connection_request.Close(); } return winrt::fire_and_forget(); @@ -328,8 +329,8 @@ bool WifiHotspotMedium::ConnectWifiHotspot( // almost guarantee to find the Hotspot wifi_adapter_.ScanAsync().get(); - wifi_connected_network_ = nullptr; - for (int i = 0; i < kMaxScans; i++) { + wifi_connected_network_ = nullptr; + for (int i = 0; i < kMaxScans; i++) { for (const auto& network : wifi_adapter_.NetworkReport().AvailableNetworks()) { if (!wifi_connected_network_ && !ssid.empty() && @@ -337,12 +338,12 @@ bool WifiHotspotMedium::ConnectWifiHotspot( wifi_connected_network_ = network; NEARBY_LOGS(INFO) << "Save the current connected network: " << ssid; } else if (!nearby_softap && winrt::to_string(network.Ssid()) == - hotspot_credentials_->GetSSID()) { + hotspot_credentials_->GetSSID()) { NEARBY_LOGS(INFO) << "Found Nearby SSID: " << winrt::to_string(network.Ssid()); nearby_softap = network; } - if (nearby_softap && wifi_connected_network_) break; + if (nearby_softap && (ssid.empty() || wifi_connected_network_)) break; } if (nearby_softap) break; NEARBY_LOGS(INFO) << "Scan ... "; @@ -366,6 +367,7 @@ bool WifiHotspotMedium::ConnectWifiHotspot( connect_result.ConnectionStatus() != WiFiConnectionStatus::Success) { NEARBY_LOGS(INFO) << "Connecting failed with reason: " << static_cast(connect_result.ConnectionStatus()); + RestoreWifiConnection(); return false; } @@ -376,6 +378,47 @@ bool WifiHotspotMedium::ConnectWifiHotspot( return true; } +void WifiHotspotMedium::RestoreWifiConnection() { + if (wifi_adapter_) { + ConnectionProfile profile = + wifi_adapter_.NetworkAdapter().GetConnectedProfileAsync().get(); + std::string ssid; + + if (profile != nullptr && profile.IsWlanConnectionProfile()) { + ssid = winrt::to_string( + profile.WlanConnectionProfileDetails().GetConnectedSsid()); + if (!ssid.empty() && + (winrt::to_string(wifi_connected_network_.Ssid()) == ssid)) { + NEARBY_LOGS(INFO) << "Already conneted to the previous WIFI network " + << ssid << "! Skip restoration."; + return; + } + } + + // Disconnect to the WiFi connection through the WiFi adapter. + wifi_adapter_.Disconnect(); + NEARBY_LOGS(INFO) << "Disconnected to current network."; + + if (wifi_connected_network_) { + auto connect_result = wifi_adapter_ + .ConnectAsync(wifi_connected_network_, + WiFiReconnectionKind::Automatic) + .get(); + + if (connect_result == nullptr || + connect_result.ConnectionStatus() != WiFiConnectionStatus::Success) { + NEARBY_LOGS(INFO) + << "Connecting to previous network failed with reason: " + << static_cast(connect_result.ConnectionStatus()); + } else { + NEARBY_LOGS(INFO) << "Restored the previous WIFI connection: " + << winrt::to_string(wifi_connected_network_.Ssid()); + } + wifi_connected_network_ = nullptr; + } + } +} + bool WifiHotspotMedium::DisconnectWifiHotspot() { absl::MutexLock lock(&mutex_); return InternalDisconnectWifiHotspot(); @@ -394,26 +437,7 @@ bool WifiHotspotMedium::InternalDisconnectWifiHotspot() { wifi_adapter_.NetworkAdapter().GetConnectedProfileAsync().get(); // Disconnect to the WiFi connection through the WiFi adapter. - wifi_adapter_.Disconnect(); - NEARBY_LOGS(INFO) << "Disconnected to SoftAP."; - - if (wifi_connected_network_) { - auto connect_result = wifi_adapter_ - .ConnectAsync(wifi_connected_network_, - WiFiReconnectionKind::Automatic) - .get(); - - if (connect_result == nullptr || - connect_result.ConnectionStatus() != WiFiConnectionStatus::Success) { - NEARBY_LOGS(INFO) - << "Connecting to previous network failed with reason: " - << static_cast(connect_result.ConnectionStatus()); - } else { - NEARBY_LOGS(INFO) << "Restored the previous WIFI connection: " - << winrt::to_string(wifi_connected_network_.Ssid()); - } - wifi_connected_network_ = nullptr; - } + RestoreWifiConnection(); wifi_adapter_ = nullptr; // Try to remove the WiFi profile