diff --git a/hadoop-common-project/hadoop-common/CHANGES.txt b/hadoop-common-project/hadoop-common/CHANGES.txt index 336737f0c2..3960abe922 100644 --- a/hadoop-common-project/hadoop-common/CHANGES.txt +++ b/hadoop-common-project/hadoop-common/CHANGES.txt @@ -19,6 +19,9 @@ Trunk (unreleased changes) HADOOP-7635. RetryInvocationHandler should release underlying resources on close (atm) + + HADOOP-7668. Add a NetUtils method that can tell if an InetAddress + belongs to local host. (suresh) BUGS diff --git a/hadoop-common-project/hadoop-common/src/main/java/org/apache/hadoop/net/NetUtils.java b/hadoop-common-project/hadoop-common/src/main/java/org/apache/hadoop/net/NetUtils.java index b22aaa009c..9b744ed3ee 100644 --- a/hadoop-common-project/hadoop-common/src/main/java/org/apache/hadoop/net/NetUtils.java +++ b/hadoop-common-project/hadoop-common/src/main/java/org/apache/hadoop/net/NetUtils.java @@ -516,4 +516,27 @@ public static InetAddress getLocalInetAddress(String host) } catch (UnknownHostException ignore) { } return addr; } + + /** + * Given an InetAddress, checks to see if the address is a local address, by + * comparing the address with all the interfaces on the node. + * @param addr address to check if it is local node's address + * @return true if the address corresponds to the local node + */ + public static boolean isLocalAddress(InetAddress addr) { + // Check if the address is any local or loop back + boolean local = addr.isAnyLocalAddress() || addr.isLoopbackAddress(); + System.out.println("address is any or loopback address " + addr); + + // Check if the address is defined on any interface + if (!local) { + try { + local = NetworkInterface.getByInetAddress(addr) != null; + } catch (SocketException e) { + local = false; + } + } + System.out.println("address " + addr + " is local " + local); + return local; + } } diff --git a/hadoop-common-project/hadoop-common/src/test/java/org/apache/hadoop/net/TestNetUtils.java b/hadoop-common-project/hadoop-common/src/test/java/org/apache/hadoop/net/TestNetUtils.java index f49d4c886e..7cc6f4d521 100644 --- a/hadoop-common-project/hadoop-common/src/test/java/org/apache/hadoop/net/TestNetUtils.java +++ b/hadoop-common-project/hadoop-common/src/test/java/org/apache/hadoop/net/TestNetUtils.java @@ -18,13 +18,17 @@ package org.apache.hadoop.net; import org.junit.Test; + import static org.junit.Assert.*; +import java.net.InetAddress; +import java.net.NetworkInterface; import java.net.Socket; import java.net.ConnectException; import java.net.SocketException; import java.net.InetSocketAddress; import java.net.UnknownHostException; +import java.util.Enumeration; import org.apache.hadoop.conf.Configuration; @@ -88,4 +92,32 @@ public void testVerifyHostnamesNoException() { fail("NetUtils.verifyHostnames threw unexpected UnknownHostException"); } } + + /** + * Test for {@link NetUtils#isLocalAddress(java.net.InetAddress)} + */ + @Test + public void testIsLocalAddress() throws Exception { + // Test - local host is local address + assertTrue(NetUtils.isLocalAddress(InetAddress.getLocalHost())); + + // Test - all addresses bound network interface is local address + Enumeration interfaces = NetworkInterface + .getNetworkInterfaces(); + if (interfaces != null) { // Iterate through all network interfaces + while (interfaces.hasMoreElements()) { + NetworkInterface i = interfaces.nextElement(); + Enumeration addrs = i.getInetAddresses(); + if (addrs == null) { + continue; + } + // Iterate through all the addresses of a network interface + while (addrs.hasMoreElements()) { + InetAddress addr = addrs.nextElement(); + assertTrue(NetUtils.isLocalAddress(addr)); + } + } + } + assertFalse(NetUtils.isLocalAddress(InetAddress.getByName("8.8.8.8"))); + } }