Inet6AddressImpl.c revision 3877
2362N/A * Copyright (c) 2000, 2008, Oracle and/or its affiliates. All rights reserved. 2115N/A * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 2115N/A * This code is free software; you can redistribute it and/or modify it 2115N/A * under the terms of the GNU General Public License version 2 only, as 2115N/A * published by the Free Software Foundation. Oracle designates this 2115N/A * particular file as subject to the "Classpath" exception as provided 2115N/A * by Oracle in the LICENSE file that accompanied this code. 2115N/A * This code is distributed in the hope that it will be useful, but WITHOUT 2115N/A * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 2115N/A * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 2115N/A * version 2 for more details (a copy is included in the LICENSE file that 2115N/A * You should have received a copy of the GNU General Public License version 2115N/A * 2 along with this work; if not, write to the Free Software Foundation, 2362N/A * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. 2362N/A * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA 2115N/A/* Retain this code a little longer to support building in 2115N/A * old environments. _MSC_VER is defined as: 2115N/A * Class: java_net_Inet6AddressImpl 2115N/A /* get the address preference */ 2115N/A /* Try once, with our static buffer. */ for (t = 0; t <
16; t++) {
/* we can't handle other family types */ /* we may have memory to free at the end of this */ if (
scope != 0) {
/* zero is default value, no need to set */ * Class: java_net_Inet6AddressImpl * For IPv4 addresses construct a sockaddr_in structure. * For IPv6 address construct a sockaddr_in6 structure. * Send a ICMP_ECHO_REQUEST packet every second until either the timeout * expires or a answer is received. * Returns true is an ECHO_REPLY is received, otherwise, false. /* Initialize the sequence number to a suitable random number and shift right one place to allow sufficient room for increamenting. */ seq = ((
unsigned short)
rand()) >>
1;
/* icmp_id is a 16 bit data type, therefore down cast the pid */ * A TTL was specified, let's set the socket option. * A network interface was specified, let's bind to it. * Make the socket non blocking * send 1 ICMP REQUEST every second until either we get a valid reply * or the timeout expired. /* let's tag the ECHO packet with our pid so we can identify it */ * We shouldn't have to do that as computing the checksum is supposed * to be done by the IPv6 stack. Unfortunately windows, here too, is * uterly broken, or non compliant, so let's do it. * Problem is to compute the checksum I need to know the source address * which happens only if I know the interface to be used... // Happens when using a "tunnel interface" for instance. // Or trying to send a packet on a different scope. * For some unknown reason, besides plain stupidity, windows * truncates the first 4 bytes of the icmpv6 header some we can't * check for the ICMP_ECHOREPLY value. * we'll check the other values, though * Is that the reply we were expecting? * Class: java_net_Inet6AddressImpl * If IPv6 is not enable, then we can't reach an IPv6 address, can we? * Actually, we probably shouldn't even get here. * If it's an IPv4 address, ICMP won't work with IPv4 mapped address, * therefore, let's delegate to the Inet4Address method. * A network interface was specified, let's convert the address * Windows implementation of ICMP & RAW sockets is too unreliable for now. * Therefore it's best not to try it at all and rely only on TCP * We may revisit and enable this code in the future. * Right now, windows doesn't generate the ICMP checksum automatically * so we have to compute it, but we can do it only if we know which * interface will be used. Therefore, don't try to use ICMP if no * interface was specified. * When ICMPv6 support improves in windows, we may change this. * If we can create a RAW socket, then when can use the ICMP ECHO_REQUEST * otherwise we'll try a tcp socket to the Echo port (7). * Note that this is empiric, and not connecting could mean it's blocked * or the echo servioe has been disabled. if (
fd != -
1) {
/* Good to go, let's do a ping */ /* No good, let's fall back on TCP */ /* note: if you run out of fds, you may not be able to load * the exception class, and get a NoClassDefFoundError * A TTL was specified, let's set the socket option. * A network interface was specified, let's bind to it. * Make the socket non blocking. /* no need to use NET_Connect as non-blocking */ * connection established or refused immediately, either way it means * we were able to reach the host! /* has connection been established? */