Add provider::Wifi::GetConnectedSsid
BUG:25820726
Change-Id: I3dc156df00e53bdf879b5a201d4f6cfa5badb1cd
Reviewed-on: https://weave-review.googlesource.com/2769
Reviewed-by: Vitaly Buka <vitalybuka@google.com>
diff --git a/examples/provider/wifi_manager.cc b/examples/provider/wifi_manager.cc
index 9337d23..7afd9ca 100644
--- a/examples/provider/wifi_manager.cc
+++ b/examples/provider/wifi_manager.cc
@@ -64,11 +64,51 @@
return "";
}
+std::string GetSsid(const std::string& interface) {
+ int sockf_d = socket(AF_INET, SOCK_DGRAM, 0);
+ CHECK_GE(sockf_d, 0) << strerror(errno);
+ iwreq wreq = {};
+ CHECK_LE(interface.size(), sizeof(wreq.ifr_name));
+ strncpy(wreq.ifr_name, interface.c_str(), sizeof(wreq.ifr_name));
+ std::string essid(' ', IW_ESSID_MAX_SIZE + 1);
+ wreq.u.essid.pointer = &essid[0];
+ wreq.u.essid.length = essid.size();
+ CHECK_GE(ioctl(sockf_d, SIOCGIWESSID, &wreq), 0) << strerror(errno);
+ essid.resize(wreq.u.essid.length);
+ close(sockf_d);
+ return essid;
+}
+
+bool CheckFreq(const std::string& interface, double start, double end) {
+ int sockf_d = socket(AF_INET, SOCK_DGRAM, 0);
+ CHECK_GE(sockf_d, 0) << strerror(errno);
+ iwreq wreq = {};
+ CHECK_LE(interface.size(), sizeof(wreq.ifr_name));
+ strncpy(wreq.ifr_name, interface.c_str(), sizeof(wreq.ifr_name));
+
+ iw_range range = {};
+ wreq.u.data.pointer = ⦥
+ wreq.u.data.length = sizeof(range);
+
+ CHECK_GE(ioctl(sockf_d, SIOCGIWRANGE, &wreq), 0) << strerror(errno);
+
+ bool result = false;
+ for (size_t i = 0; !result && i < range.num_frequency; ++i) {
+ double freq = range.freq[i].m * std::pow(10., range.freq[i].e);
+ if (start <= freq && freq <= end)
+ result = true;
+ }
+
+ close(sockf_d);
+ return result;
+}
+
} // namespace
WifiImpl::WifiImpl(provider::TaskRunner* task_runner, EventNetworkImpl* network)
: task_runner_{task_runner}, network_{network}, iface_{FindWirelessInterface()} {
CHECK(!iface_.empty()) << "WiFi interface not found";
+ CHECK(IsWifi24Supported() || IsWifi50Supported());
CHECK_EQ(0u, getuid())
<< "\nWiFi manager expects root access to control WiFi capabilities";
StopAccessPoint();
@@ -85,19 +125,7 @@
if (pid) {
int status = 0;
if (pid == waitpid(pid, &status, WNOWAIT)) {
- int sockf_d = socket(AF_INET, SOCK_DGRAM, 0);
- CHECK_GE(sockf_d, 0) << strerror(errno);
-
- iwreq wreq = {};
- strncpy(wreq.ifr_name, iface_.c_str(), sizeof(wreq.ifr_name));
- std::string essid(' ', IW_ESSID_MAX_SIZE + 1);
- wreq.u.essid.pointer = &essid[0];
- wreq.u.essid.length = essid.size();
- CHECK_GE(ioctl(sockf_d, SIOCGIWESSID, &wreq), 0) << strerror(errno);
- essid.resize(wreq.u.essid.length);
- close(sockf_d);
-
- if (ssid == essid)
+ if (ssid == GetSsid(iface_))
return task_runner_->PostDelayedTask(FROM_HERE,
base::Bind(callback, nullptr), {});
pid = 0; // Try again.
@@ -129,8 +157,7 @@
const std::string& passphrase,
const DoneCallback& callback) {
network_->SetSimulateOffline(false);
- CHECK(!hostapd_started_);
- if (hostapd_started_) {
+ if (!hostapd_ssid_.empty()) {
ErrorPtr error;
Error::AddTo(&error, FROM_HERE, "busy", "Running Access Point.");
task_runner_->PostDelayedTask(
@@ -143,8 +170,7 @@
}
void WifiImpl::StartAccessPoint(const std::string& ssid) {
- if (hostapd_started_)
- return;
+ CHECK(hostapd_ssid_.empty());
// Release wifi interface.
CHECK_EQ(0, ForkCmdAndWait("nmcli", {"nm", "wifi", "off"}));
@@ -160,7 +186,7 @@
}
CHECK_EQ(0, ForkCmdAndWait("hostapd", {"-B", "-K", hostapd_conf}));
- hostapd_started_ = true;
+ hostapd_ssid_ = ssid;
for (size_t i = 0; i < 10; ++i) {
if (0 == ForkCmdAndWait("ifconfig", {iface_, "192.168.76.1/24"}))
@@ -186,12 +212,24 @@
base::IgnoreResult(ForkCmdAndWait("pkill", {"-f", "dnsmasq.*/tmp/weave"}));
base::IgnoreResult(ForkCmdAndWait("pkill", {"-f", "hostapd.*/tmp/weave"}));
CHECK_EQ(0, ForkCmdAndWait("nmcli", {"nm", "wifi", "on"}));
- hostapd_started_ = false;
+ hostapd_ssid_.clear();
}
bool WifiImpl::HasWifiCapability() {
return !FindWirelessInterface().empty();
}
+bool WifiImpl::IsWifi24Supported() const {
+ return CheckFreq(iface_, 2.4e9, 2.5e9);
+};
+
+bool WifiImpl::IsWifi50Supported() const {
+ return CheckFreq(iface_, 4.9e9, 5.9e9);
+};
+
+std::string WifiImpl::GetConnectedSsid() const {
+ return GetSsid(iface_);
+}
+
} // namespace examples
} // namespace weave