How to track down JAR with corrupt JAR Index that cause InvalidJarIndexException in Tomcat in Eclipse
I am working with development of an application which, among other pieces of code, contains a number of servlets. The development environment I use is Eclipse (3.2.1, which is rather old) in which I run a Tomcat server (5.5.23, rather old as well) using the Eclipse Tomcat Wrapper plug-in for the task. All this runs on a RedHat 5.2 Linux system.
The Java runtime I use is JDK 1.6.0(21), which I upgraded to (from a previous JDK 1.5 version) quite recently and as far as I can recall, the software combination above (together with the application I'm working with) did actually work: I could start the Tomcat server, it got up without errors or complaints and the application's servlets were available on port 8080.
However, something has changed somewhere (could be in the application jarfiles themselves, I'm suspicious of essentially everything on the host to be the root cause of this). Now, when I try to start up the Tomcat server, I get the error sun.misc.InvalidJarIndexException
in the console output. This happens for the following classes and methods:
org.apache.commons.modeler.Registry registerComponent
(happens 3 times)org.apache.catalina.core.StandardServer initialize
(happens once)org.apache.catalina.connector.Connector start
(happens twice)
I did find this stack overflow question regarding how to find the JAR of a Java Class useful and I did run find /usr -name \*name-of-suspected-jar\*.jar
a few times to track down a number of suggested offending JARS. I also tried to check the runtime configuration of the Tomcat server in Eclipse, but could really not match the JAR files on the system with the CLASSPATH
of neither the Tomcat runtime setup (or with the CLASSPATH
used in the environment when starting Eclipse). That effort probably requires some more rigor on my part but before doing that (and that is why I right now don't post all the gory details regarding CLASSPATH
s here), I did a read up on exactly what InvalidJarIndexException
really is about.
So, JAR files may contain an optional INDEX.LIST file which contains information about what classes (and methods?) to find in the JAR file. The idea is to short-circuit the search throughout all JARS in the CLASSPATH
whic开发者_运维技巧h is useful in a number of circumstances. Problem is when the INDEX.LIST
file happens to be corrupt (or, is believed to be corrupt), that causes the loading of the class to be completely given up (the class loader does not fall back to searching all JARs in the CLASSPATH
) and the error InvalidJarIndexException
to be thrown. To make things more messy, the order in which JARs are searched might affect how the class loader treats the INDEX.LIST
file: the INDEX.LIST
file of one JAR might refer to other JARS and if those referred to JARS are not in sync with the first JAR's INDEX.LIST
file, the class loader fails with this InvalidJarIndexException
error.
So (according to this StackOverflow question), it seems like this error can be thrown not only because a JAR file has a corrupt INDEX.LIST
, it seems it can even be thrown on a JAR even if the JAR has a valid INDEX.LIST
or legitimately is lacking a INDEX.LIST
simply because a previously searched JAR has confused the class loader. (To put in another way, as things are, this exception might be thrown even for "innocent" non-corrupted JAR files due to offenders elsewhere on the system).
So, after writing a mere novel, here comes my main set of questions:
- What is the best way to track down the precise
.jar
file for which eachInvalidJarIndexException
is thrown? - What is the best way check if a randomly picked
.jar
file has anINDEX.LIST
file and if so, if said file is valid (that is, non-corrupt)? What tools exist for this task? - Is there an efficient way to automatically deduce the search order of
.jar
files? I can try to follow theCLASSPATH
manually but to be honest, that is error prone and tedious. - Is there an efficient way to figure out what
.jar
file there is in a search order which might confuse the class loader to accuse innocent, non-corrupt.jar
files later in the search to have incorrectINDEX.LIST
files?
Disclaimer: I know I run old versions software (even if I have the latest updates of my Redhat 5.2 installed though) and I know a knee-jerk reaction for many people is to suggest that I don't put any effort whatsoever in debugging this but instead upgrade to a more recent version of Tomcat, Eclipse and Linux (Java is recent though). The reason I would prefer not to is that after looking into things, I've found it rather messy to do an upgrade or to try to install a separate modern Tomcat or Eclipse next to the RHEL5.2 provided Tomcat/Eclipse I use today. Also, I consider this kind of troubleshooting an opportunity to learn some useful nitty gritty details about Java and it's associated tools and features. Figuring out how the class loading works and what causes it to throw this InvalidJarIndexException
on my system would be very educating!
(But if this troubleshooting fails, I'll seriously consider to use a modern Linux, Eclipse and Tomcat... I promise)
Take the following steps to diagnose the problem:
- Add an exception breakpoint in Eclipse (it's the J with an exclamation mark icon), and set it to halt for caught and uncaught exceptions, of type InvalidJarIndexException.
- Start debugging your program.
Eclipse will halt at your exception breakpoint, when the InvalidJarIndexException is thrown. Even without the source for URLClassPath, you will still be able to inspect the variables on the stack leading to the exception, including the name of the class that URLClassPath is attempting to locate. Knowing the name of the class should significantly narrow the list of JAR's you need to examine.
Perhaps you've locally added a new class to a package and the contents of that package are described by the index file in a stale JAR on your classpath?
Try Tattletale which is a good reporting tool for jars. What I have done in this case was to eliminate INDEX.LIST from jars one by one until I did not get InvalidJarIndexException any more
精彩评论