Index: net/base/net_util_posix.cc |
diff --git a/net/base/net_util_posix.cc b/net/base/net_util_posix.cc |
index a2fa6cdf2ce7c1c871c4415911fe04c6b2d51602..b8e7195c5c53b4f97951144ee5d235032baddfc8 100644 |
--- a/net/base/net_util_posix.cc |
+++ b/net/base/net_util_posix.cc |
@@ -7,38 +7,18 @@ |
#include <set> |
#include <sys/types.h> |
-#include "base/files/file_path.h" |
-#include "base/logging.h" |
#include "base/memory/scoped_ptr.h" |
-#include "base/strings/string_number_conversions.h" |
-#include "base/strings/string_tokenizer.h" |
-#include "base/strings/string_util.h" |
-#include "base/threading/thread_restrictions.h" |
-#include "net/base/escape.h" |
-#include "net/base/ip_endpoint.h" |
-#include "net/base/net_errors.h" |
-#include "url/gurl.h" |
#if !defined(OS_NACL) |
-#if defined(OS_MACOSX) |
-#include <ifaddrs.h> |
-#else |
-#include "net/base/address_tracker_linux.h" |
#include "net/base/net_util_posix.h" |
-#endif // OS_MACOSX |
#include <net/if.h> |
#include <netinet/in.h> |
#endif // !defined(OS_NACL) |
-#if defined(OS_MACOSX) && !defined(OS_IOS) |
-#include <net/if_media.h> |
-#include <netinet/in_var.h> |
-#include <sys/ioctl.h> |
-#endif |
- |
namespace net { |
-namespace { |
+#if !defined(OS_NACL) |
+namespace internal { |
// The application layer can pass |policy| defined in net_util.h to |
// request filtering out certain type of interfaces. |
@@ -77,330 +57,13 @@ bool IsLoopbackOrUnspecifiedAddress(const sockaddr* addr) { |
return false; |
} |
-#if defined(OS_MACOSX) |
- |
-struct NetworkInterfaceInfo { |
- NetworkInterfaceInfo() : permanent(true) { } |
- |
- bool permanent; // IPv6 has notion of temporary address. If the address is |
- // IPv6 and it's temporary this field will be false. |
- NetworkInterface interface; |
-}; |
- |
-// This method will remove permanent IPv6 addresses if a temporary address |
-// is available for same network interface. |
-void RemovePermanentIPv6AddressesWhereTemporaryExists( |
- std::vector<NetworkInterfaceInfo>* infos) { |
- if (!infos || infos->empty()) |
- return; |
- |
- // Build a set containing the names of interfaces with a temp IPv6 address |
- std::set<std::string> ifaces_with_temp_addrs; |
- std::vector<NetworkInterfaceInfo>::iterator i; |
- for (i = infos->begin(); i != infos->end(); ++i) { |
- if (!i->permanent && i->interface.address.size() == kIPv6AddressSize) { |
- ifaces_with_temp_addrs.insert(i->interface.name); |
- } |
- } |
- |
- // If there are no such interfaces then there's no further work. |
- if (ifaces_with_temp_addrs.empty()) |
- return; |
- |
- // Search for permenent addresses belonging to same network interface. |
- for (i = infos->begin(); i != infos->end(); ) { |
- // If the address is IPv6 and it's permanent and there is temporary |
- // address for it, then we can remove this address. |
- if ((i->interface.address.size() == kIPv6AddressSize) && i->permanent && |
- (ifaces_with_temp_addrs.find(i->interface.name) != |
- ifaces_with_temp_addrs.end())) { |
- i = infos->erase(i); |
- } else { |
- ++i; |
- } |
- } |
-} |
- |
-#if !defined(OS_IOS) |
-NetworkChangeNotifier::ConnectionType GetNetworkInterfaceType( |
- int addr_family, const std::string& interface_name) { |
- NetworkChangeNotifier::ConnectionType type = |
- NetworkChangeNotifier::CONNECTION_UNKNOWN; |
- |
- struct ifmediareq ifmr = {}; |
- strncpy(ifmr.ifm_name, interface_name.c_str(), sizeof(ifmr.ifm_name) - 1); |
- |
- int s = socket(addr_family, SOCK_DGRAM, 0); |
- if (s == -1) { |
- return type; |
- } |
- |
- if (ioctl(s, SIOCGIFMEDIA, &ifmr) != -1) { |
- if (ifmr.ifm_current & IFM_IEEE80211) { |
- type = NetworkChangeNotifier::CONNECTION_WIFI; |
- } else if (ifmr.ifm_current & IFM_ETHER) { |
- type = NetworkChangeNotifier::CONNECTION_ETHERNET; |
- } |
- } |
- close(s); |
- return type; |
-} |
- |
-#endif // !defined(OS_IOS) |
-#elif !defined(OS_NACL) // OS_MACOSX |
- |
-// Convert platform native IPv6 address attributes to net IP address |
-// attributes and drop ones that can't be used by the application |
-// layer. |
-bool TryConvertNativeToNetIPAttributes(int native_attributes, |
- int* net_attributes) { |
- // For Linux/ChromeOS/Android, we disallow addresses with attributes |
- // IFA_F_OPTIMISTIC, IFA_F_DADFAILED, and IFA_F_TENTATIVE as these |
- // are still progressing through duplicated address detection (DAD) |
- // and shouldn't be used by the application layer until DAD process |
- // is completed. |
- if (native_attributes & ( |
-#if !defined(OS_ANDROID) |
- IFA_F_OPTIMISTIC | IFA_F_DADFAILED | |
-#endif // !OS_ANDROID |
- IFA_F_TENTATIVE)) { |
- return false; |
- } |
- |
- if (native_attributes & IFA_F_TEMPORARY) { |
- *net_attributes |= IP_ADDRESS_ATTRIBUTE_TEMPORARY; |
- } |
- |
- if (native_attributes & IFA_F_DEPRECATED) { |
- *net_attributes |= IP_ADDRESS_ATTRIBUTE_DEPRECATED; |
- } |
- |
- return true; |
-} |
-#endif // OS_MACOSX |
-} // namespace |
- |
-namespace internal { |
- |
-#if !defined(OS_MACOSX) && !defined(OS_NACL) |
- |
-inline const unsigned char* GetIPAddressData(const IPAddressNumber& ip) { |
-#if defined(OS_ANDROID) |
- return ip.begin(); |
-#else |
- return ip.data(); |
-#endif |
-} |
- |
-bool GetNetworkListImpl( |
- NetworkInterfaceList* networks, |
- int policy, |
- const base::hash_set<int>& online_links, |
- const internal::AddressTrackerLinux::AddressMap& address_map, |
- GetInterfaceNameFunction get_interface_name) { |
- std::map<int, std::string> ifnames; |
- |
- for (internal::AddressTrackerLinux::AddressMap::const_iterator it = |
- address_map.begin(); |
- it != address_map.end(); |
- ++it) { |
- // Ignore addresses whose links are not online. |
- if (online_links.find(it->second.ifa_index) == online_links.end()) |
- continue; |
- |
- sockaddr_storage sock_addr; |
- socklen_t sock_len = sizeof(sockaddr_storage); |
- |
- // Convert to sockaddr for next check. |
- if (!IPEndPoint(it->first, 0) |
- .ToSockAddr(reinterpret_cast<sockaddr*>(&sock_addr), &sock_len)) { |
- continue; |
- } |
- |
- // Skip unspecified addresses (i.e. made of zeroes) and loopback addresses |
- if (IsLoopbackOrUnspecifiedAddress(reinterpret_cast<sockaddr*>(&sock_addr))) |
- continue; |
- |
- int ip_attributes = IP_ADDRESS_ATTRIBUTE_NONE; |
- |
- if (it->second.ifa_family == AF_INET6) { |
- // Ignore addresses whose attributes are not actionable by |
- // the application layer. |
- if (!TryConvertNativeToNetIPAttributes(it->second.ifa_flags, |
- &ip_attributes)) |
- continue; |
- } |
- |
- // Find the name of this link. |
- std::map<int, std::string>::const_iterator itname = |
- ifnames.find(it->second.ifa_index); |
- std::string ifname; |
- if (itname == ifnames.end()) { |
- char buffer[IF_NAMESIZE] = {0}; |
- if (get_interface_name(it->second.ifa_index, buffer)) { |
- ifname = ifnames[it->second.ifa_index] = buffer; |
- } else { |
- // Ignore addresses whose interface name can't be retrieved. |
- continue; |
- } |
- } else { |
- ifname = itname->second; |
- } |
- |
- // Based on the interface name and policy, determine whether we |
- // should ignore it. |
- if (ShouldIgnoreInterface(ifname, policy)) |
- continue; |
- |
- networks->push_back( |
- NetworkInterface(ifname, |
- ifname, |
- it->second.ifa_index, |
- NetworkChangeNotifier::CONNECTION_UNKNOWN, |
- it->first, |
- it->second.ifa_prefixlen, |
- ip_attributes)); |
- } |
- |
- return true; |
-} |
-#endif |
- |
} // namespace internal |
- |
+#else // OS_NACL |
bool GetNetworkList(NetworkInterfaceList* networks, int policy) { |
- if (networks == NULL) |
- return false; |
-#if defined(OS_NACL) |
NOTIMPLEMENTED(); |
return false; |
-#elif !defined(OS_MACOSX) |
- |
- internal::AddressTrackerLinux tracker; |
- tracker.Init(); |
- |
- return internal::GetNetworkListImpl(networks, |
- policy, |
- tracker.GetOnlineLinks(), |
- tracker.GetAddressMap(), |
- &if_indextoname); |
- |
-#else // Only OS_MACOSX and OS_IOS will run the code below |
- |
- // getifaddrs() may require IO operations. |
- base::ThreadRestrictions::AssertIOAllowed(); |
- |
-#if !defined(OS_IOS) |
- int ioctl_socket = -1; |
- if (policy & INCLUDE_ONLY_TEMP_IPV6_ADDRESS_IF_POSSIBLE) { |
- // we need a socket to query information about temporary address. |
- ioctl_socket = socket(AF_INET6, SOCK_DGRAM, 0); |
- DCHECK_GT(ioctl_socket, 0); |
- } |
-#endif |
- |
- ifaddrs* interfaces; |
- if (getifaddrs(&interfaces) < 0) { |
- PLOG(ERROR) << "getifaddrs"; |
- return false; |
- } |
- |
- std::vector<NetworkInterfaceInfo> network_infos; |
- |
- // Enumerate the addresses assigned to network interfaces which are up. |
- for (ifaddrs *interface = interfaces; |
- interface != NULL; |
- interface = interface->ifa_next) { |
- // Skip loopback interfaces, and ones which are down. |
- if (!(IFF_UP & interface->ifa_flags)) |
- continue; |
- if (IFF_LOOPBACK & interface->ifa_flags) |
- continue; |
- // Skip interfaces with no address configured. |
- struct sockaddr* addr = interface->ifa_addr; |
- if (!addr) |
- continue; |
- |
- // Skip unspecified addresses (i.e. made of zeroes) and loopback addresses |
- // configured on non-loopback interfaces. |
- if (IsLoopbackOrUnspecifiedAddress(addr)) |
- continue; |
- |
- int addr_size = 0; |
- if (addr->sa_family == AF_INET6) { |
- addr_size = sizeof(sockaddr_in6); |
- } else if (addr->sa_family == AF_INET) { |
- addr_size = sizeof(sockaddr_in); |
- } |
- |
- const std::string& name = interface->ifa_name; |
- // Filter out VMware interfaces, typically named vmnet1 and vmnet8. |
- if (ShouldIgnoreInterface(name, policy)) { |
- continue; |
- } |
- |
- NetworkInterfaceInfo network_info; |
- NetworkChangeNotifier::ConnectionType connection_type = |
- NetworkChangeNotifier::CONNECTION_UNKNOWN; |
-#if !defined(OS_IOS) |
- // Check if this is a temporary address. Currently this is only supported |
- // on Mac. |
- if ((policy & INCLUDE_ONLY_TEMP_IPV6_ADDRESS_IF_POSSIBLE) && |
- ioctl_socket >= 0 && addr->sa_family == AF_INET6) { |
- struct in6_ifreq ifr = {}; |
- strncpy(ifr.ifr_name, interface->ifa_name, sizeof(ifr.ifr_name) - 1); |
- memcpy(&ifr.ifr_ifru.ifru_addr, interface->ifa_addr, |
- interface->ifa_addr->sa_len); |
- int rv = ioctl(ioctl_socket, SIOCGIFAFLAG_IN6, &ifr); |
- if (rv >= 0) { |
- network_info.permanent = !(ifr.ifr_ifru.ifru_flags & IN6_IFF_TEMPORARY); |
- } |
- } |
- |
- connection_type = GetNetworkInterfaceType(addr->sa_family, name); |
-#endif |
- |
- IPEndPoint address; |
- if (address.FromSockAddr(addr, addr_size)) { |
- uint8 net_mask = 0; |
- if (interface->ifa_netmask) { |
- // If not otherwise set, assume the same sa_family as ifa_addr. |
- if (interface->ifa_netmask->sa_family == 0) { |
- interface->ifa_netmask->sa_family = addr->sa_family; |
- } |
- IPEndPoint netmask; |
- if (netmask.FromSockAddr(interface->ifa_netmask, addr_size)) { |
- net_mask = MaskPrefixLength(netmask.address()); |
- } |
- } |
- network_info.interface = NetworkInterface(name, |
- name, |
- if_nametoindex(name.c_str()), |
- connection_type, |
- address.address(), |
- net_mask, |
- IP_ADDRESS_ATTRIBUTE_NONE); |
- |
- network_infos.push_back(NetworkInterfaceInfo(network_info)); |
- } |
- } |
- freeifaddrs(interfaces); |
-#if !defined(OS_IOS) |
- if (ioctl_socket >= 0) { |
- close(ioctl_socket); |
- } |
-#endif |
- |
- if (policy & INCLUDE_ONLY_TEMP_IPV6_ADDRESS_IF_POSSIBLE) { |
- RemovePermanentIPv6AddressesWhereTemporaryExists(&network_infos); |
- } |
- |
- for (size_t i = 0; i < network_infos.size(); ++i) { |
- networks->push_back(network_infos[i].interface); |
- } |
- return true; |
-#endif |
} |
+#endif // OS_NACL |
WifiPHYLayerProtocol GetWifiPHYLayerProtocol() { |
return WIFI_PHY_LAYER_PROTOCOL_UNKNOWN; |