OLD | NEW |
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2012 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 <errno.h> | 7 #include <errno.h> |
8 | 8 |
9 #include <algorithm> | 9 #include <algorithm> |
10 #include <iterator> | 10 #include <iterator> |
(...skipping 187 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
198 begin += match.length(); | 198 begin += match.length(); |
199 | 199 |
200 std::string ret; | 200 std::string ret; |
201 base::TrimWhitespace(std::string(begin, | 201 base::TrimWhitespace(std::string(begin, |
202 std::find(begin, headers.end(), '\n')), | 202 std::find(begin, headers.end(), '\n')), |
203 base::TRIM_ALL, &ret); | 203 base::TRIM_ALL, &ret); |
204 return ret; | 204 return ret; |
205 } | 205 } |
206 | 206 |
207 std::string CanonicalizeHost(const std::string& host, | 207 std::string CanonicalizeHost(const std::string& host, |
208 url_canon::CanonHostInfo* host_info) { | 208 url::CanonHostInfo* host_info) { |
209 // Try to canonicalize the host. | 209 // Try to canonicalize the host. |
210 const url_parse::Component raw_host_component( | 210 const url::Component raw_host_component(0, static_cast<int>(host.length())); |
211 0, static_cast<int>(host.length())); | |
212 std::string canon_host; | 211 std::string canon_host; |
213 url_canon::StdStringCanonOutput canon_host_output(&canon_host); | 212 url::StdStringCanonOutput canon_host_output(&canon_host); |
214 url_canon::CanonicalizeHostVerbose(host.c_str(), raw_host_component, | 213 url::CanonicalizeHostVerbose(host.c_str(), raw_host_component, |
215 &canon_host_output, host_info); | 214 &canon_host_output, host_info); |
216 | 215 |
217 if (host_info->out_host.is_nonempty() && | 216 if (host_info->out_host.is_nonempty() && |
218 host_info->family != url_canon::CanonHostInfo::BROKEN) { | 217 host_info->family != url::CanonHostInfo::BROKEN) { |
219 // Success! Assert that there's no extra garbage. | 218 // Success! Assert that there's no extra garbage. |
220 canon_host_output.Complete(); | 219 canon_host_output.Complete(); |
221 DCHECK_EQ(host_info->out_host.len, static_cast<int>(canon_host.length())); | 220 DCHECK_EQ(host_info->out_host.len, static_cast<int>(canon_host.length())); |
222 } else { | 221 } else { |
223 // Empty host, or canonicalization failed. We'll return empty. | 222 // Empty host, or canonicalization failed. We'll return empty. |
224 canon_host.clear(); | 223 canon_host.clear(); |
225 } | 224 } |
226 | 225 |
227 return canon_host; | 226 return canon_host; |
228 } | 227 } |
(...skipping 107 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
336 #endif | 335 #endif |
337 } | 336 } |
338 | 337 |
339 bool ParseHostAndPort(std::string::const_iterator host_and_port_begin, | 338 bool ParseHostAndPort(std::string::const_iterator host_and_port_begin, |
340 std::string::const_iterator host_and_port_end, | 339 std::string::const_iterator host_and_port_end, |
341 std::string* host, | 340 std::string* host, |
342 int* port) { | 341 int* port) { |
343 if (host_and_port_begin >= host_and_port_end) | 342 if (host_and_port_begin >= host_and_port_end) |
344 return false; | 343 return false; |
345 | 344 |
346 // When using url_parse, we use char*. | 345 // When using url, we use char*. |
347 const char* auth_begin = &(*host_and_port_begin); | 346 const char* auth_begin = &(*host_and_port_begin); |
348 int auth_len = host_and_port_end - host_and_port_begin; | 347 int auth_len = host_and_port_end - host_and_port_begin; |
349 | 348 |
350 url_parse::Component auth_component(0, auth_len); | 349 url::Component auth_component(0, auth_len); |
351 url_parse::Component username_component; | 350 url::Component username_component; |
352 url_parse::Component password_component; | 351 url::Component password_component; |
353 url_parse::Component hostname_component; | 352 url::Component hostname_component; |
354 url_parse::Component port_component; | 353 url::Component port_component; |
355 | 354 |
356 url_parse::ParseAuthority(auth_begin, auth_component, &username_component, | 355 url::ParseAuthority(auth_begin, auth_component, &username_component, |
357 &password_component, &hostname_component, &port_component); | 356 &password_component, &hostname_component, &port_component); |
358 | 357 |
359 // There shouldn't be a username/password. | 358 // There shouldn't be a username/password. |
360 if (username_component.is_valid() || password_component.is_valid()) | 359 if (username_component.is_valid() || password_component.is_valid()) |
361 return false; | 360 return false; |
362 | 361 |
363 if (!hostname_component.is_nonempty()) | 362 if (!hostname_component.is_nonempty()) |
364 return false; // Failed parsing. | 363 return false; // Failed parsing. |
365 | 364 |
366 int parsed_port_number = -1; | 365 int parsed_port_number = -1; |
367 if (port_component.is_nonempty()) { | 366 if (port_component.is_nonempty()) { |
368 parsed_port_number = url_parse::ParsePort(auth_begin, port_component); | 367 parsed_port_number = url::ParsePort(auth_begin, port_component); |
369 | 368 |
370 // If parsing failed, port_number will be either PORT_INVALID or | 369 // If parsing failed, port_number will be either PORT_INVALID or |
371 // PORT_UNSPECIFIED, both of which are negative. | 370 // PORT_UNSPECIFIED, both of which are negative. |
372 if (parsed_port_number < 0) | 371 if (parsed_port_number < 0) |
373 return false; // Failed parsing the port number. | 372 return false; // Failed parsing the port number. |
374 } | 373 } |
375 | 374 |
376 if (port_component.len == 0) | 375 if (port_component.len == 0) |
377 return false; // Reject inputs like "foo:" | 376 return false; // Reject inputs like "foo:" |
378 | 377 |
(...skipping 23 matching lines...) Expand all Loading... |
402 // so it is safe to just append a colon. | 401 // so it is safe to just append a colon. |
403 if (url.has_port()) | 402 if (url.has_port()) |
404 return base::StringPrintf("%s:%s", url.host().c_str(), url.port().c_str()); | 403 return base::StringPrintf("%s:%s", url.host().c_str(), url.port().c_str()); |
405 return url.host(); | 404 return url.host(); |
406 } | 405 } |
407 | 406 |
408 bool IsHostnameNonUnique(const std::string& hostname) { | 407 bool IsHostnameNonUnique(const std::string& hostname) { |
409 // CanonicalizeHost requires surrounding brackets to parse an IPv6 address. | 408 // CanonicalizeHost requires surrounding brackets to parse an IPv6 address. |
410 const std::string host_or_ip = hostname.find(':') != std::string::npos ? | 409 const std::string host_or_ip = hostname.find(':') != std::string::npos ? |
411 "[" + hostname + "]" : hostname; | 410 "[" + hostname + "]" : hostname; |
412 url_canon::CanonHostInfo host_info; | 411 url::CanonHostInfo host_info; |
413 std::string canonical_name = CanonicalizeHost(host_or_ip, &host_info); | 412 std::string canonical_name = CanonicalizeHost(host_or_ip, &host_info); |
414 | 413 |
415 // If canonicalization fails, then the input is truly malformed. However, | 414 // If canonicalization fails, then the input is truly malformed. However, |
416 // to avoid mis-reporting bad inputs as "non-unique", treat them as unique. | 415 // to avoid mis-reporting bad inputs as "non-unique", treat them as unique. |
417 if (canonical_name.empty()) | 416 if (canonical_name.empty()) |
418 return false; | 417 return false; |
419 | 418 |
420 // If |hostname| is an IP address, check to see if it's in an IANA-reserved | 419 // If |hostname| is an IP address, check to see if it's in an IANA-reserved |
421 // range. | 420 // range. |
422 if (host_info.IsIPAddress()) { | 421 if (host_info.IsIPAddress()) { |
423 IPAddressNumber host_addr; | 422 IPAddressNumber host_addr; |
424 if (!ParseIPLiteralToNumber(hostname.substr(host_info.out_host.begin, | 423 if (!ParseIPLiteralToNumber(hostname.substr(host_info.out_host.begin, |
425 host_info.out_host.len), | 424 host_info.out_host.len), |
426 &host_addr)) { | 425 &host_addr)) { |
427 return false; | 426 return false; |
428 } | 427 } |
429 switch (host_info.family) { | 428 switch (host_info.family) { |
430 case url_canon::CanonHostInfo::IPV4: | 429 case url::CanonHostInfo::IPV4: |
431 case url_canon::CanonHostInfo::IPV6: | 430 case url::CanonHostInfo::IPV6: |
432 return IsIPAddressReserved(host_addr); | 431 return IsIPAddressReserved(host_addr); |
433 case url_canon::CanonHostInfo::NEUTRAL: | 432 case url::CanonHostInfo::NEUTRAL: |
434 case url_canon::CanonHostInfo::BROKEN: | 433 case url::CanonHostInfo::BROKEN: |
435 return false; | 434 return false; |
436 } | 435 } |
437 } | 436 } |
438 | 437 |
439 // Check for a registry controlled portion of |hostname|, ignoring private | 438 // Check for a registry controlled portion of |hostname|, ignoring private |
440 // registries, as they already chain to ICANN-administered registries, | 439 // registries, as they already chain to ICANN-administered registries, |
441 // and explicitly ignoring unknown registries. | 440 // and explicitly ignoring unknown registries. |
442 // | 441 // |
443 // Note: This means that as new gTLDs are introduced on the Internet, they | 442 // Note: This means that as new gTLDs are introduced on the Internet, they |
444 // will be treated as non-unique until the registry controlled domain list | 443 // will be treated as non-unique until the registry controlled domain list |
(...skipping 100 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
545 return true; | 544 return true; |
546 } | 545 } |
547 #endif | 546 #endif |
548 | 547 |
549 return false; // Unrecognized |sa_family|. | 548 return false; // Unrecognized |sa_family|. |
550 } | 549 } |
551 | 550 |
552 std::string IPAddressToString(const uint8* address, | 551 std::string IPAddressToString(const uint8* address, |
553 size_t address_len) { | 552 size_t address_len) { |
554 std::string str; | 553 std::string str; |
555 url_canon::StdStringCanonOutput output(&str); | 554 url::StdStringCanonOutput output(&str); |
556 | 555 |
557 if (address_len == kIPv4AddressSize) { | 556 if (address_len == kIPv4AddressSize) { |
558 url_canon::AppendIPv4Address(address, &output); | 557 url::AppendIPv4Address(address, &output); |
559 } else if (address_len == kIPv6AddressSize) { | 558 } else if (address_len == kIPv6AddressSize) { |
560 url_canon::AppendIPv6Address(address, &output); | 559 url::AppendIPv6Address(address, &output); |
561 } else { | 560 } else { |
562 CHECK(false) << "Invalid IP address with length: " << address_len; | 561 CHECK(false) << "Invalid IP address with length: " << address_len; |
563 } | 562 } |
564 | 563 |
565 output.Complete(); | 564 output.Complete(); |
566 return str; | 565 return str; |
567 } | 566 } |
568 | 567 |
569 std::string IPAddressToStringWithPort(const uint8* address, | 568 std::string IPAddressToStringWithPort(const uint8* address, |
570 size_t address_len, | 569 size_t address_len, |
(...skipping 216 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
787 return AF_UNSPEC; | 786 return AF_UNSPEC; |
788 } | 787 } |
789 | 788 |
790 bool ParseIPLiteralToNumber(const std::string& ip_literal, | 789 bool ParseIPLiteralToNumber(const std::string& ip_literal, |
791 IPAddressNumber* ip_number) { | 790 IPAddressNumber* ip_number) { |
792 // |ip_literal| could be either a IPv4 or an IPv6 literal. If it contains | 791 // |ip_literal| could be either a IPv4 or an IPv6 literal. If it contains |
793 // a colon however, it must be an IPv6 address. | 792 // a colon however, it must be an IPv6 address. |
794 if (ip_literal.find(':') != std::string::npos) { | 793 if (ip_literal.find(':') != std::string::npos) { |
795 // GURL expects IPv6 hostnames to be surrounded with brackets. | 794 // GURL expects IPv6 hostnames to be surrounded with brackets. |
796 std::string host_brackets = "[" + ip_literal + "]"; | 795 std::string host_brackets = "[" + ip_literal + "]"; |
797 url_parse::Component host_comp(0, host_brackets.size()); | 796 url::Component host_comp(0, host_brackets.size()); |
798 | 797 |
799 // Try parsing the hostname as an IPv6 literal. | 798 // Try parsing the hostname as an IPv6 literal. |
800 ip_number->resize(16); // 128 bits. | 799 ip_number->resize(16); // 128 bits. |
801 return url_canon::IPv6AddressToNumber(host_brackets.data(), | 800 return url::IPv6AddressToNumber(host_brackets.data(), host_comp, |
802 host_comp, | 801 &(*ip_number)[0]); |
803 &(*ip_number)[0]); | |
804 } | 802 } |
805 | 803 |
806 // Otherwise the string is an IPv4 address. | 804 // Otherwise the string is an IPv4 address. |
807 ip_number->resize(4); // 32 bits. | 805 ip_number->resize(4); // 32 bits. |
808 url_parse::Component host_comp(0, ip_literal.size()); | 806 url::Component host_comp(0, ip_literal.size()); |
809 int num_components; | 807 int num_components; |
810 url_canon::CanonHostInfo::Family family = url_canon::IPv4AddressToNumber( | 808 url::CanonHostInfo::Family family = url::IPv4AddressToNumber( |
811 ip_literal.data(), host_comp, &(*ip_number)[0], &num_components); | 809 ip_literal.data(), host_comp, &(*ip_number)[0], &num_components); |
812 return family == url_canon::CanonHostInfo::IPV4; | 810 return family == url::CanonHostInfo::IPV4; |
813 } | 811 } |
814 | 812 |
815 namespace { | 813 namespace { |
816 | 814 |
817 const unsigned char kIPv4MappedPrefix[] = | 815 const unsigned char kIPv4MappedPrefix[] = |
818 { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0xFF, 0xFF }; | 816 { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0xFF, 0xFF }; |
819 } | 817 } |
820 | 818 |
821 IPAddressNumber ConvertIPv4NumberToIPv6Number( | 819 IPAddressNumber ConvertIPv4NumberToIPv6Number( |
822 const IPAddressNumber& ipv4_number) { | 820 const IPAddressNumber& ipv4_number) { |
(...skipping 176 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
999 } | 997 } |
1000 return a1.size() * CHAR_BIT; | 998 return a1.size() * CHAR_BIT; |
1001 } | 999 } |
1002 | 1000 |
1003 unsigned MaskPrefixLength(const IPAddressNumber& mask) { | 1001 unsigned MaskPrefixLength(const IPAddressNumber& mask) { |
1004 IPAddressNumber all_ones(mask.size(), 0xFF); | 1002 IPAddressNumber all_ones(mask.size(), 0xFF); |
1005 return CommonPrefixLength(mask, all_ones); | 1003 return CommonPrefixLength(mask, all_ones); |
1006 } | 1004 } |
1007 | 1005 |
1008 } // namespace net | 1006 } // namespace net |
OLD | NEW |