JDK-4065037 : Cache maintained by InetAddress.getByName() is defeated by dynamic IP addresses
  • Type: Bug
  • Component: core-libs
  • Sub-Component: java.net
  • Affected Version: 1.1,1.1.1,1.1.3,1.1.4,1.1.5,1.2.0
  • Priority: P3
  • Status: Closed
  • Resolution: Fixed
  • OS:
    generic,solaris_2.5.1,solaris_2.6,windows_95,windows_nt generic,solaris_2.5.1,solaris_2.6,windows_95,windows_nt
  • CPU: generic,x86,sparc
  • Submitted: 1997-07-16
  • Updated: 1999-01-15
  • Resolved: 1999-01-15
The Version table provides details related to the release that this issue/RFE will be addressed.

Unresolved : Release in which this issue/RFE will be addressed.
Resolved: Release in which this issue/RFE has been resolved.
Fixed : Release in which this issue/RFE has been fixed. The release containing this fix may be available for download as an Early Access Release or a General Availability Release.

To download the current JDK release, click here.
Other
1.2.0 1.2beta4Fixed
Related Reports
Duplicate :  
Relates :  
Description

Name: tb29552			Date: 07/16/97

Reported by:
company - Datametrics Systems Corp. , email - ###@###.###

InetAddress.getByName() has a severe BUG.

I have a friend whose IP address changes on a regular basis. 
I have a JAVA program that looks him up by name and we establish
a connection.  The problem is that once his IP address changes, I
can no longer connect to him!

Looking at the InetAddress source code the problem is obvious.
The code is maintaining a cache of name to address translations.
This seems very, very stupid considering that I am running a JAVA
application (not an applet), that should be trusted.  How can this be fixed?

On a side note, there is a comment in this code that reads:
  * Do not purge cache of numerical IP addresses, since
  * duplicate dynamic DNS name lookups can leave the system
  * vulnerable to hostname spoofing attacks.  Once a hostname
  * has been looked up in DNS and entered into the Java cache,
  * from then on, the hostname is translated to IP address only
  * via the cache.

While I do not know how spoofing works, if I take this comment at face value,
the cache does not work as advertised.  The cache allows upper/ lower case
variations of the same name to be passed through.  For example,
jerryj.datametrics.com has 1,048,576 names that the cache would
not filter out and pass through (for example, Jerryj.datametrics.com is one
of them and so is jerryj.datametRics.com).  Doesn't this again open up spoofing?

Anyway, how is JAVA going to deal with dynamic IP addresses!

- Jerry
company - Datametrics Systems Corp. , email - ###@###.###
======================================================================


roger.lewis@Eng 1997-08-05

InetAddress holds its own cache for DNS names,
and will never resolve again a given name. 
The rationale (comment in the 1.1.3 source) is 
that its "to prevent hostname spoofing". 

This  however will break round-robin load-balancing
DNS systems. 
It is also unacceptable for servers which 
might live longer than a DNS name (that is, 
it is quite possible a hostname will change 
its name, and a server will need to access it 
in its new address.
==========================================================================
InetAddress maintains an internal cache of hosts
which are unknown. This can cause problems if a
network connection is temporarily down when an
initial by-name host lookup 
(InetAddress.getByName()) fails. If the network 
connection comes back up, then subsequent by-name
lookups of that host will continue to fail even
though the remote host has become accessible.

Ideally, I'd like to have a public method on 
InetAddress that allows me to remove a particular
host name from this cache. Failing that, a method
that allows me to turn caching off or to flush
the cache before I call InetAddress.getByName()
would solve the problem.
================================================================

Additional comment by 
company - Cyclone Software Corporation , email - ###@###.###

I feel this is very wrong. In our application, our customers
will have the loopback IP address of 127.0.0.1 *before* they
dial in to their ISP and then to have a *new* (dynamically
assigned) IP address after they have dialed in. The way the
InetAddress code is currently written the IP address is always
returned as 127.0.0.1--even after they've dialed into the ISP
and are assigned a new IP address--there are no "funny games"
being played here as suggetsed by the code comments.

Please change getLocalHost () so that it always reflects the
most current IP address.

==============================================================

Another major licensee has complained about caching unknown
addresses just because they can't be resolved at the time.
They have an application where the remote client starts 
at boot time, and runs in the background. 
   They try to resolve the server name using getByName and if this
fails due to a name unrecognised by the DNS an 'unknown host
exception' is thrown. However, if they are not connected to the
network they get the same error! Since the app 'knows' the name is
a valid name they take this to mean the network is down and they
try again after an elapsed period of time. However an 'unknown
address' value has already been cached and is always returned from
that point on. 
Mick
  
======================================================================

Comments
CONVERTED DATA BugTraq+ Release Management Values COMMIT TO FIX: 1.2fcs FIXED IN: 1.2beta4 INTEGRATED IN: 1.2beta4
14-06-2004

EVALUATION In 1.2 we have introduce the java.net.namelookup.cache property, which controls the namelookup caching policy. benjamin.renaud@Eng 1998-04-28 In 1.3 someone decided to change the property to sun.net.inetaddr.ttl : sun.net.InetAddressCachePolicy utilizes the property "sun.net.inetaddr.ttl" to specify the "cachePolicyProp". No setting (or a value of -1) indicates "FOREVER." A positive value indicates the number of seconds to cache an address for. Running the test case as is but setting this property to one second, and changing /etc/hosts between lookups works fine : Java(TM) 2 Runtime Environment, Standard Edition (build Solaris_JDK_1.3-b25_NIGHTLY_2000.07.31) rx7 266 =>java -Dsun.net.inetaddr.ttl=1 test Enter the hostname rrr Output isrrr/129.145.146.100 Enter the hostname rrr Output isrrr/129.147.146.100
11-06-2004

SUGGESTED FIX One of the licensees has suggested the following fix, however it only solves the problem caused by the caching of the unknown address. I'll put it in, as it would at-least solve some of the problems. Suggested fix is in the getAllByName0 method in InetAddress.java; /* If no entry in cache, then do the host lookup */ // if (obj == null) { /* CHANGE THIS LINE TO THE ONE BELOW! */ if ((obj == null) || (obj == unknown_array) { try { /* * Do not put the call to lookup() inside the * constructor. if you do you will still be
11-06-2004