| OLD | NEW |
| 1 // Copyright (c) 2009 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2009 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #include "net/base/net_util.h" | 5 #include "net/base/net_util.h" |
| 6 | 6 |
| 7 #include <algorithm> | 7 #include <algorithm> |
| 8 #include <map> | 8 #include <map> |
| 9 #include <unicode/ucnv.h> | 9 #include <unicode/ucnv.h> |
| 10 #include <unicode/uidna.h> | 10 #include <unicode/uidna.h> |
| 11 #include <unicode/ulocdata.h> | 11 #include <unicode/ulocdata.h> |
| 12 #include <unicode/uniset.h> | 12 #include <unicode/uniset.h> |
| 13 #include <unicode/uscript.h> | 13 #include <unicode/uscript.h> |
| 14 #include <unicode/uset.h> | 14 #include <unicode/uset.h> |
| 15 | 15 |
| 16 #include "build/build_config.h" | 16 #include "build/build_config.h" |
| 17 | 17 |
| 18 #if defined(OS_WIN) | 18 #if defined(OS_WIN) |
| 19 #include <windows.h> | 19 #include <windows.h> |
| 20 #include <winsock2.h> | 20 #include <winsock2.h> |
| 21 #include <ws2tcpip.h> | 21 #include <ws2tcpip.h> |
| 22 #include <wspiapi.h> // Needed for Win2k compat. | 22 #include <wspiapi.h> // Needed for Win2k compat. |
| 23 #elif defined(OS_POSIX) | 23 #elif defined(OS_POSIX) |
| 24 #include <fcntl.h> |
| 25 #include <ifaddrs.h> |
| 24 #include <netdb.h> | 26 #include <netdb.h> |
| 27 #include <net/if.h> |
| 25 #include <sys/socket.h> | 28 #include <sys/socket.h> |
| 26 #include <fcntl.h> | |
| 27 #endif | 29 #endif |
| 28 | 30 |
| 29 #include "base/base64.h" | 31 #include "base/base64.h" |
| 30 #include "base/basictypes.h" | 32 #include "base/basictypes.h" |
| 31 #include "base/file_path.h" | 33 #include "base/file_path.h" |
| 32 #include "base/file_util.h" | 34 #include "base/file_util.h" |
| 33 #include "base/i18n/file_util_icu.h" | 35 #include "base/i18n/file_util_icu.h" |
| 34 #include "base/i18n/icu_string_conversions.h" | 36 #include "base/i18n/icu_string_conversions.h" |
| 35 #include "base/i18n/time_formatting.h" | 37 #include "base/i18n/time_formatting.h" |
| 36 #include "base/json/string_escape.h" | 38 #include "base/json/string_escape.h" |
| (...skipping 214 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 251 ucnv_close(converter); | 253 ucnv_close(converter); |
| 252 if (U_FAILURE(err)) { | 254 if (U_FAILURE(err)) { |
| 253 return false; | 255 return false; |
| 254 } | 256 } |
| 255 output->resize(length); | 257 output->resize(length); |
| 256 return true; | 258 return true; |
| 257 } | 259 } |
| 258 | 260 |
| 259 bool DecodeWord(const std::string& encoded_word, | 261 bool DecodeWord(const std::string& encoded_word, |
| 260 const std::string& referrer_charset, | 262 const std::string& referrer_charset, |
| 261 bool *is_rfc2047, | 263 bool* is_rfc2047, |
| 262 std::string* output) { | 264 std::string* output) { |
| 263 if (!IsStringASCII(encoded_word)) { | 265 if (!IsStringASCII(encoded_word)) { |
| 264 // Try UTF-8, referrer_charset and the native OS default charset in turn. | 266 // Try UTF-8, referrer_charset and the native OS default charset in turn. |
| 265 if (IsStringUTF8(encoded_word)) { | 267 if (IsStringUTF8(encoded_word)) { |
| 266 *output = encoded_word; | 268 *output = encoded_word; |
| 267 } else { | 269 } else { |
| 268 std::wstring wide_output; | 270 std::wstring wide_output; |
| 269 if (!referrer_charset.empty() && | 271 if (!referrer_charset.empty() && |
| 270 base::CodepageToWide(encoded_word, referrer_charset.c_str(), | 272 base::CodepageToWide(encoded_word, referrer_charset.c_str(), |
| 271 base::OnStringConversionError::FAIL, | 273 base::OnStringConversionError::FAIL, |
| (...skipping 1273 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1545 allowed_ports.substr(last, length)))); | 1547 allowed_ports.substr(last, length)))); |
| 1546 last = i + 1; | 1548 last = i + 1; |
| 1547 } | 1549 } |
| 1548 } | 1550 } |
| 1549 explicitly_allowed_ports = ports; | 1551 explicitly_allowed_ports = ports; |
| 1550 } | 1552 } |
| 1551 | 1553 |
| 1552 enum IPv6SupportStatus { | 1554 enum IPv6SupportStatus { |
| 1553 IPV6_CANNOT_CREATE_SOCKETS, | 1555 IPV6_CANNOT_CREATE_SOCKETS, |
| 1554 IPV6_CAN_CREATE_SOCKETS, | 1556 IPV6_CAN_CREATE_SOCKETS, |
| 1557 IPV6_GETIFADDRS_FAILED, |
| 1558 IPV6_GLOBAL_ADDRESS_MISSING, |
| 1559 IPV6_GLOBAL_ADDRESS_PRESENT, |
| 1555 IPV6_SUPPORT_MAX // Bounding values for enumeration. | 1560 IPV6_SUPPORT_MAX // Bounding values for enumeration. |
| 1556 }; | 1561 }; |
| 1557 | 1562 |
| 1558 static void IPv6SupportResults(IPv6SupportStatus result) { | 1563 static void IPv6SupportResults(IPv6SupportStatus result) { |
| 1559 static bool run_once = false; | 1564 static bool run_once = false; |
| 1560 if (run_once) | 1565 if (!run_once) { |
| 1561 return; | 1566 run_once = true; |
| 1562 run_once = true; | 1567 UMA_HISTOGRAM_ENUMERATION("Net.IPv6Status", result, IPV6_SUPPORT_MAX); |
| 1563 UMA_HISTOGRAM_ENUMERATION("Net.IPv6Status", result, IPV6_SUPPORT_MAX); | 1568 } else { |
| 1569 UMA_HISTOGRAM_ENUMERATION("Net.IPv6Status_retest", result, |
| 1570 IPV6_SUPPORT_MAX); |
| 1571 } |
| 1564 } | 1572 } |
| 1565 | 1573 |
| 1566 // TODO(jar): The following is a simple estimate of IPv6 support. We may need | 1574 // TODO(jar): The following is a simple estimate of IPv6 support. We may need |
| 1567 // to do a test resolution, and a test connection, to REALLY verify support. | 1575 // to do a test resolution, and a test connection, to REALLY verify support. |
| 1568 // static | 1576 // static |
| 1569 bool IPv6Supported() { | 1577 bool IPv6Supported() { |
| 1570 #if defined(OS_POSIX) | 1578 #if defined(OS_POSIX) |
| 1571 int test_socket; | 1579 int test_socket = socket(AF_INET6, SOCK_STREAM, 0); |
| 1572 | |
| 1573 test_socket = socket(AF_INET6, SOCK_STREAM, 0); | |
| 1574 if (test_socket == -1) { | 1580 if (test_socket == -1) { |
| 1575 IPv6SupportResults(IPV6_CANNOT_CREATE_SOCKETS); | 1581 IPv6SupportResults(IPV6_CANNOT_CREATE_SOCKETS); |
| 1576 return false; | 1582 return false; |
| 1577 } | 1583 } |
| 1584 close(test_socket); |
| 1578 | 1585 |
| 1579 close(test_socket); | 1586 // Check to see if any interface has a IPv6 address. |
| 1580 IPv6SupportResults(IPV6_CAN_CREATE_SOCKETS); | 1587 struct ifaddrs* interface_addr = NULL; |
| 1588 int rv = getifaddrs(&interface_addr); |
| 1589 if (rv != 0) { |
| 1590 IPv6SupportResults(IPV6_GETIFADDRS_FAILED); |
| 1591 return true; // Don't yet block IPv6. |
| 1592 } |
| 1593 |
| 1594 bool found_ipv6 = false; |
| 1595 for (struct ifaddrs* interface = interface_addr; |
| 1596 interface != NULL; |
| 1597 interface = interface->ifa_next) { |
| 1598 if (!(IFF_UP & interface->ifa_flags)) |
| 1599 continue; |
| 1600 if (IFF_LOOPBACK & interface->ifa_flags) |
| 1601 continue; |
| 1602 struct sockaddr* addr = interface->ifa_addr; |
| 1603 if (!addr) |
| 1604 continue; |
| 1605 if (addr->sa_family != AF_INET6) |
| 1606 continue; |
| 1607 // Safe cast since this is AF_INET6. |
| 1608 struct sockaddr_in6* addr_in6 = |
| 1609 reinterpret_cast<struct sockaddr_in6*>(addr); |
| 1610 struct in6_addr* sin6_addr = &addr_in6->sin6_addr; |
| 1611 if (IN6_IS_ADDR_LOOPBACK(sin6_addr) || IN6_IS_ADDR_LINKLOCAL(sin6_addr)) |
| 1612 continue; |
| 1613 found_ipv6 = true; |
| 1614 break; |
| 1615 } |
| 1616 freeifaddrs(interface_addr); |
| 1617 if (!found_ipv6) { |
| 1618 IPv6SupportResults(IPV6_GLOBAL_ADDRESS_MISSING); |
| 1619 return false; |
| 1620 } |
| 1621 |
| 1622 IPv6SupportResults(IPV6_GLOBAL_ADDRESS_PRESENT); |
| 1581 return true; | 1623 return true; |
| 1582 #elif defined(OS_WIN) | 1624 #elif defined(OS_WIN) |
| 1583 EnsureWinsockInit(); | 1625 EnsureWinsockInit(); |
| 1584 SOCKET test_socket; | 1626 SOCKET test_socket = socket(AF_INET6, SOCK_STREAM, 0); |
| 1585 | |
| 1586 test_socket = socket(AF_INET6, SOCK_STREAM, 0); | |
| 1587 if (test_socket == INVALID_SOCKET) { | 1627 if (test_socket == INVALID_SOCKET) { |
| 1588 IPv6SupportResults(IPV6_CANNOT_CREATE_SOCKETS); | 1628 IPv6SupportResults(IPV6_CANNOT_CREATE_SOCKETS); |
| 1589 return false; | 1629 return false; |
| 1590 } | 1630 } |
| 1591 | |
| 1592 closesocket(test_socket); | 1631 closesocket(test_socket); |
| 1593 IPv6SupportResults(IPV6_CAN_CREATE_SOCKETS); | 1632 IPv6SupportResults(IPV6_CAN_CREATE_SOCKETS); |
| 1594 return true; | 1633 return true; |
| 1595 #else | 1634 #else |
| 1596 NOTIMPLEMENTED(); | 1635 NOTIMPLEMENTED(); |
| 1597 return true; | 1636 return true; |
| 1598 #endif // defined(various platforms) | 1637 #endif // defined(various platforms) |
| 1599 } | 1638 } |
| 1600 | 1639 |
| 1601 | |
| 1602 } // namespace net | 1640 } // namespace net |
| OLD | NEW |