| Index: net/base/address_tracker_linux.cc
|
| diff --git a/net/base/address_tracker_linux.cc b/net/base/address_tracker_linux.cc
|
| index 731bf4f97785ebf45837c35a4fe4033bd4ffffff..d94104da6294075287bc378d62b954873fb1ab74 100644
|
| --- a/net/base/address_tracker_linux.cc
|
| +++ b/net/base/address_tracker_linux.cc
|
| @@ -6,6 +6,7 @@
|
|
|
| #include <errno.h>
|
| #include <linux/if.h>
|
| +#include <linux/wireless.h>
|
| #include <sys/ioctl.h>
|
|
|
| #include "base/files/scoped_file.h"
|
| @@ -78,6 +79,22 @@ bool GetAddress(const struct nlmsghdr* header,
|
| return true;
|
| }
|
|
|
| +std::string GetInterfaceSSID(const std::string& ifname) {
|
| + int ioctl_socket = socket(AF_INET, SOCK_DGRAM, 0);
|
| + if (ioctl_socket < 0)
|
| + return "";
|
| + struct iwreq wreq;
|
| + memset(&wreq, 0, sizeof(wreq));
|
| + strncpy(wreq.ifr_name, ifname.c_str(), IFNAMSIZ - 1);
|
| +
|
| + char ssid[IW_ESSID_MAX_SIZE + 1] = {0};
|
| + wreq.u.essid.pointer = ssid;
|
| + wreq.u.essid.length = IW_ESSID_MAX_SIZE;
|
| + int rv = ioctl(ioctl_socket, SIOCGIWESSID, &wreq);
|
| + close(ioctl_socket);
|
| + return (rv == 0) ? ssid : "";
|
| +}
|
| +
|
| } // namespace
|
|
|
| // static
|
| @@ -95,6 +112,26 @@ char* AddressTrackerLinux::GetInterfaceName(int interface_index, char* buf) {
|
| return buf;
|
| }
|
|
|
| +// static
|
| +std::string AddressTrackerLinux::ConnectionSSIDFromInterfaceList(
|
| + const NetworkInterfaceList& interfaces,
|
| + GetInterfaceSSIDFunction get_interface_ssid) {
|
| + std::string connected_ssid;
|
| + bool first = true;
|
| + for (size_t i = 0; i < interfaces.size(); ++i) {
|
| + if (interfaces[i].type != NetworkChangeNotifier::CONNECTION_WIFI)
|
| + return "";
|
| + std::string ssid = get_interface_ssid(interfaces[i].name);
|
| + if (first) {
|
| + first = false;
|
| + connected_ssid = ssid;
|
| + } else if (ssid != connected_ssid) {
|
| + return "";
|
| + }
|
| + }
|
| + return connected_ssid;
|
| +}
|
| +
|
| AddressTrackerLinux::AddressTrackerLinux()
|
| : get_interface_name_(GetInterfaceName),
|
| address_callback_(base::Bind(&base::DoNothing)),
|
| @@ -223,6 +260,7 @@ void AddressTrackerLinux::AbortAndForceOnline() {
|
| current_connection_type_ = NetworkChangeNotifier::CONNECTION_UNKNOWN;
|
| connection_type_initialized_ = true;
|
| connection_type_initialized_cv_.Signal();
|
| + current_wifi_ssid_ = "";
|
| }
|
|
|
| AddressTrackerLinux::AddressMap AddressTrackerLinux::GetAddressMap() const {
|
| @@ -247,6 +285,12 @@ AddressTrackerLinux::GetCurrentConnectionType() {
|
| return current_connection_type_;
|
| }
|
|
|
| +std::string AddressTrackerLinux::GetCurrentWiFiSSID() {
|
| + // Don't wait for initialization, return an empty SSID if not initialized.
|
| + AddressTrackerAutoLock lock(*this, wifi_ssid_lock_);
|
| + return current_wifi_ssid_;
|
| +}
|
| +
|
| void AddressTrackerLinux::ReadMessages(bool* address_changed,
|
| bool* link_changed,
|
| bool* tunnel_changed) {
|
| @@ -275,7 +319,7 @@ void AddressTrackerLinux::ReadMessages(bool* address_changed,
|
| HandleMessage(buffer, rv, address_changed, link_changed, tunnel_changed);
|
| }
|
| if (*link_changed || *address_changed)
|
| - UpdateCurrentConnectionType();
|
| + UpdateCurrentConnectionTypeAndSSID();
|
| }
|
|
|
| void AddressTrackerLinux::HandleMessage(char* buffer,
|
| @@ -395,7 +439,7 @@ bool AddressTrackerLinux::IsTunnelInterface(int interface_index) const {
|
| return strncmp(get_interface_name_(interface_index, buf), "tun", 3) == 0;
|
| }
|
|
|
| -void AddressTrackerLinux::UpdateCurrentConnectionType() {
|
| +void AddressTrackerLinux::UpdateCurrentConnectionTypeAndSSID() {
|
| AddressTrackerLinux::AddressMap address_map = GetAddressMap();
|
| base::hash_set<int> online_links = GetOnlineLinks();
|
|
|
| @@ -414,16 +458,24 @@ void AddressTrackerLinux::UpdateCurrentConnectionType() {
|
| NetworkInterfaceList networks;
|
| NetworkChangeNotifier::ConnectionType type =
|
| NetworkChangeNotifier::CONNECTION_NONE;
|
| + std::string ssid;
|
| if (GetNetworkListImpl(&networks, 0, online_links, address_map,
|
| get_interface_name_)) {
|
| type = NetworkChangeNotifier::ConnectionTypeFromInterfaceList(networks);
|
| + ssid = ConnectionSSIDFromInterfaceList(networks, GetInterfaceSSID);
|
| } else {
|
| type = online_links.empty() ? NetworkChangeNotifier::CONNECTION_NONE
|
| : NetworkChangeNotifier::CONNECTION_UNKNOWN;
|
| }
|
|
|
| - AddressTrackerAutoLock lock(*this, connection_type_lock_);
|
| - current_connection_type_ = type;
|
| + {
|
| + AddressTrackerAutoLock lock(*this, connection_type_lock_);
|
| + current_connection_type_ = type;
|
| + }
|
| + {
|
| + AddressTrackerAutoLock lock(*this, wifi_ssid_lock_);
|
| + current_wifi_ssid_ = ssid;
|
| + }
|
| }
|
|
|
| AddressTrackerLinux::AddressTrackerAutoLock::AddressTrackerAutoLock(
|
|
|