Closed
Description
Some build systems (Maven sometimes, but also Gradle) opened URLClassLoaders on a JAR file they created. They just release the ClassLoader, but don't close it (as only Java 7+ allows this, and most build system are Java 5 or even below). You can check for Closeable interface and close if it is, but not all users do this correctly.
The problem with forbiddenapis is: It also uses a URLClassLoader (but closes correctly, so no issue here), but if the build system previously opened a URLClassLoader, then rebuilt the Jar file for some reason, the internal cache gets invalidated and breaks. Loading classes fails with FileNotFoundException (on older pre-Java 7 JVMs it sometimes crushed completely with mmap SIGSEGV).
The workarounds are:
- Add a setting to the Checker (one more enum Option), so it disables the URLConnection cache when fetching resources. This may slowdown forbiddenapis, but only users affected by this must use it.
- Use a hack I investigated: If opening resource fails with IOException (FNFE only), do the following: If JarURLConnection, call getJarFile(), close it, and get a new URLConnection(). Closing the JAR file removes the open file from Cache. A new URLConnection will then reopen it. The problem with that approach is: It breaks other threads accessing the same jar files possibly in other ClassLoaders. So we should carefully only apply that hack on URLs we know that they are from our URLClassLoader.