From 75776c6ffde7c5b12644b793f16943783fdf47a7 Mon Sep 17 00:00:00 2001 From: chiba Date: Tue, 18 Jul 2006 14:46:25 +0000 Subject: [PATCH] reformatted. git-svn-id: http://anonsvn.jboss.org/repos/javassist/trunk@298 30ef5769-5b8d-40dd-aea6-55b5d6557bb3 --- .../javassist/scopedpool/ScopedClassPool.java | 488 +++++++++--------- .../scopedpool/ScopedClassPoolFactory.java | 50 +- .../ScopedClassPoolFactoryImpl.java | 59 ++- .../scopedpool/ScopedClassPoolRepository.java | 151 +++--- .../ScopedClassPoolRepositoryImpl.java | 357 ++++++------- .../scopedpool/SoftValueHashMap.java | 447 ++++++++-------- src/main/javassist/scopedpool/package.html | 7 + 7 files changed, 784 insertions(+), 775 deletions(-) create mode 100644 src/main/javassist/scopedpool/package.html diff --git a/src/main/javassist/scopedpool/ScopedClassPool.java b/src/main/javassist/scopedpool/ScopedClassPool.java index 7e9a1216..4c33e634 100644 --- a/src/main/javassist/scopedpool/ScopedClassPool.java +++ b/src/main/javassist/scopedpool/ScopedClassPool.java @@ -1,18 +1,18 @@ /* -* Javassist, a Java-bytecode translator toolkit. -* Copyright (C) 2006 JBoss Inc., All Rights Reserved. -* -* The contents of this file are subject to the Mozilla Public License Version -* 1.1 (the "License"); you may not use this file except in compliance with -* the License. Alternatively, the contents of this file may be used under -* the terms of the GNU Lesser General Public License Version 2.1 or later. -* -* Software distributed under the License is distributed on an "AS IS" -basis, -* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License -* for the specific language governing rights and limitations under the -* License. -*/ + * Javassist, a Java-bytecode translator toolkit. + * Copyright (C) 2006 JBoss Inc. All Rights Reserved. + * + * The contents of this file are subject to the Mozilla Public License Version + * 1.1 (the "License"); you may not use this file except in compliance with + * the License. Alternatively, the contents of this file may be used under + * the terms of the GNU Lesser General Public License Version 2.1 or later. + * + * Software distributed under the License is distributed on an "AS IS" basis, + * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License + * for the specific language governing rights and limitations under the + * License. + */ + package javassist.scopedpool; import java.lang.ref.WeakReference; @@ -25,249 +25,257 @@ import javassist.LoaderClassPath; import javassist.NotFoundException; /** - * A scoped class pool + * A scoped class pool. * * @author Bill Burke * @author Adrian Brock * @author Kabir Khan - * @version $Revision: 1.2 $ + * @version $Revision: 1.3 $ */ -public class ScopedClassPool extends ClassPool -{ - protected ScopedClassPoolRepository repository; - protected WeakReference classLoader; - protected LoaderClassPath classPath; - protected SoftValueHashMap softcache = new SoftValueHashMap(); +public class ScopedClassPool extends ClassPool { + protected ScopedClassPoolRepository repository; - static - { - ClassPool.doPruning = false; - ClassPool.releaseUnmodifiedClassFile = false; - } - - /** - * Create a new ScopedClassPool. - * - * @param cl the classloader - * @param src the original class pool - * @param repository the repository - */ - protected ScopedClassPool(ClassLoader cl, ClassPool src, ScopedClassPoolRepository repository) - { - super(src); - this.repository = repository; - this.classLoader = new WeakReference(cl); - if (cl != null) - { - classPath = new LoaderClassPath(cl); - this.insertClassPath(classPath); - } - childFirstLookup = true; - } + protected WeakReference classLoader; - /** - * Get the class loader - * - * @return the class loader - */ - public ClassLoader getClassLoader() - { - return getClassLoader0(); - } + protected LoaderClassPath classPath; - private ClassLoader getClassLoader0() - { - ClassLoader cl = (ClassLoader) classLoader.get(); - if (cl == null) - throw new IllegalStateException("ClassLoader has been garbage collected"); - return cl; - } - - /** - * Close the class pool - */ - public void close() - { - this.removeClassPath(classPath); - classPath.close(); - classes.clear(); - softcache.clear(); - } + protected SoftValueHashMap softcache = new SoftValueHashMap(); - /** - * Flush a class - * - * @param classname the class to flush - */ - public synchronized void flushClass(String classname) - { - classes.remove(classname); - softcache.remove(classname); - } + static { + ClassPool.doPruning = false; + ClassPool.releaseUnmodifiedClassFile = false; + } - /** - * Soften a class - * - * @param clazz the class - */ - public synchronized void soften(CtClass clazz) - { - if (repository.isPrune()) clazz.prune(); - classes.remove(clazz.getName()); - softcache.put(clazz.getName(), clazz); - } + /** + * Create a new ScopedClassPool. + * + * @param cl + * the classloader + * @param src + * the original class pool + * @param repository + * the repository + */ + protected ScopedClassPool(ClassLoader cl, ClassPool src, + ScopedClassPoolRepository repository) { + super(src); + this.repository = repository; + this.classLoader = new WeakReference(cl); + if (cl != null) { + classPath = new LoaderClassPath(cl); + this.insertClassPath(classPath); + } + childFirstLookup = true; + } - /** - * Whether the classloader is loader - * - * @return false always - */ - public boolean isUnloadedClassLoader() - { - return false; - } + /** + * Get the class loader + * + * @return the class loader + */ + public ClassLoader getClassLoader() { + return getClassLoader0(); + } - /** - * Get the cached class - * - * @param classname the class name - * @return the class - */ - protected CtClass getCached(String classname) - { - CtClass clazz = getCachedLocally(classname); - if (clazz == null) - { - boolean isLocal = false; - - ClassLoader dcl = getClassLoader0(); - if (dcl != null) - { - final int lastIndex = classname.lastIndexOf('$'); - String classResourceName = null; - if (lastIndex < 0) - { - classResourceName = classname.replaceAll("[\\.]", "/") + ".class"; - } - else - { - classResourceName = classname.substring(0, lastIndex).replaceAll("[\\.]", "/") + classname.substring(lastIndex) + ".class"; + private ClassLoader getClassLoader0() { + ClassLoader cl = (ClassLoader)classLoader.get(); + if (cl == null) + throw new IllegalStateException( + "ClassLoader has been garbage collected"); + return cl; + } + + /** + * Close the class pool + */ + public void close() { + this.removeClassPath(classPath); + classPath.close(); + classes.clear(); + softcache.clear(); + } + + /** + * Flush a class + * + * @param classname + * the class to flush + */ + public synchronized void flushClass(String classname) { + classes.remove(classname); + softcache.remove(classname); + } + + /** + * Soften a class + * + * @param clazz + * the class + */ + public synchronized void soften(CtClass clazz) { + if (repository.isPrune()) + clazz.prune(); + classes.remove(clazz.getName()); + softcache.put(clazz.getName(), clazz); + } + + /** + * Whether the classloader is loader + * + * @return false always + */ + public boolean isUnloadedClassLoader() { + return false; + } + + /** + * Get the cached class + * + * @param classname + * the class name + * @return the class + */ + protected CtClass getCached(String classname) { + CtClass clazz = getCachedLocally(classname); + if (clazz == null) { + boolean isLocal = false; + + ClassLoader dcl = getClassLoader0(); + if (dcl != null) { + final int lastIndex = classname.lastIndexOf('$'); + String classResourceName = null; + if (lastIndex < 0) { + classResourceName = classname.replaceAll("[\\.]", "/") + + ".class"; + } + else { + classResourceName = classname.substring(0, lastIndex) + .replaceAll("[\\.]", "/") + + classname.substring(lastIndex) + ".class"; + } + + isLocal = dcl.getResource(classResourceName) != null; } - isLocal = dcl.getResource(classResourceName) != null; - } - - if (!isLocal) - { - Map registeredCLs = repository.getRegisteredCLs(); - synchronized (registeredCLs) - { - Iterator it = registeredCLs.values().iterator(); - while (it.hasNext()) - { - ScopedClassPool pool = (ScopedClassPool) it.next(); - if (pool.isUnloadedClassLoader()) - { - repository.unregisterClassLoader(pool.getClassLoader()); - continue; - } - - clazz = pool.getCachedLocally(classname); - if (clazz != null) - { - return clazz; - } - } + if (!isLocal) { + Map registeredCLs = repository.getRegisteredCLs(); + synchronized (registeredCLs) { + Iterator it = registeredCLs.values().iterator(); + while (it.hasNext()) { + ScopedClassPool pool = (ScopedClassPool)it.next(); + if (pool.isUnloadedClassLoader()) { + repository.unregisterClassLoader(pool + .getClassLoader()); + continue; + } + + clazz = pool.getCachedLocally(classname); + if (clazz != null) { + return clazz; + } + } + } } - } - } - // *NOTE* NEED TO TEST WHEN SUPERCLASS IS IN ANOTHER UCL!!!!!! - return clazz; - } - - /** - * Cache a class - * - * @param classname the class name - * @param c the ctClass - * @param dynamic whether the class is dynamically generated - */ - protected void cacheCtClass(String classname, CtClass c, boolean dynamic) - { - if (dynamic) - { - super.cacheCtClass(classname, c, dynamic); - } - else - { - if (repository.isPrune()) c.prune(); - softcache.put(classname, c); - } - } - - /** - * Lock a class into the cache - * - * @param c the class - */ - public void lockInCache(CtClass c) - { - super.cacheCtClass(c.getName(), c, false); - } + } + // *NOTE* NEED TO TEST WHEN SUPERCLASS IS IN ANOTHER UCL!!!!!! + return clazz; + } + + /** + * Cache a class + * + * @param classname + * the class name + * @param c + * the ctClass + * @param dynamic + * whether the class is dynamically generated + */ + protected void cacheCtClass(String classname, CtClass c, boolean dynamic) { + if (dynamic) { + super.cacheCtClass(classname, c, dynamic); + } + else { + if (repository.isPrune()) + c.prune(); + softcache.put(classname, c); + } + } + + /** + * Lock a class into the cache + * + * @param c + * the class + */ + public void lockInCache(CtClass c) { + super.cacheCtClass(c.getName(), c, false); + } - /** - * Whether the class is cached in this pooled - * - * @param classname the class name - * @return the cached class - */ - protected CtClass getCachedLocally(String classname) - { - CtClass cached = (CtClass) classes.get(classname); - if (cached != null) return cached; - synchronized (softcache) - { - return (CtClass) softcache.get(classname); - } - } + /** + * Whether the class is cached in this pooled + * + * @param classname + * the class name + * @return the cached class + */ + protected CtClass getCachedLocally(String classname) { + CtClass cached = (CtClass)classes.get(classname); + if (cached != null) + return cached; + synchronized (softcache) { + return (CtClass)softcache.get(classname); + } + } - /** - * Get any local copy of the class - * - * @param classname the class name - * @return the class - * @throws NotFoundException when the class is not found - */ - public synchronized CtClass getLocally(String classname) throws NotFoundException - { - softcache.remove(classname); - CtClass clazz = (CtClass) classes.get(classname); - if (clazz == null) - { - clazz = createCtClass(classname, true); - if (clazz == null) throw new NotFoundException(classname); - super.cacheCtClass(classname, clazz, false); - } + /** + * Get any local copy of the class + * + * @param classname + * the class name + * @return the class + * @throws NotFoundException + * when the class is not found + */ + public synchronized CtClass getLocally(String classname) + throws NotFoundException { + softcache.remove(classname); + CtClass clazz = (CtClass)classes.get(classname); + if (clazz == null) { + clazz = createCtClass(classname, true); + if (clazz == null) + throw new NotFoundException(classname); + super.cacheCtClass(classname, clazz, false); + } - return clazz; - } + return clazz; + } - /** - * Convert a javassist class to a java class - * - * @param ct the javassist class - * @param loader the loader - * @throws CannotCompileException for any error - */ - public Class toClass(CtClass ct, ClassLoader loader) throws CannotCompileException - { - //We need to pass up the classloader stored in this pool, as the default implementation uses the Thread context cl. - //In the case of JSP's in Tomcat, org.apache.jasper.servlet.JasperLoader will be stored here, while it's parent - //org.jboss.web.tomcat.tc5.WebCtxLoader$ENCLoader is used as the Thread context cl. The invocation class needs to - // be generated in the JasperLoader classloader since in the case of method invocations, the package name will be - //the same as for the class generated from the jsp, i.e. org.apache.jsp. For classes belonging to org.apache.jsp, - //JasperLoader does NOT delegate to its parent if it cannot find them. - lockInCache(ct); - return super.toClass(ct, getClassLoader0()); - } + /** + * Convert a javassist class to a java class + * + * @param ct + * the javassist class + * @param loader + * the loader + * @throws CannotCompileException + * for any error + */ + public Class toClass(CtClass ct, ClassLoader loader) + throws CannotCompileException { + // We need to pass up the classloader stored in this pool, as the + // default implementation uses the Thread context cl. + // In the case of JSP's in Tomcat, + // org.apache.jasper.servlet.JasperLoader will be stored here, while + // it's parent + // org.jboss.web.tomcat.tc5.WebCtxLoader$ENCLoader is used as the Thread + // context cl. The invocation class needs to + // be generated in the JasperLoader classloader since in the case of + // method invocations, the package name will be + // the same as for the class generated from the jsp, i.e. + // org.apache.jsp. For classes belonging to org.apache.jsp, + // JasperLoader does NOT delegate to its parent if it cannot find them. + lockInCache(ct); + return super.toClass(ct, getClassLoader0()); + } } diff --git a/src/main/javassist/scopedpool/ScopedClassPoolFactory.java b/src/main/javassist/scopedpool/ScopedClassPoolFactory.java index e6cf600e..a3d5ad5d 100644 --- a/src/main/javassist/scopedpool/ScopedClassPoolFactory.java +++ b/src/main/javassist/scopedpool/ScopedClassPoolFactory.java @@ -1,30 +1,38 @@ /* -* Javassist, a Java-bytecode translator toolkit. -* Copyright (C) 2006 JBoss Inc., All Rights Reserved. -* -* The contents of this file are subject to the Mozilla Public License Version -* 1.1 (the "License"); you may not use this file except in compliance with -* the License. Alternatively, the contents of this file may be used under -* the terms of the GNU Lesser General Public License Version 2.1 or later. -* -* Software distributed under the License is distributed on an "AS IS" -basis, -* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License -* for the specific language governing rights and limitations under the -* License. -*/ + * Javassist, a Java-bytecode translator toolkit. + * Copyright (C) 2006 JBoss Inc. All Rights Reserved. + * + * The contents of this file are subject to the Mozilla Public License Version + * 1.1 (the "License"); you may not use this file except in compliance with + * the License. Alternatively, the contents of this file may be used under + * the terms of the GNU Lesser General Public License Version 2.1 or later. + * + * Software distributed under the License is distributed on an "AS IS" basis, + * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License + * for the specific language governing rights and limitations under the + * License. + */ + package javassist.scopedpool; import javassist.ClassPool; /** - * + * A factory interface. + * * @author Kabir Khan - * @version $Revision: 1.2 $ + * @version $Revision: 1.3 $ */ -public interface ScopedClassPoolFactory -{ - ScopedClassPool create(ClassLoader cl, ClassPool src, ScopedClassPoolRepository repository); - - ScopedClassPool create(ClassPool src, ScopedClassPoolRepository repository); +public interface ScopedClassPoolFactory { + /** + * Makes an instance. + */ + ScopedClassPool create(ClassLoader cl, ClassPool src, + ScopedClassPoolRepository repository); + + /** + * Makes an instance. + */ + ScopedClassPool create(ClassPool src, + ScopedClassPoolRepository repository); } diff --git a/src/main/javassist/scopedpool/ScopedClassPoolFactoryImpl.java b/src/main/javassist/scopedpool/ScopedClassPoolFactoryImpl.java index f4552200..bcbcbec6 100644 --- a/src/main/javassist/scopedpool/ScopedClassPoolFactoryImpl.java +++ b/src/main/javassist/scopedpool/ScopedClassPoolFactoryImpl.java @@ -1,37 +1,42 @@ /* -* Javassist, a Java-bytecode translator toolkit. -* Copyright (C) 2006 JBoss Inc., All Rights Reserved. -* -* The contents of this file are subject to the Mozilla Public License Version -* 1.1 (the "License"); you may not use this file except in compliance with -* the License. Alternatively, the contents of this file may be used under -* the terms of the GNU Lesser General Public License Version 2.1 or later. -* -* Software distributed under the License is distributed on an "AS IS" -basis, -* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License -* for the specific language governing rights and limitations under the -* License. -*/ + * Javassist, a Java-bytecode translator toolkit. + * Copyright (C) 2006 JBoss Inc. All Rights Reserved. + * + * The contents of this file are subject to the Mozilla Public License Version + * 1.1 (the "License"); you may not use this file except in compliance with + * the License. Alternatively, the contents of this file may be used under + * the terms of the GNU Lesser General Public License Version 2.1 or later. + * + * Software distributed under the License is distributed on an "AS IS" basis, + * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License + * for the specific language governing rights and limitations under the + * License. + */ + package javassist.scopedpool; import javassist.ClassPool; - /** - * + * An implementation of factory. + * * @author Kabir Khan - * @version $Revision: 1.2 $ + * @version $Revision: 1.3 $ */ -public class ScopedClassPoolFactoryImpl implements ScopedClassPoolFactory -{ - public ScopedClassPool create(ClassLoader cl, ClassPool src, ScopedClassPoolRepository repository) - { - return new ScopedClassPool(cl, src, repository); - } +public class ScopedClassPoolFactoryImpl implements ScopedClassPoolFactory { + /** + * Makes an instance. + */ + public ScopedClassPool create(ClassLoader cl, ClassPool src, + ScopedClassPoolRepository repository) { + return new ScopedClassPool(cl, src, repository); + } - public ScopedClassPool create(ClassPool src, ScopedClassPoolRepository repository) - { - return new ScopedClassPool(null, src, repository); - } + /** + * Makes an instance. + */ + public ScopedClassPool create(ClassPool src, + ScopedClassPoolRepository repository) { + return new ScopedClassPool(null, src, repository); + } } diff --git a/src/main/javassist/scopedpool/ScopedClassPoolRepository.java b/src/main/javassist/scopedpool/ScopedClassPoolRepository.java index da898d19..c52a2aea 100644 --- a/src/main/javassist/scopedpool/ScopedClassPoolRepository.java +++ b/src/main/javassist/scopedpool/ScopedClassPoolRepository.java @@ -1,18 +1,18 @@ /* -* Javassist, a Java-bytecode translator toolkit. -* Copyright (C) 2006 JBoss Inc., All Rights Reserved. -* -* The contents of this file are subject to the Mozilla Public License Version -* 1.1 (the "License"); you may not use this file except in compliance with -* the License. Alternatively, the contents of this file may be used under -* the terms of the GNU Lesser General Public License Version 2.1 or later. -* -* Software distributed under the License is distributed on an "AS IS" -basis, -* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License -* for the specific language governing rights and limitations under the -* License. -*/ + * Javassist, a Java-bytecode translator toolkit. + * Copyright (C) 2006 JBoss Inc. All Rights Reserved. + * + * The contents of this file are subject to the Mozilla Public License Version + * 1.1 (the "License"); you may not use this file except in compliance with + * the License. Alternatively, the contents of this file may be used under + * the terms of the GNU Lesser General Public License Version 2.1 or later. + * + * Software distributed under the License is distributed on an "AS IS" basis, + * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License + * for the specific language governing rights and limitations under the + * License. + */ + package javassist.scopedpool; import java.util.Map; @@ -20,69 +20,78 @@ import java.util.Map; import javassist.ClassPool; /** - * + * An interface to ScopedClassPoolRepositoryImpl. + * * @author Kabir Khan - * @version $Revision: 1.2 $ + * @version $Revision: 1.3 $ */ -public interface ScopedClassPoolRepository -{ - void setClassPoolFactory(ScopedClassPoolFactory factory); - - ScopedClassPoolFactory getClassPoolFactory(); +public interface ScopedClassPoolRepository { + /** + * Records a factory. + */ + void setClassPoolFactory(ScopedClassPoolFactory factory); + + /** + * Obtains the recorded factory. + */ + ScopedClassPoolFactory getClassPoolFactory(); + + /** + * Returns whether or not the class pool is pruned. + * + * @return the prune. + */ + boolean isPrune(); - /** - * Get the prune. - * - * @return the prune. - */ - boolean isPrune(); + /** + * Sets the prune flag. + * + * @param prune a new value. + */ + void setPrune(boolean prune); - /** - * Set the prune. - * - * @param prune the prune. - */ - void setPrune(boolean prune); - - /** - * Create a scoped classpool - * - * @param cl the classloader - * @param src the original classpool - * @return the classpool - */ - ScopedClassPool createScopedClassPool(ClassLoader cl, ClassPool src); + /** + * Create a scoped classpool. + * + * @param cl the classloader. + * @param src the original classpool. + * @return the classpool. + */ + ScopedClassPool createScopedClassPool(ClassLoader cl, ClassPool src); - /** - * Finds a scoped classpool registered under the passed in classloader - * @param the classloader - * @return the classpool - */ - ClassPool findClassPool(ClassLoader cl); + /** + * Finds a scoped classpool registered under the passed in classloader. + * + * @param cl the classloader. + * @return the classpool. + */ + ClassPool findClassPool(ClassLoader cl); - /** - * Register a classloader - * - * @param ucl the classloader - * @return the classpool - */ - ClassPool registerClassLoader(ClassLoader ucl); + /** + * Register a classloader. + * + * @param ucl the classloader. + * @return the classpool. + */ + ClassPool registerClassLoader(ClassLoader ucl); - /** - * Get the registered classloaders - * - * @return the registered classloaders - */ - Map getRegisteredCLs(); + /** + * Get the registered classloaders. + * + * @return the registered classloaders. + */ + Map getRegisteredCLs(); - /** - * This method will check to see if a register classloader has been undeployed (as in JBoss) - */ - void clearUnregisteredClassLoaders(); + /** + * This method will check to see if a register classloader has been + * undeployed (as in JBoss). + */ + void clearUnregisteredClassLoaders(); - /** - * Unregisters a classpool and unregisters its classloader. - * @ClassLoader the classloader the pool is stored under - */ - void unregisterClassLoader(ClassLoader cl); -} \ No newline at end of file + /** + * Unregisters a classpool and unregisters its classloader. + * + * @param cl the classloader the pool is stored under. + */ + void unregisterClassLoader(ClassLoader cl); +} diff --git a/src/main/javassist/scopedpool/ScopedClassPoolRepositoryImpl.java b/src/main/javassist/scopedpool/ScopedClassPoolRepositoryImpl.java index f0436f47..602eb56e 100644 --- a/src/main/javassist/scopedpool/ScopedClassPoolRepositoryImpl.java +++ b/src/main/javassist/scopedpool/ScopedClassPoolRepositoryImpl.java @@ -1,18 +1,18 @@ /* -* Javassist, a Java-bytecode translator toolkit. -* Copyright (C) 2006 JBoss Inc., All Rights Reserved. -* -* The contents of this file are subject to the Mozilla Public License Version -* 1.1 (the "License"); you may not use this file except in compliance with -* the License. Alternatively, the contents of this file may be used under -* the terms of the GNU Lesser General Public License Version 2.1 or later. -* -* Software distributed under the License is distributed on an "AS IS" -basis, -* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License -* for the specific language governing rights and limitations under the -* License. -*/ + * Javassist, a Java-bytecode translator toolkit. + * Copyright (C) 2006 JBoss Inc. All Rights Reserved. + * + * The contents of this file are subject to the Mozilla Public License Version + * 1.1 (the "License"); you may not use this file except in compliance with + * the License. Alternatively, the contents of this file may be used under + * the terms of the GNU Lesser General Public License Version 2.1 or later. + * + * Software distributed under the License is distributed on an "AS IS" basis, + * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License + * for the specific language governing rights and limitations under the + * License. + */ + package javassist.scopedpool; import java.util.ArrayList; @@ -25,182 +25,163 @@ import javassist.ClassPool; import javassist.LoaderClassPath; /** - * + * An implementation of ScopedClassPoolRepository. + * It is an singleton. + * * @author Kabir Khan - * @version $Revision: 1.2 $ + * @version $Revision: 1.3 $ */ -public class ScopedClassPoolRepositoryImpl implements ScopedClassPoolRepository -{ - /** The instance */ - private static final ScopedClassPoolRepositoryImpl instance = new ScopedClassPoolRepositoryImpl(); - - /** Whether to prune */ - private boolean prune = true; - - /** Whether to prune when added to the classpool's cache */ - boolean pruneWhenCached; - - /** The registered classloaders */ - protected Map registeredCLs = Collections.synchronizedMap(new WeakHashMap()); - - /** The default class pool */ - protected ClassPool classpool; - - /** The factory for creating class pools */ - protected ScopedClassPoolFactory factory = new ScopedClassPoolFactoryImpl(); - - /** - * Get the instance - * - * @return the instance - */ - public static ScopedClassPoolRepository getInstance() - { - return instance; - } - - /** - * Singleton - */ - private ScopedClassPoolRepositoryImpl() - { - classpool = ClassPool.getDefault(); - // FIXME This doesn't look correct - ClassLoader cl = Thread.currentThread().getContextClassLoader(); - classpool.insertClassPath(new LoaderClassPath(cl)); - } - - /** - * Get the prune. - * - * @return the prune. - */ - public boolean isPrune() - { - return prune; - } - - /** - * Set the prune. - * - * @param prune the prune. - */ - public void setPrune(boolean prune) - { - this.prune = prune; - } - - /** - * Create a scoped classpool - * - * @param cl the classloader - * @param src the original classpool - * @return the classpool - */ - public ScopedClassPool createScopedClassPool(ClassLoader cl, ClassPool src) - { - return factory.create(cl, src, this); - } - - public ClassPool findClassPool(ClassLoader cl) - { - if (cl == null) - return registerClassLoader(ClassLoader.getSystemClassLoader()); - return registerClassLoader(cl); - } - - /** - * Register a classloader - * - * @param ucl the classloader - * @return the classpool - */ - public ClassPool registerClassLoader(ClassLoader ucl) - { - synchronized (registeredCLs) - { - // FIXME: Probably want to take this method out later - // so that AOP framework can be independent of JMX - // This is in here so that we can remove a UCL from the ClassPool as a - // ClassPool.classpath - if (registeredCLs.containsKey(ucl)) - { - return (ClassPool) registeredCLs.get(ucl); - } - ScopedClassPool pool = createScopedClassPool(ucl, classpool); - registeredCLs.put(ucl, pool); - return pool; - } - } - - /** - * Get the registered classloaders - * - * @return the registered classloaders - */ - public Map getRegisteredCLs() - { - clearUnregisteredClassLoaders(); - return registeredCLs; - } - - /** - * This method will check to see if a register classloader has been undeployed (as in JBoss) - */ - public void clearUnregisteredClassLoaders() - { - ArrayList toUnregister = null; - synchronized (registeredCLs) - { - Iterator it = registeredCLs.values().iterator(); - while (it.hasNext()) - { - ScopedClassPool pool = (ScopedClassPool) it.next(); - if (pool.isUnloadedClassLoader()) - { - it.remove(); - ClassLoader cl = pool.getClassLoader(); - if (cl != null) - { - if (toUnregister == null) - { - toUnregister = new ArrayList(); - } - toUnregister.add(cl); - } +public class ScopedClassPoolRepositoryImpl implements ScopedClassPoolRepository { + /** The instance */ + private static final ScopedClassPoolRepositoryImpl instance = new ScopedClassPoolRepositoryImpl(); + + /** Whether to prune */ + private boolean prune = true; + + /** Whether to prune when added to the classpool's cache */ + boolean pruneWhenCached; + + /** The registered classloaders */ + protected Map registeredCLs = Collections + .synchronizedMap(new WeakHashMap()); + + /** The default class pool */ + protected ClassPool classpool; + + /** The factory for creating class pools */ + protected ScopedClassPoolFactory factory = new ScopedClassPoolFactoryImpl(); + + /** + * Get the instance. + * + * @return the instance. + */ + public static ScopedClassPoolRepository getInstance() { + return instance; + } + + /** + * Singleton. + */ + private ScopedClassPoolRepositoryImpl() { + classpool = ClassPool.getDefault(); + // FIXME This doesn't look correct + ClassLoader cl = Thread.currentThread().getContextClassLoader(); + classpool.insertClassPath(new LoaderClassPath(cl)); + } + + /** + * Returns the value of the prune attribute. + * + * @return the prune. + */ + public boolean isPrune() { + return prune; + } + + /** + * Set the prune attribute. + * + * @param prune a new value. + */ + public void setPrune(boolean prune) { + this.prune = prune; + } + + /** + * Create a scoped classpool. + * + * @param cl the classloader. + * @param src the original classpool. + * @return the classpool + */ + public ScopedClassPool createScopedClassPool(ClassLoader cl, ClassPool src) { + return factory.create(cl, src, this); + } + + public ClassPool findClassPool(ClassLoader cl) { + if (cl == null) + return registerClassLoader(ClassLoader.getSystemClassLoader()); + + return registerClassLoader(cl); + } + + /** + * Register a classloader. + * + * @param ucl the classloader. + * @return the classpool + */ + public ClassPool registerClassLoader(ClassLoader ucl) { + synchronized (registeredCLs) { + // FIXME: Probably want to take this method out later + // so that AOP framework can be independent of JMX + // This is in here so that we can remove a UCL from the ClassPool as + // a + // ClassPool.classpath + if (registeredCLs.containsKey(ucl)) { + return (ClassPool)registeredCLs.get(ucl); + } + ScopedClassPool pool = createScopedClassPool(ucl, classpool); + registeredCLs.put(ucl, pool); + return pool; + } + } + + /** + * Get the registered classloaders. + */ + public Map getRegisteredCLs() { + clearUnregisteredClassLoaders(); + return registeredCLs; + } + + /** + * This method will check to see if a register classloader has been + * undeployed (as in JBoss) + */ + public void clearUnregisteredClassLoaders() { + ArrayList toUnregister = null; + synchronized (registeredCLs) { + Iterator it = registeredCLs.values().iterator(); + while (it.hasNext()) { + ScopedClassPool pool = (ScopedClassPool)it.next(); + if (pool.isUnloadedClassLoader()) { + it.remove(); + ClassLoader cl = pool.getClassLoader(); + if (cl != null) { + if (toUnregister == null) { + toUnregister = new ArrayList(); + } + toUnregister.add(cl); + } + } } - } - if (toUnregister != null) - { - for (int i = 0; i < toUnregister.size(); i++) - { - unregisterClassLoader((ClassLoader) toUnregister.get(i)); + if (toUnregister != null) { + for (int i = 0; i < toUnregister.size(); i++) { + unregisterClassLoader((ClassLoader)toUnregister.get(i)); + } } - } - } - } - - public void unregisterClassLoader(ClassLoader cl) - { - synchronized (registeredCLs) - { - ScopedClassPool pool = (ScopedClassPool) registeredCLs.remove(cl); - if (pool != null) pool.close(); - } - } - - public void insertDelegate(ScopedClassPoolRepository delegate) - { - //Noop - this is the end - } - - public void setClassPoolFactory(ScopedClassPoolFactory factory) - { - this.factory = factory; - } - - public ScopedClassPoolFactory getClassPoolFactory() - { - return factory; - } + } + } + + public void unregisterClassLoader(ClassLoader cl) { + synchronized (registeredCLs) { + ScopedClassPool pool = (ScopedClassPool)registeredCLs.remove(cl); + if (pool != null) + pool.close(); + } + } + + public void insertDelegate(ScopedClassPoolRepository delegate) { + // Noop - this is the end + } + + public void setClassPoolFactory(ScopedClassPoolFactory factory) { + this.factory = factory; + } + + public ScopedClassPoolFactory getClassPoolFactory() { + return factory; + } } diff --git a/src/main/javassist/scopedpool/SoftValueHashMap.java b/src/main/javassist/scopedpool/SoftValueHashMap.java index 4c2812c4..a98fb908 100644 --- a/src/main/javassist/scopedpool/SoftValueHashMap.java +++ b/src/main/javassist/scopedpool/SoftValueHashMap.java @@ -1,18 +1,18 @@ /* -* Javassist, a Java-bytecode translator toolkit. -* Copyright (C) 2006 JBoss Inc., All Rights Reserved. -* -* The contents of this file are subject to the Mozilla Public License Version -* 1.1 (the "License"); you may not use this file except in compliance with -* the License. Alternatively, the contents of this file may be used under -* the terms of the GNU Lesser General Public License Version 2.1 or later. -* -* Software distributed under the License is distributed on an "AS IS" -basis, -* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License -* for the specific language governing rights and limitations under the -* License. -*/ + * Javassist, a Java-bytecode translator toolkit. + * Copyright (C) 2006 JBoss Inc. All Rights Reserved. + * + * The contents of this file are subject to the Mozilla Public License Version + * 1.1 (the "License"); you may not use this file except in compliance with + * the License. Alternatively, the contents of this file may be used under + * the terms of the GNU Lesser General Public License Version 2.1 or later. + * + * Software distributed under the License is distributed on an "AS IS" basis, + * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License + * for the specific language governing rights and limitations under the + * License. + */ + package javassist.scopedpool; import java.lang.ref.ReferenceQueue; @@ -22,220 +22,211 @@ import java.util.HashMap; import java.util.Map; import java.util.Set; - /** - * This Map will remove entries when the value in the map has been - * cleaned from garbage collection - * - * @version $Revision: 1.2 $ - * @author Bill Burke + * This Map will remove entries when the value in the map has been cleaned from + * garbage collection + * + * @version $Revision: 1.3 $ + * @author Bill Burke */ -public class SoftValueHashMap - extends AbstractMap - implements Map -{ - private static class SoftValueRef extends SoftReference - { - public Object key; - - private SoftValueRef(Object key, Object val, ReferenceQueue q) - { - super(val, q); - this.key = key; - } - - private static SoftValueRef create(Object key, Object val, ReferenceQueue q) - { - if (val == null) return null; - else return new SoftValueRef(key, val, q); - } - - } - public Set entrySet() - { - processQueue(); - return hash.entrySet(); - } - - /* Hash table mapping WeakKeys to values */ - private Map hash; - - /* Reference queue for cleared WeakKeys */ - private ReferenceQueue queue = new ReferenceQueue(); - - /* Remove all invalidated entries from the map, that is, remove all entries - whose values have been discarded. - */ - private void processQueue() - { - SoftValueRef ref; - while ((ref = (SoftValueRef)queue.poll()) != null) { - if (ref == (SoftValueRef) hash.get(ref.key)) { - // only remove if it is the *exact* same WeakValueRef - // - hash.remove(ref.key); - } - } - } - - - /* -- Constructors -- */ - - /** - * Constructs a new, empty WeakHashMap with the given - * initial capacity and the given load factor. - * - * @param initialCapacity The initial capacity of the - * WeakHashMap - * - * @param loadFactor The load factor of the WeakHashMap - * - * @throws IllegalArgumentException If the initial capacity is less than - * zero, or if the load factor is - * nonpositive - */ - public SoftValueHashMap(int initialCapacity, float loadFactor) - { - hash = new HashMap(initialCapacity, loadFactor); - } - - /** - * Constructs a new, empty WeakHashMap with the given - * initial capacity and the default load factor, which is - * 0.75. - * - * @param initialCapacity The initial capacity of the - * WeakHashMap - * - * @throws IllegalArgumentException If the initial capacity is less than - * zero - */ - public SoftValueHashMap(int initialCapacity) - { - hash = new HashMap(initialCapacity); - } - - /** - * Constructs a new, empty WeakHashMap with the default - * initial capacity and the default load factor, which is - * 0.75. - */ - public SoftValueHashMap() - { - hash = new HashMap(); - } - - /** - * Constructs a new WeakHashMap with the same mappings as the - * specified Map. The WeakHashMap is created with an - * initial capacity of twice the number of mappings in the specified map - * or 11 (whichever is greater), and a default load factor, which is - * 0.75. - * - * @param t the map whose mappings are to be placed in this map. - * @since 1.3 - */ - public SoftValueHashMap(Map t) - { - this(Math.max(2*t.size(), 11), 0.75f); - putAll(t); - } - - /* -- Simple queries -- */ - - /** - * Returns the number of key-value mappings in this map. - * Note: In contrast with most implementations of the - * Map interface, the time required by this operation is - * linear in the size of the map. - */ - public int size() - { - processQueue(); - return hash.size(); - } - - /** - * Returns true if this map contains no key-value mappings. - */ - public boolean isEmpty() - { - processQueue(); - return hash.isEmpty(); - } - - /** - * Returns true if this map contains a mapping for the - * specified key. - * - * @param key The key whose presence in this map is to be tested - */ - public boolean containsKey(Object key) - { - processQueue(); - return hash.containsKey(key); - } - - /* -- Lookup and modification operations -- */ - - /** - * Returns the value to which this map maps the specified key. - * If this map does not contain a value for this key, then return - * null. - * - * @param key The key whose associated value, if any, is to be returned - */ - public Object get(Object key) - { - processQueue(); - SoftReference ref = (SoftReference)hash.get(key); - if (ref != null) return ref.get(); - return null; - } - - /** - * Updates this map so that the given key maps to the given - * value. If the map previously contained a mapping for - * key then that mapping is replaced and the previous value is - * returned. - * - * @param key The key that is to be mapped to the given - * value - * @param value The value to which the given key is to be - * mapped - * - * @return The previous value to which this key was mapped, or - * null if if there was no mapping for the key - */ - public Object put(Object key, Object value) - { - processQueue(); - Object rtn = hash.put(key, SoftValueRef.create(key, value, queue)); - if (rtn != null) rtn = ((SoftReference)rtn).get(); - return rtn; - } - - /** - * Removes the mapping for the given key from this map, if - * present. - * - * @param key The key whose mapping is to be removed - * - * @return The value to which this key was mapped, or null if - * there was no mapping for the key - */ - public Object remove(Object key) - { - processQueue(); - return hash.remove(key); - } - - /** - * Removes all mappings from this map. - */ - public void clear() - { - processQueue(); - hash.clear(); - } +public class SoftValueHashMap extends AbstractMap implements Map { + private static class SoftValueRef extends SoftReference { + public Object key; + + private SoftValueRef(Object key, Object val, ReferenceQueue q) { + super(val, q); + this.key = key; + } + + private static SoftValueRef create(Object key, Object val, + ReferenceQueue q) { + if (val == null) + return null; + else + return new SoftValueRef(key, val, q); + } + + } + + /** + * Returns a set of the mappings contained in this hash table. + */ + public Set entrySet() { + processQueue(); + return hash.entrySet(); + } + + /* Hash table mapping WeakKeys to values */ + private Map hash; + + /* Reference queue for cleared WeakKeys */ + private ReferenceQueue queue = new ReferenceQueue(); + + /* + * Remove all invalidated entries from the map, that is, remove all entries + * whose values have been discarded. + */ + private void processQueue() { + SoftValueRef ref; + while ((ref = (SoftValueRef)queue.poll()) != null) { + if (ref == (SoftValueRef)hash.get(ref.key)) { + // only remove if it is the *exact* same WeakValueRef + // + hash.remove(ref.key); + } + } + } + + /* -- Constructors -- */ + + /** + * Constructs a new, empty WeakHashMap with the given initial + * capacity and the given load factor. + * + * @param initialCapacity + * The initial capacity of the WeakHashMap + * + * @param loadFactor + * The load factor of the WeakHashMap + * + * @throws IllegalArgumentException + * If the initial capacity is less than zero, or if the load + * factor is nonpositive + */ + public SoftValueHashMap(int initialCapacity, float loadFactor) { + hash = new HashMap(initialCapacity, loadFactor); + } + + /** + * Constructs a new, empty WeakHashMap with the given initial + * capacity and the default load factor, which is 0.75. + * + * @param initialCapacity + * The initial capacity of the WeakHashMap + * + * @throws IllegalArgumentException + * If the initial capacity is less than zero + */ + public SoftValueHashMap(int initialCapacity) { + hash = new HashMap(initialCapacity); + } + + /** + * Constructs a new, empty WeakHashMap with the default + * initial capacity and the default load factor, which is 0.75. + */ + public SoftValueHashMap() { + hash = new HashMap(); + } + + /** + * Constructs a new WeakHashMap with the same mappings as the + * specified Map. The WeakHashMap is created with + * an initial capacity of twice the number of mappings in the specified map + * or 11 (whichever is greater), and a default load factor, which is + * 0.75. + * + * @param t the map whose mappings are to be placed in this map. + */ + public SoftValueHashMap(Map t) { + this(Math.max(2 * t.size(), 11), 0.75f); + putAll(t); + } + + /* -- Simple queries -- */ + + /** + * Returns the number of key-value mappings in this map. Note: + * In contrast with most implementations of the + * Map interface, the time required by this operation is + * linear in the size of the map. + */ + public int size() { + processQueue(); + return hash.size(); + } + + /** + * Returns true if this map contains no key-value mappings. + */ + public boolean isEmpty() { + processQueue(); + return hash.isEmpty(); + } + + /** + * Returns true if this map contains a mapping for the + * specified key. + * + * @param key + * The key whose presence in this map is to be tested. + */ + public boolean containsKey(Object key) { + processQueue(); + return hash.containsKey(key); + } + + /* -- Lookup and modification operations -- */ + + /** + * Returns the value to which this map maps the specified key. + * If this map does not contain a value for this key, then return + * null. + * + * @param key + * The key whose associated value, if any, is to be returned. + */ + public Object get(Object key) { + processQueue(); + SoftReference ref = (SoftReference)hash.get(key); + if (ref != null) + return ref.get(); + return null; + } + + /** + * Updates this map so that the given key maps to the given + * value. If the map previously contained a mapping for + * key then that mapping is replaced and the previous value + * is returned. + * + * @param key + * The key that is to be mapped to the given value + * @param value + * The value to which the given key is to be + * mapped + * + * @return The previous value to which this key was mapped, or + * null if if there was no mapping for the key + */ + public Object put(Object key, Object value) { + processQueue(); + Object rtn = hash.put(key, SoftValueRef.create(key, value, queue)); + if (rtn != null) + rtn = ((SoftReference)rtn).get(); + return rtn; + } + + /** + * Removes the mapping for the given key from this map, if + * present. + * + * @param key + * The key whose mapping is to be removed. + * + * @return The value to which this key was mapped, or null if + * there was no mapping for the key. + */ + public Object remove(Object key) { + processQueue(); + return hash.remove(key); + } + + /** + * Removes all mappings from this map. + */ + public void clear() { + processQueue(); + hash.clear(); + } } diff --git a/src/main/javassist/scopedpool/package.html b/src/main/javassist/scopedpool/package.html new file mode 100644 index 00000000..946e5e18 --- /dev/null +++ b/src/main/javassist/scopedpool/package.html @@ -0,0 +1,7 @@ + + +

A custom class pool for several JBoss products. +It is not part of Javassist. +

+ + -- 2.39.5