1adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project/* 2adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project * Licensed to the Apache Software Foundation (ASF) under one or more 3adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project * contributor license agreements. See the NOTICE file distributed with 4adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project * this work for additional information regarding copyright ownership. 5adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project * The ASF licenses this file to You under the Apache License, Version 2.0 6adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project * (the "License"); you may not use this file except in compliance with 7adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project * the License. You may obtain a copy of the License at 8adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project * 9adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project * http://www.apache.org/licenses/LICENSE-2.0 10adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project * 11adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project * Unless required by applicable law or agreed to in writing, software 12adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project * distributed under the License is distributed on an "AS IS" BASIS, 13adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 14adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project * See the License for the specific language governing permissions and 15adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project * limitations under the License. 16adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project */ 17adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project 18adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Projectpackage java.net; 19adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project 20adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Projectimport java.io.IOException; 21adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Projectimport java.io.ObjectInputStream; 22adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Projectimport java.io.ObjectOutputStream; 23adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Projectimport java.io.ObjectStreamField; 24fbbae9740d65620b417b85576aa0d6c7daf4ba34Elliott Hughesimport java.util.Arrays; 25adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Projectimport java.util.Enumeration; 2632b0fa4d1a31ef07bc4297c615f0fe50e9aa7c21Elliott Hughesimport static libcore.io.OsConstants.*; 27adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project 28adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project/** 294adff24306c86433ce4f771da8489a574e63318eElliott Hughes * An IPv6 address. See {@link InetAddress}. 30adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project */ 31adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Projectpublic final class Inet6Address extends InetAddress { 32adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project 33adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project private static final long serialVersionUID = 6880410070516793377L; 34adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project 354f11ebea266eada830d507b8f011e811a8e5d7bcElliott Hughes /** 364f11ebea266eada830d507b8f011e811a8e5d7bcElliott Hughes * @hide 374f11ebea266eada830d507b8f011e811a8e5d7bcElliott Hughes */ 384f11ebea266eada830d507b8f011e811a8e5d7bcElliott Hughes public static final InetAddress ANY = 39fbbae9740d65620b417b85576aa0d6c7daf4ba34Elliott Hughes new Inet6Address(new byte[] {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }, null, 0); 404f11ebea266eada830d507b8f011e811a8e5d7bcElliott Hughes 414f11ebea266eada830d507b8f011e811a8e5d7bcElliott Hughes /** 424f11ebea266eada830d507b8f011e811a8e5d7bcElliott Hughes * @hide 434f11ebea266eada830d507b8f011e811a8e5d7bcElliott Hughes */ 444f11ebea266eada830d507b8f011e811a8e5d7bcElliott Hughes public static final InetAddress LOOPBACK = 45fbbae9740d65620b417b85576aa0d6c7daf4ba34Elliott Hughes new Inet6Address(new byte[] {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1 }, 46fbbae9740d65620b417b85576aa0d6c7daf4ba34Elliott Hughes "localhost", 0); 47adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project 48f02f9397fd5984f476e056ddb8c04db9af9a15a0Elliott Hughes private boolean scope_id_set; 49f02f9397fd5984f476e056ddb8c04db9af9a15a0Elliott Hughes private int scope_id; 50adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project 51f02f9397fd5984f476e056ddb8c04db9af9a15a0Elliott Hughes private boolean scope_ifname_set; 52f02f9397fd5984f476e056ddb8c04db9af9a15a0Elliott Hughes private String ifname; 53adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project 54adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project /** 55adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project * Constructs an {@code InetAddress} representing the {@code address} and 56adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project * {@code name} and {@code scope_id}. 57f33eae7e84eb6d3b0f4e86b59605bb3de73009f3Elliott Hughes * 58adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project * @param address 59adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project * the network address. 60adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project * @param name 61adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project * the name associated with the address. 62adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project * @param scope_id 63adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project * the scope id for link- or site-local addresses. 64adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project */ 654f11ebea266eada830d507b8f011e811a8e5d7bcElliott Hughes Inet6Address(byte[] ipaddress, String hostName, int scope_id) { 664f11ebea266eada830d507b8f011e811a8e5d7bcElliott Hughes super(AF_INET6, ipaddress, hostName); 67adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project this.scope_id = scope_id; 68fbbae9740d65620b417b85576aa0d6c7daf4ba34Elliott Hughes this.scope_id_set = (scope_id != 0); 69adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project } 70adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project 71adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project /** 72adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project * Constructs an IPv6 address according to the given {@code host}, {@code 73adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project * addr} and {@code scope_id}. 74f33eae7e84eb6d3b0f4e86b59605bb3de73009f3Elliott Hughes * 75adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project * @param host 76adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project * the host name associated with the address. 77adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project * @param addr 78adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project * the network address. 79adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project * @param scope_id 80adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project * the scope id for link- or site-local addresses. 81adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project * @return the Inet6Address instance representing the IP address. 82adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project * @throws UnknownHostException 83adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project * if the address is null or has an invalid length. 84adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project */ 85fbbae9740d65620b417b85576aa0d6c7daf4ba34Elliott Hughes public static Inet6Address getByAddress(String host, byte[] addr, int scope_id) 86fbbae9740d65620b417b85576aa0d6c7daf4ba34Elliott Hughes throws UnknownHostException { 87b1396870f92135aa140bd2b86221768dea5bc11dElliott Hughes if (addr == null || addr.length != 16) { 88fbbae9740d65620b417b85576aa0d6c7daf4ba34Elliott Hughes throw new UnknownHostException("Not an IPv6 address: " + Arrays.toString(addr)); 89adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project } 90adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project if (scope_id < 0) { 91adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project scope_id = 0; 92adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project } 93fbbae9740d65620b417b85576aa0d6c7daf4ba34Elliott Hughes // TODO: should we clone 'addr'? 94adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project return new Inet6Address(addr, host, scope_id); 95adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project } 96adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project 97adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project /** 98adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project * Gets an IPv6 address instance according to the given {@code host}, 99adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project * {@code addr} and {@code nif}. {@code scope_id} is set according to the 100adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project * given {@code nif} and the {@code addr} type (for example site-local or 101adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project * link-local). 102f33eae7e84eb6d3b0f4e86b59605bb3de73009f3Elliott Hughes * 103adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project * @param host 104adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project * the hostname associated with the address. 105adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project * @param addr 106adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project * the network address. 107adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project * @param nif 108adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project * the network interface that this address is associated with. 109adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project * @return the Inet6Address instance representing the IP address. 110adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project * @throws UnknownHostException 111adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project * if the address is {@code null} or has an invalid length or 112adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project * the interface doesn't have a numeric scope id for the given 113adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project * address type. 114adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project */ 115adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project public static Inet6Address getByAddress(String host, byte[] addr, 116adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project NetworkInterface nif) throws UnknownHostException { 117adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project 118adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project Inet6Address address = Inet6Address.getByAddress(host, addr, 0); 119adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project 120adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project // if nif is null, nothing needs to be set. 121b46dab348e2007bc08abaf7ecae34d89a2474e50Elliott Hughes if (nif == null) { 122adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project return address; 123adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project } 124adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project 125adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project // find the first address which matches the type addr, 126a37e971343883bb582a93ffbd9f0ba84f10e55baElliott Hughes // then set the scope_id and ifname. 127adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project Enumeration<InetAddress> addressList = nif.getInetAddresses(); 128adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project while (addressList.hasMoreElements()) { 129adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project InetAddress ia = addressList.nextElement(); 130adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project if (ia.getAddress().length == 16) { 131adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project Inet6Address v6ia = (Inet6Address) ia; 132adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project boolean isSameType = v6ia.compareLocalType(address); 133adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project if (isSameType) { 134adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project address.scope_id_set = true; 135adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project address.scope_id = v6ia.scope_id; 136adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project address.scope_ifname_set = true; 137adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project address.ifname = nif.getName(); 138adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project break; 139adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project } 140adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project } 141adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project } 142adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project // if no address matches the type of addr, throws an 143adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project // UnknownHostException. 144adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project if (!address.scope_id_set) { 145fbbae9740d65620b417b85576aa0d6c7daf4ba34Elliott Hughes throw new UnknownHostException("Scope id not found for address: " + Arrays.toString(addr)); 146adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project } 147adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project return address; 148adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project } 149adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project 150adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project /** 151adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project * Returns {@code true} if one of following cases applies: 152adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project * <p> 153f5597e626ecf7949d249dea08c1a2964d890ec11Jesse Wilson * <ol> 154f5597e626ecf7949d249dea08c1a2964d890ec11Jesse Wilson * <li>both addresses are site local</li> 155f5597e626ecf7949d249dea08c1a2964d890ec11Jesse Wilson * <li>both addresses are link local</li> 156f5597e626ecf7949d249dea08c1a2964d890ec11Jesse Wilson * <li>{@code ia} is neither site local nor link local</li> 157f5597e626ecf7949d249dea08c1a2964d890ec11Jesse Wilson * </ol> 158adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project */ 159adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project private boolean compareLocalType(Inet6Address ia) { 160adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project if (ia.isSiteLocalAddress() && isSiteLocalAddress()) { 161adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project return true; 162adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project } 163adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project if (ia.isLinkLocalAddress() && isLinkLocalAddress()) { 164adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project return true; 165adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project } 166adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project if (!ia.isSiteLocalAddress() && !ia.isLinkLocalAddress()) { 167adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project return true; 168adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project } 169adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project return false; 170adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project } 171adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project 172a37e971343883bb582a93ffbd9f0ba84f10e55baElliott Hughes @Override public boolean isAnyLocalAddress() { 173a37e971343883bb582a93ffbd9f0ba84f10e55baElliott Hughes return Arrays.equals(ipaddress, Inet6Address.ANY.ipaddress); 174adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project } 175adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project 176adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project /** 177a7428d68453f6a74633221e8714f8d3d9597b2b4Elliott Hughes * Returns whether this IPv6 address is an IPv4-compatible address or not. 178a7428d68453f6a74633221e8714f8d3d9597b2b4Elliott Hughes * An IPv4-compatible address has the prefix {@code ::/96} and is a deprecated 179a7428d68453f6a74633221e8714f8d3d9597b2b4Elliott Hughes * and no-longer used equivalent of the modern IPv4-mapped IPv6 addresses. 180adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project */ 181a7428d68453f6a74633221e8714f8d3d9597b2b4Elliott Hughes public boolean isIPv4CompatibleAddress() { 182a7428d68453f6a74633221e8714f8d3d9597b2b4Elliott Hughes for (int i = 0; i < 12; i++) { 183a7428d68453f6a74633221e8714f8d3d9597b2b4Elliott Hughes if (ipaddress[i] != 0) { 184a7428d68453f6a74633221e8714f8d3d9597b2b4Elliott Hughes return false; 185a7428d68453f6a74633221e8714f8d3d9597b2b4Elliott Hughes } 186a7428d68453f6a74633221e8714f8d3d9597b2b4Elliott Hughes } 187a7428d68453f6a74633221e8714f8d3d9597b2b4Elliott Hughes return true; 188adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project } 189adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project 190a37e971343883bb582a93ffbd9f0ba84f10e55baElliott Hughes @Override public boolean isLinkLocalAddress() { 191a7428d68453f6a74633221e8714f8d3d9597b2b4Elliott Hughes return ((ipaddress[0] & 0xff) == 0xfe) && ((ipaddress[1] & 0xc0) == 0x80); // fe80:/10 192adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project } 193adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project 194a7428d68453f6a74633221e8714f8d3d9597b2b4Elliott Hughes @Override public boolean isLoopbackAddress() { 195a7428d68453f6a74633221e8714f8d3d9597b2b4Elliott Hughes return Arrays.equals(ipaddress, Inet6Address.LOOPBACK.ipaddress); 196adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project } 197adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project 198a37e971343883bb582a93ffbd9f0ba84f10e55baElliott Hughes @Override public boolean isMCGlobal() { 199a7428d68453f6a74633221e8714f8d3d9597b2b4Elliott Hughes return ((ipaddress[0] & 0xff) == 0xff) && ((ipaddress[1] & 0x0f) == 0x0e); // ffxe:/16 200a7428d68453f6a74633221e8714f8d3d9597b2b4Elliott Hughes } 201a7428d68453f6a74633221e8714f8d3d9597b2b4Elliott Hughes 202a7428d68453f6a74633221e8714f8d3d9597b2b4Elliott Hughes @Override public boolean isMCLinkLocal() { 203a7428d68453f6a74633221e8714f8d3d9597b2b4Elliott Hughes return ((ipaddress[0] & 0xff) == 0xff) && ((ipaddress[1] & 0x0f) == 0x02); // ffx2:/16 204adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project } 205adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project 206a37e971343883bb582a93ffbd9f0ba84f10e55baElliott Hughes @Override public boolean isMCNodeLocal() { 207a7428d68453f6a74633221e8714f8d3d9597b2b4Elliott Hughes return ((ipaddress[0] & 0xff) == 0xff) && ((ipaddress[1] & 0x0f) == 0x01); // ffx1:/16 208adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project } 209adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project 210a7428d68453f6a74633221e8714f8d3d9597b2b4Elliott Hughes @Override public boolean isMCOrgLocal() { 211a7428d68453f6a74633221e8714f8d3d9597b2b4Elliott Hughes return ((ipaddress[0] & 0xff) == 0xff) && ((ipaddress[1] & 0x0f) == 0x08); // ffx8:/16 212adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project } 213adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project 214a37e971343883bb582a93ffbd9f0ba84f10e55baElliott Hughes @Override public boolean isMCSiteLocal() { 215a7428d68453f6a74633221e8714f8d3d9597b2b4Elliott Hughes return ((ipaddress[0] & 0xff) == 0xff) && ((ipaddress[1] & 0x0f) == 0x05); // ffx5:/16 216adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project } 217adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project 218a7428d68453f6a74633221e8714f8d3d9597b2b4Elliott Hughes @Override public boolean isMulticastAddress() { 219a7428d68453f6a74633221e8714f8d3d9597b2b4Elliott Hughes return ((ipaddress[0] & 0xff) == 0xff); // ff::/8 220a7428d68453f6a74633221e8714f8d3d9597b2b4Elliott Hughes } 221a7428d68453f6a74633221e8714f8d3d9597b2b4Elliott Hughes 222a7428d68453f6a74633221e8714f8d3d9597b2b4Elliott Hughes @Override public boolean isSiteLocalAddress() { 223a7428d68453f6a74633221e8714f8d3d9597b2b4Elliott Hughes return ((ipaddress[0] & 0xff) == 0xfe) && ((ipaddress[1] & 0xc0) == 0xc0); // fec0:/10 224adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project } 225adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project 226adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project /** 227a37e971343883bb582a93ffbd9f0ba84f10e55baElliott Hughes * Returns the scope id if this address is scoped to an interface, 0 otherwise. 228adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project */ 229adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project public int getScopeId() { 230a37e971343883bb582a93ffbd9f0ba84f10e55baElliott Hughes return scope_id_set ? scope_id : 0; 231adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project } 232adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project 233adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project /** 234a37e971343883bb582a93ffbd9f0ba84f10e55baElliott Hughes * Returns the network interface if this address is instanced with a scoped 235a37e971343883bb582a93ffbd9f0ba84f10e55baElliott Hughes * network interface, null otherwise. 236adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project */ 237adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project public NetworkInterface getScopedInterface() { 238a37e971343883bb582a93ffbd9f0ba84f10e55baElliott Hughes try { 239f02f9397fd5984f476e056ddb8c04db9af9a15a0Elliott Hughes return (scope_ifname_set && ifname != null) ? NetworkInterface.getByName(ifname) : null; 240a37e971343883bb582a93ffbd9f0ba84f10e55baElliott Hughes } catch (SocketException ex) { 241a37e971343883bb582a93ffbd9f0ba84f10e55baElliott Hughes return null; 242adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project } 243adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project } 244adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project 245adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project private static final ObjectStreamField[] serialPersistentFields = { 246e26ba79900d471d02d656f686926918ef7dc751fElliott Hughes new ObjectStreamField("ipaddress", byte[].class), 247e26ba79900d471d02d656f686926918ef7dc751fElliott Hughes new ObjectStreamField("scope_id", int.class), 248e26ba79900d471d02d656f686926918ef7dc751fElliott Hughes new ObjectStreamField("scope_id_set", boolean.class), 249e26ba79900d471d02d656f686926918ef7dc751fElliott Hughes new ObjectStreamField("scope_ifname_set", boolean.class), 25028eb98ecd43c27702e85b0561e040e2da10320a6Elliott Hughes new ObjectStreamField("ifname", String.class), 25128eb98ecd43c27702e85b0561e040e2da10320a6Elliott Hughes }; 252adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project 253adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project private void writeObject(ObjectOutputStream stream) throws IOException { 254adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project ObjectOutputStream.PutField fields = stream.putFields(); 255adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project if (ipaddress == null) { 256f33eae7e84eb6d3b0f4e86b59605bb3de73009f3Elliott Hughes fields.put("ipaddress", null); 257adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project } else { 258f33eae7e84eb6d3b0f4e86b59605bb3de73009f3Elliott Hughes fields.put("ipaddress", ipaddress); 259adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project } 260adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project 261f33eae7e84eb6d3b0f4e86b59605bb3de73009f3Elliott Hughes fields.put("scope_id", scope_id); 262f33eae7e84eb6d3b0f4e86b59605bb3de73009f3Elliott Hughes fields.put("scope_id_set", scope_id_set); 263f33eae7e84eb6d3b0f4e86b59605bb3de73009f3Elliott Hughes fields.put("scope_ifname_set", scope_ifname_set); 264f33eae7e84eb6d3b0f4e86b59605bb3de73009f3Elliott Hughes fields.put("ifname", ifname); 265adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project stream.writeFields(); 266adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project } 267adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project 268a37e971343883bb582a93ffbd9f0ba84f10e55baElliott Hughes private void readObject(ObjectInputStream stream) throws IOException, ClassNotFoundException { 269adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project ObjectInputStream.GetField fields = stream.readFields(); 270f33eae7e84eb6d3b0f4e86b59605bb3de73009f3Elliott Hughes ipaddress = (byte[]) fields.get("ipaddress", null); 271f33eae7e84eb6d3b0f4e86b59605bb3de73009f3Elliott Hughes scope_id = fields.get("scope_id", 0); 272f33eae7e84eb6d3b0f4e86b59605bb3de73009f3Elliott Hughes scope_id_set = fields.get("scope_id_set", false); 273f33eae7e84eb6d3b0f4e86b59605bb3de73009f3Elliott Hughes ifname = (String) fields.get("ifname", null); 274f33eae7e84eb6d3b0f4e86b59605bb3de73009f3Elliott Hughes scope_ifname_set = fields.get("scope_ifname_set", false); 275adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project } 276adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project 277a37e971343883bb582a93ffbd9f0ba84f10e55baElliott Hughes @Override public String toString() { 278adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project if (ifname != null) { 279f33eae7e84eb6d3b0f4e86b59605bb3de73009f3Elliott Hughes return super.toString() + "%" + ifname; 280adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project } 281adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project if (scope_id != 0) { 282f33eae7e84eb6d3b0f4e86b59605bb3de73009f3Elliott Hughes return super.toString() + "%" + scope_id; 283adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project } 284adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project return super.toString(); 285adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project } 286adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project} 287