Use DBUS to detect presence of Wi-Fi devices.

This commit is contained in:
Robin E. R. Davies
2024-11-20 14:50:05 -05:00
parent ca87658f90
commit 0dfe7b8080
8 changed files with 316 additions and 313 deletions
+55 -11
View File
@@ -60,6 +60,7 @@ namespace pipedal::impl
virtual bool CancelPost(PostHandle handle) override;
virtual void SetNetworkChangingListener(NetworkChangingListener &&listener) override;
virtual void SetHasWifiListener(HasWifiListener &&listener) override;
private:
enum class State
@@ -75,6 +76,11 @@ namespace pipedal::impl
void SetState(State state);
State state = State::Initial;
bool hasWifi = false;
HasWifiListener hasWifiListener;
void SetHasWifi(bool hasWifi);
virtual bool GetHasWifi() override ;
void onClose();
void onError(const std::string &message);
void onInitialize();
@@ -224,6 +230,7 @@ void HotspotManagerImpl::onInitialize()
}
void HotspotManagerImpl::onDisconnect()
{
SetHasWifi(false);
if (state != State::Initial && state != State::WaitingForNetworkManager)
{
WaitForNetworkManager();
@@ -242,6 +249,8 @@ void HotspotManagerImpl::UpdateNetworkManagerStatus()
auto ethernetDevice = GetDevice(NM_DEVICE_TYPE_ETHERNET);
auto wlanDevice = GetDevice(NM_DEVICE_TYPE_WIFI);
SetHasWifi(!!wlanDevice);
if (ethernetDevice && wlanDevice)
{
if (state == State::Initial || state == State::WaitingForNetworkManager)
@@ -291,6 +300,7 @@ void HotspotManagerImpl::ReleaseNetworkManager()
this->onDeviceRemovedHandle = INVALID_DBUS_EVENT_HANDLE;
this->onDeviceAddedHandle = INVALID_DBUS_EVENT_HANDLE;
SetHasWifi(false);
}
void HotspotManagerImpl::onDevicesChanged()
@@ -401,6 +411,8 @@ void HotspotManagerImpl::onStartMonitoring()
OnEthernetStateChanged(ethernetDevice->State());
OnWlanStateChanged(wlanDevice->State());
SetHasWifi(true);
StartScanTimer();
onAccessPointChanged();
}
@@ -863,11 +875,11 @@ void HotspotManagerImpl::StartHotspot()
settings["ipv4"]["method"] = "shared";
settings["ipv6"]["method"] = "shared";
settings["ipv6"]["addr-gen-mode"] = 1; // "stable-privacy";
////////////////////////////////////////////////////////////////
// Create connection
settings["ipv4"]["method"] = sdbus::Variant(std::string("shared"));
////////////////////////////////////////////////////////////////
// Create connection
settings["ipv4"]["method"] = sdbus::Variant(std::string("shared"));
// settings["ipv6"]["method"] = sdbus::Variant(std::string("ignore"));
settings["ipv4"]["address-data"] = sdbus::Variant(std::vector<std::map<std::string, sdbus::Variant>>{{{"address", sdbus::Variant("192.168.60.1")},
@@ -1014,6 +1026,32 @@ bool HotspotManagerImpl::CancelPost(PostHandle handle)
return dbusDispatcher.CancelPost(handle);
}
void HotspotManagerImpl::SetHasWifiListener(HasWifiListener &&listener)
{
std::lock_guard<std::recursive_mutex> lock{this->networkChangingListenerMutex};
this->hasWifiListener = listener;
if (!this->closed && this->hasWifiListener)
{
this->hasWifiListener(this->hasWifi);
}
}
bool HotspotManagerImpl::GetHasWifi() {
std::lock_guard<std::recursive_mutex> lock{this->networkChangingListenerMutex};
return hasWifi;
}
void HotspotManagerImpl::SetHasWifi(bool hasWifi)
{
std::lock_guard<std::recursive_mutex> lock{this->networkChangingListenerMutex};
if (hasWifi != this->hasWifi)
{
this->hasWifi = hasWifi;
if (this->hasWifiListener)
{
this->hasWifiListener(this->hasWifi);
}
}
}
void HotspotManagerImpl::SetNetworkChangingListener(NetworkChangingListener &&listener)
{
std::lock_guard<std::recursive_mutex> lock{this->networkChangingListenerMutex};
@@ -1034,23 +1072,29 @@ std::vector<std::string> HotspotManagerImpl::GetKnownWifiNetworks()
return this->knownWifiNetworks;
}
static bool is_wireless_sysfs(const std::string& ifname) {
static bool is_wireless_sysfs(const std::string &ifname)
{
return fs::exists("/sys/class/net/" + ifname + "/wireless");
}
static std::vector<std::string> get_wireless_interfaces_sysfs() {
static std::vector<std::string> get_wireless_interfaces_sysfs()
{
std::vector<std::string> wireless_interfaces;
const std::string net_path = "/sys/class/net";
try {
for (const auto& entry : fs::directory_iterator(net_path)) {
try
{
for (const auto &entry : fs::directory_iterator(net_path))
{
std::string ifname = entry.path().filename();
if (is_wireless_sysfs(ifname)) {
if (is_wireless_sysfs(ifname))
{
wireless_interfaces.push_back(ifname);
}
}
} catch (const fs::filesystem_error& e) {
}
catch (const fs::filesystem_error &e)
{
std::cerr << "Error accessing " << net_path << ": " << e.what() << std::endl;
}