Gentlemen, thank you very much for the poking and prodding: it pointed me in the right direction. I solved the problem by modifying the code I wrote to fetch the class bytes: instead of doing a URL.openStream() I changed it to do a URL.openConnection() then disabled the use of the URLConnection cache ( URLConnection.setUseCaches(false)). Now when I do a stop all the handles are gone and I can do a complete clean and rebuild without encountering any file locking issues.
For what its worth it might be meaningful to put that behavior into the webapp class loader when antiJARLocking is enabled. Femi. On 5/23/06, Black Buddha <[EMAIL PROTECTED]> wrote:
Tried it: and antiResourceLocking as well (both set to true). Its very curious: antiResourceLocking does what it seems like it should do: extracts all referenced resource files into work\Catalina\localhost\test\loader\org\blah\blah\blah.... However, antiJARLocking doesn't seem to do anything explicit. I took an extended trip through the Tomcat source for the webapp class loader (http://svn.apache.org/repos/asf/tomcat/container/tc5.5.x/catalina/src/share/org/apache/catalina/loader/WebappClassLoader.java) to see what antiJARLocking does, and basically it does this: if (antiJARLocking) { ResourceEntry entry = (ResourceEntry) resourceEntries.get(name); try { String repository = entry.codeBase.toString(); if ((repository.endsWith (".jar")) && (!(name.endsWith(".class")))) { // Copy binary content to the work directory if not present File resourceFile = new File(loaderDir, name); url = getURI(resourceFile); } } catch (Exception e) { // Ignore } } Which basically copies any resources with URLs that don't end with .class to the work directory, but doesn't appear to do the same for .class files. This sounds like what antiResourceLocking should do, but there are no references to antiResourceLocking in that class, so I'm kind of at a loss there (anyone know where to look for the effects of the antiResourceLocking flag?) I'm thinking what I'll do is subclass the loader and force it to copy the WEB-INF/lib jars to a separate location and go from there, that way I can discard them without losing sleep. I spotted a netbeans bug (http://bugs.sun.com/bugdatabase/view_bug.do?bug_id=5100046) that seems to obliquely suffer from the same issue, so that may be the answer. Femi. On 5/23/06, Filip Hanik - Dev Lists <[EMAIL PROTECTED]> wrote: > > http://tomcat.apache.org/tomcat-5.5-doc/config/context.html > > look for "antiJARLocking" > > is that what you are after? > Filip > > > Black Buddha wrote: > > Actually, I looked at that and its a little odder than that. I use the > > Eclipse compiler, and when its locating import dependencies it uses a > > chunk > > of code like this to retrieve the bytes for a specific class: > > > > InputStream is; > > try{ > > String resourceName = className.replace('.', '/') + ".class"; > > URL u = classLoader.getResource(resourceName); > > if(u != null){ > > is = u.openStream(); > > byte[] classBytes; > > byte[] buf = new byte[8192]; > > ByteArrayOutputStream baos = new > > ByteArrayOutputStream(buf.length); > > int count; > > while ((count = is.read(buf, 0, buf.length)) > 0) { > > baos.write(buf, 0, count); > > } > > baos.flush(); > > byte[] classBytes = baos.toByteArray(); > > char[] fileName = className.toCharArray(); > > ClassFileReader classFileReader = new > ClassFileReader(classBytes, > > fileName, true); > > return new NameEnvironmentAnswer(classFileReader, null); > > } > > } finally { > > if (is != null) { > > try { is.close(); }catch (IOException exc) {} // Ignore > > } > > } > > > > This call works just fine when I start up Tomcat the first time. > However > > when I stop the webapp and attempt to recompile the jar file with the > > actual > > class being loaded above within it I get an exception when Ant tries > to > > replace the file. Then when I restart the webapp, I get a > > FileNotFoundException, even though I KNOW the jar file is present and > > I know > > the class is within it. I've tried the System.gc() call, but still no > > love. > > > > Anyone know some way of forcing Tomcat to let go of the reference to > the > > webapp class loader so I can GC it and have it let go of the handle to > > the > > jar file? Alternatively, a cleaner way of fetching the class bytes > > without > > opening a stream into the jar file? > > > > Thanks, > > > > Femi. > > > > On 5/23/06, Peter Crowther <[EMAIL PROTECTED]> wrote: > >> > >> > From: Filip Hanik - Dev Lists [mailto: [EMAIL PROTECTED] > >> > interesting, are you saying that the handle is not closed > >> > when you call stream.close()? > >> > >> There's some noise on this at: > >> > >> > http://forum.java.sun.com/thread.jspa?threadID=609458&messageID=3355532 > >> > >> Still haven't found the entry in the bug database though. Sorry, > Filip. > >> > >> - Peter > >> > >> --------------------------------------------------------------------- > >> To start a new topic, e-mail: users@tomcat.apache.org > >> To unsubscribe, e-mail: [EMAIL PROTECTED] > >> For additional commands, e-mail: [EMAIL PROTECTED] > >> > >> > > > > > ------------------------------------------------------------------------ > > > > No virus found in this incoming message. > > Checked by AVG Free Edition. > > Version: 7.1.392 / Virus Database: 268.7.0/345 - Release Date: > 5/22/2006 > > > > > --------------------------------------------------------------------- > To start a new topic, e-mail: users@tomcat.apache.org > To unsubscribe, e-mail: [EMAIL PROTECTED] > For additional commands, e-mail: [EMAIL PROTECTED] > >