8223737: Fix HostsFileNameService for IPv6 literal addresses
authoraeubanks
Fri, 10 May 2019 17:13:02 -0700
changeset 54883 4ee117b890c5
parent 54882 b99e97bc5040
child 54884 8a6093c186a6
8223737: Fix HostsFileNameService for IPv6 literal addresses Reviewed-by: chegar, msheppar Contributed-by: aeubanks@google.com
src/java.base/share/classes/java/net/InetAddress.java
test/jdk/java/net/InetAddress/InternalNameServiceWithHostsFileTest.java
--- a/src/java.base/share/classes/java/net/InetAddress.java	Wed May 15 08:58:23 2019 -0400
+++ b/src/java.base/share/classes/java/net/InetAddress.java	Fri May 10 17:13:02 2019 -0700
@@ -45,6 +45,7 @@
 import java.util.concurrent.ConcurrentMap;
 import java.util.concurrent.ConcurrentSkipListSet;
 import java.util.concurrent.atomic.AtomicLong;
+import java.util.Arrays;
 
 import jdk.internal.access.JavaNetInetAddressAccess;
 import jdk.internal.access.SharedSecrets;
@@ -989,29 +990,28 @@
             String hostEntry;
             String host = null;
 
-            String addrString = addrToString(addr);
             try (Scanner hostsFileScanner = new Scanner(new File(hostsFile), "UTF-8")) {
                 while (hostsFileScanner.hasNextLine()) {
                     hostEntry = hostsFileScanner.nextLine();
                     if (!hostEntry.startsWith("#")) {
                         hostEntry = removeComments(hostEntry);
-                        if (hostEntry.contains(addrString)) {
-                            host = extractHost(hostEntry, addrString);
-                            if (host != null) {
-                                break;
-                            }
+                        String[] mapping = hostEntry.split("\\s+");
+                        if (mapping.length >= 2 &&
+                            Arrays.equals(addr, createAddressByteArray(mapping[0]))) {
+                            host = mapping[1];
+                            break;
                         }
                     }
                 }
             } catch (FileNotFoundException e) {
                 throw new UnknownHostException("Unable to resolve address "
-                        + addrString + " as hosts file " + hostsFile
+                        + Arrays.toString(addr) + " as hosts file " + hostsFile
                         + " not found ");
             }
 
             if ((host == null) || (host.isEmpty()) || (host.equals(" "))) {
                 throw new UnknownHostException("Requested address "
-                        + addrString
+                        + Arrays.toString(addr)
                         + " resolves to an invalid entry in hosts file "
                         + hostsFile);
             }
@@ -1107,22 +1107,6 @@
             }
             return hostAddr;
         }
-
-        /**
-         * IP Address to host mapping
-         * use first host alias in list
-         */
-        private String extractHost(String hostEntry, String addrString) {
-            String[] mapping = hostEntry.split("\\s+");
-            String host = null;
-
-            if (mapping.length >= 2) {
-                if (mapping[0].equalsIgnoreCase(addrString)) {
-                    host = mapping[1];
-                }
-            }
-            return host;
-        }
     }
 
     static final InetAddressImpl  impl;
--- a/test/jdk/java/net/InetAddress/InternalNameServiceWithHostsFileTest.java	Wed May 15 08:58:23 2019 -0400
+++ b/test/jdk/java/net/InetAddress/InternalNameServiceWithHostsFileTest.java	Fri May 10 17:13:02 2019 -0700
@@ -56,19 +56,28 @@
         byte[] expectedIpv6LocalhostAddress = { 0, 0, 0, 0, 0, 0, 0,
                 0, 0, 0, 0, 0, 0, 0, 0, 1 };
 
-        try {
-            // 10.2.3.4  testHost.testDomain
-            testHostsMapping(expectedIpv4Address, "testHost.testDomain");
-            // ::1     ip6-localhost ip6-loopback
-            testHostsMapping(expectedIpv6LocalhostAddress, "ip6-localhost");
-            // fe00::0 ip6-localnet
-            testHostsMapping(expectedIpv6LocalAddress, "ip6-localnet");
-            // fe80::1 link-local-host
-            testHostsMapping(expectedIpv6Address, "link-local-host");
+        // 10.2.3.4  testHost.testDomain
+        testHostsMapping(expectedIpv4Address, "testHost.testDomain");
+        // ::1     ip6-localhost ip6-loopback
+        testHostsMapping(expectedIpv6LocalhostAddress, "ip6-localhost");
+        // fe00::0 ip6-localnet
+        testHostsMapping(expectedIpv6LocalAddress, "ip6-localnet");
+        // fe80::1 link-local-host
+        testHostsMapping(expectedIpv6Address, "link-local-host");
+
+        testReverseLookup("10.2.3.4", "testHost.testDomain");
 
-        } catch (UnknownHostException uhEx) {
-            System.out.println("UHE unexpected caught == " + uhEx.getMessage());
-        }
+        testReverseLookup("::1", "ip6-localhost");
+        testReverseLookup("0:0:0:0:0:0:0:1", "ip6-localhost");
+        testReverseLookup("0000:0000:0000:0000:0000:0000:0000:0001", "ip6-localhost");
+
+        testReverseLookup("fe00::0", "ip6-localnet");
+        testReverseLookup("fe00:0:0:0:0:0:0:0", "ip6-localnet");
+        testReverseLookup("fe00:0000:0000:0000:0000:0000:0000:0000", "ip6-localnet");
+
+        testReverseLookup("fe80::1", "link-local-host");
+        testReverseLookup("fe80:000:0:00:0:000:00:1", "link-local-host");
+        testReverseLookup("fe80:0000:0000:0000:0000:0000:0000:0001", "link-local-host");
     }
 
     private static void testHostsMapping(byte[] expectedIpAddress, String hostName)
@@ -94,4 +103,15 @@
                 + " equal to expected address == "
                 + Arrays.toString(expectedIpAddress));
     }
+
+    private static void testReverseLookup(String numericHost, String expectedName)
+            throws UnknownHostException {
+        String lookupResult = InetAddress.getByName(numericHost).getHostName();
+        if (!expectedName.equals(lookupResult)) {
+            throw new RuntimeException(
+                String.format(
+                    "reverse lookup of \"%s\" is \"%s\", should be \"%s\"\n",
+                    numericHost, lookupResult, expectedName));
+        }
+    }
 }