InetAddress.java revision a7428d68453f6a74633221e8714f8d3d9597b2b4
1/* 2 * Licensed to the Apache Software Foundation (ASF) under one or more 3 * contributor license agreements. See the NOTICE file distributed with 4 * this work for additional information regarding copyright ownership. 5 * The ASF licenses this file to You under the Apache License, Version 2.0 6 * (the "License"); you may not use this file except in compliance with 7 * the License. You may obtain a copy of the License at 8 * 9 * http://www.apache.org/licenses/LICENSE-2.0 10 * 11 * Unless required by applicable law or agreed to in writing, software 12 * distributed under the License is distributed on an "AS IS" BASIS, 13 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 14 * See the License for the specific language governing permissions and 15 * limitations under the License. 16 */ 17 18package java.net; 19 20import dalvik.system.BlockGuard; 21import java.io.FileDescriptor; 22import java.io.IOException; 23import java.io.ObjectInputStream; 24import java.io.ObjectOutputStream; 25import java.io.ObjectStreamException; 26import java.io.ObjectStreamField; 27import java.io.Serializable; 28import java.nio.ByteOrder; 29import java.util.Arrays; 30import java.util.Collections; 31import java.util.Comparator; 32import java.util.Enumeration; 33import java.util.List; 34import libcore.io.ErrnoException; 35import libcore.io.GaiException; 36import libcore.io.Libcore; 37import libcore.io.IoBridge; 38import libcore.io.Memory; 39import libcore.io.StructAddrinfo; 40import static libcore.io.OsConstants.*; 41 42/** 43 * An Internet Protocol (IP) address. This can be either an IPv4 address or an IPv6 address, and 44 * in practice you'll have an instance of either {@code Inet4Address} or {@code Inet6Address} (this 45 * class cannot be instantiated directly). Most code does not need to distinguish between the two 46 * families, and should use {@code InetAddress}. 47 * 48 * <p>An {@code InetAddress} may have a hostname (accessible via {@code getHostName}), but may not, 49 * depending on how the {@code InetAddress} was created. 50 * 51 * <h4>IPv4 numeric address formats</h4> 52 * <p>The {@code getAllByName} method accepts IPv4 addresses in the "decimal-dotted-quad" form only: 53 * <ul> 54 * <li>{@code "1.2.3.4"} - 1.2.3.4 55 * </ul> 56 * 57 * <h4>IPv6 numeric address formats</h4> 58 * <p>The {@code getAllByName} method accepts IPv6 addresses in the following forms (this text 59 * comes from <a href="http://www.ietf.org/rfc/rfc2373.txt">RFC 2373</a>, which you should consult 60 * for full details of IPv6 addressing): 61 * <ul> 62 * <li><p>The preferred form is {@code x:x:x:x:x:x:x:x}, where the 'x's are the 63 * hexadecimal values of the eight 16-bit pieces of the address. 64 * Note that it is not necessary to write the leading zeros in an 65 * individual field, but there must be at least one numeral in every 66 * field (except for the case described in the next bullet). 67 * Examples: 68 * <pre> 69 * FEDC:BA98:7654:3210:FEDC:BA98:7654:3210 70 * 1080:0:0:0:8:800:200C:417A</pre> 71 * </li> 72 * <li>Due to some methods of allocating certain styles of IPv6 73 * addresses, it will be common for addresses to contain long strings 74 * of zero bits. In order to make writing addresses containing zero 75 * bits easier a special syntax is available to compress the zeros. 76 * The use of "::" indicates multiple groups of 16-bits of zeros. 77 * The "::" can only appear once in an address. The "::" can also be 78 * used to compress the leading and/or trailing zeros in an address. 79 * 80 * For example the following addresses: 81 * <pre> 82 * 1080:0:0:0:8:800:200C:417A a unicast address 83 * FF01:0:0:0:0:0:0:101 a multicast address 84 * 0:0:0:0:0:0:0:1 the loopback address 85 * 0:0:0:0:0:0:0:0 the unspecified addresses</pre> 86 * may be represented as: 87 * <pre> 88 * 1080::8:800:200C:417A a unicast address 89 * FF01::101 a multicast address 90 * ::1 the loopback address 91 * :: the unspecified addresses</pre> 92 * </li> 93 * <li><p>An alternative form that is sometimes more convenient when dealing 94 * with a mixed environment of IPv4 and IPv6 nodes is 95 * {@code x:x:x:x:x:x:d.d.d.d}, where the 'x's are the hexadecimal values of 96 * the six high-order 16-bit pieces of the address, and the 'd's are 97 * the decimal values of the four low-order 8-bit pieces of the 98 * address (standard IPv4 representation). Examples: 99 * <pre> 100 * 0:0:0:0:0:0:13.1.68.3 101 * 0:0:0:0:0:FFFF:129.144.52.38</pre> 102 * or in compressed form: 103 * <pre> 104 * ::13.1.68.3 105 * ::FFFF:129.144.52.38</pre> 106 * </li> 107 * </ul> 108 * <p>Scopes are given using a trailing {@code %} followed by the scope id, as in 109 * {@code 1080::8:800:200C:417A%2} or {@code 1080::8:800:200C:417A%en0}. 110 * See <a href="https://www.ietf.org/rfc/rfc4007.txt">RFC 4007</a> for more on IPv6's scoped 111 * address architecture. 112 * 113 * <p>Additionally, for backwards compatibility, IPv6 addresses may be surrounded by square 114 * brackets. 115 * 116 * <h4>DNS caching</h4> 117 * <p>On Android, addresses are cached for 600 seconds (10 minutes) by default. Failed lookups are 118 * cached for 10 seconds. The underlying C library or OS may cache for longer, but you can control 119 * the Java-level caching with the usual {@code "networkaddress.cache.ttl"} and 120 * {@code "networkaddress.cache.negative.ttl"} system properties. These are parsed as integer 121 * numbers of seconds, where the special value 0 means "don't cache" and -1 means "cache forever". 122 * 123 * <p>Note also that on Android – unlike the RI – the cache is not unbounded. The 124 * current implementation caches around 512 entries, removed on a least-recently-used basis. 125 * (Obviously, you should not rely on these details.) 126 * 127 * @see Inet4Address 128 * @see Inet6Address 129 */ 130public class InetAddress implements Serializable { 131 /** Our Java-side DNS cache. */ 132 private static final AddressCache addressCache = new AddressCache(); 133 134 private static final long serialVersionUID = 3286316764910316507L; 135 136 private transient Object waitReachable = new Object(); 137 138 private boolean reached; 139 140 private int addrCount; 141 142 private int family; 143 144 byte[] ipaddress; 145 146 String hostName; 147 148 /** 149 * Used by the DatagramSocket.disconnect implementation. 150 * @hide internal use only 151 */ 152 public static final InetAddress UNSPECIFIED = new InetAddress(AF_UNSPEC, null, null); 153 154 /** 155 * Constructs an {@code InetAddress}. 156 * 157 * Note: this constructor is for subclasses only. 158 */ 159 InetAddress(int family, byte[] ipaddress, String hostName) { 160 this.family = family; 161 this.ipaddress = ipaddress; 162 this.hostName = hostName; 163 } 164 165 /** 166 * Compares this {@code InetAddress} instance against the specified address 167 * in {@code obj}. Two addresses are equal if their address byte arrays have 168 * the same length and if the bytes in the arrays are equal. 169 * 170 * @param obj 171 * the object to be tested for equality. 172 * @return {@code true} if both objects are equal, {@code false} otherwise. 173 */ 174 @Override 175 public boolean equals(Object obj) { 176 if (!(obj instanceof InetAddress)) { 177 return false; 178 } 179 return Arrays.equals(this.ipaddress, ((InetAddress) obj).ipaddress); 180 } 181 182 /** 183 * Returns the IP address represented by this {@code InetAddress} instance 184 * as a byte array. The elements are in network order (the highest order 185 * address byte is in the zeroth element). 186 * 187 * @return the address in form of a byte array. 188 */ 189 public byte[] getAddress() { 190 return ipaddress.clone(); 191 } 192 193 /** 194 * Converts an array of byte arrays representing raw IP addresses of a host 195 * to an array of InetAddress objects. 196 * 197 * @param rawAddresses the raw addresses to convert. 198 * @param hostName the hostname corresponding to the IP address. 199 * @return the corresponding InetAddresses, appropriately sorted. 200 */ 201 private static InetAddress[] bytesToInetAddresses(byte[][] rawAddresses, String hostName) 202 throws UnknownHostException { 203 // Convert the byte arrays to InetAddresses. 204 InetAddress[] returnedAddresses = new InetAddress[rawAddresses.length]; 205 for (int i = 0; i < rawAddresses.length; i++) { 206 returnedAddresses[i] = makeInetAddress(rawAddresses[i], hostName); 207 } 208 return returnedAddresses; 209 } 210 211 /** 212 * Gets all IP addresses associated with the given {@code host} identified 213 * by name or literal IP address. The IP address is resolved by the 214 * configured name service. If the host name is empty or {@code null} an 215 * {@code UnknownHostException} is thrown. If the host name is a literal IP 216 * address string an array with the corresponding single {@code InetAddress} 217 * is returned. 218 * 219 * @param host the hostname or literal IP string to be resolved. 220 * @return the array of addresses associated with the specified host. 221 * @throws UnknownHostException if the address lookup fails. 222 */ 223 public static InetAddress[] getAllByName(String host) throws UnknownHostException { 224 return getAllByNameImpl(host).clone(); 225 } 226 227 /** 228 * Returns the InetAddresses for {@code host}. The returned array is shared 229 * and must be cloned before it is returned to application code. 230 */ 231 private static InetAddress[] getAllByNameImpl(String host) throws UnknownHostException { 232 if (host == null || host.isEmpty()) { 233 return loopbackAddresses(); 234 } 235 236 // Is it a numeric address? 237 InetAddress result = parseNumericAddressNoThrow(host); 238 if (result != null) { 239 result = disallowDeprecatedFormats(host, result); 240 if (result == null) { 241 throw new UnknownHostException("Deprecated IPv4 address format: " + host); 242 } 243 return new InetAddress[] { result }; 244 } 245 246 return lookupHostByName(host).clone(); 247 } 248 249 private static InetAddress makeInetAddress(byte[] bytes, String hostName) throws UnknownHostException { 250 if (bytes.length == 4) { 251 return new Inet4Address(bytes, hostName); 252 } else if (bytes.length == 16) { 253 return new Inet6Address(bytes, hostName, 0); 254 } else { 255 throw badAddressLength(bytes); 256 } 257 } 258 259 private static InetAddress disallowDeprecatedFormats(String address, InetAddress inetAddress) { 260 // Only IPv4 addresses are problematic. 261 if (!(inetAddress instanceof Inet4Address) || address.indexOf(':') != -1) { 262 return inetAddress; 263 } 264 // If inet_pton(3) can't parse it, it must have been a deprecated format. 265 // We need to return inet_pton(3)'s result to ensure that numbers assumed to be octal 266 // by getaddrinfo(3) are reinterpreted by inet_pton(3) as decimal. 267 return Libcore.os.inet_pton(AF_INET, address); 268 } 269 270 private static InetAddress parseNumericAddressNoThrow(String address) { 271 // Accept IPv6 addresses (only) in square brackets for compatibility. 272 if (address.startsWith("[") && address.endsWith("]") && address.indexOf(':') != -1) { 273 address = address.substring(1, address.length() - 1); 274 } 275 StructAddrinfo hints = new StructAddrinfo(); 276 hints.ai_flags = AI_NUMERICHOST; 277 InetAddress[] addresses = null; 278 try { 279 addresses = Libcore.os.getaddrinfo(address, hints); 280 } catch (GaiException ignored) { 281 } 282 return (addresses != null) ? addresses[0] : null; 283 } 284 285 /** 286 * Returns the address of a host according to the given host string name 287 * {@code host}. The host string may be either a machine name or a dotted 288 * string IP address. If the latter, the {@code hostName} field is 289 * determined upon demand. {@code host} can be {@code null} which means that 290 * an address of the loopback interface is returned. 291 * 292 * @param host 293 * the hostName to be resolved to an address or {@code null}. 294 * @return the {@code InetAddress} instance representing the host. 295 * @throws UnknownHostException 296 * if the address lookup fails. 297 */ 298 public static InetAddress getByName(String host) throws UnknownHostException { 299 return getAllByNameImpl(host)[0]; 300 } 301 302 /** 303 * Returns the numeric representation of this IP address (such as "127.0.0.1"). 304 */ 305 public String getHostAddress() { 306 return Libcore.os.getnameinfo(this, NI_NUMERICHOST); // Can't throw. 307 } 308 309 /** 310 * Returns the host name corresponding to this IP address. This may or may not be a 311 * fully-qualified name. If the IP address could not be resolved, the numeric representation 312 * is returned instead (see {@link #getHostAddress}). 313 */ 314 public String getHostName() { 315 if (hostName == null) { 316 try { 317 hostName = getHostByAddrImpl(this).hostName; 318 } catch (UnknownHostException ex) { 319 hostName = getHostAddress(); 320 } 321 } 322 return hostName; 323 } 324 325 /** 326 * Returns the fully qualified hostname corresponding to this IP address. 327 */ 328 public String getCanonicalHostName() { 329 try { 330 return getHostByAddrImpl(this).hostName; 331 } catch (UnknownHostException ex) { 332 return getHostAddress(); 333 } 334 } 335 336 /** 337 * Returns an {@code InetAddress} for the local host if possible, or the 338 * loopback address otherwise. This method works by getting the hostname, 339 * performing a DNS lookup, and then taking the first returned address. 340 * For devices with multiple network interfaces and/or multiple addresses 341 * per interface, this does not necessarily return the {@code InetAddress} 342 * you want. 343 * 344 * <p>Multiple interface/address configurations were relatively rare 345 * when this API was designed, but multiple interfaces are the default for 346 * modern mobile devices (with separate wifi and radio interfaces), and 347 * the need to support both IPv4 and IPv6 has made multiple addresses 348 * commonplace. New code should thus avoid this method except where it's 349 * basically being used to get a loopback address or equivalent. 350 * 351 * <p>There are two main ways to get a more specific answer: 352 * <ul> 353 * <li>If you have a connected socket, you should probably use 354 * {@link Socket#getLocalAddress} instead: that will give you the address 355 * that's actually in use for that connection. (It's not possible to ask 356 * the question "what local address would a connection to a given remote 357 * address use?"; you have to actually make the connection and see.)</li> 358 * <li>For other use cases, see {@link NetworkInterface}, which lets you 359 * enumerate all available network interfaces and their addresses.</li> 360 * </ul> 361 * 362 * <p>Note that if the host doesn't have a hostname set – as 363 * Android devices typically don't – this method will 364 * effectively return the loopback address, albeit by getting the name 365 * {@code localhost} and then doing a lookup to translate that to 366 * {@code 127.0.0.1}. 367 * 368 * @return an {@code InetAddress} representing the local host, or the 369 * loopback address. 370 * @throws UnknownHostException 371 * if the address lookup fails. 372 */ 373 public static InetAddress getLocalHost() throws UnknownHostException { 374 String host = Libcore.os.uname().nodename; 375 return lookupHostByName(host)[0]; 376 } 377 378 /** 379 * Gets the hashcode of the represented IP address. 380 * 381 * @return the appropriate hashcode value. 382 */ 383 @Override 384 public int hashCode() { 385 return Arrays.hashCode(ipaddress); 386 } 387 388 /** 389 * Resolves a hostname to its IP addresses using a cache. 390 * 391 * @param host the hostname to resolve. 392 * @return the IP addresses of the host. 393 */ 394 private static InetAddress[] lookupHostByName(String host) throws UnknownHostException { 395 BlockGuard.getThreadPolicy().onNetwork(); 396 // Do we have a result cached? 397 Object cachedResult = addressCache.get(host); 398 if (cachedResult != null) { 399 if (cachedResult instanceof InetAddress[]) { 400 // A cached positive result. 401 return (InetAddress[]) cachedResult; 402 } else { 403 // A cached negative result. 404 throw new UnknownHostException((String) cachedResult); 405 } 406 } 407 try { 408 StructAddrinfo hints = new StructAddrinfo(); 409 hints.ai_flags = AI_ADDRCONFIG; 410 hints.ai_family = AF_UNSPEC; 411 // If we don't specify a socket type, every address will appear twice, once 412 // for SOCK_STREAM and one for SOCK_DGRAM. Since we do not return the family 413 // anyway, just pick one. 414 hints.ai_socktype = SOCK_STREAM; 415 InetAddress[] addresses = Libcore.os.getaddrinfo(host, hints); 416 // TODO: should getaddrinfo set the hostname of the InetAddresses it returns? 417 for (InetAddress address : addresses) { 418 address.hostName = host; 419 } 420 addressCache.put(host, addresses); 421 return addresses; 422 } catch (GaiException gaiException) { 423 // TODO: bionic currently returns EAI_NODATA, which is indistinguishable from a real 424 // failure. We need to fix bionic before we can report a more useful error. 425 // if (gaiException.error == EAI_SYSTEM) { 426 // throw new SecurityException("Permission denied (missing INTERNET permission?)"); 427 // } 428 String detailMessage = "Unable to resolve host \"" + host + "\": " + Libcore.os.gai_strerror(gaiException.error); 429 addressCache.putUnknownHost(host, detailMessage); 430 throw gaiException.rethrowAsUnknownHostException(detailMessage); 431 } 432 } 433 434 /** 435 * Removes all entries from the VM's DNS cache. This does not affect the C library's DNS 436 * cache, nor any caching DNS servers between you and the canonical server. 437 * @hide 438 */ 439 public static void clearDnsCache() { 440 addressCache.clear(); 441 } 442 443 private static InetAddress getHostByAddrImpl(InetAddress address) throws UnknownHostException { 444 BlockGuard.getThreadPolicy().onNetwork(); 445 try { 446 String hostname = Libcore.os.getnameinfo(address, NI_NAMEREQD); 447 return makeInetAddress(address.ipaddress.clone(), hostname); 448 } catch (GaiException gaiException) { 449 throw gaiException.rethrowAsUnknownHostException(); 450 } 451 } 452 453 /** 454 * Returns a string containing a concise, human-readable description of this 455 * IP address. 456 * 457 * @return the description, as host/address. 458 */ 459 @Override 460 public String toString() { 461 return (hostName == null ? "" : hostName) + "/" + getHostAddress(); 462 } 463 464 /** 465 * Returns true if the string is a valid numeric IPv4 or IPv6 address (such as "192.168.0.1"). 466 * This copes with all forms of address that Java supports, detailed in the {@link InetAddress} 467 * class documentation. 468 * 469 * @hide used by frameworks/base to ensure that a getAllByName won't cause a DNS lookup. 470 */ 471 public static boolean isNumeric(String address) { 472 InetAddress inetAddress = parseNumericAddressNoThrow(address); 473 return inetAddress != null && disallowDeprecatedFormats(address, inetAddress) != null; 474 } 475 476 /** 477 * Returns an InetAddress corresponding to the given numeric address (such 478 * as {@code "192.168.0.1"} or {@code "2001:4860:800d::68"}). 479 * This method will never do a DNS lookup. Non-numeric addresses are errors. 480 * 481 * @hide used by frameworks/base's NetworkUtils.numericToInetAddress 482 * @throws IllegalArgumentException if {@code numericAddress} is not a numeric address 483 */ 484 public static InetAddress parseNumericAddress(String numericAddress) { 485 if (numericAddress == null || numericAddress.isEmpty()) { 486 return Inet6Address.LOOPBACK; 487 } 488 InetAddress result = parseNumericAddressNoThrow(numericAddress); 489 result = disallowDeprecatedFormats(numericAddress, result); 490 if (result == null) { 491 throw new IllegalArgumentException("Not a numeric address: " + numericAddress); 492 } 493 return result; 494 } 495 496 private static InetAddress[] loopbackAddresses() { 497 return new InetAddress[] { Inet6Address.LOOPBACK, Inet4Address.LOOPBACK }; 498 } 499 500 /** 501 * Returns the IPv6 loopback address {@code ::1} or the IPv4 loopback address {@code 127.0.0.1}. 502 * @since 1.7 503 * @hide 1.7 504 */ 505 public static InetAddress getLoopbackAddress() { 506 return Inet6Address.LOOPBACK; 507 } 508 509 /** 510 * Returns whether this is the IPv6 unspecified wildcard address {@code ::} 511 * or the IPv4 "any" address, {@code 0.0.0.0}. 512 */ 513 public boolean isAnyLocalAddress() { 514 return false; 515 } 516 517 /** 518 * Returns whether this address is a link-local address or not. 519 * 520 * <p>Valid Ipv6 link-local addresses have the prefix {@code fe80::/10}. 521 * 522 * <p><a href="http://www.ietf.org/rfc/rfc3484.txt">RFC 3484</a> 523 * "Default Address Selection for Internet Protocol Version 6 (IPv6)" states 524 * that both IPv4 auto-configuration addresses (prefix {@code 169.254/16}) and 525 * IPv4 loopback addresses (prefix {@code 127/8}) have link-local scope, but 526 * {@link Inet4Address} only considers the auto-configuration addresses 527 * to have link-local scope. That is: the IPv4 loopback address returns false. 528 */ 529 public boolean isLinkLocalAddress() { 530 return false; 531 } 532 533 /** 534 * Returns whether this address is a loopback address or not. 535 * 536 * <p>Valid IPv4 loopback addresses have the prefix {@code 127/8}. 537 * 538 * <p>The only valid IPv6 loopback address is {@code ::1}. 539 */ 540 public boolean isLoopbackAddress() { 541 return false; 542 } 543 544 /** 545 * Returns whether this address is a global multicast address or not. 546 * 547 * <p>Valid IPv6 global multicast addresses have the prefix {@code ffxe::/16}, 548 * where {@code x} is a set of flags and the additional 112 bits make 549 * up the global multicast address space. 550 * 551 * <p>Valid IPv4 global multicast addresses are the range of addresses 552 * from {@code 224.0.1.0} to {@code 238.255.255.255}. 553 */ 554 public boolean isMCGlobal() { 555 return false; 556 } 557 558 /** 559 * Returns whether this address is a link-local multicast address or not. 560 * 561 * <p>Valid IPv6 link-local multicast addresses have the prefix {@code ffx2::/16}, 562 * where x is a set of flags and the additional 112 bits make up the link-local multicast 563 * address space. 564 * 565 * <p>Valid IPv4 link-local multicast addresses have the prefix {@code 224.0.0/24}. 566 */ 567 public boolean isMCLinkLocal() { 568 return false; 569 } 570 571 /** 572 * Returns whether this address is a node-local multicast address or not. 573 * 574 * <p>Valid IPv6 node-local multicast addresses have the prefix {@code ffx1::/16}, 575 * where x is a set of flags and the additional 112 bits make up the link-local multicast 576 * address space. 577 * 578 * <p>There are no valid IPv4 node-local multicast addresses. 579 */ 580 public boolean isMCNodeLocal() { 581 return false; 582 } 583 584 /** 585 * Returns whether this address is a organization-local multicast address or not. 586 * 587 * <p>Valid IPv6 organization-local multicast addresses have the prefix {@code ffx8::/16}, 588 * where x is a set of flags and the additional 112 bits make up the link-local multicast 589 * address space. 590 * 591 * <p>Valid IPv4 organization-local multicast addresses have the prefix {@code 239.192/14}. 592 */ 593 public boolean isMCOrgLocal() { 594 return false; 595 } 596 597 /** 598 * Returns whether this address is a site-local multicast address or not. 599 * 600 * <p>Valid IPv6 site-local multicast addresses have the prefix {@code ffx5::/16}, 601 * where x is a set of flags and the additional 112 bits make up the link-local multicast 602 * address space. 603 * 604 * <p>Valid IPv4 site-local multicast addresses have the prefix {@code 239.255/16}. 605 */ 606 public boolean isMCSiteLocal() { 607 return false; 608 } 609 610 /** 611 * Returns whether this address is a multicast address or not. 612 * 613 * <p>Valid IPv6 multicast addresses have the prefix {@code ff::/8}. 614 * 615 * <p>Valid IPv4 multicast addresses have the prefix {@code 224/4}. 616 */ 617 public boolean isMulticastAddress() { 618 return false; 619 } 620 621 /** 622 * Returns whether this address is a site-local address or not. 623 * 624 * <p>For the purposes of this method, valid IPv6 site-local addresses have 625 * the deprecated prefix {@code fec0::/10} from 626 * <a href="http://www.ietf.org/rfc/rfc1884.txt">RFC 1884</a>, 627 * <i>not</i> the modern prefix {@code fc00::/7} from 628 * <a href="http://www.ietf.org/rfc/rfc4193.txt">RFC 4193</a>. 629 * 630 * <p><a href="http://www.ietf.org/rfc/rfc3484.txt">RFC 3484</a> 631 * "Default Address Selection for Internet Protocol Version 6 (IPv6)" states 632 * that IPv4 private addresses have the prefix {@code 10/8}, {@code 172.16/12}, 633 * or {@code 192.168/16}. 634 * 635 * @return {@code true} if this instance represents a site-local address, 636 * {@code false} otherwise. 637 */ 638 public boolean isSiteLocalAddress() { 639 return false; 640 } 641 642 /** 643 * Tries to reach this {@code InetAddress}. This method first tries to use 644 * ICMP <i>(ICMP ECHO REQUEST)</i>. When first step fails, a TCP connection 645 * on port 7 (Echo) of the remote host is established. 646 * 647 * @param timeout 648 * timeout in milliseconds before the test fails if no connection 649 * could be established. 650 * @return {@code true} if this address is reachable, {@code false} 651 * otherwise. 652 * @throws IOException 653 * if an error occurs during an I/O operation. 654 * @throws IllegalArgumentException 655 * if timeout is less than zero. 656 */ 657 public boolean isReachable(int timeout) throws IOException { 658 return isReachable(null, 0, timeout); 659 } 660 661 /** 662 * Tries to reach this {@code InetAddress}. This method first tries to use 663 * ICMP <i>(ICMP ECHO REQUEST)</i>. When first step fails, a TCP connection 664 * on port 7 (Echo) of the remote host is established. 665 * 666 * @param networkInterface 667 * the network interface on which to connection should be 668 * established. 669 * @param ttl 670 * the maximum count of hops (time-to-live). 671 * @param timeout 672 * timeout in milliseconds before the test fails if no connection 673 * could be established. 674 * @return {@code true} if this address is reachable, {@code false} 675 * otherwise. 676 * @throws IOException 677 * if an error occurs during an I/O operation. 678 * @throws IllegalArgumentException 679 * if ttl or timeout is less than zero. 680 */ 681 public boolean isReachable(NetworkInterface networkInterface, final int ttl, 682 final int timeout) throws IOException { 683 if (ttl < 0 || timeout < 0) { 684 throw new IllegalArgumentException("ttl < 0 || timeout < 0"); 685 } 686 if (networkInterface == null) { 687 return isReachableByTCP(this, null, timeout); 688 } else { 689 return isReachableByMultiThread(networkInterface, ttl, timeout); 690 } 691 } 692 693 /* 694 * Uses multi-Thread to try if isReachable, returns true if any of threads 695 * returns in time 696 */ 697 private boolean isReachableByMultiThread(NetworkInterface netif, 698 final int ttl, final int timeout) 699 throws IOException { 700 List<InetAddress> addresses = Collections.list(netif.getInetAddresses()); 701 if (addresses.isEmpty()) { 702 return false; 703 } 704 reached = false; 705 addrCount = addresses.size(); 706 boolean needWait = false; 707 for (final InetAddress addr : addresses) { 708 // loopback interface can only reach to local addresses 709 if (addr.isLoopbackAddress()) { 710 Enumeration<NetworkInterface> NetworkInterfaces = NetworkInterface 711 .getNetworkInterfaces(); 712 while (NetworkInterfaces.hasMoreElements()) { 713 NetworkInterface networkInterface = NetworkInterfaces 714 .nextElement(); 715 Enumeration<InetAddress> localAddresses = networkInterface 716 .getInetAddresses(); 717 while (localAddresses.hasMoreElements()) { 718 if (InetAddress.this.equals(localAddresses 719 .nextElement())) { 720 return true; 721 } 722 } 723 } 724 725 synchronized (waitReachable) { 726 addrCount--; 727 728 if (addrCount == 0) { 729 // if count equals zero, all thread 730 // expired,notifies main thread 731 waitReachable.notifyAll(); 732 } 733 } 734 continue; 735 } 736 737 needWait = true; 738 new Thread() { 739 @Override public void run() { 740 /* 741 * Spec violation! This implementation doesn't attempt an 742 * ICMP; it skips right to TCP echo. 743 */ 744 boolean threadReached = false; 745 try { 746 threadReached = isReachableByTCP(addr, InetAddress.this, timeout); 747 } catch (IOException e) { 748 } 749 750 synchronized (waitReachable) { 751 if (threadReached) { 752 // if thread reached this address, sets reached to 753 // true and notifies main thread 754 reached = true; 755 waitReachable.notifyAll(); 756 } else { 757 addrCount--; 758 if (addrCount == 0) { 759 // if count equals zero, all thread 760 // expired,notifies main thread 761 waitReachable.notifyAll(); 762 } 763 } 764 } 765 } 766 }.start(); 767 } 768 769 if (needWait) { 770 synchronized (waitReachable) { 771 try { 772 while (!reached && (addrCount != 0)) { 773 // wait for notification 774 waitReachable.wait(1000); 775 } 776 } catch (InterruptedException e) { 777 // do nothing 778 } 779 return reached; 780 } 781 } 782 783 return false; 784 } 785 786 private boolean isReachableByTCP(InetAddress destination, InetAddress source, int timeout) throws IOException { 787 FileDescriptor fd = IoBridge.socket(true); 788 boolean reached = false; 789 try { 790 if (source != null) { 791 IoBridge.bind(fd, source, 0); 792 } 793 IoBridge.connect(fd, destination, 7, timeout); 794 reached = true; 795 } catch (IOException e) { 796 if (e.getCause() instanceof ErrnoException) { 797 // "Connection refused" means the IP address was reachable. 798 reached = (((ErrnoException) e.getCause()).errno == ECONNREFUSED); 799 } 800 } 801 802 IoBridge.closeSocket(fd); 803 804 return reached; 805 } 806 807 /** 808 * Equivalent to {@code getByAddress(null, ipAddress)}. Handy for addresses with 809 * no associated hostname. 810 */ 811 public static InetAddress getByAddress(byte[] ipAddress) throws UnknownHostException { 812 return getByAddress(null, ipAddress, 0); 813 } 814 815 /** 816 * Returns an {@code InetAddress} corresponding to the given network-order 817 * bytes {@code ipAddress} and {@code scopeId}. 818 * 819 * <p>For an IPv4 address, the byte array must be of length 4. 820 * For IPv6, the byte array must be of length 16. Any other length will cause an {@code 821 * UnknownHostException}. 822 * 823 * <p>No reverse lookup is performed. The given {@code hostName} (which may be null) is 824 * associated with the new {@code InetAddress} with no validation done. 825 * 826 * <p>(Note that numeric addresses such as {@code "127.0.0.1"} are names for the 827 * purposes of this API. Most callers probably want {@link #getAllByName} instead.) 828 * 829 * @throws UnknownHostException if {@code ipAddress} is null or the wrong length. 830 */ 831 public static InetAddress getByAddress(String hostName, byte[] ipAddress) throws UnknownHostException { 832 return getByAddress(hostName, ipAddress, 0); 833 } 834 835 private static InetAddress getByAddress(String hostName, byte[] ipAddress, int scopeId) throws UnknownHostException { 836 if (ipAddress == null) { 837 throw new UnknownHostException("ipAddress == null"); 838 } 839 if (ipAddress.length == 4) { 840 return new Inet4Address(ipAddress.clone(), hostName); 841 } else if (ipAddress.length == 16) { 842 // First check to see if the address is an IPv6-mapped 843 // IPv4 address. If it is, then we can make it a IPv4 844 // address, otherwise, we'll create an IPv6 address. 845 if (isIPv4MappedAddress(ipAddress)) { 846 return new Inet4Address(ipv4MappedToIPv4(ipAddress), hostName); 847 } else { 848 return new Inet6Address(ipAddress.clone(), hostName, scopeId); 849 } 850 } else { 851 throw badAddressLength(ipAddress); 852 } 853 } 854 855 private static UnknownHostException badAddressLength(byte[] bytes) throws UnknownHostException { 856 throw new UnknownHostException("Address is neither 4 or 16 bytes: " + Arrays.toString(bytes)); 857 } 858 859 private static boolean isIPv4MappedAddress(byte[] ipAddress) { 860 // Check if the address matches ::FFFF:d.d.d.d 861 // The first 10 bytes are 0. The next to are -1 (FF). 862 // The last 4 bytes are varied. 863 if (ipAddress == null || ipAddress.length != 16) { 864 return false; 865 } 866 for (int i = 0; i < 10; i++) { 867 if (ipAddress[i] != 0) { 868 return false; 869 } 870 } 871 if (ipAddress[10] != -1 || ipAddress[11] != -1) { 872 return false; 873 } 874 return true; 875 } 876 877 private static byte[] ipv4MappedToIPv4(byte[] mappedAddress) { 878 byte[] ipv4Address = new byte[4]; 879 for (int i = 0; i < 4; i++) { 880 ipv4Address[i] = mappedAddress[12 + i]; 881 } 882 return ipv4Address; 883 } 884 885 private static final ObjectStreamField[] serialPersistentFields = { 886 new ObjectStreamField("address", int.class), 887 new ObjectStreamField("family", int.class), 888 new ObjectStreamField("hostName", String.class), 889 }; 890 891 private void writeObject(ObjectOutputStream stream) throws IOException { 892 ObjectOutputStream.PutField fields = stream.putFields(); 893 if (ipaddress == null) { 894 fields.put("address", 0); 895 } else { 896 fields.put("address", Memory.peekInt(ipaddress, 0, ByteOrder.BIG_ENDIAN)); 897 } 898 fields.put("family", family); 899 fields.put("hostName", hostName); 900 901 stream.writeFields(); 902 } 903 904 private void readObject(ObjectInputStream stream) throws IOException, ClassNotFoundException { 905 ObjectInputStream.GetField fields = stream.readFields(); 906 int addr = fields.get("address", 0); 907 ipaddress = new byte[4]; 908 Memory.pokeInt(ipaddress, 0, addr, ByteOrder.BIG_ENDIAN); 909 hostName = (String) fields.get("hostName", null); 910 family = fields.get("family", 2); 911 } 912 913 /* 914 * The spec requires that if we encounter a generic InetAddress in 915 * serialized form then we should interpret it as an Inet4Address. 916 */ 917 private Object readResolve() throws ObjectStreamException { 918 return new Inet4Address(ipaddress, hostName); 919 } 920} 921